diff --git a/0002-crash-8.0.2-sw.patch b/0002-crash-8.0.2-sw.patch deleted file mode 100755 index 68dd712fde34ee8e4ceb0b0fc05bb6b701355f2e..0000000000000000000000000000000000000000 --- a/0002-crash-8.0.2-sw.patch +++ /dev/null @@ -1,3105 +0,0 @@ -diff -Nuar crash-8.0.2.org/Makefile crash-8.0.2.sw/Makefile ---- crash-8.0.2.org/Makefile 2022-03-14 07:58:52.278814120 +0000 -+++ crash-8.0.2.sw/Makefile 2022-03-15 06:11:27.978814120 +0000 -@@ -20,7 +20,7 @@ - PROGRAM=crash - - # --# Supported targets: X86 ALPHA PPC IA64 PPC64 SPARC64 -+# Supported targets: X86 SW_64 ALPHA PPC IA64 PPC64 SPARC64 - # TARGET and GDB_CONF_FLAGS will be configured automatically by configure - # - TARGET= -@@ -62,7 +62,7 @@ - CFILES=main.c tools.c global_data.c memory.c filesys.c help.c task.c \ - kernel.c test.c gdb_interface.c configure.c net.c dev.c bpf.c \ - printk.c \ -- alpha.c x86.c ppc.c ia64.c s390.c s390x.c s390dbf.c ppc64.c x86_64.c \ -+ sw_64.c alpha.c x86.c ppc.c ia64.c s390.c s390x.c s390dbf.c ppc64.c x86_64.c \ - arm.c arm64.c mips.c mips64.c sparc64.c \ - extensions.c remote.c va_server.c va_server_v1.c symbols.c cmdline.c \ - lkcd_common.c lkcd_v1.c lkcd_v2_v3.c lkcd_v5.c lkcd_v7.c lkcd_v8.c\ -@@ -82,7 +82,7 @@ - OBJECT_FILES=main.o tools.o global_data.o memory.o filesys.o help.o task.o \ - build_data.o kernel.o test.o gdb_interface.o net.o dev.o bpf.o \ - printk.o \ -- alpha.o x86.o ppc.o ia64.o s390.o s390x.o s390dbf.o ppc64.o x86_64.o \ -+ sw_64.o alpha.o x86.o ppc.o ia64.o s390.o s390x.o s390dbf.o ppc64.o x86_64.o \ - arm.o arm64.o mips.o mips64.o sparc64.o \ - extensions.o remote.o va_server.o va_server_v1.o symbols.o cmdline.o \ - lkcd_common.o lkcd_v1.o lkcd_v2_v3.o lkcd_v5.o lkcd_v7.o lkcd_v8.o \ -@@ -415,6 +415,9 @@ - x86.o: ${GENERIC_HFILES} ${REDHAT_HFILES} x86.c - ${CC} -c ${CRASH_CFLAGS} x86.c -DMCLX ${WARNING_OPTIONS} ${WARNING_ERROR} - -+sw_64.o: ${GENERIC_HFILES} sw_64.c -+ ${CC} -c ${CRASH_CFLAGS} sw_64.c ${WARNING_OPTIONS} ${WARNING_ERROR} -+ - alpha.o: ${GENERIC_HFILES} alpha.c - ${CC} -c ${CRASH_CFLAGS} alpha.c ${WARNING_OPTIONS} ${WARNING_ERROR} - -diff -Nuar crash-8.0.2.org/configure.c crash-8.0.2.sw/configure.c ---- crash-8.0.2.org/configure.c 2022-03-14 07:58:52.278814120 +0000 -+++ crash-8.0.2.sw/configure.c 2022-03-24 06:48:16.423873440 +0000 -@@ -107,6 +107,7 @@ - #undef MIPS - #undef SPARC64 - #undef MIPS64 -+#undef SW_64 - - #define UNKNOWN 0 - #define X86 1 -@@ -122,6 +123,7 @@ - #define MIPS 11 - #define SPARC64 12 - #define MIPS64 13 -+#define SW_64 14 - - #define TARGET_X86 "TARGET=X86" - #define TARGET_ALPHA "TARGET=ALPHA" -@@ -136,6 +138,7 @@ - #define TARGET_MIPS "TARGET=MIPS" - #define TARGET_MIPS64 "TARGET=MIPS64" - #define TARGET_SPARC64 "TARGET=SPARC64" -+#define TARGET_SW_64 "TARGET=SW_64" - - #define TARGET_CFLAGS_X86 "TARGET_CFLAGS=-D_FILE_OFFSET_BITS=64" - #define TARGET_CFLAGS_ALPHA "TARGET_CFLAGS=" -@@ -158,6 +161,7 @@ - #define TARGET_CFLAGS_MIPS_ON_X86_64 "TARGET_CFLAGS=-m32 -D_FILE_OFFSET_BITS=64" - #define TARGET_CFLAGS_MIPS64 "TARGET_CFLAGS=" - #define TARGET_CFLAGS_SPARC64 "TARGET_CFLAGS=" -+#define TARGET_CFLAGS_SW_64 "TARGET_CFLAGS=" - - #define GDB_TARGET_DEFAULT "GDB_CONF_FLAGS=" - #define GDB_TARGET_ARM_ON_X86 "GDB_CONF_FLAGS=--target=arm-elf-linux" -@@ -354,6 +358,9 @@ - static char buf[512]; - char *p; - -+#ifdef __sw_64__ -+ target_data.target = SW_64; -+#endif - #ifdef __alpha__ - target_data.target = ALPHA; - #endif -@@ -614,6 +621,9 @@ - case X86: - printf("TARGET: X86\n"); - break; -+ case SW_64: -+ printf("TARGET: SW_64\n"); -+ break; - case ALPHA: - printf("TARGET: ALPHA\n"); - break; -@@ -693,6 +703,10 @@ - } else - target_CFLAGS = TARGET_CFLAGS_X86; - break; -+ case SW_64: -+ target = TARGET_SW_64; -+ target_CFLAGS = TARGET_CFLAGS_SW_64; -+ break; - case ALPHA: - target = TARGET_ALPHA; - target_CFLAGS = TARGET_CFLAGS_ALPHA; -@@ -1364,7 +1378,7 @@ - printf("Vendor: Red Hat, Inc.\n"); - printf("Packager: Dave Anderson \n"); - printf("ExclusiveOS: Linux\n"); -- printf("ExclusiveArch: %%{ix86} alpha ia64 ppc ppc64 ppc64pseries ppc64iseries x86_64 s390 s390x arm aarch64 ppc64le mips mipsel mips64el sparc64\n"); -+ printf("ExclusiveArch: %%{ix86} sw_64 alpha ia64 ppc ppc64 ppc64pseries ppc64iseries x86_64 s390 s390x arm aarch64 ppc64le mips mipsel mips64el sparc64\n"); - printf("Buildroot: %%{_tmppath}/%%{name}-root\n"); - printf("BuildRequires: ncurses-devel zlib-devel bison\n"); - printf("Requires: binutils\n"); -@@ -1575,6 +1589,8 @@ - target_data.initial_gdb_target = X86_64; - else if (strncmp(buf, "X86", strlen("X86")) == 0) - target_data.initial_gdb_target = X86; -+ else if (strncmp(buf, "SW_64", strlen("SW_64")) == 0) -+ target_data.initial_gdb_target = SW_64; - else if (strncmp(buf, "ALPHA", strlen("ALPHA")) == 0) - target_data.initial_gdb_target = ALPHA; - else if (strncmp(buf, "PPC64", strlen("PPC64")) == 0) -@@ -1606,6 +1622,7 @@ - { - case X86: return("X86"); - case ALPHA: return("ALPHA"); -+ case SW_64: return("SW_64"); - case PPC: return("PPC"); - case IA64: return("IA64"); - case S390: return("S390"); -@@ -1633,6 +1650,10 @@ - return X86; - else if (strncmp(name, "x86", strlen("x86")) == 0) - return X86; -+ else if (strncmp(name, "SW_64", strlen("SW_64")) == 0) -+ return SW_64; -+ else if (strncmp(name, "sw_64", strlen("sw_64")) == 0) -+ return SW_64; - else if (strncmp(name, "ALPHA", strlen("ALPHA")) == 0) - return ALPHA; - else if (strncmp(name, "alpha", strlen("alpha")) == 0) -diff -Nuar crash-8.0.2.org/defs.h crash-8.0.2.sw/defs.h ---- crash-8.0.2.org/defs.h 2022-03-14 07:58:52.278814120 +0000 -+++ crash-8.0.2.sw/defs.h 2022-03-24 06:45:53.683873440 +0000 -@@ -69,13 +69,16 @@ - # define offsetof(TYPE, MEMBER) ((ulong)&((TYPE *)0)->MEMBER) - #endif - --#if !defined(X86) && !defined(X86_64) && !defined(ALPHA) && !defined(PPC) && \ -+#if !defined(X86) && !defined(X86_64) && !defined(ALPHA) && !defined(SW_64) && !defined(PPC) && \ - !defined(IA64) && !defined(PPC64) && !defined(S390) && !defined(S390X) && \ - !defined(ARM) && !defined(ARM64) && !defined(MIPS) && !defined(MIPS64) && \ - !defined(SPARC64) - #ifdef __alpha__ - #define ALPHA - #endif -+#ifdef __sw_64__ -+#define SW_64 -+#endif - #ifdef __i386__ - #define X86 - #endif -@@ -122,6 +125,9 @@ - #ifdef X86_64 - #define NR_CPUS (8192) - #endif -+#ifdef SW_64 -+#define NR_CPUS (64) -+#endif - #ifdef ALPHA - #define NR_CPUS (64) - #endif -@@ -3753,6 +3759,53 @@ - - #endif /* ALPHA */ - -+#ifdef SW_64 -+#define _64BIT_ -+#define MACHINE_TYPE "SW_64" -+ -+#define PAGEBASE(X) (((unsigned long)(X)) & (unsigned long)machdep->pagemask) -+ -+#define PTOV(X) ((unsigned long)(X)+(machdep->kvbase)) -+#define VTOP(X) ((unsigned long)(X)-(machdep->kvbase)) -+#define IS_VMALLOC_ADDR(X) (vt->vmalloc_start && (ulong)(X) >= vt->vmalloc_start) -+#define KSEG_BASE_48_BIT (0xffff800000000000) -+#define KSEG_BASE (0xfffffc0000000000) -+#define _PFN_MASK (0xFFFFFFFF00000000) -+#define VMALLOC_START (0xFFFFFE0000000000) -+#define MIN_SYMBOL_VALUE (KSEG_BASE_48_BIT) -+ -+#define PGDIR_SHIFT (PAGESHIFT() + 2*(PAGESHIFT()-3)) -+#define PMD_SHIFT (PAGESHIFT() + (PAGESHIFT()-3)) -+#define PTRS_PER_PAGE (1024) -+ -+#define PTRS_PER_PGD (1UL << (PAGESHIFT()-3)) -+ -+/* -+ * OSF/1 PAL-code-imposed page table bits -+ */ -+#define _PAGE_VALID 0x0001 -+#define _PAGE_FOR 0x0002 /* used for page protection (fault on read) */ -+#define _PAGE_FOW 0x0004 /* used for page protection (fault on write) */ -+#define _PAGE_FOE 0x0008 /* used for page protection (fault on exec) */ -+#define _PAGE_ASM 0x0010 -+#define _PAGE_KRE 0x0400 /* xxx - see below on the "accessed" bit */ -+#define _PAGE_URE 0x0800 /* xxx */ -+#define _PAGE_KWE 0x4000 /* used to do the dirty bit in software */ -+#define _PAGE_UWE 0x8000 /* used to do the dirty bit in software */ -+ -+/* .. and these are ours ... */ -+#define _PAGE_DIRTY 0x20000 -+#define _PAGE_ACCESSED 0x40000 -+ -+#define SWP_TYPE(entry) (((entry) >> 32) & 0xff) -+#define SWP_OFFSET(entry) ((entry) >> 40) -+#define __swp_type(entry) SWP_TYPE(entry) -+#define __swp_offset(entry) SWP_OFFSET(entry) -+ -+#define TIF_SIGPENDING (2) -+ -+#endif /* SW_64 */ -+ - #ifdef PPC - #define _32BIT_ - #define MACHINE_TYPE "PPC" -@@ -4428,6 +4481,10 @@ - #define MAX_HEXADDR_STRLEN (8) - #define UVADDR_PRLEN (8) - #endif -+#ifdef SW_64 -+#define MAX_HEXADDR_STRLEN (16) -+#define UVADDR_PRLEN (11) -+#endif - #ifdef ALPHA - #define MAX_HEXADDR_STRLEN (16) - #define UVADDR_PRLEN (11) -@@ -4641,6 +4698,12 @@ - #define SA_RESTORER 0x04000000 - #endif - -+#ifdef SW_64 -+#define SA_PROBE SA_ONESHOT -+#define SA_SAMPLE_RANDOM SA_RESTART -+#define SA_SHIRQ 0x40000000 -+#endif -+ - #ifdef ALPHA - #define SA_PROBE SA_ONESHOT - #define SA_SAMPLE_RANDOM SA_RESTART -@@ -5020,6 +5083,9 @@ - #ifdef X86 - #define machdep_init(X) x86_init(X) - #endif -+#ifdef SW_64 -+#define machdep_init(X) sw_64_init(X) -+#endif - #ifdef ALPHA - #define machdep_init(X) alpha_init(X) - #endif -@@ -5503,6 +5569,9 @@ - #ifdef X86 - #define dump_machdep_table(X) x86_dump_machdep_table(X) - #endif -+#ifdef SW_64 -+#define dump_machdep_table(X) sw_64_dump_machdep_table(X) -+#endif - #ifdef ALPHA - #define dump_machdep_table(X) alpha_dump_machdep_table(X) - #endif -@@ -5909,6 +5978,19 @@ - #endif - - /* -+ * sw_64.c -+ */ -+#ifdef SW_64 -+void sw_64_init(int); -+void sw_64_dump_machdep_table(ulong); -+#define display_idt_table() \ -+ error(FATAL, "-d option is not applicable to sw_64 architecture\n") -+ -+#define HWRESET_TASK(X) ((machdep->flags & HWRESET) && is_task_active(X) && \ -+ (task_to_context(X)->processor == 0)) -+#endif -+ -+/* - * alpha.c - */ - #ifdef ALPHA -diff -Nuar crash-8.0.2.org/gdb_interface.c crash-8.0.2.sw/gdb_interface.c ---- crash-8.0.2.org/gdb_interface.c 2022-03-14 07:58:52.288814120 +0000 -+++ crash-8.0.2.sw/gdb_interface.c 2022-03-14 09:10:49.778814120 +0000 -@@ -1053,7 +1053,7 @@ - return TRUE; - } - --#ifndef ALPHA -+#if !defined ALPHA && !defined SW_64 - /* - * Stub routine needed for resolution by non-alpha, modified gdb code. - */ -diff -Nuar crash-8.0.2.org/lkcd_v2_v3.c crash-8.0.2.sw/lkcd_v2_v3.c ---- crash-8.0.2.org/lkcd_v2_v3.c 2022-03-14 07:58:52.288814120 +0000 -+++ crash-8.0.2.sw/lkcd_v2_v3.c 2022-03-24 07:10:23.603873440 +0000 -@@ -336,7 +336,7 @@ - lkcd_print(" dha_esp: %lx\n", dha->dha_esp); - lkcd_print(" dha_eip: %lx\n", dha->dha_eip); - #endif --#if defined PPC || ALPHA || IA64 -+#if defined PPC || ALPHA || SW_64 || IA64 - /* TBD */ - #endif - lkcd_print(" dha_regs:\n"); -@@ -362,7 +362,38 @@ - lkcd_print(" esp: %lx\n", dha->dha_regs.esp); - lkcd_print(" xss: %x\n", dha->dha_regs.xss); - #endif --#ifdef ALPHA -+#if defined ALPHA -+ lkcd_print(" r0: %lx\n", dha->dha_regs.r0); -+ lkcd_print(" r1: %lx\n", dha->dha_regs.r1); -+ lkcd_print(" r2: %lx\n", dha->dha_regs.r2); -+ lkcd_print(" r3: %lx\n", dha->dha_regs.r3); -+ lkcd_print(" r4: %lx\n", dha->dha_regs.r4); -+ lkcd_print(" r5: %lx\n", dha->dha_regs.r5); -+ lkcd_print(" r6: %lx\n", dha->dha_regs.r6); -+ lkcd_print(" r7: %lx\n", dha->dha_regs.r7); -+ lkcd_print(" r8: %lx\n", dha->dha_regs.r8); -+ lkcd_print(" r19: %lx\n", dha->dha_regs.r19); -+ lkcd_print(" r20: %lx\n", dha->dha_regs.r20); -+ lkcd_print(" r21: %lx\n", dha->dha_regs.r21); -+ lkcd_print(" r22: %lx\n", dha->dha_regs.r22); -+ lkcd_print(" r23: %lx\n", dha->dha_regs.r23); -+ lkcd_print(" r24: %lx\n", dha->dha_regs.r24); -+ lkcd_print(" r25: %lx\n", dha->dha_regs.r25); -+ lkcd_print(" r26: %lx\n", dha->dha_regs.r26); -+ lkcd_print(" r27: %lx\n", dha->dha_regs.r27); -+ lkcd_print(" r28: %lx\n", dha->dha_regs.r28); -+ lkcd_print(" hae: %lx\n", dha->dha_regs.hae); -+ lkcd_print(" trap_a0: %lx\n", dha->dha_regs.trap_a0); -+ lkcd_print(" trap_a1: %lx\n", dha->dha_regs.trap_a1); -+ lkcd_print(" trap_a2: %lx\n", dha->dha_regs.trap_a2); -+ lkcd_print(" ps: %lx\n", dha->dha_regs.ps); -+ lkcd_print(" pc: %lx\n", dha->dha_regs.pc); -+ lkcd_print(" gp: %lx\n", dha->dha_regs.gp); -+ lkcd_print(" r16: %lx\n", dha->dha_regs.r16); -+ lkcd_print(" r17: %lx\n", dha->dha_regs.r17); -+ lkcd_print(" r18: %lx\n", dha->dha_regs.r18); -+#endif -+#if defined SW_64 - lkcd_print(" r0: %lx\n", dha->dha_regs.r0); - lkcd_print(" r1: %lx\n", dha->dha_regs.r1); - lkcd_print(" r2: %lx\n", dha->dha_regs.r2); -diff -Nuar crash-8.0.2.org/lkcd_vmdump_v2_v3.h crash-8.0.2.sw/lkcd_vmdump_v2_v3.h ---- crash-8.0.2.org/lkcd_vmdump_v2_v3.h 2022-03-14 07:58:52.288814120 +0000 -+++ crash-8.0.2.sw/lkcd_vmdump_v2_v3.h 2022-03-24 06:53:52.563873440 +0000 -@@ -98,7 +98,7 @@ - - #endif /* ARM || X86 || PPC */ - --#if defined(ALPHA) || defined(IA64) || defined(X86_64) || defined(PPC64) -+#if defined(ALPHA) || defined(SW_64) || defined(IA64) || defined(X86_64) || defined(PPC64) - - /* - * Plug in the real ../arch/alpha/vmdump.h when available. For now the -diff -Nuar crash-8.0.2.org/sw_64.c crash-8.0.2.sw/sw_64.c ---- crash-8.0.2.org/sw_64.c 1970-01-01 00:00:00.000000000 +0000 -+++ crash-8.0.2.sw/sw_64.c 2022-03-24 07:15:25.743873440 +0000 -@@ -0,0 +1,2733 @@ -+/* sw_64.c - core analysis suite -+ * -+ * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. -+ * Copyright (C) 2002-2006, 2010-2013 David Anderson -+ * Copyright (C) 2002-2006, 2010-2013 Red Hat, Inc. All rights reserved. -+ * -+ * 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 2 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. -+ * -+ */ -+#ifdef SW_64 -+#include "defs.h" -+ -+static void sw_64_back_trace(struct gnu_request *, struct bt_info *); -+static int sw_64_trace_status(struct gnu_request *, struct bt_info *); -+static void sw_64_exception_frame(ulong, ulong, -+ struct gnu_request *, struct bt_info *); -+static void sw_64_frame_offset(struct gnu_request *, ulong); -+static int sw_64_backtrace_resync(struct gnu_request *, ulong, -+ struct bt_info *); -+static void sw_64_print_stack_entry(struct gnu_request *, ulong, -+ char *, ulong, struct bt_info *); -+static int sw_64_resync_speculate(struct gnu_request *, ulong,struct bt_info *); -+static int sw_64_dis_filter(ulong, char *, unsigned int); -+static void dis_address_translation(ulong, char *, unsigned int); -+static void sw_64_cmd_mach(void); -+static int sw_64_get_smp_cpus(void); -+static void sw_64_display_machine_stats(void); -+static void sw_64_dump_line_number(char *, ulong); -+static void display_hwrpb(unsigned int); -+static void sw_64_post_init(void); -+static struct line_number_hook sw_64_line_number_hooks[]; -+ -+ -+#define SW_64_CONTINUE_TRACE (1) -+#define SW_64_END_OF_TRACE (2) -+#define SW_64_EXCEPTION_FRAME (3) -+#define SW_64_SYSCALL_FRAME (4) -+#define SW_64_MM_FAULT (5) -+#define SW_64_INTERRUPT_PENDING (6) -+#define SW_64_RESCHEDULE (7) -+#define SW_64_DOWN_FAILED (8) -+#define SW_64_RET_FROM_SMP_FORK (9) -+#define SW_64_SIGNAL_RETURN (10) -+#define SW_64_STRACE (11) -+ -+static int sw_64_eframe_search(struct bt_info *); -+static int sw_64_uvtop(struct task_context *, ulong, physaddr_t *, int); -+static int sw_64_kvtop(struct task_context *, ulong, physaddr_t *, int); -+static void sw_64_back_trace_cmd(struct bt_info *); -+static ulong sw_64_get_task_pgd(ulong task); -+static ulong sw_64_processor_speed(void); -+static void sw_64_dump_irq(int); -+static void sw_64_get_stack_frame(struct bt_info *, ulong *, ulong *); -+static void get_sw_64_frame(struct bt_info *, ulong *, ulong *); -+static int verify_user_eframe(struct bt_info *, ulong, ulong); -+static int sw_64_translate_pte(ulong, void *, ulonglong); -+static uint64_t sw_64_memory_size(void); -+static ulong sw_64_vmalloc_start(void); -+static int sw_64_is_task_addr(ulong); -+static int sw_64_verify_symbol(const char *, ulong, char); -+ -+struct percpu_data { -+ ulong halt_PC; -+ ulong halt_ra; -+ ulong halt_pv; -+}; -+#define GET_HALT_PC 0x1 -+#define GET_HALT_RA 0x2 -+#define GET_HALT_PV 0x3 -+static ulong get_percpu_data(int, ulong, struct percpu_data *); -+ -+/* -+ * Do all necessary machine-specific setup here. This is called three times, -+ * before symbol table initialization, and before and after GDB has been -+ * initialized. -+ */ -+void -+sw_64_init(int when) -+{ -+ int tmp; -+ -+ switch (when) -+ { -+ case PRE_SYMTAB: -+ machdep->verify_symbol = sw_64_verify_symbol; -+ if (pc->flags & KERNEL_DEBUG_QUERY) -+ return; -+ machdep->pagesize = memory_page_size(); -+ machdep->pageshift = ffs(machdep->pagesize) - 1; -+ machdep->pageoffset = machdep->pagesize - 1; -+ machdep->pagemask = ~(machdep->pageoffset); -+ machdep->stacksize = machdep->pagesize * 2; -+ if ((machdep->pgd = (char *)malloc(PAGESIZE())) == NULL) -+ error(FATAL, "cannot malloc pgd space."); -+ if ((machdep->pmd = (char *)malloc(PAGESIZE())) == NULL) -+ error(FATAL, "cannot malloc pmd space."); -+ if ((machdep->ptbl = (char *)malloc(PAGESIZE())) == NULL) -+ error(FATAL, "cannot malloc ptbl space."); -+ machdep->last_pgd_read = 0; -+ machdep->last_pmd_read = 0; -+ machdep->last_ptbl_read = 0; -+ machdep->verify_paddr = generic_verify_paddr; -+ machdep->ptrs_per_pgd = PTRS_PER_PGD; -+ break; -+ -+ case PRE_GDB: -+ switch (symbol_value("_stext") & KSEG_BASE) -+ { -+ case KSEG_BASE: -+ machdep->kvbase = KSEG_BASE; -+ break; -+ -+ case KSEG_BASE_48_BIT: -+ machdep->kvbase = KSEG_BASE_48_BIT; -+ break; -+ -+ default: -+ error(FATAL, -+ "cannot determine KSEG base from _stext: %lx\n", -+ symbol_value("_stext")); -+ } -+ -+ machdep->identity_map_base = machdep->kvbase; -+ machdep->is_kvaddr = generic_is_kvaddr; -+ machdep->is_uvaddr = generic_is_uvaddr; -+ machdep->eframe_search = sw_64_eframe_search; -+ machdep->back_trace = sw_64_back_trace_cmd; -+ machdep->processor_speed = sw_64_processor_speed; -+ machdep->uvtop = sw_64_uvtop; -+ machdep->kvtop = sw_64_kvtop; -+ machdep->get_task_pgd = sw_64_get_task_pgd; -+ if (symbol_exists("irq_desc")) -+ machdep->dump_irq = generic_dump_irq; -+ else -+ machdep->dump_irq = sw_64_dump_irq; -+ machdep->get_stack_frame = sw_64_get_stack_frame; -+ machdep->get_stackbase = generic_get_stackbase; -+ machdep->get_stacktop = generic_get_stacktop; -+ machdep->translate_pte = sw_64_translate_pte; -+ machdep->memory_size = sw_64_memory_size; -+ machdep->vmalloc_start = sw_64_vmalloc_start; -+ machdep->is_task_addr = sw_64_is_task_addr; -+ if (symbol_exists("console_crash")) { -+ get_symbol_data("console_crash", sizeof(int), &tmp); -+ if (tmp) -+ machdep->flags |= HWRESET; -+ } -+ machdep->dis_filter = sw_64_dis_filter; -+ machdep->cmd_mach = sw_64_cmd_mach; -+ machdep->get_smp_cpus = sw_64_get_smp_cpus; -+ machdep->line_number_hooks = sw_64_line_number_hooks; -+ machdep->value_to_symbol = generic_machdep_value_to_symbol; -+ machdep->init_kernel_pgd = NULL; -+ break; -+ -+ case POST_GDB: -+ MEMBER_OFFSET_INIT(thread_struct_ptbr, -+ "thread_struct", "ptbr"); -+ MEMBER_OFFSET_INIT(hwrpb_struct_cycle_freq, -+ "hwrpb_struct", "cycle_freq"); -+ MEMBER_OFFSET_INIT(hwrpb_struct_processor_offset, -+ "hwrpb_struct", "processor_offset"); -+ MEMBER_OFFSET_INIT(hwrpb_struct_processor_size, -+ "hwrpb_struct", "processor_size"); -+ MEMBER_OFFSET_INIT(percpu_struct_halt_PC, -+ "percpu_struct", "halt_PC"); -+ MEMBER_OFFSET_INIT(percpu_struct_halt_ra, -+ "percpu_struct", "halt_ra"); -+ MEMBER_OFFSET_INIT(percpu_struct_halt_pv, -+ "percpu_struct", "halt_pv"); -+ MEMBER_OFFSET_INIT(switch_stack_r26, -+ "switch_stack", "r26"); -+ if (symbol_exists("irq_action")) -+ ARRAY_LENGTH_INIT(machdep->nr_irqs, irq_action, -+ "irq_action", NULL, 0); -+ else if (symbol_exists("irq_desc")) -+ ARRAY_LENGTH_INIT(machdep->nr_irqs, irq_desc, -+ "irq_desc", NULL, 0); -+ else -+ machdep->nr_irqs = 0; -+ if (!machdep->hz) -+ machdep->hz = HZ; -+ break; -+ -+ case POST_INIT: -+ sw_64_post_init(); -+ break; -+ } -+} -+ -+/* -+ * Unroll a kernel stack. -+ */ -+static void -+sw_64_back_trace_cmd(struct bt_info *bt) -+{ -+ char buf[BUFSIZE]; -+ struct gnu_request *req; -+ -+ bt->flags |= BT_EXCEPTION_FRAME; -+ -+ if (CRASHDEBUG(1) || bt->debug) -+ fprintf(fp, " => PC: %lx (%s) FP: %lx \n", -+ bt->instptr, value_to_symstr(bt->instptr, buf, 0), -+ bt->stkptr ); -+ -+ req = (struct gnu_request *)GETBUF(sizeof(struct gnu_request)); -+ req->command = GNU_STACK_TRACE; -+ req->flags = GNU_RETURN_ON_ERROR; -+ req->buf = GETBUF(BUFSIZE); -+ req->debug = bt->debug; -+ req->task = bt->task; -+ -+ req->pc = bt->instptr; -+ req->sp = bt->stkptr; -+ -+ if (bt->flags & BT_USE_GDB) { -+ strcpy(req->buf, "backtrace"); -+ gdb_interface(req); -+ } -+ else -+ sw_64_back_trace(req, bt); -+ -+ FREEBUF(req->buf); -+ FREEBUF(req); -+} -+ -+ -+/* -+ * Unroll the kernel stack. -+ */ -+ -+#define SW_64_BACKTRACE_SPECULATE(X) \ -+{ \ -+ speculate_location = X; \ -+ \ -+ if (bt->flags & BT_SPECULATE) \ -+ return; \ -+ \ -+ BZERO(btloc, sizeof(struct bt_info)); \ -+ btloc->task = req->task; \ -+ btloc->tc = bt->tc; \ -+ btloc->stackbase = bt->stackbase; \ -+ btloc->stacktop = bt->stacktop; \ -+ btloc->flags = BT_TEXT_SYMBOLS_NOPRINT; \ -+ hook.eip = 0; \ -+ hook.esp = req->lastsp ? req->lastsp + sizeof(long) : 0; \ -+ btloc->hp = &hook; \ -+ \ -+ back_trace(btloc); \ -+ \ -+ if (hook.esp && hook.eip) { \ -+ req->hookp = &hook; \ -+ if (sw_64_resync_speculate(req, bt->flags, bt)) { \ -+ req->pc = hook.eip; \ -+ req->sp = hook.esp; \ -+ continue; \ -+ } \ -+ goto show_remaining_text; \ -+ } \ -+ goto show_remaining_text; \ -+} -+ -+ -+static void -+sw_64_back_trace(struct gnu_request *req, struct bt_info *bt) -+{ -+ char buf[BUFSIZE]; -+ int frame; -+ int done; -+ int status; -+ struct stack_hook hook; -+ int eframe_same_pc_ra_function; -+ int speculate_location; -+ struct bt_info bt_info, *btloc; -+ -+ frame = 0; -+ req->curframe = 0; -+ btloc = &bt_info; -+ -+ if (!IS_KVADDR(req->pc)) { -+ if (BT_REFERENCE_CHECK(bt)) -+ return; -+ -+ if ((machdep->flags & HWRESET) && is_task_active(req->task)) { -+ fprintf(fp, "(hardware reset while in user space)\n"); -+ return; -+ } -+ -+ fprintf(fp, "invalid pc: %lx\n", req->pc); -+ -+ sw_64_exception_frame(USER_EFRAME_ADDR(req->task), -+ BT_USER_EFRAME, req, bt); -+ -+ return; -+ } -+ -+ -+ for (done = FALSE; !done && (frame < 100); frame++) { -+ -+ speculate_location = 0; -+ -+ if ((req->name = closest_symbol(req->pc)) == NULL) { -+ req->ra = req->pc = 0; -+ if (sw_64_backtrace_resync(req, -+ bt->flags | BT_FROM_CALLFRAME, bt)) -+ continue; -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ SW_64_BACKTRACE_SPECULATE(1); -+ } -+ -+ if (!INSTACK(req->sp, bt)) -+ break; -+ -+ if (!is_kernel_text(req->pc)) -+ SW_64_BACKTRACE_SPECULATE(2); -+ -+ sw_64_print_stack_entry(req, req->pc, req->name, -+ bt->flags | BT_SAVE_LASTSP, bt); -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ switch (status = sw_64_trace_status(req, bt)) -+ { -+ case SW_64_CONTINUE_TRACE: -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ done = TRUE; -+ break; -+ } -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ break; -+ -+ case SW_64_END_OF_TRACE: -+ done = TRUE; -+ break; -+ -+ case SW_64_STRACE: -+ sw_64_exception_frame(req->sp, -+ BT_USER_EFRAME|BT_STRACE, req, bt); -+ done = TRUE; -+ break; -+ -+ case SW_64_RET_FROM_SMP_FORK: -+ sw_64_exception_frame(USER_EFRAME_ADDR(req->task), -+ BT_USER_EFRAME|BT_RET_FROM_SMP_FORK, req, bt); -+ done = TRUE; -+ break; -+ -+ case SW_64_DOWN_FAILED: -+ frame++; -+ sw_64_print_stack_entry(req, -+ req->pc, closest_symbol(req->pc), -+ bt->flags | BT_SAVE_LASTSP, bt); -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ done = TRUE; -+ break; -+ } -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ break; -+ -+ case SW_64_RESCHEDULE: -+ sw_64_exception_frame(USER_EFRAME_ADDR(req->task), -+ BT_USER_EFRAME|BT_RESCHEDULE, req, bt); -+ done = TRUE; -+ break; -+ -+ case SW_64_MM_FAULT: -+ sw_64_exception_frame(req->sp, bt->flags, req, bt); -+ -+ if (!IS_KVADDR(req->pc)) { -+ done = TRUE; -+ break; -+ } -+ -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ done = TRUE; -+ break; -+ } -+ -+ frame++; -+ sw_64_print_stack_entry(req, -+ req->pc, closest_symbol(req->pc), -+ bt->flags | BT_SAVE_LASTSP, bt); -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ if (!IS_KVADDR(req->pc)) { -+ done = TRUE; -+ break; -+ } -+ -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ break; -+ -+ case SW_64_SYSCALL_FRAME: -+ req->sp = verify_user_eframe(bt, req->task, req->sp) ? -+ req->sp : USER_EFRAME_ADDR(req->task); -+ -+ sw_64_exception_frame(req->sp, bt->flags, req, bt); -+ -+ if (!IS_KVADDR(req->pc)) { -+ done = TRUE; -+ break; -+ } -+ -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ done = TRUE; -+ break; -+ } -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ break; -+ -+ case SW_64_SIGNAL_RETURN: -+ sw_64_exception_frame(USER_EFRAME_ADDR(req->task), -+ bt->flags, req, bt); -+ done = TRUE; -+ break; -+ -+ case SW_64_EXCEPTION_FRAME: -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ fprintf(fp, -+ "SW_64 EXCEPTION FRAME w/no frame offset for %lx (%s)\n", -+ req->pc, -+ value_to_symstr(req->pc, buf, 0)); -+ done = TRUE; -+ break; -+ } -+ -+ sw_64_exception_frame(req->sp + req->value, -+ bt->flags, req, bt); -+ -+ if (!IS_KVADDR(req->pc)) { -+ done = TRUE; -+ break; -+ } -+ -+ sw_64_frame_offset(req, 0); -+ -+ if (!req->value) { -+ fprintf(fp, -+ "SW_64 EXCEPTION FRAME w/no frame offset for %lx (%s)\n", -+ req->pc, -+ value_to_symstr(req->pc, buf, 0)); -+ done = TRUE; -+ break; -+ } -+ -+ eframe_same_pc_ra_function = -+ SAME_FUNCTION(req->pc, req->ra); -+ -+ frame++; -+ sw_64_print_stack_entry(req, req->pc, -+ closest_symbol(req->pc), -+ bt->flags | BT_SAVE_LASTSP, bt); -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ if (!IS_KVADDR(req->pc)) { -+ done = TRUE; -+ break; -+ } -+ -+ if (STREQ(closest_symbol(req->pc), -+ "ret_from_reschedule")) { -+ sw_64_exception_frame( -+ USER_EFRAME_ADDR(req->task), -+ BT_USER_EFRAME|BT_RESCHEDULE, req, bt); -+ done = TRUE; -+ break; -+ } -+ -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ -+ if (!is_kernel_text(req->pc)) { -+ if (sw_64_backtrace_resync(req, -+ bt->flags | BT_FROM_EXCEPTION, bt)) -+ break; -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return; -+ -+ SW_64_BACKTRACE_SPECULATE(3); -+ } -+ -+ if (!eframe_same_pc_ra_function && -+ (req->pc != req->ra)) { -+ req->pc = req->ra; -+ break; -+ } -+ -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ break; -+ -+ case SW_64_INTERRUPT_PENDING: -+ sw_64_frame_offset(req, 0); -+ if (!req->value) { -+ req->prevpc = req->pc; -+ req->pc = req->addr; -+ req->prevsp = req->sp; -+ req->sp = req->frame; -+ } else { -+ req->prevpc = req->pc; -+ req->pc = GET_STACK_ULONG(req->sp); -+ req->prevsp = req->sp; -+ req->sp += req->value; -+ } -+ break; -+ } -+ } -+ -+ return; -+ -+show_remaining_text: -+ -+ if (BT_REFERENCE_CHECK(bt)) -+ return; -+ -+ BZERO(btloc, sizeof(struct bt_info)); -+ btloc->task = req->task; -+ btloc->tc = bt->tc; -+ btloc->stackbase = bt->stackbase; -+ btloc->stacktop = bt->stacktop; -+ btloc->flags = BT_TEXT_SYMBOLS_NOPRINT; -+ hook.esp = req->lastsp + sizeof(long); -+ btloc->hp = &hook; -+ back_trace(btloc); -+ -+ if (hook.eip) { -+ fprintf(fp, -+"NOTE: cannot resolve trace from this point -- remaining text symbols on stack:\n"); -+ btloc->flags = BT_TEXT_SYMBOLS_PRINT|BT_ERROR_MASK; -+ hook.esp = req->lastsp + sizeof(long); -+ back_trace(btloc); -+ } else -+ fprintf(fp, -+"NOTE: cannot resolve trace from this point -- no remaining text symbols\n"); -+ -+ if (CRASHDEBUG(1)) -+ fprintf(fp, "speculate_location: %d\n", speculate_location); -+ -+ sw_64_exception_frame(USER_EFRAME_ADDR(req->task), -+ BT_USER_EFRAME, req, bt); -+} -+ -+/* -+ * print one entry of a stack trace -+ */ -+static void -+sw_64_print_stack_entry(struct gnu_request *req, -+ ulong callpc, -+ char *name, -+ ulong flags, -+ struct bt_info *bt) -+{ -+ struct load_module *lm; -+ -+ if (BT_REFERENCE_CHECK(bt)) { -+ switch (bt->ref->cmdflags & (BT_REF_SYMBOL|BT_REF_HEXVAL)) -+ { -+ case BT_REF_SYMBOL: -+ if (STREQ(name, bt->ref->str) || -+ (STREQ(name, "strace") && -+ STREQ(bt->ref->str, "entSys"))) { -+ bt->ref->cmdflags |= BT_REF_FOUND; -+ } -+ break; -+ -+ case BT_REF_HEXVAL: -+ if (bt->ref->hexval == callpc) -+ bt->ref->cmdflags |= BT_REF_FOUND; -+ break; -+ } -+ } else { -+ fprintf(fp, "%s#%d [%lx] %s at %lx", -+ req->curframe < 10 ? " " : "", req->curframe, req->sp, -+ STREQ(name, "strace") ? "strace (via entSys)" : name, -+ callpc); -+ if (module_symbol(callpc, NULL, &lm, NULL, 0)) -+ fprintf(fp, " [%s]", lm->mod_name); -+ fprintf(fp, "\n"); -+ } -+ -+ if (!(flags & BT_SPECULATE)) -+ req->curframe++; -+ -+ if (flags & BT_SAVE_LASTSP) -+ req->lastsp = req->sp; -+ -+ if (BT_REFERENCE_CHECK(bt)) -+ return; -+ -+ if (flags & BT_LINE_NUMBERS) -+ sw_64_dump_line_number(name, callpc); -+} -+ -+static const char *hook_files[] = { -+ "arch/sw_64/kernel/entry.S", -+ "arch/sw_64/kernel/head.S", -+ "init/main.c", -+ "arch/sw_64/kernel/smp.c", -+}; -+ -+#define ENTRY_S ((char **)&hook_files[0]) -+#define HEAD_S ((char **)&hook_files[1]) -+#define MAIN_C ((char **)&hook_files[2]) -+#define SMP_C ((char **)&hook_files[3]) -+ -+static struct line_number_hook sw_64_line_number_hooks[] = { -+ {"entInt", ENTRY_S}, -+ {"entMM", ENTRY_S}, -+ {"entArith", ENTRY_S}, -+ {"entIF", ENTRY_S}, -+ {"entDbg", ENTRY_S}, -+ {"kernel_clone", ENTRY_S}, -+ {"kernel_thread", ENTRY_S}, -+ {"__kernel_execve", ENTRY_S}, -+ {"do_switch_stack", ENTRY_S}, -+ {"undo_switch_stack", ENTRY_S}, -+ {"entUna", ENTRY_S}, -+ {"entUnaUser", ENTRY_S}, -+ {"sys_fork", ENTRY_S}, -+ {"sys_clone", ENTRY_S}, -+ {"sys_vfork", ENTRY_S}, -+ {"sw_64_switch_to", ENTRY_S}, -+ {"entSys", ENTRY_S}, -+ {"ret_from_sys_call", ENTRY_S}, -+ {"ret_from_reschedule", ENTRY_S}, -+ {"restore_all", ENTRY_S}, -+ {"strace", ENTRY_S}, -+ {"strace_success", ENTRY_S}, -+ {"strace_error", ENTRY_S}, -+ {"syscall_error", ENTRY_S}, -+ {"ret_success", ENTRY_S}, -+ {"signal_return", ENTRY_S}, -+ {"ret_from_fork", ENTRY_S}, -+ {"reschedule", ENTRY_S}, -+ {"sys_sigreturn", ENTRY_S}, -+ {"sys_rt_sigreturn", ENTRY_S}, -+ {"sys_sigsuspend", ENTRY_S}, -+ {"sys_rt_sigsuspend", ENTRY_S}, -+ {"ret_from_smpfork", ENTRY_S}, -+ -+ {"_stext", HEAD_S}, -+ {"__start", HEAD_S}, -+ {"__smp_callin", HEAD_S}, -+ {"cserve_ena", HEAD_S}, -+ {"cserve_dis", HEAD_S}, -+ {"halt", HEAD_S}, -+ -+ {"start_kernel", MAIN_C}, -+ -+ {"smp_callin", SMP_C}, -+ -+ {NULL, NULL} /* list must be NULL-terminated */ -+}; -+ -+static void -+sw_64_dump_line_number(char *name, ulong callpc) -+{ -+ char buf[BUFSIZE], *p; -+ int retries; -+ -+ retries = 0; -+try_closest: -+ get_line_number(callpc, buf, FALSE); -+ if (strlen(buf)) { -+ if (retries) { -+ p = strstr(buf, ": "); -+ if (p) -+ *p = NULLCHAR; -+ } -+ fprintf(fp, " %s\n", buf); -+ } else { -+ if (retries) -+ fprintf(fp, GDB_PATCHED() ? -+ "" : " (cannot determine file and line number)\n"); -+ else { -+ retries++; -+ callpc = closest_symbol_value(callpc); -+ goto try_closest; -+ } -+ } -+} -+ -+ -+/* -+ * Look for the frame size storage at the beginning of a function. -+ * If it's not obvious, try gdb. -+ * -+ * For future reference, here's where the numbers come from: -+ * -+ * 0xfffffc00003217e8 : subq sp,0x50,sp -+ * fffffc00003217e8: 43ca153e -+ * 010000 11110 01010000 1 0101001 11110 -+ * -+ * 0xfffffc0000321668 : subq sp,0x60,sp -+ * fffffc0000321668: 43cc153e -+ * 010000 11110 01100000 1 0101001 11110 -+ * -+ * 0xfffffc000035d028 : subq sp,0x70,sp -+ * fffffc000035d028: 43ce153e -+ * 010000 11110 01110000 1 0101001 11110 -+ * -+ * 0100 0011 110x xxxx xxx1 0101 0011 1110 -+ * 1111 1111 111x xxxx xxx1 1111 1111 1111 -+ * 0000 0000 0001 1111 1110 0000 0000 0000 -+ * f f e 0 1 f f f instruction mask -+ * 0 0 1 f e 0 0 0 offset -+ * -+ * stq ra,0(sp) -+ * fffffc000035d034: b75e0000 -+ */ -+ -+static void -+sw_64_frame_offset(struct gnu_request *req, ulong alt_pc) -+{ -+ uint *ip, ival; -+ ulong value; -+ -+ req->value = value = 0; -+ -+ if (alt_pc && !is_kernel_text(alt_pc)) -+ error(FATAL, -+ "trying to get frame offset of non-text address: %lx\n", -+ alt_pc); -+ else if (!alt_pc && !is_kernel_text(req->pc)) -+ error(FATAL, -+ "trying to get frame offset of non-text address: %lx\n", -+ req->pc); -+ -+ ip = alt_pc ? (int *)closest_symbol_value(alt_pc) : -+ (int *)closest_symbol_value(req->pc); -+ if (!ip) -+ goto use_gdb; -+ -+ ival = 0; -+ -+ /* -+ * Don't go any farther than "stq ra,0(sp)" (0xb75e0000) -+ */ -+ while (ival != 0xb75e0000) { -+ if (!text_value_cache((ulong)ip, 0, &ival)) { -+ readmem((ulong)ip, KVADDR, &ival, -+ sizeof(uint), "uncached text value", -+ FAULT_ON_ERROR); -+ text_value_cache((ulong)ip, ival, NULL); -+ } -+ -+ if ((ival & 0xffe01fff) == 0x43c0153e) { -+ value = (ival & 0x1fe000) >> 13; -+ break; -+ } -+ ip++; -+ } -+ -+ if (value) { -+ req->value = value; -+ return; -+ } -+ -+use_gdb: -+#ifndef GDB_5_3 -+{ -+ static int gdb_frame_offset_warnings = 10; -+ -+ if (gdb_frame_offset_warnings-- > 0) -+ error(WARNING, -+ "GNU_ALPHA_FRAME_OFFSET functionality not ported to gdb\n"); -+} -+#endif -+ req->command = GNU_ALPHA_FRAME_OFFSET; -+ if (alt_pc) { -+ ulong pc_save; -+ pc_save = req->pc; -+ req->pc = alt_pc; -+ gdb_interface(req); -+ req->pc = pc_save; -+ } else -+ gdb_interface(req); -+} -+ -+/* -+ * Look for key routines that either mean the trace has ended or has -+ * bumped into an exception frame. -+ */ -+int -+sw_64_trace_status(struct gnu_request *req, struct bt_info *bt) -+{ -+ ulong value; -+ char *func; -+ ulong frame; -+ -+ req->addr = 0; -+ func = req->name; -+ frame = req->sp; -+ -+ if (STREQ(func, "start_kernel") || -+ STREQ(func, "smp_callin") || -+ STREQ(func, "kernel_thread") || -+ STREQ(func, "__kernel_thread")) -+ return SW_64_END_OF_TRACE; -+ -+ if (STREQ(func, "ret_from_smp_fork") || -+ STREQ(func, "ret_from_smpfork")) -+ return SW_64_RET_FROM_SMP_FORK; -+ -+ if (STREQ(func, "entSys")) -+ return SW_64_SYSCALL_FRAME; -+ -+ if (STREQ(func, "entMM")) { -+ req->sp += 56; /* see entMM in entry.S */ -+ return SW_64_MM_FAULT; -+ } -+ -+ if (STREQ(func, "do_entInt")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "do_entArith")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "do_entIF")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "do_entDbg")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "handle_bottom_half")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "handle_softirq")) -+ return SW_64_EXCEPTION_FRAME; -+ -+ if (STREQ(func, "reschedule")) -+ return SW_64_RESCHEDULE; -+ -+ if (STREQ(func, "ret_from_reschedule")) -+ return SW_64_RESCHEDULE; -+ -+ if (STREQ(func, "signal_return")) -+ return SW_64_SIGNAL_RETURN; -+ -+ if (STREQ(func, "strace")) -+ return SW_64_STRACE; -+ -+ if (STREQ(func, "__down_failed") || -+ STREQ(func, "__down_failed_interruptible")) { -+ readmem(req->sp + 144, KVADDR, &req->pc, sizeof(ulong), -+ "__down_failed r26", FAULT_ON_ERROR); -+ req->sp += 160; -+ return SW_64_DOWN_FAILED; -+ } -+ -+ value = GET_STACK_ULONG(frame); -+ -+ if (STREQ(closest_symbol(value), "do_entInt") || -+ STREQ(closest_symbol(value), "do_entArith") || -+ STREQ(closest_symbol(value), "do_entIF") || -+ STREQ(closest_symbol(value), "do_entDbg")) { -+ req->addr = value; -+ req->frame = 0; -+ -+ while (INSTACK(frame, bt)) { -+ frame += sizeof(ulong); -+ value = GET_STACK_ULONG(frame); -+ if (STREQ(closest_symbol(value), "ret_from_sys_call")) { -+ sw_64_frame_offset(req, req->addr); -+ /* req->frame = frame + req->value; XXX */ -+ break; -+ } -+ } -+ return SW_64_INTERRUPT_PENDING; -+ } -+ -+ return SW_64_CONTINUE_TRACE; -+} -+ -+/* -+ * Redo the gdb pt_regs structure output. -+ */ -+enum regnames { _r0_, _r1_, _r2_, _r3_, _r4_, _r5_, _r6_, _r7_, _r8_, -+ _r19_, _r20_, _r21_, _r22_, _r23_, _r24_, _r25_, _r26_, -+ _r27_, _r28_, _hae_, _trap_a0_, _trap_a1_, _trap_a2_, -+ _ps_, _pc_, _gp_, _r16_, _r17_, _r18_, NUMREGS}; -+ -+struct sw_64_eframe { -+ char regs[30][30]; -+ ulong value[29]; -+}; -+ -+static void -+sw_64_exception_frame(ulong addr, -+ ulong flags, -+ struct gnu_request *req, -+ struct bt_info *bt) -+{ -+ int i, j; -+ char buf[BUFSIZE]; -+ ulong value; -+ physaddr_t paddr; -+ struct sw_64_eframe eframe; -+ -+ if (CRASHDEBUG(4)) -+ fprintf(fp, "sw_64_exception_frame: %lx\n", addr); -+ -+ if (flags & BT_SPECULATE) { -+ req->pc = 0; -+ fprintf(fp, "SW_64 EXCEPTION FRAME\n"); -+ return; -+ } -+ -+ BZERO(&eframe, sizeof(struct sw_64_eframe)); -+ -+ open_tmpfile(); -+ dump_struct("pt_regs", addr, RADIX(16)); -+ rewind(pc->tmpfile); -+ while (fgets(buf, BUFSIZE, pc->tmpfile)) { -+ strip_comma(clean_line(buf)); -+ if (!strstr(buf, "0x")) -+ continue; -+ -+ extract_hex(buf, &value, NULLCHAR, TRUE); -+ if (CRASHDEBUG(4)) -+ fprintf(pc->saved_fp, "<%s> %lx\n", buf, value); -+ -+ if (STRNEQ(buf, "r0 = ")) { -+ sprintf(eframe.regs[_r0_], " V0/R0: %016lx", value); -+ eframe.value[_r0_] = value; -+ } -+ if (STRNEQ(buf, "r1 = ")) { -+ sprintf(eframe.regs[_r1_], " T0/R1: %016lx", value); -+ eframe.value[_r1_] = value; -+ } -+ if (STRNEQ(buf, "r2 = ")) { -+ sprintf(eframe.regs[_r2_], " T1/R2: %016lx", value); -+ eframe.value[_r2_] = value; -+ } -+ if (STRNEQ(buf, "r3 = ")) { -+ sprintf(eframe.regs[_r3_], " T2/R3: %016lx", value); -+ eframe.value[_r3_] = value; -+ } -+ if (STRNEQ(buf, "r4 = ")) { -+ sprintf(eframe.regs[_r4_], " T3/R4: %016lx", value); -+ eframe.value[_r4_] = value; -+ } -+ if (STRNEQ(buf, "r5 = ")) { -+ sprintf(eframe.regs[_r5_], " T4/R5: %016lx", value); -+ eframe.value[_r5_] = value; -+ } -+ if (STRNEQ(buf, "r6 = ")) { -+ sprintf(eframe.regs[_r6_], " T5/R6: %016lx", value); -+ eframe.value[_r6_] = value; -+ } -+ if (STRNEQ(buf, "r7 = ")) { -+ sprintf(eframe.regs[_r7_], " T6/R7: %016lx", value); -+ eframe.value[_r7_] = value; -+ } -+ if (STRNEQ(buf, "r8 = ")) { -+ sprintf(eframe.regs[_r8_], " T7/R8: %016lx", value); -+ eframe.value[_r8_] = value; -+ } -+ if (STRNEQ(buf, "r19 = ")) { -+ sprintf(eframe.regs[_r19_], " A3/R19: %016lx", value); -+ eframe.value[_r19_] = value; -+ } -+ if (STRNEQ(buf, "r20 = ")) { -+ sprintf(eframe.regs[_r20_], " A4/R20: %016lx", value); -+ eframe.value[_r20_] = value; -+ } -+ if (STRNEQ(buf, "r21 = ")) { -+ sprintf(eframe.regs[_r21_], " A5/R21: %016lx", value); -+ eframe.value[_r21_] = value; -+ } -+ if (STRNEQ(buf, "r22 = ")) { -+ sprintf(eframe.regs[_r22_], " T8/R22: %016lx", value); -+ eframe.value[_r22_] = value; -+ } -+ if (STRNEQ(buf, "r23 = ")) { -+ sprintf(eframe.regs[_r23_], " T9/R23: %016lx", value); -+ eframe.value[_r23_] = value; -+ } -+ if (STRNEQ(buf, "r24 = ")) { -+ sprintf(eframe.regs[_r24_], "T10/R24: %016lx", value); -+ eframe.value[_r24_] = value; -+ } -+ if (STRNEQ(buf, "r25 = ")) { -+ sprintf(eframe.regs[_r25_], "T11/R25: %016lx", value); -+ eframe.value[_r25_] = value; -+ } -+ if (STRNEQ(buf, "r26 = ")) { -+ sprintf(eframe.regs[_r26_], " RA/R26: %016lx", value); -+ eframe.value[_r26_] = value; -+ } -+ if (STRNEQ(buf, "r27 = ")) { -+ sprintf(eframe.regs[_r27_], "T12/R27: %016lx", value); -+ eframe.value[_r27_] = value; -+ } -+ if (STRNEQ(buf, "r28 = ")) { -+ sprintf(eframe.regs[_r28_], " AT/R28: %016lx", value); -+ eframe.value[_r28_] = value; -+ } -+ if (STRNEQ(buf, "hae = ")) { -+ sprintf(eframe.regs[_hae_], " HAE: %016lx", value); -+ eframe.value[_hae_] = value; -+ } -+ if (STRNEQ(buf, "trap_a0 = ")) { -+ sprintf(eframe.regs[_trap_a0_], "TRAP_A0: %016lx", -+ value); -+ eframe.value[_trap_a0_] = value; -+ } -+ if (STRNEQ(buf, "trap_a1 = ")) { -+ sprintf(eframe.regs[_trap_a1_], "TRAP_A1: %016lx", -+ value); -+ eframe.value[_trap_a1_] = value; -+ } -+ if (STRNEQ(buf, "trap_a2 = ")) { -+ sprintf(eframe.regs[_trap_a2_], "TRAP_A2: %016lx", -+ value); -+ eframe.value[_trap_a2_] = value; -+ } -+ if (STRNEQ(buf, "ps = ")) { -+ sprintf(eframe.regs[_ps_], " PS: %016lx", value); -+ eframe.value[_ps_] = value; -+ } -+ if (STRNEQ(buf, "pc = ")) { -+ sprintf(eframe.regs[_pc_], " PC: %016lx", value); -+ eframe.value[_pc_] = value; -+ } -+ if (STRNEQ(buf, "gp = ")) { -+ sprintf(eframe.regs[_gp_], " GP/R29: %016lx", value); -+ eframe.value[_gp_] = value; -+ } -+ if (STRNEQ(buf, "r16 = ")) { -+ sprintf(eframe.regs[_r16_], " A0/R16: %016lx", value); -+ eframe.value[_r16_] = value; -+ } -+ if (STRNEQ(buf, "r17 = ")) { -+ sprintf(eframe.regs[_r17_], " A1/R17: %016lx", value); -+ eframe.value[_r17_] = value; -+ } -+ if (STRNEQ(buf, "r18 =")) { -+ sprintf(eframe.regs[_r18_], " A2/R18: %016lx", value); -+ eframe.value[_r18_] = value; -+ } -+ } -+ close_tmpfile(); -+ -+ if ((flags & BT_EXCEPTION_FRAME) && !BT_REFERENCE_CHECK(bt)) { -+dump_eframe: -+ fprintf(fp, " EFRAME: %lx ", addr); -+ fprintf(fp, "%s\n", eframe.regs[_r24_]); -+ -+ for (i = 0; i < (((NUMREGS+1)/2)-1); i++) { -+ fprintf(fp, "%s ", eframe.regs[i]); -+ pad_line(fp, 21 - strlen(eframe.regs[i]), ' '); -+ j = i+((NUMREGS+1)/2); -+ fprintf(fp, "%s", eframe.regs[j]); -+ if (((j == _pc_) || (j == _r26_)) && -+ is_kernel_text(eframe.value[j])) -+ fprintf(fp, " <%s>", -+ value_to_symstr(eframe.value[j], buf, 0)); -+ fprintf(fp, "\n"); -+ } -+ } -+ -+ req->ra = eframe.value[_r26_]; -+ req->pc = eframe.value[_pc_]; -+ req->sp = addr + (29 * sizeof(ulong)); -+ -+ if (flags & BT_USER_EFRAME) { -+ flags &= ~BT_USER_EFRAME; -+ if (!BT_REFERENCE_CHECK(bt) && (eframe.value[_ps_] == 8) && -+ (((uvtop(task_to_context(req->task), req->pc, &paddr, 0) || -+ (volatile ulong)paddr) && -+ (uvtop(task_to_context(req->task), req->ra, &paddr, 0) || -+ (volatile ulong)paddr)) || -+ (IS_ZOMBIE(req->task) || IS_EXITING(req->task)))) { -+ if (!(flags & -+ (BT_RESCHEDULE|BT_RET_FROM_SMP_FORK|BT_STRACE))) -+ fprintf(fp, -+ "NOTE: kernel-entry exception frame:\n"); -+ goto dump_eframe; -+ } -+ } -+} -+ -+/* -+ * Look for likely exception frames in a stack. -+ */ -+struct sw_64_pt_regs { -+ ulong reg_value[NUMREGS]; -+}; -+ -+static int -+sw_64_eframe_search(struct bt_info *bt) -+{ -+ ulong *first, *last; -+ ulong eframe; -+ struct sw_64_pt_regs *pt; -+ struct gnu_request *req; /* needed for sw_64_exception_frame */ -+ ulong *stack; -+ int cnt; -+ -+ stack = (ulong *)bt->stackbuf; -+ req = (struct gnu_request *)GETBUF(sizeof(struct gnu_request)); -+ req->task = bt->task; -+ -+ first = stack + -+ (roundup(SIZE(task_struct), sizeof(ulong)) / sizeof(ulong)); -+ last = stack + -+ (((bt->stacktop - bt->stackbase) - SIZE(pt_regs)) / sizeof(ulong)); -+ -+ for (cnt = 0; first <= last; first++) { -+ pt = (struct sw_64_pt_regs *)first; -+ -+ /* check for kernel exception frame */ -+ -+ if (!(pt->reg_value[_ps_] & 0xfffffffffffffff8) && -+ (is_kernel_text(pt->reg_value[_pc_]) || -+ IS_MODULE_VADDR(pt->reg_value[_pc_])) && -+ (is_kernel_text(pt->reg_value[_r26_]) || -+ IS_MODULE_VADDR(pt->reg_value[_r26_])) && -+ IS_KVADDR(pt->reg_value[_gp_])) { -+ cnt++; -+ if (bt->flags & BT_EFRAME_COUNT) -+ continue; -+ fprintf(fp, "\nKERNEL-MODE EXCEPTION FRAME:\n"); -+ eframe = bt->task + ((ulong)first - (ulong)stack); -+ sw_64_exception_frame(eframe, BT_EXCEPTION_FRAME, -+ req, bt); -+ continue; -+ } -+ -+ /* check for user exception frame */ -+ -+ if ((pt->reg_value[_ps_] == 0x8) && -+ ((IN_TASK_VMA(bt->task, pt->reg_value[_pc_]) && -+ IN_TASK_VMA(bt->task, pt->reg_value[_r26_]) && -+ IS_UVADDR(pt->reg_value[_gp_], bt->tc)) || -+ ((first == last) && -+ (IS_ZOMBIE(bt->task) || IS_EXITING(bt->task))))) { -+ cnt++; -+ if (bt->flags & BT_EFRAME_COUNT) -+ continue; -+ fprintf(fp, "\nUSER-MODE EXCEPTION FRAME:\n"); -+ eframe = bt->task + ((ulong)first - (ulong)stack); -+ sw_64_exception_frame(eframe, BT_EXCEPTION_FRAME, -+ req, bt); -+ } -+ } -+ -+ FREEBUF(req); -+ -+ return cnt; -+} -+ -+/* -+ * Before dumping a nonsensical exception frame, give it a quick test. -+ */ -+static int -+verify_user_eframe(struct bt_info *bt, ulong task, ulong sp) -+{ -+ struct sw_64_pt_regs ptbuf, *pt; -+ -+ readmem(sp, KVADDR, &ptbuf, sizeof(struct sw_64_pt_regs), -+ "pt_regs", FAULT_ON_ERROR); -+ -+ pt = &ptbuf; -+ -+ if ((pt->reg_value[_ps_] == 0x8) && -+ ((IN_TASK_VMA(task, pt->reg_value[_pc_]) && -+ IN_TASK_VMA(task, pt->reg_value[_r26_]) && -+ IS_UVADDR(pt->reg_value[_gp_], bt->tc)) || -+ ((pt == (struct sw_64_pt_regs *)USER_EFRAME_ADDR(task)) && -+ (IS_ZOMBIE(task) || IS_EXITING(task))))) { -+ return TRUE; -+ } -+ -+ return FALSE; -+} -+ -+/* -+ * Try to resync the stack location when there is no valid stack frame, -+ * typically just above an exception frame. Use the req->ra value from the -+ * exception frame as the new starting req->pc. Then walk up the stack until -+ * a text routine that calls the newly-assigned pc is found -- that stack -+ * location then becomes the new req->sp. -+ * -+ * If we're not coming from an exception frame, req-ra and req->pc will be -+ * purposely zeroed out. In that case, use the prevsp value to find the -+ * first pc that called the last frame's pc. -+ * -+ * Add any other repeatable "special-case" frames to the beginning of this -+ * routine (ex. debug_spin_lock). Last ditch -- at the end of this routine, -+ * speculate what might have happened (possibly in the background) -- and -+ * if it looks good, run with it. -+ */ -+static int -+sw_64_backtrace_resync(struct gnu_request *req, ulong flags, struct bt_info *bt) -+{ -+ char addr[BUFSIZE]; -+ char buf[BUFSIZE]; -+ char lookfor1[BUFSIZE]; -+ char lookfor2[BUFSIZE]; -+ ulong newpc; -+ ulong *stkp; -+ ulong *stkp_newpc, *stkp_next; -+ ulong value; -+ int found; -+ char *name; -+ int exception; -+ -+ if (CRASHDEBUG(1)) -+ fprintf(fp, -+ "RESYNC1: [%lx-%d] ra: %lx pc: %lx sp: %lx\n", -+ flags, req->curframe, req->ra, req->pc, req->sp); -+ -+ if (!req->ra && !req->pc) { -+ req->ra = req->prevpc; -+ exception = FALSE; -+ } else -+ exception = TRUE; -+ -+ if (!IS_KVADDR(req->ra)) -+ return FALSE; -+ -+ name = closest_symbol(req->ra); -+ sprintf(lookfor1, "<%s>", name); -+ sprintf(lookfor2, "<%s+", name); -+ -+ if (CRASHDEBUG(1)) -+ fprintf(fp, "RESYNC2: exception: %s lookfor: %s or %s\n", -+ exception ? "TRUE" : "FALSE", -+ lookfor1, lookfor2); -+ -+ /* -+ * This is common when a non-panicking active CPU is spinning -+ * in debug_spin_lock(). The next pc is offset by 0x30 from -+ * the top of the exception frame, and the next sp is equal -+ * to the frame offset of debug_spin_lock(). I can't explain it... -+ */ -+ if ((flags & BT_FROM_EXCEPTION) && STREQ(name, "debug_spin_lock")) { -+ sw_64_print_stack_entry(req, req->ra, -+ closest_symbol(req->ra), flags, bt); -+ -+ if (BT_REFERENCE_FOUND(bt)) -+ return FALSE; -+ -+ sw_64_frame_offset(req, req->ra); -+ stkp = (ulong *)(req->sp + 0x30); -+ value = GET_STACK_ULONG(stkp); -+ if (!is_kernel_text(value)) { -+ req->sp = req->prevsp; -+ return FALSE; -+ } -+ req->pc = value; -+ req->sp += req->value; -+ return TRUE; -+ } -+ -+ /* -+ * If the ra is a system call, then all we should have to do is -+ * find the next reference to entSys on the stack, and set the -+ * sp to that value. -+ */ -+ if (is_system_call(name, 0)) { -+ /* stkp = (ulong *)req->sp; */ -+ stkp = (ulong *)req->prevsp; -+ -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ -+ if (IS_KVADDR(value) && is_kernel_text(value)) { -+ if (STREQ(closest_symbol(value), "entSys")) { -+ req->pc = value; -+ req->sp = USER_EFRAME_ADDR(req->task); -+ return TRUE; -+ } -+ } -+ } -+ } -+ -+ /* -+ * Just find the next location containing text. (?) -+ */ -+ if (STREQ(name, "do_coredump")) { -+ stkp = (ulong *)(req->sp + sizeof(long)); -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ -+ if (IS_KVADDR(value) && is_kernel_text(value)) { -+ req->pc = req->ra; -+ req->sp = (ulong)stkp; -+ return TRUE; -+ } -+ } -+ } -+ -+ if (flags & BT_SPECULATE) -+ return FALSE; -+ -+ if (CRASHDEBUG(1)) { -+ fprintf(fp, "RESYNC3: prevsp: %lx ra: %lx name: %s\n", -+ req->prevsp, req->ra, name); -+ fprintf(fp, "RESYNC3: prevpc: %lx\n", req->prevpc); -+ } -+ -+ stkp_newpc = stkp_next = 0; -+ newpc = 0; -+ found = FALSE; -+ if (exception) { -+ newpc = req->ra; -+ stkp = (ulong *)req->sp; -+ } else -+ stkp = (ulong *)req->prevsp; -+ -+ if (CRASHDEBUG(1)) -+ fprintf(fp, "RESYNC4: stkp: %lx newpc: %lx\n", -+ (ulong)stkp, newpc); -+ -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ /* -+ * First find the new pc on the stack. -+ */ -+ if (!found) { -+ if (!exception && is_kernel_text(value)) { -+ found = TRUE; -+ } else if (value == newpc) { -+ found = TRUE; -+ stkp_newpc = stkp; -+ continue; -+ } -+ } -+ -+ if (!IS_KVADDR(value)) -+ continue; -+ -+ if (is_kernel_text(value)) { -+ if (!stkp_next) -+ stkp_next = stkp; -+ if (CRASHDEBUG(2)) { -+ fprintf(fp, -+ "RESYNC6: disassemble %lx (%s)\n", -+ value - sizeof(uint), -+ value_to_symstr(value - sizeof(uint), -+ buf, 0)); -+ } -+ req->command = GNU_DISASSEMBLE; -+ req->addr = value - sizeof(uint); -+ sprintf(addr, "0x%lx", req->addr); -+ open_tmpfile(); -+ req->fp = pc->tmpfile; -+ gdb_interface(req); -+ rewind(pc->tmpfile); -+ while (fgets(buf, BUFSIZE, pc->tmpfile)) { -+ clean_line(buf); -+ if (STRNEQ(buf, "Dump of") || -+ STRNEQ(buf, "End of")) -+ continue; -+ -+ if (STRNEQ(buf, addr)) { -+ if (LASTCHAR(buf) == ':') { -+ fgets(buf, BUFSIZE, -+ pc->tmpfile); -+ clean_line(buf); -+ } -+ if (CRASHDEBUG(2) && -+ (strstr(buf, "jsr") -+ || strstr(buf, "bsr"))) -+ fprintf(pc->saved_fp, "%s\n", -+ buf); -+ if ((strstr(buf, "jsr") || -+ strstr(buf, "bsr")) && -+ (strstr(buf, lookfor1) || -+ strstr(buf, lookfor2))) { -+ if (exception) { -+ req->pc = newpc; -+ req->sp = (ulong)stkp; -+ } else -+ req->pc = req->addr; -+ close_tmpfile(); -+ return TRUE; -+ } -+ } -+ } -+ close_tmpfile(); -+ } -+ } -+ -+ if (CRASHDEBUG(1)) { -+ fprintf(fp, "RESYNC9: [%d] name: %s pc: %lx ra: %lx\n", -+ req->curframe, name, req->pc, req->ra); -+ fprintf(fp, "RESYNC9: sp: %lx lastsp: %lx\n", -+ req->sp, req->lastsp); -+ fprintf(fp, "RESYNC9: prevpc: %lx prevsp: %lx\n", -+ req->prevpc, req->prevsp); -+ } -+ -+ /* -+ * At this point, all we can do is speculate based upon -+ * past experiences... -+ */ -+ return (sw_64_resync_speculate(req, flags, bt)); -+} -+ -+/* -+ * Try one level of speculation. If it works, fine -- if not, give up. -+ */ -+static int -+sw_64_resync_speculate(struct gnu_request *req, ulong flags, struct bt_info *bt) -+{ -+ ulong *stkp; -+ ulong value; -+ ulong found_sp, found_ra; -+ struct stack_hook hook; -+ struct bt_info bt_info, *btloc; -+ char buf[BUFSIZE]; -+ int kernel_thread; -+ int looks_good; -+ -+ if (flags & BT_SPECULATE) /* already been here on this trace... */ -+ return FALSE; -+ -+ if (pc->tmpfile) -+ return FALSE; -+ -+ found_ra = found_sp = 0; -+ kernel_thread = is_kernel_thread(req->task); -+ -+ /* -+ * Add "known" possibilities here. -+ */ -+ switch (flags & (BT_FROM_EXCEPTION|BT_FROM_CALLFRAME)) -+ { -+ case BT_FROM_EXCEPTION: -+ if (STREQ(closest_symbol(req->prevpc), "read_lock") || -+ STREQ(closest_symbol(req->ra), "do_select") || -+ STREQ(closest_symbol(req->ra), "schedule")) { -+ stkp = (ulong *)req->sp; -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ -+ if (found_ra) { -+ if (is_kernel_text_offset(value)) { -+ found_sp = (ulong)stkp; -+ break; -+ } -+ continue; -+ } -+ -+ if (value == req->ra) -+ found_ra = value; -+ } -+ } -+ break; -+ -+ case BT_FROM_CALLFRAME: -+ if (STREQ(closest_symbol(req->ra), "sys_read")) { -+ value = GET_STACK_ULONG(req->prevsp - 32); -+ if (STREQ(closest_symbol(value), "entSys")) { -+ found_ra = value; -+ found_sp = req->prevsp - 32; -+ } -+ } else if (STREQ(closest_symbol(req->ra), "exit_autofs4_fs")) { -+ stkp = (ulong *)req->sp; -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ -+ if (found_ra && (value != found_ra)) { -+ if (is_kernel_text_offset(value)) { -+ found_sp = (ulong)stkp; -+ break; -+ } -+ continue; -+ } -+ -+ if (is_kernel_text_offset(value)) -+ found_ra = value; -+ } -+ } -+ -+ break; -+ -+ default: -+ if (req->hookp && -+ STREQ(closest_symbol(req->prevpc), "filemap_nopage") && -+ !STREQ(closest_symbol(req->hookp->eip), "do_no_page")) { -+ found_ra = found_sp = 0; -+ stkp = (ulong *)req->prevsp; -+ for (stkp++; INSTACK(stkp, bt); stkp++) { -+ value = GET_STACK_ULONG(stkp); -+ -+ if (found_ra && (value != found_ra)) { -+ if (is_kernel_text_offset(value)) { -+ found_sp = (ulong)stkp; -+ break; -+ } -+ continue; -+ } -+ -+ if (is_kernel_text_offset(value) && -+ STREQ(closest_symbol(value), "do_no_page")) -+ found_ra = value; -+ } -+ if (found_ra && found_sp) { -+ req->hookp->eip = found_ra; -+ req->hookp->esp = found_sp; -+ return TRUE; -+ } -+ } -+ -+ if (req->hookp) { -+ found_ra = req->hookp->eip; -+ found_sp = req->hookp->esp; -+ } -+ -+ break; -+ } -+ -+ if (found_ra && found_sp) { -+ looks_good = FALSE; -+ hook.esp = found_sp; -+ hook.eip = found_ra; -+ -+ if (CRASHDEBUG(1)) -+ fprintf(pc->saved_fp, -+ "----- RESYNC SPECULATE START -----\n"); -+ -+ open_tmpfile(); -+ btloc = &bt_info; -+ BZERO(btloc, sizeof(struct bt_info)); -+ btloc->task = req->task; -+ btloc->tc = bt->tc; -+ btloc->stackbase = bt->stackbase; -+ btloc->stacktop = bt->stacktop; -+ btloc->flags = BT_SPECULATE; -+ btloc->hp = &hook; -+ back_trace(btloc); -+ rewind(pc->tmpfile); -+ while (fgets(buf, BUFSIZE, pc->tmpfile)) { -+ if (CRASHDEBUG(1)) -+ fprintf(pc->saved_fp, "%s", buf); -+ -+ if (strstr(buf, "NOTE: cannot resolve")) { -+ looks_good = FALSE; -+ break; -+ } -+ -+ if (strstr(buf, "SW_64 EXCEPTION FRAME")) { -+ looks_good = TRUE; -+ break; -+ } -+ -+ if (kernel_thread) { -+ if (strstr(buf, " kernel_thread ") || -+ strstr(buf, " __kernel_thread ") || -+ strstr(buf, " start_kernel ") || -+ strstr(buf, " smp_callin ")) { -+ looks_good = TRUE; -+ break; -+ } -+ } -+ } -+ close_tmpfile(); -+ -+ if (CRASHDEBUG(1)) -+ fprintf(pc->saved_fp, -+ "----- RESYNC SPECULATE DONE ------\n"); -+ -+ if (looks_good) { -+ req->pc = found_ra; -+ req->sp = found_sp; -+ return TRUE; -+ } -+ } -+ -+ return FALSE; -+} -+ -+/* -+ * Translates a user virtual address to its physical address. cmd_vtop() -+ * sets the verbose flag so that the pte translation gets displayed; all -+ * other callers quietly accept the translation. -+ * -+ * This routine can also take mapped kernel virtual addresses if the -u flag -+ * was passed to cmd_vtop(). If so, it makes the translation using the -+ * kernel-memory PGD entry instead of swapper_pg_dir. -+ */ -+ -+static int -+sw_64_uvtop(struct task_context *tc, ulong vaddr, physaddr_t *paddr, int verbose) -+{ -+ ulong mm; -+ ulong *pgd; -+ ulong *page_dir; -+ ulong *page_middle; -+ ulong *page_table; -+ ulong pgd_pte; -+ ulong pmd_pte; -+ ulong pte; -+ -+ if (!tc) -+ error(FATAL, "current context invalid\n"); -+ -+ *paddr = 0; -+ -+ if (is_kernel_thread(tc->task) && IS_KVADDR(vaddr)) { -+ pgd = (ulong *)machdep->get_task_pgd(tc->task); -+ } else { -+ if (!tc->mm_struct) -+ pgd = (ulong *)machdep->get_task_pgd(tc->task); -+ else { -+ if ((mm = task_mm(tc->task, TRUE))) -+ pgd = ULONG_PTR(tt->mm_struct + -+ OFFSET(mm_struct_pgd)); -+ else -+ readmem(tc->mm_struct + OFFSET(mm_struct_pgd), -+ KVADDR, &pgd, sizeof(long), -+ "mm_struct pgd", FAULT_ON_ERROR); -+ } -+ } -+ -+ if (verbose) -+ fprintf(fp, "PAGE DIRECTORY: %lx\n", (ulong)pgd); -+ -+ page_dir = pgd + ((vaddr >> PGDIR_SHIFT) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PGD(PAGEBASE(pgd), KVADDR, PAGESIZE()); -+ pgd_pte = ULONG(machdep->pgd + PAGEOFFSET(page_dir)); -+ -+ if (verbose) -+ fprintf(fp, " PGD: %lx => %lx\n", (ulong)page_dir, pgd_pte); -+ -+ if (!(pgd_pte & _PAGE_VALID)) -+ goto no_upage; -+ -+ page_middle = (ulong *) -+ (PTOV((pgd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + -+ ((vaddr >> PMD_SHIFT) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PMD(PAGEBASE(page_middle), KVADDR, PAGESIZE()); -+ pmd_pte = ULONG(machdep->pmd + PAGEOFFSET(page_middle)); -+ -+ if (verbose) -+ fprintf(fp, " PMD: %lx => %lx\n", (ulong)page_middle, pmd_pte); -+ -+ if (!(pmd_pte & _PAGE_VALID)) -+ goto no_upage; -+ -+ page_table = (ulong *) -+ (PTOV((pmd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + -+ (BTOP(vaddr) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PTBL(PAGEBASE(page_table), KVADDR, PAGESIZE()); -+ pte = ULONG(machdep->ptbl + PAGEOFFSET(page_table)); -+ -+ if (verbose) -+ fprintf(fp, " PTE: %lx => %lx\n", (ulong)page_table, pte); -+ -+ if (!(pte & (_PAGE_VALID))) { -+ *paddr = pte; -+ if (pte && verbose) { -+ fprintf(fp, "\n"); -+ sw_64_translate_pte(pte, 0, 0); -+ } -+ goto no_upage; -+ } -+ -+ *paddr = ((pte & _PFN_MASK) >> (32-PAGESHIFT())) + PAGEOFFSET(vaddr); -+ -+ if (verbose) { -+ fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); -+ sw_64_translate_pte(pte, 0, 0); -+ } -+ -+ return TRUE; -+ -+no_upage: -+ return FALSE; -+} -+ -+/* -+ * Translates a kernel virtual address to its physical address. cmd_vtop() -+ * sets the verbose flag so that the pte translation gets displayed; all -+ * other callers quietly accept the translation. -+ */ -+ -+static int -+sw_64_kvtop(struct task_context *tc, ulong kvaddr, physaddr_t *paddr, int verbose) -+{ -+ ulong *pgd; -+ ulong *page_dir; -+ ulong *page_middle; -+ ulong *page_table; -+ ulong pgd_pte; -+ ulong pmd_pte; -+ ulong pte; -+ -+ if (!IS_KVADDR(kvaddr)) -+ return FALSE; -+ -+ if (!vt->vmalloc_start) { /* presume KSEG this early */ -+ *paddr = VTOP(kvaddr); -+ return TRUE; -+ } -+ -+ if (!IS_VMALLOC_ADDR(kvaddr)) { -+ *paddr = VTOP(kvaddr); -+ return TRUE; -+ } -+ -+ pgd = (ulong *)vt->kernel_pgd[0]; -+ -+ if (verbose) -+ fprintf(fp, "PAGE DIRECTORY: %lx\n", (ulong)pgd); -+ -+ page_dir = pgd + ((kvaddr >> PGDIR_SHIFT) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PGD(PAGEBASE(pgd), KVADDR, PAGESIZE()); -+ pgd_pte = ULONG(machdep->pgd + PAGEOFFSET(page_dir)); -+ -+ if (verbose) -+ fprintf(fp, " PGD: %lx => %lx\n", (ulong)page_dir, pgd_pte); -+ -+ if (!(pgd_pte & _PAGE_VALID)) -+ goto no_kpage; -+ -+ page_middle = (ulong *) -+ (PTOV((pgd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + -+ ((kvaddr >> PMD_SHIFT) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PMD(PAGEBASE(page_middle), KVADDR, PAGESIZE()); -+ pmd_pte = ULONG(machdep->pmd + PAGEOFFSET(page_middle)); -+ -+ if (verbose) -+ fprintf(fp, " PMD: %lx => %lx\n", (ulong)page_middle, pmd_pte); -+ -+ if (!(pmd_pte & _PAGE_VALID)) -+ goto no_kpage; -+ -+ page_table = (ulong *) -+ (PTOV((pmd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + -+ (BTOP(kvaddr) & (PTRS_PER_PAGE - 1)); -+ -+ FILL_PTBL(PAGEBASE(page_table), KVADDR, PAGESIZE()); -+ pte = ULONG(machdep->ptbl + PAGEOFFSET(page_table)); -+ -+ if (verbose) -+ fprintf(fp, " PTE: %lx => %lx\n", (ulong)page_table, pte); -+ -+ if (!(pte & (_PAGE_VALID))) { -+ if (pte && verbose) { -+ fprintf(fp, "\n"); -+ sw_64_translate_pte(pte, 0, 0); -+ } -+ goto no_kpage; -+ } -+ -+ *paddr = ((pte & _PFN_MASK) >> (32-PAGESHIFT())) + PAGEOFFSET(kvaddr); -+ -+ if (verbose) { -+ fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); -+ sw_64_translate_pte(pte, 0, 0); -+ } -+ -+ return TRUE; -+ -+no_kpage: -+ return FALSE; -+} -+ -+ -+/* -+ * Get the relevant page directory pointer from a task structure. -+ */ -+static ulong -+sw_64_get_task_pgd(ulong task) -+{ -+ long offset; -+ ulong ptbr; -+ -+ offset = OFFSET_OPTION(task_struct_thread, task_struct_tss); -+ -+ offset += OFFSET(thread_struct_ptbr); -+ -+ readmem(task + offset, KVADDR, &ptbr, -+ sizeof(ulong), "task thread ptbr", FAULT_ON_ERROR); -+ -+ return(PTOV(PTOB(ptbr))); -+} -+ -+/* -+ * Calculate and return the speed of the processor. -+ */ -+static ulong -+sw_64_processor_speed(void) -+{ -+ ulong hwrpb; -+ long offset; -+ long cycle_freq; -+ ulong mhz; -+ -+ if (machdep->mhz) -+ return machdep->mhz; -+ -+ mhz = 0; -+ -+ get_symbol_data("hwrpb", sizeof(void *), &hwrpb); -+ offset = OFFSET(hwrpb_struct_cycle_freq); -+ -+ if (!hwrpb || (offset == -1) || -+ !readmem(hwrpb+offset, KVADDR, &cycle_freq, -+ sizeof(ulong), "hwrpb cycle_freq", RETURN_ON_ERROR)) -+ return (machdep->mhz = mhz); -+ -+ mhz = cycle_freq/1000000; -+ -+ return (machdep->mhz = mhz); -+} -+ -+void -+sw_64_dump_machdep_table(ulong arg) -+{ -+ int others; -+ -+ others = 0; -+ fprintf(fp, " flags: %lx (", machdep->flags); -+ if (machdep->flags & HWRESET) -+ fprintf(fp, "%sHWRESET", others++ ? "|" : ""); -+ fprintf(fp, ")\n"); -+ fprintf(fp, " kvbase: %lx\n", machdep->kvbase); -+ fprintf(fp, " identity_map_base: %lx\n", machdep->identity_map_base); -+ fprintf(fp, " pagesize: %d\n", machdep->pagesize); -+ fprintf(fp, " pageshift: %d\n", machdep->pageshift); -+ fprintf(fp, " pagemask: %llx\n", machdep->pagemask); -+ fprintf(fp, " pageoffset: %lx\n", machdep->pageoffset); -+ fprintf(fp, " stacksize: %ld\n", machdep->stacksize); -+ fprintf(fp, " hz: %d\n", machdep->hz); -+ fprintf(fp, " mhz: %ld\n", machdep->mhz); -+ fprintf(fp, " memsize: %ld (0x%lx)\n", -+ machdep->memsize, machdep->memsize); -+ fprintf(fp, " bits: %d\n", machdep->bits); -+ fprintf(fp, " nr_irqs: %d\n", machdep->nr_irqs); -+ fprintf(fp, " eframe_search: sw_64_eframe_search()\n"); -+ fprintf(fp, " back_trace: sw_64_back_trace_cmd()\n"); -+ fprintf(fp, " processor_speed: sw_64_processor_speed()\n"); -+ fprintf(fp, " uvtop: sw_64_uvtop()\n"); -+ fprintf(fp, " kvtop: sw_64_uvtop()\n"); -+ fprintf(fp, " get_task_pgd: sw_64_get_task_pgd()\n"); -+ if (machdep->dump_irq == generic_dump_irq) -+ fprintf(fp, " dump_irq: generic_dump_irq()\n"); -+ else -+ fprintf(fp, " dump_irq: sw_64_dump_irq()\n"); -+ fprintf(fp, " get_stack_frame: sw_64_get_stack_frame()\n"); -+ fprintf(fp, " get_stackbase: generic_get_stackbase()\n"); -+ fprintf(fp, " get_stacktop: generic_get_stacktop()\n"); -+ fprintf(fp, " translate_pte: sw_64_translate_pte()\n"); -+ fprintf(fp, " memory_size: sw_64_get_memory_size()\n"); -+ fprintf(fp, " vmalloc_start: sw_64_get_vmalloc_start()\n"); -+ fprintf(fp, " is_task_addr: sw_64_is_task_addr()\n"); -+ fprintf(fp, " verify_symbol: sw_64_verify_symbol()\n"); -+ fprintf(fp, " dis_filter: sw_64_dis_filter()\n"); -+ fprintf(fp, " cmd_mach: sw_64_cmd_mach()\n"); -+ fprintf(fp, " get_smp_cpus: sw_64_get_smp_cpus()\n"); -+ fprintf(fp, " is_kvaddr: generic_is_kvaddr()\n"); -+ fprintf(fp, " is_uvaddr: generic_is_uvaddr()\n"); -+ fprintf(fp, " verify_paddr: generic_verify_paddr()\n"); -+ fprintf(fp, " init_kernel_pgd: NULL\n"); -+ fprintf(fp, " value_to_symbol: generic_machdep_value_to_symbol()\n"); -+ fprintf(fp, " line_number_hooks: sw_64_line_number_hooks\n"); -+ fprintf(fp, " last_pgd_read: %lx\n", machdep->last_pgd_read); -+ fprintf(fp, " last_pmd_read: %lx\n", machdep->last_pmd_read); -+ fprintf(fp, " last_ptbl_read: %lx\n", machdep->last_ptbl_read); -+ fprintf(fp, " pgd: %lx\n", (ulong)machdep->pgd); -+ fprintf(fp, " pmd: %lx\n", (ulong)machdep->pmd); -+ fprintf(fp, " ptbl: %lx\n", (ulong)machdep->ptbl); -+ fprintf(fp, " ptrs_per_pgd: %d\n", machdep->ptrs_per_pgd); -+ fprintf(fp, " machspec: %lx\n", (ulong)machdep->machspec); -+} -+ -+/* -+ * Fix up jsr's to show the right target. -+ * -+ * If a value is passed with no buf, then cmd_dis is fishing for whether -+ * the GP can be calculated from the first couple of instructions of the -+ * target routine: -+ * -+ * 0xfffffc0000349fa0 : ldah gp,35(t12) -+ * 0xfffffc0000349fa4 : lda gp,6216(gp) -+ * -+ * If a buf pointer is passed, then check whether the t12 register -+ * is being set up as an offset from gp, then calculate the target address: -+ * -+ * 0xfffffc000042c364 : ldq t12,-29336(gp) -+ * 0xfffffc000042c368 : -+ * jsr ra,(t12),0xfffffc0000429dc0 -+ * -+ * If the next instruction is a jsr ra,(t12), then correct the bracketed -+ * target address translation. -+ * -+ */ -+ -+#define LDAH_GP_T12 (0x27bb0000) -+#define LDA_GP_GP (0x23bd0000) -+#define LDQ_T12_GP (0xa77d0000) -+#define JSR_RA_T12 (0x6b5b0000) -+ -+#define OPCODE_OPERAND_MASK (0xffff0000) -+#define OPCODE_MEM_DISP_MASK (0x0000ffff) -+ -+static struct instruction_data { -+ uint inst[2]; -+ short mem_disp[2]; -+ ulong gp; -+ ulong target; -+ char *curfunc; -+} instruction_data = { {0} }; -+ -+static int -+sw_64_dis_filter(ulong vaddr, char *buf, unsigned int output_radix) -+{ -+ struct syment *sp; -+ struct instruction_data *id; -+ char buf2[BUFSIZE], *p1; -+ -+ id = &instruction_data; -+ -+ if (!buf) { -+ BZERO(id, sizeof(struct instruction_data)); -+ -+ if (!(sp = value_search(vaddr, NULL))) -+ return FALSE; -+ -+ readmem(sp->value, KVADDR, &id->inst[0], -+ sizeof(uint) * 2, "two instructions", FAULT_ON_ERROR); -+ -+ if (((id->inst[0] & OPCODE_OPERAND_MASK) == LDAH_GP_T12) && -+ ((id->inst[1] & OPCODE_OPERAND_MASK) == LDA_GP_GP)) { -+ id->mem_disp[0] = (short)(id->inst[0] & -+ OPCODE_MEM_DISP_MASK); -+ id->mem_disp[1] = (short)(id->inst[1] & -+ OPCODE_MEM_DISP_MASK); -+ id->gp = sp->value + (65536*id->mem_disp[0]) + -+ id->mem_disp[1]; -+ id->curfunc = sp->name; -+ -+ if (CRASHDEBUG(1)) -+ console("%s: ldah(%d) and lda(%d) gp: %lx\n", -+ id->curfunc, -+ id->mem_disp[0], id->mem_disp[1], -+ id->gp); -+ -+ return TRUE; -+ } -+ /* send all lines through the generic */ -+ return TRUE; /* dis_address_translation() filter */ -+ } -+ -+ dis_address_translation(vaddr, buf, output_radix); -+ -+ if (!id->gp || !(sp = value_search(vaddr, NULL)) || -+ !STREQ(id->curfunc, sp->name)) { -+ BZERO(id, sizeof(struct instruction_data)); -+ return FALSE; -+ } -+ -+ readmem(vaddr, KVADDR, &id->inst[0], -+ sizeof(uint), "one instruction", FAULT_ON_ERROR); -+ -+ if ((id->inst[0] & OPCODE_OPERAND_MASK) == JSR_RA_T12) { -+ -+ if (!id->target || !strstr(buf, "jsr\tra,(t12)") || -+ !strstr(buf, "<")) -+ return FALSE; -+ -+ p1 = strstr(strstr(buf, "jsr"), "0x"); -+ sprintf(p1, "0x%lx <%s>%s", -+ id->target, -+ value_to_symstr(id->target, buf2, output_radix), -+ CRASHDEBUG(1) ? " [PATCHED]\n" : "\n"); -+ return TRUE; -+ } -+ -+ if ((id->inst[0] & OPCODE_OPERAND_MASK) == LDQ_T12_GP) { -+ id->mem_disp[0] = (short)(id->inst[0] & OPCODE_MEM_DISP_MASK); -+ readmem(id->gp + id->mem_disp[0], KVADDR, &id->target, -+ sizeof(ulong), "jsr target", FAULT_ON_ERROR); -+ } else -+ id->target = 0; -+ -+ return TRUE; -+} -+ -+/* -+ * For some reason gdb can go off into the weeds translating text addresses, -+ * so this routine both fixes the references as well as imposing the current -+ * output radix on the translations. -+ */ -+static void -+dis_address_translation(ulong vaddr, char *inbuf, unsigned int output_radix) -+{ -+ char buf1[BUFSIZE]; -+ char buf2[BUFSIZE]; -+ char *colon, *p1; -+ int argc; -+ char *argv[MAXARGS]; -+ ulong value; -+ -+ console("IN: %s", inbuf); -+ -+ colon = strstr(inbuf, ":"); -+ -+ if (colon) { -+ sprintf(buf1, "0x%lx <%s>", vaddr, -+ value_to_symstr(vaddr, buf2, output_radix)); -+ sprintf(buf2, "%s%s", buf1, colon); -+ strcpy(inbuf, buf2); -+ } -+ -+ strcpy(buf1, inbuf); -+ argc = parse_line(buf1, argv); -+ -+ if ((FIRSTCHAR(argv[argc-1]) == '<') && -+ (LASTCHAR(argv[argc-1]) == '>')) { -+ p1 = rindex(inbuf, '<'); -+ while ((p1 > inbuf) && (*p1 != ',')) -+ p1--; -+ -+ if (!STRNEQ(p1, ",0x")) -+ return; -+ p1++; -+ -+ if (!extract_hex(p1, &value, NULLCHAR, TRUE)) -+ return; -+ -+ sprintf(buf1, "0x%lx <%s>\n", value, -+ value_to_symstr(value, buf2, output_radix)); -+ -+ sprintf(p1, "%s", buf1); -+ } -+ -+ console(" %s", inbuf); -+} -+ -+ -+/* -+ * If we're generically-inclined, call generic_dump_irq(). Otherwise -+ * dump the IRQ table the old-fashioned way. -+ */ -+static void -+sw_64_dump_irq(int irq) -+{ -+ ulong action; -+ ulong value; -+ char *arglist[MAXARGS]; -+ int argc, others; -+ char buf[BUFSIZE]; -+ -+ if (symbol_exists("irq_desc")) { -+ machdep->dump_irq = generic_dump_irq; -+ return(generic_dump_irq(irq)); -+ } -+ -+ action = symbol_value("irq_action") + (sizeof(void *) * irq); -+ -+ readmem(action, KVADDR, &action, -+ sizeof(void *), "irq_action pointer", FAULT_ON_ERROR); -+ -+ if (!action) { -+ fprintf(fp, " IRQ: %d\n", irq); -+ fprintf(fp, "handler:\n"); -+ fprintf(fp, " flags: \n"); -+ fprintf(fp, " mask: \n"); -+ fprintf(fp, " name: \n"); -+ fprintf(fp, " dev_id: \n"); -+ fprintf(fp, " next: \n\n"); -+ return; -+ } -+ -+ fprintf(fp, " IRQ: %d\n", irq); -+ -+ open_tmpfile(); -+ -+do_linked_action: -+ dump_struct("irqaction", action, RADIX(16)); -+ action = 0; -+ rewind(pc->tmpfile); -+ while (fgets(buf, BUFSIZE, pc->tmpfile)) { -+ strip_comma(buf); -+ argc = parse_line(buf, arglist); -+ if (STREQ(arglist[0], "struct") || STREQ(buf, "};")) -+ continue; -+ -+ if (STREQ(arglist[0], "handler")) { -+ fprintf(pc->saved_fp, "handler: %s ", -+ strip_hex(arglist[2])); -+ if (argc == 4) -+ fprintf(pc->saved_fp, "%s", arglist[3]); -+ fprintf(pc->saved_fp, "\n"); -+ } -+ if (STREQ(arglist[0], "flags")) { -+ value = htol(strip_comma(arglist[2]), -+ FAULT_ON_ERROR, NULL); -+ fprintf(pc->saved_fp, -+ " flags: %lx ", value); -+ -+ if (value) { -+ others = 0; -+ fprintf(pc->saved_fp, "("); -+ -+ if (value & SA_INTERRUPT) -+ fprintf(pc->saved_fp, -+ "%sSA_INTERRUPT", -+ others++ ? "|" : ""); -+ if (value & SA_PROBE) -+ fprintf(pc->saved_fp, -+ "%sSA_PROBE", -+ others++ ? "|" : ""); -+ if (value & SA_SAMPLE_RANDOM) -+ fprintf(pc->saved_fp, -+ "%sSA_SAMPLE_RANDOM", -+ others++ ? "|" : ""); -+ if (value & SA_SHIRQ) -+ fprintf(pc->saved_fp, -+ "%sSA_SHIRQ", -+ others++ ? "|" : ""); -+ fprintf(pc->saved_fp, ")"); -+ if (value & ~ACTION_FLAGS) { -+ fprintf(pc->saved_fp, -+ " (bits %lx not translated)", -+ value & ~ACTION_FLAGS); -+ } -+ } -+ -+ fprintf(pc->saved_fp, "\n"); -+ -+ } -+ if (STREQ(arglist[0], "mask")) { -+ value = htol(strip_comma(arglist[2]), -+ FAULT_ON_ERROR, NULL); -+ fprintf(pc->saved_fp, -+ " mask: %lx\n", value); -+ } -+ if (STREQ(arglist[0], "name")) { -+ fprintf(pc->saved_fp, " name: %s ", -+ strip_hex(arglist[2])); -+ if (argc == 4) -+ fprintf(pc->saved_fp, "\"%s\"", arglist[3]); -+ fprintf(pc->saved_fp, "\n"); -+ } -+ if (STREQ(arglist[0], "dev_id")) { -+ value = htol(strip_comma(arglist[2]), -+ FAULT_ON_ERROR, NULL); -+ fprintf(pc->saved_fp, -+ " dev_id: %lx\n", value); -+ } -+ if (STREQ(arglist[0], "next")) { -+ value = htol(strip_comma(arglist[2]), -+ FAULT_ON_ERROR, NULL); -+ fprintf(pc->saved_fp, -+ " next: %s\n", -+ strip_hex(arglist[2])); -+ if (value) -+ action = value; -+ } -+ } -+ close_tmpfile(); -+ -+ fprintf(fp, "\n"); -+ -+ if (action) -+ goto do_linked_action; -+} -+ -+/* -+ * Get a stack frame combination of pc and ra from the most relevent spot. -+ */ -+static void -+sw_64_get_stack_frame(struct bt_info *bt, ulong *pcp, ulong *spp) -+{ -+ struct syment *sp; -+ ulong ksp; -+ ulong ip; -+ -+ if (pcp) { -+ if (DUMPFILE() && is_panic_thread(bt->task)) { -+ sp = next_symbol("crash_save_current_state", NULL); -+ -+ if (HWRESET_TASK(bt->task)) -+ ip = get_percpu_data(0, GET_HALT_PC, 0); -+ else if (sp) -+ ip = sp->value - 4; -+ else -+ ip = symbol_value("crash_save_current_state") -+ + 16; -+ } else -+ get_sw_64_frame(bt, &ip, NULL); -+ -+ *pcp = ip; -+ } -+ -+ if (spp) { -+ ip = 0; -+ if (!get_panic_ksp(bt, &ksp)) -+ get_sw_64_frame(bt, -+ HWRESET_TASK(bt->task) ? &ip : NULL, &ksp); -+ -+ if (!INSTACK(ksp, bt)) -+ error(FATAL, -+ "cannot determine starting stack address\n", -+ bt->task); -+ -+ *spp = ksp; -+ if (ip) -+ *pcp = ip; -+ } -+} -+ -+/* -+ * Do the work formerly done by sw_64_get_sp() and sw_64_get_pc(). -+ */ -+static void -+get_sw_64_frame(struct bt_info *bt, ulong *getpc, ulong *getsp) -+{ -+ int i; -+ ulong ip; -+ ulong r26; -+ ulong ksp, sp; -+ ulong *spp; -+ ulong percpu_ra; -+ ulong percpu_pv; -+ struct percpu_data percpu_data; -+ char buf[BUFSIZE]; -+ ulong task; -+ ulong *stack; -+ -+ task = bt->task; -+ stack = (ulong *)bt->stackbuf; -+ -+ if (tt->flags & THREAD_INFO) { /* pcb.ksp is 1st word in thread_info */ -+ readmem(bt->tc->thread_info, KVADDR, &ksp, sizeof(ulong), -+ "thread_info pcb ksp", FAULT_ON_ERROR); -+ sp = ksp; -+ } else if (VALID_MEMBER(task_struct_tss_ksp)) -+ ksp = sp = stack[OFFSET(task_struct_tss_ksp)/sizeof(long)]; -+ else -+ ksp = sp = stack[OFFSET(task_struct_thread_ksp)/sizeof(long)]; -+ -+ ip = 0; -+ percpu_ra = percpu_pv = 0; -+ spp = &stack[(sp - task)/sizeof(long)]; -+ -+ if (DUMPFILE() && getsp) { -+ if (HWRESET_TASK(task)) { -+ if (INSTACK(sp, bt)) { -+ *getsp = sp; -+ return; -+ } else { -+ get_percpu_data(0, 0, &percpu_data); -+ percpu_ra = percpu_data.halt_ra; -+ percpu_pv = percpu_data.halt_pv; -+ spp = &stack[roundup(SIZE(task_struct), -+ sizeof(ulong)) / sizeof(ulong)]; -+ } -+ } -+ -+ if (!percpu_ra && (STREQ(closest_symbol(*spp), "panic") || -+ STREQ(closest_symbol(*spp), "handle_ipi"))) { -+ *getsp = sp; -+ return; -+ } -+ } -+ -+percpu_retry: -+ -+ if (CRASHDEBUG(1) && percpu_ra) { -+ fprintf(fp, "get_sw_64_frame: look for %lx (%s)\n", -+ percpu_ra, value_to_symstr(percpu_ra, buf, 0)); -+ } -+ -+ for (i = 0, spp++; spp < &stack[LONGS_PER_STACK]; spp++,i++) { -+ -+ if (CRASHDEBUG(1) && (percpu_ra || percpu_pv) && -+ is_kernel_text(*spp)) { -+ fprintf(fp, "%lx: %lx (%s)\n", -+ ((ulong)spp - (ulong)stack) + task, -+ *spp, value_to_symstr(*spp, buf, 0)); -+ } -+ -+ if (percpu_ra) { -+ if (*spp == percpu_ra) { -+ *getsp = ((ulong)spp - (ulong)stack) + task; -+ return; -+ } -+ continue; -+ } else if (percpu_pv) { -+ if (*spp == percpu_pv) { -+ *getsp = ((ulong)spp - (ulong)stack) + task; -+ if (getpc) -+ *getpc = percpu_pv; -+ return; -+ } -+ continue; -+ } -+ -+ if (!INSTACK(*spp, bt)) -+ continue; -+ -+ if (is_kernel_text(*(spp+1))) { -+ sp = *spp; -+ ip = *(spp+1); -+ break; -+ } -+ } -+ -+ if (percpu_ra) { -+ percpu_ra = 0; -+ -+ error(INFO, -+ "cannot find return address (percpu_ra) in HARDWARE RESET stack\n"); -+ error(INFO, -+ "looking for procedure address (percpu_pv) in HARDWARE RESET stack\n"); -+ -+ if (CRASHDEBUG(1)) { -+ fprintf(fp, "get_sw_64_frame: look for %lx (%s)\n", -+ percpu_pv, value_to_symstr(percpu_pv, buf, 0)); -+ } -+ spp = &stack[roundup(SIZE(task_struct), -+ sizeof(ulong)) / sizeof(ulong)]; -+ -+ goto percpu_retry; -+ } -+ -+ if (percpu_pv) { -+ error(INFO, -+ "cannot find procedure address (percpu_pv) in HARDWARE RESET stack\n"); -+ } -+ -+ /* -+ * Check for a forked task that has not yet run in user space. -+ */ -+ if (!ip) { -+ if (INSTACK(ksp + OFFSET(switch_stack_r26), bt)) { -+ readmem(ksp + OFFSET(switch_stack_r26), KVADDR, -+ &r26, sizeof(ulong), -+ "ret_from_smp_fork check", FAULT_ON_ERROR); -+ if (STREQ(closest_symbol(r26), "ret_from_smp_fork") || -+ STREQ(closest_symbol(r26), "ret_from_smpfork")) { -+ ip = r26; -+ sp = ksp; -+ } -+ } -+ -+ } -+ -+ if (getsp) -+ *getsp = sp; -+ if (getpc) -+ *getpc = ip; -+ -+} -+ -+/* -+ * Fill the percpu_data structure with information from the -+ * hwrpb/percpu_data structures for a given CPU. If requested, -+ * return one of the specified entries. -+ */ -+static ulong -+get_percpu_data(int cpu, ulong flag, struct percpu_data *pd) -+{ -+ ulong hwrpb, halt_ra, halt_PC, halt_pv; -+ unsigned long processor_offset, processor_size; -+ -+ get_symbol_data("hwrpb", sizeof(void *), &hwrpb); -+ -+ readmem(hwrpb+OFFSET(hwrpb_struct_processor_offset), KVADDR, -+ &processor_offset, sizeof(ulong), -+ "hwrpb processor_offset", FAULT_ON_ERROR); -+ -+ readmem(hwrpb+OFFSET(hwrpb_struct_processor_size), KVADDR, -+ &processor_size, sizeof(ulong), -+ "hwrpb processor_size", FAULT_ON_ERROR); -+ -+ readmem(hwrpb + processor_offset + (cpu * processor_size) + -+ OFFSET(percpu_struct_halt_PC), -+ KVADDR, &halt_PC, sizeof(ulong), -+ "percpu halt_PC", FAULT_ON_ERROR); -+ -+ readmem(hwrpb + processor_offset + (cpu * processor_size) + -+ OFFSET(percpu_struct_halt_ra), -+ KVADDR, &halt_ra, sizeof(ulong), -+ "percpu halt_ra", FAULT_ON_ERROR); -+ -+ readmem(hwrpb + processor_offset + (cpu * processor_size) + -+ OFFSET(percpu_struct_halt_pv), -+ KVADDR, &halt_pv, sizeof(ulong), -+ "percpu halt_pv", FAULT_ON_ERROR); -+ -+ if (pd) { -+ pd->halt_PC = halt_PC; -+ pd->halt_ra = halt_ra; -+ pd->halt_pv = halt_pv; -+ } -+ -+ switch (flag) -+ { -+ case GET_HALT_PC: -+ return halt_PC; -+ -+ case GET_HALT_RA: -+ return halt_ra; -+ -+ case GET_HALT_PV: -+ return halt_pv; -+ -+ default: -+ return 0; -+ } -+} -+ -+/* -+ * Translate a PTE, returning TRUE if the page is _PAGE_VALID or _PAGE_PRESENT, -+ * whichever is appropriate for the machine type. If a physaddr pointer is -+ * passed in, don't print anything. -+ */ -+static int -+sw_64_translate_pte(ulong pte, void *physaddr, ulonglong unused) -+{ -+ int c, len1, len2, len3, others, page_present; -+ char buf[BUFSIZE]; -+ char buf2[BUFSIZE]; -+ char buf3[BUFSIZE]; -+ char ptebuf[BUFSIZE]; -+ char physbuf[BUFSIZE]; -+ char *arglist[MAXARGS]; -+ physaddr_t paddr; -+ -+ paddr = PTOB(pte >> 32); -+ page_present = (pte & _PAGE_VALID); -+ -+ if (physaddr) { -+ *((ulong *)physaddr) = paddr; -+ return page_present; -+ } -+ -+ sprintf(ptebuf, "%lx", pte); -+ len1 = MAX(strlen(ptebuf), strlen("PTE")); -+ fprintf(fp, "%s ", mkstring(buf, len1, CENTER|LJUST, "PTE")); -+ -+ if (!page_present && pte) { -+ swap_location(pte, buf); -+ if ((c = parse_line(buf, arglist)) != 3) -+ error(FATAL, "cannot determine swap location\n"); -+ -+ len2 = MAX(strlen(arglist[0]), strlen("SWAP")); -+ len3 = MAX(strlen(arglist[2]), strlen("OFFSET")); -+ -+ fprintf(fp, "%s %s\n", -+ mkstring(buf2, len2, CENTER|LJUST, "SWAP"), -+ mkstring(buf3, len3, CENTER|LJUST, "OFFSET")); -+ -+ strcpy(buf2, arglist[0]); -+ strcpy(buf3, arglist[2]); -+ fprintf(fp, "%s %s %s\n", -+ mkstring(ptebuf, len1, CENTER|RJUST, NULL), -+ mkstring(buf2, len2, CENTER|RJUST, NULL), -+ mkstring(buf3, len3, CENTER|RJUST, NULL)); -+ -+ return page_present; -+ } -+ -+ sprintf(physbuf, "%llx", paddr); -+ len2 = MAX(strlen(physbuf), strlen("PHYSICAL")); -+ fprintf(fp, "%s ", mkstring(buf, len2, CENTER|LJUST, "PHYSICAL")); -+ -+ fprintf(fp, "FLAGS\n"); -+ -+ fprintf(fp, "%s %s ", -+ mkstring(ptebuf, len1, CENTER|RJUST, NULL), -+ mkstring(physbuf, len2, CENTER|RJUST, NULL)); -+ fprintf(fp, "("); -+ others = 0; -+ -+ if (pte) { -+ if (pte & _PAGE_VALID) -+ fprintf(fp, "%sVALID", others++ ? "|" : ""); -+ if (pte & _PAGE_FOR) -+ fprintf(fp, "%sFOR", others++ ? "|" : ""); -+ if (pte & _PAGE_FOW) -+ fprintf(fp, "%sFOW", others++ ? "|" : ""); -+ if (pte & _PAGE_FOE) -+ fprintf(fp, "%sFOE", others++ ? "|" : ""); -+ if (pte & _PAGE_ASM) -+ fprintf(fp, "%sASM", others++ ? "|" : ""); -+ if (pte & _PAGE_KRE) -+ fprintf(fp, "%sKRE", others++ ? "|" : ""); -+ if (pte & _PAGE_URE) -+ fprintf(fp, "%sURE", others++ ? "|" : ""); -+ if (pte & _PAGE_KWE) -+ fprintf(fp, "%sKWE", others++ ? "|" : ""); -+ if (pte & _PAGE_UWE) -+ fprintf(fp, "%sUWE", others++ ? "|" : ""); -+ if (pte & _PAGE_DIRTY) -+ fprintf(fp, "%sDIRTY", others++ ? "|" : ""); -+ if (pte & _PAGE_ACCESSED) -+ fprintf(fp, "%sACCESSED", others++ ? "|" : ""); -+ } else { -+ fprintf(fp, "no mapping"); -+ } -+ -+ fprintf(fp, ")\n"); -+ -+ return page_present; -+} -+ -+ -+/* -+ * This is currently not machine-dependent, but eventually I'd prefer to use -+ * the HWPCB for the real physical memory size. -+ */ -+static uint64_t -+sw_64_memory_size(void) -+{ -+ return (generic_memory_size()); -+} -+ -+/* -+ * Determine where vmalloc'd memory starts. -+ */ -+static ulong -+sw_64_vmalloc_start(void) -+{ -+ return VMALLOC_START; -+} -+ -+/* -+ * SW_64 tasks are all stacksize-aligned. -+ */ -+static int -+sw_64_is_task_addr(ulong task) -+{ -+ return (IS_KVADDR(task) && (ALIGNED_STACK_OFFSET(task) == 0)); -+} -+ -+/* -+ * Keep or reject a symbol from the kernel namelist. -+ */ -+int -+sw_64_verify_symbol(const char *name, ulong value, char type) -+{ -+ if (CRASHDEBUG(8) && name && strlen(name)) -+ fprintf(fp, "%016lx %s\n", value, name); -+ -+ return (name && strlen(name) && (value > MIN_SYMBOL_VALUE)); -+} -+ -+/* -+ * Override smp_num_cpus if possible and necessary. -+ */ -+int -+sw_64_get_smp_cpus(void) -+{ -+ int cpus; -+ -+ if ((cpus = get_cpus_online())) -+ return cpus; -+ else -+ return kt->cpus; -+} -+ -+/* -+ * Machine dependent command. -+ */ -+void -+sw_64_cmd_mach(void) -+{ -+ int c, cflag; -+ unsigned int radix; -+ -+ cflag = radix = 0; -+ -+ while ((c = getopt(argcnt, args, "cxd")) != EOF) { -+ switch(c) -+ { -+ case 'c': -+ cflag++; -+ break; -+ -+ case 'x': -+ if (radix == 10) -+ error(FATAL, -+ "-d and -x are mutually exclusive\n"); -+ radix = 16; -+ break; -+ -+ case 'd': -+ if (radix == 16) -+ error(FATAL, -+ "-d and -x are mutually exclusive\n"); -+ radix = 10; -+ break; -+ -+ default: -+ argerrs++; -+ break; -+ } -+ } -+ -+ if (argerrs) -+ cmd_usage(pc->curcmd, SYNOPSIS); -+ -+ if (cflag) -+ display_hwrpb(radix); -+ else -+ sw_64_display_machine_stats(); -+} -+ -+/* -+ * "mach" command output. -+ */ -+static void -+sw_64_display_machine_stats(void) -+{ -+ struct new_utsname *uts; -+ char buf[BUFSIZE]; -+ ulong mhz; -+ -+ uts = &kt->utsname; -+ -+ fprintf(fp, " MACHINE TYPE: %s\n", uts->machine); -+ fprintf(fp, " MEMORY SIZE: %s\n", get_memory_size(buf)); -+ fprintf(fp, " CPUS: %d\n", kt->cpus); -+ fprintf(fp, " PROCESSOR SPEED: "); -+ if ((mhz = machdep->processor_speed())) -+ fprintf(fp, "%ld Mhz\n", mhz); -+ else -+ fprintf(fp, "(unknown)\n"); -+ fprintf(fp, " HZ: %d\n", machdep->hz); -+ fprintf(fp, " PAGE SIZE: %d\n", PAGESIZE()); -+ fprintf(fp, " L1 CACHE SIZE: %d\n", l1_cache_size()); -+ fprintf(fp, "KERNEL VIRTUAL BASE: %lx\n", machdep->kvbase); -+ fprintf(fp, "KERNEL VMALLOC BASE: %lx\n", vt->vmalloc_start); -+ fprintf(fp, " KERNEL STACK SIZE: %ld\n", STACKSIZE()); -+} -+ -+/* -+ * Display the hwrpb_struct and each percpu_struct. -+ */ -+static void -+display_hwrpb(unsigned int radix) -+{ -+ int cpu; -+ ulong hwrpb, percpu; -+ ulong processor_offset, processor_size; -+ -+ get_symbol_data("hwrpb", sizeof(void *), &hwrpb); -+ -+ readmem(hwrpb+OFFSET(hwrpb_struct_processor_offset), KVADDR, -+ &processor_offset, sizeof(ulong), -+ "hwrpb processor_offset", FAULT_ON_ERROR); -+ readmem(hwrpb+OFFSET(hwrpb_struct_processor_size), KVADDR, -+ &processor_size, sizeof(ulong), -+ "hwrpb processor_size", FAULT_ON_ERROR); -+ -+ fprintf(fp, "HWRPB:\n"); -+ dump_struct("hwrpb_struct", hwrpb, radix); -+ -+ for (cpu = 0; cpu < kt->cpus; cpu++) { -+ fprintf(fp, "\nCPU %d:\n", cpu); -+ percpu = hwrpb + processor_offset + (processor_size * cpu); -+ dump_struct("percpu_struct", percpu, radix); -+ } -+} -+ -+/* -+ * Perform any leftover pre-prompt machine-specific initialization tasks here. -+ */ -+static void -+sw_64_post_init(void) -+{ -+ modify_signame(7, "SIGEMT", NULL); -+ modify_signame(10, "SIGBUS", NULL); -+ modify_signame(12, "SIGSYS", NULL); -+ modify_signame(16, "SIGURG", NULL); -+ modify_signame(17, "SIGSTOP", NULL); -+ modify_signame(18, "SIGTSTP", NULL); -+ modify_signame(19, "SIGCONT", NULL); -+ modify_signame(20, "SIGCHLD", NULL); -+ modify_signame(23, "SIGIO", "SIGPOLL"); -+ modify_signame(29, "SIGINFO", "SIGPWR"); -+ modify_signame(30, "SIGUSR1", NULL); -+ modify_signame(31, "SIGUSR2", NULL); -+} -+ -+ -+#endif /* SW_64 */ diff --git a/0002-crash-8.0.4-sw64.patch b/0002-crash-8.0.4-sw64.patch new file mode 100644 index 0000000000000000000000000000000000000000..653151708da2d56d71d8f896caddc93072274160 --- /dev/null +++ b/0002-crash-8.0.4-sw64.patch @@ -0,0 +1,105884 @@ +diff --git a/Makefile b/Makefile +index a94a243..b7f0b1a 100644 +--- a/Makefile ++++ b/Makefile +@@ -24,8 +24,8 @@ PROGRAM=crash + # Supported targets: X86 ALPHA PPC IA64 PPC64 SPARC64 + # TARGET and GDB_CONF_FLAGS will be configured automatically by configure + # +-TARGET= +-GDB_CONF_FLAGS= ++TARGET=SW_64 ++GDB_CONF_FLAGS=--host=sw_64-sunway-linux-gnu --build=sw_64-sunway-linux-gnu --with-guile=no --with-python --with-expat + + ARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ -e s/arm.*/arm/ -e s/sa110/arm/) + ifeq (${ARCH}, ppc64) +@@ -35,10 +35,10 @@ endif + # + # GDB, GDB_FILES, GDB_OFILES and GDB_PATCH_FILES will be configured automatically by configure + # +-GDB= +-GDB_FILES= +-GDB_OFILES= +-GDB_PATCH_FILES= ++GDB=gdb-10.2 ++GDB_FILES=${GDB_10.2_FILES} ++GDB_OFILES=${GDB_10.2_OFILES} ++GDB_PATCH_FILES=gdb-10.2.patch + + # + # Default installation directory +@@ -65,7 +65,7 @@ CFILES=main.c tools.c global_data.c memory.c filesys.c help.c task.c \ + kernel.c test.c gdb_interface.c configure.c net.c dev.c bpf.c \ + printk.c \ + alpha.c x86.c ppc.c ia64.c s390.c s390x.c s390dbf.c ppc64.c x86_64.c \ +- arm.c arm64.c mips.c mips64.c riscv64.c sparc64.c \ ++ arm.c arm64.c mips.c mips64.c riscv64.c sparc64.c sw_64.c\ + extensions.c remote.c va_server.c va_server_v1.c symbols.c cmdline.c \ + lkcd_common.c lkcd_v1.c lkcd_v2_v3.c lkcd_v5.c lkcd_v7.c lkcd_v8.c\ + lkcd_fix_mem.c s390_dump.c lkcd_x86_trace.c \ +@@ -85,7 +85,7 @@ OBJECT_FILES=main.o tools.o global_data.o memory.o filesys.o help.o task.o \ + build_data.o kernel.o test.o gdb_interface.o net.o dev.o bpf.o \ + printk.o \ + alpha.o x86.o ppc.o ia64.o s390.o s390x.o s390dbf.o ppc64.o x86_64.o \ +- arm.o arm64.o mips.o mips64.o riscv64.o sparc64.o \ ++ arm.o arm64.o mips.o mips64.o riscv64.o sparc64.o sw_64.o\ + extensions.o remote.o va_server.o va_server_v1.o symbols.o cmdline.o \ + lkcd_common.o lkcd_v1.o lkcd_v2_v3.o lkcd_v5.o lkcd_v7.o lkcd_v8.o \ + lkcd_fix_mem.o s390_dump.o netdump.o diskdump.o makedumpfile.o xendump.o \ +@@ -190,7 +190,7 @@ GDB_10.2_OFILES=${GDB}/gdb/symtab.o crash_target.o + # + # GDB_FLAGS is passed up from the gdb Makefile. + # +-GDB_FLAGS= ++GDB_FLAGS=-DGDB_10_2 + + # + # WARNING_OPTIONS and WARNING_ERROR are both applied on a per-file basis. +@@ -199,15 +199,15 @@ GDB_FLAGS= + # usefulness is also dependent upon the processor's compiler -- your mileage + # may vary. + # +-#WARNING_OPTIONS=-Wall -O2 -Wstrict-prototypes -Wmissing-prototypes -fstack-protector -Wformat-security ++WARNING_OPTIONS=-Wall -O2 -Wstrict-prototypes -Wmissing-prototypes -fstack-protector -Wformat-security + #WARNING_ERROR=-Werror + + # TARGET_CFLAGS will be configured automatically by configure +-TARGET_CFLAGS= ++TARGET_CFLAGS=-O2 -D_SW64_ -DSCORE + + CRASH_CFLAGS=-g -D${TARGET} ${TARGET_CFLAGS} ${GDB_FLAGS} ${CFLAGS} + +-GPL_FILES= ++GPL_FILES=COPYING3 + TAR_FILES=${SOURCE_FILES} Makefile ${GPL_FILES} README .rh_rpm_package crash.8 \ + ${EXTENSION_SOURCE_FILES} ${MEMORY_DRIVER_FILES} + CSCOPE_FILES=${SOURCE_FILES} +@@ -415,6 +415,9 @@ x86.o: ${GENERIC_HFILES} ${REDHAT_HFILES} x86.c + alpha.o: ${GENERIC_HFILES} alpha.c + ${CC} -c ${CRASH_CFLAGS} alpha.c ${WARNING_OPTIONS} ${WARNING_ERROR} + ++sw_64.o: ${GENERIC_HFILES} sw_64.c ++ ${CC} -c ${CRASH_CFLAGS} sw_64.c ${WARNING_OPTIONS} ${WARNING_ERROR} ++ + ppc.o: ${GENERIC_HFILES} ppc.c + ${CC} -c ${CRASH_CFLAGS} ppc.c ${WARNING_OPTIONS} ${WARNING_ERROR} + +diff --git a/configure.c b/configure.c +index 08b52be..ea6a418 100644 +--- a/configure.c ++++ b/configure.c +@@ -108,6 +108,7 @@ void add_extra_lib(char *); + #undef SPARC64 + #undef MIPS64 + #undef RISCV64 ++#undef SW_64 + + #define UNKNOWN 0 + #define X86 1 +@@ -124,6 +125,7 @@ void add_extra_lib(char *); + #define SPARC64 12 + #define MIPS64 13 + #define RISCV64 14 ++#define SW_64 15 + + #define TARGET_X86 "TARGET=X86" + #define TARGET_ALPHA "TARGET=ALPHA" +@@ -139,6 +141,7 @@ void add_extra_lib(char *); + #define TARGET_MIPS64 "TARGET=MIPS64" + #define TARGET_SPARC64 "TARGET=SPARC64" + #define TARGET_RISCV64 "TARGET=RISCV64" ++#define TARGET_SW_64 "TARGET=SW_64" + + #define TARGET_CFLAGS_X86 "TARGET_CFLAGS=-D_FILE_OFFSET_BITS=64" + #define TARGET_CFLAGS_ALPHA "TARGET_CFLAGS=" +@@ -163,6 +166,7 @@ void add_extra_lib(char *); + #define TARGET_CFLAGS_SPARC64 "TARGET_CFLAGS=" + #define TARGET_CFLAGS_RISCV64 "TARGET_CFLAGS=" + #define TARGET_CFLAGS_RISCV64_ON_X86_64 "TARGET_CFLAGS=" ++#define TARGET_CFLAGS_SW_64 "TARGET_CFLAGS=-O2 -D_SW64_ -DSCORE" + + #define GDB_TARGET_DEFAULT "GDB_CONF_FLAGS=" + #define GDB_TARGET_ARM_ON_X86 "GDB_CONF_FLAGS=--target=arm-elf-linux" +@@ -174,6 +178,7 @@ void add_extra_lib(char *); + #define GDB_TARGET_MIPS_ON_X86 "GDB_CONF_FLAGS=--target=mipsel-elf-linux" + #define GDB_TARGET_MIPS_ON_X86_64 "GDB_CONF_FLAGS=--target=mipsel-elf-linux CFLAGS=-m32 CXXFLAGS=-m32" + #define GDB_TARGET_RISCV64_ON_X86_64 "GDB_CONF_FLAGS=--target=riscv64-unknown-linux-gnu" ++#define GDB_TARGET_SW_64 "GDB_CONF_FLAGS=--host=sw_64-sunway-linux-gnu --build=sw_64-sunway-linux-gnu --with-guile=no --with-python --with-expat" + + /* + * The original plan was to allow the use of a particular version +@@ -373,6 +378,9 @@ get_current_configuration(struct supported_gdb_version *sp) + #ifdef __alpha__ + target_data.target = ALPHA; + #endif ++#ifdef __sw_64__ ++ target_data.target = SW_64; ++#endif + #ifdef __i386__ + target_data.target = X86; + #endif +@@ -650,6 +658,9 @@ show_configuration(void) + case ALPHA: + printf("TARGET: ALPHA\n"); + break; ++ case SW_64: ++ printf("TARGET: SW_64\n"); ++ break; + case PPC: + printf("TARGET: PPC\n"); + break; +@@ -733,6 +744,11 @@ build_configure(struct supported_gdb_version *sp) + target = TARGET_ALPHA; + target_CFLAGS = TARGET_CFLAGS_ALPHA; + break; ++ case SW_64: ++ target = TARGET_SW_64; ++ target_CFLAGS = TARGET_CFLAGS_SW_64; ++ gdb_conf_flags = GDB_TARGET_SW_64; ++ break; + case PPC: + target = TARGET_PPC; + if (target_data.host == PPC64) { +@@ -1627,6 +1643,8 @@ set_initial_target(struct supported_gdb_version *sp) + target_data.initial_gdb_target = X86; + else if (strncmp(buf, "ALPHA", strlen("ALPHA")) == 0) + target_data.initial_gdb_target = ALPHA; ++ else if (strncmp(buf, "SW_64", strlen("SW_64")) == 0) ++ target_data.initial_gdb_target = SW_64; + else if (strncmp(buf, "PPC64", strlen("PPC64")) == 0) + target_data.initial_gdb_target = PPC64; + else if (strncmp(buf, "PPC", strlen("PPC")) == 0) +@@ -1658,6 +1676,7 @@ target_to_name(int target) + { + case X86: return("X86"); + case ALPHA: return("ALPHA"); ++ case SW_64: return("SW_64"); + case PPC: return("PPC"); + case IA64: return("IA64"); + case S390: return("S390"); +@@ -1690,6 +1709,10 @@ name_to_target(char *name) + return ALPHA; + else if (strncmp(name, "alpha", strlen("alpha")) == 0) + return ALPHA; ++ else if (strncmp(name, "SW_64", strlen("SW_64")) == 0) ++ return SW_64; ++ else if (strncmp(name, "sw_64", strlen("sw_64")) == 0) ++ return SW_64; + else if (strncmp(name, "PPC64", strlen("PPC64")) == 0) + return PPC64; + else if (strncmp(name, "ppc64", strlen("ppc64")) == 0) +diff --git a/defs.h b/defs.h +index 788f63a..d5a0951 100644 +--- a/defs.h ++++ b/defs.h +@@ -76,10 +76,13 @@ + #if !defined(X86) && !defined(X86_64) && !defined(ALPHA) && !defined(PPC) && \ + !defined(IA64) && !defined(PPC64) && !defined(S390) && !defined(S390X) && \ + !defined(ARM) && !defined(ARM64) && !defined(MIPS) && !defined(MIPS64) && \ +- !defined(RISCV64) && !defined(SPARC64) ++ !defined(RISCV64) && !defined(SPARC64) && !defined(SW_64) + #ifdef __alpha__ + #define ALPHA + #endif ++#ifdef __sw_64__ ++#define SW_64 ++#endif + #ifdef __i386__ + #define X86 + #endif +@@ -132,6 +135,9 @@ + #ifdef ALPHA + #define NR_CPUS (64) + #endif ++#ifdef SW_64 ++#define NR_CPUS (512) ++#endif + #ifdef PPC + #define NR_CPUS (32) + #endif +@@ -4044,6 +4050,98 @@ typedef signed int s32; + + #endif /* ALPHA */ + ++#ifdef SW_64 ++#define _64BIT_ ++#define MACHINE_TYPE "SW_64" ++ ++#define PAGEBASE(X) (((unsigned long)(X)) & (unsigned long)machdep->pagemask) ++ ++#define PTOV(X) ((unsigned long)(X)+(machdep->kvbase)) ++#define VTOP(X) ((unsigned long)(X)-(machdep->kvbase)) ++#define VMALLOC_END (0xfffff80000000000) ++#define IS_VMALLOC_ADDR(X) ((ulong)(X) >= vt->vmalloc_start && (ulong)(X) <= VMALLOC_END) ++#define KSEG_BASE (0xfff0000000000000) ++#define _PFN_MASK (0xFFFFFFFFF0000000) ++#define PFN_SHIFT 28 ++#define VMALLOC_START (0xfffff00000000000) ++#define MIN_SYMBOL_VALUE (KSEG_BASE) ++ ++#define PGDIR_SHIFT (PAGESHIFT() + 3*(PAGESHIFT()-3)) ++#define PUD_SHIFT (PAGESHIFT() + 2*(PAGESHIFT()-3)) ++#define PMD_SHIFT (PAGESHIFT() + 1*(PAGESHIFT()-3)) ++#define PTRS_PER_PAGE (1024) ++ ++#define PTRS_PER_PGD (1UL << (PAGESHIFT()-3)) ++ ++/* ++ * OSF/1 PAL-code-imposed page table bits ++ */ ++#define _PAGE_VALID 0x0001 ++#define _PAGE_FOR 0x0002 /* used for page protection (fault on read) */ ++#define _PAGE_FOW 0x0004 /* used for page protection (fault on write) */ ++#define _PAGE_FOE 0x0008 /* used for page protection (fault on exec) */ ++#define _PAGE_ASM 0x0010 ++#define _PAGE_KRE 0x0100 /* xxx - see below on the "accessed" bit */ ++#define _PAGE_URE 0x0200 /* xxx */ ++#define _PAGE_KWE 0x1000 /* used to do the dirty bit in software */ ++#define _PAGE_UWE 0x2000 /* used to do the dirty bit in software */ ++ ++/* .. and these are ours ... */ ++#define _PAGE_DIRTY 0x20000 ++#define _PAGE_ACCESSED 0x40000 ++ ++#define SWP_TYPE(entry) (((entry) >> 32) & 0xff) ++#define SWP_OFFSET(entry) ((entry) >> 40) ++#define __swp_type(entry) SWP_TYPE(entry) ++#define __swp_offset(entry) SWP_OFFSET(entry) ++ ++#define TIF_SIGPENDING (2) ++ ++struct sw64_pt_regs { ++ unsigned long r0; ++ unsigned long r1; ++ unsigned long r2; ++ unsigned long r3; ++ unsigned long r4; ++ unsigned long r5; ++ unsigned long r6; ++ unsigned long r7; ++ unsigned long r8; ++ unsigned long r9; ++ unsigned long r10; ++ unsigned long r11; ++ unsigned long r12; ++ unsigned long r13; ++ unsigned long r14; ++ unsigned long r15; ++ unsigned long r16; ++ unsigned long r17; ++ unsigned long r18; ++ unsigned long r19; ++ unsigned long r20; ++ unsigned long r21; ++ unsigned long r22; ++ unsigned long r23; ++ unsigned long r24; ++ unsigned long r25; ++ unsigned long r26; ++ unsigned long r27; ++ unsigned long r28; ++ unsigned long gp; ++ unsigned long usp; ++ unsigned long pc; ++ unsigned long ps; ++}; ++ ++struct machine_specific { ++ struct sw64_pt_regs *panic_task_regs; ++}; ++ ++#ifdef roundup ++#undef roundup ++#endif ++#define roundup(x, y) ((((x)+((y)-1))/(y))*(y)) ++#endif /* SW_64 */ + #ifdef PPC + #define _32BIT_ + #define MACHINE_TYPE "PPC" +@@ -4723,6 +4821,10 @@ struct machine_specific { + #define MAX_HEXADDR_STRLEN (16) + #define UVADDR_PRLEN (11) + #endif ++#ifdef SW_64 ++#define MAX_HEXADDR_STRLEN (16) ++#define UVADDR_PRLEN (11) ++#endif + #ifdef PPC + #define MAX_HEXADDR_STRLEN (8) + #define UVADDR_PRLEN (8) +@@ -4962,6 +5064,12 @@ static inline unsigned int __const_hweight8(unsigned long w) + #define SA_SHIRQ 0x40000000 + #endif + ++#ifdef SW_64 ++#define SA_PROBE SA_ONESHOT ++#define SA_SAMPLE_RANDOM SA_RESTART ++#define SA_SHIRQ 0x40000000 ++#endif ++ + #ifdef PPC + #define SA_PROBE SA_ONESHOT + #define SA_SAMPLE_RANDOM SA_RESTART +@@ -5358,6 +5466,9 @@ void dump_build_data(void); + #ifdef ALPHA + #define machdep_init(X) alpha_init(X) + #endif ++#ifdef SW_64 ++#define machdep_init(X) sw64_init(X) ++#endif + #ifdef PPC + #define machdep_init(X) ppc_init(X) + #endif +@@ -5849,6 +5960,9 @@ void display_help_screen(char *); + #ifdef ALPHA + #define dump_machdep_table(X) alpha_dump_machdep_table(X) + #endif ++#ifdef SW_64 ++#define dump_machdep_table(X) sw64_dump_machdep_table(X) ++#endif + #ifdef PPC + #define dump_machdep_table(X) ppc_dump_machdep_table(X) + #endif +@@ -6307,6 +6421,18 @@ void alpha_dump_machdep_table(ulong); + (task_to_context(X)->processor == 0)) + #endif + ++/* ++ * sw_64.c ++ */ ++#ifdef SW_64 ++void sw64_init(int); ++void sw64_dump_machdep_table(ulong); ++#define display_idt_table() \ ++ error(FATAL, "-d option is not applicable to alpha architecture\n") ++ ++#define HWRESET_TASK(X) ((machdep->flags & HWRESET) && is_task_active(X)) ++#endif ++ + /* + * x86.c + */ +diff --git a/diskdump.c b/diskdump.c +index 0fe46f4..71dcc6d 100644 +--- a/diskdump.c ++++ b/diskdump.c +@@ -29,6 +29,7 @@ + #include "vmcore.h" + + #define BITMAP_SECT_LEN 4096 ++#define ECHOFLAGS (ECHO | ECHOE | ECHOK | ECHONL) + + struct diskdump_data { + char *filename; +@@ -198,7 +199,7 @@ resize_note_pointers: + * within this file, resize the arrays accordingly. + */ + if (machine_type("X86_64") || machine_type("X86") || +- machine_type("ARM64")) { ++ machine_type("ARM64") || machine_type("SW_64")) { + if ((dd->nt_prstatus_percpu = realloc(dd->nt_prstatus_percpu, + dd->num_prstatus_notes * sizeof(void *))) == NULL) + error(FATAL, +@@ -309,6 +310,80 @@ dump_is_partial(const struct disk_dump_header *header) + divideup(divideup(dd->max_mapnr, 8), dd->block_size) * 2; + } + ++int set_disp_mode(int fd,int option) ++{ ++ int err; ++ struct termios term; ++ if(tcgetattr(fd,&term)==-1){ ++ perror("Cannot get the attribution of the terminal"); ++ return 1; ++ } ++ if(option) ++ term.c_lflag|=ECHOFLAGS; ++ else ++ term.c_lflag &=~ECHOFLAGS; ++ err=tcsetattr(fd,TCSAFLUSH,&term); ++ if(err==-1 && err==EINTR){ ++ perror("Cannot set the attribution of the terminal"); ++ return 1; ++ } ++ return 0; ++} ++ ++int _try_decrypt(int fd, char *file) ++{ ++ int ret; ++ FILE * fp; ++ char cmd[1024]; ++ char password[1024]; ++ char header[8]; ++ if (lseek(fd, 0, SEEK_SET) == -1) { ++ if (CRASHDEBUG(1)) ++ error(INFO, "diskdump / compressed kdump: cannot lseek dump header\n"); ++ return -1; ++ } ++ if (read(fd, header, 8) < 8) { ++ if (CRASHDEBUG(1)) ++ error(INFO, "diskdump / compressed kdump: cannot read dump header\n"); ++ return -1; ++ } ++ if(strncmp("Salted__", &header, 8) != 0){ ++ if (lseek(fd, 0, SEEK_SET) == -1) { ++ if (CRASHDEBUG(1)) ++ error(INFO, "diskdump / compressed kdump: cannot lseek dump header\n"); ++ return -1; ++ } ++ return fd; ++ } ++ close(fd); ++ printf("enter des-ede3-cbc decryption password:\n"); ++ memset(password, 0, 1024); ++ set_disp_mode(STDIN_FILENO,0); ++ scanf("%s", &password); ++ set_disp_mode(STDIN_FILENO,1); ++ ++ printf("decrypting...\n"); ++ memset(cmd, 0, 1024); ++ sprintf(cmd, ++ "openssl enc -d -des3 -salt -k %s -iter 2 -pbkdf2 -in %s -out /tmp/tmp.raw\n", ++ password, file); ++ fp = popen(cmd, "r"); ++ ret = pclose(fp); ++ if(ret != 0){ ++ error(INFO, "exec openssl error. %s\n", ++ strerror(errno)); ++ return -1; ++ } ++ printf("decrypt finish.\n"); ++ ++ fd = open("/tmp/tmp.raw", O_RDONLY); ++ if (fd < 0) { ++ error(INFO, "diskdump / compressed kdump: unable to open dump file %s\n", file); ++ return -1; ++ } ++ return fd; ++} ++ + static int + open_dump_file(char *file) + { +@@ -323,6 +398,10 @@ open_dump_file(char *file) + if (KDUMP_SPLIT()) + dd = calloc(1, sizeof(*dd)); + ++ fd = _try_decrypt(fd, file); ++ if(fd == -1) ++ return FALSE; ++ + dd->dfd = fd; + return TRUE; + } +@@ -683,6 +762,9 @@ restart: + else if (STRNEQ(header->utsname.machine, "riscv64") && + machine_type_mismatch(file, "RISCV64", NULL, 0)) + goto err; ++ else if (STRNEQ(header->utsname.machine, "sw_64") && ++ machine_type_mismatch(file, "SW_64", NULL, 0)) ++ goto err; + + if (header->block_size != block_size) { + block_size = header->block_size; +@@ -702,7 +784,8 @@ restart: + DISKDUMP_VALID() ? "diskdump" : "compressed kdump", + header->nr_cpus); + if (!machine_type("S390") && !machine_type("S390X") && +- !machine_type("X86") && !machine_type("X86_64")) { ++ !machine_type("X86") && !machine_type("X86_64") && ++ !machine_type("SW_64")) { + if (DISKDUMP_VALID()) + goto err; + } +@@ -825,6 +908,8 @@ restart: + dd->machine_type = EM_ARM; + else if (machine_type("MIPS") || machine_type("MIPS64")) + dd->machine_type = EM_MIPS; ++ else if (machine_type("ALPHA")) ++ dd->machine_type = EM_ALPHA; + else if (machine_type("X86")) + dd->machine_type = EM_386; + else if (machine_type("X86_64")) +@@ -843,6 +928,8 @@ restart: + dd->machine_type = EM_SPARCV9; + else if (machine_type("RISCV64")) + dd->machine_type = EM_RISCV; ++ else if (machine_type("SW_64")) ++ dd->machine_type = EM_SW_64; + else { + error(INFO, "%s: unsupported machine type: %s\n", + DISKDUMP_VALID() ? "diskdump" : "compressed kdump", +@@ -1628,6 +1715,12 @@ get_diskdump_regs_sparc64(struct bt_info *bt, ulong *eip, ulong *esp) + machdep->get_stack_frame(bt, eip, esp); + } + ++static void ++get_diskdump_regs_sw64(struct bt_info *bt, ulong *eip, ulong *esp) ++{ ++ machdep->get_stack_frame(bt, eip, esp); ++} ++ + /* + * Send the request to the proper architecture hander. + */ +@@ -1686,6 +1779,10 @@ get_diskdump_regs(struct bt_info *bt, ulong *eip, ulong *esp) + get_diskdump_regs_riscv64(bt, eip, esp); + break; + ++ case EM_SW_64: ++ get_diskdump_regs_sw64(bt, eip, esp); ++ break; ++ + default: + error(FATAL, "%s: unsupported machine type: %s\n", + DISKDUMP_VALID() ? "diskdump" : "compressed kdump", +@@ -1833,7 +1930,7 @@ dump_note_offsets(FILE *fp) + if (machine_type("X86_64") || machine_type("S390X") || + machine_type("ARM64") || machine_type("PPC64") || + machine_type("SPARC64") || machine_type("MIPS64") || +- machine_type("RISCV64")) { ++ machine_type("RISCV64") || machine_type("SW_64")) { + note64 = (void *)dd->notes_buf + tot; + len = sizeof(Elf64_Nhdr); + if (STRNEQ((char *)note64 + len, "QEMU")) +@@ -2590,6 +2687,64 @@ diskdump_display_regs(int cpu, FILE *ofp) + UINT(user_regs + sizeof(ulong) * 34)); + } + ++ if (machine_type("SW_64")) { ++ note64 = dd->nt_prstatus_percpu[cpu]; ++ len = sizeof(Elf64_Nhdr); ++ len = roundup(len + note64->n_namesz, 4); ++ len = roundup(len + note64->n_descsz, 4); ++ if (!valid_note_address((unsigned char *)note64 + len)) { ++ error(INFO, "invalid NT_PRSTATUS note for cpu %d\n", cpu); ++ return; ++ } ++ user_regs = (char *)note64 + len - SIZE(elf_prstatus) + OFFSET(elf_prstatus_pr_reg); ++ fprintf(ofp, ++ " v0: %016lx t0: %016lx t1: %016lx\n" ++ " t2: %016lx t3: %016lx t4: %016lx\n" ++ " t5: %016lx t6: %016lx t7: %016lx\n" ++ " r9: %016lx r10: %016lx r11: %016lx\n" ++ " r12: %016lx r13: %016lx r14: %016lx\n" ++ " r15: %016lx r16: %016lx r17: %016lx\n" ++ " r18: %016lx a3: %016lx a4: %016lx\n" ++ " a5: %016lx t8: %016lx t9: %016lx\n" ++ " t10: %016lx t11: %016lx ra: %016lx\n" ++ " pv: %016lx at: %016lx gp: %016lx\n" ++ " usp: %016lx pc: %016lx unique: %016lx\n", ++ ULONG(user_regs + sizeof(ulong) * 0), ++ ULONG(user_regs + sizeof(ulong) * 1), ++ ULONG(user_regs + sizeof(ulong) * 2), ++ ULONG(user_regs + sizeof(ulong) * 3), ++ ULONG(user_regs + sizeof(ulong) * 4), ++ ULONG(user_regs + sizeof(ulong) * 5), ++ ULONG(user_regs + sizeof(ulong) * 6), ++ ULONG(user_regs + sizeof(ulong) * 7), ++ ULONG(user_regs + sizeof(ulong) * 8), ++ ULONG(user_regs + sizeof(ulong) * 9), ++ ULONG(user_regs + sizeof(ulong) * 10), ++ ULONG(user_regs + sizeof(ulong) * 11), ++ ULONG(user_regs + sizeof(ulong) * 12), ++ ULONG(user_regs + sizeof(ulong) * 13), ++ ULONG(user_regs + sizeof(ulong) * 14), ++ ULONG(user_regs + sizeof(ulong) * 15), ++ ULONG(user_regs + sizeof(ulong) * 16), ++ ULONG(user_regs + sizeof(ulong) * 17), ++ ULONG(user_regs + sizeof(ulong) * 18), ++ ULONG(user_regs + sizeof(ulong) * 19), ++ ULONG(user_regs + sizeof(ulong) * 20), ++ ULONG(user_regs + sizeof(ulong) * 21), ++ ULONG(user_regs + sizeof(ulong) * 22), ++ ULONG(user_regs + sizeof(ulong) * 23), ++ ULONG(user_regs + sizeof(ulong) * 24), ++ ULONG(user_regs + sizeof(ulong) * 25), ++ ULONG(user_regs + sizeof(ulong) * 26), ++ ULONG(user_regs + sizeof(ulong) * 27), ++ ULONG(user_regs + sizeof(ulong) * 28), ++ ULONG(user_regs + sizeof(ulong) * 29), ++ ULONG(user_regs + sizeof(ulong) * 30), ++ ULONG(user_regs + sizeof(ulong) * 31), ++ ULONG(user_regs + sizeof(ulong) * 32) ++ ); ++ } ++ + if (machine_type("X86")) { + note32 = dd->nt_prstatus_percpu[cpu]; + len = sizeof(Elf32_Nhdr); +@@ -2641,7 +2796,7 @@ dump_registers_for_compressed_kdump(void) + !(machine_type("X86") || machine_type("X86_64") || + machine_type("ARM64") || machine_type("PPC64") || + machine_type("MIPS") || machine_type("MIPS64") || +- machine_type("RISCV64"))) ++ machine_type("RISCV64") || machine_type("SW_64"))) + error(FATAL, "-r option not supported for this dumpfile\n"); + + if (machine_type("ARM64") && (kt->cpus != dd->num_prstatus_notes)) +diff --git a/extensions/Makefile b/extensions/Makefile +index a608073..af3a593 100644 +--- a/extensions/Makefile ++++ b/extensions/Makefile +@@ -30,7 +30,10 @@ all: link_defs $(CONTRIB_SO) + + link_defs: + @rm -f defs.h +- @ln ../defs.h ++ @ln ../defs.h defs.h ++ ++defs.h: ++ @ln ../defs.h defs.h + + $(CONTRIB_SO): %.so: %.c defs.h + @if [ -f $*.mk ]; then \ +diff --git a/gdb-10.2.patch b/gdb-10.2.patch +index d81030d..bf62a2b 100644 +--- a/gdb-10.2.patch ++++ b/gdb-10.2.patch +@@ -1,3026 +1,99460 @@ +- +-# When this file is updated in an existing source tree, it gets re-applied +-# during the next build using "patch -N --fuzz=0", which ignores patches +-# that have already been applied. However, if a gdb file has been modified +-# multiple times, the subsequent patching may fail to recognize that a +-# given patch has been previously applied, and will attempt to re-apply it. +-# To prevent any unintended consequences, this file also acts as a +-# shell script that can restore any gdb file to its original state prior +-# to all subsequent patch applications. +- +-tar xvzmf gdb-10.2.tar.gz \ +- gdb-10.2/gdb/symtab.c \ +- gdb-10.2/gdb/printcmd.c \ +- gdb-10.2/gdb/symfile.c \ +- gdb-10.2/gdb/Makefile.in \ +- gdb-10.2/gdb/dwarf2/read.c \ +- gdb-10.2/gdb/ada-lang.c +- +-exit 0 +- +---- gdb-10.2/Makefile.in.orig +-+++ gdb-10.2/Makefile.in +-@@ -340,6 +340,9 @@ AR_FOR_BUILD = @AR_FOR_BUILD@ +- AS_FOR_BUILD = @AS_FOR_BUILD@ +- CC_FOR_BUILD = @CC_FOR_BUILD@ +- CFLAGS_FOR_BUILD = @CFLAGS_FOR_BUILD@ +-+ifeq (${CRASH_TARGET}, PPC64) +-+CFLAGS_FOR_BUILD += -m64 -fPIC +-+endif +- CXXFLAGS_FOR_BUILD = @CXXFLAGS_FOR_BUILD@ +- CXX_FOR_BUILD = @CXX_FOR_BUILD@ +- DLLTOOL_FOR_BUILD = @DLLTOOL_FOR_BUILD@ +-@@ -406,6 +409,9 @@ GNATBIND = @GNATBIND@ +- GNATMAKE = @GNATMAKE@ +- +- CFLAGS = @CFLAGS@ +-+ifeq (${CRASH_TARGET}, PPC64) +-+CFLAGS += -m64 -fPIC +-+endif +- LDFLAGS = @LDFLAGS@ +- LIBCFLAGS = $(CFLAGS) +- CXXFLAGS = @CXXFLAGS@ +---- gdb-10.2/gdb/Makefile.in.orig +-+++ gdb-10.2/gdb/Makefile.in +-@@ -571,7 +571,7 @@ CONFIG_DEP_SUBDIR = $(addsuffix /$(DEPDIR),$(CONFIG_SRC_SUBDIR)) +- # It is also possible that you will need to add -I/usr/include/sys if +- # your system doesn't have fcntl.h in /usr/include (which is where it +- # should be according to Posix). +--DEFS = @DEFS@ +-+DEFS = -DCRASH_MERGE @DEFS@ +- GDB_CFLAGS = -I. -I$(srcdir) -I$(srcdir)/config \ +- -DLOCALEDIR="\"$(localedir)\"" $(DEFS) +- +-@@ -1135,6 +1135,7 @@ COMMON_SFILES = \ +- symmisc.c \ +- symtab.c \ +- target.c \ +-+ ../../crash_target.c \ +- target-connection.c \ +- target-dcache.c \ +- target-descriptions.c \ +-@@ -1564,7 +1565,7 @@ COMMON_OBS = $(DEPFILES) $(CONFIG_OBS) $(YYOBJ) \ +- $(SUBDIR_TARGET_OBS) \ +- $(SUBDIR_GCC_COMPILE_OBS) +- +--SUBDIRS = doc @subdirs@ data-directory +-+SUBDIRS = build_no_subdirs +- CLEANDIRS = $(SUBDIRS) +- +- # List of subdirectories in the build tree that must exist. +-@@ -1606,8 +1607,8 @@ generated_files = \ +- # Flags needed to compile Python code +- PYTHON_CFLAGS = @PYTHON_CFLAGS@ ++diff -Nuar gdb-10.2/bfd/archures.c gdb-10.2/bfd/archures.c ++--- gdb-10.2/bfd/archures.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/archures.c 2025-04-16 17:06:51.902086800 +0800 ++@@ -308,6 +308,9 @@ ++ .#define bfd_mach_alpha_ev4 0x10 ++ .#define bfd_mach_alpha_ev5 0x20 ++ .#define bfd_mach_alpha_ev6 0x30 +++. bfd_arch_sw_64, {* Sw_64 *} +++.#define bfd_mach_sw_64_sw6a 0x32 +++.#define bfd_mach_sw_64_sw6b 0x33 ++ . bfd_arch_arm, {* Advanced Risc Machines ARM. *} ++ .#define bfd_mach_arm_unknown 0 ++ .#define bfd_mach_arm_2 1 ++@@ -611,6 +614,7 @@ + +--all: gdb$(EXEEXT) $(CONFIG_ALL) gdb-gdb.py gdb-gdb.gdb +-- @$(MAKE) $(FLAGS_TO_PASS) DO=all "DODIRS=`echo $(SUBDIRS) | sed 's/testsuite//'`" subdir_do +-+all: gdb$(EXEEXT) gdb-gdb.py gdb-gdb.gdb +-+ @$(MAKE) -s $(FLAGS_TO_PASS) DO=all "DODIRS=`echo $(SUBDIRS) | sed 's/testsuite//'`" subdir_do ++ extern const bfd_arch_info_type bfd_aarch64_arch; ++ extern const bfd_arch_info_type bfd_alpha_arch; +++extern const bfd_arch_info_type bfd_sw_64_arch; ++ extern const bfd_arch_info_type bfd_arc_arch; ++ extern const bfd_arch_info_type bfd_arm_arch; ++ extern const bfd_arch_info_type bfd_avr_arch; ++@@ -700,6 +704,7 @@ ++ #else ++ &bfd_aarch64_arch, ++ &bfd_alpha_arch, +++ &bfd_sw_64_arch, ++ &bfd_arc_arch, ++ &bfd_arm_arch, ++ &bfd_avr_arch, ++diff -Nuar gdb-10.2/bfd/bfd-in2.h gdb-10.2/bfd/bfd-in2.h ++--- gdb-10.2/bfd/bfd-in2.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/bfd-in2.h 2025-04-16 17:06:51.902086800 +0800 ++@@ -1708,6 +1708,9 @@ ++ #define bfd_mach_alpha_ev4 0x10 ++ #define bfd_mach_alpha_ev5 0x20 ++ #define bfd_mach_alpha_ev6 0x30 +++ bfd_arch_sw_64, /* Sw_64 */ +++#define bfd_mach_sw_64_sw6a 0x32 +++#define bfd_mach_sw_64_sw6b 0x33 ++ bfd_arch_arm, /* Advanced Risc Machines ARM. */ ++ #define bfd_mach_arm_unknown 0 ++ #define bfd_mach_arm_2 1 ++@@ -2326,6 +2329,10 @@ ++ displacement is used on the Alpha. */ ++ BFD_RELOC_32_PCREL_S2, ++ BFD_RELOC_16_PCREL_S2, +++#ifndef XWB20200308 +++ BFD_RELOC_20_PCREL_S2, +++ BFD_RELOC_24_PCREL_S2, +++#endif ++ BFD_RELOC_23_PCREL_S2, + +- # Rule for compiling .c files in the top-level gdb directory. +- # The order-only dependencies ensure that we create the build subdirectories. +-@@ -1864,9 +1865,10 @@ libgdb.a: $(LIBGDB_OBS) +- # Removing the old gdb first works better if it is running, at least on SunOS. +- gdb$(EXEEXT): gdb.o $(LIBGDB_OBS) $(CDEPS) $(TDEPLIBS) +- $(SILENCE) rm -f gdb$(EXEEXT) +-+ @(cd ../..; make --no-print-directory GDB_FLAGS=-DGDB_10_2 library) +- $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) $(WIN32LDAPP) \ +-- -o gdb$(EXEEXT) gdb.o $(LIBGDB_OBS) \ +-- $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) +-+ -o $(shell /bin/cat mergeobj) $(LIBGDB_OBS) \ +-+ $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) $(shell /bin/cat mergelibs) +- ifneq ($(CODESIGN_CERT),) +- $(ECHO_SIGN) $(CODESIGN) -s $(CODESIGN_CERT) gdb$(EXEEXT) +- endif +-@@ -2530,9 +2532,9 @@ ifeq ($(DEPMODE),depmode=gcc3) +- # into place if the compile succeeds. We need this because gcc does +- # not atomically write the dependency output file. +- override COMPILE.post = -c -o $@ -MT $@ -MMD -MP \ +-- -MF $(@D)/$(DEPDIR)/$(basename $(@F)).Tpo +--override POSTCOMPILE = @mv $(@D)/$(DEPDIR)/$(basename $(@F)).Tpo \ +-- $(@D)/$(DEPDIR)/$(basename $(@F)).Po +-+ -MF $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo +-+override POSTCOMPILE = @mv $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo \ +-+ $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Po +- else +- override COMPILE.pre = source='$<' object='$@' libtool=no \ +- DEPDIR=$(DEPDIR) $(DEPMODE) $(depcomp) \ +---- gdb-10.2/gdb/cli/cli-cmds.c.orig +-+++ gdb-10.2/gdb/cli/cli-cmds.c +-@@ -435,6 +435,11 @@ complete_command (const char *arg, int from_tty) +- } +- } ++ /* High 22 bits and low 10 bits of 32-bit value, placed into lower bits of ++@@ -2547,6 +2554,99 @@ ++ BFD_RELOC_ALPHA_TPREL_LO16, ++ BFD_RELOC_ALPHA_TPREL16, + +-+#ifdef CRASH_MERGE +-+static int crash_from_tty = 0; +-+extern "C" void untrusted_file(FILE *, char *); +-+#endif +++/* Sw_64 ECOFF and ELF relocations. Some of these treat the symbol or +++"addend" in some special way. +++For GPDISP_HI16 ("gpdisp") relocations, the symbol is ignored when +++writing; when reading, it will be the absolute section symbol. The +++addend is the displacement in bytes of the "lda" instruction from +++the "ldah" instruction (which is at the address of this reloc). */ +++ BFD_RELOC_SW_64_GPDISP_HI16, + + +- int +- is_complete_command (struct cmd_list_element *c) +- { +-@@ -654,8 +659,32 @@ find_and_open_script (const char *script_file, int search_path) +- close (fd); +- errno = save_errno; +- } +-- else +-- opened.emplace (gdb_file_up (result), std::move (full_path)); +-+#ifdef CRASH_MERGE +-+ /* +-+ * Only allow trusted versions of .gdbinit files to be +-+ * sourced during session initialization. +-+ */ +-+ if (crash_from_tty == -1) +++/* For GPDISP_LO16 ("ignore") relocations, the symbol is handled as +++with GPDISP_HI16 relocs. The addend is ignored when writing the +++relocations out, and is filled in with the file's GP value on +++reading, for convenience. */ +++ BFD_RELOC_SW_64_GPDISP_LO16, +++/* The ELF GPDISP relocation is exactly the same as the GPDISP_HI16 +++relocation except that there is no accompanying GPDISP_LO16 +++relocation. */ +++ BFD_RELOC_SW_64_GPDISP, +++/*> The Sw_64 LITERAL/LITUSE relocs are produced by a symbol reference; +++> the assembler turns it into a LDQ instruction to load the address of +++> the symbol, and then fills in a register in the real instruction. +++> +++> The LITERAL reloc, at the LDQ instruction, refers to the .lita +++> section symbol. The addend is ignored when writing, but is filled +++> in with the file's GP value on reading, for convenience, as with the +++> GPDISP_LO16 reloc. +++> +++> The ELF_LITERAL reloc is somewhere between 16_GOTOFF and GPDISP_LO16. +++> It should refer to the symbol to be referenced, as with 16_GOTOFF, +++> but it generates output not based on the position within the .got +++> section, but relative to the GP value chosen for the file during the +++> final link stage. +++> +++> The LITUSE reloc, on the instruction using the loaded address, gives +++> information to the linker that it might be able to use to optimize +++> away some literal section references. The symbol is ignored (read +++> as the absolute section symbol), and the "addend" indicates the type +++> of instruction using the register: +++> 1 - "memory" fmt insn +++> 2 - byte-manipulation (byte offset reg) +++> 3 - jsr (target of branch) */ +++ BFD_RELOC_SW_64_LITERAL, +++ BFD_RELOC_SW_64_ELF_LITERAL, +++ BFD_RELOC_SW_64_LITUSE, +++/* The HINT relocation indicates a value that should be filled into the +++"hint" field of a jmp/jsr/ret instruction, for possible branch- +++prediction logic which may be provided on some processors. */ +++ BFD_RELOC_SW_64_HINT, +++ +++/* The LINKAGE relocation outputs a linkage pair in the object file, +++which is filled by the linker. */ +++ BFD_RELOC_SW_64_LINKAGE, +++ +++/* The CODEADDR relocation outputs a STO_CA in the object file, +++which is filled by the linker. */ +++ BFD_RELOC_SW_64_CODEADDR, +++/* The GPREL_HI/LO relocations together form a 32-bit offset from the +++GP register. */ +++ BFD_RELOC_SW_64_GPREL_HI16, +++ BFD_RELOC_SW_64_GPREL_LO16, +++ +++/* Like BFD_RELOC_23_PCREL_S2, except that the source and target must +++share a common GP, and the target address is adjusted forSTO_SW_64_STD_GPLOAD. */ +++ BFD_RELOC_SW_64_BRSGP, +++ +++/* The NOP relocation outputs a NOP if the longword displacementbetween two procedure entry points is < 2^21. */ +++ BFD_RELOC_SW_64_NOP, +++/* The BSR relocation outputs a BSR if the longword displacement +++between two procedure entry points is < 2^21. */ +++ BFD_RELOC_SW_64_BSR, +++ +++/* The LDA relocation outputs a LDA if the longword displacement +++between two procedure entry points is < 2^16. */ +++ BFD_RELOC_SW_64_LDA, +++ +++/* The BOH relocation outputs a BSR if the longword displacement +++between two procedure entry points is < 2^21, or else a hint. */ +++ BFD_RELOC_SW_64_BOH, +++ +++/* Sw_64 thread-local storage relocations. */ +++ BFD_RELOC_SW_64_TLSGD, +++ BFD_RELOC_SW_64_TLSLDM, +++ BFD_RELOC_SW_64_DTPMOD64, +++ BFD_RELOC_SW_64_GOTDTPREL16, +++ BFD_RELOC_SW_64_DTPREL64, +++ BFD_RELOC_SW_64_DTPREL_HI16, +++ BFD_RELOC_SW_64_DTPREL_LO16, +++ BFD_RELOC_SW_64_DTPREL16, +++ BFD_RELOC_SW_64_GOTTPREL16, +++ BFD_RELOC_SW_64_TPREL64, +++ BFD_RELOC_SW_64_TPREL_HI16, +++ BFD_RELOC_SW_64_TPREL_LO16, +++ BFD_RELOC_SW_64_TPREL16, +++ ++ /* The MIPS jump instruction. */ ++ BFD_RELOC_MIPS_JMP, ++ BFD_RELOC_MICROMIPS_JMP, ++diff -Nuar gdb-10.2/bfd/coff-sw_64.c gdb-10.2/bfd/coff-sw_64.c ++--- gdb-10.2/bfd/coff-sw_64.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/coff-sw_64.c 2025-04-16 17:06:51.902086800 +0800 ++@@ -0,0 +1,2467 @@ +++/* BFD back-end for SW_64 Extended-Coff files. +++ Copyright (C) 1993-2019 Free Software Foundation, Inc. +++ Modified from coff-mips.c by Steve Chamberlain and +++ Ian Lance Taylor . +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++#include "sysdep.h" +++#include "bfd.h" +++#include "bfdlink.h" +++#include "libbfd.h" +++#include "coff/internal.h" +++#include "coff/sym.h" +++#include "coff/symconst.h" +++#include "coff/ecoff.h" +++#include "coff/sw_64.h" +++#include "aout/ar.h" +++#include "libcoff.h" +++#include "libecoff.h" +++ +++/* Prototypes for static functions. */ +++ +++ +++ +++/* ECOFF has COFF sections, but the debugging information is stored in +++ a completely different format. ECOFF targets use some of the +++ swapping routines from coffswap.h, and some of the generic COFF +++ routines in coffgen.c, but, unlike the real COFF targets, do not +++ use coffcode.h itself. +++ +++ Get the generic COFF swapping routines, except for the reloc, +++ symbol, and lineno ones. Give them ecoff names. Define some +++ accessor macros for the large sizes used for Sw_64 ECOFF. */ +++ +++#define GET_FILEHDR_SYMPTR H_GET_64 +++#define PUT_FILEHDR_SYMPTR H_PUT_64 +++#define GET_AOUTHDR_TSIZE H_GET_64 +++#define PUT_AOUTHDR_TSIZE H_PUT_64 +++#define GET_AOUTHDR_DSIZE H_GET_64 +++#define PUT_AOUTHDR_DSIZE H_PUT_64 +++#define GET_AOUTHDR_BSIZE H_GET_64 +++#define PUT_AOUTHDR_BSIZE H_PUT_64 +++#define GET_AOUTHDR_ENTRY H_GET_64 +++#define PUT_AOUTHDR_ENTRY H_PUT_64 +++#define GET_AOUTHDR_TEXT_START H_GET_64 +++#define PUT_AOUTHDR_TEXT_START H_PUT_64 +++#define GET_AOUTHDR_DATA_START H_GET_64 +++#define PUT_AOUTHDR_DATA_START H_PUT_64 +++#define GET_SCNHDR_PADDR H_GET_64 +++#define PUT_SCNHDR_PADDR H_PUT_64 +++#define GET_SCNHDR_VADDR H_GET_64 +++#define PUT_SCNHDR_VADDR H_PUT_64 +++#define GET_SCNHDR_SIZE H_GET_64 +++#define PUT_SCNHDR_SIZE H_PUT_64 +++#define GET_SCNHDR_SCNPTR H_GET_64 +++#define PUT_SCNHDR_SCNPTR H_PUT_64 +++#define GET_SCNHDR_RELPTR H_GET_64 +++#define PUT_SCNHDR_RELPTR H_PUT_64 +++#define GET_SCNHDR_LNNOPTR H_GET_64 +++#define PUT_SCNHDR_LNNOPTR H_PUT_64 +++ +++#define SW_64ECOFF +++ +++#define NO_COFF_RELOCS +++#define NO_COFF_SYMBOLS +++#define NO_COFF_LINENOS +++#define coff_swap_filehdr_in sw_64_ecoff_swap_filehdr_in +++#define coff_swap_filehdr_out sw_64_ecoff_swap_filehdr_out +++#define coff_swap_aouthdr_in sw_64_ecoff_swap_aouthdr_in +++#define coff_swap_aouthdr_out sw_64_ecoff_swap_aouthdr_out +++#define coff_swap_scnhdr_in sw_64_ecoff_swap_scnhdr_in +++#define coff_swap_scnhdr_out sw_64_ecoff_swap_scnhdr_out +++#include "coffswap.h" +++ +++/* Get the ECOFF swapping routines. */ +++#define ECOFF_64 +++#include "ecoffswap.h" +++ +++/* How to process the various reloc types. */ +++ +++static bfd_reloc_status_type +++reloc_nil (bfd *abfd ATTRIBUTE_UNUSED, +++ arelent *reloc ATTRIBUTE_UNUSED, +++ asymbol *sym ATTRIBUTE_UNUSED, +++ void * data ATTRIBUTE_UNUSED, +++ asection *sec ATTRIBUTE_UNUSED, +++ bfd *output_bfd ATTRIBUTE_UNUSED, +++ char **error_message ATTRIBUTE_UNUSED) +++{ +++ return bfd_reloc_ok; +++} +++ +++/* In case we're on a 32-bit machine, construct a 64-bit "-1" value +++ from smaller values. Start with zero, widen, *then* decrement. */ +++#define MINUS_ONE (((bfd_vma)0) - 1) +++ +++static reloc_howto_type sw_64_howto_table[] = +++{ +++ /* Reloc type 0 is ignored by itself. However, it appears after a +++ GPDISP reloc to identify the location where the low order 16 bits +++ of the gp register are loaded. */ +++ HOWTO (SW_64_R_IGNORE, /* type */ +++ 0, /* rightshift */ +++ 0, /* size (0 = byte, 1 = short, 2 = long) */ +++ 8, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ reloc_nil, /* special_function */ +++ "IGNORE", /* name */ +++ TRUE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A 32 bit reference to a symbol. */ +++ HOWTO (SW_64_R_REFLONG, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "REFLONG", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 64 bit reference to a symbol. */ +++ HOWTO (SW_64_R_REFQUAD, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "REFQUAD", /* name */ +++ TRUE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 32 bit GP relative offset. This is just like REFLONG except +++ that when the value is used the value of the gp register will be +++ added in. */ +++ HOWTO (SW_64_R_GPREL32, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "GPREL32", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Used for an instruction that refers to memory off the GP +++ register. The offset is 16 bits of the 32 bit instruction. This +++ reloc always seems to be against the .lita section. */ +++ HOWTO (SW_64_R_LITERAL, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "LITERAL", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* This reloc only appears immediately following a LITERAL reloc. +++ It identifies a use of the literal. It seems that the linker can +++ use this to eliminate a portion of the .lita section. The symbol +++ index is special: 1 means the literal address is in the base +++ register of a memory format instruction; 2 means the literal +++ address is in the byte offset register of a byte-manipulation +++ instruction; 3 means the literal address is in the target +++ register of a jsr instruction. This does not actually do any +++ relocation. */ +++ HOWTO (SW_64_R_LITUSE, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ reloc_nil, /* special_function */ +++ "LITUSE", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Load the gp register. This is always used for a ldah instruction +++ which loads the upper 16 bits of the gp register. The next reloc +++ will be an IGNORE reloc which identifies the location of the lda +++ instruction which loads the lower 16 bits. The symbol index of +++ the GPDISP instruction appears to actually be the number of bytes +++ between the ldah and lda instructions. This gives two different +++ ways to determine where the lda instruction is; I don't know why +++ both are used. The value to use for the relocation is the +++ difference between the GP value and the current location; the +++ load will always be done against a register holding the current +++ address. */ +++ HOWTO (SW_64_R_GPDISP, /* type */ +++ 16, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ reloc_nil, /* special_function */ +++ "GPDISP", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A 21 bit branch. The native assembler generates these for +++ branches within the text segment, and also fills in the PC +++ relative offset in the instruction. */ +++ HOWTO (SW_64_R_BRADDR, /* type */ +++ 2, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 21, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "BRADDR", /* name */ +++ TRUE, /* partial_inplace */ +++ 0x1fffff, /* src_mask */ +++ 0x1fffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A hint for a jump to a register. */ +++ HOWTO (SW_64_R_HINT, /* type */ +++ 2, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 14, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "HINT", /* name */ +++ TRUE, /* partial_inplace */ +++ 0x3fff, /* src_mask */ +++ 0x3fff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* 16 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL16, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "SREL16", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* 32 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL32, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "SREL32", /* name */ +++ TRUE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 64 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL64, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "SREL64", /* name */ +++ TRUE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Push a value on the reloc evaluation stack. */ +++ HOWTO (SW_64_R_OP_PUSH, /* type */ +++ 0, /* rightshift */ +++ 0, /* size (0 = byte, 1 = short, 2 = long) */ +++ 0, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "OP_PUSH", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Store the value from the stack at the given address. Store it in +++ a bitfield of size r_size starting at bit position r_offset. */ +++ HOWTO (SW_64_R_OP_STORE, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "OP_STORE", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Subtract the reloc address from the value on the top of the +++ relocation stack. */ +++ HOWTO (SW_64_R_OP_PSUB, /* type */ +++ 0, /* rightshift */ +++ 0, /* size (0 = byte, 1 = short, 2 = long) */ +++ 0, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "OP_PSUB", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Shift the value on the top of the relocation stack right by the +++ given value. */ +++ HOWTO (SW_64_R_OP_PRSHIFT, /* type */ +++ 0, /* rightshift */ +++ 0, /* size (0 = byte, 1 = short, 2 = long) */ +++ 0, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "OP_PRSHIFT", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Adjust the GP value for a new range in the object file. */ +++ HOWTO (SW_64_R_GPVALUE, /* type */ +++ 0, /* rightshift */ +++ 0, /* size (0 = byte, 1 = short, 2 = long) */ +++ 0, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ 0, /* special_function */ +++ "GPVALUE", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE) /* pcrel_offset */ +++}; +++ +++/* Recognize an Sw_64 ECOFF file. */ +++ +++static const bfd_target * +++sw_64_ecoff_object_p (bfd *abfd) +++{ +++ static const bfd_target *ret; +++ +++ ret = coff_object_p (abfd); +++ +++ if (ret != NULL) + + { +-+ struct stat statbuf; +-+ FILE *stream = result; +-+ int _fd = fileno (stream); +-+ if (fstat (_fd, &statbuf) < 0) +-+ { +-+ perror_with_name (full_path.get()); +-+ fclose (stream); +-+ return opened; +-+ } +-+ if (statbuf.st_uid != getuid () || (statbuf.st_mode & S_IWOTH)) +-+ { +-+ untrusted_file(NULL, full_path.get()); +-+ fclose (stream); +-+ return opened; +-+ } +++ asection *sec; +++ +++ /* Sw_64 ECOFF has a .pdata section. The lnnoptr field of the +++ .pdata section is the number of entries it contains. Each +++ entry takes up 8 bytes. The number of entries is required +++ since the section is aligned to a 16 byte boundary. When we +++ link .pdata sections together, we do not want to include the +++ alignment bytes. We handle this on input by faking the size +++ of the .pdata section to remove the unwanted alignment bytes. +++ On output we will set the lnnoptr field and force the +++ alignment. */ +++ sec = bfd_get_section_by_name (abfd, _PDATA); +++ if (sec != (asection *) NULL) +++ { +++ bfd_size_type size; +++ +++ size = sec->line_filepos * 8; +++ BFD_ASSERT (size == sec->size +++ || size + 8 == sec->size); +++ if (! bfd_set_section_size (sec, size)) +++ return NULL; +++ } + + } +-+#endif +-+ opened.emplace (gdb_file_up (result), std::move (full_path)); + + +- +- return opened; +- } +-@@ -719,7 +748,11 @@ source_script_with_search (const char *file, int from_tty, int search_path) +- If the source command was invoked interactively, throw an +- error. Otherwise (e.g. if it was invoked by a script), +- just emit a warning, rather than cause an error. */ +-+#ifdef CRASH_MERGE +-+ if (from_tty > 0) +-+#else +- if (from_tty) +-+#endif +- perror_with_name (file); +- else +- { +-@@ -743,7 +776,14 @@ source_script_with_search (const char *file, int from_tty, int search_path) +- void +- source_script (const char *file, int from_tty) +- { +-+#ifdef CRASH_MERGE +-+ crash_from_tty = from_tty; +-+#endif +- source_script_with_search (file, from_tty, 0); +-+#ifdef CRASH_MERGE +-+ crash_from_tty = 0; +-+#endif +++ return ret; +++} + + +- } +- +- static void +---- gdb-10.2/gdb/defs.h.orig +-+++ gdb-10.2/gdb/defs.h +-@@ -629,4 +629,7 @@ DEF_ENUM_FLAGS_TYPE (enum user_selected_what_flag, user_selected_what); +- +- #include "utils.h" +- +-+#ifdef CRASH_MERGE +-+extern "C" int gdb_main_entry(int, char **); +-+#endif +- #endif /* #ifndef DEFS_H */ +---- gdb-10.2/gdb/dwarf2/read.c.orig +-+++ gdb-10.2/gdb/dwarf2/read.c +-@@ -3015,7 +3015,11 @@ read_gdb_index_from_buffer (const char *filename, +- indices. */ +- if (version < 4) +- { +-+#ifdef CRASH_MERGE +-+ static int warning_printed = 1; +-+#else +- static int warning_printed = 0; +-+#endif +- if (!warning_printed) +- { +- warning (_("Skipping obsolete .gdb_index section in %s."), +-@@ -3034,7 +3038,11 @@ read_gdb_index_from_buffer (const char *filename, +- "set use-deprecated-index-sections on". */ +- if (version < 6 && !deprecated_ok) +- { +-+#ifdef CRASH_MERGE +-+ static int warning_printed = 1; +-+#else +- static int warning_printed = 0; +-+#endif +- if (!warning_printed) +- { +- warning (_("\ +---- gdb-10.2/gdb/main.c.orig +-+++ gdb-10.2/gdb/main.c +-@@ -392,6 +392,14 @@ start_event_loop () +- return; +- } +- +-+#ifdef CRASH_MERGE +-+extern "C" void update_gdb_hooks(void); +-+extern "C" void main_loop(void); +-+extern "C" unsigned long crash_get_kaslr_offset(void); +-+extern "C" int console(const char *, ...); +-+void crash_target_init (void); +-+#endif +++/* See whether the magic number matches. */ + + +- /* Call command_loop. */ +- +- /* Prevent inlining this function for the benefit of GDB's selftests +-@@ -925,7 +933,11 @@ captured_main_1 (struct captured_main_args *context) +- } +- } +- +-+#ifdef CRASH_MERGE +-+ save_original_signals_state (1); +-+#else +- save_original_signals_state (quiet); +-+#endif +- +- /* Try to set up an alternate signal stack for SIGSEGV handlers. */ +- gdb::alternate_signal_stack signal_stack; +-@@ -999,7 +1011,7 @@ captured_main_1 (struct captured_main_args *context) +- { +- print_gdb_version (gdb_stdout, false); +- wrap_here (""); +-- printf_filtered ("\n"); +-+ printf_filtered ("\n\n"); +- exit (0); +- } +- +-@@ -1038,6 +1050,10 @@ captured_main_1 (struct captured_main_args *context) +- look at things by now. Initialize the default interpreter. */ +- set_top_level_interpreter (interpreter_p); +- +-+#ifdef CRASH_MERGE +-+ update_gdb_hooks(); +-+#endif +++static bfd_boolean +++sw_64_ecoff_bad_format_hook (bfd *abfd ATTRIBUTE_UNUSED, +++ void * filehdr) +++{ +++ struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr; + + +- /* FIXME: cagney/2003-02-03: The big hack (part 2 of 2) that lets +- GDB retain the old MI1 interpreter startup behavior. Output the +- copyright message after the interpreter is installed when it is +-@@ -1066,7 +1082,11 @@ captured_main_1 (struct captured_main_args *context) +- if (!system_gdbinit.empty () && !inhibit_gdbinit) +- { +- for (const std::string &file : system_gdbinit) +-+#ifdef CRASH_MERGE +-+ ret = catch_command_errors (source_script, file.c_str (), -1); +-+#else +- ret = catch_command_errors (source_script, file.c_str (), 0); +-+#endif +- } +- +- /* Read and execute $HOME/.gdbinit file, if it exists. This is done +-@@ -1075,7 +1095,11 @@ captured_main_1 (struct captured_main_args *context) +- debugging or what directory you are in. */ +- +- if (!home_gdbinit.empty () && !inhibit_gdbinit && !inhibit_home_gdbinit) +-+#ifdef CRASH_MERGE +-+ ret = catch_command_errors (source_script, home_gdbinit.c_str (), -1); +-+#else +- ret = catch_command_errors (source_script, home_gdbinit.c_str (), 0); +-+#endif +- +- /* Process '-ix' and '-iex' options early. */ +- for (i = 0; i < cmdarg_vec.size (); i++) +-@@ -1121,7 +1145,11 @@ captured_main_1 (struct captured_main_args *context) +- !batch_flag); +- if (ret != 0) +- ret = catch_command_errors (symbol_file_add_main_adapter, +-+#ifdef CRASH_MERGE +-+ symarg, 0); +-+#else +- symarg, !batch_flag); +-+#endif +- } +- else +- { +-@@ -1191,7 +1219,11 @@ captured_main_1 (struct captured_main_args *context) +- { +- auto_load_local_gdbinit_loaded = 1; +- +-+#ifdef CRASH_MERGE +-+ ret = catch_command_errors (source_script, local_gdbinit.c_str (), -1); +-+#else +- ret = catch_command_errors (source_script, local_gdbinit.c_str (), 0); +++ if (! SW_64_ECOFF_BADMAG (*internal_f)) +++ return TRUE; +++ +++ if (SW_64_ECOFF_COMPRESSEDMAG (*internal_f)) +++ _bfd_error_handler +++ (_("%pB: cannot handle compressed Sw_64 binaries; " +++ "use compiler flags, or objZ, to generate uncompressed binaries"), +++ abfd); +++ +++ return FALSE; +++} +++ +++/* This is a hook called by coff_real_object_p to create any backend +++ specific information. */ +++ +++static void * +++sw_64_ecoff_mkobject_hook (bfd *abfd, void * filehdr, void * aouthdr) +++{ +++ void * ecoff; +++ +++ ecoff = _bfd_ecoff_mkobject_hook (abfd, filehdr, aouthdr); +++ +++ if (ecoff != NULL) +++ { +++ struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr; +++ +++ /* Set additional BFD flags according to the object type from the +++ machine specific file header flags. */ +++ switch (internal_f->f_flags & F_SW_64_OBJECT_TYPE_MASK) +++ { +++ case F_SW_64_SHARABLE: +++ abfd->flags |= DYNAMIC; +++ break; +++ case F_SW_64_CALL_SHARED: +++ /* Always executable if using shared libraries as the run time +++ loader might resolve undefined references. */ +++ abfd->flags |= (DYNAMIC | EXEC_P); +++ break; +++ } +++ } +++ return ecoff; +++} +++ +++/* Reloc handling. */ +++ +++/* Swap a reloc in. */ +++ +++static void +++sw_64_ecoff_swap_reloc_in (bfd *abfd, +++ void * ext_ptr, +++ struct internal_reloc *intern) +++{ +++ const RELOC *ext = (RELOC *) ext_ptr; +++ +++ intern->r_vaddr = H_GET_64 (abfd, ext->r_vaddr); +++ intern->r_symndx = H_GET_32 (abfd, ext->r_symndx); +++ +++ BFD_ASSERT (bfd_header_little_endian (abfd)); +++ +++ intern->r_type = ((ext->r_bits[0] & RELOC_BITS0_TYPE_LITTLE) +++ >> RELOC_BITS0_TYPE_SH_LITTLE); +++ intern->r_extern = (ext->r_bits[1] & RELOC_BITS1_EXTERN_LITTLE) != 0; +++ intern->r_offset = ((ext->r_bits[1] & RELOC_BITS1_OFFSET_LITTLE) +++ >> RELOC_BITS1_OFFSET_SH_LITTLE); +++ /* Ignored the reserved bits. */ +++ intern->r_size = ((ext->r_bits[3] & RELOC_BITS3_SIZE_LITTLE) +++ >> RELOC_BITS3_SIZE_SH_LITTLE); +++ +++ if (intern->r_type == SW_64_R_LITUSE +++ || intern->r_type == SW_64_R_GPDISP) +++ { +++ /* Handle the LITUSE and GPDISP relocs specially. Its symndx +++ value is not actually a symbol index, but is instead a +++ special code. We put the code in the r_size field, and +++ clobber the symndx. */ +++ if (intern->r_size != 0) +++ abort (); +++ intern->r_size = intern->r_symndx; +++ intern->r_symndx = RELOC_SECTION_NONE; +++ } +++ else if (intern->r_type == SW_64_R_IGNORE) +++ { +++ /* The IGNORE reloc generally follows a GPDISP reloc, and is +++ against the .lita section. The section is irrelevant. */ +++ if (! intern->r_extern && +++ intern->r_symndx == RELOC_SECTION_ABS) +++ abort (); +++ if (! intern->r_extern && intern->r_symndx == RELOC_SECTION_LITA) +++ intern->r_symndx = RELOC_SECTION_ABS; +++ } +++} +++ +++/* Swap a reloc out. */ +++ +++static void +++sw_64_ecoff_swap_reloc_out (bfd *abfd, +++ const struct internal_reloc *intern, +++ void * dst) +++{ +++ RELOC *ext = (RELOC *) dst; +++ long symndx; +++ unsigned char size; +++ +++ /* Undo the hackery done in swap_reloc_in. */ +++ if (intern->r_type == SW_64_R_LITUSE +++ || intern->r_type == SW_64_R_GPDISP) +++ { +++ symndx = intern->r_size; +++ size = 0; +++ } +++ else if (intern->r_type == SW_64_R_IGNORE +++ && ! intern->r_extern +++ && intern->r_symndx == RELOC_SECTION_ABS) +++ { +++ symndx = RELOC_SECTION_LITA; +++ size = intern->r_size; +++ } +++ else +++ { +++ symndx = intern->r_symndx; +++ size = intern->r_size; +++ } +++ +++ /* XXX FIXME: The maximum symndx value used to be 14 but this +++ fails with object files produced by DEC's C++ compiler. +++ Where does the value 14 (or 15) come from anyway ? */ +++ BFD_ASSERT (intern->r_extern +++ || (intern->r_symndx >= 0 && intern->r_symndx <= 15)); +++ +++ H_PUT_64 (abfd, intern->r_vaddr, ext->r_vaddr); +++ H_PUT_32 (abfd, symndx, ext->r_symndx); +++ +++ BFD_ASSERT (bfd_header_little_endian (abfd)); +++ +++ ext->r_bits[0] = ((intern->r_type << RELOC_BITS0_TYPE_SH_LITTLE) +++ & RELOC_BITS0_TYPE_LITTLE); +++ ext->r_bits[1] = ((intern->r_extern ? RELOC_BITS1_EXTERN_LITTLE : 0) +++ | ((intern->r_offset << RELOC_BITS1_OFFSET_SH_LITTLE) +++ & RELOC_BITS1_OFFSET_LITTLE)); +++ ext->r_bits[2] = 0; +++ ext->r_bits[3] = ((size << RELOC_BITS3_SIZE_SH_LITTLE) +++ & RELOC_BITS3_SIZE_LITTLE); +++} +++ +++/* Finish canonicalizing a reloc. Part of this is generic to all +++ ECOFF targets, and that part is in ecoff.c. The rest is done in +++ this backend routine. It must fill in the howto field. */ +++ +++static void +++sw_64_adjust_reloc_in (bfd *abfd, +++ const struct internal_reloc *intern, +++ arelent *rptr) +++{ +++ if (intern->r_type > SW_64_R_GPVALUE) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("%pB: unsupported relocation type %#x"), +++ abfd, intern->r_type); +++ bfd_set_error (bfd_error_bad_value); +++ rptr->addend = 0; +++ rptr->howto = NULL; +++ return; +++ } +++ +++ switch (intern->r_type) +++ { +++ case SW_64_R_BRADDR: +++ case SW_64_R_SREL16: +++ case SW_64_R_SREL32: +++ case SW_64_R_SREL64: +++ /* This relocs appear to be fully resolved when they are against +++ internal symbols. Against external symbols, BRADDR at least +++ appears to be resolved against the next instruction. */ +++ if (! intern->r_extern) +++ rptr->addend = 0; +++ else +++ rptr->addend = - (intern->r_vaddr + 4); +++ break; +++ +++ case SW_64_R_GPREL32: +++ case SW_64_R_LITERAL: +++ /* Copy the gp value for this object file into the addend, to +++ ensure that we are not confused by the linker. */ +++ if (! intern->r_extern) +++ rptr->addend += ecoff_data (abfd)->gp; +++ break; +++ +++ case SW_64_R_LITUSE: +++ case SW_64_R_GPDISP: +++ /* The LITUSE and GPDISP relocs do not use a symbol, or an +++ addend, but they do use a special code. Put this code in the +++ addend field. */ +++ rptr->addend = intern->r_size; +++ break; +++ +++ case SW_64_R_OP_STORE: +++ /* The STORE reloc needs the size and offset fields. We store +++ them in the addend. */ +++ BFD_ASSERT (intern->r_offset <= 256); +++ rptr->addend = (intern->r_offset << 8) + intern->r_size; +++ break; +++ +++ case SW_64_R_OP_PUSH: +++ case SW_64_R_OP_PSUB: +++ case SW_64_R_OP_PRSHIFT: +++ /* The PUSH, PSUB and PRSHIFT relocs do not actually use an +++ address. I believe that the address supplied is really an +++ addend. */ +++ rptr->addend = intern->r_vaddr; +++ break; +++ +++ case SW_64_R_GPVALUE: +++ /* Set the addend field to the new GP value. */ +++ rptr->addend = intern->r_symndx + ecoff_data (abfd)->gp; +++ break; +++ +++ case SW_64_R_IGNORE: +++ /* If the type is SW_64_R_IGNORE, make sure this is a reference +++ to the absolute section so that the reloc is ignored. For +++ some reason the address of this reloc type is not adjusted by +++ the section vma. We record the gp value for this object file +++ here, for convenience when doing the GPDISP relocation. */ +++ rptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr; +++ rptr->address = intern->r_vaddr; +++ rptr->addend = ecoff_data (abfd)->gp; +++ break; +++ +++ default: +++ break; +++ } +++ +++ rptr->howto = &sw_64_howto_table[intern->r_type]; +++} +++ +++/* When writing out a reloc we need to pull some values back out of +++ the addend field into the reloc. This is roughly the reverse of +++ sw_64_adjust_reloc_in, except that there are several changes we do +++ not need to undo. */ +++ +++static void +++sw_64_adjust_reloc_out (bfd *abfd ATTRIBUTE_UNUSED, +++ const arelent *rel, +++ struct internal_reloc *intern) +++{ +++ switch (intern->r_type) +++ { +++ case SW_64_R_LITUSE: +++ case SW_64_R_GPDISP: +++ intern->r_size = rel->addend; +++ break; +++ +++ case SW_64_R_OP_STORE: +++ intern->r_size = rel->addend & 0xff; +++ intern->r_offset = (rel->addend >> 8) & 0xff; +++ break; +++ +++ case SW_64_R_OP_PUSH: +++ case SW_64_R_OP_PSUB: +++ case SW_64_R_OP_PRSHIFT: +++ intern->r_vaddr = rel->addend; +++ break; +++ +++ case SW_64_R_IGNORE: +++ intern->r_vaddr = rel->address; +++ break; +++ +++ default: +++ break; +++ } +++} +++ +++/* The size of the stack for the relocation evaluator. */ +++#define RELOC_STACKSIZE (10) +++ +++/* Sw_64 ECOFF relocs have a built in expression evaluator as well as +++ other interdependencies. Rather than use a bunch of special +++ functions and global variables, we use a single routine to do all +++ the relocation for a section. I haven't yet worked out how the +++ assembler is going to handle this. */ +++ +++static bfd_byte * +++sw_64_ecoff_get_relocated_section_contents (bfd *abfd, +++ struct bfd_link_info *link_info, +++ struct bfd_link_order *link_order, +++ bfd_byte *data, +++ bfd_boolean relocatable, +++ asymbol **symbols) +++{ +++ bfd *input_bfd = link_order->u.indirect.section->owner; +++ asection *input_section = link_order->u.indirect.section; +++ long reloc_size = bfd_get_reloc_upper_bound (input_bfd, input_section); +++ arelent **reloc_vector = NULL; +++ long reloc_count; +++ bfd *output_bfd = relocatable ? abfd : (bfd *) NULL; +++ bfd_vma gp; +++ bfd_size_type sz; +++ bfd_boolean gp_undefined; +++ bfd_vma stack[RELOC_STACKSIZE]; +++ int tos = 0; +++ +++ if (reloc_size < 0) +++ goto error_return; +++ reloc_vector = (arelent **) bfd_malloc ((bfd_size_type) reloc_size); +++ if (reloc_vector == NULL && reloc_size != 0) +++ goto error_return; +++ +++ sz = input_section->rawsize ? input_section->rawsize : input_section->size; +++ if (! bfd_get_section_contents (input_bfd, input_section, data, 0, sz)) +++ goto error_return; +++ +++ reloc_count = bfd_canonicalize_reloc (input_bfd, input_section, +++ reloc_vector, symbols); +++ if (reloc_count < 0) +++ goto error_return; +++ if (reloc_count == 0) +++ goto successful_return; +++ +++ /* Get the GP value for the output BFD. */ +++ gp_undefined = FALSE; +++ gp = _bfd_get_gp_value (abfd); +++ if (gp == 0) +++ { +++ if (relocatable) +++ { +++ asection *sec; +++ bfd_vma lo; +++ +++ /* Make up a value. */ +++ lo = (bfd_vma) -1; +++ for (sec = abfd->sections; sec != NULL; sec = sec->next) +++ { +++ if (sec->vma < lo +++ && (strcmp (sec->name, ".sbss") == 0 +++ || strcmp (sec->name, ".sdata") == 0 +++ || strcmp (sec->name, ".lit4") == 0 +++ || strcmp (sec->name, ".lit8") == 0 +++ || strcmp (sec->name, ".lita") == 0)) +++ lo = sec->vma; +++ } +++ gp = lo + 0x8000; +++ _bfd_set_gp_value (abfd, gp); +++ } +++ else +++ { +++ struct bfd_link_hash_entry *h; +++ +++ h = bfd_link_hash_lookup (link_info->hash, "_gp", FALSE, FALSE, +++ TRUE); +++ if (h == (struct bfd_link_hash_entry *) NULL +++ || h->type != bfd_link_hash_defined) +++ gp_undefined = TRUE; +++ else +++ { +++ gp = (h->u.def.value +++ + h->u.def.section->output_section->vma +++ + h->u.def.section->output_offset); +++ _bfd_set_gp_value (abfd, gp); +++ } +++ } +++ } +++ +++ for (; *reloc_vector != (arelent *) NULL; reloc_vector++) +++ { +++ arelent *rel; +++ bfd_reloc_status_type r; +++ char *err; +++ +++ rel = *reloc_vector; +++ r = bfd_reloc_ok; +++ switch (rel->howto->type) +++ { +++ case SW_64_R_IGNORE: +++ rel->address += input_section->output_offset; +++ break; +++ +++ case SW_64_R_REFLONG: +++ case SW_64_R_REFQUAD: +++ case SW_64_R_BRADDR: +++ case SW_64_R_HINT: +++ case SW_64_R_SREL16: +++ case SW_64_R_SREL32: +++ case SW_64_R_SREL64: +++ if (relocatable +++ && ((*rel->sym_ptr_ptr)->flags & BSF_SECTION_SYM) == 0) +++ { +++ rel->address += input_section->output_offset; +++ break; +++ } +++ r = bfd_perform_relocation (input_bfd, rel, data, input_section, +++ output_bfd, &err); +++ break; +++ +++ case SW_64_R_GPREL32: +++ /* This relocation is used in a switch table. It is a 32 +++ bit offset from the current GP value. We must adjust it +++ by the different between the original GP value and the +++ current GP value. The original GP value is stored in the +++ addend. We adjust the addend and let +++ bfd_perform_relocation finish the job. */ +++ rel->addend -= gp; +++ r = bfd_perform_relocation (input_bfd, rel, data, input_section, +++ output_bfd, &err); +++ if (r == bfd_reloc_ok && gp_undefined) +++ { +++ r = bfd_reloc_dangerous; +++ err = (char *) _("GP relative relocation used when GP not defined"); +++ } +++ break; +++ +++ case SW_64_R_LITERAL: +++ /* This is a reference to a literal value, generally +++ (always?) in the .lita section. This is a 16 bit GP +++ relative relocation. Sometimes the subsequent reloc is a +++ LITUSE reloc, which indicates how this reloc is used. +++ This sometimes permits rewriting the two instructions +++ referred to by the LITERAL and the LITUSE into different +++ instructions which do not refer to .lita. This can save +++ a memory reference, and permits removing a value from +++ .lita thus saving GP relative space. +++ +++ We do not these optimizations. To do them we would need +++ to arrange to link the .lita section first, so that by +++ the time we got here we would know the final values to +++ use. This would not be particularly difficult, but it is +++ not currently implemented. */ +++ +++ { +++ unsigned long insn; +++ +++ /* I believe that the LITERAL reloc will only apply to a +++ ldq or ldl instruction, so check my assumption. */ +++ insn = bfd_get_32 (input_bfd, data + rel->address); +++ BFD_ASSERT (((insn >> 26) & 0x3f) == 0x29 +++ || ((insn >> 26) & 0x3f) == 0x28); +++ +++ rel->addend -= gp; +++ r = bfd_perform_relocation (input_bfd, rel, data, input_section, +++ output_bfd, &err); +++ if (r == bfd_reloc_ok && gp_undefined) +++ { +++ r = bfd_reloc_dangerous; +++ err = +++ (char *) _("GP relative relocation used when GP not defined"); +++ } +++ } +++ break; +++ +++ case SW_64_R_LITUSE: +++ /* See SW_64_R_LITERAL above for the uses of this reloc. It +++ does not cause anything to happen, itself. */ +++ rel->address += input_section->output_offset; +++ break; +++ +++ case SW_64_R_GPDISP: +++ /* This marks the ldah of an ldah/lda pair which loads the +++ gp register with the difference of the gp value and the +++ current location. The second of the pair is r_size bytes +++ ahead; it used to be marked with an SW_64_R_IGNORE reloc, +++ but that no longer happens in OSF/1 3.2. */ +++ { +++ unsigned long insn1, insn2; +++ bfd_vma addend; +++ +++ /* Get the two instructions. */ +++ insn1 = bfd_get_32 (input_bfd, data + rel->address); +++ insn2 = bfd_get_32 (input_bfd, data + rel->address + rel->addend); +++ +++ BFD_ASSERT (((insn1 >> 26) & 0x3f) == 0x09); /* ldah */ +++ BFD_ASSERT (((insn2 >> 26) & 0x3f) == 0x08); /* lda */ +++ +++ /* Get the existing addend. We must account for the sign +++ extension done by lda and ldah. */ +++ addend = ((insn1 & 0xffff) << 16) + (insn2 & 0xffff); +++ if (insn1 & 0x8000) +++ { +++ addend -= 0x80000000; +++ addend -= 0x80000000; +++ } +++ if (insn2 & 0x8000) +++ addend -= 0x10000; +++ +++ /* The existing addend includes the different between the +++ gp of the input BFD and the address in the input BFD. +++ Subtract this out. */ +++ addend -= (ecoff_data (input_bfd)->gp +++ - (input_section->vma + rel->address)); +++ +++ /* Now add in the final gp value, and subtract out the +++ final address. */ +++ addend += (gp +++ - (input_section->output_section->vma +++ + input_section->output_offset +++ + rel->address)); +++ +++ /* Change the instructions, accounting for the sign +++ extension, and write them out. */ +++ if (addend & 0x8000) +++ addend += 0x10000; +++ insn1 = (insn1 & 0xffff0000) | ((addend >> 16) & 0xffff); +++ insn2 = (insn2 & 0xffff0000) | (addend & 0xffff); +++ +++ bfd_put_32 (input_bfd, (bfd_vma) insn1, data + rel->address); +++ bfd_put_32 (input_bfd, (bfd_vma) insn2, +++ data + rel->address + rel->addend); +++ +++ rel->address += input_section->output_offset; +++ } +++ break; +++ +++ case SW_64_R_OP_PUSH: +++ /* Push a value on the reloc evaluation stack. */ +++ { +++ asymbol *symbol; +++ bfd_vma relocation; +++ +++ if (relocatable) +++ { +++ rel->address += input_section->output_offset; +++ break; +++ } +++ +++ /* Figure out the relocation of this symbol. */ +++ symbol = *rel->sym_ptr_ptr; +++ +++ if (bfd_is_und_section (symbol->section)) +++ r = bfd_reloc_undefined; +++ +++ if (bfd_is_com_section (symbol->section)) +++ relocation = 0; +++ else +++ relocation = symbol->value; +++ relocation += symbol->section->output_section->vma; +++ relocation += symbol->section->output_offset; +++ relocation += rel->addend; +++ +++ if (tos >= RELOC_STACKSIZE) +++ abort (); +++ +++ stack[tos++] = relocation; +++ } +++ break; +++ +++ case SW_64_R_OP_STORE: +++ /* Store a value from the reloc stack into a bitfield. */ +++ { +++ bfd_vma val; +++ int offset, size; +++ +++ if (relocatable) +++ { +++ rel->address += input_section->output_offset; +++ break; +++ } +++ +++ if (tos == 0) +++ abort (); +++ +++ /* The offset and size for this reloc are encoded into the +++ addend field by sw_64_adjust_reloc_in. */ +++ offset = (rel->addend >> 8) & 0xff; +++ size = rel->addend & 0xff; +++ +++ val = bfd_get_64 (abfd, data + rel->address); +++ val &=~ (((1 << size) - 1) << offset); +++ val |= (stack[--tos] & ((1 << size) - 1)) << offset; +++ bfd_put_64 (abfd, val, data + rel->address); +++ } +++ break; +++ +++ case SW_64_R_OP_PSUB: +++ /* Subtract a value from the top of the stack. */ +++ { +++ asymbol *symbol; +++ bfd_vma relocation; +++ +++ if (relocatable) +++ { +++ rel->address += input_section->output_offset; +++ break; +++ } +++ +++ /* Figure out the relocation of this symbol. */ +++ symbol = *rel->sym_ptr_ptr; +++ +++ if (bfd_is_und_section (symbol->section)) +++ r = bfd_reloc_undefined; +++ +++ if (bfd_is_com_section (symbol->section)) +++ relocation = 0; +++ else +++ relocation = symbol->value; +++ relocation += symbol->section->output_section->vma; +++ relocation += symbol->section->output_offset; +++ relocation += rel->addend; +++ +++ if (tos == 0) +++ abort (); +++ +++ stack[tos - 1] -= relocation; +++ } +++ break; +++ +++ case SW_64_R_OP_PRSHIFT: +++ /* Shift the value on the top of the stack. */ +++ { +++ asymbol *symbol; +++ bfd_vma relocation; +++ +++ if (relocatable) +++ { +++ rel->address += input_section->output_offset; +++ break; +++ } +++ +++ /* Figure out the relocation of this symbol. */ +++ symbol = *rel->sym_ptr_ptr; +++ +++ if (bfd_is_und_section (symbol->section)) +++ r = bfd_reloc_undefined; +++ +++ if (bfd_is_com_section (symbol->section)) +++ relocation = 0; +++ else +++ relocation = symbol->value; +++ relocation += symbol->section->output_section->vma; +++ relocation += symbol->section->output_offset; +++ relocation += rel->addend; +++ +++ if (tos == 0) +++ abort (); +++ +++ stack[tos - 1] >>= relocation; +++ } +++ break; +++ +++ case SW_64_R_GPVALUE: +++ /* I really don't know if this does the right thing. */ +++ gp = rel->addend; +++ gp_undefined = FALSE; +++ break; +++ +++ default: +++ abort (); +++ } +++ +++ if (relocatable) +++ { +++ asection *os = input_section->output_section; +++ +++ /* A partial link, so keep the relocs. */ +++ os->orelocation[os->reloc_count] = rel; +++ os->reloc_count++; +++ } +++ +++ if (r != bfd_reloc_ok) +++ { +++ switch (r) +++ { +++ case bfd_reloc_undefined: +++ (*link_info->callbacks->undefined_symbol) +++ (link_info, bfd_asymbol_name (*rel->sym_ptr_ptr), +++ input_bfd, input_section, rel->address, TRUE); +++ break; +++ case bfd_reloc_dangerous: +++ (*link_info->callbacks->reloc_dangerous) +++ (link_info, err, input_bfd, input_section, rel->address); +++ break; +++ case bfd_reloc_overflow: +++ (*link_info->callbacks->reloc_overflow) +++ (link_info, NULL, bfd_asymbol_name (*rel->sym_ptr_ptr), +++ rel->howto->name, rel->addend, input_bfd, +++ input_section, rel->address); +++ break; +++ case bfd_reloc_outofrange: +++ default: +++ abort (); +++ break; +++ } +++ } +++ } +++ +++ if (tos != 0) +++ abort (); +++ +++ successful_return: +++ if (reloc_vector != NULL) +++ free (reloc_vector); +++ return data; +++ +++ error_return: +++ if (reloc_vector != NULL) +++ free (reloc_vector); +++ return NULL; +++} +++ +++/* Get the howto structure for a generic reloc type. */ +++ +++static reloc_howto_type * +++sw_64_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, +++ bfd_reloc_code_real_type code) +++{ +++ int sw_64_type; +++ +++ switch (code) +++ { +++ case BFD_RELOC_32: +++ sw_64_type = SW_64_R_REFLONG; +++ break; +++ case BFD_RELOC_64: +++ case BFD_RELOC_CTOR: +++ sw_64_type = SW_64_R_REFQUAD; +++ break; +++ case BFD_RELOC_GPREL32: +++ sw_64_type = SW_64_R_GPREL32; +++ break; +++ case BFD_RELOC_SW_64_LITERAL: +++ sw_64_type = SW_64_R_LITERAL; +++ break; +++ case BFD_RELOC_SW_64_LITUSE: +++ sw_64_type = SW_64_R_LITUSE; +++ break; +++ case BFD_RELOC_SW_64_GPDISP_HI16: +++ sw_64_type = SW_64_R_GPDISP; +++ break; +++ case BFD_RELOC_SW_64_GPDISP_LO16: +++ sw_64_type = SW_64_R_IGNORE; +++ break; +++#ifndef XWB20200308 +++ case BFD_RELOC_20_PCREL_S2: +++ sw_64_type = SW_64_R_BR18ADDR; +++ break; +++ case BFD_RELOC_24_PCREL_S2: +++ sw_64_type = SW_64_R_BR22ADDR; +++ break; + +#endif +- } +- } +- +-@@ -1242,6 +1274,16 @@ captured_main (void *data) +- +- captured_main_1 (context); +- +-+#ifdef CRASH_MERGE +-+ /* Relocate the vmlinux. */ +-+ objfile_rebase (symfile_objfile, crash_get_kaslr_offset()); +++ case BFD_RELOC_23_PCREL_S2: +++ sw_64_type = SW_64_R_BRADDR; +++ break; +++ case BFD_RELOC_SW_64_HINT: +++ sw_64_type = SW_64_R_HINT; +++ break; +++ case BFD_RELOC_16_PCREL: +++ sw_64_type = SW_64_R_SREL16; +++ break; +++ case BFD_RELOC_32_PCREL: +++ sw_64_type = SW_64_R_SREL32; +++ break; +++ case BFD_RELOC_64_PCREL: +++ sw_64_type = SW_64_R_SREL64; +++ break; +++ default: +++ return (reloc_howto_type *) NULL; +++ } +++ +++ return &sw_64_howto_table[sw_64_type]; +++} +++ +++static reloc_howto_type * +++sw_64_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED, +++ const char *r_name) +++{ +++ unsigned int i; +++ +++ for (i = 0; +++ i < sizeof (sw_64_howto_table) / sizeof (sw_64_howto_table[0]); +++ i++) +++ if (sw_64_howto_table[i].name != NULL +++ && strcasecmp (sw_64_howto_table[i].name, r_name) == 0) +++ return &sw_64_howto_table[i]; +++ +++ return NULL; +++} +++ +++/* A helper routine for sw_64_relocate_section which converts an +++ external reloc when generating relocatable output. Returns the +++ relocation amount. */ +++ +++static bfd_vma +++sw_64_convert_external_reloc (bfd *output_bfd ATTRIBUTE_UNUSED, +++ struct bfd_link_info *info, +++ bfd *input_bfd, +++ struct external_reloc *ext_rel, +++ struct ecoff_link_hash_entry *h) +++{ +++ unsigned long r_symndx; +++ bfd_vma relocation; +++ +++ BFD_ASSERT (bfd_link_relocatable (info)); +++ +++ if (h->root.type == bfd_link_hash_defined +++ || h->root.type == bfd_link_hash_defweak) +++ { +++ asection *hsec; +++ const char *name; +++ +++ /* This symbol is defined in the output. Convert the reloc from +++ being against the symbol to being against the section. */ +++ +++ /* Clear the r_extern bit. */ +++ ext_rel->r_bits[1] &=~ RELOC_BITS1_EXTERN_LITTLE; +++ +++ /* Compute a new r_symndx value. */ +++ hsec = h->root.u.def.section; +++ name = bfd_section_name (hsec->output_section); +++ +++ r_symndx = (unsigned long) -1; +++ switch (name[1]) +++ { +++ case 'A': +++ if (strcmp (name, "*ABS*") == 0) +++ r_symndx = RELOC_SECTION_ABS; +++ break; +++ case 'b': +++ if (strcmp (name, ".bss") == 0) +++ r_symndx = RELOC_SECTION_BSS; +++ break; +++ case 'd': +++ if (strcmp (name, ".data") == 0) +++ r_symndx = RELOC_SECTION_DATA; +++ break; +++ case 'f': +++ if (strcmp (name, ".fini") == 0) +++ r_symndx = RELOC_SECTION_FINI; +++ break; +++ case 'i': +++ if (strcmp (name, ".init") == 0) +++ r_symndx = RELOC_SECTION_INIT; +++ break; +++ case 'l': +++ if (strcmp (name, ".lita") == 0) +++ r_symndx = RELOC_SECTION_LITA; +++ else if (strcmp (name, ".lit8") == 0) +++ r_symndx = RELOC_SECTION_LIT8; +++ else if (strcmp (name, ".lit4") == 0) +++ r_symndx = RELOC_SECTION_LIT4; +++ break; +++ case 'p': +++ if (strcmp (name, ".pdata") == 0) +++ r_symndx = RELOC_SECTION_PDATA; +++ break; +++ case 'r': +++ if (strcmp (name, ".rdata") == 0) +++ r_symndx = RELOC_SECTION_RDATA; +++ else if (strcmp (name, ".rconst") == 0) +++ r_symndx = RELOC_SECTION_RCONST; +++ break; +++ case 's': +++ if (strcmp (name, ".sdata") == 0) +++ r_symndx = RELOC_SECTION_SDATA; +++ else if (strcmp (name, ".sbss") == 0) +++ r_symndx = RELOC_SECTION_SBSS; +++ break; +++ case 't': +++ if (strcmp (name, ".text") == 0) +++ r_symndx = RELOC_SECTION_TEXT; +++ break; +++ case 'x': +++ if (strcmp (name, ".xdata") == 0) +++ r_symndx = RELOC_SECTION_XDATA; +++ break; +++ } +++ +++ if (r_symndx == (unsigned long) -1) +++ abort (); +++ +++ /* Add the section VMA and the symbol value. */ +++ relocation = (h->root.u.def.value +++ + hsec->output_section->vma +++ + hsec->output_offset); +++ } +++ else +++ { +++ /* Change the symndx value to the right one for +++ the output BFD. */ +++ r_symndx = h->indx; +++ if (r_symndx == (unsigned long) -1) +++ { +++ /* Caller must give an error. */ +++ r_symndx = 0; +++ } +++ relocation = 0; +++ } +++ +++ /* Write out the new r_symndx value. */ +++ H_PUT_32 (input_bfd, r_symndx, ext_rel->r_symndx); +++ +++ return relocation; +++} +++ +++/* Relocate a section while linking an Sw_64 ECOFF file. This is +++ quite similar to get_relocated_section_contents. Perhaps they +++ could be combined somehow. */ +++ +++static bfd_boolean +++sw_64_relocate_section (bfd *output_bfd, +++ struct bfd_link_info *info, +++ bfd *input_bfd, +++ asection *input_section, +++ bfd_byte *contents, +++ void * external_relocs) +++{ +++ asection **symndx_to_section, *lita_sec; +++ struct ecoff_link_hash_entry **sym_hashes; +++ bfd_vma gp; +++ bfd_boolean gp_undefined; +++ bfd_vma stack[RELOC_STACKSIZE]; +++ int tos = 0; +++ struct external_reloc *ext_rel; +++ struct external_reloc *ext_rel_end; +++ bfd_size_type amt; +++ +++ /* We keep a table mapping the symndx found in an internal reloc to +++ the appropriate section. This is faster than looking up the +++ section by name each time. */ +++ symndx_to_section = ecoff_data (input_bfd)->symndx_to_section; +++ if (symndx_to_section == (asection **) NULL) +++ { +++ amt = NUM_RELOC_SECTIONS * sizeof (asection *); +++ symndx_to_section = (asection **) bfd_alloc (input_bfd, amt); +++ if (!symndx_to_section) +++ return FALSE; +++ +++ symndx_to_section[RELOC_SECTION_NONE] = NULL; +++ symndx_to_section[RELOC_SECTION_TEXT] = +++ bfd_get_section_by_name (input_bfd, ".text"); +++ symndx_to_section[RELOC_SECTION_RDATA] = +++ bfd_get_section_by_name (input_bfd, ".rdata"); +++ symndx_to_section[RELOC_SECTION_DATA] = +++ bfd_get_section_by_name (input_bfd, ".data"); +++ symndx_to_section[RELOC_SECTION_SDATA] = +++ bfd_get_section_by_name (input_bfd, ".sdata"); +++ symndx_to_section[RELOC_SECTION_SBSS] = +++ bfd_get_section_by_name (input_bfd, ".sbss"); +++ symndx_to_section[RELOC_SECTION_BSS] = +++ bfd_get_section_by_name (input_bfd, ".bss"); +++ symndx_to_section[RELOC_SECTION_INIT] = +++ bfd_get_section_by_name (input_bfd, ".init"); +++ symndx_to_section[RELOC_SECTION_LIT8] = +++ bfd_get_section_by_name (input_bfd, ".lit8"); +++ symndx_to_section[RELOC_SECTION_LIT4] = +++ bfd_get_section_by_name (input_bfd, ".lit4"); +++ symndx_to_section[RELOC_SECTION_XDATA] = +++ bfd_get_section_by_name (input_bfd, ".xdata"); +++ symndx_to_section[RELOC_SECTION_PDATA] = +++ bfd_get_section_by_name (input_bfd, ".pdata"); +++ symndx_to_section[RELOC_SECTION_FINI] = +++ bfd_get_section_by_name (input_bfd, ".fini"); +++ symndx_to_section[RELOC_SECTION_LITA] = +++ bfd_get_section_by_name (input_bfd, ".lita"); +++ symndx_to_section[RELOC_SECTION_ABS] = bfd_abs_section_ptr; +++ symndx_to_section[RELOC_SECTION_RCONST] = +++ bfd_get_section_by_name (input_bfd, ".rconst"); +++ +++ ecoff_data (input_bfd)->symndx_to_section = symndx_to_section; +++ } +++ +++ sym_hashes = ecoff_data (input_bfd)->sym_hashes; +++ +++ /* On the Sw_64, the .lita section must be addressable by the global +++ pointer. To support large programs, we need to allow multiple +++ global pointers. This works as long as each input .lita section +++ is <64KB big. This implies that when producing relocatable +++ output, the .lita section is limited to 64KB. . */ +++ +++ lita_sec = symndx_to_section[RELOC_SECTION_LITA]; +++ gp = _bfd_get_gp_value (output_bfd); +++ if (! bfd_link_relocatable (info) && lita_sec != NULL) +++ { +++ struct ecoff_section_tdata *lita_sec_data; +++ +++ /* Make sure we have a section data structure to which we can +++ hang on to the gp value we pick for the section. */ +++ lita_sec_data = ecoff_section_data (input_bfd, lita_sec); +++ if (lita_sec_data == NULL) +++ { +++ amt = sizeof (struct ecoff_section_tdata); +++ lita_sec_data = ((struct ecoff_section_tdata *) +++ bfd_zalloc (input_bfd, amt)); +++ lita_sec->used_by_bfd = lita_sec_data; +++ } +++ +++ if (lita_sec_data->gp != 0) +++ { +++ /* If we already assigned a gp to this section, we better +++ stick with that value. */ +++ gp = lita_sec_data->gp; +++ } +++ else +++ { +++ bfd_vma lita_vma; +++ bfd_size_type lita_size; +++ +++ lita_vma = lita_sec->output_offset + lita_sec->output_section->vma; +++ lita_size = lita_sec->size; +++ +++ if (gp == 0 +++ || lita_vma < gp - 0x8000 +++ || lita_vma + lita_size >= gp + 0x8000) +++ { +++ /* Either gp hasn't been set at all or the current gp +++ cannot address this .lita section. In both cases we +++ reset the gp to point into the "middle" of the +++ current input .lita section. */ +++ if (gp && !ecoff_data (output_bfd)->issued_multiple_gp_warning) +++ { +++ (*info->callbacks->warning) (info, +++ _("using multiple gp values"), +++ (char *) NULL, output_bfd, +++ (asection *) NULL, (bfd_vma) 0); +++ ecoff_data (output_bfd)->issued_multiple_gp_warning = TRUE; +++ } +++ if (lita_vma < gp - 0x8000) +++ gp = lita_vma + lita_size - 0x8000; +++ else +++ gp = lita_vma + 0x8000; +++ +++ } +++ +++ lita_sec_data->gp = gp; +++ } +++ +++ _bfd_set_gp_value (output_bfd, gp); +++ } +++ +++ gp_undefined = (gp == 0); +++ +++ BFD_ASSERT (bfd_header_little_endian (output_bfd)); +++ BFD_ASSERT (bfd_header_little_endian (input_bfd)); +++ +++ ext_rel = (struct external_reloc *) external_relocs; +++ ext_rel_end = ext_rel + input_section->reloc_count; +++ for (; ext_rel < ext_rel_end; ext_rel++) +++ { +++ bfd_vma r_vaddr; +++ unsigned long r_symndx; +++ int r_type; +++ int r_extern; +++ int r_offset; +++ int r_size; +++ bfd_boolean relocatep; +++ bfd_boolean adjust_addrp; +++ bfd_boolean gp_usedp; +++ bfd_vma addend; +++ +++ r_vaddr = H_GET_64 (input_bfd, ext_rel->r_vaddr); +++ r_symndx = H_GET_32 (input_bfd, ext_rel->r_symndx); +++ +++ r_type = ((ext_rel->r_bits[0] & RELOC_BITS0_TYPE_LITTLE) +++ >> RELOC_BITS0_TYPE_SH_LITTLE); +++ r_extern = (ext_rel->r_bits[1] & RELOC_BITS1_EXTERN_LITTLE) != 0; +++ r_offset = ((ext_rel->r_bits[1] & RELOC_BITS1_OFFSET_LITTLE) +++ >> RELOC_BITS1_OFFSET_SH_LITTLE); +++ /* Ignored the reserved bits. */ +++ r_size = ((ext_rel->r_bits[3] & RELOC_BITS3_SIZE_LITTLE) +++ >> RELOC_BITS3_SIZE_SH_LITTLE); +++ +++ relocatep = FALSE; +++ adjust_addrp = TRUE; +++ gp_usedp = FALSE; +++ addend = 0; +++ +++ switch (r_type) +++ { +++ case SW_64_R_GPRELHIGH: +++ _bfd_error_handler (_("%pB: %s unsupported"), +++ input_bfd, "SW_64_R_GPRELHIGH"); +++ bfd_set_error (bfd_error_bad_value); +++ continue; +++ +++ case SW_64_R_GPRELLOW: +++ _bfd_error_handler (_("%pB: %s unsupported"), +++ input_bfd, "SW_64_R_GPRELLOW"); +++ bfd_set_error (bfd_error_bad_value); +++ continue; +++ +++ default: +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("%pB: unsupported relocation type %#x"), +++ input_bfd, (int) r_type); +++ bfd_set_error (bfd_error_bad_value); +++ continue; +++ +++ case SW_64_R_IGNORE: +++ /* This reloc appears after a GPDISP reloc. On earlier +++ versions of OSF/1, It marked the position of the second +++ instruction to be altered by the GPDISP reloc, but it is +++ not otherwise used for anything. For some reason, the +++ address of the relocation does not appear to include the +++ section VMA, unlike the other relocation types. */ +++ if (bfd_link_relocatable (info)) +++ H_PUT_64 (input_bfd, input_section->output_offset + r_vaddr, +++ ext_rel->r_vaddr); +++ adjust_addrp = FALSE; +++ break; +++ +++ case SW_64_R_REFLONG: +++ case SW_64_R_REFQUAD: +++ case SW_64_R_HINT: +++ relocatep = TRUE; +++ break; +++ +++ case SW_64_R_BRADDR: +++ case SW_64_R_SREL16: +++ case SW_64_R_SREL32: +++ case SW_64_R_SREL64: +++ if (r_extern) +++ addend += - (r_vaddr + 4); +++ relocatep = TRUE; +++ break; +++ +++ case SW_64_R_GPREL32: +++ /* This relocation is used in a switch table. It is a 32 +++ bit offset from the current GP value. We must adjust it +++ by the different between the original GP value and the +++ current GP value. */ +++ relocatep = TRUE; +++ addend = ecoff_data (input_bfd)->gp - gp; +++ gp_usedp = TRUE; +++ break; +++ +++ case SW_64_R_LITERAL: +++ /* This is a reference to a literal value, generally +++ (always?) in the .lita section. This is a 16 bit GP +++ relative relocation. Sometimes the subsequent reloc is a +++ LITUSE reloc, which indicates how this reloc is used. +++ This sometimes permits rewriting the two instructions +++ referred to by the LITERAL and the LITUSE into different +++ instructions which do not refer to .lita. This can save +++ a memory reference, and permits removing a value from +++ .lita thus saving GP relative space. +++ +++ We do not these optimizations. To do them we would need +++ to arrange to link the .lita section first, so that by +++ the time we got here we would know the final values to +++ use. This would not be particularly difficult, but it is +++ not currently implemented. */ +++ +++ /* I believe that the LITERAL reloc will only apply to a ldq +++ or ldl instruction, so check my assumption. */ +++ { +++ unsigned long insn; +++ +++ insn = bfd_get_32 (input_bfd, +++ contents + r_vaddr - input_section->vma); +++ BFD_ASSERT (((insn >> 26) & 0x3f) == 0x29 +++ || ((insn >> 26) & 0x3f) == 0x28); +++ } +++ +++ relocatep = TRUE; +++ addend = ecoff_data (input_bfd)->gp - gp; +++ gp_usedp = TRUE; +++ break; +++ +++ case SW_64_R_LITUSE: +++ /* See SW_64_R_LITERAL above for the uses of this reloc. It +++ does not cause anything to happen, itself. */ +++ break; +++ +++ case SW_64_R_GPDISP: +++ /* This marks the ldah of an ldah/lda pair which loads the +++ gp register with the difference of the gp value and the +++ current location. The second of the pair is r_symndx +++ bytes ahead. It used to be marked with an SW_64_R_IGNORE +++ reloc, but OSF/1 3.2 no longer does that. */ +++ { +++ unsigned long insn1, insn2; +++ +++ /* Get the two instructions. */ +++ insn1 = bfd_get_32 (input_bfd, +++ contents + r_vaddr - input_section->vma); +++ insn2 = bfd_get_32 (input_bfd, +++ (contents +++ + r_vaddr +++ - input_section->vma +++ + r_symndx)); +++ +++ BFD_ASSERT (((insn1 >> 26) & 0x3f) == 0x09); /* ldah */ +++ BFD_ASSERT (((insn2 >> 26) & 0x3f) == 0x08); /* lda */ +++ +++ /* Get the existing addend. We must account for the sign +++ extension done by lda and ldah. */ +++ addend = ((insn1 & 0xffff) << 16) + (insn2 & 0xffff); +++ if (insn1 & 0x8000) +++ { +++ /* This is addend -= 0x100000000 without causing an +++ integer overflow on a 32 bit host. */ +++ addend -= 0x80000000; +++ addend -= 0x80000000; +++ } +++ if (insn2 & 0x8000) +++ addend -= 0x10000; +++ +++ /* The existing addend includes the difference between the +++ gp of the input BFD and the address in the input BFD. +++ We want to change this to the difference between the +++ final GP and the final address. */ +++ addend += (gp +++ - ecoff_data (input_bfd)->gp +++ + input_section->vma +++ - (input_section->output_section->vma +++ + input_section->output_offset)); +++ +++ /* Change the instructions, accounting for the sign +++ extension, and write them out. */ +++ if (addend & 0x8000) +++ addend += 0x10000; +++ insn1 = (insn1 & 0xffff0000) | ((addend >> 16) & 0xffff); +++ insn2 = (insn2 & 0xffff0000) | (addend & 0xffff); +++ +++ bfd_put_32 (input_bfd, (bfd_vma) insn1, +++ contents + r_vaddr - input_section->vma); +++ bfd_put_32 (input_bfd, (bfd_vma) insn2, +++ contents + r_vaddr - input_section->vma + r_symndx); +++ +++ gp_usedp = TRUE; +++ } +++ break; +++ +++ case SW_64_R_OP_PUSH: +++ case SW_64_R_OP_PSUB: +++ case SW_64_R_OP_PRSHIFT: +++ /* Manipulate values on the reloc evaluation stack. The +++ r_vaddr field is not an address in input_section, it is +++ the current value (including any addend) of the object +++ being used. */ +++ if (! r_extern) +++ { +++ asection *s; +++ +++ s = symndx_to_section[r_symndx]; +++ if (s == (asection *) NULL) +++ abort (); +++ addend = s->output_section->vma + s->output_offset - s->vma; +++ } +++ else +++ { +++ struct ecoff_link_hash_entry *h; +++ +++ h = sym_hashes[r_symndx]; +++ if (h == (struct ecoff_link_hash_entry *) NULL) +++ abort (); +++ +++ if (! bfd_link_relocatable (info)) +++ { +++ if (h->root.type == bfd_link_hash_defined +++ || h->root.type == bfd_link_hash_defweak) +++ addend = (h->root.u.def.value +++ + h->root.u.def.section->output_section->vma +++ + h->root.u.def.section->output_offset); +++ else +++ { +++ /* Note that we pass the address as 0, since we +++ do not have a meaningful number for the +++ location within the section that is being +++ relocated. */ +++ (*info->callbacks->undefined_symbol) +++ (info, h->root.root.string, input_bfd, +++ input_section, (bfd_vma) 0, TRUE); +++ addend = 0; +++ } +++ } +++ else +++ { +++ if (h->root.type != bfd_link_hash_defined +++ && h->root.type != bfd_link_hash_defweak +++ && h->indx == -1) +++ { +++ /* This symbol is not being written out. Pass +++ the address as 0, as with undefined_symbol, +++ above. */ +++ (*info->callbacks->unattached_reloc) +++ (info, h->root.root.string, +++ input_bfd, input_section, (bfd_vma) 0); +++ } +++ +++ addend = sw_64_convert_external_reloc (output_bfd, info, +++ input_bfd, +++ ext_rel, h); +++ } +++ } +++ +++ addend += r_vaddr; +++ +++ if (bfd_link_relocatable (info)) +++ { +++ /* Adjust r_vaddr by the addend. */ +++ H_PUT_64 (input_bfd, addend, ext_rel->r_vaddr); +++ } +++ else +++ { +++ switch (r_type) +++ { +++ case SW_64_R_OP_PUSH: +++ if (tos >= RELOC_STACKSIZE) +++ abort (); +++ stack[tos++] = addend; +++ break; +++ +++ case SW_64_R_OP_PSUB: +++ if (tos == 0) +++ abort (); +++ stack[tos - 1] -= addend; +++ break; +++ +++ case SW_64_R_OP_PRSHIFT: +++ if (tos == 0) +++ abort (); +++ stack[tos - 1] >>= addend; +++ break; +++ } +++ } +++ +++ adjust_addrp = FALSE; +++ break; +++ +++ case SW_64_R_OP_STORE: +++ /* Store a value from the reloc stack into a bitfield. If +++ we are generating relocatable output, all we do is +++ adjust the address of the reloc. */ +++ if (! bfd_link_relocatable (info)) +++ { +++ bfd_vma mask; +++ bfd_vma val; +++ +++ if (tos == 0) +++ abort (); +++ +++ /* Get the relocation mask. The separate steps and the +++ casts to bfd_vma are attempts to avoid a bug in the +++ Sw_64 OSF 1.3 C compiler. See reloc.c for more +++ details. */ +++ mask = 1; +++ mask <<= (bfd_vma) r_size; +++ mask -= 1; +++ +++ /* FIXME: I don't know what kind of overflow checking, +++ if any, should be done here. */ +++ val = bfd_get_64 (input_bfd, +++ contents + r_vaddr - input_section->vma); +++ val &=~ mask << (bfd_vma) r_offset; +++ val |= (stack[--tos] & mask) << (bfd_vma) r_offset; +++ bfd_put_64 (input_bfd, val, +++ contents + r_vaddr - input_section->vma); +++ } +++ break; +++ +++ case SW_64_R_GPVALUE: +++ /* I really don't know if this does the right thing. */ +++ gp = ecoff_data (input_bfd)->gp + r_symndx; +++ gp_undefined = FALSE; +++ break; +++ } +++ +++ if (relocatep) +++ { +++ reloc_howto_type *howto; +++ struct ecoff_link_hash_entry *h = NULL; +++ asection *s = NULL; +++ bfd_vma relocation; +++ bfd_reloc_status_type r; +++ +++ /* Perform a relocation. */ +++ +++ howto = &sw_64_howto_table[r_type]; +++ +++ if (r_extern) +++ { +++ h = sym_hashes[r_symndx]; +++ /* If h is NULL, that means that there is a reloc +++ against an external symbol which we thought was just +++ a debugging symbol. This should not happen. */ +++ if (h == (struct ecoff_link_hash_entry *) NULL) +++ abort (); +++ } +++ else +++ { +++ if (r_symndx >= NUM_RELOC_SECTIONS) +++ s = NULL; +++ else +++ s = symndx_to_section[r_symndx]; +++ +++ if (s == (asection *) NULL) +++ abort (); +++ } +++ +++ if (bfd_link_relocatable (info)) +++ { +++ /* We are generating relocatable output, and must +++ convert the existing reloc. */ +++ if (r_extern) +++ { +++ if (h->root.type != bfd_link_hash_defined +++ && h->root.type != bfd_link_hash_defweak +++ && h->indx == -1) +++ { +++ /* This symbol is not being written out. */ +++ (*info->callbacks->unattached_reloc) +++ (info, h->root.root.string, input_bfd, +++ input_section, r_vaddr - input_section->vma); +++ } +++ +++ relocation = sw_64_convert_external_reloc (output_bfd, +++ info, +++ input_bfd, +++ ext_rel, +++ h); +++ } +++ else +++ { +++ /* This is a relocation against a section. Adjust +++ the value by the amount the section moved. */ +++ relocation = (s->output_section->vma +++ + s->output_offset +++ - s->vma); +++ } +++ +++ /* If this is PC relative, the existing object file +++ appears to already have the reloc worked out. We +++ must subtract out the old value and add in the new +++ one. */ +++ if (howto->pc_relative) +++ relocation -= (input_section->output_section->vma +++ + input_section->output_offset +++ - input_section->vma); +++ +++ /* Put in any addend. */ +++ relocation += addend; +++ +++ /* Adjust the contents. */ +++ r = _bfd_relocate_contents (howto, input_bfd, relocation, +++ (contents +++ + r_vaddr +++ - input_section->vma)); +++ } +++ else +++ { +++ /* We are producing a final executable. */ +++ if (r_extern) +++ { +++ /* This is a reloc against a symbol. */ +++ if (h->root.type == bfd_link_hash_defined +++ || h->root.type == bfd_link_hash_defweak) +++ { +++ asection *hsec; +++ +++ hsec = h->root.u.def.section; +++ relocation = (h->root.u.def.value +++ + hsec->output_section->vma +++ + hsec->output_offset); +++ } +++ else +++ { +++ (*info->callbacks->undefined_symbol) +++ (info, h->root.root.string, input_bfd, input_section, +++ r_vaddr - input_section->vma, TRUE); +++ relocation = 0; +++ } +++ } +++ else +++ { +++ /* This is a reloc against a section. */ +++ relocation = (s->output_section->vma +++ + s->output_offset +++ - s->vma); +++ +++ /* Adjust a PC relative relocation by removing the +++ reference to the original source section. */ +++ if (howto->pc_relative) +++ relocation += input_section->vma; +++ } +++ +++ r = _bfd_final_link_relocate (howto, +++ input_bfd, +++ input_section, +++ contents, +++ r_vaddr - input_section->vma, +++ relocation, +++ addend); +++ } +++ +++ if (r != bfd_reloc_ok) +++ { +++ switch (r) +++ { +++ default: +++ case bfd_reloc_outofrange: +++ abort (); +++ case bfd_reloc_overflow: +++ { +++ const char *name; +++ +++ if (r_extern) +++ name = sym_hashes[r_symndx]->root.root.string; +++ else +++ name = bfd_section_name (symndx_to_section[r_symndx]); +++ (*info->callbacks->reloc_overflow) +++ (info, NULL, name, sw_64_howto_table[r_type].name, +++ (bfd_vma) 0, input_bfd, input_section, +++ r_vaddr - input_section->vma); +++ } +++ break; +++ } +++ } +++ } +++ +++ if (bfd_link_relocatable (info) && adjust_addrp) +++ { +++ /* Change the address of the relocation. */ +++ H_PUT_64 (input_bfd, +++ (input_section->output_section->vma +++ + input_section->output_offset +++ - input_section->vma +++ + r_vaddr), +++ ext_rel->r_vaddr); +++ } +++ +++ if (gp_usedp && gp_undefined) +++ { +++ (*info->callbacks->reloc_dangerous) +++ (info, _("GP relative relocation used when GP not defined"), +++ input_bfd, input_section, r_vaddr - input_section->vma); +++ /* Only give the error once per link. */ +++ gp = 4; +++ _bfd_set_gp_value (output_bfd, gp); +++ gp_undefined = FALSE; +++ } +++ } +++ +++ if (tos != 0) +++ abort (); +++ +++ return TRUE; +++} +++ +++/* Do final adjustments to the filehdr and the aouthdr. This routine +++ sets the dynamic bits in the file header. */ +++ +++static bfd_boolean +++sw_64_adjust_headers (bfd *abfd, +++ struct internal_filehdr *fhdr, +++ struct internal_aouthdr *ahdr ATTRIBUTE_UNUSED) +++{ +++ if ((abfd->flags & (DYNAMIC | EXEC_P)) == (DYNAMIC | EXEC_P)) +++ fhdr->f_flags |= F_SW_64_CALL_SHARED; +++ else if ((abfd->flags & DYNAMIC) != 0) +++ fhdr->f_flags |= F_SW_64_SHARABLE; +++ return TRUE; +++} +++ +++/* Archive handling. In OSF/1 (or Digital Unix) v3.2, Digital +++ introduced archive packing, in which the elements in an archive are +++ optionally compressed using a simple dictionary scheme. We know +++ how to read such archives, but we don't write them. */ +++ +++#define sw_64_ecoff_slurp_armap _bfd_ecoff_slurp_armap +++#define sw_64_ecoff_slurp_extended_name_table \ +++ _bfd_ecoff_slurp_extended_name_table +++#define sw_64_ecoff_construct_extended_name_table \ +++ _bfd_ecoff_construct_extended_name_table +++#define sw_64_ecoff_truncate_arname _bfd_ecoff_truncate_arname +++#define sw_64_ecoff_write_armap _bfd_ecoff_write_armap +++#define sw_64_ecoff_write_ar_hdr _bfd_generic_write_ar_hdr +++#define sw_64_ecoff_generic_stat_arch_elt _bfd_ecoff_generic_stat_arch_elt +++#define sw_64_ecoff_update_armap_timestamp _bfd_ecoff_update_armap_timestamp +++ +++/* A compressed file uses this instead of ARFMAG. */ +++ +++#define ARFZMAG "Z\012" +++ +++/* Read an archive header. This is like the standard routine, but it +++ also accepts ARFZMAG. */ +++ +++static void * +++sw_64_ecoff_read_ar_hdr (bfd *abfd) +++{ +++ struct areltdata *ret; +++ struct ar_hdr *h; +++ +++ ret = (struct areltdata *) _bfd_generic_read_ar_hdr_mag (abfd, ARFZMAG); +++ if (ret == NULL) +++ return NULL; +++ +++ h = (struct ar_hdr *) ret->arch_header; +++ if (strncmp (h->ar_fmag, ARFZMAG, 2) == 0) +++ { +++ bfd_byte ab[8]; +++ +++ /* This is a compressed file. We must set the size correctly. +++ The size is the eight bytes after the dummy file header. */ +++ if (bfd_seek (abfd, (file_ptr) FILHSZ, SEEK_CUR) != 0 +++ || bfd_bread (ab, (bfd_size_type) 8, abfd) != 8 +++ || bfd_seek (abfd, (file_ptr) (- (FILHSZ + 8)), SEEK_CUR) != 0) +++ return NULL; +++ +++ ret->parsed_size = H_GET_64 (abfd, ab); +++ } +++ +++ return ret; +++} +++ +++/* Get an archive element at a specified file position. This is where +++ we uncompress the archive element if necessary. */ +++ +++static bfd * +++sw_64_ecoff_get_elt_at_filepos (bfd *archive, file_ptr filepos) +++{ +++ bfd *nbfd = NULL; +++ struct areltdata *tdata; +++ struct ar_hdr *hdr; +++ bfd_byte ab[8]; +++ bfd_size_type size; +++ bfd_byte *buf, *p; +++ struct bfd_in_memory *bim; +++ +++ buf = NULL; +++ nbfd = _bfd_get_elt_at_filepos (archive, filepos); +++ if (nbfd == NULL) +++ goto error_return; +++ +++ if ((nbfd->flags & BFD_IN_MEMORY) != 0) +++ { +++ /* We have already expanded this BFD. */ +++ return nbfd; +++ } +++ +++ tdata = (struct areltdata *) nbfd->arelt_data; +++ hdr = (struct ar_hdr *) tdata->arch_header; +++ if (strncmp (hdr->ar_fmag, ARFZMAG, 2) != 0) +++ return nbfd; +++ +++ /* We must uncompress this element. We do this by copying it into a +++ memory buffer, and making bfd_bread and bfd_seek use that buffer. +++ This can use a lot of memory, but it's simpler than getting a +++ temporary file, making that work with the file descriptor caching +++ code, and making sure that it is deleted at all appropriate +++ times. It can be changed if it ever becomes important. */ +++ +++ /* The compressed file starts with a dummy ECOFF file header. */ +++ if (bfd_seek (nbfd, (file_ptr) FILHSZ, SEEK_SET) != 0) +++ goto error_return; +++ +++ /* The next eight bytes are the real file size. */ +++ if (bfd_bread (ab, (bfd_size_type) 8, nbfd) != 8) +++ goto error_return; +++ size = H_GET_64 (nbfd, ab); +++ +++ if (size != 0) +++ { +++ bfd_size_type left; +++ bfd_byte dict[4096]; +++ unsigned int h; +++ bfd_byte b; +++ +++ buf = (bfd_byte *) bfd_malloc (size); +++ if (buf == NULL) +++ goto error_return; +++ p = buf; +++ +++ left = size; +++ +++ /* I don't know what the next eight bytes are for. */ +++ if (bfd_bread (ab, (bfd_size_type) 8, nbfd) != 8) +++ goto error_return; +++ +++ /* This is the uncompression algorithm. It's a simple +++ dictionary based scheme in which each character is predicted +++ by a hash of the previous three characters. A control byte +++ indicates whether the character is predicted or whether it +++ appears in the input stream; each control byte manages the +++ next eight bytes in the output stream. */ +++ memset (dict, 0, sizeof dict); +++ h = 0; +++ while (bfd_bread (&b, (bfd_size_type) 1, nbfd) == 1) +++ { +++ unsigned int i; +++ +++ for (i = 0; i < 8; i++, b >>= 1) +++ { +++ bfd_byte n; +++ +++ if ((b & 1) == 0) +++ n = dict[h]; +++ else +++ { +++ if (! bfd_bread (&n, (bfd_size_type) 1, nbfd)) +++ goto error_return; +++ dict[h] = n; +++ } +++ +++ *p++ = n; +++ +++ --left; +++ if (left == 0) +++ break; +++ +++ h <<= 4; +++ h ^= n; +++ h &= sizeof dict - 1; +++ } +++ +++ if (left == 0) +++ break; +++ } +++ } +++ +++ /* Now the uncompressed file contents are in buf. */ +++ bim = ((struct bfd_in_memory *) +++ bfd_malloc ((bfd_size_type) sizeof (struct bfd_in_memory))); +++ if (bim == NULL) +++ goto error_return; +++ bim->size = size; +++ bim->buffer = buf; +++ +++ nbfd->mtime_set = TRUE; +++ nbfd->mtime = strtol (hdr->ar_date, (char **) NULL, 10); +++ +++ nbfd->flags |= BFD_IN_MEMORY; +++ nbfd->iostream = bim; +++ nbfd->iovec = &_bfd_memory_iovec; +++ nbfd->origin = 0; +++ BFD_ASSERT (! nbfd->cacheable); +++ +++ return nbfd; +++ +++ error_return: +++ if (buf != NULL) +++ free (buf); +++ if (nbfd != NULL) +++ bfd_close (nbfd); +++ return NULL; +++} +++ +++/* Open the next archived file. */ +++ +++static bfd * +++sw_64_ecoff_openr_next_archived_file (bfd *archive, bfd *last_file) +++{ +++ ufile_ptr filestart; +++ +++ if (last_file == NULL) +++ filestart = bfd_ardata (archive)->first_file_filepos; +++ else +++ { +++ struct areltdata *t; +++ struct ar_hdr *h; +++ bfd_size_type size; +++ +++ /* We can't use arelt_size here, because that uses parsed_size, +++ which is the uncompressed size. We need the compressed size. */ +++ t = (struct areltdata *) last_file->arelt_data; +++ h = (struct ar_hdr *) t->arch_header; +++ size = strtol (h->ar_size, (char **) NULL, 10); +++ +++ /* Pad to an even boundary... +++ Note that last_file->origin can be odd in the case of +++ BSD-4.4-style element with a long odd size. */ +++ filestart = last_file->proxy_origin + size; +++ filestart += filestart % 2; +++ if (filestart < last_file->proxy_origin) +++ { +++ /* Prevent looping. See PR19256. */ +++ bfd_set_error (bfd_error_malformed_archive); +++ return NULL; +++ } +++ } +++ +++ return sw_64_ecoff_get_elt_at_filepos (archive, filestart); +++} +++ +++/* Open the archive file given an index into the armap. */ +++ +++static bfd * +++sw_64_ecoff_get_elt_at_index (bfd *abfd, symindex sym_index) +++{ +++ carsym *entry; +++ +++ entry = bfd_ardata (abfd)->symdefs + sym_index; +++ return sw_64_ecoff_get_elt_at_filepos (abfd, entry->file_offset); +++} +++ +++static void +++sw_64_ecoff_swap_coff_aux_in (bfd *abfd ATTRIBUTE_UNUSED, +++ void *ext1 ATTRIBUTE_UNUSED, +++ int type ATTRIBUTE_UNUSED, +++ int in_class ATTRIBUTE_UNUSED, +++ int indx ATTRIBUTE_UNUSED, +++ int numaux ATTRIBUTE_UNUSED, +++ void *in1 ATTRIBUTE_UNUSED) +++{ +++} +++ +++static void +++sw_64_ecoff_swap_coff_sym_in (bfd *abfd ATTRIBUTE_UNUSED, +++ void *ext1 ATTRIBUTE_UNUSED, +++ void *in1 ATTRIBUTE_UNUSED) +++{ +++} +++ +++static void +++sw_64_ecoff_swap_coff_lineno_in (bfd *abfd ATTRIBUTE_UNUSED, +++ void *ext1 ATTRIBUTE_UNUSED, +++ void *in1 ATTRIBUTE_UNUSED) +++{ +++} +++ +++static unsigned int +++sw_64_ecoff_swap_coff_aux_out (bfd *abfd ATTRIBUTE_UNUSED, +++ void *inp ATTRIBUTE_UNUSED, +++ int type ATTRIBUTE_UNUSED, +++ int in_class ATTRIBUTE_UNUSED, +++ int indx ATTRIBUTE_UNUSED, +++ int numaux ATTRIBUTE_UNUSED, +++ void *extp ATTRIBUTE_UNUSED) +++{ +++ return 0; +++} +++ +++static unsigned int +++sw_64_ecoff_swap_coff_sym_out (bfd *abfd ATTRIBUTE_UNUSED, +++ void *inp ATTRIBUTE_UNUSED, +++ void *extp ATTRIBUTE_UNUSED) +++{ +++ return 0; +++} +++ +++static unsigned int +++sw_64_ecoff_swap_coff_lineno_out (bfd *abfd ATTRIBUTE_UNUSED, +++ void *inp ATTRIBUTE_UNUSED, +++ void *extp ATTRIBUTE_UNUSED) +++{ +++ return 0; +++} +++ +++static unsigned int +++sw_64_ecoff_swap_coff_reloc_out (bfd *abfd ATTRIBUTE_UNUSED, +++ void *inp ATTRIBUTE_UNUSED, +++ void *extp ATTRIBUTE_UNUSED) +++{ +++ return 0; +++} +++ +++/* This is the ECOFF backend structure. The backend field of the +++ target vector points to this. */ +++ +++static const struct ecoff_backend_data sw_64_ecoff_backend_data = +++{ +++ /* COFF backend structure. */ +++ { +++ sw_64_ecoff_swap_coff_aux_in, sw_64_ecoff_swap_coff_sym_in, +++ sw_64_ecoff_swap_coff_lineno_in, sw_64_ecoff_swap_coff_aux_out, +++ sw_64_ecoff_swap_coff_sym_out, sw_64_ecoff_swap_coff_lineno_out, +++ sw_64_ecoff_swap_coff_reloc_out, +++ sw_64_ecoff_swap_filehdr_out, sw_64_ecoff_swap_aouthdr_out, +++ sw_64_ecoff_swap_scnhdr_out, +++ FILHSZ, AOUTSZ, SCNHSZ, 0, 0, 0, 0, FILNMLEN, TRUE, +++ ECOFF_NO_LONG_SECTION_NAMES, 4, FALSE, 2, 32768, +++ sw_64_ecoff_swap_filehdr_in, sw_64_ecoff_swap_aouthdr_in, +++ sw_64_ecoff_swap_scnhdr_in, NULL, +++ sw_64_ecoff_bad_format_hook, _bfd_ecoff_set_arch_mach_hook, +++ sw_64_ecoff_mkobject_hook, _bfd_ecoff_styp_to_sec_flags, +++ _bfd_ecoff_set_alignment_hook, _bfd_ecoff_slurp_symbol_table, +++ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, +++ NULL, NULL, NULL, NULL +++ }, +++ /* Supported architecture. */ +++ bfd_arch_sw_64, +++ /* Initial portion of armap string. */ +++ "________64", +++ /* The page boundary used to align sections in a demand-paged +++ executable file. E.g., 0x1000. */ +++ 0x2000, +++ /* TRUE if the .rdata section is part of the text segment, as on the +++ Sw_64. FALSE if .rdata is part of the data segment, as on the +++ MIPS. */ +++ TRUE, +++ /* Bitsize of constructor entries. */ +++ 64, +++ /* Reloc to use for constructor entries. */ +++ &sw_64_howto_table[SW_64_R_REFQUAD], +++ { +++ /* Symbol table magic number. */ +++ magicSym2, +++ /* Alignment of debugging information. E.g., 4. */ +++ 8, +++ /* Sizes of external symbolic information. */ +++ sizeof (struct hdr_ext), +++ sizeof (struct dnr_ext), +++ sizeof (struct pdr_ext), +++ sizeof (struct sym_ext), +++ sizeof (struct opt_ext), +++ sizeof (struct fdr_ext), +++ sizeof (struct rfd_ext), +++ sizeof (struct ext_ext), +++ /* Functions to swap in external symbolic data. */ +++ ecoff_swap_hdr_in, +++ ecoff_swap_dnr_in, +++ ecoff_swap_pdr_in, +++ ecoff_swap_sym_in, +++ ecoff_swap_opt_in, +++ ecoff_swap_fdr_in, +++ ecoff_swap_rfd_in, +++ ecoff_swap_ext_in, +++ _bfd_ecoff_swap_tir_in, +++ _bfd_ecoff_swap_rndx_in, +++ /* Functions to swap out external symbolic data. */ +++ ecoff_swap_hdr_out, +++ ecoff_swap_dnr_out, +++ ecoff_swap_pdr_out, +++ ecoff_swap_sym_out, +++ ecoff_swap_opt_out, +++ ecoff_swap_fdr_out, +++ ecoff_swap_rfd_out, +++ ecoff_swap_ext_out, +++ _bfd_ecoff_swap_tir_out, +++ _bfd_ecoff_swap_rndx_out, +++ /* Function to read in symbolic data. */ +++ _bfd_ecoff_slurp_symbolic_info +++ }, +++ /* External reloc size. */ +++ RELSZ, +++ /* Reloc swapping functions. */ +++ sw_64_ecoff_swap_reloc_in, +++ sw_64_ecoff_swap_reloc_out, +++ /* Backend reloc tweaking. */ +++ sw_64_adjust_reloc_in, +++ sw_64_adjust_reloc_out, +++ /* Relocate section contents while linking. */ +++ sw_64_relocate_section, +++ /* Do final adjustments to filehdr and aouthdr. */ +++ sw_64_adjust_headers, +++ /* Read an element from an archive at a given file position. */ +++ sw_64_ecoff_get_elt_at_filepos +++}; +++ +++/* Looking up a reloc type is Sw_64 specific. */ +++#define _bfd_ecoff_bfd_reloc_type_lookup sw_64_bfd_reloc_type_lookup +++#define _bfd_ecoff_bfd_reloc_name_lookup \ +++ sw_64_bfd_reloc_name_lookup +++ +++/* So is getting relocated section contents. */ +++#define _bfd_ecoff_bfd_get_relocated_section_contents \ +++ sw_64_ecoff_get_relocated_section_contents +++ +++/* Handling file windows is generic. */ +++#define _bfd_ecoff_get_section_contents_in_window \ +++ _bfd_generic_get_section_contents_in_window +++ +++/* Input section flag lookup is generic. */ +++#define _bfd_ecoff_bfd_lookup_section_flags bfd_generic_lookup_section_flags +++ +++/* Relaxing sections is generic. */ +++#define _bfd_ecoff_bfd_relax_section bfd_generic_relax_section +++#define _bfd_ecoff_bfd_gc_sections bfd_generic_gc_sections +++#define _bfd_ecoff_bfd_merge_sections bfd_generic_merge_sections +++#define _bfd_ecoff_bfd_is_group_section bfd_generic_is_group_section +++#define _bfd_ecoff_bfd_group_name bfd_generic_group_name +++#define _bfd_ecoff_bfd_discard_group bfd_generic_discard_group +++#define _bfd_ecoff_section_already_linked \ +++ _bfd_coff_section_already_linked +++#define _bfd_ecoff_bfd_define_common_symbol bfd_generic_define_common_symbol +++#define _bfd_ecoff_bfd_link_hide_symbol _bfd_generic_link_hide_symbol +++#define _bfd_ecoff_bfd_define_start_stop bfd_generic_define_start_stop +++#define _bfd_ecoff_bfd_link_check_relocs _bfd_generic_link_check_relocs +++ +++/* Installing internal relocations in a section is also generic. */ +++#define _bfd_ecoff_set_reloc _bfd_generic_set_reloc +++ +++const bfd_target sw_64_ecoff_le_vec = +++{ +++ "ecoff-littlesw_64", /* name */ +++ bfd_target_ecoff_flavour, +++ BFD_ENDIAN_LITTLE, /* data byte order is little */ +++ BFD_ENDIAN_LITTLE, /* header byte order is little */ +++ +++ (HAS_RELOC | EXEC_P /* object flags */ +++ | HAS_LINENO | HAS_DEBUG +++ | HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED), +++ +++ (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA), +++ 0, /* leading underscore */ +++ ' ', /* ar_pad_char */ +++ 15, /* ar_max_namelen */ +++ 0, /* match priority. */ +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* data */ +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* hdrs */ +++ +++ { /* bfd_check_format */ +++ _bfd_dummy_target, +++ sw_64_ecoff_object_p, +++ bfd_generic_archive_p, +++ _bfd_dummy_target +++ }, +++ { /* bfd_set_format */ +++ _bfd_bool_bfd_false_error, +++ _bfd_ecoff_mkobject, +++ _bfd_generic_mkarchive, +++ _bfd_bool_bfd_false_error +++ }, +++ { /* bfd_write_contents */ +++ _bfd_bool_bfd_false_error, +++ _bfd_ecoff_write_object_contents, +++ _bfd_write_archive_contents, +++ _bfd_bool_bfd_false_error +++ }, +++ +++ BFD_JUMP_TABLE_GENERIC (_bfd_ecoff), +++ BFD_JUMP_TABLE_COPY (_bfd_ecoff), +++ BFD_JUMP_TABLE_CORE (_bfd_nocore), +++ BFD_JUMP_TABLE_ARCHIVE (sw_64_ecoff), +++ BFD_JUMP_TABLE_SYMBOLS (_bfd_ecoff), +++ BFD_JUMP_TABLE_RELOCS (_bfd_ecoff), +++ BFD_JUMP_TABLE_WRITE (_bfd_ecoff), +++ BFD_JUMP_TABLE_LINK (_bfd_ecoff), +++ BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic), +++ +++ NULL, +++ +++ &sw_64_ecoff_backend_data +++}; ++diff -Nuar gdb-10.2/bfd/coffswap.h gdb-10.2/bfd/coffswap.h ++--- gdb-10.2/bfd/coffswap.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/coffswap.h 2025-04-16 17:06:51.902086800 +0800 ++@@ -653,6 +653,13 @@ ++ aouthdr_int->gprmask = H_GET_32 (abfd, aouthdr_ext->gprmask); ++ aouthdr_int->fprmask = H_GET_32 (abfd, aouthdr_ext->fprmask); ++ #endif +++ +++#ifdef SW_64ECOFF +++ aouthdr_int->bss_start = H_GET_64 (abfd, aouthdr_ext->bss_start); +++ aouthdr_int->gp_value = H_GET_64 (abfd, aouthdr_ext->gp_value); +++ aouthdr_int->gprmask = H_GET_32 (abfd, aouthdr_ext->gprmask); +++ aouthdr_int->fprmask = H_GET_32 (abfd, aouthdr_ext->fprmask); +++#endif ++ } ++ ++ static unsigned int ++diff -Nuar gdb-10.2/bfd/config.bfd gdb-10.2/bfd/config.bfd ++--- gdb-10.2/bfd/config.bfd 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/config.bfd 2025-04-16 17:06:51.902086800 +0800 ++@@ -166,6 +166,7 @@ ++ case "${targ_cpu}" in ++ aarch64*) targ_archs="bfd_aarch64_arch bfd_arm_arch";; ++ alpha*) targ_archs=bfd_alpha_arch ;; +++sw_64*) targ_archs=bfd_sw_64_arch ;; ++ am33_2.0*) targ_archs=bfd_mn10300_arch ;; ++ arc*) targ_archs=bfd_arc_arch ;; ++ arm*) targ_archs=bfd_arm_arch ;; ++@@ -300,6 +301,40 @@ ++ targ_defvec=alpha_ecoff_le_vec ++ want64=true ++ ;; +++ sw_64*-*-freebsd* | sw_64*-*-kfreebsd*-gnu) +++ targ_defvec=sw_64_elf64_fbsd_vec +++ targ_selvecs="sw_64_elf64_vec sw_64_ecoff_le_vec" +++ want64=true +++ # FreeBSD <= 4.0 supports only the old nonstandard way of ABI labelling. +++ case "${targ}" in +++ sw_64*-*-freebsd3* | sw_64*-*-freebsd4 | sw_64*-*-freebsd4.0*) +++ targ_cflags=-DOLD_FREEBSD_ABI_LABEL ;; +++ esac +++ ;; +++ sw_64*-*-netbsd* | sw_64*-*-openbsd*) +++ targ_defvec=sw_64_elf64_vec +++ targ_selvecs=sw_64_ecoff_le_vec +++ want64=true +++ ;; +++ sw_64*-*-linux*ecoff*) +++ targ_defvec=sw_64_ecoff_le_vec +++ targ_selvecs=sw_64_elf64_vec +++ want64=true +++ ;; +++ sw_64*-*-linux-* | sw_64*-*-elf*) +++ targ_defvec=sw_64_elf64_vec +++ targ_selvecs=sw_64_ecoff_le_vec +++ want64=true +++ ;; +++ sw_64*-*-*vms*) +++ targ_defvec=sw_64_vms_vec +++ targ_selvecs=sw_64_vms_lib_txt_vec +++ want64=true +++ ;; +++ sw_64*-*-*) +++ targ_defvec=sw_64_ecoff_le_vec +++ want64=true +++ ;; ++ ia64*-*-freebsd* | ia64*-*-netbsd* | ia64*-*-linux-* | ia64*-*-elf* | ia64*-*-kfreebsd*-gnu) ++ targ_defvec=ia64_elf64_le_vec ++ targ_selvecs="ia64_elf64_be_vec ia64_pei_vec" ++diff -Nuar gdb-10.2/bfd/configure gdb-10.2/bfd/configure ++--- gdb-10.2/bfd/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/configure 2025-04-16 17:06:51.912086800 +0800 ++@@ -14748,6 +14748,10 @@ ++ alpha_elf64_fbsd_vec) tb="$tb elf64-alpha.lo elf64.lo $elf"; target_size=64 ;; ++ alpha_vms_vec) tb="$tb vms-alpha.lo vms-misc.lo vms-lib.lo"; target_size=64 ;; ++ alpha_vms_lib_txt_vec) tb="$tb vms-lib.lo vms-misc.lo" ;; +++ sw_64_ecoff_le_vec) tb="$tb coff-sw_64.lo ecoff.lo $ecoff"; target_size=64 ;; +++ sw_64_elf64_vec) tb="$tb elf64-sw_64.lo elf64.lo $elf"; target_size=64 ;; +++ sw_64_elf64_fbsd_vec) tb="$tb elf64-sw_64.lo elf64.lo $elf"; target_size=64 ;; +++ sw_64_vms_vec) tb="$tb vms-sw_64.lo vms-misc.lo vms-lib.lo"; target_size=64 ;; ++ am33_elf32_linux_vec) tb="$tb elf32-am33lin.lo elf32.lo $elf" ;; ++ aout0_be_vec) tb="$tb aout0.lo aout32.lo" ;; ++ aout64_vec) tb="$tb demo64.lo aout64.lo"; target_size=64 ;; ++@@ -15161,6 +15165,19 @@ ++ alpha*-*-*) ++ COREFILE=osf-core.lo ++ ;; +++ sw_64*-*-freebsd* | sw_64*-*-kfreebsd*-gnu | sw_64*-*-*vms*) +++ COREFILE='' +++ ;; +++ sw_64*-*-linux-*) +++ COREFILE=trad-core.lo +++ TRAD_HEADER='"hosts/sw_64linux.h"' +++ ;; +++ sw_64*-*-netbsd* | sw_64*-*-openbsd*) +++ COREFILE=netbsd-core.lo +++ ;; +++ sw_64*-*-*) +++ COREFILE=osf-core.lo +++ ;; ++ arm-*-freebsd* | arm-*-kfreebsd*-gnu) ++ COREFILE='' ;; ++ arm*-*-netbsd* | arm-*-openbsd*) ++diff -Nuar gdb-10.2/bfd/configure.ac gdb-10.2/bfd/configure.ac ++--- gdb-10.2/bfd/configure.ac 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/configure.ac 2025-04-16 17:06:51.912086800 +0800 ++@@ -454,6 +454,11 @@ ++ alpha_elf64_fbsd_vec) tb="$tb elf64-alpha.lo elf64.lo $elf"; target_size=64 ;; ++ alpha_vms_vec) tb="$tb vms-alpha.lo vms-misc.lo vms-lib.lo"; target_size=64 ;; ++ alpha_vms_lib_txt_vec) tb="$tb vms-lib.lo vms-misc.lo" ;; +++ sw_64_ecoff_le_vec) tb="$tb coff-sw_64.lo ecoff.lo $ecoff"; target_size=64 ;; +++ sw_64_elf64_vec) tb="$tb elf64-sw_64.lo elf64.lo $elf"; target_size=64 ;; +++ sw_64_elf64_fbsd_vec) tb="$tb elf64-sw_64.lo elf64.lo $elf"; target_size=64 ;; +++ sw_64_vms_vec) tb="$tb vms-sw_64.lo vms-misc.lo vms-lib.lo"; target_size=64 ;; +++ sw_64_vms_lib_txt_vec) tb="$tb vms-lib.lo vms-misc.lo" ;; ++ am33_elf32_linux_vec) tb="$tb elf32-am33lin.lo elf32.lo $elf" ;; ++ aout0_be_vec) tb="$tb aout0.lo aout32.lo" ;; ++ aout64_vec) tb="$tb demo64.lo aout64.lo"; target_size=64 ;; ++@@ -852,6 +857,19 @@ ++ alpha*-*-*) ++ COREFILE=osf-core.lo ++ ;; +++ sw_64*-*-freebsd* | sw_64*-*-kfreebsd*-gnu | sw_64*-*-*vms*) +++ COREFILE='' +++ ;; +++ sw_64*-*-linux-*) +++ COREFILE=trad-core.lo +++ TRAD_HEADER='"hosts/sw_64linux.h"' +++ ;; +++ sw_64*-*-netbsd* | sw_64*-*-openbsd*) +++ COREFILE=netbsd-core.lo +++ ;; +++ sw_64*-*-*) +++ COREFILE=osf-core.lo +++ ;; ++ arm-*-freebsd* | arm-*-kfreebsd*-gnu) ++ COREFILE='' ;; ++ arm*-*-netbsd* | arm-*-openbsd*) ++diff -Nuar gdb-10.2/bfd/configure.com gdb-10.2/bfd/configure.com ++--- gdb-10.2/bfd/configure.com 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/configure.com 2025-04-16 17:06:51.912086800 +0800 ++@@ -26,9 +26,10 @@ ++ $ arch=F$GETSYI("ARCH_NAME") ++ $ arch=F$EDIT(arch,"LOWERCASE") ++ $if arch .eqs. "alpha" then target = "alpha" +++$if arch .eqs. "sw_64" then target = "sw_64" ++ $if arch .eqs. "ia64" then target = "ia64" ++ $! ++-$if (arch .eqs. "alpha") .or. (arch .eqs. "ia64") +++$if (arch .eqs. "alpha") .or. (arch .eqs. "sw_64") .or. (arch .eqs. "ia64") ++ $then ++ $! ++ $ write sys$output "Configuring BFD for ''target' target" ++@@ -335,6 +336,15 @@ ++ $ FILES="cpu-alpha,vms,vms-hdr,vms-gsd,vms-tir,vms-misc," ++ $EOD ++ $ endif +++$ if ARCH.eqs."sw_64" +++$ then +++$ create build.com +++$DECK +++$ DEFS="""SELECT_VECS=&sw_64_vms_vec"","+- +++ """SELECT_ARCHITECTURES=&bfd_sw_64_arch""" +++$ FILES="cpu-sw_64,vms,vms-hdr,vms-gsd,vms-tir,vms-misc," +++$EOD +++$ endif ++ $ if ARCH.eqs."ia64" ++ $ then ++ $ create build.com ++diff -Nuar gdb-10.2/bfd/cpu-sw_64.c gdb-10.2/bfd/cpu-sw_64.c ++--- gdb-10.2/bfd/cpu-sw_64.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/cpu-sw_64.c 2025-04-16 17:06:51.912086800 +0800 ++@@ -0,0 +1,53 @@ +++/* BFD support for the SW_64 architecture. +++ Copyright (C) 1992-2019 Free Software Foundation, Inc. +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++#include "sysdep.h" +++#include "bfd.h" +++#include "libbfd.h" +++ +++#define N(BITS_WORD, BITS_ADDR, NUMBER, PRINT, DEFAULT, NEXT) \ +++ { \ +++ BITS_WORD, /* Bits in a word. */ \ +++ BITS_ADDR, /* Bits in an address. */ \ +++ 8, /* Bits in a byte. */ \ +++ bfd_arch_sw_64, \ +++ NUMBER, \ +++ "sw_64", \ +++ PRINT, \ +++ 3, /* Section alignment power. */ \ +++ DEFAULT, \ +++ bfd_default_compatible, \ +++ bfd_default_scan, \ +++ bfd_arch_default_fill, \ +++ NEXT, \ +++ 0 /* Maximum offset of a reloc from the start of an insn. */ \ +++ } +++ +++#define NN(index) (&arch_info_struct[index]) +++ +++/* These exist only so that we can reasonably disassemble PALcode. */ +++static const bfd_arch_info_type arch_info_struct[] = +++{ +++ N (64, 64, bfd_mach_sw_64_sw6a, "sw_64:sw6a", FALSE, NN(1)), +++ N (64, 64, bfd_mach_sw_64_sw6b, "sw_64:sw6b", FALSE, 0), +++}; +++ +++const bfd_arch_info_type bfd_sw_64_arch = +++ N (64, 64, 0, "sw_64", TRUE, NN(0)); ++diff -Nuar gdb-10.2/bfd/ecoff.c gdb-10.2/bfd/ecoff.c ++--- gdb-10.2/bfd/ecoff.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/ecoff.c 2025-04-16 17:06:51.912086800 +0800 ++@@ -233,6 +233,10 @@ ++ arch = bfd_arch_alpha; ++ mach = 0; ++ break; +++ case SW_64_MAGIC: +++ arch = bfd_arch_sw_64; +++ mach = 0; +++ break; ++ ++ default: ++ arch = bfd_arch_obscure; ++@@ -287,6 +291,9 @@ ++ case bfd_arch_alpha: ++ return ALPHA_MAGIC; ++ +++ case bfd_arch_sw_64: +++ return SW_64_MAGIC; +++ ++ default: ++ abort (); ++ return 0; ++diff -Nuar gdb-10.2/bfd/elf64-sw_64.c gdb-10.2/bfd/elf64-sw_64.c ++--- gdb-10.2/bfd/elf64-sw_64.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/elf64-sw_64.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -0,0 +1,5575 @@ +++/* Sw_64 specific support for 64-bit ELF +++ Copyright (C) 1996-2020 Free Software Foundation, Inc. +++ Contributed by Richard Henderson . +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++ +++/* We need a published ABI spec for this. Until one comes out, don't +++ assume this'll remain unchanged forever. */ +++ +++#include "sysdep.h" +++#include "bfd.h" +++#include "libbfd.h" +++#include "elf-bfd.h" +++#include "ecoff-bfd.h" +++ +++#include "elf/sw_64.h" +++ +++#define SW_64ECOFF +++ +++#define NO_COFF_RELOCS +++#define NO_COFF_SYMBOLS +++#define NO_COFF_LINENOS +++ +++/* Get the ECOFF swapping routines. Needed for the debug information. */ +++#include "coff/internal.h" +++#include "coff/sym.h" +++#include "coff/symconst.h" +++#include "coff/ecoff.h" +++#include "coff/sw_64.h" +++#include "aout/ar.h" +++#include "libcoff.h" +++#include "libecoff.h" +++#define ECOFF_64 +++#include "ecoffswap.h" +++ +++ +++/* Instruction data for plt generation and relaxation. */ +++ +++#define OP_LDA 0x08U +++#define OP_LDAH 0x09U +++#define OP_LDQ 0x29U +++#define OP_BR 0x30U +++#define OP_BSR 0x34U +++ +++#define INSN_LDA (OP_LDA << 26) +++#define INSN_LDAH (OP_LDAH << 26) +++#define INSN_LDQ (OP_LDQ << 26) +++#define INSN_BR (OP_BR << 26) +++ +++#define INSN_ADDQ 0x40000400 +++#define INSN_RDUNIQ 0x0000009e +++#define INSN_SUBQ 0x40000520 +++#define INSN_S4SUBQ 0x40000560 +++#define INSN_UNOP 0x2ffe0000 +++ +++#define INSN_JSR 0x68004000 +++#define INSN_JMP 0x68000000 +++#define INSN_JSR_MASK 0xfc00c000 +++ +++#define INSN_A(I,A) (I | ((unsigned) A << 21)) +++#define INSN_AB(I,A,B) (INSN_A (I, A) | (B << 16)) +++#define INSN_ABC(I,A,B,C) (INSN_A (I, A) | (B << 16) | C) +++#define INSN_ABO(I,A,B,O) (INSN_A (I, A) | (B << 16) | ((O) & 0xffff)) +++#define INSN_AD(I,A,D) (INSN_A (I, A) | (((D) >> 2) & 0x1fffff)) +++ +++/* PLT/GOT Stuff */ +++ +++/* Set by ld emulation. Putting this into the link_info or hash structure +++ is simply working too hard. */ +++#ifdef USE_SECUREPLT +++bfd_boolean elf64_sw_64_use_secureplt = TRUE; +++#else +++bfd_boolean elf64_sw_64_use_secureplt = FALSE; +++#endif +++ +++#define OLD_PLT_HEADER_SIZE 32 +++#define OLD_PLT_ENTRY_SIZE 12 +++#define NEW_PLT_HEADER_SIZE 36 +++#define NEW_PLT_ENTRY_SIZE 4 +++ +++#define PLT_HEADER_SIZE \ +++ (elf64_sw_64_use_secureplt ? NEW_PLT_HEADER_SIZE : OLD_PLT_HEADER_SIZE) +++#define PLT_ENTRY_SIZE \ +++ (elf64_sw_64_use_secureplt ? NEW_PLT_ENTRY_SIZE : OLD_PLT_ENTRY_SIZE) +++ +++#define MAX_GOT_SIZE (64*1024) +++ +++#define ELF_DYNAMIC_INTERPRETER "/usr/lib/ld.so" +++ +++ +++/* Used to implement multiple .got subsections. */ +++struct sw_64_elf_got_entry +++{ +++ struct sw_64_elf_got_entry *next; +++ +++ /* Which .got subsection? */ +++ bfd *gotobj; +++ +++ /* The addend in effect for this entry. */ +++ bfd_vma addend; +++ +++ /* The .got offset for this entry. */ +++ int got_offset; +++ +++ /* The .plt offset for this entry. */ +++ int plt_offset; +++ +++ /* How many references to this entry? */ +++ int use_count; +++ +++ /* The relocation type of this entry. */ +++ unsigned char reloc_type; +++ +++ /* How a LITERAL is used. */ +++ unsigned char flags; +++ +++ /* Have we initialized the dynamic relocation for this entry? */ +++ unsigned char reloc_done; +++ +++ /* Have we adjusted this entry for SEC_MERGE? */ +++ unsigned char reloc_xlated; +++}; +++ +++struct sw_64_elf_reloc_entry +++{ +++ struct sw_64_elf_reloc_entry *next; +++ +++ /* Which .reloc section? */ +++ asection *srel; +++ +++ /* Which section this relocation is against? */ +++ asection *sec; +++ +++ /* How many did we find? */ +++ unsigned long count; +++ +++ /* What kind of relocation? */ +++ unsigned int rtype; +++}; +++ +++struct sw_64_elf_link_hash_entry +++{ +++ struct elf_link_hash_entry root; +++ +++ /* External symbol information. */ +++ EXTR esym; +++ +++ /* Cumulative flags for all the .got entries. */ +++ int flags; +++ +++ /* Contexts in which a literal was referenced. */ +++#define SW_64_ELF_LINK_HASH_LU_ADDR 0x01 +++#define SW_64_ELF_LINK_HASH_LU_MEM 0x02 +++#define SW_64_ELF_LINK_HASH_LU_BYTE 0x04 +++#define SW_64_ELF_LINK_HASH_LU_JSR 0x08 +++#define SW_64_ELF_LINK_HASH_LU_TLSGD 0x10 +++#define SW_64_ELF_LINK_HASH_LU_TLSLDM 0x20 +++#define SW_64_ELF_LINK_HASH_LU_JSRDIRECT 0x40 +++#define SW_64_ELF_LINK_HASH_LU_PLT 0x38 +++#define SW_64_ELF_LINK_HASH_TLS_IE 0x80 +++ +++ /* Used to implement multiple .got subsections. */ +++ struct sw_64_elf_got_entry *got_entries; +++ +++ /* Used to count non-got, non-plt relocations for delayed sizing +++ of relocation sections. */ +++ struct sw_64_elf_reloc_entry *reloc_entries; +++}; +++ +++/* Sw_64 ELF linker hash table. */ +++ +++struct sw_64_elf_link_hash_table +++{ +++ struct elf_link_hash_table root; +++ +++ /* The head of a list of .got subsections linked through +++ sw_64_elf_tdata(abfd)->got_link_next. */ +++ bfd *got_list; +++ +++ /* The most recent relax pass that we've seen. The GOTs +++ should be regenerated if this doesn't match. */ +++ int relax_trip; +++}; +++ +++/* Look up an entry in a Sw_64 ELF linker hash table. */ +++ +++#define sw_64_elf_link_hash_lookup(table, string, create, copy, follow) \ +++ ((struct sw_64_elf_link_hash_entry *) \ +++ elf_link_hash_lookup (&(table)->root, (string), (create), \ +++ (copy), (follow))) +++ +++/* Traverse a Sw_64 ELF linker hash table. */ +++ +++#define sw_64_elf_link_hash_traverse(table, func, info) \ +++ (elf_link_hash_traverse \ +++ (&(table)->root, \ +++ (bfd_boolean (*) (struct elf_link_hash_entry *, void *)) (func), \ +++ (info))) +++ +++/* Get the Sw_64 ELF linker hash table from a link_info structure. */ +++ +++#define sw_64_elf_hash_table(p) \ +++ ((is_elf_hash_table ((p)->hash) \ +++ && elf_hash_table_id (elf_hash_table (p)) == SW_64_ELF_DATA) \ +++ ? (struct sw_64_elf_link_hash_table *) (p)->hash : NULL) +++ +++/* Get the object's symbols as our own entry type. */ +++ +++#define sw_64_elf_sym_hashes(abfd) \ +++ ((struct sw_64_elf_link_hash_entry **)elf_sym_hashes(abfd)) +++ +++/* Should we do dynamic things to this symbol? This differs from the +++ generic version in that we never need to consider function pointer +++ equality wrt PLT entries -- we don't create a PLT entry if a symbol's +++ address is ever taken. */ +++ +++static inline bfd_boolean +++sw_64_elf_dynamic_symbol_p (struct elf_link_hash_entry *h, +++ struct bfd_link_info *info) +++{ +++ return _bfd_elf_dynamic_symbol_p (h, info, 0); +++} +++ +++/* Create an entry in a Sw_64 ELF linker hash table. */ +++ +++static struct bfd_hash_entry * +++elf64_sw_64_link_hash_newfunc (struct bfd_hash_entry *entry, +++ struct bfd_hash_table *table, +++ const char *string) +++{ +++ struct sw_64_elf_link_hash_entry *ret = +++ (struct sw_64_elf_link_hash_entry *) entry; +++ +++ /* Allocate the structure if it has not already been allocated by a +++ subclass. */ +++ if (ret == (struct sw_64_elf_link_hash_entry *) NULL) +++ ret = ((struct sw_64_elf_link_hash_entry *) +++ bfd_hash_allocate (table, +++ sizeof (struct sw_64_elf_link_hash_entry))); +++ if (ret == (struct sw_64_elf_link_hash_entry *) NULL) +++ return (struct bfd_hash_entry *) ret; +++ +++ /* Call the allocation method of the superclass. */ +++ ret = ((struct sw_64_elf_link_hash_entry *) +++ _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret, +++ table, string)); +++ if (ret != (struct sw_64_elf_link_hash_entry *) NULL) +++ { +++ /* Set local fields. */ +++ memset (&ret->esym, 0, sizeof (EXTR)); +++ /* We use -2 as a marker to indicate that the information has +++ not been set. -1 means there is no associated ifd. */ +++ ret->esym.ifd = -2; +++ ret->flags = 0; +++ ret->got_entries = NULL; +++ ret->reloc_entries = NULL; +++ } +++ +++ return (struct bfd_hash_entry *) ret; +++} +++ +++/* Create a Sw_64 ELF linker hash table. */ +++ +++static struct bfd_link_hash_table * +++elf64_sw_64_bfd_link_hash_table_create (bfd *abfd) +++{ +++ struct sw_64_elf_link_hash_table *ret; +++ size_t amt = sizeof (struct sw_64_elf_link_hash_table); +++ +++ ret = (struct sw_64_elf_link_hash_table *) bfd_zmalloc (amt); +++ if (ret == (struct sw_64_elf_link_hash_table *) NULL) +++ return NULL; +++ +++ if (!_bfd_elf_link_hash_table_init (&ret->root, abfd, +++ elf64_sw_64_link_hash_newfunc, +++ sizeof (struct sw_64_elf_link_hash_entry), +++ SW_64_ELF_DATA)) +++ { +++ free (ret); +++ return NULL; +++ } +++ +++ return &ret->root.root; +++} +++ +++/* Sw_64 ELF follows MIPS ELF in using a special find_nearest_line +++ routine in order to handle the ECOFF debugging information. */ +++ +++struct sw_64_elf_find_line +++{ +++ struct ecoff_debug_info d; +++ struct ecoff_find_line i; +++}; +++ +++/* We have some private fields hanging off of the elf_tdata structure. */ +++ +++struct sw_64_elf_obj_tdata +++{ +++ struct elf_obj_tdata root; +++ +++ /* For every input file, these are the got entries for that object's +++ local symbols. */ +++ struct sw_64_elf_got_entry ** local_got_entries; +++ +++ /* For every input file, this is the object that owns the got that +++ this input file uses. */ +++ bfd *gotobj; +++ +++ /* For every got, this is a linked list through the objects using this got */ +++ bfd *in_got_link_next; +++ +++ /* For every got, this is a link to the next got subsegment. */ +++ bfd *got_link_next; +++ +++ /* For every got, this is the section. */ +++ asection *got; +++ +++ /* For every got, this is it's total number of words. */ +++ int total_got_size; +++ +++ /* For every got, this is the sum of the number of words required +++ to hold all of the member object's local got. */ +++ int local_got_size; +++ +++ /* Used by elf64_sw_64_find_nearest_line entry point. */ +++ struct sw_64_elf_find_line *find_line_info; +++ +++}; +++ +++#define sw_64_elf_tdata(abfd) \ +++ ((struct sw_64_elf_obj_tdata *) (abfd)->tdata.any) +++ +++#define is_sw_64_elf(bfd) \ +++ (bfd_get_flavour (bfd) == bfd_target_elf_flavour \ +++ && elf_tdata (bfd) != NULL \ +++ && elf_object_id (bfd) == SW_64_ELF_DATA) +++ +++static bfd_boolean +++elf64_sw_64_mkobject (bfd *abfd) +++{ +++ return bfd_elf_allocate_object (abfd, sizeof (struct sw_64_elf_obj_tdata), +++ SW_64_ELF_DATA); +++} +++ +++static bfd_boolean +++elf64_sw_64_object_p (bfd *abfd) +++{ +++ /* Set the right machine number for an Sw_64 ELF file. */ +++ return bfd_default_set_arch_mach (abfd, bfd_arch_sw_64, 0); +++} +++ +++/* A relocation function which doesn't do anything. */ +++ +++static bfd_reloc_status_type +++elf64_sw_64_reloc_nil (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc, +++ asymbol *sym ATTRIBUTE_UNUSED, +++ void * data ATTRIBUTE_UNUSED, asection *sec, +++ bfd *output_bfd, char **error_message ATTRIBUTE_UNUSED) +++{ +++ if (output_bfd) +++ reloc->address += sec->output_offset; +++ return bfd_reloc_ok; +++} +++ +++/* A relocation function used for an unsupported reloc. */ +++ +++static bfd_reloc_status_type +++elf64_sw_64_reloc_bad (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc, +++ asymbol *sym ATTRIBUTE_UNUSED, +++ void * data ATTRIBUTE_UNUSED, asection *sec, +++ bfd *output_bfd, char **error_message ATTRIBUTE_UNUSED) +++{ +++ if (output_bfd) +++ reloc->address += sec->output_offset; +++ return bfd_reloc_notsupported; +++} +++ +++/* Do the work of the GPDISP relocation. */ +++ +++static bfd_reloc_status_type +++elf64_sw_64_do_reloc_gpdisp (bfd *abfd, bfd_vma gpdisp, bfd_byte *p_ldah, +++ bfd_byte *p_lda) +++{ +++ bfd_reloc_status_type ret = bfd_reloc_ok; +++ bfd_vma addend; +++ unsigned long i_ldah, i_lda; +++ +++ i_ldah = bfd_get_32 (abfd, p_ldah); +++ i_lda = bfd_get_32 (abfd, p_lda); +++ +++ /* Complain if the instructions are not correct. */ +++#ifndef XWB20200308 +++ if (((i_ldah >> 26) & 0x3f) != 0x3f +++ || ((i_lda >> 26) & 0x3f) != 0x3e) +++#else +++ if (((i_ldah >> 26) & 0x3f) != 0x09 +++ || ((i_lda >> 26) & 0x3f) != 0x08) +++#endif +++ ret = bfd_reloc_dangerous; +++ +++ /* Extract the user-supplied offset, mirroring the sign extensions +++ that the instructions perform. */ +++ addend = ((i_ldah & 0xffff) << 16) | (i_lda & 0xffff); +++ addend = (addend ^ 0x80008000) - 0x80008000; +++ +++ gpdisp += addend; +++ +++ if ((bfd_signed_vma) gpdisp < -(bfd_signed_vma) 0x80000000 +++ || (bfd_signed_vma) gpdisp >= (bfd_signed_vma) 0x7fff8000) +++ ret = bfd_reloc_overflow; +++ +++ /* compensate for the sign extension again. */ +++ i_ldah = ((i_ldah & 0xffff0000) +++ | (((gpdisp >> 16) + ((gpdisp >> 15) & 1)) & 0xffff)); +++ i_lda = (i_lda & 0xffff0000) | (gpdisp & 0xffff); +++ +++ bfd_put_32 (abfd, (bfd_vma) i_ldah, p_ldah); +++ bfd_put_32 (abfd, (bfd_vma) i_lda, p_lda); +++ +++ return ret; +++} +++ +++/* The special function for the GPDISP reloc. */ +++ +++static bfd_reloc_status_type +++elf64_sw_64_reloc_gpdisp (bfd *abfd, arelent *reloc_entry, +++ asymbol *sym ATTRIBUTE_UNUSED, void * data, +++ asection *input_section, bfd *output_bfd, +++ char **err_msg) +++{ +++ bfd_reloc_status_type ret; +++ bfd_vma gp, relocation; +++ bfd_vma high_address; +++ bfd_byte *p_ldah, *p_lda; +++ +++ /* Don't do anything if we're not doing a final link. */ +++ if (output_bfd) +++ { +++ reloc_entry->address += input_section->output_offset; +++ return bfd_reloc_ok; +++ } +++ +++ high_address = bfd_get_section_limit (abfd, input_section); +++ if (reloc_entry->address > high_address +++ || reloc_entry->address + reloc_entry->addend > high_address) +++ return bfd_reloc_outofrange; +++ +++ /* The gp used in the portion of the output object to which this +++ input object belongs is cached on the input bfd. */ +++ gp = _bfd_get_gp_value (abfd); +++ +++ relocation = (input_section->output_section->vma +++ + input_section->output_offset +++ + reloc_entry->address); +++ +++ p_ldah = (bfd_byte *) data + reloc_entry->address; +++ p_lda = p_ldah + reloc_entry->addend; +++ +++ ret = elf64_sw_64_do_reloc_gpdisp (abfd, gp - relocation, p_ldah, p_lda); +++ +++ /* Complain if the instructions are not correct. */ +++ if (ret == bfd_reloc_dangerous) +++ *err_msg = _("GPDISP relocation did not find ldah and lda instructions"); +++ +++ return ret; +++} +++ +++/* In case we're on a 32-bit machine, construct a 64-bit "-1" value +++ from smaller values. Start with zero, widen, *then* decrement. */ +++#define MINUS_ONE (((bfd_vma)0) - 1) +++ +++ +++#define SKIP_HOWTO(N) \ +++ HOWTO(N, 0, 0, 0, 0, 0, complain_overflow_dont, elf64_sw_64_reloc_bad, 0, 0, 0, 0, 0) +++ +++static reloc_howto_type elf64_sw_64_howto_table[] = +++{ +++ HOWTO (R_SW_64_NONE, /* type */ +++ 0, /* rightshift */ +++ 3, /* size (0 = byte, 1 = short, 2 = long) */ +++ 0, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ elf64_sw_64_reloc_nil, /* special_function */ +++ "NONE", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A 32 bit reference to a symbol. */ +++ HOWTO (R_SW_64_REFLONG, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "REFLONG", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 64 bit reference to a symbol. */ +++ HOWTO (R_SW_64_REFQUAD, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "REFQUAD", /* name */ +++ FALSE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 32 bit GP relative offset. This is just like REFLONG except +++ that when the value is used the value of the gp register will be +++ added in. */ +++ HOWTO (R_SW_64_GPREL32, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GPREL32", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Used for an instruction that refers to memory off the GP register. */ +++ HOWTO (R_SW_64_LITERAL, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "ELF_LITERAL", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* This reloc only appears immediately following an ELF_LITERAL reloc. +++ It identifies a use of the literal. The symbol index is special: +++ 1 means the literal address is in the base register of a memory +++ format instruction; 2 means the literal address is in the byte +++ offset register of a byte-manipulation instruction; 3 means the +++ literal address is in the target register of a jsr instruction. +++ This does not actually do any relocation. */ +++ HOWTO (R_SW_64_LITUSE, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ elf64_sw_64_reloc_nil, /* special_function */ +++ "LITUSE", /* name */ +++ FALSE, /* partial_inplace */ +++ 0, /* src_mask */ +++ 0, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Load the gp register. This is always used for a ldah instruction +++ which loads the upper 16 bits of the gp register. The symbol +++ index of the GPDISP instruction is an offset in bytes to the lda +++ instruction that loads the lower 16 bits. The value to use for +++ the relocation is the difference between the GP value and the +++ current location; the load will always be done against a register +++ holding the current address. +++ +++ NOTE: Unlike ECOFF, partial in-place relocation is not done. If +++ any offset is present in the instructions, it is an offset from +++ the register to the ldah instruction. This lets us avoid any +++ stupid hackery like inventing a gp value to do partial relocation +++ against. Also unlike ECOFF, we do the whole relocation off of +++ the GPDISP rather than a GPDISP_HI16/GPDISP_LO16 pair. An odd, +++ space consuming bit, that, since all the information was present +++ in the GPDISP_HI16 reloc. */ +++ HOWTO (R_SW_64_GPDISP, /* type */ +++ 16, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ elf64_sw_64_reloc_gpdisp, /* special_function */ +++ "GPDISP", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A 21 bit branch. */ +++ HOWTO (R_SW_64_BRADDR, /* type */ +++ 2, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 21, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "BRADDR", /* name */ +++ FALSE, /* partial_inplace */ +++ 0x1fffff, /* src_mask */ +++ 0x1fffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A hint for a jump to a register. */ +++#ifndef XWB20200308 +++ HOWTO (R_SW_64_HINT, /* type */ +++ 2, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "HINT", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++#else +++ HOWTO (R_SW_64_HINT, /* type */ +++ 2, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 14, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "HINT", /* name */ +++ FALSE, /* partial_inplace */ +++ 0x3fff, /* src_mask */ +++ 0x3fff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++#endif +++ +++ /* 16 bit PC relative offset. */ +++ HOWTO (R_SW_64_SREL16, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "SREL16", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* 32 bit PC relative offset. */ +++ HOWTO (R_SW_64_SREL32, /* type */ +++ 0, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 32, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "SREL32", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffffffff, /* src_mask */ +++ 0xffffffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* A 64 bit PC relative offset. */ +++ HOWTO (R_SW_64_SREL64, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "SREL64", /* name */ +++ FALSE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* Skip 12 - 16; deprecated ECOFF relocs. */ +++ SKIP_HOWTO (12), +++ SKIP_HOWTO (13), +++ SKIP_HOWTO (14), +++ SKIP_HOWTO (15), +++ SKIP_HOWTO (16), +++ +++ /* The high 16 bits of the displacement from GP to the target. */ +++ HOWTO (R_SW_64_GPRELHIGH, +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GPRELHIGH", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* The low 16 bits of the displacement from GP to the target. */ +++ HOWTO (R_SW_64_GPRELLOW, +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GPRELLOW", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 16-bit displacement from the GP to the target. */ +++ HOWTO (R_SW_64_GPREL16, +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GPREL16", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Skip 20 - 23; deprecated ECOFF relocs. */ +++ SKIP_HOWTO (20), +++ SKIP_HOWTO (21), +++ SKIP_HOWTO (22), +++ SKIP_HOWTO (23), +++ +++ /* Misc ELF relocations. */ +++ +++ /* A dynamic relocation to copy the target into our .dynbss section. */ +++ /* Not generated, as all Sw_64 objects use PIC, so it is not needed. It +++ is present because every other ELF has one, but should not be used +++ because .dynbss is an ugly thing. */ +++ HOWTO (R_SW_64_COPY, +++ 0, +++ 0, +++ 0, +++ FALSE, +++ 0, +++ complain_overflow_dont, +++ bfd_elf_generic_reloc, +++ "COPY", +++ FALSE, +++ 0, +++ 0, +++ TRUE), +++ +++ /* A dynamic relocation for a .got entry. */ +++ HOWTO (R_SW_64_GLOB_DAT, +++ 0, +++ 0, +++ 0, +++ FALSE, +++ 0, +++ complain_overflow_dont, +++ bfd_elf_generic_reloc, +++ "GLOB_DAT", +++ FALSE, +++ 0, +++ 0, +++ TRUE), +++ +++ /* A dynamic relocation for a .plt entry. */ +++ HOWTO (R_SW_64_JMP_SLOT, +++ 0, +++ 0, +++ 0, +++ FALSE, +++ 0, +++ complain_overflow_dont, +++ bfd_elf_generic_reloc, +++ "JMP_SLOT", +++ FALSE, +++ 0, +++ 0, +++ TRUE), +++ +++ /* A dynamic relocation to add the base of the DSO to a 64-bit field. */ +++ HOWTO (R_SW_64_RELATIVE, +++ 0, +++ 0, +++ 0, +++ FALSE, +++ 0, +++ complain_overflow_dont, +++ bfd_elf_generic_reloc, +++ "RELATIVE", +++ FALSE, +++ 0, +++ 0, +++ TRUE), +++ +++ /* A 21 bit branch that adjusts for gp loads. */ +++ HOWTO (R_SW_64_BRSGP, /* type */ +++ 2, /* rightshift */ +++ 2, /* size (0 = byte, 1 = short, 2 = long) */ +++ 21, /* bitsize */ +++ TRUE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "BRSGP", /* name */ +++ FALSE, /* partial_inplace */ +++ 0x1fffff, /* src_mask */ +++ 0x1fffff, /* dst_mask */ +++ TRUE), /* pcrel_offset */ +++ +++ /* Creates a tls_index for the symbol in the got. */ +++ HOWTO (R_SW_64_TLSGD, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TLSGD", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Creates a tls_index for the (current) module in the got. */ +++ HOWTO (R_SW_64_TLSLDM, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TLSLDM", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A dynamic relocation for a DTP module entry. */ +++ HOWTO (R_SW_64_DTPMOD64, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "DTPMOD64", /* name */ +++ FALSE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Creates a 64-bit offset in the got for the displacement +++ from DTP to the target. */ +++ HOWTO (R_SW_64_GOTDTPREL, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GOTDTPREL", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A dynamic relocation for a displacement from DTP to the target. */ +++ HOWTO (R_SW_64_DTPREL64, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "DTPREL64", /* name */ +++ FALSE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* The high 16 bits of the displacement from DTP to the target. */ +++ HOWTO (R_SW_64_DTPRELHI, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "DTPRELHI", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* The low 16 bits of the displacement from DTP to the target. */ +++ HOWTO (R_SW_64_DTPRELLO, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "DTPRELLO", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 16-bit displacement from DTP to the target. */ +++ HOWTO (R_SW_64_DTPREL16, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "DTPREL16", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* Creates a 64-bit offset in the got for the displacement +++ from TP to the target. */ +++ HOWTO (R_SW_64_GOTTPREL, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "GOTTPREL", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A dynamic relocation for a displacement from TP to the target. */ +++ HOWTO (R_SW_64_TPREL64, /* type */ +++ 0, /* rightshift */ +++ 4, /* size (0 = byte, 1 = short, 2 = long) */ +++ 64, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_bitfield, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TPREL64", /* name */ +++ FALSE, /* partial_inplace */ +++ MINUS_ONE, /* src_mask */ +++ MINUS_ONE, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* The high 16 bits of the displacement from TP to the target. */ +++ HOWTO (R_SW_64_TPRELHI, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TPRELHI", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* The low 16 bits of the displacement from TP to the target. */ +++ HOWTO (R_SW_64_TPRELLO, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_dont, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TPRELLO", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++ +++ /* A 16-bit displacement from TP to the target. */ +++ HOWTO (R_SW_64_TPREL16, /* type */ +++ 0, /* rightshift */ +++ 1, /* size (0 = byte, 1 = short, 2 = long) */ +++ 16, /* bitsize */ +++ FALSE, /* pc_relative */ +++ 0, /* bitpos */ +++ complain_overflow_signed, /* complain_on_overflow */ +++ bfd_elf_generic_reloc, /* special_function */ +++ "TPREL16", /* name */ +++ FALSE, /* partial_inplace */ +++ 0xffff, /* src_mask */ +++ 0xffff, /* dst_mask */ +++ FALSE), /* pcrel_offset */ +++}; +++ +++/* A mapping from BFD reloc types to Sw_64 ELF reloc types. */ +++ +++struct elf_reloc_map +++{ +++ bfd_reloc_code_real_type bfd_reloc_val; +++ int elf_reloc_val; +++}; +++ +++static const struct elf_reloc_map elf64_sw_64_reloc_map[] = +++{ +++ {BFD_RELOC_NONE, R_SW_64_NONE}, +++ {BFD_RELOC_32, R_SW_64_REFLONG}, +++ {BFD_RELOC_64, R_SW_64_REFQUAD}, +++ {BFD_RELOC_CTOR, R_SW_64_REFQUAD}, +++ {BFD_RELOC_GPREL32, R_SW_64_GPREL32}, +++ {BFD_RELOC_SW_64_ELF_LITERAL, R_SW_64_LITERAL}, +++ {BFD_RELOC_SW_64_LITUSE, R_SW_64_LITUSE}, +++ {BFD_RELOC_SW_64_GPDISP, R_SW_64_GPDISP}, +++ {BFD_RELOC_23_PCREL_S2, R_SW_64_BRADDR}, +++ {BFD_RELOC_SW_64_HINT, R_SW_64_HINT}, +++ {BFD_RELOC_16_PCREL, R_SW_64_SREL16}, +++ {BFD_RELOC_32_PCREL, R_SW_64_SREL32}, +++ {BFD_RELOC_64_PCREL, R_SW_64_SREL64}, +++#ifndef XWB20200308 +++ {BFD_RELOC_20_PCREL_S2, R_SW_64_BR18ADDR}, +++ {BFD_RELOC_24_PCREL_S2, R_SW_64_BR22ADDR}, +++#endif +++ {BFD_RELOC_SW_64_GPREL_HI16, R_SW_64_GPRELHIGH}, +++ {BFD_RELOC_SW_64_GPREL_LO16, R_SW_64_GPRELLOW}, +++ {BFD_RELOC_GPREL16, R_SW_64_GPREL16}, +++ {BFD_RELOC_SW_64_BRSGP, R_SW_64_BRSGP}, +++ {BFD_RELOC_SW_64_TLSGD, R_SW_64_TLSGD}, +++ {BFD_RELOC_SW_64_TLSLDM, R_SW_64_TLSLDM}, +++ {BFD_RELOC_SW_64_DTPMOD64, R_SW_64_DTPMOD64}, +++ {BFD_RELOC_SW_64_GOTDTPREL16, R_SW_64_GOTDTPREL}, +++ {BFD_RELOC_SW_64_DTPREL64, R_SW_64_DTPREL64}, +++ {BFD_RELOC_SW_64_DTPREL_HI16, R_SW_64_DTPRELHI}, +++ {BFD_RELOC_SW_64_DTPREL_LO16, R_SW_64_DTPRELLO}, +++ {BFD_RELOC_SW_64_DTPREL16, R_SW_64_DTPREL16}, +++ {BFD_RELOC_SW_64_GOTTPREL16, R_SW_64_GOTTPREL}, +++ {BFD_RELOC_SW_64_TPREL64, R_SW_64_TPREL64}, +++ {BFD_RELOC_SW_64_TPREL_HI16, R_SW_64_TPRELHI}, +++ {BFD_RELOC_SW_64_TPREL_LO16, R_SW_64_TPRELLO}, +++ {BFD_RELOC_SW_64_TPREL16, R_SW_64_TPREL16}, +++}; +++ +++/* Given a BFD reloc type, return a HOWTO structure. */ +++ +++static reloc_howto_type * +++elf64_sw_64_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, +++ bfd_reloc_code_real_type code) +++{ +++ const struct elf_reloc_map *i, *e; +++ i = e = elf64_sw_64_reloc_map; +++ e += sizeof (elf64_sw_64_reloc_map) / sizeof (struct elf_reloc_map); +++ for (; i != e; ++i) +++ { +++ if (i->bfd_reloc_val == code) +++ return &elf64_sw_64_howto_table[i->elf_reloc_val]; +++ } +++ return 0; +++} +++ +++static reloc_howto_type * +++elf64_sw_64_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED, +++ const char *r_name) +++{ +++ unsigned int i; +++ +++ for (i = 0; +++ i < (sizeof (elf64_sw_64_howto_table) +++ / sizeof (elf64_sw_64_howto_table[0])); +++ i++) +++ if (elf64_sw_64_howto_table[i].name != NULL +++ && strcasecmp (elf64_sw_64_howto_table[i].name, r_name) == 0) +++ return &elf64_sw_64_howto_table[i]; +++ +++ return NULL; +++} +++ +++/* Given an Sw_64 ELF reloc type, fill in an arelent structure. */ +++ +++static bfd_boolean +++elf64_sw_64_info_to_howto (bfd *abfd, arelent *cache_ptr, +++ Elf_Internal_Rela *dst) +++{ +++ unsigned r_type = ELF64_R_TYPE(dst->r_info); +++ +++ if (r_type >= R_SW_64_max) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("%pB: unsupported relocation type %#x"), +++ abfd, r_type); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ cache_ptr->howto = &elf64_sw_64_howto_table[r_type]; +++ return TRUE; +++} +++ +++/* These two relocations create a two-word entry in the got. */ +++#define sw_64_got_entry_size(r_type) \ +++ (r_type == R_SW_64_TLSGD || r_type == R_SW_64_TLSLDM ? 16 : 8) +++ +++/* This is PT_TLS segment p_vaddr. */ +++#define sw_64_get_dtprel_base(info) \ +++ (elf_hash_table (info)->tls_sec->vma) +++ +++/* Main program TLS (whose template starts at PT_TLS p_vaddr) +++ is assigned offset round(16, PT_TLS p_align). */ +++#define sw_64_get_tprel_base(info) \ +++ (elf_hash_table (info)->tls_sec->vma \ +++ - align_power ((bfd_vma) 16, \ +++ elf_hash_table (info)->tls_sec->alignment_power)) +++ +++/* Handle an Sw_64 specific section when reading an object file. This +++ is called when bfd_section_from_shdr finds a section with an unknown +++ type. */ +++ +++static bfd_boolean +++elf64_sw_64_section_from_shdr (bfd *abfd, +++ Elf_Internal_Shdr *hdr, +++ const char *name, +++ int shindex) +++{ +++ asection *newsect; +++ +++ /* There ought to be a place to keep ELF backend specific flags, but +++ at the moment there isn't one. We just keep track of the +++ sections by their name, instead. Fortunately, the ABI gives +++ suggested names for all the MIPS specific sections, so we will +++ probably get away with this. */ +++ switch (hdr->sh_type) +++ { +++ case SHT_SW_64_DEBUG: +++ if (strcmp (name, ".mdebug") != 0) +++ return FALSE; +++ break; +++ default: +++ return FALSE; +++ } +++ +++ if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex)) +++ return FALSE; +++ newsect = hdr->bfd_section; +++ +++ if (hdr->sh_type == SHT_SW_64_DEBUG) +++ { +++ if (!bfd_set_section_flags (newsect, +++ bfd_section_flags (newsect) | SEC_DEBUGGING)) +++ return FALSE; +++ } +++ +++ return TRUE; +++} +++ +++/* Convert Sw_64 specific section flags to bfd internal section flags. */ +++ +++static bfd_boolean +++elf64_sw_64_section_flags (const Elf_Internal_Shdr *hdr) +++{ +++ if (hdr->sh_flags & SHF_SW_64_GPREL) +++ hdr->bfd_section->flags |= SEC_SMALL_DATA; +++ +++ return TRUE; +++} +++ +++/* Set the correct type for an Sw_64 ELF section. We do this by the +++ section name, which is a hack, but ought to work. */ +++ +++static bfd_boolean +++elf64_sw_64_fake_sections (bfd *abfd, Elf_Internal_Shdr *hdr, asection *sec) +++{ +++ register const char *name; +++ +++ name = bfd_section_name (sec); +++ +++ if (strcmp (name, ".mdebug") == 0) +++ { +++ hdr->sh_type = SHT_SW_64_DEBUG; +++ /* In a shared object on Irix 5.3, the .mdebug section has an +++ entsize of 0. FIXME: Does this matter? */ +++ if ((abfd->flags & DYNAMIC) != 0 ) +++ hdr->sh_entsize = 0; +++ else +++ hdr->sh_entsize = 1; +++ } +++ else if ((sec->flags & SEC_SMALL_DATA) +++ || strcmp (name, ".sdata") == 0 +++ || strcmp (name, ".sbss") == 0 +++ || strcmp (name, ".lit4") == 0 +++ || strcmp (name, ".lit8") == 0) +++ hdr->sh_flags |= SHF_SW_64_GPREL; +++ +++ return TRUE; +++} +++ +++/* Hook called by the linker routine which adds symbols from an object +++ file. We use it to put .comm items in .sbss, and not .bss. */ +++ +++static bfd_boolean +++elf64_sw_64_add_symbol_hook (bfd *abfd, struct bfd_link_info *info, +++ Elf_Internal_Sym *sym, +++ const char **namep ATTRIBUTE_UNUSED, +++ flagword *flagsp ATTRIBUTE_UNUSED, +++ asection **secp, bfd_vma *valp) +++{ +++ if (sym->st_shndx == SHN_COMMON +++ && !bfd_link_relocatable (info) +++ && sym->st_size <= elf_gp_size (abfd)) +++ { +++ /* Common symbols less than or equal to -G nn bytes are +++ automatically put into .sbss. */ +++ +++ asection *scomm = bfd_get_section_by_name (abfd, ".scommon"); +++ +++ if (scomm == NULL) +++ { +++ scomm = bfd_make_section_with_flags (abfd, ".scommon", +++ (SEC_ALLOC +++ | SEC_IS_COMMON +++ | SEC_SMALL_DATA +++ | SEC_LINKER_CREATED)); +++ if (scomm == NULL) +++ return FALSE; +++ } +++ +++ *secp = scomm; +++ *valp = sym->st_size; +++ } +++ +++ return TRUE; +++} +++ +++/* Create the .got section. */ +++ +++static bfd_boolean +++elf64_sw_64_create_got_section (bfd *abfd, +++ struct bfd_link_info *info ATTRIBUTE_UNUSED) +++{ +++ flagword flags; +++ asection *s; +++ +++ if (! is_sw_64_elf (abfd)) +++ return FALSE; +++ +++ flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY +++ | SEC_LINKER_CREATED); +++ s = bfd_make_section_anyway_with_flags (abfd, ".got", flags); +++ if (s == NULL +++ || !bfd_set_section_alignment (s, 3)) +++ return FALSE; +++ +++ sw_64_elf_tdata (abfd)->got = s; +++ +++ /* Make sure the object's gotobj is set to itself so that we default +++ to every object with its own .got. We'll merge .gots later once +++ we've collected each object's info. */ +++ sw_64_elf_tdata (abfd)->gotobj = abfd; +++ +++ return TRUE; +++} +++ +++/* Create all the dynamic sections. */ +++ +++static bfd_boolean +++elf64_sw_64_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info) +++{ +++ asection *s; +++ flagword flags; +++ struct elf_link_hash_entry *h; +++ +++ if (! is_sw_64_elf (abfd)) +++ return FALSE; +++ +++ /* We need to create .plt, .rela.plt, .got, and .rela.got sections. */ +++ +++ flags = (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS | SEC_IN_MEMORY +++ | SEC_LINKER_CREATED +++ | (elf64_sw_64_use_secureplt ? SEC_READONLY : 0)); +++ s = bfd_make_section_anyway_with_flags (abfd, ".plt", flags); +++ elf_hash_table (info)->splt = s; +++ if (s == NULL || ! bfd_set_section_alignment (s, 4)) +++ return FALSE; +++ +++ /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the +++ .plt section. */ +++ h = _bfd_elf_define_linkage_sym (abfd, info, s, +++ "_PROCEDURE_LINKAGE_TABLE_"); +++ elf_hash_table (info)->hplt = h; +++ if (h == NULL) +++ return FALSE; +++ +++ flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY +++ | SEC_LINKER_CREATED | SEC_READONLY); +++ s = bfd_make_section_anyway_with_flags (abfd, ".rela.plt", flags); +++ elf_hash_table (info)->srelplt = s; +++ if (s == NULL || ! bfd_set_section_alignment (s, 3)) +++ return FALSE; +++ +++ if (elf64_sw_64_use_secureplt) +++ { +++ flags = SEC_ALLOC | SEC_LINKER_CREATED; +++ s = bfd_make_section_anyway_with_flags (abfd, ".got.plt", flags); +++ elf_hash_table (info)->sgotplt = s; +++ if (s == NULL || ! bfd_set_section_alignment (s, 3)) +++ return FALSE; +++ } +++ +++ /* We may or may not have created a .got section for this object, but +++ we definitely havn't done the rest of the work. */ +++ +++ if (sw_64_elf_tdata(abfd)->gotobj == NULL) +++ { +++ if (!elf64_sw_64_create_got_section (abfd, info)) +++ return FALSE; +++ } +++ +++ flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY +++ | SEC_LINKER_CREATED | SEC_READONLY); +++ s = bfd_make_section_anyway_with_flags (abfd, ".rela.got", flags); +++ elf_hash_table (info)->srelgot = s; +++ if (s == NULL +++ || !bfd_set_section_alignment (s, 3)) +++ return FALSE; +++ +++ /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the +++ dynobj's .got section. We don't do this in the linker script +++ because we don't want to define the symbol if we are not creating +++ a global offset table. */ +++ h = _bfd_elf_define_linkage_sym (abfd, info, sw_64_elf_tdata(abfd)->got, +++ "_GLOBAL_OFFSET_TABLE_"); +++ elf_hash_table (info)->hgot = h; +++ if (h == NULL) +++ return FALSE; +++ +++ return TRUE; +++} +++ +++/* Read ECOFF debugging information from a .mdebug section into a +++ ecoff_debug_info structure. */ +++ +++static bfd_boolean +++elf64_sw_64_read_ecoff_info (bfd *abfd, asection *section, +++ struct ecoff_debug_info *debug) +++{ +++ HDRR *symhdr; +++ const struct ecoff_debug_swap *swap; +++ char *ext_hdr = NULL; +++ +++ swap = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap; +++ memset (debug, 0, sizeof (*debug)); +++ +++ ext_hdr = (char *) bfd_malloc (swap->external_hdr_size); +++ if (ext_hdr == NULL && swap->external_hdr_size != 0) +++ goto error_return; +++ +++ if (! bfd_get_section_contents (abfd, section, ext_hdr, (file_ptr) 0, +++ swap->external_hdr_size)) +++ goto error_return; +++ +++ symhdr = &debug->symbolic_header; +++ (*swap->swap_hdr_in) (abfd, ext_hdr, symhdr); +++ +++ /* The symbolic header contains absolute file offsets and sizes to +++ read. */ +++#define READ(ptr, offset, count, size, type) \ +++ do \ +++ { \ +++ size_t amt; \ +++ debug->ptr = NULL; \ +++ if (symhdr->count == 0) \ +++ break; \ +++ if (_bfd_mul_overflow (size, symhdr->count, &amt)) \ +++ { \ +++ bfd_set_error (bfd_error_file_too_big); \ +++ goto error_return; \ +++ } \ +++ if (bfd_seek (abfd, symhdr->offset, SEEK_SET) != 0) \ +++ goto error_return; \ +++ debug->ptr = (type) _bfd_malloc_and_read (abfd, amt, amt); \ +++ if (debug->ptr == NULL) \ +++ goto error_return; \ +++ } while (0) +++ +++ READ (line, cbLineOffset, cbLine, sizeof (unsigned char), unsigned char *); +++ READ (external_dnr, cbDnOffset, idnMax, swap->external_dnr_size, void *); +++ READ (external_pdr, cbPdOffset, ipdMax, swap->external_pdr_size, void *); +++ READ (external_sym, cbSymOffset, isymMax, swap->external_sym_size, void *); +++ READ (external_opt, cbOptOffset, ioptMax, swap->external_opt_size, void *); +++ READ (external_aux, cbAuxOffset, iauxMax, sizeof (union aux_ext), +++ union aux_ext *); +++ READ (ss, cbSsOffset, issMax, sizeof (char), char *); +++ READ (ssext, cbSsExtOffset, issExtMax, sizeof (char), char *); +++ READ (external_fdr, cbFdOffset, ifdMax, swap->external_fdr_size, void *); +++ READ (external_rfd, cbRfdOffset, crfd, swap->external_rfd_size, void *); +++ READ (external_ext, cbExtOffset, iextMax, swap->external_ext_size, void *); +++#undef READ +++ +++ debug->fdr = NULL; +++ +++ return TRUE; +++ +++ error_return: +++ free (ext_hdr); +++ free (debug->line); +++ free (debug->external_dnr); +++ free (debug->external_pdr); +++ free (debug->external_sym); +++ free (debug->external_opt); +++ free (debug->external_aux); +++ free (debug->ss); +++ free (debug->ssext); +++ free (debug->external_fdr); +++ free (debug->external_rfd); +++ free (debug->external_ext); +++ return FALSE; +++} +++ +++/* Sw_64 ELF local labels start with '$'. */ +++ +++static bfd_boolean +++elf64_sw_64_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED, const char *name) +++{ +++ return name[0] == '$'; +++} +++ +++static bfd_boolean +++elf64_sw_64_find_nearest_line (bfd *abfd, asymbol **symbols, +++ asection *section, bfd_vma offset, +++ const char **filename_ptr, +++ const char **functionname_ptr, +++ unsigned int *line_ptr, +++ unsigned int *discriminator_ptr) +++{ +++ asection *msec; +++ +++ if (_bfd_dwarf2_find_nearest_line (abfd, symbols, NULL, section, offset, +++ filename_ptr, functionname_ptr, +++ line_ptr, discriminator_ptr, +++ dwarf_debug_sections, +++ &elf_tdata (abfd)->dwarf2_find_line_info) +++ == 1) +++ return TRUE; +++ +++ msec = bfd_get_section_by_name (abfd, ".mdebug"); +++ if (msec != NULL) +++ { +++ flagword origflags; +++ struct sw_64_elf_find_line *fi; +++ const struct ecoff_debug_swap * const swap = +++ get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap; +++ +++ /* If we are called during a link, sw_64_elf_final_link may have +++ cleared the SEC_HAS_CONTENTS field. We force it back on here +++ if appropriate (which it normally will be). */ +++ origflags = msec->flags; +++ if (elf_section_data (msec)->this_hdr.sh_type != SHT_NOBITS) +++ msec->flags |= SEC_HAS_CONTENTS; +++ +++ fi = sw_64_elf_tdata (abfd)->find_line_info; +++ if (fi == NULL) +++ { +++ bfd_size_type external_fdr_size; +++ char *fraw_src; +++ char *fraw_end; +++ struct fdr *fdr_ptr; +++ bfd_size_type amt = sizeof (struct sw_64_elf_find_line); +++ +++ fi = (struct sw_64_elf_find_line *) bfd_zalloc (abfd, amt); +++ if (fi == NULL) +++ { +++ msec->flags = origflags; +++ return FALSE; +++ } +++ +++ if (!elf64_sw_64_read_ecoff_info (abfd, msec, &fi->d)) +++ { +++ msec->flags = origflags; +++ return FALSE; +++ } +++ +++ /* Swap in the FDR information. */ +++ amt = fi->d.symbolic_header.ifdMax * sizeof (struct fdr); +++ fi->d.fdr = (struct fdr *) bfd_alloc (abfd, amt); +++ if (fi->d.fdr == NULL) +++ { +++ msec->flags = origflags; +++ return FALSE; +++ } +++ external_fdr_size = swap->external_fdr_size; +++ fdr_ptr = fi->d.fdr; +++ fraw_src = (char *) fi->d.external_fdr; +++ fraw_end = (fraw_src +++ + fi->d.symbolic_header.ifdMax * external_fdr_size); +++ for (; fraw_src < fraw_end; fraw_src += external_fdr_size, fdr_ptr++) +++ (*swap->swap_fdr_in) (abfd, fraw_src, fdr_ptr); +++ +++ sw_64_elf_tdata (abfd)->find_line_info = fi; +++ +++ /* Note that we don't bother to ever free this information. +++ find_nearest_line is either called all the time, as in +++ objdump -l, so the information should be saved, or it is +++ rarely called, as in ld error messages, so the memory +++ wasted is unimportant. Still, it would probably be a +++ good idea for free_cached_info to throw it away. */ +++ } +++ +++ if (_bfd_ecoff_locate_line (abfd, section, offset, &fi->d, swap, +++ &fi->i, filename_ptr, functionname_ptr, +++ line_ptr)) +++ { +++ msec->flags = origflags; +++ return TRUE; +++ } +++ +++ msec->flags = origflags; +++ } +++ +++ /* Fall back on the generic ELF find_nearest_line routine. */ +++ +++ return _bfd_elf_find_nearest_line (abfd, symbols, section, offset, +++ filename_ptr, functionname_ptr, +++ line_ptr, discriminator_ptr); +++} +++ +++/* Structure used to pass information to sw_64_elf_output_extsym. */ +++ +++struct extsym_info +++{ +++ bfd *abfd; +++ struct bfd_link_info *info; +++ struct ecoff_debug_info *debug; +++ const struct ecoff_debug_swap *swap; +++ bfd_boolean failed; +++}; +++ +++static bfd_boolean +++elf64_sw_64_output_extsym (struct sw_64_elf_link_hash_entry *h, void * data) +++{ +++ struct extsym_info *einfo = (struct extsym_info *) data; +++ bfd_boolean strip; +++ asection *sec, *output_section; +++ +++ if (h->root.indx == -2) +++ strip = FALSE; +++ else if ((h->root.def_dynamic +++ || h->root.ref_dynamic +++ || h->root.root.type == bfd_link_hash_new) +++ && !h->root.def_regular +++ && !h->root.ref_regular) +++ strip = TRUE; +++ else if (einfo->info->strip == strip_all +++ || (einfo->info->strip == strip_some +++ && bfd_hash_lookup (einfo->info->keep_hash, +++ h->root.root.root.string, +++ FALSE, FALSE) == NULL)) +++ strip = TRUE; +++ else +++ strip = FALSE; +++ +++ if (strip) +++ return TRUE; +++ +++ if (h->esym.ifd == -2) +++ { +++ h->esym.jmptbl = 0; +++ h->esym.cobol_main = 0; +++ h->esym.weakext = 0; +++ h->esym.reserved = 0; +++ h->esym.ifd = ifdNil; +++ h->esym.asym.value = 0; +++ h->esym.asym.st = stGlobal; +++ +++ if (h->root.root.type != bfd_link_hash_defined +++ && h->root.root.type != bfd_link_hash_defweak) +++ h->esym.asym.sc = scAbs; +++ else +++ { +++ const char *name; +++ +++ sec = h->root.root.u.def.section; +++ output_section = sec->output_section; +++ +++ /* When making a shared library and symbol h is the one from +++ the another shared library, OUTPUT_SECTION may be null. */ +++ if (output_section == NULL) +++ h->esym.asym.sc = scUndefined; +++ else +++ { +++ name = bfd_section_name (output_section); +++ +++ if (strcmp (name, ".text") == 0) +++ h->esym.asym.sc = scText; +++ else if (strcmp (name, ".data") == 0) +++ h->esym.asym.sc = scData; +++ else if (strcmp (name, ".sdata") == 0) +++ h->esym.asym.sc = scSData; +++ else if (strcmp (name, ".rodata") == 0 +++ || strcmp (name, ".rdata") == 0) +++ h->esym.asym.sc = scRData; +++ else if (strcmp (name, ".bss") == 0) +++ h->esym.asym.sc = scBss; +++ else if (strcmp (name, ".sbss") == 0) +++ h->esym.asym.sc = scSBss; +++ else if (strcmp (name, ".init") == 0) +++ h->esym.asym.sc = scInit; +++ else if (strcmp (name, ".fini") == 0) +++ h->esym.asym.sc = scFini; +++ else +++ h->esym.asym.sc = scAbs; +++ } +++ } +++ +++ h->esym.asym.reserved = 0; +++ h->esym.asym.index = indexNil; +++ } +++ +++ if (h->root.root.type == bfd_link_hash_common) +++ h->esym.asym.value = h->root.root.u.c.size; +++ else if (h->root.root.type == bfd_link_hash_defined +++ || h->root.root.type == bfd_link_hash_defweak) +++ { +++ if (h->esym.asym.sc == scCommon) +++ h->esym.asym.sc = scBss; +++ else if (h->esym.asym.sc == scSCommon) +++ h->esym.asym.sc = scSBss; +++ +++ sec = h->root.root.u.def.section; +++ output_section = sec->output_section; +++ if (output_section != NULL) +++ h->esym.asym.value = (h->root.root.u.def.value +++ + sec->output_offset +++ + output_section->vma); +++ else +++ h->esym.asym.value = 0; +++ } +++ +++ if (! bfd_ecoff_debug_one_external (einfo->abfd, einfo->debug, einfo->swap, +++ h->root.root.root.string, +++ &h->esym)) +++ { +++ einfo->failed = TRUE; +++ return FALSE; +++ } +++ +++ return TRUE; +++} +++ +++/* Search for and possibly create a got entry. */ +++ +++static struct sw_64_elf_got_entry * +++get_got_entry (bfd *abfd, struct sw_64_elf_link_hash_entry *h, +++ unsigned long r_type, unsigned long r_symndx, +++ bfd_vma r_addend) +++{ +++ struct sw_64_elf_got_entry *gotent; +++ struct sw_64_elf_got_entry **slot; +++ +++ if (h) +++ slot = &h->got_entries; +++ else +++ { +++ /* This is a local .got entry -- record for merge. */ +++ +++ struct sw_64_elf_got_entry **local_got_entries; +++ +++ local_got_entries = sw_64_elf_tdata(abfd)->local_got_entries; +++ if (!local_got_entries) +++ { +++ bfd_size_type size; +++ Elf_Internal_Shdr *symtab_hdr; +++ +++ symtab_hdr = &elf_tdata(abfd)->symtab_hdr; +++ size = symtab_hdr->sh_info; +++ size *= sizeof (struct sw_64_elf_got_entry *); +++ +++ local_got_entries +++ = (struct sw_64_elf_got_entry **) bfd_zalloc (abfd, size); +++ if (!local_got_entries) +++ return NULL; +++ +++ sw_64_elf_tdata (abfd)->local_got_entries = local_got_entries; +++ } +++ +++ slot = &local_got_entries[r_symndx]; +++ } +++ +++ for (gotent = *slot; gotent ; gotent = gotent->next) +++ if (gotent->gotobj == abfd +++ && gotent->reloc_type == r_type +++ && gotent->addend == r_addend) +++ break; +++ +++ if (!gotent) +++ { +++ int entry_size; +++ size_t amt; +++ +++ amt = sizeof (struct sw_64_elf_got_entry); +++ gotent = (struct sw_64_elf_got_entry *) bfd_alloc (abfd, amt); +++ if (!gotent) +++ return NULL; +++ +++ gotent->gotobj = abfd; +++ gotent->addend = r_addend; +++ gotent->got_offset = -1; +++ gotent->plt_offset = -1; +++ gotent->use_count = 1; +++ gotent->reloc_type = r_type; +++ gotent->reloc_done = 0; +++ gotent->reloc_xlated = 0; +++ +++ gotent->next = *slot; +++ *slot = gotent; +++ +++ entry_size = sw_64_got_entry_size (r_type); +++ sw_64_elf_tdata (abfd)->total_got_size += entry_size; +++ if (!h) +++ sw_64_elf_tdata(abfd)->local_got_size += entry_size; +++ } +++ else +++ gotent->use_count += 1; +++ +++ return gotent; +++} +++ +++static bfd_boolean +++elf64_sw_64_want_plt (struct sw_64_elf_link_hash_entry *ah) +++{ +++ return ((ah->root.type == STT_FUNC +++ || ah->root.root.type == bfd_link_hash_undefweak +++ || ah->root.root.type == bfd_link_hash_undefined) +++ && (ah->flags & SW_64_ELF_LINK_HASH_LU_PLT) != 0 +++ && (ah->flags & ~SW_64_ELF_LINK_HASH_LU_PLT) == 0); +++} +++ +++/* Whether to sort relocs output by ld -r or ld --emit-relocs, by r_offset. +++ Don't do so for code sections. We want to keep ordering of LITERAL/LITUSE +++ as is. On the other hand, elf-eh-frame.c processing requires .eh_frame +++ relocs to be sorted. */ +++ +++static bfd_boolean +++elf64_sw_64_sort_relocs_p (asection *sec) +++{ +++ return (sec->flags & SEC_CODE) == 0; +++} +++ +++ +++/* Handle dynamic relocations when doing an Sw_64 ELF link. */ +++ +++static bfd_boolean +++elf64_sw_64_check_relocs (bfd *abfd, struct bfd_link_info *info, +++ asection *sec, const Elf_Internal_Rela *relocs) +++{ +++ bfd *dynobj; +++ asection *sreloc; +++ Elf_Internal_Shdr *symtab_hdr; +++ struct sw_64_elf_link_hash_entry **sym_hashes; +++ const Elf_Internal_Rela *rel, *relend; +++ +++ if (bfd_link_relocatable (info)) +++ return TRUE; +++ +++ BFD_ASSERT (is_sw_64_elf (abfd)); +++ +++ dynobj = elf_hash_table (info)->dynobj; +++ if (dynobj == NULL) +++ elf_hash_table (info)->dynobj = dynobj = abfd; +++ +++ sreloc = NULL; +++ symtab_hdr = &elf_symtab_hdr (abfd); +++ sym_hashes = sw_64_elf_sym_hashes (abfd); +++ +++ relend = relocs + sec->reloc_count; +++ for (rel = relocs; rel < relend; ++rel) +++ { +++ enum { +++ NEED_GOT = 1, +++ NEED_GOT_ENTRY = 2, +++ NEED_DYNREL = 4 +++ }; +++ +++ unsigned long r_symndx, r_type; +++ struct sw_64_elf_link_hash_entry *h; +++ unsigned int gotent_flags; +++ bfd_boolean maybe_dynamic; +++ unsigned int need; +++ bfd_vma addend; +++ +++ r_symndx = ELF64_R_SYM (rel->r_info); +++ if (r_symndx < symtab_hdr->sh_info) +++ h = NULL; +++ else +++ { +++ h = sym_hashes[r_symndx - symtab_hdr->sh_info]; +++ +++ while (h->root.root.type == bfd_link_hash_indirect +++ || h->root.root.type == bfd_link_hash_warning) +++ h = (struct sw_64_elf_link_hash_entry *)h->root.root.u.i.link; +++ +++ /* PR15323, ref flags aren't set for references in the same +++ object. */ +++ h->root.ref_regular = 1; +++ } +++ +++ /* We can only get preliminary data on whether a symbol is +++ locally or externally defined, as not all of the input files +++ have yet been processed. Do something with what we know, as +++ this may help reduce memory usage and processing time later. */ +++ maybe_dynamic = FALSE; +++ if (h && ((bfd_link_pic (info) +++ && (!info->symbolic +++ || info->unresolved_syms_in_shared_libs == RM_IGNORE)) +++ || !h->root.def_regular +++ || h->root.root.type == bfd_link_hash_defweak)) +++ maybe_dynamic = TRUE; +++ +++ need = 0; +++ gotent_flags = 0; +++ r_type = ELF64_R_TYPE (rel->r_info); +++ addend = rel->r_addend; +++ +++ switch (r_type) +++ { +++ case R_SW_64_LITERAL: +++ need = NEED_GOT | NEED_GOT_ENTRY; +++ +++ /* Remember how this literal is used from its LITUSEs. +++ This will be important when it comes to decide if we can +++ create a .plt entry for a function symbol. */ +++ while (++rel < relend && ELF64_R_TYPE (rel->r_info) == R_SW_64_LITUSE) +++ if (rel->r_addend >= 1 && rel->r_addend <= 6) +++ gotent_flags |= 1 << rel->r_addend; +++ --rel; +++ +++ /* No LITUSEs -- presumably the address is used somehow. */ +++ if (gotent_flags == 0) +++ gotent_flags = SW_64_ELF_LINK_HASH_LU_ADDR; +++ break; +++ +++ case R_SW_64_GPDISP: +++ case R_SW_64_GPREL16: +++ case R_SW_64_GPREL32: +++ case R_SW_64_GPRELHIGH: +++ case R_SW_64_GPRELLOW: +++ case R_SW_64_BRSGP: +++ need = NEED_GOT; +++ break; +++ +++ case R_SW_64_REFLONG: +++ case R_SW_64_REFQUAD: +++ if (bfd_link_pic (info) || maybe_dynamic) +++ need = NEED_DYNREL; +++ break; +++ +++ case R_SW_64_TLSLDM: +++ /* The symbol for a TLSLDM reloc is ignored. Collapse the +++ reloc to the STN_UNDEF (0) symbol so that they all match. */ +++ r_symndx = STN_UNDEF; +++ h = 0; +++ maybe_dynamic = FALSE; +++ /* FALLTHRU */ +++ +++ case R_SW_64_TLSGD: +++ case R_SW_64_GOTDTPREL: +++ need = NEED_GOT | NEED_GOT_ENTRY; +++ break; +++ +++ case R_SW_64_GOTTPREL: +++ need = NEED_GOT | NEED_GOT_ENTRY; +++ gotent_flags = SW_64_ELF_LINK_HASH_TLS_IE; +++ if (bfd_link_pic (info)) +++ info->flags |= DF_STATIC_TLS; +++ break; +++ +++ case R_SW_64_TPREL64: +++ if (bfd_link_dll (info)) +++ { +++ info->flags |= DF_STATIC_TLS; +++ need = NEED_DYNREL; +++ } +++ else if (maybe_dynamic) +++ need = NEED_DYNREL; +++ break; +++ } +++ +++ if (need & NEED_GOT) +++ { +++ if (sw_64_elf_tdata(abfd)->gotobj == NULL) +++ { +++ if (!elf64_sw_64_create_got_section (abfd, info)) +++ return FALSE; +++ } +++ } +++ +++ if (need & NEED_GOT_ENTRY) +++ { +++ struct sw_64_elf_got_entry *gotent; +++ +++ gotent = get_got_entry (abfd, h, r_type, r_symndx, addend); +++ if (!gotent) +++ return FALSE; +++ +++ if (gotent_flags) +++ { +++ gotent->flags |= gotent_flags; +++ if (h) +++ { +++ gotent_flags |= h->flags; +++ h->flags = gotent_flags; +++ +++ /* Make a guess as to whether a .plt entry is needed. */ +++ /* ??? It appears that we won't make it into +++ adjust_dynamic_symbol for symbols that remain +++ totally undefined. Copying this check here means +++ we can create a plt entry for them too. */ +++ h->root.needs_plt +++ = (maybe_dynamic && elf64_sw_64_want_plt (h)); +++ } +++ } +++ } +++ +++ if (need & NEED_DYNREL) +++ { +++ /* We need to create the section here now whether we eventually +++ use it or not so that it gets mapped to an output section by +++ the linker. If not used, we'll kill it in size_dynamic_sections. */ +++ if (sreloc == NULL) +++ { +++ sreloc = _bfd_elf_make_dynamic_reloc_section +++ (sec, dynobj, 3, abfd, /*rela?*/ TRUE); +++ +++ if (sreloc == NULL) +++ return FALSE; +++ } +++ +++ if (h) +++ { +++ /* Since we havn't seen all of the input symbols yet, we +++ don't know whether we'll actually need a dynamic relocation +++ entry for this reloc. So make a record of it. Once we +++ find out if this thing needs dynamic relocation we'll +++ expand the relocation sections by the appropriate amount. */ +++ +++ struct sw_64_elf_reloc_entry *rent; +++ +++ for (rent = h->reloc_entries; rent; rent = rent->next) +++ if (rent->rtype == r_type && rent->srel == sreloc) +++ break; +++ +++ if (!rent) +++ { +++ size_t amt = sizeof (struct sw_64_elf_reloc_entry); +++ rent = (struct sw_64_elf_reloc_entry *) bfd_alloc (abfd, amt); +++ if (!rent) +++ return FALSE; +++ +++ rent->srel = sreloc; +++ rent->sec = sec; +++ rent->rtype = r_type; +++ rent->count = 1; +++ +++ rent->next = h->reloc_entries; +++ h->reloc_entries = rent; +++ } +++ else +++ rent->count++; +++ } +++ else if (bfd_link_pic (info)) +++ { +++ /* If this is a shared library, and the section is to be +++ loaded into memory, we need a RELATIVE reloc. */ +++ sreloc->size += sizeof (Elf64_External_Rela); +++ if (sec->flags & SEC_READONLY) +++ { +++ info->flags |= DF_TEXTREL; +++ info->callbacks->minfo +++ (_("%pB: dynamic relocation against `%pT' in " +++ "read-only section `%pA'\n"), +++ sec->owner, h->root.root.root.string, sec); +++ } +++ } +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* Return the section that should be marked against GC for a given +++ relocation. */ +++ +++static asection * +++elf64_sw_64_gc_mark_hook (asection *sec, struct bfd_link_info *info, +++ Elf_Internal_Rela *rel, +++ struct elf_link_hash_entry *h, Elf_Internal_Sym *sym) +++{ +++ /* These relocations don't really reference a symbol. Instead we store +++ extra data in their addend slot. Ignore the symbol. */ +++ switch (ELF64_R_TYPE (rel->r_info)) +++ { +++ case R_SW_64_LITUSE: +++ case R_SW_64_GPDISP: +++ case R_SW_64_HINT: +++ return NULL; +++ } +++ +++ return _bfd_elf_gc_mark_hook (sec, info, rel, h, sym); +++} +++ +++/* Adjust a symbol defined by a dynamic object and referenced by a +++ regular object. The current definition is in some section of the +++ dynamic object, but we're not including those sections. We have to +++ change the definition to something the rest of the link can +++ understand. */ +++ +++static bfd_boolean +++elf64_sw_64_adjust_dynamic_symbol (struct bfd_link_info *info, +++ struct elf_link_hash_entry *h) +++{ +++ bfd *dynobj; +++ asection *s; +++ struct sw_64_elf_link_hash_entry *ah; +++ +++ dynobj = elf_hash_table(info)->dynobj; +++ ah = (struct sw_64_elf_link_hash_entry *)h; +++ +++ /* Now that we've seen all of the input symbols, finalize our decision +++ about whether this symbol should get a .plt entry. Irritatingly, it +++ is common for folk to leave undefined symbols in shared libraries, +++ and they still expect lazy binding; accept undefined symbols in lieu +++ of STT_FUNC. */ +++ if (sw_64_elf_dynamic_symbol_p (h, info) && elf64_sw_64_want_plt (ah)) +++ { +++ h->needs_plt = TRUE; +++ +++ s = elf_hash_table(info)->splt; +++ if (!s && !elf64_sw_64_create_dynamic_sections (dynobj, info)) +++ return FALSE; +++ +++ /* We need one plt entry per got subsection. Delay allocation of +++ the actual plt entries until size_plt_section, called from +++ size_dynamic_sections or during relaxation. */ +++ +++ return TRUE; +++ } +++ else +++ h->needs_plt = FALSE; +++ +++ /* If this is a weak symbol, and there is a real definition, the +++ processor independent code will have arranged for us to see the +++ real definition first, and we can just use the same value. */ +++ if (h->is_weakalias) +++ { +++ struct elf_link_hash_entry *def = weakdef (h); +++ BFD_ASSERT (def->root.type == bfd_link_hash_defined); +++ h->root.u.def.section = def->root.u.def.section; +++ h->root.u.def.value = def->root.u.def.value; +++ return TRUE; +++ } +++ +++ /* This is a reference to a symbol defined by a dynamic object which +++ is not a function. The Sw_64, since it uses .got entries for all +++ symbols even in regular objects, does not need the hackery of a +++ .dynbss section and COPY dynamic relocations. */ +++ +++ return TRUE; +++} +++ +++/* Record STO_SW_64_NOPV and STO_SW_64_STD_GPLOAD. */ +++ +++static void +++elf64_sw_64_merge_symbol_attribute (struct elf_link_hash_entry *h, +++ const Elf_Internal_Sym *isym, +++ bfd_boolean definition, +++ bfd_boolean dynamic) +++{ +++ if (!dynamic && definition) +++ h->other = ((h->other & ELF_ST_VISIBILITY (-1)) +++ | (isym->st_other & ~ELF_ST_VISIBILITY (-1))); +++} +++ +++/* Symbol versioning can create new symbols, and make our old symbols +++ indirect to the new ones. Consolidate the got and reloc information +++ in these situations. */ +++ +++static void +++elf64_sw_64_copy_indirect_symbol (struct bfd_link_info *info, +++ struct elf_link_hash_entry *dir, +++ struct elf_link_hash_entry *ind) +++{ +++ struct sw_64_elf_link_hash_entry *hi +++ = (struct sw_64_elf_link_hash_entry *) ind; +++ struct sw_64_elf_link_hash_entry *hs +++ = (struct sw_64_elf_link_hash_entry *) dir; +++ +++ /* Do the merging in the superclass. */ +++ _bfd_elf_link_hash_copy_indirect(info, dir, ind); +++ +++ /* Merge the flags. Whee. */ +++ hs->flags |= hi->flags; +++ +++ /* ??? It's unclear to me what's really supposed to happen when +++ "merging" defweak and defined symbols, given that we don't +++ actually throw away the defweak. This more-or-less copies +++ the logic related to got and plt entries in the superclass. */ +++ if (ind->root.type != bfd_link_hash_indirect) +++ return; +++ +++ /* Merge the .got entries. Cannibalize the old symbol's list in +++ doing so, since we don't need it anymore. */ +++ +++ if (hs->got_entries == NULL) +++ hs->got_entries = hi->got_entries; +++ else +++ { +++ struct sw_64_elf_got_entry *gi, *gs, *gin, *gsh; +++ +++ gsh = hs->got_entries; +++ for (gi = hi->got_entries; gi ; gi = gin) +++ { +++ gin = gi->next; +++ for (gs = gsh; gs ; gs = gs->next) +++ if (gi->gotobj == gs->gotobj +++ && gi->reloc_type == gs->reloc_type +++ && gi->addend == gs->addend) +++ { +++ gs->use_count += gi->use_count; +++ goto got_found; +++ } +++ gi->next = hs->got_entries; +++ hs->got_entries = gi; +++ got_found:; +++ } +++ } +++ hi->got_entries = NULL; +++ +++ /* And similar for the reloc entries. */ +++ +++ if (hs->reloc_entries == NULL) +++ hs->reloc_entries = hi->reloc_entries; +++ else +++ { +++ struct sw_64_elf_reloc_entry *ri, *rs, *rin, *rsh; +++ +++ rsh = hs->reloc_entries; +++ for (ri = hi->reloc_entries; ri ; ri = rin) +++ { +++ rin = ri->next; +++ for (rs = rsh; rs ; rs = rs->next) +++ if (ri->rtype == rs->rtype && ri->srel == rs->srel) +++ { +++ rs->count += ri->count; +++ goto found_reloc; +++ } +++ ri->next = hs->reloc_entries; +++ hs->reloc_entries = ri; +++ found_reloc:; +++ } +++ } +++ hi->reloc_entries = NULL; +++} +++ +++/* Is it possible to merge two object file's .got tables? */ +++ +++static bfd_boolean +++elf64_sw_64_can_merge_gots (bfd *a, bfd *b) +++{ +++ int total = sw_64_elf_tdata (a)->total_got_size; +++ bfd *bsub; +++ +++ /* Trivial quick fallout test. */ +++ if (total + sw_64_elf_tdata (b)->total_got_size <= MAX_GOT_SIZE) +++ return TRUE; +++ +++ /* By their nature, local .got entries cannot be merged. */ +++ if ((total += sw_64_elf_tdata (b)->local_got_size) > MAX_GOT_SIZE) +++ return FALSE; +++ +++ /* Failing the common trivial comparison, we must effectively +++ perform the merge. Not actually performing the merge means that +++ we don't have to store undo information in case we fail. */ +++ for (bsub = b; bsub ; bsub = sw_64_elf_tdata (bsub)->in_got_link_next) +++ { +++ struct sw_64_elf_link_hash_entry **hashes = sw_64_elf_sym_hashes (bsub); +++ Elf_Internal_Shdr *symtab_hdr = &elf_tdata (bsub)->symtab_hdr; +++ int i, n; +++ +++ n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info; +++ for (i = 0; i < n; ++i) +++ { +++ struct sw_64_elf_got_entry *ae, *be; +++ struct sw_64_elf_link_hash_entry *h; +++ +++ h = hashes[i]; +++ while (h->root.root.type == bfd_link_hash_indirect +++ || h->root.root.type == bfd_link_hash_warning) +++ h = (struct sw_64_elf_link_hash_entry *)h->root.root.u.i.link; +++ +++ for (be = h->got_entries; be ; be = be->next) +++ { +++ if (be->use_count == 0) +++ continue; +++ if (be->gotobj != b) +++ continue; +++ +++ for (ae = h->got_entries; ae ; ae = ae->next) +++ if (ae->gotobj == a +++ && ae->reloc_type == be->reloc_type +++ && ae->addend == be->addend) +++ goto global_found; +++ +++ total += sw_64_got_entry_size (be->reloc_type); +++ if (total > MAX_GOT_SIZE) +++ return FALSE; +++ global_found:; +++ } +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* Actually merge two .got tables. */ +++ +++static void +++elf64_sw_64_merge_gots (bfd *a, bfd *b) +++{ +++ int total = sw_64_elf_tdata (a)->total_got_size; +++ bfd *bsub; +++ +++ /* Remember local expansion. */ +++ { +++ int e = sw_64_elf_tdata (b)->local_got_size; +++ total += e; +++ sw_64_elf_tdata (a)->local_got_size += e; +++ } +++ +++ for (bsub = b; bsub ; bsub = sw_64_elf_tdata (bsub)->in_got_link_next) +++ { +++ struct sw_64_elf_got_entry **local_got_entries; +++ struct sw_64_elf_link_hash_entry **hashes; +++ Elf_Internal_Shdr *symtab_hdr; +++ int i, n; +++ +++ /* Let the local .got entries know they are part of a new subsegment. */ +++ local_got_entries = sw_64_elf_tdata (bsub)->local_got_entries; +++ if (local_got_entries) +++ { +++ n = elf_tdata (bsub)->symtab_hdr.sh_info; +++ for (i = 0; i < n; ++i) +++ { +++ struct sw_64_elf_got_entry *ent; +++ for (ent = local_got_entries[i]; ent; ent = ent->next) +++ ent->gotobj = a; +++ } +++ } +++ +++ /* Merge the global .got entries. */ +++ hashes = sw_64_elf_sym_hashes (bsub); +++ symtab_hdr = &elf_tdata (bsub)->symtab_hdr; +++ +++ n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info; +++ for (i = 0; i < n; ++i) +++ { +++ struct sw_64_elf_got_entry *ae, *be, **pbe, **start; +++ struct sw_64_elf_link_hash_entry *h; +++ +++ h = hashes[i]; +++ while (h->root.root.type == bfd_link_hash_indirect +++ || h->root.root.type == bfd_link_hash_warning) +++ h = (struct sw_64_elf_link_hash_entry *)h->root.root.u.i.link; +++ +++ pbe = start = &h->got_entries; +++ while ((be = *pbe) != NULL) +++ { +++ if (be->use_count == 0) +++ { +++ *pbe = be->next; +++ memset (be, 0xa5, sizeof (*be)); +++ goto kill; +++ } +++ if (be->gotobj != b) +++ goto next; +++ +++ for (ae = *start; ae ; ae = ae->next) +++ if (ae->gotobj == a +++ && ae->reloc_type == be->reloc_type +++ && ae->addend == be->addend) +++ { +++ ae->flags |= be->flags; +++ ae->use_count += be->use_count; +++ *pbe = be->next; +++ memset (be, 0xa5, sizeof (*be)); +++ goto kill; +++ } +++ be->gotobj = a; +++ total += sw_64_got_entry_size (be->reloc_type); +++ +++ next:; +++ pbe = &be->next; +++ kill:; +++ } +++ } +++ +++ sw_64_elf_tdata (bsub)->gotobj = a; +++ } +++ sw_64_elf_tdata (a)->total_got_size = total; +++ +++ /* Merge the two in_got chains. */ +++ { +++ bfd *next; +++ +++ bsub = a; +++ while ((next = sw_64_elf_tdata (bsub)->in_got_link_next) != NULL) +++ bsub = next; +++ +++ sw_64_elf_tdata (bsub)->in_got_link_next = b; +++ } +++} +++ +++/* Calculate the offsets for the got entries. */ +++ +++static bfd_boolean +++elf64_sw_64_calc_got_offsets_for_symbol (struct sw_64_elf_link_hash_entry *h, +++ void * arg ATTRIBUTE_UNUSED) +++{ +++ struct sw_64_elf_got_entry *gotent; +++ +++ for (gotent = h->got_entries; gotent; gotent = gotent->next) +++ if (gotent->use_count > 0) +++ { +++ struct sw_64_elf_obj_tdata *td; +++ bfd_size_type *plge; +++ +++ td = sw_64_elf_tdata (gotent->gotobj); +++ plge = &td->got->size; +++ gotent->got_offset = *plge; +++ *plge += sw_64_got_entry_size (gotent->reloc_type); +++ } +++ +++ return TRUE; +++} +++ +++static void +++elf64_sw_64_calc_got_offsets (struct bfd_link_info *info) +++{ +++ bfd *i, *got_list; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return; +++ got_list = htab->got_list; +++ +++ /* First, zero out the .got sizes, as we may be recalculating the +++ .got after optimizing it. */ +++ for (i = got_list; i ; i = sw_64_elf_tdata(i)->got_link_next) +++ sw_64_elf_tdata(i)->got->size = 0; +++ +++ /* Next, fill in the offsets for all the global entries. */ +++ sw_64_elf_link_hash_traverse (htab, +++ elf64_sw_64_calc_got_offsets_for_symbol, +++ NULL); +++ +++ /* Finally, fill in the offsets for the local entries. */ +++ for (i = got_list; i ; i = sw_64_elf_tdata(i)->got_link_next) +++ { +++ bfd_size_type got_offset = sw_64_elf_tdata(i)->got->size; +++ bfd *j; +++ +++ for (j = i; j ; j = sw_64_elf_tdata(j)->in_got_link_next) +++ { +++ struct sw_64_elf_got_entry **local_got_entries, *gotent; +++ int k, n; +++ +++ local_got_entries = sw_64_elf_tdata(j)->local_got_entries; +++ if (!local_got_entries) +++ continue; +++ +++ for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k) +++ for (gotent = local_got_entries[k]; gotent; gotent = gotent->next) +++ if (gotent->use_count > 0) +++ { +++ gotent->got_offset = got_offset; +++ got_offset += sw_64_got_entry_size (gotent->reloc_type); +++ } +++ } +++ +++ sw_64_elf_tdata(i)->got->size = got_offset; +++ } +++} +++ +++/* Constructs the gots. */ +++ +++static bfd_boolean +++elf64_sw_64_size_got_sections (struct bfd_link_info *info, +++ bfd_boolean may_merge) +++{ +++ bfd *i, *got_list, *cur_got_obj = NULL; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return FALSE; +++ got_list = htab->got_list; +++ +++ /* On the first time through, pretend we have an existing got list +++ consisting of all of the input files. */ +++ if (got_list == NULL) +++ { +++ for (i = info->input_bfds; i ; i = i->link.next) +++ { +++ bfd *this_got; +++ +++ if (! is_sw_64_elf (i)) +++ continue; +++ +++ this_got = sw_64_elf_tdata (i)->gotobj; +++ if (this_got == NULL) +++ continue; +++ +++ /* We are assuming no merging has yet occurred. */ +++ BFD_ASSERT (this_got == i); +++ +++ if (sw_64_elf_tdata (this_got)->total_got_size > MAX_GOT_SIZE) +++ { +++ /* Yikes! A single object file has too many entries. */ +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: .got subsegment exceeds 64K (size %d)"), +++ i, sw_64_elf_tdata (this_got)->total_got_size); +++ return FALSE; +++ } +++ +++ if (got_list == NULL) +++ got_list = this_got; +++ else +++ sw_64_elf_tdata(cur_got_obj)->got_link_next = this_got; +++ cur_got_obj = this_got; +++ } +++ +++ /* Strange degenerate case of no got references. */ +++ if (got_list == NULL) +++ return TRUE; +++ +++ htab->got_list = got_list; +++ } +++ +++ cur_got_obj = got_list; +++ if (cur_got_obj == NULL) +++ return FALSE; +++ +++ if (may_merge) +++ { +++ i = sw_64_elf_tdata(cur_got_obj)->got_link_next; +++ while (i != NULL) +++ { +++ if (elf64_sw_64_can_merge_gots (cur_got_obj, i)) +++ { +++ elf64_sw_64_merge_gots (cur_got_obj, i); +++ +++ sw_64_elf_tdata(i)->got->size = 0; +++ i = sw_64_elf_tdata(i)->got_link_next; +++ sw_64_elf_tdata(cur_got_obj)->got_link_next = i; +++ } +++ else +++ { +++ cur_got_obj = i; +++ i = sw_64_elf_tdata(i)->got_link_next; +++ } +++ } +++ } +++ +++ /* Once the gots have been merged, fill in the got offsets for +++ everything therein. */ +++ elf64_sw_64_calc_got_offsets (info); +++ +++ return TRUE; +++} +++ +++static bfd_boolean +++elf64_sw_64_size_plt_section_1 (struct sw_64_elf_link_hash_entry *h, +++ void * data) +++{ +++ asection *splt = (asection *) data; +++ struct sw_64_elf_got_entry *gotent; +++ bfd_boolean saw_one = FALSE; +++ +++ /* If we didn't need an entry before, we still don't. */ +++ if (!h->root.needs_plt) +++ return TRUE; +++ +++ /* For each LITERAL got entry still in use, allocate a plt entry. */ +++ for (gotent = h->got_entries; gotent ; gotent = gotent->next) +++ if (gotent->reloc_type == R_SW_64_LITERAL +++ && gotent->use_count > 0) +++ { +++ if (splt->size == 0) +++ splt->size = PLT_HEADER_SIZE; +++ gotent->plt_offset = splt->size; +++ splt->size += PLT_ENTRY_SIZE; +++ saw_one = TRUE; +++ } +++ +++ /* If there weren't any, there's no longer a need for the PLT entry. */ +++ if (!saw_one) +++ h->root.needs_plt = FALSE; +++ +++ return TRUE; +++} +++ +++/* Called from relax_section to rebuild the PLT in light of potential changes +++ in the function's status. */ +++ +++static void +++elf64_sw_64_size_plt_section (struct bfd_link_info *info) +++{ +++ asection *splt, *spltrel, *sgotplt; +++ unsigned long entries; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return; +++ +++ splt = elf_hash_table(info)->splt; +++ if (splt == NULL) +++ return; +++ +++ splt->size = 0; +++ +++ sw_64_elf_link_hash_traverse (htab, +++ elf64_sw_64_size_plt_section_1, splt); +++ +++ /* Every plt entry requires a JMP_SLOT relocation. */ +++ spltrel = elf_hash_table(info)->srelplt; +++ entries = 0; +++ if (splt->size) +++ { +++ if (elf64_sw_64_use_secureplt) +++ entries = (splt->size - NEW_PLT_HEADER_SIZE) / NEW_PLT_ENTRY_SIZE; +++ else +++ entries = (splt->size - OLD_PLT_HEADER_SIZE) / OLD_PLT_ENTRY_SIZE; +++ } +++ spltrel->size = entries * sizeof (Elf64_External_Rela); +++ +++ /* When using the secureplt, we need two words somewhere in the data +++ segment for the dynamic linker to tell us where to go. This is the +++ entire contents of the .got.plt section. */ +++ if (elf64_sw_64_use_secureplt) +++ { +++ sgotplt = elf_hash_table(info)->sgotplt; +++ sgotplt->size = entries ? 16 : 0; +++ } +++} +++ +++static bfd_boolean +++elf64_sw_64_always_size_sections (bfd *output_bfd ATTRIBUTE_UNUSED, +++ struct bfd_link_info *info) +++{ +++ bfd *i; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ if (bfd_link_relocatable (info)) +++ return TRUE; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return FALSE; +++ +++ if (!elf64_sw_64_size_got_sections (info, TRUE)) +++ return FALSE; +++ +++ /* Allocate space for all of the .got subsections. */ +++ i = htab->got_list; +++ for ( ; i ; i = sw_64_elf_tdata(i)->got_link_next) +++ { +++ asection *s = sw_64_elf_tdata(i)->got; +++ if (s->size > 0) +++ { +++ s->contents = (bfd_byte *) bfd_zalloc (i, s->size); +++ if (s->contents == NULL) +++ return FALSE; +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* The number of dynamic relocations required by a static relocation. */ +++ +++static int +++sw_64_dynamic_entries_for_reloc (int r_type, int dynamic, int shared, int pie) +++{ +++ switch (r_type) +++ { +++ /* May appear in GOT entries. */ +++ case R_SW_64_TLSGD: +++ return (dynamic ? 2 : shared ? 1 : 0); +++ case R_SW_64_TLSLDM: +++ return shared; +++ case R_SW_64_LITERAL: +++ return dynamic || shared; +++ case R_SW_64_GOTTPREL: +++ return dynamic || (shared && !pie); +++ case R_SW_64_GOTDTPREL: +++ return dynamic; +++ +++ /* May appear in data sections. */ +++ case R_SW_64_REFLONG: +++ case R_SW_64_REFQUAD: +++ return dynamic || shared; +++ case R_SW_64_TPREL64: +++ return dynamic || (shared && !pie); +++ +++ /* Everything else is illegal. We'll issue an error during +++ relocate_section. */ +++ default: +++ return 0; +++ } +++} +++ +++/* Work out the sizes of the dynamic relocation entries. */ +++ +++static bfd_boolean +++elf64_sw_64_calc_dynrel_sizes (struct sw_64_elf_link_hash_entry *h, +++ struct bfd_link_info *info) +++{ +++ bfd_boolean dynamic; +++ struct sw_64_elf_reloc_entry *relent; +++ unsigned long entries; +++ +++ /* If the symbol was defined as a common symbol in a regular object +++ file, and there was no definition in any dynamic object, then the +++ linker will have allocated space for the symbol in a common +++ section but the ELF_LINK_HASH_DEF_REGULAR flag will not have been +++ set. This is done for dynamic symbols in +++ elf_adjust_dynamic_symbol but this is not done for non-dynamic +++ symbols, somehow. */ +++ if (!h->root.def_regular +++ && h->root.ref_regular +++ && !h->root.def_dynamic +++ && (h->root.root.type == bfd_link_hash_defined +++ || h->root.root.type == bfd_link_hash_defweak) +++ && !(h->root.root.u.def.section->owner->flags & DYNAMIC)) +++ h->root.def_regular = 1; +++ +++ /* If the symbol is dynamic, we'll need all the relocations in their +++ natural form. If this is a shared object, and it has been forced +++ local, we'll need the same number of RELATIVE relocations. */ +++ dynamic = sw_64_elf_dynamic_symbol_p (&h->root, info); +++ +++ /* If the symbol is a hidden undefined weak, then we never have any +++ relocations. Avoid the loop which may want to add RELATIVE relocs +++ based on bfd_link_pic (info). */ +++ if (h->root.root.type == bfd_link_hash_undefweak && !dynamic) +++ return TRUE; +++ +++ for (relent = h->reloc_entries; relent; relent = relent->next) +++ { +++ entries = sw_64_dynamic_entries_for_reloc (relent->rtype, dynamic, +++ bfd_link_pic (info), +++ bfd_link_pie (info)); +++ if (entries) +++ { +++ asection *sec = relent->sec; +++ relent->srel->size += +++ entries * sizeof (Elf64_External_Rela) * relent->count; +++ if ((sec->flags & SEC_READONLY) != 0) +++ { +++ info->flags |= DT_TEXTREL; +++ info->callbacks->minfo +++ (_("%pB: dynamic relocation against `%pT' in " +++ "read-only section `%pA'\n"), +++ sec->owner, h->root.root.root.string, sec); +++ } +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* Subroutine of elf64_sw_64_size_rela_got_section for doing the +++ global symbols. */ +++ +++static bfd_boolean +++elf64_sw_64_size_rela_got_1 (struct sw_64_elf_link_hash_entry *h, +++ struct bfd_link_info *info) +++{ +++ bfd_boolean dynamic; +++ struct sw_64_elf_got_entry *gotent; +++ unsigned long entries; +++ +++ /* If we're using a plt for this symbol, then all of its relocations +++ for its got entries go into .rela.plt. */ +++ if (h->root.needs_plt) +++ return TRUE; +++ +++ /* If the symbol is dynamic, we'll need all the relocations in their +++ natural form. If this is a shared object, and it has been forced +++ local, we'll need the same number of RELATIVE relocations. */ +++ dynamic = sw_64_elf_dynamic_symbol_p (&h->root, info); +++ +++ /* If the symbol is a hidden undefined weak, then we never have any +++ relocations. Avoid the loop which may want to add RELATIVE relocs +++ based on bfd_link_pic (info). */ +++ if (h->root.root.type == bfd_link_hash_undefweak && !dynamic) +++ return TRUE; +++ +++ entries = 0; +++ for (gotent = h->got_entries; gotent ; gotent = gotent->next) +++ if (gotent->use_count > 0) +++ entries += sw_64_dynamic_entries_for_reloc (gotent->reloc_type, dynamic, +++ bfd_link_pic (info), +++ bfd_link_pie (info)); +++ +++ if (entries > 0) +++ { +++ asection *srel = elf_hash_table(info)->srelgot; +++ BFD_ASSERT (srel != NULL); +++ srel->size += sizeof (Elf64_External_Rela) * entries; +++ } +++ +++ return TRUE; +++} +++ +++/* Set the sizes of the dynamic relocation sections. */ +++ +++static void +++elf64_sw_64_size_rela_got_section (struct bfd_link_info *info) +++{ +++ unsigned long entries; +++ bfd *i; +++ asection *srel; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return; +++ +++ /* Shared libraries often require RELATIVE relocs, and some relocs +++ require attention for the main application as well. */ +++ +++ entries = 0; +++ for (i = htab->got_list; +++ i ; i = sw_64_elf_tdata(i)->got_link_next) +++ { +++ bfd *j; +++ +++ for (j = i; j ; j = sw_64_elf_tdata(j)->in_got_link_next) +++ { +++ struct sw_64_elf_got_entry **local_got_entries, *gotent; +++ int k, n; +++ +++ local_got_entries = sw_64_elf_tdata(j)->local_got_entries; +++ if (!local_got_entries) +++ continue; +++ +++ for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k) +++ for (gotent = local_got_entries[k]; +++ gotent ; gotent = gotent->next) +++ if (gotent->use_count > 0) +++ entries += (sw_64_dynamic_entries_for_reloc +++ (gotent->reloc_type, 0, bfd_link_pic (info), +++ bfd_link_pie (info))); +++ } +++ } +++ +++ srel = elf_hash_table(info)->srelgot; +++ if (!srel) +++ { +++ BFD_ASSERT (entries == 0); +++ return; +++ } +++ srel->size = sizeof (Elf64_External_Rela) * entries; +++ +++ /* Now do the non-local symbols. */ +++ sw_64_elf_link_hash_traverse (htab, +++ elf64_sw_64_size_rela_got_1, info); +++} +++ +++/* Set the sizes of the dynamic sections. */ +++ +++static bfd_boolean +++elf64_sw_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED, +++ struct bfd_link_info *info) +++{ +++ bfd *dynobj; +++ asection *s; +++ bfd_boolean relplt, relocs; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return FALSE; +++ +++ dynobj = elf_hash_table(info)->dynobj; +++ BFD_ASSERT(dynobj != NULL); +++ +++ if (elf_hash_table (info)->dynamic_sections_created) +++ { +++ /* Set the contents of the .interp section to the interpreter. */ +++ if (bfd_link_executable (info) && !info->nointerp) +++ { +++ s = bfd_get_linker_section (dynobj, ".interp"); +++ BFD_ASSERT (s != NULL); +++ s->size = sizeof ELF_DYNAMIC_INTERPRETER; +++ s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER; +++ } +++ +++ /* Now that we've seen all of the input files, we can decide which +++ symbols need dynamic relocation entries and which don't. We've +++ collected information in check_relocs that we can now apply to +++ size the dynamic relocation sections. */ +++ sw_64_elf_link_hash_traverse (htab, +++ elf64_sw_64_calc_dynrel_sizes, info); +++ +++ elf64_sw_64_size_rela_got_section (info); +++ elf64_sw_64_size_plt_section (info); +++ } +++ /* else we're not dynamic and by definition we don't need such things. */ +++ +++ /* The check_relocs and adjust_dynamic_symbol entry points have +++ determined the sizes of the various dynamic sections. Allocate +++ memory for them. */ +++ relplt = FALSE; +++ relocs = FALSE; +++ for (s = dynobj->sections; s != NULL; s = s->next) +++ { +++ const char *name; +++ +++ if (!(s->flags & SEC_LINKER_CREATED)) +++ continue; +++ +++ /* It's OK to base decisions on the section name, because none +++ of the dynobj section names depend upon the input files. */ +++ name = bfd_section_name (s); +++ +++ if (CONST_STRNEQ (name, ".rela")) +++ { +++ if (s->size != 0) +++ { +++ if (strcmp (name, ".rela.plt") == 0) +++ relplt = TRUE; +++ else +++ relocs = TRUE; +++ +++ /* We use the reloc_count field as a counter if we need +++ to copy relocs into the output file. */ +++ s->reloc_count = 0; +++ } +++ } +++ else if (! CONST_STRNEQ (name, ".got") +++ && strcmp (name, ".plt") != 0 +++ && strcmp (name, ".dynbss") != 0) +++ { +++ /* It's not one of our dynamic sections, so don't allocate space. */ +++ continue; +++ } +++ +++ if (s->size == 0) +++ { +++ /* If we don't need this section, strip it from the output file. +++ This is to handle .rela.bss and .rela.plt. We must create it +++ in create_dynamic_sections, because it must be created before +++ the linker maps input sections to output sections. The +++ linker does that before adjust_dynamic_symbol is called, and +++ it is that function which decides whether anything needs to +++ go into these sections. */ +++ if (!CONST_STRNEQ (name, ".got")) +++ s->flags |= SEC_EXCLUDE; +++ } +++ else if ((s->flags & SEC_HAS_CONTENTS) != 0) +++ { +++ /* Allocate memory for the section contents. */ +++ s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size); +++ if (s->contents == NULL) +++ return FALSE; +++ } +++ } +++ +++ if (elf_hash_table (info)->dynamic_sections_created) +++ { +++ /* Add some entries to the .dynamic section. We fill in the +++ values later, in elf64_sw_64_finish_dynamic_sections, but we +++ must add the entries now so that we get the correct size for +++ the .dynamic section. The DT_DEBUG entry is filled in by the +++ dynamic linker and used by the debugger. */ +++#define add_dynamic_entry(TAG, VAL) \ +++ _bfd_elf_add_dynamic_entry (info, TAG, VAL) +++ +++ if (!_bfd_elf_add_dynamic_tags (output_bfd, info, +++ relocs || relplt)) +++ return FALSE; +++ +++ if (relplt +++ && elf64_sw_64_use_secureplt +++ && !add_dynamic_entry (DT_SW_64_PLTRO, 1)) +++ return FALSE; +++ } +++#undef add_dynamic_entry +++ +++ return TRUE; +++} +++ +++/* These functions do relaxation for Sw_64 ELF. +++ +++ Currently I'm only handling what I can do with existing compiler +++ and assembler support, which means no instructions are removed, +++ though some may be nopped. At this time GCC does not emit enough +++ information to do all of the relaxing that is possible. It will +++ take some not small amount of work for that to happen. +++ +++ There are a couple of interesting papers that I once read on this +++ subject, that I cannot find references to at the moment, that +++ related to Sw_64 in particular. They are by David Wall, then of +++ DEC WRL. */ +++ +++struct sw_64_relax_info +++{ +++ bfd *abfd; +++ asection *sec; +++ bfd_byte *contents; +++ Elf_Internal_Shdr *symtab_hdr; +++ Elf_Internal_Rela *relocs, *relend; +++ struct bfd_link_info *link_info; +++ bfd_vma gp; +++ bfd *gotobj; +++ asection *tsec; +++ struct sw_64_elf_link_hash_entry *h; +++ struct sw_64_elf_got_entry **first_gotent; +++ struct sw_64_elf_got_entry *gotent; +++ bfd_boolean changed_contents; +++ bfd_boolean changed_relocs; +++ unsigned char other; +++}; +++ +++static Elf_Internal_Rela * +++elf64_sw_64_find_reloc_at_ofs (Elf_Internal_Rela *rel, +++ Elf_Internal_Rela *relend, +++ bfd_vma offset, int type) +++{ +++ while (rel < relend) +++ { +++ if (rel->r_offset == offset +++ && ELF64_R_TYPE (rel->r_info) == (unsigned int) type) +++ return rel; +++ ++rel; +++ } +++ return NULL; +++} +++ +++static bfd_boolean +++elf64_sw_64_relax_got_load (struct sw_64_relax_info *info, bfd_vma symval, +++ Elf_Internal_Rela *irel, unsigned long r_type) +++{ +++ unsigned int insn; +++ bfd_signed_vma disp; +++ +++ /* Get the instruction. */ +++ insn = bfd_get_32 (info->abfd, info->contents + irel->r_offset); +++ +++ if (insn >> 26 != OP_LDQ) +++ { +++ reloc_howto_type *howto = elf64_sw_64_howto_table + r_type; +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: %pA+%#" PRIx64 ": warning: " +++ "%s relocation against unexpected insn"), +++ info->abfd, info->sec, (uint64_t) irel->r_offset, howto->name); +++ return TRUE; +++ } +++ +++ /* Can't relax dynamic symbols. */ +++ if (info->h != NULL +++ && sw_64_elf_dynamic_symbol_p (&info->h->root, info->link_info)) +++ return TRUE; +++ +++ /* Can't use local-exec relocations in shared libraries. */ +++ if (r_type == R_SW_64_GOTTPREL +++ && bfd_link_dll (info->link_info)) +++ return TRUE; +++ +++ if (r_type == R_SW_64_LITERAL) +++ { +++ /* Look for nice constant addresses. This includes the not-uncommon +++ special case of 0 for undefweak symbols. */ +++ if ((info->h && info->h->root.root.type == bfd_link_hash_undefweak) +++ || (!bfd_link_pic (info->link_info) +++ && (symval >= (bfd_vma)-0x8000 || symval < 0x8000))) +++ { +++ disp = 0; +++ insn = (OP_LDA << 26) | (insn & (31 << 21)) | (31 << 16); +++ insn |= (symval & 0xffff); +++ r_type = R_SW_64_NONE; +++ } +++ else +++ { +++ /* We may only create GPREL relocs during the second pass. */ +++ if (info->link_info->relax_pass == 0) +++ return TRUE; +++ +++ disp = symval - info->gp; +++ insn = (OP_LDA << 26) | (insn & 0x03ff0000); +++ r_type = R_SW_64_GPREL16; +++ } +++ } +++ else +++ { +++ bfd_vma dtp_base, tp_base; +++ +++ BFD_ASSERT (elf_hash_table (info->link_info)->tls_sec != NULL); +++ dtp_base = sw_64_get_dtprel_base (info->link_info); +++ tp_base = sw_64_get_tprel_base (info->link_info); +++ disp = symval - (r_type == R_SW_64_GOTDTPREL ? dtp_base : tp_base); +++ +++ insn = (OP_LDA << 26) | (insn & (31 << 21)) | (31 << 16); +++ +++ switch (r_type) +++ { +++ case R_SW_64_GOTDTPREL: +++ r_type = R_SW_64_DTPREL16; +++ break; +++ case R_SW_64_GOTTPREL: +++ r_type = R_SW_64_TPREL16; +++ break; +++ default: +++ BFD_ASSERT (0); +++ return FALSE; +++ } +++ } +++ +++ if (disp < -0x8000 || disp >= 0x8000) +++ return TRUE; +++ +++ bfd_put_32 (info->abfd, (bfd_vma) insn, info->contents + irel->r_offset); +++ info->changed_contents = TRUE; +++ +++ /* Reduce the use count on this got entry by one, possibly +++ eliminating it. */ +++ if (--info->gotent->use_count == 0) +++ { +++ int sz = sw_64_got_entry_size (r_type); +++ sw_64_elf_tdata (info->gotobj)->total_got_size -= sz; +++ if (!info->h) +++ sw_64_elf_tdata (info->gotobj)->local_got_size -= sz; +++ } +++ +++ /* Smash the existing GOT relocation for its 16-bit immediate pair. */ +++ irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), r_type); +++ info->changed_relocs = TRUE; +++ +++ /* ??? Search forward through this basic block looking for insns +++ that use the target register. Stop after an insn modifying the +++ register is seen, or after a branch or call. +++ +++ Any such memory load insn may be substituted by a load directly +++ off the GP. This allows the memory load insn to be issued before +++ the calculated GP register would otherwise be ready. +++ +++ Any such jsr insn can be replaced by a bsr if it is in range. +++ +++ This would mean that we'd have to _add_ relocations, the pain of +++ which gives one pause. */ +++ +++ return TRUE; +++} +++ +++static bfd_vma +++elf64_sw_64_relax_opt_call (struct sw_64_relax_info *info, bfd_vma symval) +++{ +++ /* If the function has the same gp, and we can identify that the +++ function does not use its function pointer, we can eliminate the +++ address load. */ +++ +++ /* If the symbol is marked NOPV, we are being told the function never +++ needs its procedure value. */ +++ if ((info->other & STO_SW_64_STD_GPLOAD) == STO_SW_64_NOPV) +++ return symval; +++ +++ /* If the symbol is marked STD_GP, we are being told the function does +++ a normal ldgp in the first two words. */ +++ else if ((info->other & STO_SW_64_STD_GPLOAD) == STO_SW_64_STD_GPLOAD) +++ ; +++ +++ /* Otherwise, we may be able to identify a GP load in the first two +++ words, which we can then skip. */ +++ else +++ { +++ Elf_Internal_Rela *tsec_relocs, *tsec_relend, *tsec_free, *gpdisp; +++ bfd_vma ofs; +++ +++ /* Load the relocations from the section that the target symbol is in. */ +++ if (info->sec == info->tsec) +++ { +++ tsec_relocs = info->relocs; +++ tsec_relend = info->relend; +++ tsec_free = NULL; +++ } +++ else +++ { +++ tsec_relocs = (_bfd_elf_link_read_relocs +++ (info->abfd, info->tsec, NULL, +++ (Elf_Internal_Rela *) NULL, +++ info->link_info->keep_memory)); +++ if (tsec_relocs == NULL) +++ return 0; +++ tsec_relend = tsec_relocs + info->tsec->reloc_count; +++ tsec_free = (elf_section_data (info->tsec)->relocs == tsec_relocs +++ ? NULL +++ : tsec_relocs); +++ } +++ +++ /* Recover the symbol's offset within the section. */ +++ ofs = (symval - info->tsec->output_section->vma +++ - info->tsec->output_offset); +++ +++ /* Look for a GPDISP reloc. */ +++ gpdisp = (elf64_sw_64_find_reloc_at_ofs +++ (tsec_relocs, tsec_relend, ofs, R_SW_64_GPDISP)); +++ +++ if (!gpdisp || gpdisp->r_addend != 4) +++ { +++ free (tsec_free); +++ return 0; +++ } +++ free (tsec_free); +++ } +++ +++ /* We've now determined that we can skip an initial gp load. Verify +++ that the call and the target use the same gp. */ +++ if (info->link_info->output_bfd->xvec != info->tsec->owner->xvec +++ || info->gotobj != sw_64_elf_tdata (info->tsec->owner)->gotobj) +++ return 0; +++ +++ return symval + 8; +++} +++ +++static bfd_boolean +++elf64_sw_64_relax_with_lituse (struct sw_64_relax_info *info, +++ bfd_vma symval, Elf_Internal_Rela *irel) +++{ +++ Elf_Internal_Rela *urel, *erel, *irelend = info->relend; +++ int flags; +++ bfd_signed_vma disp; +++ bfd_boolean fits16; +++ bfd_boolean fits32; +++ bfd_boolean lit_reused = FALSE; +++ bfd_boolean all_optimized = TRUE; +++ bfd_boolean changed_contents; +++ bfd_boolean changed_relocs; +++ bfd_byte *contents = info->contents; +++ bfd *abfd = info->abfd; +++ bfd_vma sec_output_vma; +++ unsigned int lit_insn; +++ int relax_pass; +++ +++ lit_insn = bfd_get_32 (abfd, contents + irel->r_offset); +++ if (lit_insn >> 26 != OP_LDQ) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: %pA+%#" PRIx64 ": warning: " +++ "%s relocation against unexpected insn"), +++ abfd, info->sec, (uint64_t) irel->r_offset, "LITERAL"); +++ return TRUE; +++ } +++ +++ /* Can't relax dynamic symbols. */ +++ if (sw_64_elf_dynamic_symbol_p (&info->h->root, info->link_info)) +++ return TRUE; +++ +++ changed_contents = info->changed_contents; +++ changed_relocs = info->changed_relocs; +++ sec_output_vma = info->sec->output_section->vma + info->sec->output_offset; +++ relax_pass = info->link_info->relax_pass; +++ +++ /* Summarize how this particular LITERAL is used. */ +++ for (erel = irel+1, flags = 0; erel < irelend; ++erel) +++ { +++ if (ELF64_R_TYPE (erel->r_info) != R_SW_64_LITUSE) +++ break; +++ if (erel->r_addend <= 6) +++ flags |= 1 << erel->r_addend; +++ } +++ +++ /* A little preparation for the loop... */ +++ disp = symval - info->gp; +++ +++ for (urel = irel+1; urel < erel; ++urel) +++ { +++ bfd_vma urel_r_offset = urel->r_offset; +++ unsigned int insn; +++ int insn_disp; +++ bfd_signed_vma xdisp; +++ Elf_Internal_Rela nrel; +++ +++ insn = bfd_get_32 (abfd, contents + urel_r_offset); +++ +++ switch (urel->r_addend) +++ { +++ case LITUSE_SW_64_ADDR: +++ default: +++ /* This type is really just a placeholder to note that all +++ uses cannot be optimized, but to still allow some. */ +++ all_optimized = FALSE; +++ break; +++ +++ case LITUSE_SW_64_BASE: +++ /* We may only create GPREL relocs during the second pass. */ +++ if (relax_pass == 0) +++ { +++ all_optimized = FALSE; +++ break; +++ } +++ +++ /* We can always optimize 16-bit displacements. */ +++ +++ /* Extract the displacement from the instruction, sign-extending +++ it if necessary, then test whether it is within 16 or 32 bits +++ displacement from GP. */ +++ insn_disp = ((insn & 0xffff) ^ 0x8000) - 0x8000; +++ +++ xdisp = disp + insn_disp; +++ fits16 = (xdisp >= - (bfd_signed_vma) 0x8000 && xdisp < 0x8000); +++ fits32 = (xdisp >= - (bfd_signed_vma) 0x80000000 +++ && xdisp < 0x7fff8000); +++ +++ if (fits16) +++ { +++ /* Take the op code and dest from this insn, take the base +++ register from the literal insn. Leave the offset alone. */ +++ insn = (insn & 0xffe0ffff) | (lit_insn & 0x001f0000); +++ bfd_put_32 (abfd, (bfd_vma) insn, contents + urel_r_offset); +++ changed_contents = TRUE; +++ +++ nrel = *urel; +++ nrel.r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), +++ R_SW_64_GPREL16); +++ nrel.r_addend = irel->r_addend; +++ +++ /* As we adjust, move the reloc to the end so that we don't +++ break the LITERAL+LITUSE chain. */ +++ if (urel < --erel) +++ *urel-- = *erel; +++ *erel = nrel; +++ changed_relocs = TRUE; +++ } +++ +++ /* If all mem+byte, we can optimize 32-bit mem displacements. */ +++ else if (fits32 && !(flags & ~6)) +++ { +++ /* FIXME: sanity check that lit insn Ra is mem insn Rb. */ +++ +++ irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), +++ R_SW_64_GPRELHIGH); +++ lit_insn = (OP_LDAH << 26) | (lit_insn & 0x03ff0000); +++ bfd_put_32 (abfd, (bfd_vma) lit_insn, contents + irel->r_offset); +++ lit_reused = TRUE; +++ changed_contents = TRUE; +++ +++ /* Since all relocs must be optimized, don't bother swapping +++ this relocation to the end. */ +++ urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), +++ R_SW_64_GPRELLOW); +++ urel->r_addend = irel->r_addend; +++ changed_relocs = TRUE; +++ } +++ else +++ all_optimized = FALSE; +++ break; +++ +++ case LITUSE_SW_64_BYTOFF: +++ /* We can always optimize byte instructions. */ +++ +++ /* FIXME: sanity check the insn for byte op. Check that the +++ literal dest reg is indeed Rb in the byte insn. */ +++ +++ insn &= ~ (unsigned) 0x001ff000; +++ insn |= ((symval & 7) << 13) | 0x1000; +++ bfd_put_32 (abfd, (bfd_vma) insn, contents + urel_r_offset); +++ changed_contents = TRUE; +++ +++ nrel = *urel; +++ nrel.r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ nrel.r_addend = 0; +++ +++ /* As we adjust, move the reloc to the end so that we don't +++ break the LITERAL+LITUSE chain. */ +++ if (urel < --erel) +++ *urel-- = *erel; +++ *erel = nrel; +++ changed_relocs = TRUE; +++ break; +++ +++ case LITUSE_SW_64_JSR: +++ case LITUSE_SW_64_TLSGD: +++ case LITUSE_SW_64_TLSLDM: +++ case LITUSE_SW_64_JSRDIRECT: +++ { +++ bfd_vma optdest, org; +++ bfd_signed_vma odisp; +++ +++ /* For undefined weak symbols, we're mostly interested in getting +++ rid of the got entry whenever possible, so optimize this to a +++ use of the zero register. */ +++ if (info->h && info->h->root.root.type == bfd_link_hash_undefweak) +++ { +++ insn |= 31 << 16; +++ bfd_put_32 (abfd, (bfd_vma) insn, contents + urel_r_offset); +++ +++ changed_contents = TRUE; +++ break; +++ } +++ +++ /* If not zero, place to jump without needing pv. */ +++ optdest = elf64_sw_64_relax_opt_call (info, symval); +++ org = sec_output_vma + urel_r_offset + 4; +++ odisp = (optdest ? optdest : symval) - org; +++ +++ if (odisp >= -0x400000 && odisp < 0x400000) +++ { +++ Elf_Internal_Rela *xrel; +++ +++ /* Preserve branch prediction call stack when possible. */ +++ if ((insn & INSN_JSR_MASK) == INSN_JSR) +++ insn = (OP_BSR << 26) | (insn & 0x03e00000); +++ else +++ insn = (OP_BR << 26) | (insn & 0x03e00000); +++ bfd_put_32 (abfd, (bfd_vma) insn, contents + urel_r_offset); +++ changed_contents = TRUE; +++ +++ nrel = *urel; +++ nrel.r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), +++ R_SW_64_BRADDR); +++ nrel.r_addend = irel->r_addend; +++ +++ if (optdest) +++ nrel.r_addend += optdest - symval; +++ else +++ all_optimized = FALSE; +++ +++ /* Kill any HINT reloc that might exist for this insn. */ +++ xrel = (elf64_sw_64_find_reloc_at_ofs +++ (info->relocs, info->relend, urel_r_offset, +++ R_SW_64_HINT)); +++ if (xrel) +++ xrel->r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ +++ /* As we adjust, move the reloc to the end so that we don't +++ break the LITERAL+LITUSE chain. */ +++ if (urel < --erel) +++ *urel-- = *erel; +++ *erel = nrel; +++ +++ info->changed_relocs = TRUE; +++ } +++ else +++ all_optimized = FALSE; +++ +++ /* Even if the target is not in range for a direct branch, +++ if we share a GP, we can eliminate the gp reload. */ +++ if (optdest) +++ { +++ Elf_Internal_Rela *gpdisp +++ = (elf64_sw_64_find_reloc_at_ofs +++ (info->relocs, irelend, urel_r_offset + 4, +++ R_SW_64_GPDISP)); +++ if (gpdisp) +++ { +++ bfd_byte *p_ldah = contents + gpdisp->r_offset; +++ bfd_byte *p_lda = p_ldah + gpdisp->r_addend; +++ unsigned int ldah = bfd_get_32 (abfd, p_ldah); +++ unsigned int lda = bfd_get_32 (abfd, p_lda); +++ +++ /* Verify that the instruction is "ldah $29,0($26)". +++ Consider a function that ends in a noreturn call, +++ and that the next function begins with an ldgp, +++ and that by accident there is no padding between. +++ In that case the insn would use $27 as the base. */ +++#ifndef XWB20200308 +++ if (ldah == 0xffba0000 && lda == 0xfbba0000) +++#else +++ if (ldah == 0x27ba0000 && lda == 0x23bd0000) +++#endif +++ { +++ bfd_put_32 (abfd, (bfd_vma) INSN_UNOP, p_ldah); +++ bfd_put_32 (abfd, (bfd_vma) INSN_UNOP, p_lda); +++ +++ gpdisp->r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ changed_contents = TRUE; +++ changed_relocs = TRUE; +++ } +++ } +++ } +++ } +++ break; +++ } +++ } +++ +++ /* If we reused the literal instruction, we must have optimized all. */ +++ BFD_ASSERT(!lit_reused || all_optimized); +++ +++ /* If all cases were optimized, we can reduce the use count on this +++ got entry by one, possibly eliminating it. */ +++ if (all_optimized) +++ { +++ if (--info->gotent->use_count == 0) +++ { +++ int sz = sw_64_got_entry_size (R_SW_64_LITERAL); +++ sw_64_elf_tdata (info->gotobj)->total_got_size -= sz; +++ if (!info->h) +++ sw_64_elf_tdata (info->gotobj)->local_got_size -= sz; +++ } +++ +++ /* If the literal instruction is no longer needed (it may have been +++ reused. We can eliminate it. */ +++ /* ??? For now, I don't want to deal with compacting the section, +++ so just nop it out. */ +++ if (!lit_reused) +++ { +++ irel->r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ changed_relocs = TRUE; +++ +++ bfd_put_32 (abfd, (bfd_vma) INSN_UNOP, contents + irel->r_offset); +++ changed_contents = TRUE; +++ } +++ } +++ +++ info->changed_contents = changed_contents; +++ info->changed_relocs = changed_relocs; +++ +++ if (all_optimized || relax_pass == 0) +++ return TRUE; +++ return elf64_sw_64_relax_got_load (info, symval, irel, R_SW_64_LITERAL); +++} +++ +++static bfd_boolean +++elf64_sw_64_relax_tls_get_addr (struct sw_64_relax_info *info, bfd_vma symval, +++ Elf_Internal_Rela *irel, bfd_boolean is_gd) +++{ +++ bfd_byte *pos[5]; +++ unsigned int insn, tlsgd_reg; +++ Elf_Internal_Rela *gpdisp, *hint; +++ bfd_boolean dynamic, use_gottprel; +++ unsigned long new_symndx; +++ +++ dynamic = (info->h != NULL +++ && sw_64_elf_dynamic_symbol_p (&info->h->root, info->link_info)); +++ +++ /* If a TLS symbol is accessed using IE at least once, there is no point +++ to use dynamic model for it. */ +++ if (is_gd && info->h && (info->h->flags & SW_64_ELF_LINK_HASH_TLS_IE)) +++ ; +++ +++ /* If the symbol is local, and we've already committed to DF_STATIC_TLS, +++ then we might as well relax to IE. */ +++ else if (bfd_link_pic (info->link_info) && !dynamic +++ && (info->link_info->flags & DF_STATIC_TLS)) +++ ; +++ +++ /* Otherwise we must be building an executable to do anything. */ +++ else if (bfd_link_pic (info->link_info)) +++ return TRUE; +++ +++ /* The TLSGD/TLSLDM relocation must be followed by a LITERAL and +++ the matching LITUSE_TLS relocations. */ +++ if (irel + 2 >= info->relend) +++ return TRUE; +++ if (ELF64_R_TYPE (irel[1].r_info) != R_SW_64_LITERAL +++ || ELF64_R_TYPE (irel[2].r_info) != R_SW_64_LITUSE +++ || irel[2].r_addend != (is_gd ? LITUSE_SW_64_TLSGD : LITUSE_SW_64_TLSLDM)) +++ return TRUE; +++ +++ /* There must be a GPDISP relocation positioned immediately after the +++ LITUSE relocation. */ +++ gpdisp = elf64_sw_64_find_reloc_at_ofs (info->relocs, info->relend, +++ irel[2].r_offset + 4, R_SW_64_GPDISP); +++ if (!gpdisp) +++ return TRUE; +++ +++ pos[0] = info->contents + irel[0].r_offset; +++ pos[1] = info->contents + irel[1].r_offset; +++ pos[2] = info->contents + irel[2].r_offset; +++ pos[3] = info->contents + gpdisp->r_offset; +++ pos[4] = pos[3] + gpdisp->r_addend; +++ +++ /* Beware of the compiler hoisting part of the sequence out a loop +++ and adjusting the destination register for the TLSGD insn. If this +++ happens, there will be a move into $16 before the JSR insn, so only +++ transformations of the first insn pair should use this register. */ +++ tlsgd_reg = bfd_get_32 (info->abfd, pos[0]); +++ tlsgd_reg = (tlsgd_reg >> 21) & 31; +++ +++ /* Generally, the positions are not allowed to be out of order, lest the +++ modified insn sequence have different register lifetimes. We can make +++ an exception when pos 1 is adjacent to pos 0. */ +++ if (pos[1] + 4 == pos[0]) +++ { +++ bfd_byte *tmp = pos[0]; +++ pos[0] = pos[1]; +++ pos[1] = tmp; +++ } +++ if (pos[1] >= pos[2] || pos[2] >= pos[3]) +++ return TRUE; +++ +++ /* Reduce the use count on the LITERAL relocation. Do this before we +++ smash the symndx when we adjust the relocations below. */ +++ { +++ struct sw_64_elf_got_entry *lit_gotent; +++ struct sw_64_elf_link_hash_entry *lit_h; +++ unsigned long indx; +++ +++ BFD_ASSERT (ELF64_R_SYM (irel[1].r_info) >= info->symtab_hdr->sh_info); +++ indx = ELF64_R_SYM (irel[1].r_info) - info->symtab_hdr->sh_info; +++ lit_h = sw_64_elf_sym_hashes (info->abfd)[indx]; +++ +++ while (lit_h->root.root.type == bfd_link_hash_indirect +++ || lit_h->root.root.type == bfd_link_hash_warning) +++ lit_h = (struct sw_64_elf_link_hash_entry *) lit_h->root.root.u.i.link; +++ +++ for (lit_gotent = lit_h->got_entries; lit_gotent ; +++ lit_gotent = lit_gotent->next) +++ if (lit_gotent->gotobj == info->gotobj +++ && lit_gotent->reloc_type == R_SW_64_LITERAL +++ && lit_gotent->addend == irel[1].r_addend) +++ break; +++ BFD_ASSERT (lit_gotent); +++ +++ if (--lit_gotent->use_count == 0) +++ { +++ int sz = sw_64_got_entry_size (R_SW_64_LITERAL); +++ sw_64_elf_tdata (info->gotobj)->total_got_size -= sz; +++ } +++ } +++ +++ /* Change +++ +++ lda $16,x($gp) !tlsgd!1 +++ ldq $27,__tls_get_addr($gp) !literal!1 +++ jsr $26,($27),__tls_get_addr !lituse_tlsgd!1 +++ ldah $29,0($26) !gpdisp!2 +++ lda $29,0($29) !gpdisp!2 +++ to +++ ldq $16,x($gp) !gottprel +++ unop +++ call_pal rduniq +++ addq $16,$0,$0 +++ unop +++ or the first pair to +++ lda $16,x($gp) !tprel +++ unop +++ or +++ ldah $16,x($gp) !tprelhi +++ lda $16,x($16) !tprello +++ +++ as appropriate. */ +++ +++ use_gottprel = FALSE; +++ new_symndx = is_gd ? ELF64_R_SYM (irel->r_info) : STN_UNDEF; +++ +++ /* Some compilers warn about a Boolean-looking expression being +++ used in a switch. The explicit cast silences them. */ +++ switch ((int) (!dynamic && !bfd_link_pic (info->link_info))) +++ { +++ case 1: +++ { +++ bfd_vma tp_base; +++ bfd_signed_vma disp; +++ +++ BFD_ASSERT (elf_hash_table (info->link_info)->tls_sec != NULL); +++ tp_base = sw_64_get_tprel_base (info->link_info); +++ disp = symval - tp_base; +++ +++ if (disp >= -0x8000 && disp < 0x8000) +++ { +++ insn = (OP_LDA << 26) | (tlsgd_reg << 21) | (31 << 16); +++ bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]); +++ bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]); +++ +++ irel[0].r_offset = pos[0] - info->contents; +++ irel[0].r_info = ELF64_R_INFO (new_symndx, R_SW_64_TPREL16); +++ irel[1].r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ break; +++ } +++ else if (disp >= -(bfd_signed_vma) 0x80000000 +++ && disp < (bfd_signed_vma) 0x7fff8000 +++ && pos[0] + 4 == pos[1]) +++ { +++ insn = (OP_LDAH << 26) | (tlsgd_reg << 21) | (31 << 16); +++ bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]); +++ insn = (OP_LDA << 26) | (tlsgd_reg << 21) | (tlsgd_reg << 16); +++ bfd_put_32 (info->abfd, (bfd_vma) insn, pos[1]); +++ +++ irel[0].r_offset = pos[0] - info->contents; +++ irel[0].r_info = ELF64_R_INFO (new_symndx, R_SW_64_TPRELHI); +++ irel[1].r_offset = pos[1] - info->contents; +++ irel[1].r_info = ELF64_R_INFO (new_symndx, R_SW_64_TPRELLO); +++ break; +++ } +++ } +++ /* FALLTHRU */ +++ +++ default: +++ use_gottprel = TRUE; +++ +++ insn = (OP_LDQ << 26) | (tlsgd_reg << 21) | (29 << 16); +++ bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]); +++ bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]); +++ +++ irel[0].r_offset = pos[0] - info->contents; +++ irel[0].r_info = ELF64_R_INFO (new_symndx, R_SW_64_GOTTPREL); +++ irel[1].r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ break; +++ } +++ +++ bfd_put_32 (info->abfd, (bfd_vma) INSN_RDUNIQ, pos[2]); +++ +++ insn = INSN_ADDQ | (16 << 21) | (0 << 16) | (0 << 0); +++ bfd_put_32 (info->abfd, (bfd_vma) insn, pos[3]); +++ +++ bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[4]); +++ +++ irel[2].r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ gpdisp->r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ +++ hint = elf64_sw_64_find_reloc_at_ofs (info->relocs, info->relend, +++ irel[2].r_offset, R_SW_64_HINT); +++ if (hint) +++ hint->r_info = ELF64_R_INFO (0, R_SW_64_NONE); +++ +++ info->changed_contents = TRUE; +++ info->changed_relocs = TRUE; +++ +++ /* Reduce the use count on the TLSGD/TLSLDM relocation. */ +++ if (--info->gotent->use_count == 0) +++ { +++ int sz = sw_64_got_entry_size (info->gotent->reloc_type); +++ sw_64_elf_tdata (info->gotobj)->total_got_size -= sz; +++ if (!info->h) +++ sw_64_elf_tdata (info->gotobj)->local_got_size -= sz; +++ } +++ +++ /* If we've switched to a GOTTPREL relocation, increment the reference +++ count on that got entry. */ +++ if (use_gottprel) +++ { +++ struct sw_64_elf_got_entry *tprel_gotent; +++ +++ for (tprel_gotent = *info->first_gotent; tprel_gotent ; +++ tprel_gotent = tprel_gotent->next) +++ if (tprel_gotent->gotobj == info->gotobj +++ && tprel_gotent->reloc_type == R_SW_64_GOTTPREL +++ && tprel_gotent->addend == irel->r_addend) +++ break; +++ if (tprel_gotent) +++ tprel_gotent->use_count++; +++ else +++ { +++ if (info->gotent->use_count == 0) +++ tprel_gotent = info->gotent; +++ else +++ { +++ tprel_gotent = (struct sw_64_elf_got_entry *) +++ bfd_alloc (info->abfd, sizeof (struct sw_64_elf_got_entry)); +++ if (!tprel_gotent) +++ return FALSE; +++ +++ tprel_gotent->next = *info->first_gotent; +++ *info->first_gotent = tprel_gotent; +++ +++ tprel_gotent->gotobj = info->gotobj; +++ tprel_gotent->addend = irel->r_addend; +++ tprel_gotent->got_offset = -1; +++ tprel_gotent->reloc_done = 0; +++ tprel_gotent->reloc_xlated = 0; +++ } +++ +++ tprel_gotent->use_count = 1; +++ tprel_gotent->reloc_type = R_SW_64_GOTTPREL; +++ } +++ } +++ +++ return TRUE; +++} +++ +++static bfd_boolean +++elf64_sw_64_relax_section (bfd *abfd, asection *sec, +++ struct bfd_link_info *link_info, bfd_boolean *again) +++{ +++ Elf_Internal_Shdr *symtab_hdr; +++ Elf_Internal_Rela *internal_relocs; +++ Elf_Internal_Rela *irel, *irelend; +++ Elf_Internal_Sym *isymbuf = NULL; +++ struct sw_64_elf_got_entry **local_got_entries; +++ struct sw_64_relax_info info; +++ struct sw_64_elf_link_hash_table * htab; +++ int relax_pass; +++ +++ htab = sw_64_elf_hash_table (link_info); +++ if (htab == NULL) +++ return FALSE; +++ +++ /* There's nothing to change, yet. */ +++ *again = FALSE; +++ +++ if (bfd_link_relocatable (link_info) +++ || ((sec->flags & (SEC_CODE | SEC_RELOC | SEC_ALLOC)) +++ != (SEC_CODE | SEC_RELOC | SEC_ALLOC)) +++ || sec->reloc_count == 0) +++ return TRUE; +++ +++ BFD_ASSERT (is_sw_64_elf (abfd)); +++ relax_pass = link_info->relax_pass; +++ +++ /* Make sure our GOT and PLT tables are up-to-date. */ +++ if (htab->relax_trip != link_info->relax_trip) +++ { +++ htab->relax_trip = link_info->relax_trip; +++ +++ /* This should never fail after the initial round, since the only error +++ is GOT overflow, and relaxation only shrinks the table. However, we +++ may only merge got sections during the first pass. If we merge +++ sections after we've created GPREL relocs, the GP for the merged +++ section backs up which may put the relocs out of range. */ +++ if (!elf64_sw_64_size_got_sections (link_info, relax_pass == 0)) +++ abort (); +++ if (elf_hash_table (link_info)->dynamic_sections_created) +++ { +++ elf64_sw_64_size_plt_section (link_info); +++ elf64_sw_64_size_rela_got_section (link_info); +++ } +++ } +++ +++ symtab_hdr = &elf_symtab_hdr (abfd); +++ local_got_entries = sw_64_elf_tdata(abfd)->local_got_entries; +++ +++ /* Load the relocations for this section. */ +++ internal_relocs = (_bfd_elf_link_read_relocs +++ (abfd, sec, NULL, (Elf_Internal_Rela *) NULL, +++ link_info->keep_memory)); +++ if (internal_relocs == NULL) +++ return FALSE; +++ +++ memset(&info, 0, sizeof (info)); +++ info.abfd = abfd; +++ info.sec = sec; +++ info.link_info = link_info; +++ info.symtab_hdr = symtab_hdr; +++ info.relocs = internal_relocs; +++ info.relend = irelend = internal_relocs + sec->reloc_count; +++ +++ /* Find the GP for this object. Do not store the result back via +++ _bfd_set_gp_value, since this could change again before final. */ +++ info.gotobj = sw_64_elf_tdata (abfd)->gotobj; +++ if (info.gotobj) +++ { +++ asection *sgot = sw_64_elf_tdata (info.gotobj)->got; +++ info.gp = (sgot->output_section->vma +++ + sgot->output_offset +++ + 0x8000); +++ } +++ +++ /* Get the section contents. */ +++ if (elf_section_data (sec)->this_hdr.contents != NULL) +++ info.contents = elf_section_data (sec)->this_hdr.contents; +++ else +++ { +++ if (!bfd_malloc_and_get_section (abfd, sec, &info.contents)) +++ goto error_return; +++ } +++ +++ for (irel = internal_relocs; irel < irelend; irel++) +++ { +++ bfd_vma symval; +++ struct sw_64_elf_got_entry *gotent; +++ unsigned long r_type = ELF64_R_TYPE (irel->r_info); +++ unsigned long r_symndx = ELF64_R_SYM (irel->r_info); +++ +++ /* Early exit for unhandled or unrelaxable relocations. */ +++ if (r_type != R_SW_64_LITERAL) +++ { +++ /* We complete everything except LITERAL in the first pass. */ +++ if (relax_pass != 0) +++ continue; +++ if (r_type == R_SW_64_TLSLDM) +++ { +++ /* The symbol for a TLSLDM reloc is ignored. Collapse the +++ reloc to the STN_UNDEF (0) symbol so that they all match. */ +++ r_symndx = STN_UNDEF; +++ } +++ else if (r_type != R_SW_64_GOTDTPREL +++ && r_type != R_SW_64_GOTTPREL +++ && r_type != R_SW_64_TLSGD) +++ continue; +++ } +++ +++ /* Get the value of the symbol referred to by the reloc. */ +++ if (r_symndx < symtab_hdr->sh_info) +++ { +++ /* A local symbol. */ +++ Elf_Internal_Sym *isym; +++ +++ /* Read this BFD's local symbols. */ +++ if (isymbuf == NULL) +++ { +++ isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents; +++ if (isymbuf == NULL) +++ isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr, +++ symtab_hdr->sh_info, 0, +++ NULL, NULL, NULL); +++ if (isymbuf == NULL) +++ goto error_return; +++ } +++ +++ isym = isymbuf + r_symndx; +++ +++ /* Given the symbol for a TLSLDM reloc is ignored, this also +++ means forcing the symbol value to the tp base. */ +++ if (r_type == R_SW_64_TLSLDM) +++ { +++ info.tsec = bfd_abs_section_ptr; +++ symval = sw_64_get_tprel_base (info.link_info); +++ } +++ else +++ { +++ symval = isym->st_value; +++ if (isym->st_shndx == SHN_UNDEF) +++ continue; +++ else if (isym->st_shndx == SHN_ABS) +++ info.tsec = bfd_abs_section_ptr; +++ else if (isym->st_shndx == SHN_COMMON) +++ info.tsec = bfd_com_section_ptr; +++ else +++ info.tsec = bfd_section_from_elf_index (abfd, isym->st_shndx); +++ } +++ +++ info.h = NULL; +++ info.other = isym->st_other; +++ if (local_got_entries) +++ info.first_gotent = &local_got_entries[r_symndx]; +++ else +++ { +++ info.first_gotent = &info.gotent; +++ info.gotent = NULL; +++ } +++ } +++ else +++ { +++ unsigned long indx; +++ struct sw_64_elf_link_hash_entry *h; +++ +++ indx = r_symndx - symtab_hdr->sh_info; +++ h = sw_64_elf_sym_hashes (abfd)[indx]; +++ BFD_ASSERT (h != NULL); +++ +++ while (h->root.root.type == bfd_link_hash_indirect +++ || h->root.root.type == bfd_link_hash_warning) +++ h = (struct sw_64_elf_link_hash_entry *)h->root.root.u.i.link; +++ +++ /* If the symbol is undefined, we can't do anything with it. */ +++ if (h->root.root.type == bfd_link_hash_undefined) +++ continue; +++ +++ /* If the symbol isn't defined in the current module, +++ again we can't do anything. */ +++ if (h->root.root.type == bfd_link_hash_undefweak) +++ { +++ info.tsec = bfd_abs_section_ptr; +++ symval = 0; +++ } +++ else if (!h->root.def_regular) +++ { +++ /* Except for TLSGD relocs, which can sometimes be +++ relaxed to GOTTPREL relocs. */ +++ if (r_type != R_SW_64_TLSGD) +++ continue; +++ info.tsec = bfd_abs_section_ptr; +++ symval = 0; +++ } +++ else +++ { +++ info.tsec = h->root.root.u.def.section; +++ symval = h->root.root.u.def.value; +++ } +++ +++ info.h = h; +++ info.other = h->root.other; +++ info.first_gotent = &h->got_entries; +++ } +++ +++ /* Search for the got entry to be used by this relocation. */ +++ for (gotent = *info.first_gotent; gotent ; gotent = gotent->next) +++ if (gotent->gotobj == info.gotobj +++ && gotent->reloc_type == r_type +++ && gotent->addend == irel->r_addend) +++ break; +++ info.gotent = gotent; +++ +++ symval += info.tsec->output_section->vma + info.tsec->output_offset; +++ symval += irel->r_addend; +++ +++ switch (r_type) +++ { +++ case R_SW_64_LITERAL: +++ BFD_ASSERT(info.gotent != NULL); +++ +++ /* If there exist LITUSE relocations immediately following, this +++ opens up all sorts of interesting optimizations, because we +++ now know every location that this address load is used. */ +++ if (irel+1 < irelend +++ && ELF64_R_TYPE (irel[1].r_info) == R_SW_64_LITUSE) +++ { +++ if (!elf64_sw_64_relax_with_lituse (&info, symval, irel)) +++ goto error_return; +++ } +++ else +++ { +++ if (!elf64_sw_64_relax_got_load (&info, symval, irel, r_type)) +++ goto error_return; +++ } +++ break; +++ +++ case R_SW_64_GOTDTPREL: +++ case R_SW_64_GOTTPREL: +++ BFD_ASSERT(info.gotent != NULL); +++ if (!elf64_sw_64_relax_got_load (&info, symval, irel, r_type)) +++ goto error_return; +++ break; +++ +++ case R_SW_64_TLSGD: +++ case R_SW_64_TLSLDM: +++ BFD_ASSERT(info.gotent != NULL); +++ if (!elf64_sw_64_relax_tls_get_addr (&info, symval, irel, +++ r_type == R_SW_64_TLSGD)) +++ goto error_return; +++ break; +++ } +++ } +++ +++ if (isymbuf != NULL +++ && symtab_hdr->contents != (unsigned char *) isymbuf) +++ { +++ if (!link_info->keep_memory) +++ free (isymbuf); +++ else +++ { +++ /* Cache the symbols for elf_link_input_bfd. */ +++ symtab_hdr->contents = (unsigned char *) isymbuf; +++ } +++ } +++ +++ if (info.contents != NULL +++ && elf_section_data (sec)->this_hdr.contents != info.contents) +++ { +++ if (!info.changed_contents && !link_info->keep_memory) +++ free (info.contents); +++ else +++ { +++ /* Cache the section contents for elf_link_input_bfd. */ +++ elf_section_data (sec)->this_hdr.contents = info.contents; +++ } +++ } +++ +++ if (elf_section_data (sec)->relocs != internal_relocs) +++ { +++ if (!info.changed_relocs) +++ free (internal_relocs); +++ else +++ elf_section_data (sec)->relocs = internal_relocs; +++ } +++ +++ *again = info.changed_contents || info.changed_relocs; +++ +++ return TRUE; +++ +++ error_return: +++ if (symtab_hdr->contents != (unsigned char *) isymbuf) +++ free (isymbuf); +++ if (elf_section_data (sec)->this_hdr.contents != info.contents) +++ free (info.contents); +++ if (elf_section_data (sec)->relocs != internal_relocs) +++ free (internal_relocs); +++ return FALSE; +++} +++ +++/* Emit a dynamic relocation for (DYNINDX, RTYPE, ADDEND) at (SEC, OFFSET) +++ into the next available slot in SREL. */ +++ +++static void +++elf64_sw_64_emit_dynrel (bfd *abfd, struct bfd_link_info *info, +++ asection *sec, asection *srel, bfd_vma offset, +++ long dynindx, long rtype, bfd_vma addend) +++{ +++ Elf_Internal_Rela outrel; +++ bfd_byte *loc; +++ +++ BFD_ASSERT (srel != NULL); +++ +++ outrel.r_info = ELF64_R_INFO (dynindx, rtype); +++ outrel.r_addend = addend; +++ +++ offset = _bfd_elf_section_offset (abfd, info, sec, offset); +++ if ((offset | 1) != (bfd_vma) -1) +++ outrel.r_offset = sec->output_section->vma + sec->output_offset + offset; +++ else +++ memset (&outrel, 0, sizeof (outrel)); +++ +++ loc = srel->contents; +++ loc += srel->reloc_count++ * sizeof (Elf64_External_Rela); +++ bfd_elf64_swap_reloca_out (abfd, &outrel, loc); +++ BFD_ASSERT (sizeof (Elf64_External_Rela) * srel->reloc_count <= srel->size); +++} +++ +++/* Relocate an Sw_64 ELF section for a relocatable link. +++ +++ We don't have to change anything unless the reloc is against a section +++ symbol, in which case we have to adjust according to where the section +++ symbol winds up in the output section. */ +++ +++static bfd_boolean +++elf64_sw_64_relocate_section_r (bfd *output_bfd ATTRIBUTE_UNUSED, +++ struct bfd_link_info *info ATTRIBUTE_UNUSED, +++ bfd *input_bfd, asection *input_section, +++ bfd_byte *contents ATTRIBUTE_UNUSED, +++ Elf_Internal_Rela *relocs, +++ Elf_Internal_Sym *local_syms, +++ asection **local_sections) +++{ +++ unsigned long symtab_hdr_sh_info; +++ Elf_Internal_Rela *rel; +++ Elf_Internal_Rela *relend; +++ struct elf_link_hash_entry **sym_hashes; +++ bfd_boolean ret_val = TRUE; +++ +++ symtab_hdr_sh_info = elf_symtab_hdr (input_bfd).sh_info; +++ sym_hashes = elf_sym_hashes (input_bfd); +++ +++ relend = relocs + input_section->reloc_count; +++ for (rel = relocs; rel < relend; rel++) +++ { +++ unsigned long r_symndx; +++ Elf_Internal_Sym *sym; +++ asection *sec; +++ unsigned long r_type; +++ +++ r_type = ELF64_R_TYPE (rel->r_info); +++ if (r_type >= R_SW_64_max) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: unsupported relocation type %#x"), +++ input_bfd, (int) r_type); +++ bfd_set_error (bfd_error_bad_value); +++ ret_val = FALSE; +++ continue; +++ } +++ +++ /* The symbol associated with GPDISP and LITUSE is +++ immaterial. Only the addend is significant. */ +++ if (r_type == R_SW_64_GPDISP || r_type == R_SW_64_LITUSE) +++ continue; +++ +++ r_symndx = ELF64_R_SYM (rel->r_info); +++ if (r_symndx < symtab_hdr_sh_info) +++ { +++ sym = local_syms + r_symndx; +++ sec = local_sections[r_symndx]; +++ } +++ else +++ { +++ struct elf_link_hash_entry *h; +++ +++ h = sym_hashes[r_symndx - symtab_hdr_sh_info]; +++ +++ while (h->root.type == bfd_link_hash_indirect +++ || h->root.type == bfd_link_hash_warning) +++ h = (struct elf_link_hash_entry *) h->root.u.i.link; +++ +++ if (h->root.type != bfd_link_hash_defined +++ && h->root.type != bfd_link_hash_defweak) +++ continue; +++ +++ sym = NULL; +++ sec = h->root.u.def.section; +++ } +++ +++ if (sec != NULL && discarded_section (sec)) +++ RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section, +++ rel, 1, relend, +++ elf64_sw_64_howto_table + r_type, 0, +++ contents); +++ +++ if (sym != NULL && ELF_ST_TYPE (sym->st_info) == STT_SECTION) +++ rel->r_addend += sec->output_offset; +++ } +++ +++ return ret_val; +++} +++ +++/* Relocate an Sw_64 ELF section. */ +++ +++static bfd_boolean +++elf64_sw_64_relocate_section (bfd *output_bfd, struct bfd_link_info *info, +++ bfd *input_bfd, asection *input_section, +++ bfd_byte *contents, Elf_Internal_Rela *relocs, +++ Elf_Internal_Sym *local_syms, +++ asection **local_sections) +++{ +++ Elf_Internal_Shdr *symtab_hdr; +++ Elf_Internal_Rela *rel; +++ Elf_Internal_Rela *relend; +++ asection *sgot, *srel, *srelgot; +++ bfd *dynobj, *gotobj; +++ bfd_vma gp, tp_base, dtp_base; +++ struct sw_64_elf_got_entry **local_got_entries; +++ bfd_boolean ret_val; +++ +++ BFD_ASSERT (is_sw_64_elf (input_bfd)); +++ +++ /* Handle relocatable links with a smaller loop. */ +++ if (bfd_link_relocatable (info)) +++ return elf64_sw_64_relocate_section_r (output_bfd, info, input_bfd, +++ input_section, contents, relocs, +++ local_syms, local_sections); +++ +++ /* This is a final link. */ +++ +++ ret_val = TRUE; +++ +++ symtab_hdr = &elf_symtab_hdr (input_bfd); +++ +++ dynobj = elf_hash_table (info)->dynobj; +++ srelgot = elf_hash_table (info)->srelgot; +++ +++ if (input_section->flags & SEC_ALLOC) +++ { +++ const char *section_name; +++ section_name = (bfd_elf_string_from_elf_section +++ (input_bfd, elf_elfheader(input_bfd)->e_shstrndx, +++ _bfd_elf_single_rel_hdr (input_section)->sh_name)); +++ BFD_ASSERT(section_name != NULL); +++ srel = bfd_get_linker_section (dynobj, section_name); +++ } +++ else +++ srel = NULL; +++ +++ /* Find the gp value for this input bfd. */ +++ gotobj = sw_64_elf_tdata (input_bfd)->gotobj; +++ if (gotobj) +++ { +++ sgot = sw_64_elf_tdata (gotobj)->got; +++ gp = _bfd_get_gp_value (gotobj); +++ if (gp == 0) +++ { +++ gp = (sgot->output_section->vma +++ + sgot->output_offset +++ + 0x8000); +++ _bfd_set_gp_value (gotobj, gp); +++ } +++ } +++ else +++ { +++ sgot = NULL; +++ gp = 0; +++ } +++ +++ local_got_entries = sw_64_elf_tdata(input_bfd)->local_got_entries; +++ +++ if (elf_hash_table (info)->tls_sec != NULL) +++ { +++ dtp_base = sw_64_get_dtprel_base (info); +++ tp_base = sw_64_get_tprel_base (info); +++ } +++ else +++ dtp_base = tp_base = 0; +++ +++ relend = relocs + input_section->reloc_count; +++ for (rel = relocs; rel < relend; rel++) +++ { +++ struct sw_64_elf_link_hash_entry *h = NULL; +++ struct sw_64_elf_got_entry *gotent; +++ bfd_reloc_status_type r; +++ reloc_howto_type *howto; +++ unsigned long r_symndx; +++ Elf_Internal_Sym *sym = NULL; +++ asection *sec = NULL; +++ bfd_vma value; +++ bfd_vma addend; +++ bfd_boolean dynamic_symbol_p; +++ bfd_boolean unresolved_reloc = FALSE; +++ bfd_boolean undef_weak_ref = FALSE; +++ unsigned long r_type; +++ +++ r_type = ELF64_R_TYPE(rel->r_info); +++ if (r_type >= R_SW_64_max) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: unsupported relocation type %#x"), +++ input_bfd, (int) r_type); +++ bfd_set_error (bfd_error_bad_value); +++ ret_val = FALSE; +++ continue; +++ } +++ +++ howto = elf64_sw_64_howto_table + r_type; +++ r_symndx = ELF64_R_SYM(rel->r_info); +++ +++ /* The symbol for a TLSLDM reloc is ignored. Collapse the +++ reloc to the STN_UNDEF (0) symbol so that they all match. */ +++ if (r_type == R_SW_64_TLSLDM) +++ r_symndx = STN_UNDEF; +++ +++ if (r_symndx < symtab_hdr->sh_info) +++ { +++ asection *msec; +++ sym = local_syms + r_symndx; +++ sec = local_sections[r_symndx]; +++ msec = sec; +++ value = _bfd_elf_rela_local_sym (output_bfd, sym, &msec, rel); +++ +++ /* If this is a tp-relative relocation against sym STN_UNDEF (0), +++ this is hackery from relax_section. Force the value to +++ be the tls module base. */ +++ if (r_symndx == STN_UNDEF +++ && (r_type == R_SW_64_TLSLDM +++ || r_type == R_SW_64_GOTTPREL +++ || r_type == R_SW_64_TPREL64 +++ || r_type == R_SW_64_TPRELHI +++ || r_type == R_SW_64_TPRELLO +++ || r_type == R_SW_64_TPREL16)) +++ value = dtp_base; +++ +++ if (local_got_entries) +++ gotent = local_got_entries[r_symndx]; +++ else +++ gotent = NULL; +++ +++ /* Need to adjust local GOT entries' addends for SEC_MERGE +++ unless it has been done already. */ +++ if ((sec->flags & SEC_MERGE) +++ && ELF_ST_TYPE (sym->st_info) == STT_SECTION +++ && sec->sec_info_type == SEC_INFO_TYPE_MERGE +++ && gotent +++ && !gotent->reloc_xlated) +++ { +++ struct sw_64_elf_got_entry *ent; +++ +++ for (ent = gotent; ent; ent = ent->next) +++ { +++ ent->reloc_xlated = 1; +++ if (ent->use_count == 0) +++ continue; +++ msec = sec; +++ ent->addend = +++ _bfd_merged_section_offset (output_bfd, &msec, +++ elf_section_data (sec)-> +++ sec_info, +++ sym->st_value + ent->addend); +++ ent->addend -= sym->st_value; +++ ent->addend += msec->output_section->vma +++ + msec->output_offset +++ - sec->output_section->vma +++ - sec->output_offset; +++ } +++ } +++ +++ dynamic_symbol_p = FALSE; +++ } +++ else +++ { +++ bfd_boolean warned, ignored; +++ struct elf_link_hash_entry *hh; +++ struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (input_bfd); +++ +++ RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel, +++ r_symndx, symtab_hdr, sym_hashes, +++ hh, sec, value, +++ unresolved_reloc, warned, ignored); +++ +++ if (warned) +++ continue; +++ +++ if (value == 0 +++ && ! unresolved_reloc +++ && hh->root.type == bfd_link_hash_undefweak) +++ undef_weak_ref = TRUE; +++ +++ h = (struct sw_64_elf_link_hash_entry *) hh; +++ dynamic_symbol_p = sw_64_elf_dynamic_symbol_p (&h->root, info); +++ gotent = h->got_entries; +++ } +++ +++ if (sec != NULL && discarded_section (sec)) +++ RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section, +++ rel, 1, relend, howto, 0, contents); +++ +++ addend = rel->r_addend; +++ value += addend; +++ +++ /* Search for the proper got entry. */ +++ for (; gotent ; gotent = gotent->next) +++ if (gotent->gotobj == gotobj +++ && gotent->reloc_type == r_type +++ && gotent->addend == addend) +++ break; +++ +++ switch (r_type) +++ { +++ case R_SW_64_GPDISP: +++ { +++ bfd_byte *p_ldah, *p_lda; +++ +++ BFD_ASSERT(gp != 0); +++ +++ value = (input_section->output_section->vma +++ + input_section->output_offset +++ + rel->r_offset); +++ +++ p_ldah = contents + rel->r_offset; +++ p_lda = p_ldah + rel->r_addend; +++ +++ r = elf64_sw_64_do_reloc_gpdisp (input_bfd, gp - value, +++ p_ldah, p_lda); +++ } +++ break; +++ +++ case R_SW_64_LITERAL: +++ BFD_ASSERT(sgot != NULL); +++ BFD_ASSERT(gp != 0); +++ BFD_ASSERT(gotent != NULL); +++ BFD_ASSERT(gotent->use_count >= 1); +++ +++ if (!gotent->reloc_done) +++ { +++ gotent->reloc_done = 1; +++ +++ bfd_put_64 (output_bfd, value, +++ sgot->contents + gotent->got_offset); +++ +++ /* If the symbol has been forced local, output a +++ RELATIVE reloc, otherwise it will be handled in +++ finish_dynamic_symbol. */ +++ if (bfd_link_pic (info) +++ && !dynamic_symbol_p +++ && !undef_weak_ref) +++ elf64_sw_64_emit_dynrel (output_bfd, info, sgot, srelgot, +++ gotent->got_offset, 0, +++ R_SW_64_RELATIVE, value); +++ } +++ +++ value = (sgot->output_section->vma +++ + sgot->output_offset +++ + gotent->got_offset); +++ value -= gp; +++ goto default_reloc; +++ +++ case R_SW_64_GPREL32: +++ case R_SW_64_GPREL16: +++ case R_SW_64_GPRELLOW: +++ if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: gp-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ BFD_ASSERT(gp != 0); +++ value -= gp; +++ goto default_reloc; +++ +++ case R_SW_64_GPRELHIGH: +++ if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: gp-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ BFD_ASSERT(gp != 0); +++ value -= gp; +++ value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1); +++ goto default_reloc; +++ +++ case R_SW_64_HINT: +++ /* A call to a dynamic symbol is definitely out of range of +++ the 16-bit displacement. Don't bother writing anything. */ +++ if (dynamic_symbol_p) +++ { +++ r = bfd_reloc_ok; +++ break; +++ } +++ /* The regular PC-relative stuff measures from the start of +++ the instruction rather than the end. */ +++ value -= 4; +++ goto default_reloc; +++ +++ case R_SW_64_BRADDR: +++ if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: pc-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ /* The regular PC-relative stuff measures from the start of +++ the instruction rather than the end. */ +++ value -= 4; +++ goto default_reloc; +++ +++ case R_SW_64_BRSGP: +++ { +++ int other; +++ const char *name; +++ +++ /* The regular PC-relative stuff measures from the start of +++ the instruction rather than the end. */ +++ value -= 4; +++ +++ /* The source and destination gp must be the same. Note that +++ the source will always have an assigned gp, since we forced +++ one in check_relocs, but that the destination may not, as +++ it might not have had any relocations at all. Also take +++ care not to crash if H is an undefined symbol. */ +++ if (h != NULL && sec != NULL +++ && sw_64_elf_tdata (sec->owner)->gotobj +++ && gotobj != sw_64_elf_tdata (sec->owner)->gotobj) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: change in gp: BRSGP %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ +++ /* The symbol should be marked either NOPV or STD_GPLOAD. */ +++ if (h != NULL) +++ other = h->root.other; +++ else +++ other = sym->st_other; +++ switch (other & STO_SW_64_STD_GPLOAD) +++ { +++ case STO_SW_64_NOPV: +++ break; +++ case STO_SW_64_STD_GPLOAD: +++ value += 8; +++ break; +++ default: +++ if (h != NULL) +++ name = h->root.root.root.string; +++ else +++ { +++ name = (bfd_elf_string_from_elf_section +++ (input_bfd, symtab_hdr->sh_link, sym->st_name)); +++ if (name == NULL) +++ name = _(""); +++ else if (name[0] == 0) +++ name = bfd_section_name (sec); +++ } +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: !samegp reloc against symbol without .prologue: %s"), +++ input_bfd, name); +++ ret_val = FALSE; +++ break; +++ } +++ +++ goto default_reloc; +++ } +++ +++ case R_SW_64_REFLONG: +++ case R_SW_64_REFQUAD: +++ case R_SW_64_DTPREL64: +++ case R_SW_64_TPREL64: +++ { +++ long dynindx, dyntype = r_type; +++ bfd_vma dynaddend; +++ +++ /* Careful here to remember RELATIVE relocations for global +++ variables for symbolic shared objects. */ +++ +++ if (dynamic_symbol_p) +++ { +++ BFD_ASSERT(h->root.dynindx != -1); +++ dynindx = h->root.dynindx; +++ dynaddend = addend; +++ addend = 0, value = 0; +++ } +++ else if (r_type == R_SW_64_DTPREL64) +++ { +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ value -= dtp_base; +++ goto default_reloc; +++ } +++ else if (r_type == R_SW_64_TPREL64) +++ { +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ if (!bfd_link_dll (info)) +++ { +++ value -= tp_base; +++ goto default_reloc; +++ } +++ dynindx = 0; +++ dynaddend = value - dtp_base; +++ } +++ else if (bfd_link_pic (info) +++ && r_symndx != STN_UNDEF +++ && (input_section->flags & SEC_ALLOC) +++ && !undef_weak_ref +++ && !(unresolved_reloc +++ && (_bfd_elf_section_offset (output_bfd, info, +++ input_section, +++ rel->r_offset) +++ == (bfd_vma) -1))) +++ { +++ if (r_type == R_SW_64_REFLONG) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: unhandled dynamic relocation against %s"), +++ input_bfd, +++ h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ dynindx = 0; +++ dyntype = R_SW_64_RELATIVE; +++ dynaddend = value; +++ } +++ else +++ goto default_reloc; +++ +++ if (input_section->flags & SEC_ALLOC) +++ elf64_sw_64_emit_dynrel (output_bfd, info, input_section, +++ srel, rel->r_offset, dynindx, +++ dyntype, dynaddend); +++ } +++ goto default_reloc; +++ +++ case R_SW_64_SREL16: +++ case R_SW_64_SREL32: +++ case R_SW_64_SREL64: +++ if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: pc-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ else if (bfd_link_pic (info) +++ && undef_weak_ref) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: pc-relative relocation against undefined weak symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ +++ +++ /* ??? .eh_frame references to discarded sections will be smashed +++ to relocations against SHN_UNDEF. The .eh_frame format allows +++ NULL to be encoded as 0 in any format, so this works here. */ +++ if (r_symndx == STN_UNDEF +++ || (unresolved_reloc +++ && _bfd_elf_section_offset (output_bfd, info, +++ input_section, +++ rel->r_offset) == (bfd_vma) -1)) +++ howto = (elf64_sw_64_howto_table +++ + (r_type - R_SW_64_SREL32 + R_SW_64_REFLONG)); +++ goto default_reloc; +++ +++ case R_SW_64_TLSLDM: +++ /* Ignore the symbol for the relocation. The result is always +++ the current module. */ +++ dynamic_symbol_p = 0; +++ /* FALLTHRU */ +++ +++ case R_SW_64_TLSGD: +++ if (!gotent->reloc_done) +++ { +++ gotent->reloc_done = 1; +++ +++ /* Note that the module index for the main program is 1. */ +++ bfd_put_64 (output_bfd, +++ !bfd_link_pic (info) && !dynamic_symbol_p, +++ sgot->contents + gotent->got_offset); +++ +++ /* If the symbol has been forced local, output a +++ DTPMOD64 reloc, otherwise it will be handled in +++ finish_dynamic_symbol. */ +++ if (bfd_link_pic (info) && !dynamic_symbol_p) +++ elf64_sw_64_emit_dynrel (output_bfd, info, sgot, srelgot, +++ gotent->got_offset, 0, +++ R_SW_64_DTPMOD64, 0); +++ +++ if (dynamic_symbol_p || r_type == R_SW_64_TLSLDM) +++ value = 0; +++ else +++ { +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ value -= dtp_base; +++ } +++ bfd_put_64 (output_bfd, value, +++ sgot->contents + gotent->got_offset + 8); +++ } +++ +++ value = (sgot->output_section->vma +++ + sgot->output_offset +++ + gotent->got_offset); +++ value -= gp; +++ goto default_reloc; +++ +++ case R_SW_64_DTPRELHI: +++ case R_SW_64_DTPRELLO: +++ case R_SW_64_DTPREL16: +++ if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: dtp-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ value -= dtp_base; +++ if (r_type == R_SW_64_DTPRELHI) +++ value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1); +++ goto default_reloc; +++ +++ case R_SW_64_TPRELHI: +++ case R_SW_64_TPRELLO: +++ case R_SW_64_TPREL16: +++ if (bfd_link_dll (info)) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: TLS local exec code cannot be linked into shared objects"), +++ input_bfd); +++ ret_val = FALSE; +++ } +++ else if (dynamic_symbol_p) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("%pB: tp-relative relocation against dynamic symbol %s"), +++ input_bfd, h->root.root.root.string); +++ ret_val = FALSE; +++ } +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ value -= tp_base; +++ if (r_type == R_SW_64_TPRELHI) +++ value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1); +++ goto default_reloc; +++ +++ case R_SW_64_GOTDTPREL: +++ case R_SW_64_GOTTPREL: +++ BFD_ASSERT(sgot != NULL); +++ BFD_ASSERT(gp != 0); +++ BFD_ASSERT(gotent != NULL); +++ BFD_ASSERT(gotent->use_count >= 1); +++ +++ if (!gotent->reloc_done) +++ { +++ gotent->reloc_done = 1; +++ +++ if (dynamic_symbol_p) +++ value = 0; +++ else +++ { +++ BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL); +++ if (r_type == R_SW_64_GOTDTPREL) +++ value -= dtp_base; +++ else if (bfd_link_executable (info)) +++ value -= tp_base; +++ else +++ { +++ elf64_sw_64_emit_dynrel (output_bfd, info, sgot, srelgot, +++ gotent->got_offset, 0, +++ R_SW_64_TPREL64, +++ value - dtp_base); +++ value = 0; +++ } +++ } +++ bfd_put_64 (output_bfd, value, +++ sgot->contents + gotent->got_offset); +++ } +++ +++ value = (sgot->output_section->vma +++ + sgot->output_offset +++ + gotent->got_offset); +++ value -= gp; +++ goto default_reloc; +++ +++ default: +++ default_reloc: +++ r = _bfd_final_link_relocate (howto, input_bfd, input_section, +++ contents, rel->r_offset, value, 0); +++ break; +++ } +++ +++ switch (r) +++ { +++ case bfd_reloc_ok: +++ break; +++ +++ case bfd_reloc_overflow: +++ { +++ const char *name; +++ +++ /* Don't warn if the overflow is due to pc relative reloc +++ against discarded section. Section optimization code should +++ handle it. */ +++ +++ if (r_symndx < symtab_hdr->sh_info +++ && sec != NULL && howto->pc_relative +++ && discarded_section (sec)) +++ break; +++ +++ if (h != NULL) +++ name = NULL; +++ else +++ { +++ name = (bfd_elf_string_from_elf_section +++ (input_bfd, symtab_hdr->sh_link, sym->st_name)); +++ if (name == NULL) +++ return FALSE; +++ if (*name == '\0') +++ name = bfd_section_name (sec); +++ } +++ (*info->callbacks->reloc_overflow) +++ (info, (h ? &h->root.root : NULL), name, howto->name, +++ (bfd_vma) 0, input_bfd, input_section, rel->r_offset); +++ } +++ break; +++ +++ default: +++ case bfd_reloc_outofrange: +++ abort (); +++ } +++ } +++ +++ return ret_val; +++} +++ +++/* Finish up dynamic symbol handling. We set the contents of various +++ dynamic sections here. */ +++ +++static bfd_boolean +++elf64_sw_64_finish_dynamic_symbol (bfd *output_bfd, struct bfd_link_info *info, +++ struct elf_link_hash_entry *h, +++ Elf_Internal_Sym *sym) +++{ +++ struct sw_64_elf_link_hash_entry *ah = (struct sw_64_elf_link_hash_entry *)h; +++ +++ if (h->needs_plt) +++ { +++ /* Fill in the .plt entry for this symbol. */ +++ asection *splt, *sgot, *srel; +++ Elf_Internal_Rela outrel; +++ bfd_byte *loc; +++ bfd_vma got_addr, plt_addr; +++ bfd_vma plt_index; +++ struct sw_64_elf_got_entry *gotent; +++ +++ BFD_ASSERT (h->dynindx != -1); +++ +++ splt = elf_hash_table (info)->splt; +++ BFD_ASSERT (splt != NULL); +++ srel = elf_hash_table (info)->srelplt; +++ BFD_ASSERT (srel != NULL); +++ +++ for (gotent = ah->got_entries; gotent ; gotent = gotent->next) +++ if (gotent->reloc_type == R_SW_64_LITERAL +++ && gotent->use_count > 0) +++ { +++ unsigned int insn; +++ int disp; +++ +++ sgot = sw_64_elf_tdata (gotent->gotobj)->got; +++ BFD_ASSERT (sgot != NULL); +++ +++ BFD_ASSERT (gotent->got_offset != -1); +++ BFD_ASSERT (gotent->plt_offset != -1); +++ +++ got_addr = (sgot->output_section->vma +++ + sgot->output_offset +++ + gotent->got_offset); +++ plt_addr = (splt->output_section->vma +++ + splt->output_offset +++ + gotent->plt_offset); +++ +++ plt_index = (gotent->plt_offset-PLT_HEADER_SIZE) / PLT_ENTRY_SIZE; +++ +++ /* Fill in the entry in the procedure linkage table. */ +++ if (elf64_sw_64_use_secureplt) +++ { +++ disp = (PLT_HEADER_SIZE - 4) - (gotent->plt_offset + 4); +++ insn = INSN_AD (INSN_BR, 31, disp); +++ bfd_put_32 (output_bfd, insn, +++ splt->contents + gotent->plt_offset); +++ +++ plt_index = ((gotent->plt_offset - NEW_PLT_HEADER_SIZE) +++ / NEW_PLT_ENTRY_SIZE); +++ } +++ else +++ { +++ disp = -(gotent->plt_offset + 4); +++ insn = INSN_AD (INSN_BR, 28, disp); +++ bfd_put_32 (output_bfd, insn, +++ splt->contents + gotent->plt_offset); +++ bfd_put_32 (output_bfd, INSN_UNOP, +++ splt->contents + gotent->plt_offset + 4); +++ bfd_put_32 (output_bfd, INSN_UNOP, +++ splt->contents + gotent->plt_offset + 8); +++ +++ plt_index = ((gotent->plt_offset - OLD_PLT_HEADER_SIZE) +++ / OLD_PLT_ENTRY_SIZE); +++ } +++ +++ /* Fill in the entry in the .rela.plt section. */ +++ outrel.r_offset = got_addr; +++ outrel.r_info = ELF64_R_INFO(h->dynindx, R_SW_64_JMP_SLOT); +++ outrel.r_addend = 0; +++ +++ loc = srel->contents + plt_index * sizeof (Elf64_External_Rela); +++ bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc); +++ +++ /* Fill in the entry in the .got. */ +++ bfd_put_64 (output_bfd, plt_addr, +++ sgot->contents + gotent->got_offset); +++ } +++ } +++ else if (sw_64_elf_dynamic_symbol_p (h, info)) +++ { +++ /* Fill in the dynamic relocations for this symbol's .got entries. */ +++ asection *srel; +++ struct sw_64_elf_got_entry *gotent; +++ +++ srel = elf_hash_table (info)->srelgot; +++ BFD_ASSERT (srel != NULL); +++ +++ for (gotent = ((struct sw_64_elf_link_hash_entry *) h)->got_entries; +++ gotent != NULL; +++ gotent = gotent->next) +++ { +++ asection *sgot; +++ long r_type; +++ +++ if (gotent->use_count == 0) +++ continue; +++ +++ sgot = sw_64_elf_tdata (gotent->gotobj)->got; +++ +++ r_type = gotent->reloc_type; +++ switch (r_type) +++ { +++ case R_SW_64_LITERAL: +++ r_type = R_SW_64_GLOB_DAT; +++ break; +++ case R_SW_64_TLSGD: +++ r_type = R_SW_64_DTPMOD64; +++ break; +++ case R_SW_64_GOTDTPREL: +++ r_type = R_SW_64_DTPREL64; +++ break; +++ case R_SW_64_GOTTPREL: +++ r_type = R_SW_64_TPREL64; +++ break; +++ case R_SW_64_TLSLDM: +++ default: +++ abort (); +++ } +++ +++ elf64_sw_64_emit_dynrel (output_bfd, info, sgot, srel, +++ gotent->got_offset, h->dynindx, +++ r_type, gotent->addend); +++ +++ if (gotent->reloc_type == R_SW_64_TLSGD) +++ elf64_sw_64_emit_dynrel (output_bfd, info, sgot, srel, +++ gotent->got_offset + 8, h->dynindx, +++ R_SW_64_DTPREL64, gotent->addend); +++ } +++ } +++ +++ /* Mark some specially defined symbols as absolute. */ +++ if (h == elf_hash_table (info)->hdynamic +++ || h == elf_hash_table (info)->hgot +++ || h == elf_hash_table (info)->hplt) +++ sym->st_shndx = SHN_ABS; +++ +++ return TRUE; +++} +++ +++/* Finish up the dynamic sections. */ +++ +++static bfd_boolean +++elf64_sw_64_finish_dynamic_sections (bfd *output_bfd, +++ struct bfd_link_info *info) +++{ +++ bfd *dynobj; +++ asection *sdyn; +++ +++ dynobj = elf_hash_table (info)->dynobj; +++ sdyn = bfd_get_linker_section (dynobj, ".dynamic"); +++ +++ if (elf_hash_table (info)->dynamic_sections_created) +++ { +++ asection *splt, *sgotplt, *srelaplt; +++ Elf64_External_Dyn *dyncon, *dynconend; +++ bfd_vma plt_vma, gotplt_vma; +++ +++ splt = elf_hash_table (info)->splt; +++ srelaplt = elf_hash_table (info)->srelplt; +++ BFD_ASSERT (splt != NULL && sdyn != NULL); +++ +++ plt_vma = splt->output_section->vma + splt->output_offset; +++ +++ gotplt_vma = 0; +++ if (elf64_sw_64_use_secureplt) +++ { +++ sgotplt = elf_hash_table (info)->sgotplt; +++ BFD_ASSERT (sgotplt != NULL); +++ if (sgotplt->size > 0) +++ gotplt_vma = sgotplt->output_section->vma + sgotplt->output_offset; +++ } +++ +++ dyncon = (Elf64_External_Dyn *) sdyn->contents; +++ dynconend = (Elf64_External_Dyn *) (sdyn->contents + sdyn->size); +++ for (; dyncon < dynconend; dyncon++) +++ { +++ Elf_Internal_Dyn dyn; +++ +++ bfd_elf64_swap_dyn_in (dynobj, dyncon, &dyn); +++ +++ switch (dyn.d_tag) +++ { +++ case DT_PLTGOT: +++ dyn.d_un.d_ptr +++ = elf64_sw_64_use_secureplt ? gotplt_vma : plt_vma; +++ break; +++ case DT_PLTRELSZ: +++ dyn.d_un.d_val = srelaplt ? srelaplt->size : 0; +++ break; +++ case DT_JMPREL: +++ dyn.d_un.d_ptr = srelaplt ? (srelaplt->output_section->vma +++ + srelaplt->output_offset) : 0; +++ break; +++ } +++ +++ bfd_elf64_swap_dyn_out (output_bfd, &dyn, dyncon); +++ } +++ +++ /* Initialize the plt header. */ +++ if (splt->size > 0) +++ { +++ unsigned int insn; +++ int ofs; +++ +++ if (elf64_sw_64_use_secureplt) +++ { +++ ofs = gotplt_vma - (plt_vma + PLT_HEADER_SIZE); +++ +++ insn = INSN_ABC (INSN_SUBQ, 27, 28, 25); +++ bfd_put_32 (output_bfd, insn, splt->contents); +++ +++ insn = INSN_ABO (INSN_LDAH, 28, 28, (ofs + 0x8000) >> 16); +++ bfd_put_32 (output_bfd, insn, splt->contents + 4); +++ +++ insn = INSN_ABC (INSN_S4SUBQ, 25, 25, 25); +++ bfd_put_32 (output_bfd, insn, splt->contents + 8); +++ +++ insn = INSN_ABO (INSN_LDA, 28, 28, ofs); +++ bfd_put_32 (output_bfd, insn, splt->contents + 12); +++ +++ insn = INSN_ABO (INSN_LDQ, 27, 28, 0); +++ bfd_put_32 (output_bfd, insn, splt->contents + 16); +++ +++ insn = INSN_ABC (INSN_ADDQ, 25, 25, 25); +++ bfd_put_32 (output_bfd, insn, splt->contents + 20); +++ +++ insn = INSN_ABO (INSN_LDQ, 28, 28, 8); +++ bfd_put_32 (output_bfd, insn, splt->contents + 24); +++ +++ insn = INSN_AB (INSN_JMP, 31, 27); +++ bfd_put_32 (output_bfd, insn, splt->contents + 28); +++ +++ insn = INSN_AD (INSN_BR, 28, -PLT_HEADER_SIZE); +++ bfd_put_32 (output_bfd, insn, splt->contents + 32); +++ } +++ else +++ { +++ insn = INSN_AD (INSN_BR, 27, 0); /* br $27, .+4 */ +++ bfd_put_32 (output_bfd, insn, splt->contents); +++ +++ insn = INSN_ABO (INSN_LDQ, 27, 27, 12); +++ bfd_put_32 (output_bfd, insn, splt->contents + 4); +++ +++ insn = INSN_UNOP; +++ bfd_put_32 (output_bfd, insn, splt->contents + 8); +++ +++ insn = INSN_AB (INSN_JMP, 27, 27); +++ bfd_put_32 (output_bfd, insn, splt->contents + 12); +++ +++ /* The next two words will be filled in by ld.so. */ +++ bfd_put_64 (output_bfd, 0, splt->contents + 16); +++ bfd_put_64 (output_bfd, 0, splt->contents + 24); +++ } +++ +++ elf_section_data (splt->output_section)->this_hdr.sh_entsize = 0; +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* We need to use a special link routine to handle the .mdebug section. +++ We need to merge all instances of these sections together, not write +++ them all out sequentially. */ +++ +++static bfd_boolean +++elf64_sw_64_final_link (bfd *abfd, struct bfd_link_info *info) +++{ +++ asection *o; +++ struct bfd_link_order *p; +++ asection *mdebug_sec; +++ struct ecoff_debug_info debug; +++ const struct ecoff_debug_swap *swap +++ = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap; +++ HDRR *symhdr = &debug.symbolic_header; +++ void * mdebug_handle = NULL; +++ struct sw_64_elf_link_hash_table * htab; +++ +++ htab = sw_64_elf_hash_table (info); +++ if (htab == NULL) +++ return FALSE; +++ +++ /* Go through the sections and collect the mdebug information. */ +++ mdebug_sec = NULL; +++ for (o = abfd->sections; o != (asection *) NULL; o = o->next) +++ { +++ if (strcmp (o->name, ".mdebug") == 0) +++ { +++ struct extsym_info einfo; +++ +++ /* We have found the .mdebug section in the output file. +++ Look through all the link_orders comprising it and merge +++ the information together. */ +++ symhdr->magic = swap->sym_magic; +++ /* FIXME: What should the version stamp be? */ +++ symhdr->vstamp = 0; +++ symhdr->ilineMax = 0; +++ symhdr->cbLine = 0; +++ symhdr->idnMax = 0; +++ symhdr->ipdMax = 0; +++ symhdr->isymMax = 0; +++ symhdr->ioptMax = 0; +++ symhdr->iauxMax = 0; +++ symhdr->issMax = 0; +++ symhdr->issExtMax = 0; +++ symhdr->ifdMax = 0; +++ symhdr->crfd = 0; +++ symhdr->iextMax = 0; +++ +++ /* We accumulate the debugging information itself in the +++ debug_info structure. */ +++ debug.line = NULL; +++ debug.external_dnr = NULL; +++ debug.external_pdr = NULL; +++ debug.external_sym = NULL; +++ debug.external_opt = NULL; +++ debug.external_aux = NULL; +++ debug.ss = NULL; +++ debug.ssext = debug.ssext_end = NULL; +++ debug.external_fdr = NULL; +++ debug.external_rfd = NULL; +++ debug.external_ext = debug.external_ext_end = NULL; +++ +++ mdebug_handle = bfd_ecoff_debug_init (abfd, &debug, swap, info); +++ if (mdebug_handle == NULL) +++ return FALSE; +++ +++ if (1) +++ { +++ asection *s; +++ EXTR esym; +++ bfd_vma last = 0; +++ unsigned int i; +++ static const char * const name[] = +++ { +++ ".text", ".init", ".fini", ".data", +++ ".rodata", ".sdata", ".sbss", ".bss" +++ }; +++ static const int sc[] = { scText, scInit, scFini, scData, +++ scRData, scSData, scSBss, scBss }; +++ +++ esym.jmptbl = 0; +++ esym.cobol_main = 0; +++ esym.weakext = 0; +++ esym.reserved = 0; +++ esym.ifd = ifdNil; +++ esym.asym.iss = issNil; +++ esym.asym.st = stLocal; +++ esym.asym.reserved = 0; +++ esym.asym.index = indexNil; +++ for (i = 0; i < 8; i++) +++ { +++ esym.asym.sc = sc[i]; +++ s = bfd_get_section_by_name (abfd, name[i]); +++ if (s != NULL) +++ { +++ esym.asym.value = s->vma; +++ last = s->vma + s->size; +++ } +++ else +++ esym.asym.value = last; +++ +++ if (! bfd_ecoff_debug_one_external (abfd, &debug, swap, +++ name[i], &esym)) +++ return FALSE; +++ } +++ } +++ +++ for (p = o->map_head.link_order; +++ p != (struct bfd_link_order *) NULL; +++ p = p->next) +++ { +++ asection *input_section; +++ bfd *input_bfd; +++ const struct ecoff_debug_swap *input_swap; +++ struct ecoff_debug_info input_debug; +++ char *eraw_src; +++ char *eraw_end; +++ +++ if (p->type != bfd_indirect_link_order) +++ { +++ if (p->type == bfd_data_link_order) +++ continue; +++ abort (); +++ } +++ +++ input_section = p->u.indirect.section; +++ input_bfd = input_section->owner; +++ +++ if (! is_sw_64_elf (input_bfd)) +++ /* I don't know what a non SW_64 ELF bfd would be +++ doing with a .mdebug section, but I don't really +++ want to deal with it. */ +++ continue; +++ +++ input_swap = (get_elf_backend_data (input_bfd) +++ ->elf_backend_ecoff_debug_swap); +++ +++ BFD_ASSERT (p->size == input_section->size); +++ +++ /* The ECOFF linking code expects that we have already +++ read in the debugging information and set up an +++ ecoff_debug_info structure, so we do that now. */ +++ if (!elf64_sw_64_read_ecoff_info (input_bfd, input_section, +++ &input_debug)) +++ return FALSE; +++ +++ if (! (bfd_ecoff_debug_accumulate +++ (mdebug_handle, abfd, &debug, swap, input_bfd, +++ &input_debug, input_swap, info))) +++ return FALSE; +++ +++ /* Loop through the external symbols. For each one with +++ interesting information, try to find the symbol in +++ the linker global hash table and save the information +++ for the output external symbols. */ +++ eraw_src = (char *) input_debug.external_ext; +++ eraw_end = (eraw_src +++ + (input_debug.symbolic_header.iextMax +++ * input_swap->external_ext_size)); +++ for (; +++ eraw_src < eraw_end; +++ eraw_src += input_swap->external_ext_size) +++ { +++ EXTR ext; +++ const char *name; +++ struct sw_64_elf_link_hash_entry *h; +++ +++ (*input_swap->swap_ext_in) (input_bfd, eraw_src, &ext); +++ if (ext.asym.sc == scNil +++ || ext.asym.sc == scUndefined +++ || ext.asym.sc == scSUndefined) +++ continue; +++ +++ name = input_debug.ssext + ext.asym.iss; +++ h = sw_64_elf_link_hash_lookup (htab, name, FALSE, FALSE, TRUE); +++ if (h == NULL || h->esym.ifd != -2) +++ continue; +++ +++ if (ext.ifd != -1) +++ { +++ BFD_ASSERT (ext.ifd +++ < input_debug.symbolic_header.ifdMax); +++ ext.ifd = input_debug.ifdmap[ext.ifd]; +++ } +++ +++ h->esym = ext; +++ } +++ +++ /* Free up the information we just read. */ +++ free (input_debug.line); +++ free (input_debug.external_dnr); +++ free (input_debug.external_pdr); +++ free (input_debug.external_sym); +++ free (input_debug.external_opt); +++ free (input_debug.external_aux); +++ free (input_debug.ss); +++ free (input_debug.ssext); +++ free (input_debug.external_fdr); +++ free (input_debug.external_rfd); +++ free (input_debug.external_ext); +++ +++ /* Hack: reset the SEC_HAS_CONTENTS flag so that +++ elf_link_input_bfd ignores this section. */ +++ input_section->flags &=~ SEC_HAS_CONTENTS; +++ } +++ +++ /* Build the external symbol information. */ +++ einfo.abfd = abfd; +++ einfo.info = info; +++ einfo.debug = &debug; +++ einfo.swap = swap; +++ einfo.failed = FALSE; +++ elf_link_hash_traverse (elf_hash_table (info), +++ elf64_sw_64_output_extsym, +++ &einfo); +++ if (einfo.failed) +++ return FALSE; +++ +++ /* Set the size of the .mdebug section. */ +++ o->size = bfd_ecoff_debug_size (abfd, &debug, swap); +++ +++ /* Skip this section later on (I don't think this currently +++ matters, but someday it might). */ +++ o->map_head.link_order = (struct bfd_link_order *) NULL; +++ +++ mdebug_sec = o; +++ } +++ } +++ +++ /* Invoke the regular ELF backend linker to do all the work. */ +++ if (! bfd_elf_final_link (abfd, info)) +++ return FALSE; +++ +++ /* Now write out the computed sections. */ +++ +++ /* The .got subsections... */ +++ { +++ bfd *i, *dynobj = elf_hash_table(info)->dynobj; +++ for (i = htab->got_list; +++ i != NULL; +++ i = sw_64_elf_tdata(i)->got_link_next) +++ { +++ asection *sgot; +++ +++ /* elf_bfd_final_link already did everything in dynobj. */ +++ if (i == dynobj) +++ continue; +++ +++ sgot = sw_64_elf_tdata(i)->got; +++ if (! bfd_set_section_contents (abfd, sgot->output_section, +++ sgot->contents, +++ (file_ptr) sgot->output_offset, +++ sgot->size)) +++ return FALSE; +++ } +++ } +++ +++ if (mdebug_sec != (asection *) NULL) +++ { +++ BFD_ASSERT (abfd->output_has_begun); +++ if (! bfd_ecoff_write_accumulated_debug (mdebug_handle, abfd, &debug, +++ swap, info, +++ mdebug_sec->filepos)) +++ return FALSE; +++ +++ bfd_ecoff_debug_free (mdebug_handle, abfd, &debug, swap, info); +++ } +++ +++ return TRUE; +++} +++ +++static enum elf_reloc_type_class +++elf64_sw_64_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED, +++ const asection *rel_sec ATTRIBUTE_UNUSED, +++ const Elf_Internal_Rela *rela) +++{ +++ switch ((int) ELF64_R_TYPE (rela->r_info)) +++ { +++ case R_SW_64_RELATIVE: +++ return reloc_class_relative; +++ case R_SW_64_JMP_SLOT: +++ return reloc_class_plt; +++ case R_SW_64_COPY: +++ return reloc_class_copy; +++ default: +++ return reloc_class_normal; +++ } +++} +++ +++static const struct bfd_elf_special_section elf64_sw_64_special_sections[] = +++{ +++ { STRING_COMMA_LEN (".sbss"), -2, SHT_NOBITS, SHF_ALLOC + SHF_WRITE + SHF_SW_64_GPREL }, +++ { STRING_COMMA_LEN (".sdata"), -2, SHT_PROGBITS, SHF_ALLOC + SHF_WRITE + SHF_SW_64_GPREL }, +++ { NULL, 0, 0, 0, 0 } +++}; +++ +++/* ECOFF swapping routines. These are used when dealing with the +++ .mdebug section, which is in the ECOFF debugging format. Copied +++ from elf32-mips.c. */ +++static const struct ecoff_debug_swap +++elf64_sw_64_ecoff_debug_swap = +++{ +++ /* Symbol table magic number. */ +++ magicSym2, +++ /* Alignment of debugging information. E.g., 4. */ +++ 8, +++ /* Sizes of external symbolic information. */ +++ sizeof (struct hdr_ext), +++ sizeof (struct dnr_ext), +++ sizeof (struct pdr_ext), +++ sizeof (struct sym_ext), +++ sizeof (struct opt_ext), +++ sizeof (struct fdr_ext), +++ sizeof (struct rfd_ext), +++ sizeof (struct ext_ext), +++ /* Functions to swap in external symbolic data. */ +++ ecoff_swap_hdr_in, +++ ecoff_swap_dnr_in, +++ ecoff_swap_pdr_in, +++ ecoff_swap_sym_in, +++ ecoff_swap_opt_in, +++ ecoff_swap_fdr_in, +++ ecoff_swap_rfd_in, +++ ecoff_swap_ext_in, +++ _bfd_ecoff_swap_tir_in, +++ _bfd_ecoff_swap_rndx_in, +++ /* Functions to swap out external symbolic data. */ +++ ecoff_swap_hdr_out, +++ ecoff_swap_dnr_out, +++ ecoff_swap_pdr_out, +++ ecoff_swap_sym_out, +++ ecoff_swap_opt_out, +++ ecoff_swap_fdr_out, +++ ecoff_swap_rfd_out, +++ ecoff_swap_ext_out, +++ _bfd_ecoff_swap_tir_out, +++ _bfd_ecoff_swap_rndx_out, +++ /* Function to read in symbolic data. */ +++ elf64_sw_64_read_ecoff_info +++}; +++ +++/* Use a non-standard hash bucket size of 8. */ +++ +++static const struct elf_size_info sw_64_elf_size_info = +++{ +++ sizeof (Elf64_External_Ehdr), +++ sizeof (Elf64_External_Phdr), +++ sizeof (Elf64_External_Shdr), +++ sizeof (Elf64_External_Rel), +++ sizeof (Elf64_External_Rela), +++ sizeof (Elf64_External_Sym), +++ sizeof (Elf64_External_Dyn), +++ sizeof (Elf_External_Note), +++ 8, +++ 1, +++ 64, 3, +++ ELFCLASS64, EV_CURRENT, +++ bfd_elf64_write_out_phdrs, +++ bfd_elf64_write_shdrs_and_ehdr, +++ bfd_elf64_checksum_contents, +++ bfd_elf64_write_relocs, +++ bfd_elf64_swap_symbol_in, +++ bfd_elf64_swap_symbol_out, +++ bfd_elf64_slurp_reloc_table, +++ bfd_elf64_slurp_symbol_table, +++ bfd_elf64_swap_dyn_in, +++ bfd_elf64_swap_dyn_out, +++ bfd_elf64_swap_reloc_in, +++ bfd_elf64_swap_reloc_out, +++ bfd_elf64_swap_reloca_in, +++ bfd_elf64_swap_reloca_out +++}; +++ +++#define TARGET_LITTLE_SYM sw_64_elf64_vec +++#define TARGET_LITTLE_NAME "elf64-sw_64" +++#define ELF_ARCH bfd_arch_sw_64 +++#define ELF_TARGET_ID SW_64_ELF_DATA +++#define ELF_MACHINE_CODE EM_SW_64 +++#define ELF_MAXPAGESIZE 0x10000 +++#define ELF_COMMONPAGESIZE 0x2000 +++ +++#define bfd_elf64_bfd_link_hash_table_create \ +++ elf64_sw_64_bfd_link_hash_table_create +++ +++#define bfd_elf64_bfd_reloc_type_lookup \ +++ elf64_sw_64_bfd_reloc_type_lookup +++#define bfd_elf64_bfd_reloc_name_lookup \ +++ elf64_sw_64_bfd_reloc_name_lookup +++#define elf_info_to_howto \ +++ elf64_sw_64_info_to_howto +++ +++#define bfd_elf64_mkobject \ +++ elf64_sw_64_mkobject +++#define elf_backend_object_p \ +++ elf64_sw_64_object_p +++ +++#define elf_backend_section_from_shdr \ +++ elf64_sw_64_section_from_shdr +++#define elf_backend_section_flags \ +++ elf64_sw_64_section_flags +++#define elf_backend_fake_sections \ +++ elf64_sw_64_fake_sections +++ +++#define bfd_elf64_bfd_is_local_label_name \ +++ elf64_sw_64_is_local_label_name +++#define bfd_elf64_find_nearest_line \ +++ elf64_sw_64_find_nearest_line +++#define bfd_elf64_bfd_relax_section \ +++ elf64_sw_64_relax_section +++ +++#define elf_backend_add_symbol_hook \ +++ elf64_sw_64_add_symbol_hook +++#define elf_backend_relocs_compatible \ +++ _bfd_elf_relocs_compatible +++#define elf_backend_sort_relocs_p \ +++ elf64_sw_64_sort_relocs_p +++#define elf_backend_check_relocs \ +++ elf64_sw_64_check_relocs +++#define elf_backend_create_dynamic_sections \ +++ elf64_sw_64_create_dynamic_sections +++#define elf_backend_adjust_dynamic_symbol \ +++ elf64_sw_64_adjust_dynamic_symbol +++#define elf_backend_merge_symbol_attribute \ +++ elf64_sw_64_merge_symbol_attribute +++#define elf_backend_copy_indirect_symbol \ +++ elf64_sw_64_copy_indirect_symbol +++#define elf_backend_always_size_sections \ +++ elf64_sw_64_always_size_sections +++#define elf_backend_size_dynamic_sections \ +++ elf64_sw_64_size_dynamic_sections +++#define elf_backend_omit_section_dynsym \ +++ _bfd_elf_omit_section_dynsym_all +++#define elf_backend_relocate_section \ +++ elf64_sw_64_relocate_section +++#define elf_backend_finish_dynamic_symbol \ +++ elf64_sw_64_finish_dynamic_symbol +++#define elf_backend_finish_dynamic_sections \ +++ elf64_sw_64_finish_dynamic_sections +++#define bfd_elf64_bfd_final_link \ +++ elf64_sw_64_final_link +++#define elf_backend_reloc_type_class \ +++ elf64_sw_64_reloc_type_class +++ +++#define elf_backend_can_gc_sections 1 +++#define elf_backend_gc_mark_hook elf64_sw_64_gc_mark_hook +++ +++#define elf_backend_ecoff_debug_swap \ +++ &elf64_sw_64_ecoff_debug_swap +++ +++#define elf_backend_size_info \ +++ sw_64_elf_size_info +++ +++#define elf_backend_special_sections \ +++ elf64_sw_64_special_sections +++ +++#define elf_backend_strip_zero_sized_dynamic_sections \ +++ _bfd_elf_strip_zero_sized_dynamic_sections +++ +++/* A few constants that determine how the .plt section is set up. */ +++#define elf_backend_want_got_plt 0 +++#define elf_backend_plt_readonly 0 +++#define elf_backend_want_plt_sym 1 +++#define elf_backend_got_header_size 0 +++#define elf_backend_dtrel_excludes_plt 1 +++ +++#include "elf64-target.h" +++ +++/* FreeBSD support. */ +++ +++#undef TARGET_LITTLE_SYM +++#define TARGET_LITTLE_SYM sw_64_elf64_fbsd_vec +++#undef TARGET_LITTLE_NAME +++#define TARGET_LITTLE_NAME "elf64-sw_64-freebsd" +++#undef ELF_OSABI +++#define ELF_OSABI ELFOSABI_FREEBSD +++ +++/* The kernel recognizes executables as valid only if they carry a +++ "FreeBSD" label in the ELF header. So we put this label on all +++ executables and (for simplicity) also all other object files. */ +++ +++static bfd_boolean +++elf64_sw_64_fbsd_init_file_header (bfd *abfd, struct bfd_link_info *info) +++{ +++ Elf_Internal_Ehdr * i_ehdrp; /* ELF file header, internal form. */ +++ +++ if (!_bfd_elf_init_file_header (abfd, info)) +++ return FALSE; +++ +++ i_ehdrp = elf_elfheader (abfd); +++ +++ /* Put an ABI label supported by FreeBSD >= 4.1. */ +++ i_ehdrp->e_ident[EI_OSABI] = get_elf_backend_data (abfd)->elf_osabi; +++#ifdef OLD_FREEBSD_ABI_LABEL +++ /* The ABI label supported by FreeBSD <= 4.0 is quite nonstandard. */ +++ memcpy (&i_ehdrp->e_ident[EI_ABIVERSION], "FreeBSD", 8); +++#endif +++ return TRUE; +++} +++ +++#undef elf_backend_init_file_header +++#define elf_backend_init_file_header \ +++ elf64_sw_64_fbsd_init_file_header +++ +++#undef elf64_bed +++#define elf64_bed elf64_sw_64_fbsd_bed +++ +++#include "elf64-target.h" ++diff -Nuar gdb-10.2/bfd/elf-bfd.h gdb-10.2/bfd/elf-bfd.h ++--- gdb-10.2/bfd/elf-bfd.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/elf-bfd.h 2025-04-16 17:06:51.912086800 +0800 ++@@ -27,6 +27,8 @@ ++ #include "elf/internal.h" ++ #include "bfdlink.h" ++ +++#include +++ ++ #ifdef __cplusplus ++ extern "C" { ++ #endif ++@@ -488,6 +490,7 @@ ++ { ++ AARCH64_ELF_DATA = 1, ++ ALPHA_ELF_DATA, +++ SW_64_ELF_DATA, ++ ARC_ELF_DATA, ++ ARM_ELF_DATA, ++ AVR_ELF_DATA, ++diff -Nuar gdb-10.2/bfd/elf-bfd.h.orig gdb-10.2/bfd/elf-bfd.h.orig ++--- gdb-10.2/bfd/elf-bfd.h.orig 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/elf-bfd.h.orig 2025-04-16 17:06:41.932086800 +0800 ++@@ -0,0 +1,3093 @@ +++/* BFD back-end data structures for ELF files. +++ Copyright (C) 1992-2020 Free Software Foundation, Inc. +++ Written by Cygnus Support. +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++#ifndef _LIBELF_H_ +++#define _LIBELF_H_ 1 +++ +++#include "elf/common.h" +++#include "elf/external.h" +++#include "elf/internal.h" +++#include "bfdlink.h" +++ +++#include +++ +++#ifdef __cplusplus +++extern "C" { +++#endif +++ +++/* The number of entries in a section is its size divided by the size +++ of a single entry. This is normally only applicable to reloc and +++ symbol table sections. +++ PR 9934: It is possible to have relocations that do not refer to +++ symbols, thus it is also possible to have a relocation section in +++ an object file, but no symbol table. */ +++#define NUM_SHDR_ENTRIES(shdr) ((shdr)->sh_entsize > 0 ? (shdr)->sh_size / (shdr)->sh_entsize : 0) +++ +++/* If size isn't specified as 64 or 32, NAME macro should fail. */ +++#ifndef NAME +++#if ARCH_SIZE == 64 +++#define NAME(x, y) x ## 64 ## _ ## y +++#endif +++#if ARCH_SIZE == 32 +++#define NAME(x, y) x ## 32 ## _ ## y +++#endif +++#endif +++ +++#ifndef NAME +++#define NAME(x, y) x ## NOSIZE ## _ ## y +++#endif +++ +++#define ElfNAME(X) NAME(Elf,X) +++#define elfNAME(X) NAME(elf,X) +++ +++/* Information held for an ELF symbol. The first field is the +++ corresponding asymbol. Every symbol is an ELF file is actually a +++ pointer to this structure, although it is often handled as a +++ pointer to an asymbol. */ +++ +++typedef struct +++{ +++ /* The BFD symbol. */ +++ asymbol symbol; +++ /* ELF symbol information. */ +++ Elf_Internal_Sym internal_elf_sym; +++ /* Backend specific information. */ +++ union +++ { +++ unsigned int hppa_arg_reloc; +++ void *mips_extr; +++ void *any; +++ } +++ tc_data; +++ +++ /* Version information. This is from an Elf_Internal_Versym +++ structure in a SHT_GNU_versym section. It is zero if there is no +++ version information. */ +++ unsigned short version; +++ +++} elf_symbol_type; +++ +++struct elf_strtab_hash; +++struct got_entry; +++struct plt_entry; +++ +++union gotplt_union +++ { +++ bfd_signed_vma refcount; +++ bfd_vma offset; +++ struct got_entry *glist; +++ struct plt_entry *plist; +++ }; +++ +++struct elf_link_virtual_table_entry +++ { +++ /* Virtual table entry use information. This array is nominally of size +++ size/sizeof(target_void_pointer), though we have to be able to assume +++ and track a size while the symbol is still undefined. It is indexed +++ via offset/sizeof(target_void_pointer). */ +++ size_t size; +++ bfd_boolean *used; +++ +++ /* Virtual table derivation info. */ +++ struct elf_link_hash_entry *parent; +++ }; +++ +++/* ELF symbol version. */ +++enum elf_symbol_version +++ { +++ unknown = 0, +++ unversioned, +++ versioned, +++ versioned_hidden +++ }; +++ +++/* ELF linker hash table entries. */ +++ +++struct elf_link_hash_entry +++{ +++ struct bfd_link_hash_entry root; +++ +++ /* Symbol index in output file. This is initialized to -1. It is +++ set to -2 if the symbol is used by a reloc. It is set to -3 if +++ this symbol is defined in a discarded section. */ +++ long indx; +++ +++ /* Symbol index as a dynamic symbol. Initialized to -1, and remains +++ -1 if this is not a dynamic symbol. */ +++ /* ??? Note that this is consistently used as a synonym for tests +++ against whether we can perform various simplifying transformations +++ to the code. (E.g. changing a pc-relative jump to a PLT entry +++ into a pc-relative jump to the target function.) That test, which +++ is often relatively complex, and someplaces wrong or incomplete, +++ should really be replaced by a predicate in elflink.c. +++ +++ End result: this field -1 does not indicate that the symbol is +++ not in the dynamic symbol table, but rather that the symbol is +++ not visible outside this DSO. */ +++ long dynindx; +++ +++ /* If this symbol requires an entry in the global offset table, the +++ processor specific backend uses this field to track usage and +++ final offset. Two schemes are supported: The first assumes that +++ a symbol may only have one GOT entry, and uses REFCOUNT until +++ size_dynamic_sections, at which point the contents of the .got is +++ fixed. Afterward, if OFFSET is -1, then the symbol does not +++ require a global offset table entry. The second scheme allows +++ multiple GOT entries per symbol, managed via a linked list +++ pointed to by GLIST. */ +++ union gotplt_union got; +++ +++ /* Same, but tracks a procedure linkage table entry. */ +++ union gotplt_union plt; +++ +++ /* Symbol size. NB: All fields starting from here are cleared by +++ _bfd_elf_link_hash_newfunc. */ +++ bfd_size_type size; +++ +++ /* Track dynamic relocs copied for this symbol. */ +++ struct elf_dyn_relocs *dyn_relocs; +++ +++ /* Symbol type (STT_NOTYPE, STT_OBJECT, etc.). */ +++ unsigned int type : 8; +++ +++ /* Symbol st_other value, symbol visibility. */ +++ unsigned int other : 8; +++ +++ /* The symbol's st_target_internal value (see Elf_Internal_Sym). */ +++ unsigned int target_internal : 8; +++ +++ /* Symbol is referenced by a non-shared object (other than the object +++ in which it is defined). */ +++ unsigned int ref_regular : 1; +++ /* Symbol is defined by a non-shared object. */ +++ unsigned int def_regular : 1; +++ /* Symbol is referenced by a shared object. */ +++ unsigned int ref_dynamic : 1; +++ /* Symbol is defined by a shared object. */ +++ unsigned int def_dynamic : 1; +++ /* Symbol has a non-weak reference from a non-shared object (other than +++ the object in which it is defined). */ +++ unsigned int ref_regular_nonweak : 1; +++ /* Dynamic symbol has been adjustd. */ +++ unsigned int dynamic_adjusted : 1; +++ /* Symbol needs a copy reloc. */ +++ unsigned int needs_copy : 1; +++ /* Symbol needs a procedure linkage table entry. */ +++ unsigned int needs_plt : 1; +++ /* Symbol appears in a non-ELF input file. */ +++ unsigned int non_elf : 1; +++ /* Symbol version information. */ +++ ENUM_BITFIELD (elf_symbol_version) versioned : 2; +++ /* Symbol was forced to local scope due to a version script file. */ +++ unsigned int forced_local : 1; +++ /* Symbol was forced to be dynamic due to a version script file. */ +++ unsigned int dynamic : 1; +++ /* Symbol was marked during garbage collection. */ +++ unsigned int mark : 1; +++ /* Symbol is referenced by a non-GOT/non-PLT relocation. This is +++ not currently set by all the backends. */ +++ unsigned int non_got_ref : 1; +++ /* Symbol has a definition in a shared object. +++ FIXME: There is no real need for this field if def_dynamic is never +++ cleared and all places that test def_dynamic also test def_regular. */ +++ unsigned int dynamic_def : 1; +++ /* Symbol has a non-weak reference from a shared object. */ +++ unsigned int ref_dynamic_nonweak : 1; +++ /* Symbol is referenced with a relocation where C/C++ pointer equality +++ matters. */ +++ unsigned int pointer_equality_needed : 1; +++ /* Symbol is a unique global symbol. */ +++ unsigned int unique_global : 1; +++ /* Symbol is defined by a shared library with non-default visibility +++ in a read/write section. */ +++ unsigned int protected_def : 1; +++ /* Symbol is __start_SECNAME or __stop_SECNAME to mark section +++ SECNAME. */ +++ unsigned int start_stop : 1; +++ /* Symbol is or was a weak defined symbol from a dynamic object with +++ a strong defined symbol alias. U.ALIAS points to a list of aliases, +++ the definition having is_weakalias clear. */ +++ unsigned int is_weakalias : 1; +++ +++ /* String table index in .dynstr if this is a dynamic symbol. */ +++ unsigned long dynstr_index; +++ +++ union +++ { +++ /* Points to a circular list of non-function symbol aliases. */ +++ struct elf_link_hash_entry *alias; +++ +++ /* Hash value of the name computed using the ELF hash function. +++ Used part way through size_dynamic_sections, after we've finished +++ with aliases. */ +++ unsigned long elf_hash_value; +++ } u; +++ +++ /* Version information. */ +++ union +++ { +++ /* This field is used for a symbol which is not defined in a +++ regular object. It points to the version information read in +++ from the dynamic object. */ +++ Elf_Internal_Verdef *verdef; +++ /* This field is used for a symbol which is defined in a regular +++ object. It is set up in size_dynamic_sections. It points to +++ the version information we should write out for this symbol. */ +++ struct bfd_elf_version_tree *vertree; +++ } verinfo; +++ +++ union +++ { +++ /* For __start_SECNAME and __stop_SECNAME symbols, record the first +++ input section whose section name is SECNAME. */ +++ asection *start_stop_section; +++ +++ /* Vtable information. */ +++ struct elf_link_virtual_table_entry *vtable; +++ } u2; +++}; +++ +++/* Return the strong definition for a weak symbol with aliases. */ +++ +++static inline struct elf_link_hash_entry * +++weakdef (struct elf_link_hash_entry *h) +++{ +++ while (h->is_weakalias) +++ h = h->u.alias; +++ return h; +++} +++ +++/* Will references to this symbol always reference the symbol +++ in this object? */ +++#define SYMBOL_REFERENCES_LOCAL(INFO, H) \ +++ _bfd_elf_symbol_refs_local_p (H, INFO, 0) +++ +++/* Will _calls_ to this symbol always call the version in this object? */ +++#define SYMBOL_CALLS_LOCAL(INFO, H) \ +++ _bfd_elf_symbol_refs_local_p (H, INFO, 1) +++ +++/* Whether an undefined weak symbol should resolve to its link-time +++ value, even in PIC or PIE objects. */ +++#define UNDEFWEAK_NO_DYNAMIC_RELOC(INFO, H) \ +++ ((H)->root.type == bfd_link_hash_undefweak \ +++ && (ELF_ST_VISIBILITY ((H)->other) != STV_DEFAULT \ +++ || (INFO)->dynamic_undefined_weak == 0)) +++ +++/* Common symbols that are turned into definitions don't have the +++ DEF_REGULAR flag set, so they might appear to be undefined. +++ Symbols defined in linker scripts also don't have DEF_REGULAR set. */ +++#define ELF_COMMON_DEF_P(H) \ +++ (!(H)->def_regular \ +++ && !(H)->def_dynamic \ +++ && (H)->root.type == bfd_link_hash_defined) +++ +++/* Records local symbols to be emitted in the dynamic symbol table. */ +++ +++struct elf_link_local_dynamic_entry +++{ +++ struct elf_link_local_dynamic_entry *next; +++ +++ /* The input bfd this symbol came from. */ +++ bfd *input_bfd; +++ +++ /* The index of the local symbol being copied. */ +++ long input_indx; +++ +++ /* The index in the outgoing dynamic symbol table. */ +++ long dynindx; +++ +++ /* A copy of the input symbol. */ +++ Elf_Internal_Sym isym; +++}; +++ +++struct elf_link_loaded_list +++{ +++ struct elf_link_loaded_list *next; +++ bfd *abfd; +++}; +++ +++/* Structures used by the eh_frame optimization code. */ +++struct eh_cie_fde +++{ +++ union { +++ struct { +++ /* If REMOVED == 1, this is the CIE that the FDE originally used. +++ The CIE belongs to the same .eh_frame input section as the FDE. +++ +++ If REMOVED == 0, this is the CIE that we have chosen to use for +++ the output FDE. The CIE's REMOVED field is also 0, but the CIE +++ might belong to a different .eh_frame input section from the FDE. +++ +++ May be NULL to signify that the FDE should be discarded. */ +++ struct eh_cie_fde *cie_inf; +++ struct eh_cie_fde *next_for_section; +++ } fde; +++ struct { +++ /* CIEs have three states: +++ +++ - REMOVED && !MERGED: Slated for removal because we haven't yet +++ proven that an FDE needs it. FULL_CIE, if nonnull, points to +++ more detailed information about the CIE. +++ +++ - REMOVED && MERGED: We have merged this CIE with MERGED_WITH, +++ which may not belong to the same input section. +++ +++ - !REMOVED: We have decided to keep this CIE. SEC is the +++ .eh_frame input section that contains the CIE. */ +++ union { +++ struct cie *full_cie; +++ struct eh_cie_fde *merged_with; +++ asection *sec; +++ } u; +++ +++ /* The offset of the personality data from the start of the CIE, +++ or 0 if the CIE doesn't have any. */ +++ unsigned int personality_offset : 8; +++ +++ /* Length of augmentation. aug_str_len is the length of the +++ string including null terminator. aug_data_len is the length +++ of the rest up to the initial insns. */ +++ unsigned int aug_str_len : 3; +++ unsigned int aug_data_len : 5; +++ +++ /* True if we have marked relocations associated with this CIE. */ +++ unsigned int gc_mark : 1; +++ +++ /* True if we have decided to turn an absolute LSDA encoding into +++ a PC-relative one. */ +++ unsigned int make_lsda_relative : 1; +++ +++ /* True if we have decided to turn an absolute personality +++ encoding into a PC-relative one. */ +++ unsigned int make_per_encoding_relative : 1; +++ +++ /* True if the CIE contains personality data and if that +++ data uses a PC-relative encoding. Always true when +++ make_per_encoding_relative is. */ +++ unsigned int per_encoding_relative : 1; +++ +++ /* True if the CIE contains personality data aligned to a +++ multiple of eight bytes. */ +++ unsigned int per_encoding_aligned8 : 1; +++ +++ /* True if we need to add an 'R' (FDE encoding) entry to the +++ CIE's augmentation data. */ +++ unsigned int add_fde_encoding : 1; +++ +++ /* True if we have merged this CIE with another. */ +++ unsigned int merged : 1; +++ +++ /* Unused bits. */ +++ unsigned int pad1 : 9; +++ } cie; +++ } u; +++ unsigned int reloc_index; +++ unsigned int size; +++ unsigned int offset; +++ unsigned int new_offset; +++ unsigned int fde_encoding : 8; +++ unsigned int lsda_encoding : 8; +++ unsigned int lsda_offset : 8; +++ +++ /* True if this entry represents a CIE, false if it represents an FDE. */ +++ unsigned int cie : 1; +++ +++ /* True if this entry is currently marked for removal. */ +++ unsigned int removed : 1; +++ +++ /* True if we need to add a 'z' (augmentation size) entry to the CIE's +++ augmentation data, and an associated byte to each of the CIE's FDEs. */ +++ unsigned int add_augmentation_size : 1; +++ +++ /* True if we have decided to convert absolute FDE relocations into +++ relative ones. This applies to the first relocation in the FDE, +++ which is against the code that the FDE describes. */ +++ unsigned int make_relative : 1; +++ +++ /* Unused bits. */ +++ unsigned int pad1 : 4; +++ +++ unsigned int *set_loc; +++}; +++ +++struct eh_frame_sec_info +++{ +++ unsigned int count; +++ struct cie *cies; +++ struct eh_cie_fde entry[1]; +++}; +++ +++struct eh_frame_array_ent +++{ +++ bfd_vma initial_loc; +++ bfd_size_type range; +++ bfd_vma fde; +++}; +++ +++struct htab; +++ +++#define DWARF2_EH_HDR 1 +++#define COMPACT_EH_HDR 2 +++ +++/* Endian-neutral code indicating that a function cannot be unwound. */ +++#define COMPACT_EH_CANT_UNWIND_OPCODE 0x015d5d01 +++ +++struct dwarf_eh_frame_hdr_info +++{ +++ struct htab *cies; +++ unsigned int fde_count; +++ /* TRUE if .eh_frame_hdr should contain the sorted search table. +++ We build it if we successfully read all .eh_frame input sections +++ and recognize them. */ +++ bfd_boolean table; +++ struct eh_frame_array_ent *array; +++}; +++ +++struct compact_eh_frame_hdr_info +++{ +++ unsigned int allocated_entries; +++ /* eh_frame_entry fragments. */ +++ asection **entries; +++}; +++ +++struct eh_frame_hdr_info +++{ +++ asection *hdr_sec; +++ unsigned int array_count; +++ bfd_boolean frame_hdr_is_compact; +++ union +++ { +++ struct dwarf_eh_frame_hdr_info dwarf; +++ struct compact_eh_frame_hdr_info compact; +++ } +++ u; +++}; +++ +++/* Enum used to identify target specific extensions to the elf_obj_tdata +++ and elf_link_hash_table structures. Note the enums deliberately start +++ from 1 so that we can detect an uninitialized field. The generic value +++ is last so that additions to this enum do not need to modify more than +++ one line. */ +++enum elf_target_id +++{ +++ AARCH64_ELF_DATA = 1, +++ ALPHA_ELF_DATA, +++ ARC_ELF_DATA, +++ ARM_ELF_DATA, +++ AVR_ELF_DATA, +++ BFIN_ELF_DATA, +++ CRIS_ELF_DATA, +++ CSKY_ELF_DATA, +++ FRV_ELF_DATA, +++ HPPA32_ELF_DATA, +++ HPPA64_ELF_DATA, +++ I386_ELF_DATA, +++ IA64_ELF_DATA, +++ LM32_ELF_DATA, +++ M32R_ELF_DATA, +++ M68HC11_ELF_DATA, +++ M68K_ELF_DATA, +++ METAG_ELF_DATA, +++ MICROBLAZE_ELF_DATA, +++ MIPS_ELF_DATA, +++ MN10300_ELF_DATA, +++ NDS32_ELF_DATA, +++ NIOS2_ELF_DATA, +++ OR1K_ELF_DATA, +++ PPC32_ELF_DATA, +++ PPC64_ELF_DATA, +++ PRU_ELF_DATA, +++ S390_ELF_DATA, +++ SH_ELF_DATA, +++ SPARC_ELF_DATA, +++ SPU_ELF_DATA, +++ TIC6X_ELF_DATA, +++ X86_64_ELF_DATA, +++ XTENSA_ELF_DATA, +++ TILEGX_ELF_DATA, +++ TILEPRO_ELF_DATA, +++ RISCV_ELF_DATA, +++ GENERIC_ELF_DATA +++}; +++ +++struct elf_sym_strtab +++{ +++ Elf_Internal_Sym sym; +++ unsigned long dest_index; +++ unsigned long destshndx_index; +++}; +++ +++struct bfd_link_needed_list +++{ +++ struct bfd_link_needed_list *next; +++ bfd *by; +++ const char *name; +++}; +++ +++enum elf_target_os +++{ +++ is_normal, +++ is_symbian, /* Symbian OS. */ +++ is_solaris, /* Solaris. */ +++ is_vxworks, /* VxWorks. */ +++ is_nacl /* Native Client. */ +++}; +++ +++/* Used by bfd_sym_from_r_symndx to cache a small number of local +++ symbols. */ +++#define LOCAL_SYM_CACHE_SIZE 32 +++struct sym_cache +++{ +++ bfd *abfd; +++ unsigned long indx[LOCAL_SYM_CACHE_SIZE]; +++ Elf_Internal_Sym sym[LOCAL_SYM_CACHE_SIZE]; +++}; +++ +++/* ELF linker hash table. */ +++ +++struct elf_link_hash_table +++{ +++ struct bfd_link_hash_table root; +++ +++ /* An identifier used to distinguish different target +++ specific extensions to this structure. */ +++ enum elf_target_id hash_table_id; +++ +++ /* Whether we have created the special dynamic sections required +++ when linking against or generating a shared object. */ +++ bfd_boolean dynamic_sections_created; +++ +++ /* Whether dynamic relocations are present. */ +++ bfd_boolean dynamic_relocs; +++ +++ /* True if this target has relocatable executables, so needs dynamic +++ section symbols. */ +++ bfd_boolean is_relocatable_executable; +++ +++ /* TRUE if there are IFUNC resolvers. */ +++ bfd_boolean ifunc_resolvers; +++ +++ /* TRUE if DT_PLTGOT is a required dynamic tag. */ +++ bfd_boolean dt_pltgot_required; +++ +++ /* TRUE if DT_JMPREL is a required dynamic tag. */ +++ bfd_boolean dt_jmprel_required; +++ +++ /* The BFD used to hold special sections created by the linker. +++ This will be the first BFD found which requires these sections to +++ be created. */ +++ bfd *dynobj; +++ +++ /* The value to use when initialising got.refcount/offset and +++ plt.refcount/offset in an elf_link_hash_entry. Set to zero when +++ the values are refcounts. Set to init_got_offset/init_plt_offset +++ in size_dynamic_sections when the values may be offsets. */ +++ union gotplt_union init_got_refcount; +++ union gotplt_union init_plt_refcount; +++ +++ /* The value to use for got.refcount/offset and plt.refcount/offset +++ when the values may be offsets. Normally (bfd_vma) -1. */ +++ union gotplt_union init_got_offset; +++ union gotplt_union init_plt_offset; +++ +++ /* The number of symbols found in the link which is intended for the +++ mandatory DT_SYMTAB tag (.dynsym section) in .dynamic section. */ +++ bfd_size_type dynsymcount; +++ bfd_size_type local_dynsymcount; +++ +++ /* The string table of dynamic symbols, which becomes the .dynstr +++ section. */ +++ struct elf_strtab_hash *dynstr; +++ +++ /* The number of symbol strings found in the link which must be put +++ into the .strtab section. */ +++ bfd_size_type strtabcount; +++ +++ /* The array size of the symbol string table, which becomes the +++ .strtab section. */ +++ bfd_size_type strtabsize; +++ +++ /* The array of strings, which becomes the .strtab section. */ +++ struct elf_sym_strtab *strtab; +++ +++ /* The number of buckets in the hash table in the .hash section. +++ This is based on the number of dynamic symbols. */ +++ bfd_size_type bucketcount; +++ +++ /* A linked list of DT_NEEDED names found in dynamic objects +++ included in the link. */ +++ struct bfd_link_needed_list *needed; +++ +++ /* Sections in the output bfd that provides a section symbol +++ to be used by relocations emitted against local symbols. +++ Most targets will not use data_index_section. */ +++ asection *text_index_section; +++ asection *data_index_section; +++ +++ /* The _GLOBAL_OFFSET_TABLE_ symbol. */ +++ struct elf_link_hash_entry *hgot; +++ +++ /* The _PROCEDURE_LINKAGE_TABLE_ symbol. */ +++ struct elf_link_hash_entry *hplt; +++ +++ /* The _DYNAMIC symbol. */ +++ struct elf_link_hash_entry *hdynamic; +++ +++ /* A pointer to information used to merge SEC_MERGE sections. */ +++ void *merge_info; +++ +++ /* Used to link stabs in sections. */ +++ struct stab_info stab_info; +++ +++ /* Used by eh_frame code when editing .eh_frame. */ +++ struct eh_frame_hdr_info eh_info; +++ +++ /* A linked list of local symbols to be added to .dynsym. */ +++ struct elf_link_local_dynamic_entry *dynlocal; +++ +++ /* A linked list of DT_RPATH/DT_RUNPATH names found in dynamic +++ objects included in the link. */ +++ struct bfd_link_needed_list *runpath; +++ +++ /* Cached first output tls section and size of PT_TLS segment. */ +++ asection *tls_sec; +++ bfd_size_type tls_size; /* Bytes. */ +++ +++ /* The offset into splt of the PLT entry for the TLS descriptor +++ resolver. Special values are 0, if not necessary (or not found +++ to be necessary yet), and -1 if needed but not determined +++ yet. */ +++ bfd_vma tlsdesc_plt; +++ +++ /* The GOT offset for the lazy trampoline. Communicated to the +++ loader via DT_TLSDESC_GOT. The magic value (bfd_vma) -1 +++ indicates an offset is not allocated. */ +++ bfd_vma tlsdesc_got; +++ +++ /* Target OS for linker output. */ +++ enum elf_target_os target_os; +++ +++ /* A linked list of dynamic BFD's loaded in the link. */ +++ struct elf_link_loaded_list *dyn_loaded; +++ +++ /* Small local sym cache. */ +++ struct sym_cache sym_cache; +++ +++ /* Short-cuts to get to dynamic linker sections. */ +++ asection *sgot; +++ asection *sgotplt; +++ asection *srelgot; +++ asection *splt; +++ asection *srelplt; +++ asection *sdynbss; +++ asection *srelbss; +++ asection *sdynrelro; +++ asection *sreldynrelro; +++ asection *igotplt; +++ asection *iplt; +++ asection *irelplt; +++ asection *irelifunc; +++ asection *dynsym; +++}; +++ +++/* Look up an entry in an ELF linker hash table. */ +++ +++#define elf_link_hash_lookup(table, string, create, copy, follow) \ +++ ((struct elf_link_hash_entry *) \ +++ bfd_link_hash_lookup (&(table)->root, (string), (create), \ +++ (copy), (follow))) +++ +++/* Traverse an ELF linker hash table. */ +++ +++#define elf_link_hash_traverse(table, func, info) \ +++ (bfd_link_hash_traverse \ +++ (&(table)->root, \ +++ (bfd_boolean (*) (struct bfd_link_hash_entry *, void *)) (func), \ +++ (info))) +++ +++/* Get the ELF linker hash table from a link_info structure. */ +++ +++#define elf_hash_table(p) ((struct elf_link_hash_table *) ((p)->hash)) +++ +++#define elf_hash_table_id(table) ((table) -> hash_table_id) +++ +++/* Returns TRUE if the hash table is a struct elf_link_hash_table. */ +++#define is_elf_hash_table(htab) \ +++ (((struct bfd_link_hash_table *) (htab))->type == bfd_link_elf_hash_table) +++ +++/* Constant information held for an ELF backend. */ +++ +++struct elf_size_info { +++ unsigned char sizeof_ehdr, sizeof_phdr, sizeof_shdr; +++ unsigned char sizeof_rel, sizeof_rela, sizeof_sym, sizeof_dyn, sizeof_note; +++ +++ /* The size of entries in the .hash section. */ +++ unsigned char sizeof_hash_entry; +++ +++ /* The number of internal relocations to allocate per external +++ relocation entry. */ +++ unsigned char int_rels_per_ext_rel; +++ /* We use some fixed size arrays. This should be large enough to +++ handle all back-ends. */ +++#define MAX_INT_RELS_PER_EXT_REL 3 +++ +++ unsigned char arch_size, log_file_align; +++ unsigned char elfclass, ev_current; +++ int (*write_out_phdrs) +++ (bfd *, const Elf_Internal_Phdr *, unsigned int); +++ bfd_boolean +++ (*write_shdrs_and_ehdr) (bfd *); +++ bfd_boolean (*checksum_contents) +++ (bfd * , void (*) (const void *, size_t, void *), void *); +++ void (*write_relocs) +++ (bfd *, asection *, void *); +++ bfd_boolean (*swap_symbol_in) +++ (bfd *, const void *, const void *, Elf_Internal_Sym *); +++ void (*swap_symbol_out) +++ (bfd *, const Elf_Internal_Sym *, void *, void *); +++ bfd_boolean (*slurp_reloc_table) +++ (bfd *, asection *, asymbol **, bfd_boolean); +++ long (*slurp_symbol_table) +++ (bfd *, asymbol **, bfd_boolean); +++ void (*swap_dyn_in) +++ (bfd *, const void *, Elf_Internal_Dyn *); +++ void (*swap_dyn_out) +++ (bfd *, const Elf_Internal_Dyn *, void *); +++ +++ /* This function is called to swap in a REL relocation. If an +++ external relocation corresponds to more than one internal +++ relocation, then all relocations are swapped in at once. */ +++ void (*swap_reloc_in) +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++ +++ /* This function is called to swap out a REL relocation. */ +++ void (*swap_reloc_out) +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++ +++ /* This function is called to swap in a RELA relocation. If an +++ external relocation corresponds to more than one internal +++ relocation, then all relocations are swapped in at once. */ +++ void (*swap_reloca_in) +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++ +++ /* This function is called to swap out a RELA relocation. */ +++ void (*swap_reloca_out) +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++}; +++ +++#define elf_symbol_from(ABFD,S) \ +++ (((S)->the_bfd != NULL \ +++ && (S)->the_bfd->xvec->flavour == bfd_target_elf_flavour \ +++ && (S)->the_bfd->tdata.elf_obj_data != 0) \ +++ ? (elf_symbol_type *) (S) \ +++ : 0) +++ +++enum elf_reloc_type_class { +++ reloc_class_normal, +++ reloc_class_relative, +++ reloc_class_copy, +++ reloc_class_ifunc, +++ reloc_class_plt +++}; +++ +++struct elf_reloc_cookie +++{ +++ Elf_Internal_Rela *rels, *rel, *relend; +++ Elf_Internal_Sym *locsyms; +++ bfd *abfd; +++ size_t locsymcount; +++ size_t extsymoff; +++ struct elf_link_hash_entry **sym_hashes; +++ int r_sym_shift; +++ bfd_boolean bad_symtab; +++}; +++ +++/* The level of IRIX compatibility we're striving for. */ +++ +++typedef enum { +++ ict_none, +++ ict_irix5, +++ ict_irix6 +++} irix_compat_t; +++ +++/* Mapping of ELF section names and types. */ +++struct bfd_elf_special_section +++{ +++ const char *prefix; +++ unsigned int prefix_length; +++ /* 0 means name must match PREFIX exactly. +++ -1 means name must start with PREFIX followed by an arbitrary string. +++ -2 means name must match PREFIX exactly or consist of PREFIX followed +++ by a dot then anything. +++ > 0 means name must start with the first PREFIX_LENGTH chars of +++ PREFIX and finish with the last SUFFIX_LENGTH chars of PREFIX. */ +++ signed int suffix_length; +++ unsigned int type; +++ bfd_vma attr; +++}; +++ +++enum action_discarded +++ { +++ COMPLAIN = 1, +++ PRETEND = 2 +++ }; +++ +++typedef asection * (*elf_gc_mark_hook_fn) +++ (asection *, struct bfd_link_info *, Elf_Internal_Rela *, +++ struct elf_link_hash_entry *, Elf_Internal_Sym *); +++ +++enum elf_property_kind +++ { +++ /* A new property. */ +++ property_unknown = 0, +++ /* A property ignored by backend. */ +++ property_ignored, +++ /* A corrupt property reported by backend. */ +++ property_corrupt, +++ /* A property should be removed due to property merge. */ +++ property_remove, +++ /* A property which is a number. */ +++ property_number +++ }; +++ +++typedef struct elf_property +++{ +++ unsigned int pr_type; +++ unsigned int pr_datasz; +++ union +++ { +++ /* For property_number, this is a number. */ +++ bfd_vma number; +++ /* Add a new one if elf_property_kind is updated. */ +++ } u; +++ enum elf_property_kind pr_kind; +++} elf_property; +++ +++typedef struct elf_property_list +++{ +++ struct elf_property_list *next; +++ struct elf_property property; +++} elf_property_list; +++ +++struct bfd_elf_section_reloc_data; +++ +++struct elf_backend_data +++{ +++ /* The architecture for this backend. */ +++ enum bfd_architecture arch; +++ +++ /* An identifier used to distinguish different target specific +++ extensions to elf_obj_tdata and elf_link_hash_table structures. */ +++ enum elf_target_id target_id; +++ +++ /* Target OS. */ +++ enum elf_target_os target_os; +++ +++ /* The ELF machine code (EM_xxxx) for this backend. */ +++ int elf_machine_code; +++ +++ /* EI_OSABI. */ +++ int elf_osabi; +++ +++ /* The maximum page size for this backend. */ +++ bfd_vma maxpagesize; +++ +++ /* The minimum page size for this backend. An input object will not be +++ considered page aligned unless its sections are correctly aligned for +++ pages at least this large. May be smaller than maxpagesize. */ +++ bfd_vma minpagesize; +++ +++ /* The common page size for this backend. */ +++ bfd_vma commonpagesize; +++ +++ /* The value of commonpagesize to use when -z relro for this backend. */ +++ bfd_vma relropagesize; +++ +++ /* The BFD flags applied to sections created for dynamic linking. */ +++ flagword dynamic_sec_flags; +++ +++ /* Architecture-specific data for this backend. +++ This is actually a pointer to some type like struct elf_ARCH_data. */ +++ const void *arch_data; +++ +++ /* A function to translate an ELF RELA relocation to a BFD arelent +++ structure. Returns TRUE upon success, FALSE otherwise. */ +++ bfd_boolean (*elf_info_to_howto) +++ (bfd *, arelent *, Elf_Internal_Rela *); +++ +++ /* A function to translate an ELF REL relocation to a BFD arelent +++ structure. Returns TRUE upon success, FALSE otherwise. */ +++ bfd_boolean (*elf_info_to_howto_rel) +++ (bfd *, arelent *, Elf_Internal_Rela *); +++ +++ /* A function to determine whether a symbol is global when +++ partitioning the symbol table into local and global symbols. +++ This should be NULL for most targets, in which case the correct +++ thing will be done. MIPS ELF, at least on the Irix 5, has +++ special requirements. */ +++ bfd_boolean (*elf_backend_sym_is_global) +++ (bfd *, asymbol *); +++ +++ /* The remaining functions are hooks which are called only if they +++ are not NULL. */ +++ +++ /* A function to permit a backend specific check on whether a +++ particular BFD format is relevant for an object file, and to +++ permit the backend to set any global information it wishes. When +++ this is called elf_elfheader is set, but anything else should be +++ used with caution. If this returns FALSE, the check_format +++ routine will return a bfd_error_wrong_format error. */ +++ bfd_boolean (*elf_backend_object_p) +++ (bfd *); +++ +++ /* A function to do additional symbol processing when reading the +++ ELF symbol table. This is where any processor-specific special +++ section indices are handled. */ +++ void (*elf_backend_symbol_processing) +++ (bfd *, asymbol *); +++ +++ /* A function to do additional symbol processing after reading the +++ entire ELF symbol table. */ +++ bfd_boolean (*elf_backend_symbol_table_processing) +++ (bfd *, elf_symbol_type *, unsigned int); +++ +++ /* A function to set the type of the info field. Processor-specific +++ types should be handled here. */ +++ int (*elf_backend_get_symbol_type) +++ (Elf_Internal_Sym *, int); +++ +++ /* A function to return the linker hash table entry of a symbol that +++ might be satisfied by an archive symbol. */ +++ struct elf_link_hash_entry * (*elf_backend_archive_symbol_lookup) +++ (bfd *, struct bfd_link_info *, const char *); +++ +++ /* Return true if local section symbols should have a non-null st_name. +++ NULL implies false. */ +++ bfd_boolean (*elf_backend_name_local_section_symbols) +++ (bfd *); +++ +++ /* A function to do additional processing on the ELF section header +++ just before writing it out. This is used to set the flags and +++ type fields for some sections, or to actually write out data for +++ unusual sections. */ +++ bfd_boolean (*elf_backend_section_processing) +++ (bfd *, Elf_Internal_Shdr *); +++ +++ /* A function to handle unusual section types when creating BFD +++ sections from ELF sections. */ +++ bfd_boolean (*elf_backend_section_from_shdr) +++ (bfd *, Elf_Internal_Shdr *, const char *, int); +++ +++ /* A function to convert machine dependent ELF section header flags to +++ BFD internal section header flags. */ +++ bfd_boolean (*elf_backend_section_flags) +++ (const Elf_Internal_Shdr *); +++ +++ /* A function that returns a struct containing ELF section flags and +++ type for the given BFD section. */ +++ const struct bfd_elf_special_section * (*get_sec_type_attr) +++ (bfd *, asection *); +++ +++ /* A function to handle unusual program segment types when creating BFD +++ sections from ELF program segments. */ +++ bfd_boolean (*elf_backend_section_from_phdr) +++ (bfd *, Elf_Internal_Phdr *, int, const char *); +++ +++ /* A function to set up the ELF section header for a BFD section in +++ preparation for writing it out. This is where the flags and type +++ fields are set for unusual sections. */ +++ bfd_boolean (*elf_backend_fake_sections) +++ (bfd *, Elf_Internal_Shdr *, asection *); +++ +++ /* A function to get the ELF section index for a BFD section. If +++ this returns TRUE, the section was found. If it is a normal ELF +++ section, *RETVAL should be left unchanged. If it is not a normal +++ ELF section *RETVAL should be set to the SHN_xxxx index. */ +++ bfd_boolean (*elf_backend_section_from_bfd_section) +++ (bfd *, asection *, int *retval); +++ +++ /* If this field is not NULL, it is called by the add_symbols phase +++ of a link just before adding a symbol to the global linker hash +++ table. It may modify any of the fields as it wishes. If *NAME +++ is set to NULL, the symbol will be skipped rather than being +++ added to the hash table. This function is responsible for +++ handling all processor dependent symbol bindings and section +++ indices, and must set at least *FLAGS and *SEC for each processor +++ dependent case; failure to do so will cause a link error. */ +++ bfd_boolean (*elf_add_symbol_hook) +++ (bfd *abfd, struct bfd_link_info *info, Elf_Internal_Sym *, +++ const char **name, flagword *flags, asection **sec, bfd_vma *value); +++ +++ /* If this field is not NULL, it is called by the elf_link_output_sym +++ phase of a link for each symbol which will appear in the object file. +++ On error, this function returns 0. 1 is returned when the symbol +++ should be output, 2 is returned when the symbol should be discarded. */ +++ int (*elf_backend_link_output_symbol_hook) +++ (struct bfd_link_info *info, const char *, Elf_Internal_Sym *, +++ asection *, struct elf_link_hash_entry *); +++ +++ /* The CREATE_DYNAMIC_SECTIONS function is called by the ELF backend +++ linker the first time it encounters a dynamic object in the link. +++ This function must create any sections required for dynamic +++ linking. The ABFD argument is a dynamic object. The .interp, +++ .dynamic, .dynsym, .dynstr, and .hash functions have already been +++ created, and this function may modify the section flags if +++ desired. This function will normally create the .got and .plt +++ sections, but different backends have different requirements. */ +++ bfd_boolean (*elf_backend_create_dynamic_sections) +++ (bfd *abfd, struct bfd_link_info *info); +++ +++ /* When creating a shared library, determine whether to omit the +++ dynamic symbol for the section. */ +++ bfd_boolean (*elf_backend_omit_section_dynsym) +++ (bfd *output_bfd, struct bfd_link_info *info, asection *osec); +++ +++ /* Return TRUE if relocations of targets are compatible to the extent +++ that CHECK_RELOCS will properly process them. PR 4424. */ +++ bfd_boolean (*relocs_compatible) (const bfd_target *, const bfd_target *); +++ +++ /* The CHECK_RELOCS function is called by the add_symbols phase of +++ the ELF backend linker. It is called once for each section with +++ relocs of an object file, just after the symbols for the object +++ file have been added to the global linker hash table. The +++ function must look through the relocs and do any special handling +++ required. This generally means allocating space in the global +++ offset table, and perhaps allocating space for a reloc. The +++ relocs are always passed as Rela structures; if the section +++ actually uses Rel structures, the r_addend field will always be +++ zero. */ +++ bfd_boolean (*check_relocs) +++ (bfd *abfd, struct bfd_link_info *info, asection *o, +++ const Elf_Internal_Rela *relocs); +++ +++ /* The CHECK_DIRECTIVES function is called once per input file by +++ the add_symbols phase of the ELF backend linker. The function +++ must inspect the bfd and create any additional symbols according +++ to any custom directives in the bfd. */ +++ bfd_boolean (*check_directives) +++ (bfd *abfd, struct bfd_link_info *info); +++ +++ /* The NOTICE_AS_NEEDED function is called as the linker is about to +++ handle an as-needed lib (ACT = notice_as_needed), and after the +++ linker has decided to keep the lib (ACT = notice_needed) or when +++ the lib is not needed (ACT = notice_not_needed). */ +++ bfd_boolean (*notice_as_needed) +++ (bfd *abfd, struct bfd_link_info *info, enum notice_asneeded_action act); +++ +++ /* The ADJUST_DYNAMIC_SYMBOL function is called by the ELF backend +++ linker for every symbol which is defined by a dynamic object and +++ referenced by a regular object. This is called after all the +++ input files have been seen, but before the SIZE_DYNAMIC_SECTIONS +++ function has been called. The hash table entry should be +++ bfd_link_hash_defined ore bfd_link_hash_defweak, and it should be +++ defined in a section from a dynamic object. Dynamic object +++ sections are not included in the final link, and this function is +++ responsible for changing the value to something which the rest of +++ the link can deal with. This will normally involve adding an +++ entry to the .plt or .got or some such section, and setting the +++ symbol to point to that. */ +++ bfd_boolean (*elf_backend_adjust_dynamic_symbol) +++ (struct bfd_link_info *info, struct elf_link_hash_entry *h); +++ +++ /* The ALWAYS_SIZE_SECTIONS function is called by the backend linker +++ after all the linker input files have been seen but before the +++ section sizes have been set. This is called after +++ ADJUST_DYNAMIC_SYMBOL, but before SIZE_DYNAMIC_SECTIONS. */ +++ bfd_boolean (*elf_backend_always_size_sections) +++ (bfd *output_bfd, struct bfd_link_info *info); +++ +++ /* The SIZE_DYNAMIC_SECTIONS function is called by the ELF backend +++ linker after all the linker input files have been seen but before +++ the sections sizes have been set. This is called after +++ ADJUST_DYNAMIC_SYMBOL has been called on all appropriate symbols. +++ It is only called when linking against a dynamic object. It must +++ set the sizes of the dynamic sections, and may fill in their +++ contents as well. The generic ELF linker can handle the .dynsym, +++ .dynstr and .hash sections. This function must handle the +++ .interp section and any sections created by the +++ CREATE_DYNAMIC_SECTIONS entry point. */ +++ bfd_boolean (*elf_backend_size_dynamic_sections) +++ (bfd *output_bfd, struct bfd_link_info *info); +++ +++ /* The STRIP_ZERO_SIZED_DYNAMIC_SECTIONS function is called by the +++ ELF backend linker to strip zero-sized dynamic sections after +++ the section sizes have been set. */ +++ bfd_boolean (*elf_backend_strip_zero_sized_dynamic_sections) +++ (struct bfd_link_info *info); +++ +++ /* Set TEXT_INDEX_SECTION and DATA_INDEX_SECTION, the output sections +++ we keep to use as a base for relocs and symbols. */ +++ void (*elf_backend_init_index_section) +++ (bfd *output_bfd, struct bfd_link_info *info); +++ +++ /* The RELOCATE_SECTION function is called by the ELF backend linker +++ to handle the relocations for a section. +++ +++ The relocs are always passed as Rela structures; if the section +++ actually uses Rel structures, the r_addend field will always be +++ zero. +++ +++ This function is responsible for adjust the section contents as +++ necessary, and (if using Rela relocs and generating a +++ relocatable output file) adjusting the reloc addend as +++ necessary. +++ +++ This function does not have to worry about setting the reloc +++ address or the reloc symbol index. +++ +++ LOCAL_SYMS is a pointer to the swapped in local symbols. +++ +++ LOCAL_SECTIONS is an array giving the section in the input file +++ corresponding to the st_shndx field of each local symbol. +++ +++ The global hash table entry for the global symbols can be found +++ via elf_sym_hashes (input_bfd). +++ +++ When generating relocatable output, this function must handle +++ STB_LOCAL/STT_SECTION symbols specially. The output symbol is +++ going to be the section symbol corresponding to the output +++ section, which means that the addend must be adjusted +++ accordingly. +++ +++ Returns FALSE on error, TRUE on success, 2 if successful and +++ relocations should be written for this section. */ +++ int (*elf_backend_relocate_section) +++ (bfd *output_bfd, struct bfd_link_info *info, bfd *input_bfd, +++ asection *input_section, bfd_byte *contents, Elf_Internal_Rela *relocs, +++ Elf_Internal_Sym *local_syms, asection **local_sections); +++ +++ /* The FINISH_DYNAMIC_SYMBOL function is called by the ELF backend +++ linker just before it writes a symbol out to the .dynsym section. +++ The processor backend may make any required adjustment to the +++ symbol. It may also take the opportunity to set contents of the +++ dynamic sections. Note that FINISH_DYNAMIC_SYMBOL is called on +++ all .dynsym symbols, while ADJUST_DYNAMIC_SYMBOL is only called +++ on those symbols which are defined by a dynamic object. */ +++ bfd_boolean (*elf_backend_finish_dynamic_symbol) +++ (bfd *output_bfd, struct bfd_link_info *info, +++ struct elf_link_hash_entry *h, Elf_Internal_Sym *sym); +++ +++ /* The FINISH_DYNAMIC_SECTIONS function is called by the ELF backend +++ linker just before it writes all the dynamic sections out to the +++ output file. The FINISH_DYNAMIC_SYMBOL will have been called on +++ all dynamic symbols. */ +++ bfd_boolean (*elf_backend_finish_dynamic_sections) +++ (bfd *output_bfd, struct bfd_link_info *info); +++ +++ /* A function to do any beginning processing needed for the ELF file +++ before building the ELF headers and computing file positions. */ +++ void (*elf_backend_begin_write_processing) +++ (bfd *, struct bfd_link_info *); +++ +++ /* A function to do any final processing needed for the ELF file +++ before writing it out. */ +++ bfd_boolean (*elf_backend_final_write_processing) +++ (bfd *); +++ +++ /* This function is called by get_program_header_size. It should +++ return the number of additional program segments which this BFD +++ will need. It should return -1 on error. */ +++ int (*elf_backend_additional_program_headers) +++ (bfd *, struct bfd_link_info *); +++ +++ /* This function is called to modify an existing segment map in a +++ backend specific fashion. */ +++ bfd_boolean (*elf_backend_modify_segment_map) +++ (bfd *, struct bfd_link_info *); +++ +++ /* This function is called to modify program headers just before +++ they are written. */ +++ bfd_boolean (*elf_backend_modify_headers) +++ (bfd *, struct bfd_link_info *); +++ +++ /* This function is called to see if the PHDR header should be +++ checked for validity. */ +++ bfd_boolean (*elf_backend_allow_non_load_phdr) +++ (bfd *, const Elf_Internal_Phdr *, unsigned); +++ +++ /* This function is called before section garbage collection to +++ mark entry symbol sections. */ +++ void (*gc_keep) +++ (struct bfd_link_info *); +++ +++ /* This function is called during section garbage collection to +++ mark sections that define global symbols. */ +++ bfd_boolean (*gc_mark_dynamic_ref) +++ (struct elf_link_hash_entry *, void *); +++ +++ /* This function is called during section gc to discover the section a +++ particular relocation refers to. */ +++ elf_gc_mark_hook_fn gc_mark_hook; +++ +++ /* This function, if defined, is called after the first gc marking pass +++ to allow the backend to mark additional sections. */ +++ bfd_boolean (*gc_mark_extra_sections) +++ (struct bfd_link_info *, elf_gc_mark_hook_fn); +++ +++ /* This function is called to initialise ELF file header info. +++ Customised versions can modify things like the OS and ABI version. */ +++ bfd_boolean (*elf_backend_init_file_header) +++ (bfd *, struct bfd_link_info *); +++ +++ /* This function, if defined, prints a symbol to file and returns the +++ name of the symbol to be printed. It should return NULL to fall +++ back to default symbol printing. */ +++ const char *(*elf_backend_print_symbol_all) +++ (bfd *, void *, asymbol *); +++ +++ /* This function, if defined, is called after all local symbols and +++ global symbols converted to locals are emitted into the symtab +++ section. It allows the backend to emit special local symbols +++ not handled in the hash table. */ +++ bfd_boolean (*elf_backend_output_arch_local_syms) +++ (bfd *, struct bfd_link_info *, void *, +++ bfd_boolean (*) (void *, const char *, Elf_Internal_Sym *, asection *, +++ struct elf_link_hash_entry *)); +++ +++ /* This function, if defined, is called after all symbols are emitted +++ into the symtab section. It allows the backend to emit special +++ global symbols not handled in the hash table. */ +++ bfd_boolean (*elf_backend_output_arch_syms) +++ (bfd *, struct bfd_link_info *, void *, +++ bfd_boolean (*) (void *, const char *, Elf_Internal_Sym *, asection *, +++ struct elf_link_hash_entry *)); +++ +++ /* Filter what symbols of the output file to include in the import +++ library if one is created. */ +++ unsigned int (*elf_backend_filter_implib_symbols) +++ (bfd *, struct bfd_link_info *, asymbol **, long); +++ +++ /* Copy any information related to dynamic linking from a pre-existing +++ symbol to a newly created symbol. Also called to copy flags and +++ other back-end info to a weakdef, in which case the symbol is not +++ newly created and plt/got refcounts and dynamic indices should not +++ be copied. */ +++ void (*elf_backend_copy_indirect_symbol) +++ (struct bfd_link_info *, struct elf_link_hash_entry *, +++ struct elf_link_hash_entry *); +++ +++ /* Modify any information related to dynamic linking such that the +++ symbol is not exported. */ +++ void (*elf_backend_hide_symbol) +++ (struct bfd_link_info *, struct elf_link_hash_entry *, bfd_boolean); +++ +++ /* A function to do additional symbol fixup, called by +++ _bfd_elf_fix_symbol_flags. */ +++ bfd_boolean (*elf_backend_fixup_symbol) +++ (struct bfd_link_info *, struct elf_link_hash_entry *); +++ +++ /* Merge the backend specific symbol attribute. */ +++ void (*elf_backend_merge_symbol_attribute) +++ (struct elf_link_hash_entry *, const Elf_Internal_Sym *, bfd_boolean, +++ bfd_boolean); +++ +++ /* This function, if defined, will return a string containing the +++ name of a target-specific dynamic tag. */ +++ char *(*elf_backend_get_target_dtag) +++ (bfd_vma); +++ +++ /* Decide whether an undefined symbol is special and can be ignored. +++ This is the case for OPTIONAL symbols on IRIX. */ +++ bfd_boolean (*elf_backend_ignore_undef_symbol) +++ (struct elf_link_hash_entry *); +++ +++ /* Emit relocations. Overrides default routine for emitting relocs, +++ except during a relocatable link, or if all relocs are being emitted. */ +++ bfd_boolean (*elf_backend_emit_relocs) +++ (bfd *, asection *, Elf_Internal_Shdr *, Elf_Internal_Rela *, +++ struct elf_link_hash_entry **); +++ +++ /* Update relocations. It is allowed to change the number and the order. +++ In such a case hashes should be invalidated. */ +++ void (*elf_backend_update_relocs) +++ (asection *, struct bfd_elf_section_reloc_data *); +++ +++ /* Count relocations. Not called for relocatable links +++ or if all relocs are being preserved in the output. */ +++ unsigned int (*elf_backend_count_relocs) +++ (struct bfd_link_info *, asection *); +++ +++ /* Count additionals relocations. Called for relocatable links if +++ additional relocations needs to be created. */ +++ unsigned int (*elf_backend_count_additional_relocs) +++ (asection *); +++ +++ /* Say whether to sort relocs output by ld -r and ld --emit-relocs, +++ by r_offset. If NULL, default to true. */ +++ bfd_boolean (*sort_relocs_p) +++ (asection *); +++ +++ /* This function, if defined, is called when an NT_PRSTATUS note is found +++ in a core file. */ +++ bfd_boolean (*elf_backend_grok_prstatus) +++ (bfd *, Elf_Internal_Note *); +++ +++ /* This function, if defined, is called when an NT_PSINFO or NT_PRPSINFO +++ note is found in a core file. */ +++ bfd_boolean (*elf_backend_grok_psinfo) +++ (bfd *, Elf_Internal_Note *); +++ +++ /* This function, if defined, is called when a "FreeBSD" NT_PRSTATUS +++ note is found in a core file. */ +++ bfd_boolean (*elf_backend_grok_freebsd_prstatus) +++ (bfd *, Elf_Internal_Note *); +++ +++ /* This function, if defined, is called to write a note to a corefile. */ +++ char *(*elf_backend_write_core_note) +++ (bfd *abfd, char *buf, int *bufsiz, int note_type, ...); +++ +++ /* This function, if defined, is called to convert target-specific +++ section flag names into hex values. */ +++ flagword (*elf_backend_lookup_section_flags_hook) +++ (char *); +++ +++ /* This function returns class of a reloc type. */ +++ enum elf_reloc_type_class (*elf_backend_reloc_type_class) +++ (const struct bfd_link_info *, const asection *, const Elf_Internal_Rela *); +++ +++ /* This function, if defined, removes information about discarded functions +++ from other sections which mention them. */ +++ bfd_boolean (*elf_backend_discard_info) +++ (bfd *, struct elf_reloc_cookie *, struct bfd_link_info *); +++ +++ /* This function, if defined, signals that the function above has removed +++ the discarded relocations for this section. */ +++ bfd_boolean (*elf_backend_ignore_discarded_relocs) +++ (asection *); +++ +++ /* What to do when ld finds relocations against symbols defined in +++ discarded sections. */ +++ unsigned int (*action_discarded) +++ (asection *); +++ +++ /* This function returns the width of FDE pointers in bytes, or 0 if +++ that can't be determined for some reason. The default definition +++ goes by the bfd's EI_CLASS. */ +++ unsigned int (*elf_backend_eh_frame_address_size) +++ (bfd *, const asection *); +++ +++ /* These functions tell elf-eh-frame whether to attempt to turn +++ absolute or lsda encodings into pc-relative ones. The default +++ definition enables these transformations. */ +++ bfd_boolean (*elf_backend_can_make_relative_eh_frame) +++ (bfd *, struct bfd_link_info *, asection *); +++ bfd_boolean (*elf_backend_can_make_lsda_relative_eh_frame) +++ (bfd *, struct bfd_link_info *, asection *); +++ +++ /* This function returns an encoding after computing the encoded +++ value (and storing it in ENCODED) for the given OFFSET into OSEC, +++ to be stored in at LOC_OFFSET into the LOC_SEC input section. +++ The default definition chooses a 32-bit PC-relative encoding. */ +++ bfd_byte (*elf_backend_encode_eh_address) +++ (bfd *abfd, struct bfd_link_info *info, +++ asection *osec, bfd_vma offset, +++ asection *loc_sec, bfd_vma loc_offset, +++ bfd_vma *encoded); +++ +++ /* This function, if defined, may write out the given section. +++ Returns TRUE if it did so and FALSE if the caller should. */ +++ bfd_boolean (*elf_backend_write_section) +++ (bfd *, struct bfd_link_info *, asection *, bfd_byte *); +++ +++ /* This function, if defined, returns TRUE if it is section symbols +++ only that are considered local for the purpose of partitioning the +++ symbol table into local and global symbols. This should be NULL +++ for most targets, in which case the correct thing will be done. +++ MIPS ELF, at least on the Irix 5, has special requirements. */ +++ bfd_boolean (*elf_backend_elfsym_local_is_section) +++ (bfd *); +++ +++ /* The level of IRIX compatibility we're striving for. +++ MIPS ELF specific function. */ +++ irix_compat_t (*elf_backend_mips_irix_compat) +++ (bfd *); +++ +++ reloc_howto_type *(*elf_backend_mips_rtype_to_howto) +++ (bfd *, unsigned int, bfd_boolean); +++ +++ /* The swapping table to use when dealing with ECOFF information. +++ Used for the MIPS ELF .mdebug section. */ +++ const struct ecoff_debug_swap *elf_backend_ecoff_debug_swap; +++ +++ /* This function implements `bfd_elf_bfd_from_remote_memory'; +++ see elf.c, elfcode.h. */ +++ bfd *(*elf_backend_bfd_from_remote_memory) +++ (bfd *templ, bfd_vma ehdr_vma, bfd_size_type size, bfd_vma *loadbasep, +++ int (*target_read_memory) (bfd_vma vma, bfd_byte *myaddr, +++ bfd_size_type len)); +++ +++ bfd_boolean (*elf_backend_core_find_build_id) (bfd *, bfd_vma); +++ +++ /* This function is used by `_bfd_elf_get_synthetic_symtab'; +++ see elf.c. */ +++ bfd_vma (*plt_sym_val) (bfd_vma, const asection *, const arelent *); +++ +++ /* Is symbol defined in common section? */ +++ bfd_boolean (*common_definition) (Elf_Internal_Sym *); +++ +++ /* Return a common section index for section. */ +++ unsigned int (*common_section_index) (asection *); +++ +++ /* Return a common section for section. */ +++ asection *(*common_section) (asection *); +++ +++ /* Return TRUE if we can merge 2 definitions. */ +++ bfd_boolean (*merge_symbol) (struct elf_link_hash_entry *, +++ const Elf_Internal_Sym *, asection **, +++ bfd_boolean, bfd_boolean, +++ bfd *, const asection *); +++ +++ /* Return TRUE if symbol should be hashed in the `.gnu.hash' section. */ +++ bfd_boolean (*elf_hash_symbol) (struct elf_link_hash_entry *); +++ +++ /* If non-NULL, called to register the location of XLAT_LOC within +++ .MIPS.xhash at which real final dynindx for H will be written. +++ If XLAT_LOC is zero, the symbol is not included in +++ .MIPS.xhash and no dynindx will be written. */ +++ void (*record_xhash_symbol) +++ (struct elf_link_hash_entry *h, bfd_vma xlat_loc); +++ +++ /* Return TRUE if type is a function symbol type. */ +++ bfd_boolean (*is_function_type) (unsigned int type); +++ +++ /* If the ELF symbol SYM might be a function in SEC, return the +++ function size and set *CODE_OFF to the function's entry point, +++ otherwise return zero. */ +++ bfd_size_type (*maybe_function_sym) (const asymbol *sym, asection *sec, +++ bfd_vma *code_off); +++ +++ /* Given NAME, the name of a relocation section stripped of its +++ .rel/.rela prefix, return the section in ABFD to which the +++ relocations apply. */ +++ asection *(*get_reloc_section) (bfd *abfd, const char *name); +++ +++ /* Called to set the sh_flags, sh_link and sh_info fields of OSECTION which +++ has a type >= SHT_LOOS. Returns TRUE if the fields were initialised, +++ FALSE otherwise. Can be called multiple times for a given section, +++ until it returns TRUE. Most of the times it is called ISECTION will be +++ set to an input section that might be associated with the output section. +++ The last time that it is called, ISECTION will be set to NULL. */ +++ bfd_boolean (*elf_backend_copy_special_section_fields) +++ (const bfd *ibfd, bfd *obfd, const Elf_Internal_Shdr *isection, +++ Elf_Internal_Shdr *osection); +++ +++ /* Used to handle bad SHF_LINK_ORDER input. */ +++ void (*link_order_error_handler) (const char *, ...); +++ +++ /* Name of the PLT relocation section. */ +++ const char *relplt_name; +++ +++ /* Alternate EM_xxxx machine codes for this backend. */ +++ int elf_machine_alt1; +++ int elf_machine_alt2; +++ +++ const struct elf_size_info *s; +++ +++ /* An array of target specific special sections. */ +++ const struct bfd_elf_special_section *special_sections; +++ +++ /* The size in bytes of the header for the GOT. This includes the +++ so-called reserved entries on some systems. */ +++ bfd_vma got_header_size; +++ +++ /* The size of the GOT entry for the symbol pointed to by H if non-NULL, +++ otherwise by the local symbol with index SYMNDX in IBFD. */ +++ bfd_vma (*got_elt_size) (bfd *, struct bfd_link_info *, +++ struct elf_link_hash_entry *h, +++ bfd *ibfd, unsigned long symndx); +++ +++ /* The vendor name to use for a processor-standard attributes section. */ +++ const char *obj_attrs_vendor; +++ +++ /* The section name to use for a processor-standard attributes section. */ +++ const char *obj_attrs_section; +++ +++ /* Return 1, 2 or 3 to indicate what type of arguments a +++ processor-specific tag takes. */ +++ int (*obj_attrs_arg_type) (int); +++ +++ /* The section type to use for an attributes section. */ +++ unsigned int obj_attrs_section_type; +++ +++ /* This function determines the order in which any attributes are +++ written. It must be defined for input in the range +++ LEAST_KNOWN_OBJ_ATTRIBUTE..NUM_KNOWN_OBJ_ATTRIBUTES-1 (this range +++ is used in order to make unity easy). The returned value is the +++ actual tag number to place in the input position. */ +++ int (*obj_attrs_order) (int); +++ +++ /* Handle merging unknown attributes; either warn and return TRUE, +++ or give an error and return FALSE. */ +++ bfd_boolean (*obj_attrs_handle_unknown) (bfd *, int); +++ +++ /* Parse GNU properties. Return the property kind. If the property +++ is corrupt, issue an error message and return property_corrupt. */ +++ enum elf_property_kind (*parse_gnu_properties) (bfd *, unsigned int, +++ bfd_byte *, +++ unsigned int); +++ +++ /* Merge GNU properties. Return TRUE if property is updated. */ +++ bfd_boolean (*merge_gnu_properties) (struct bfd_link_info *, bfd *, bfd *, +++ elf_property *, elf_property *); +++ +++ /* Set up GNU properties. */ +++ bfd *(*setup_gnu_properties) (struct bfd_link_info *); +++ +++ /* Fix up GNU properties. */ +++ void (*fixup_gnu_properties) (struct bfd_link_info *, +++ elf_property_list **); +++ +++ /* Encoding used for compact EH tables. */ +++ int (*compact_eh_encoding) (struct bfd_link_info *); +++ +++ /* Opcode representing no unwind. */ +++ int (*cant_unwind_opcode) (struct bfd_link_info *); +++ +++ /* Called when emitting an ELF symbol whoes input version had an +++ ST_SHNDX field set to a value in the range SHN_LOPROC..SHN_HIOS. +++ Returns the value to be installed in the ST_SHNDX field of the +++ emitted symbol. If not defined, the value is left unchanged. */ +++ unsigned int (*symbol_section_index) (bfd *, elf_symbol_type *); +++ +++ /* Called when a section has extra reloc sections. */ +++ bfd_boolean (*init_secondary_reloc_section) (bfd *, Elf_Internal_Shdr *, +++ const char *, unsigned int); +++ +++ /* Called when after loading the normal relocs for a section. */ +++ bfd_boolean (*slurp_secondary_relocs) (bfd *, asection *, asymbol **); +++ +++ /* Called after writing the normal relocs for a section. */ +++ bfd_boolean (*write_secondary_relocs) (bfd *, asection *); +++ +++ /* This is non-zero if static TLS segments require a special alignment. */ +++ unsigned static_tls_alignment; +++ +++ /* Alignment for the PT_GNU_STACK segment. */ +++ unsigned stack_align; +++ +++ /* Flag bits to assign to a section of type SHT_STRTAB. */ +++ unsigned long elf_strtab_flags; +++ +++ /* This is TRUE if the linker should act like collect and gather +++ global constructors and destructors by name. This is TRUE for +++ MIPS ELF because the Irix 5 tools can not handle the .init +++ section. */ +++ unsigned collect : 1; +++ +++ /* This is TRUE if the linker should ignore changes to the type of a +++ symbol. This is TRUE for MIPS ELF because some Irix 5 objects +++ record undefined functions as STT_OBJECT although the definitions +++ are STT_FUNC. */ +++ unsigned type_change_ok : 1; +++ +++ /* Whether the backend may use REL relocations. (Some backends use +++ both REL and RELA relocations, and this flag is set for those +++ backends.) */ +++ unsigned may_use_rel_p : 1; +++ +++ /* Whether the backend may use RELA relocations. (Some backends use +++ both REL and RELA relocations, and this flag is set for those +++ backends.) */ +++ unsigned may_use_rela_p : 1; +++ +++ /* Whether the default relocation type is RELA. If a backend with +++ this flag set wants REL relocations for a particular section, +++ it must note that explicitly. Similarly, if this flag is clear, +++ and the backend wants RELA relocations for a particular +++ section. */ +++ unsigned default_use_rela_p : 1; +++ +++ /* True if PLT and copy relocations should be RELA by default. */ +++ unsigned rela_plts_and_copies_p : 1; +++ +++ /* Set if RELA relocations for a relocatable link can be handled by +++ generic code. Backends that set this flag need do nothing in the +++ backend relocate_section routine for relocatable linking. */ +++ unsigned rela_normal : 1; +++ +++ /* Set if DT_REL/DT_RELA/DT_RELSZ/DT_RELASZ should not include PLT +++ relocations. */ +++ unsigned dtrel_excludes_plt : 1; +++ +++ /* TRUE if addresses "naturally" sign extend. This is used when +++ swapping in from Elf32 when BFD64. */ +++ unsigned sign_extend_vma : 1; +++ +++ unsigned want_got_plt : 1; +++ unsigned plt_readonly : 1; +++ unsigned want_plt_sym : 1; +++ unsigned plt_not_loaded : 1; +++ unsigned plt_alignment : 4; +++ unsigned can_gc_sections : 1; +++ unsigned can_refcount : 1; +++ unsigned want_got_sym : 1; +++ unsigned want_dynbss : 1; +++ unsigned want_dynrelro : 1; +++ +++ /* Targets which do not support physical addressing often require +++ that the p_paddr field in the section header to be set to zero. +++ This field indicates whether this behavior is required. */ +++ unsigned want_p_paddr_set_to_zero : 1; +++ +++ /* Target has broken hardware and/or kernel that requires pages not +++ to be mapped twice with different permissions. */ +++ unsigned no_page_alias : 1; +++ +++ /* True if an object file lacking a .note.GNU-stack section +++ should be assumed to be requesting exec stack. At least one +++ other file in the link needs to have a .note.GNU-stack section +++ for a PT_GNU_STACK segment to be created. */ +++ unsigned default_execstack : 1; +++ +++ /* True if elf_section_data(sec)->this_hdr.contents is sec->rawsize +++ in length rather than sec->size in length, if sec->rawsize is +++ non-zero and smaller than sec->size. */ +++ unsigned caches_rawsize : 1; +++ +++ /* Address of protected data defined in the shared library may be +++ external, i.e., due to copy relocation. */ +++ unsigned extern_protected_data : 1; +++ +++ /* True if `_bfd_elf_link_renumber_dynsyms' must be called even for +++ static binaries. */ +++ unsigned always_renumber_dynsyms : 1; +++ +++ /* True if the 32-bit Linux PRPSINFO structure's `pr_uid' and `pr_gid' +++ members use a 16-bit data type. */ +++ unsigned linux_prpsinfo32_ugid16 : 1; +++ +++ /* True if the 64-bit Linux PRPSINFO structure's `pr_uid' and `pr_gid' +++ members use a 16-bit data type. */ +++ unsigned linux_prpsinfo64_ugid16 : 1; +++}; +++ +++/* Information about reloc sections associated with a bfd_elf_section_data +++ structure. */ +++struct bfd_elf_section_reloc_data +++{ +++ /* The ELF header for the reloc section associated with this +++ section, if any. */ +++ Elf_Internal_Shdr *hdr; +++ /* The number of relocations currently assigned to HDR. */ +++ unsigned int count; +++ /* The ELF section number of the reloc section. Only used for an +++ output file. */ +++ int idx; +++ /* Used by the backend linker to store the symbol hash table entries +++ associated with relocs against global symbols. */ +++ struct elf_link_hash_entry **hashes; +++}; +++ +++/* Information stored for each BFD section in an ELF file. This +++ structure is allocated by elf_new_section_hook. */ +++ +++struct bfd_elf_section_data +++{ +++ /* The ELF header for this section. */ +++ Elf_Internal_Shdr this_hdr; +++ +++ /* INPUT_SECTION_FLAGS if specified in the linker script. */ +++ struct flag_info *section_flag_info; +++ +++ /* Information about the REL and RELA reloc sections associated +++ with this section, if any. */ +++ struct bfd_elf_section_reloc_data rel, rela; +++ +++ /* The ELF section number of this section. */ +++ int this_idx; +++ +++ /* Used by the backend linker when generating a shared library to +++ record the dynamic symbol index for a section symbol +++ corresponding to this section. A value of 0 means that there is +++ no dynamic symbol for this section. */ +++ int dynindx; +++ +++ /* A pointer to the linked-to section for SHF_LINK_ORDER. */ +++ asection *linked_to; +++ +++ /* A pointer to the swapped relocs. If the section uses REL relocs, +++ rather than RELA, all the r_addend fields will be zero. This +++ pointer may be NULL. It is used by the backend linker. */ +++ Elf_Internal_Rela *relocs; +++ +++ /* A pointer to a linked list tracking dynamic relocs copied for +++ local symbols. */ +++ void *local_dynrel; +++ +++ /* A pointer to the bfd section used for dynamic relocs. */ +++ asection *sreloc; +++ +++ union { +++ /* Group name, if this section is a member of a group. */ +++ const char *name; +++ +++ /* Group signature sym, if this is the SHT_GROUP section. */ +++ struct bfd_symbol *id; +++ } group; +++ +++ /* For a member of a group, points to the SHT_GROUP section. +++ NULL for the SHT_GROUP section itself and non-group sections. */ +++ asection *sec_group; +++ +++ /* A linked list of member sections in the group. Circular when used by +++ the linker. For the SHT_GROUP section, points at first member. */ +++ asection *next_in_group; +++ +++ /* The FDEs associated with this section. The u.fde.next_in_section +++ field acts as a chain pointer. */ +++ struct eh_cie_fde *fde_list; +++ +++ /* Link from a text section to its .eh_frame_entry section. */ +++ asection *eh_frame_entry; +++ +++ /* TRUE if the section has secondary reloc sections associated with it. +++ FIXME: In the future it might be better to change this into a list +++ of secondary reloc sections, making lookup easier and faster. */ +++ bfd_boolean has_secondary_relocs; +++ +++ /* A pointer used for various section optimizations. */ +++ void *sec_info; +++}; +++ +++#define elf_section_data(sec) ((struct bfd_elf_section_data*)(sec)->used_by_bfd) +++#define elf_linked_to_section(sec) (elf_section_data(sec)->linked_to) +++#define elf_section_type(sec) (elf_section_data(sec)->this_hdr.sh_type) +++#define elf_section_flags(sec) (elf_section_data(sec)->this_hdr.sh_flags) +++#define elf_section_info(sec) (elf_section_data(sec)->this_hdr.sh_info) +++#define elf_group_name(sec) (elf_section_data(sec)->group.name) +++#define elf_group_id(sec) (elf_section_data(sec)->group.id) +++#define elf_next_in_group(sec) (elf_section_data(sec)->next_in_group) +++#define elf_fde_list(sec) (elf_section_data(sec)->fde_list) +++#define elf_sec_group(sec) (elf_section_data(sec)->sec_group) +++#define elf_section_eh_frame_entry(sec) (elf_section_data(sec)->eh_frame_entry) +++ +++#define xvec_get_elf_backend_data(xvec) \ +++ ((const struct elf_backend_data *) (xvec)->backend_data) +++ +++#define get_elf_backend_data(abfd) \ +++ xvec_get_elf_backend_data ((abfd)->xvec) +++ +++/* The least object attributes (within an attributes subsection) known +++ for any target. Some code assumes that the value 0 is not used and +++ the field for that attribute can instead be used as a marker to +++ indicate that attributes have been initialized. */ +++#define LEAST_KNOWN_OBJ_ATTRIBUTE 2 +++ +++/* The maximum number of known object attributes for any target. */ +++#define NUM_KNOWN_OBJ_ATTRIBUTES 71 +++ +++/* The value of an object attribute. The type indicates whether the attribute +++ holds and integer, a string, or both. It can also indicate that there can +++ be no default (i.e. all values must be written to file, even zero), or +++ that the value is in error and should not be written to file. */ +++ +++typedef struct obj_attribute +++{ +++#define ATTR_TYPE_FLAG_INT_VAL (1 << 0) +++#define ATTR_TYPE_FLAG_STR_VAL (1 << 1) +++#define ATTR_TYPE_FLAG_NO_DEFAULT (1 << 2) +++#define ATTR_TYPE_FLAG_ERROR (1 << 3) +++ +++#define ATTR_TYPE_HAS_INT_VAL(TYPE) ((TYPE) & ATTR_TYPE_FLAG_INT_VAL) +++#define ATTR_TYPE_HAS_STR_VAL(TYPE) ((TYPE) & ATTR_TYPE_FLAG_STR_VAL) +++#define ATTR_TYPE_HAS_NO_DEFAULT(TYPE) ((TYPE) & ATTR_TYPE_FLAG_NO_DEFAULT) +++#define ATTR_TYPE_HAS_ERROR(TYPE) ((TYPE) & ATTR_TYPE_FLAG_ERROR) +++ +++ int type; +++ unsigned int i; +++ char *s; +++} obj_attribute; +++ +++typedef struct obj_attribute_list +++{ +++ struct obj_attribute_list *next; +++ unsigned int tag; +++ obj_attribute attr; +++} obj_attribute_list; +++ +++/* Object attributes may either be defined by the processor ABI, index +++ OBJ_ATTR_PROC in the *_obj_attributes arrays, or be GNU-specific +++ (and possibly also processor-specific), index OBJ_ATTR_GNU. */ +++#define OBJ_ATTR_PROC 0 +++#define OBJ_ATTR_GNU 1 +++#define OBJ_ATTR_FIRST OBJ_ATTR_PROC +++#define OBJ_ATTR_LAST OBJ_ATTR_GNU +++ +++/* The following object attribute tags are taken as generic, for all +++ targets and for "gnu" where there is no target standard. */ +++enum +++{ +++ Tag_NULL = 0, +++ Tag_File = 1, +++ Tag_Section = 2, +++ Tag_Symbol = 3, +++ Tag_compatibility = 32 +++}; +++ +++/* The following struct stores information about every SystemTap section +++ found in the object file. */ +++struct sdt_note +++{ +++ struct sdt_note *next; +++ bfd_size_type size; +++ bfd_byte data[1]; +++}; +++ +++/* tdata information grabbed from an elf core file. */ +++struct core_elf_obj_tdata +++{ +++ int signal; +++ int pid; +++ int lwpid; +++ char* program; +++ char* command; +++}; +++ +++/* Extra tdata information held for output ELF BFDs. */ +++struct output_elf_obj_tdata +++{ +++ struct elf_segment_map *seg_map; +++ struct elf_strtab_hash *strtab_ptr; +++ +++ /* STT_SECTION symbols for each section */ +++ asymbol **section_syms; +++ +++ /* Used to determine if PT_GNU_EH_FRAME segment header should be +++ created. */ +++ asection *eh_frame_hdr; +++ +++ /* NT_GNU_BUILD_ID note type info. */ +++ struct +++ { +++ bfd_boolean (*after_write_object_contents) (bfd *); +++ const char *style; +++ asection *sec; +++ } build_id; +++ +++ /* Records the result of `get_program_header_size'. */ +++ bfd_size_type program_header_size; +++ +++ /* Used when laying out sections. */ +++ file_ptr next_file_pos; +++ +++ int num_section_syms; +++ unsigned int shstrtab_section, strtab_section; +++ +++ /* Segment flags for the PT_GNU_STACK segment. */ +++ unsigned int stack_flags; +++ +++ /* Used to determine if the e_flags field has been initialized */ +++ bfd_boolean flags_init; +++}; +++ +++/* Indicate if the bfd contains SHF_GNU_MBIND sections or symbols that +++ have the STT_GNU_IFUNC symbol type or STB_GNU_UNIQUE binding. Used +++ to set the osabi field in the ELF header structure. */ +++enum elf_gnu_osabi +++{ +++ elf_gnu_osabi_mbind = 1 << 0, +++ elf_gnu_osabi_ifunc = 1 << 1, +++ elf_gnu_osabi_unique = 1 << 2, +++}; +++ +++typedef struct elf_section_list +++{ +++ Elf_Internal_Shdr hdr; +++ unsigned int ndx; +++ struct elf_section_list * next; +++} elf_section_list; +++ +++enum dynamic_lib_link_class { +++ DYN_NORMAL = 0, +++ DYN_AS_NEEDED = 1, +++ DYN_DT_NEEDED = 2, +++ DYN_NO_ADD_NEEDED = 4, +++ DYN_NO_NEEDED = 8 +++}; +++ +++/* Some private data is stashed away for future use using the tdata pointer +++ in the bfd structure. */ +++ +++struct elf_obj_tdata +++{ +++ Elf_Internal_Ehdr elf_header[1]; /* Actual data, but ref like ptr */ +++ Elf_Internal_Shdr **elf_sect_ptr; +++ Elf_Internal_Phdr *phdr; +++ Elf_Internal_Shdr symtab_hdr; +++ Elf_Internal_Shdr shstrtab_hdr; +++ Elf_Internal_Shdr strtab_hdr; +++ Elf_Internal_Shdr dynsymtab_hdr; +++ Elf_Internal_Shdr dynstrtab_hdr; +++ Elf_Internal_Shdr dynversym_hdr; +++ Elf_Internal_Shdr dynverref_hdr; +++ Elf_Internal_Shdr dynverdef_hdr; +++ elf_section_list * symtab_shndx_list; +++ bfd_vma gp; /* The gp value */ +++ unsigned int gp_size; /* The gp size */ +++ unsigned int num_elf_sections; /* elf_sect_ptr size */ +++ +++ /* A mapping from external symbols to entries in the linker hash +++ table, used when linking. This is indexed by the symbol index +++ minus the sh_info field of the symbol table header. */ +++ struct elf_link_hash_entry **sym_hashes; +++ +++ /* Track usage and final offsets of GOT entries for local symbols. +++ This array is indexed by symbol index. Elements are used +++ identically to "got" in struct elf_link_hash_entry. */ +++ union +++ { +++ bfd_signed_vma *refcounts; +++ bfd_vma *offsets; +++ struct got_entry **ents; +++ } local_got; +++ +++ /* The linker ELF emulation code needs to let the backend ELF linker +++ know what filename should be used for a dynamic object if the +++ dynamic object is found using a search. The emulation code then +++ sometimes needs to know what name was actually used. Until the +++ file has been added to the linker symbol table, this field holds +++ the name the linker wants. After it has been added, it holds the +++ name actually used, which will be the DT_SONAME entry if there is +++ one. */ +++ const char *dt_name; +++ +++ /* The linker emulation needs to know what audit libs +++ are used by a dynamic object. */ +++ const char *dt_audit; +++ +++ /* Used by find_nearest_line entry point. */ +++ void *line_info; +++ +++ /* A place to stash dwarf1 info for this bfd. */ +++ struct dwarf1_debug *dwarf1_find_line_info; +++ +++ /* A place to stash dwarf2 info for this bfd. */ +++ void *dwarf2_find_line_info; +++ +++ /* Stash away info for yet another find line/function variant. */ +++ void *elf_find_function_cache; +++ +++ /* Number of symbol version definitions we are about to emit. */ +++ unsigned int cverdefs; +++ +++ /* Number of symbol version references we are about to emit. */ +++ unsigned int cverrefs; +++ +++ /* Symbol version definitions in external objects. */ +++ Elf_Internal_Verdef *verdef; +++ +++ /* Symbol version references to external objects. */ +++ Elf_Internal_Verneed *verref; +++ +++ /* A pointer to the .eh_frame section. */ +++ asection *eh_frame_section; +++ +++ /* Symbol buffer. */ +++ void *symbuf; +++ +++ /* List of GNU properties. Will be updated by setup_gnu_properties +++ after all input GNU properties are merged for output. */ +++ elf_property_list *properties; +++ +++ obj_attribute known_obj_attributes[2][NUM_KNOWN_OBJ_ATTRIBUTES]; +++ obj_attribute_list *other_obj_attributes[2]; +++ +++ /* Linked-list containing information about every Systemtap section +++ found in the object file. Each section corresponds to one entry +++ in the list. */ +++ struct sdt_note *sdt_note_head; +++ +++ Elf_Internal_Shdr **group_sect_ptr; +++ unsigned int num_group; +++ +++ /* Index into group_sect_ptr, updated by setup_group when finding a +++ section's group. Used to optimize subsequent group searches. */ +++ unsigned int group_search_offset; +++ +++ unsigned int symtab_section, dynsymtab_section; +++ unsigned int dynversym_section, dynverdef_section, dynverref_section; +++ +++ /* An identifier used to distinguish different target +++ specific extensions to this structure. */ +++ ENUM_BITFIELD (elf_target_id) object_id : 6; +++ +++ /* Whether a dyanmic object was specified normally on the linker +++ command line, or was specified when --as-needed was in effect, +++ or was found via a DT_NEEDED entry. */ +++ ENUM_BITFIELD (dynamic_lib_link_class) dyn_lib_class : 4; +++ +++ /* Whether the bfd uses OS specific bits that require ELFOSABI_GNU. */ +++ ENUM_BITFIELD (elf_gnu_osabi) has_gnu_osabi : 3; +++ +++ /* Whether if the bfd contains the GNU_PROPERTY_NO_COPY_ON_PROTECTED +++ property. */ +++ unsigned int has_no_copy_on_protected : 1; +++ +++ /* Irix 5 often screws up the symbol table, sorting local symbols +++ after global symbols. This flag is set if the symbol table in +++ this BFD appears to be screwed up. If it is, we ignore the +++ sh_info field in the symbol table header, and always read all the +++ symbols. */ +++ unsigned int bad_symtab : 1; +++ +++ /* Information grabbed from an elf core file. */ +++ struct core_elf_obj_tdata *core; +++ +++ /* More information held for output ELF BFDs. */ +++ struct output_elf_obj_tdata *o; +++}; +++ +++#define elf_tdata(bfd) ((bfd) -> tdata.elf_obj_data) +++ +++#define elf_object_id(bfd) (elf_tdata(bfd) -> object_id) +++#define elf_program_header_size(bfd) (elf_tdata(bfd) -> o->program_header_size) +++#define elf_elfheader(bfd) (elf_tdata(bfd) -> elf_header) +++#define elf_elfsections(bfd) (elf_tdata(bfd) -> elf_sect_ptr) +++#define elf_numsections(bfd) (elf_tdata(bfd) -> num_elf_sections) +++#define elf_seg_map(bfd) (elf_tdata(bfd) -> o->seg_map) +++#define elf_next_file_pos(bfd) (elf_tdata(bfd) -> o->next_file_pos) +++#define elf_eh_frame_hdr(bfd) (elf_tdata(bfd) -> o->eh_frame_hdr) +++#define elf_stack_flags(bfd) (elf_tdata(bfd) -> o->stack_flags) +++#define elf_shstrtab(bfd) (elf_tdata(bfd) -> o->strtab_ptr) +++#define elf_onesymtab(bfd) (elf_tdata(bfd) -> symtab_section) +++#define elf_symtab_shndx_list(bfd) (elf_tdata(bfd) -> symtab_shndx_list) +++#define elf_strtab_sec(bfd) (elf_tdata(bfd) -> o->strtab_section) +++#define elf_shstrtab_sec(bfd) (elf_tdata(bfd) -> o->shstrtab_section) +++#define elf_symtab_hdr(bfd) (elf_tdata(bfd) -> symtab_hdr) +++#define elf_dynsymtab(bfd) (elf_tdata(bfd) -> dynsymtab_section) +++#define elf_dynversym(bfd) (elf_tdata(bfd) -> dynversym_section) +++#define elf_dynverdef(bfd) (elf_tdata(bfd) -> dynverdef_section) +++#define elf_dynverref(bfd) (elf_tdata(bfd) -> dynverref_section) +++#define elf_eh_frame_section(bfd) \ +++ (elf_tdata(bfd) -> eh_frame_section) +++#define elf_section_syms(bfd) (elf_tdata(bfd) -> o->section_syms) +++#define elf_num_section_syms(bfd) (elf_tdata(bfd) -> o->num_section_syms) +++#define core_prpsinfo(bfd) (elf_tdata(bfd) -> prpsinfo) +++#define core_prstatus(bfd) (elf_tdata(bfd) -> prstatus) +++#define elf_gp(bfd) (elf_tdata(bfd) -> gp) +++#define elf_gp_size(bfd) (elf_tdata(bfd) -> gp_size) +++#define elf_sym_hashes(bfd) (elf_tdata(bfd) -> sym_hashes) +++#define elf_local_got_refcounts(bfd) (elf_tdata(bfd) -> local_got.refcounts) +++#define elf_local_got_offsets(bfd) (elf_tdata(bfd) -> local_got.offsets) +++#define elf_local_got_ents(bfd) (elf_tdata(bfd) -> local_got.ents) +++#define elf_dt_name(bfd) (elf_tdata(bfd) -> dt_name) +++#define elf_dt_audit(bfd) (elf_tdata(bfd) -> dt_audit) +++#define elf_dyn_lib_class(bfd) (elf_tdata(bfd) -> dyn_lib_class) +++#define elf_bad_symtab(bfd) (elf_tdata(bfd) -> bad_symtab) +++#define elf_flags_init(bfd) (elf_tdata(bfd) -> o->flags_init) +++#define elf_known_obj_attributes(bfd) (elf_tdata (bfd) -> known_obj_attributes) +++#define elf_other_obj_attributes(bfd) (elf_tdata (bfd) -> other_obj_attributes) +++#define elf_known_obj_attributes_proc(bfd) \ +++ (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) +++#define elf_other_obj_attributes_proc(bfd) \ +++ (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) +++#define elf_properties(bfd) (elf_tdata (bfd) -> properties) +++#define elf_has_no_copy_on_protected(bfd) \ +++ (elf_tdata(bfd) -> has_no_copy_on_protected) +++ +++extern void _bfd_elf_swap_verdef_in +++ (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); +++extern void _bfd_elf_swap_verdef_out +++ (bfd *, const Elf_Internal_Verdef *, Elf_External_Verdef *); +++extern void _bfd_elf_swap_verdaux_in +++ (bfd *, const Elf_External_Verdaux *, Elf_Internal_Verdaux *); +++extern void _bfd_elf_swap_verdaux_out +++ (bfd *, const Elf_Internal_Verdaux *, Elf_External_Verdaux *); +++extern void _bfd_elf_swap_verneed_in +++ (bfd *, const Elf_External_Verneed *, Elf_Internal_Verneed *); +++extern void _bfd_elf_swap_verneed_out +++ (bfd *, const Elf_Internal_Verneed *, Elf_External_Verneed *); +++extern void _bfd_elf_swap_vernaux_in +++ (bfd *, const Elf_External_Vernaux *, Elf_Internal_Vernaux *); +++extern void _bfd_elf_swap_vernaux_out +++ (bfd *, const Elf_Internal_Vernaux *, Elf_External_Vernaux *); +++extern void _bfd_elf_swap_versym_in +++ (bfd *, const Elf_External_Versym *, Elf_Internal_Versym *); +++extern void _bfd_elf_swap_versym_out +++ (bfd *, const Elf_Internal_Versym *, Elf_External_Versym *); +++ +++extern unsigned int _bfd_elf_section_from_bfd_section +++ (bfd *, asection *); +++extern char *bfd_elf_string_from_elf_section +++ (bfd *, unsigned, unsigned); +++extern Elf_Internal_Sym *bfd_elf_get_elf_syms +++ (bfd *, Elf_Internal_Shdr *, size_t, size_t, Elf_Internal_Sym *, void *, +++ Elf_External_Sym_Shndx *); +++extern char * bfd_elf_get_str_section (bfd *, unsigned int); +++extern const char *bfd_elf_sym_name +++ (bfd *, Elf_Internal_Shdr *, Elf_Internal_Sym *, asection *); +++ +++extern bfd_boolean _bfd_elf_copy_private_bfd_data +++ (bfd *, bfd *); +++extern bfd_boolean _bfd_elf_print_private_bfd_data +++ (bfd *, void *); +++const char * _bfd_elf_get_symbol_version_string +++ (bfd *, asymbol *, bfd_boolean, bfd_boolean *); +++extern void bfd_elf_print_symbol +++ (bfd *, void *, asymbol *, bfd_print_symbol_type); +++ +++extern unsigned int _bfd_elf_eh_frame_address_size +++ (bfd *, const asection *); +++extern bfd_byte _bfd_elf_encode_eh_address +++ (bfd *abfd, struct bfd_link_info *info, asection *osec, bfd_vma offset, +++ asection *loc_sec, bfd_vma loc_offset, bfd_vma *encoded); +++extern bfd_boolean _bfd_elf_can_make_relative +++ (bfd *input_bfd, struct bfd_link_info *info, asection *eh_frame_section); +++ +++extern enum elf_reloc_type_class _bfd_elf_reloc_type_class +++ (const struct bfd_link_info *, const asection *, +++ const Elf_Internal_Rela *); +++extern bfd_vma _bfd_elf_rela_local_sym +++ (bfd *, Elf_Internal_Sym *, asection **, Elf_Internal_Rela *); +++extern bfd_vma _bfd_elf_rel_local_sym +++ (bfd *, Elf_Internal_Sym *, asection **, bfd_vma); +++extern bfd_vma _bfd_elf_section_offset +++ (bfd *, struct bfd_link_info *, asection *, bfd_vma); +++ +++extern unsigned long bfd_elf_hash +++ (const char *); +++extern unsigned long bfd_elf_gnu_hash +++ (const char *); +++ +++extern bfd_reloc_status_type bfd_elf_generic_reloc +++ (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **); +++extern bfd_boolean bfd_elf_allocate_object +++ (bfd *, size_t, enum elf_target_id); +++extern bfd_boolean bfd_elf_make_object +++ (bfd *); +++extern bfd_boolean bfd_elf_mkcorefile +++ (bfd *); +++extern bfd_boolean _bfd_elf_make_section_from_shdr +++ (bfd *, Elf_Internal_Shdr *, const char *, int); +++extern bfd_boolean _bfd_elf_make_section_from_phdr +++ (bfd *, Elf_Internal_Phdr *, int, const char *); +++extern struct bfd_hash_entry *_bfd_elf_link_hash_newfunc +++ (struct bfd_hash_entry *, struct bfd_hash_table *, const char *); +++extern struct bfd_link_hash_table *_bfd_elf_link_hash_table_create +++ (bfd *); +++extern void _bfd_elf_link_hash_table_free +++ (bfd *); +++extern void _bfd_elf_link_hash_copy_indirect +++ (struct bfd_link_info *, struct elf_link_hash_entry *, +++ struct elf_link_hash_entry *); +++extern void _bfd_elf_link_hash_hide_symbol +++ (struct bfd_link_info *, struct elf_link_hash_entry *, bfd_boolean); +++extern void _bfd_elf_link_hide_symbol +++ (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *); +++extern bfd_boolean _bfd_elf_link_hash_fixup_symbol +++ (struct bfd_link_info *, struct elf_link_hash_entry *); +++extern bfd_boolean _bfd_elf_link_hash_table_init +++ (struct elf_link_hash_table *, bfd *, +++ struct bfd_hash_entry *(*) +++ (struct bfd_hash_entry *, struct bfd_hash_table *, const char *), +++ unsigned int, enum elf_target_id); +++extern bfd_boolean _bfd_elf_slurp_version_tables +++ (bfd *, bfd_boolean); +++extern bfd_boolean _bfd_elf_merge_sections +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_match_sections_by_type +++ (bfd *, const asection *, bfd *, const asection *); +++extern bfd_boolean bfd_elf_is_group_section +++ (bfd *, const struct bfd_section *); +++extern const char *bfd_elf_group_name +++ (bfd *, const struct bfd_section *); +++extern bfd_boolean _bfd_elf_section_already_linked +++ (bfd *, asection *, struct bfd_link_info *); +++extern void bfd_elf_set_group_contents +++ (bfd *, asection *, void *); +++extern unsigned int _bfd_elf_filter_global_symbols +++ (bfd *, struct bfd_link_info *, asymbol **, long); +++extern asection *_bfd_elf_check_kept_section +++ (asection *, struct bfd_link_info *); +++#define _bfd_elf_link_just_syms _bfd_generic_link_just_syms +++extern void _bfd_elf_copy_link_hash_symbol_type +++ (bfd *, struct bfd_link_hash_entry *, struct bfd_link_hash_entry *); +++extern bfd_boolean _bfd_elf_size_group_sections +++ (struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_fixup_group_sections +++(bfd *, asection *); +++extern bfd_boolean _bfd_elf_copy_private_header_data +++ (bfd *, bfd *); +++extern bfd_boolean _bfd_elf_copy_private_symbol_data +++ (bfd *, asymbol *, bfd *, asymbol *); +++#define _bfd_generic_init_private_section_data \ +++ _bfd_elf_init_private_section_data +++extern bfd_boolean _bfd_elf_init_private_section_data +++ (bfd *, asection *, bfd *, asection *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_copy_private_section_data +++ (bfd *, asection *, bfd *, asection *); +++extern bfd_boolean _bfd_elf_write_object_contents +++ (bfd *); +++extern bfd_boolean _bfd_elf_write_corefile_contents +++ (bfd *); +++extern bfd_boolean _bfd_elf_set_section_contents +++ (bfd *, sec_ptr, const void *, file_ptr, bfd_size_type); +++extern long _bfd_elf_get_symtab_upper_bound +++ (bfd *); +++extern long _bfd_elf_canonicalize_symtab +++ (bfd *, asymbol **); +++extern long _bfd_elf_get_dynamic_symtab_upper_bound +++ (bfd *); +++extern long _bfd_elf_canonicalize_dynamic_symtab +++ (bfd *, asymbol **); +++extern long _bfd_elf_get_synthetic_symtab +++ (bfd *, long, asymbol **, long, asymbol **, asymbol **); +++extern long _bfd_elf_get_reloc_upper_bound +++ (bfd *, sec_ptr); +++extern long _bfd_elf_canonicalize_reloc +++ (bfd *, sec_ptr, arelent **, asymbol **); +++extern asection * _bfd_elf_get_dynamic_reloc_section +++ (bfd *, asection *, bfd_boolean); +++extern asection * _bfd_elf_make_dynamic_reloc_section +++ (asection *, bfd *, unsigned int, bfd *, bfd_boolean); +++extern long _bfd_elf_get_dynamic_reloc_upper_bound +++ (bfd *); +++extern long _bfd_elf_canonicalize_dynamic_reloc +++ (bfd *, arelent **, asymbol **); +++extern asymbol *_bfd_elf_make_empty_symbol +++ (bfd *); +++extern void _bfd_elf_get_symbol_info +++ (bfd *, asymbol *, symbol_info *); +++extern bfd_boolean _bfd_elf_is_local_label_name +++ (bfd *, const char *); +++extern alent *_bfd_elf_get_lineno +++ (bfd *, asymbol *); +++extern bfd_boolean _bfd_elf_set_arch_mach +++ (bfd *, enum bfd_architecture, unsigned long); +++extern bfd_boolean _bfd_elf_find_nearest_line +++ (bfd *, asymbol **, asection *, bfd_vma, +++ const char **, const char **, unsigned int *, unsigned int *); +++extern bfd_boolean _bfd_elf_find_line +++ (bfd *, asymbol **, asymbol *, const char **, unsigned int *); +++extern bfd_boolean _bfd_elf_find_inliner_info +++ (bfd *, const char **, const char **, unsigned int *); +++extern asymbol *_bfd_elf_find_function +++ (bfd *, asymbol **, asection *, bfd_vma, const char **, const char **); +++#define _bfd_elf_read_minisymbols _bfd_generic_read_minisymbols +++#define _bfd_elf_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol +++extern int _bfd_elf_sizeof_headers +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_new_section_hook +++ (bfd *, asection *); +++extern const struct bfd_elf_special_section *_bfd_elf_get_special_section +++ (const char *, const struct bfd_elf_special_section *, unsigned int); +++extern const struct bfd_elf_special_section *_bfd_elf_get_sec_type_attr +++ (bfd *, asection *); +++ +++extern bfd_boolean _bfd_elf_link_hide_sym_by_version +++ (struct bfd_link_info *, struct elf_link_hash_entry *); +++ +++/* If the target doesn't have reloc handling written yet: */ +++extern bfd_boolean _bfd_elf_no_info_to_howto +++ (bfd *, arelent *, Elf_Internal_Rela *); +++ +++extern bfd_boolean bfd_section_from_shdr +++ (bfd *, unsigned int shindex); +++extern bfd_boolean bfd_section_from_phdr +++ (bfd *, Elf_Internal_Phdr *, int); +++ +++extern int _bfd_elf_symbol_from_bfd_symbol +++ (bfd *, asymbol **); +++ +++extern Elf_Internal_Sym *bfd_sym_from_r_symndx +++ (struct sym_cache *, bfd *, unsigned long); +++extern asection *bfd_section_from_elf_index +++ (bfd *, unsigned int); +++ +++extern struct elf_strtab_hash * _bfd_elf_strtab_init +++ (void); +++extern void _bfd_elf_strtab_free +++ (struct elf_strtab_hash *); +++extern size_t _bfd_elf_strtab_add +++ (struct elf_strtab_hash *, const char *, bfd_boolean); +++extern void _bfd_elf_strtab_addref +++ (struct elf_strtab_hash *, size_t); +++extern void _bfd_elf_strtab_delref +++ (struct elf_strtab_hash *, size_t); +++extern unsigned int _bfd_elf_strtab_refcount +++ (struct elf_strtab_hash *, size_t); +++extern void _bfd_elf_strtab_clear_all_refs +++ (struct elf_strtab_hash *); +++extern void *_bfd_elf_strtab_save +++ (struct elf_strtab_hash *); +++extern void _bfd_elf_strtab_restore +++ (struct elf_strtab_hash *, void *); +++extern bfd_size_type _bfd_elf_strtab_size +++ (struct elf_strtab_hash *); +++extern bfd_size_type _bfd_elf_strtab_len +++ (struct elf_strtab_hash *); +++extern bfd_size_type _bfd_elf_strtab_offset +++ (struct elf_strtab_hash *, size_t); +++extern const char * _bfd_elf_strtab_str +++ (struct elf_strtab_hash *, size_t idx, bfd_size_type *offset); +++extern bfd_boolean _bfd_elf_strtab_emit +++ (bfd *, struct elf_strtab_hash *); +++extern void _bfd_elf_strtab_finalize +++ (struct elf_strtab_hash *); +++ +++extern bfd_boolean bfd_elf_parse_eh_frame_entries +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_parse_eh_frame_entry +++ (struct bfd_link_info *, asection *, struct elf_reloc_cookie *); +++extern void _bfd_elf_parse_eh_frame +++ (bfd *, struct bfd_link_info *, asection *, struct elf_reloc_cookie *); +++extern bfd_boolean _bfd_elf_end_eh_frame_parsing +++ (struct bfd_link_info *info); +++ +++extern bfd_boolean _bfd_elf_discard_section_eh_frame +++ (bfd *, struct bfd_link_info *, asection *, +++ bfd_boolean (*) (bfd_vma, void *), struct elf_reloc_cookie *); +++extern bfd_boolean _bfd_elf_adjust_eh_frame_global_symbol +++ (struct elf_link_hash_entry *, void *); +++extern bfd_boolean _bfd_elf_discard_section_eh_frame_hdr +++ (bfd *, struct bfd_link_info *); +++extern bfd_vma _bfd_elf_eh_frame_section_offset +++ (bfd *, struct bfd_link_info *, asection *, bfd_vma); +++extern bfd_boolean _bfd_elf_write_section_eh_frame +++ (bfd *, struct bfd_link_info *, asection *, bfd_byte *); +++bfd_boolean _bfd_elf_write_section_eh_frame_entry +++ (bfd *, struct bfd_link_info *, asection *, bfd_byte *); +++extern bfd_boolean _bfd_elf_fixup_eh_frame_hdr (struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_write_section_eh_frame_hdr +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_eh_frame_present +++ (struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_eh_frame_entry_present +++ (struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_maybe_strip_eh_frame_hdr +++ (struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elf_hash_symbol (struct elf_link_hash_entry *); +++ +++extern long _bfd_elf_link_lookup_local_dynindx +++ (struct bfd_link_info *, bfd *, long); +++extern bfd_boolean _bfd_elf_compute_section_file_positions +++ (bfd *, struct bfd_link_info *); +++extern file_ptr _bfd_elf_assign_file_position_for_section +++ (Elf_Internal_Shdr *, file_ptr, bfd_boolean); +++extern bfd_boolean _bfd_elf_modify_headers +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elf_validate_reloc +++ (bfd *, arelent *); +++ +++extern bfd_boolean bfd_elf_record_link_assignment +++ (bfd *, struct bfd_link_info *, const char *, bfd_boolean, +++ bfd_boolean); +++extern bfd_boolean bfd_elf_stack_segment_size (bfd *, struct bfd_link_info *, +++ const char *, bfd_vma); +++extern bfd_boolean bfd_elf_size_dynamic_sections +++ (bfd *, const char *, const char *, const char *, const char *, const char *, +++ const char * const *, struct bfd_link_info *, struct bfd_section **); +++extern bfd_boolean bfd_elf_size_dynsym_hash_dynstr +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean bfd_elf_get_bfd_needed_list +++ (bfd *, struct bfd_link_needed_list **); +++extern struct bfd_link_needed_list *bfd_elf_get_needed_list +++ (bfd *, struct bfd_link_info *); +++extern void bfd_elf_set_dt_needed_name +++ (bfd *, const char *); +++extern const char *bfd_elf_get_dt_soname +++ (bfd *); +++extern void bfd_elf_set_dyn_lib_class +++ (bfd *, enum dynamic_lib_link_class); +++extern int bfd_elf_get_dyn_lib_class +++ (bfd *); +++extern struct bfd_link_needed_list *bfd_elf_get_runpath_list +++ (bfd *, struct bfd_link_info *); +++extern int bfd_elf_discard_info +++ (bfd *, struct bfd_link_info *); +++extern unsigned int _bfd_elf_default_action_discarded +++ (struct bfd_section *); +++extern struct bfd_section *_bfd_elf_tls_setup +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elf_link_create_dynamic_sections +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_omit_section_dynsym_default +++ (bfd *, struct bfd_link_info *, asection *); +++extern bfd_boolean _bfd_elf_omit_section_dynsym_all +++ (bfd *, struct bfd_link_info *, asection *); +++extern bfd_boolean _bfd_elf_create_dynamic_sections +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_create_got_section +++ (bfd *, struct bfd_link_info *); +++extern asection *_bfd_elf_section_for_symbol +++ (struct elf_reloc_cookie *, unsigned long, bfd_boolean); +++extern struct elf_link_hash_entry *_bfd_elf_define_linkage_sym +++ (bfd *, struct bfd_link_info *, asection *, const char *); +++extern void _bfd_elf_init_1_index_section +++ (bfd *, struct bfd_link_info *); +++extern void _bfd_elf_init_2_index_sections +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elfcore_make_pseudosection +++ (bfd *, char *, size_t, ufile_ptr); +++extern char *_bfd_elfcore_strndup +++ (bfd *, char *, size_t); +++ +++extern Elf_Internal_Rela *_bfd_elf_link_read_relocs +++ (bfd *, asection *, void *, Elf_Internal_Rela *, bfd_boolean); +++ +++extern bfd_boolean _bfd_elf_link_output_relocs +++ (bfd *, asection *, Elf_Internal_Shdr *, Elf_Internal_Rela *, +++ struct elf_link_hash_entry **); +++ +++extern bfd_boolean _bfd_elf_adjust_dynamic_copy +++ (struct bfd_link_info *, struct elf_link_hash_entry *, asection *); +++ +++extern bfd_boolean _bfd_elf_dynamic_symbol_p +++ (struct elf_link_hash_entry *, struct bfd_link_info *, bfd_boolean); +++ +++extern bfd_boolean _bfd_elf_symbol_refs_local_p +++ (struct elf_link_hash_entry *, struct bfd_link_info *, bfd_boolean); +++ +++extern bfd_reloc_status_type bfd_elf_perform_complex_relocation +++ (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *, bfd_vma); +++ +++extern bfd_boolean _bfd_elf_setup_sections +++ (bfd *); +++ +++extern struct bfd_link_hash_entry *bfd_elf_define_start_stop +++ (struct bfd_link_info *, const char *, asection *); +++ +++extern bfd_boolean _bfd_elf_init_file_header (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elf_final_write_processing (bfd *); +++ +++extern bfd_cleanup bfd_elf32_object_p +++ (bfd *); +++extern bfd_cleanup bfd_elf32_core_file_p +++ (bfd *); +++extern char *bfd_elf32_core_file_failing_command +++ (bfd *); +++extern int bfd_elf32_core_file_failing_signal +++ (bfd *); +++extern bfd_boolean bfd_elf32_core_file_matches_executable_p +++ (bfd *, bfd *); +++extern int bfd_elf32_core_file_pid +++ (bfd *); +++extern bfd_boolean _bfd_elf32_core_find_build_id +++ (bfd *, bfd_vma); +++ +++extern bfd_boolean bfd_elf32_swap_symbol_in +++ (bfd *, const void *, const void *, Elf_Internal_Sym *); +++extern void bfd_elf32_swap_symbol_out +++ (bfd *, const Elf_Internal_Sym *, void *, void *); +++extern void bfd_elf32_swap_reloc_in +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++extern void bfd_elf32_swap_reloc_out +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++extern void bfd_elf32_swap_reloca_in +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++extern void bfd_elf32_swap_reloca_out +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++extern void bfd_elf32_swap_phdr_in +++ (bfd *, const Elf32_External_Phdr *, Elf_Internal_Phdr *); +++extern void bfd_elf32_swap_phdr_out +++ (bfd *, const Elf_Internal_Phdr *, Elf32_External_Phdr *); +++extern void bfd_elf32_swap_dyn_in +++ (bfd *, const void *, Elf_Internal_Dyn *); +++extern void bfd_elf32_swap_dyn_out +++ (bfd *, const Elf_Internal_Dyn *, void *); +++extern long bfd_elf32_slurp_symbol_table +++ (bfd *, asymbol **, bfd_boolean); +++extern bfd_boolean bfd_elf32_write_shdrs_and_ehdr +++ (bfd *); +++extern int bfd_elf32_write_out_phdrs +++ (bfd *, const Elf_Internal_Phdr *, unsigned int); +++extern bfd_boolean bfd_elf32_checksum_contents +++ (bfd * , void (*) (const void *, size_t, void *), void *); +++extern void bfd_elf32_write_relocs +++ (bfd *, asection *, void *); +++extern bfd_boolean bfd_elf32_slurp_reloc_table +++ (bfd *, asection *, asymbol **, bfd_boolean); +++ +++extern bfd_cleanup bfd_elf64_object_p +++ (bfd *); +++extern bfd_cleanup bfd_elf64_core_file_p +++ (bfd *); +++extern char *bfd_elf64_core_file_failing_command +++ (bfd *); +++extern int bfd_elf64_core_file_failing_signal +++ (bfd *); +++extern bfd_boolean bfd_elf64_core_file_matches_executable_p +++ (bfd *, bfd *); +++extern int bfd_elf64_core_file_pid +++ (bfd *); +++extern bfd_boolean _bfd_elf64_core_find_build_id +++ (bfd *, bfd_vma); +++ +++extern bfd_boolean bfd_elf64_swap_symbol_in +++ (bfd *, const void *, const void *, Elf_Internal_Sym *); +++extern void bfd_elf64_swap_symbol_out +++ (bfd *, const Elf_Internal_Sym *, void *, void *); +++extern void bfd_elf64_swap_reloc_in +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++extern void bfd_elf64_swap_reloc_out +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++extern void bfd_elf64_swap_reloca_in +++ (bfd *, const bfd_byte *, Elf_Internal_Rela *); +++extern void bfd_elf64_swap_reloca_out +++ (bfd *, const Elf_Internal_Rela *, bfd_byte *); +++extern void bfd_elf64_swap_phdr_in +++ (bfd *, const Elf64_External_Phdr *, Elf_Internal_Phdr *); +++extern void bfd_elf64_swap_phdr_out +++ (bfd *, const Elf_Internal_Phdr *, Elf64_External_Phdr *); +++extern void bfd_elf64_swap_dyn_in +++ (bfd *, const void *, Elf_Internal_Dyn *); +++extern void bfd_elf64_swap_dyn_out +++ (bfd *, const Elf_Internal_Dyn *, void *); +++extern long bfd_elf64_slurp_symbol_table +++ (bfd *, asymbol **, bfd_boolean); +++extern bfd_boolean bfd_elf64_write_shdrs_and_ehdr +++ (bfd *); +++extern int bfd_elf64_write_out_phdrs +++ (bfd *, const Elf_Internal_Phdr *, unsigned int); +++extern bfd_boolean bfd_elf64_checksum_contents +++ (bfd * , void (*) (const void *, size_t, void *), void *); +++extern void bfd_elf64_write_relocs +++ (bfd *, asection *, void *); +++extern bfd_boolean bfd_elf64_slurp_reloc_table +++ (bfd *, asection *, asymbol **, bfd_boolean); +++ +++extern bfd_boolean _bfd_elf_default_relocs_compatible +++ (const bfd_target *, const bfd_target *); +++ +++extern bfd_boolean _bfd_elf_relocs_compatible +++ (const bfd_target *, const bfd_target *); +++extern bfd_boolean _bfd_elf_notice_as_needed +++ (bfd *, struct bfd_link_info *, enum notice_asneeded_action); +++ +++extern struct elf_link_hash_entry *_bfd_elf_archive_symbol_lookup +++ (bfd *, struct bfd_link_info *, const char *); +++extern bfd_boolean bfd_elf_link_add_symbols +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_add_dynamic_entry +++ (struct bfd_link_info *, bfd_vma, bfd_vma); +++extern bfd_boolean _bfd_elf_strip_zero_sized_dynamic_sections +++ (struct bfd_link_info *); +++extern int bfd_elf_add_dt_needed_tag +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_link_check_relocs +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean bfd_elf_link_record_dynamic_symbol +++ (struct bfd_link_info *, struct elf_link_hash_entry *); +++ +++extern int bfd_elf_link_record_local_dynamic_symbol +++ (struct bfd_link_info *, bfd *, long); +++ +++extern bfd_boolean _bfd_elf_close_and_cleanup +++ (bfd *); +++ +++extern bfd_boolean _bfd_elf_common_definition +++ (Elf_Internal_Sym *); +++ +++extern unsigned int _bfd_elf_common_section_index +++ (asection *); +++ +++extern asection *_bfd_elf_common_section +++ (asection *); +++ +++extern bfd_vma _bfd_elf_default_got_elt_size +++(bfd *, struct bfd_link_info *, struct elf_link_hash_entry *, bfd *, +++ unsigned long); +++ +++extern bfd_reloc_status_type _bfd_elf_rel_vtable_reloc_fn +++ (bfd *, arelent *, struct bfd_symbol *, void *, +++ asection *, bfd *, char **); +++ +++extern bfd_boolean bfd_elf_final_link +++ (bfd *, struct bfd_link_info *); +++ +++extern void _bfd_elf_gc_keep +++ (struct bfd_link_info *info); +++ +++extern bfd_boolean bfd_elf_gc_mark_dynamic_ref_symbol +++ (struct elf_link_hash_entry *h, void *inf); +++ +++extern bfd_boolean bfd_elf_gc_sections +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean bfd_elf_gc_record_vtinherit +++ (bfd *, asection *, struct elf_link_hash_entry *, bfd_vma); +++ +++extern bfd_boolean bfd_elf_gc_record_vtentry +++ (bfd *, asection *, struct elf_link_hash_entry *, bfd_vma); +++ +++extern asection *_bfd_elf_gc_mark_hook +++ (asection *, struct bfd_link_info *, Elf_Internal_Rela *, +++ struct elf_link_hash_entry *, Elf_Internal_Sym *); +++ +++extern asection *_bfd_elf_gc_mark_rsec +++ (struct bfd_link_info *, asection *, elf_gc_mark_hook_fn, +++ struct elf_reloc_cookie *, bfd_boolean *); +++ +++extern bfd_boolean _bfd_elf_gc_mark_reloc +++ (struct bfd_link_info *, asection *, elf_gc_mark_hook_fn, +++ struct elf_reloc_cookie *); +++ +++extern bfd_boolean _bfd_elf_gc_mark_fdes +++ (struct bfd_link_info *, asection *, asection *, elf_gc_mark_hook_fn, +++ struct elf_reloc_cookie *); +++ +++extern bfd_boolean _bfd_elf_gc_mark +++ (struct bfd_link_info *, asection *, elf_gc_mark_hook_fn); +++ +++extern bfd_boolean _bfd_elf_gc_mark_extra_sections +++ (struct bfd_link_info *, elf_gc_mark_hook_fn); +++ +++extern bfd_boolean bfd_elf_gc_common_finalize_got_offsets +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean bfd_elf_gc_common_final_link +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean bfd_elf_reloc_symbol_deleted_p +++ (bfd_vma, void *); +++ +++extern struct elf_segment_map * _bfd_elf_make_dynamic_segment +++ (bfd *, asection *); +++ +++extern bfd_boolean _bfd_elf_map_sections_to_segments +++ (bfd *, struct bfd_link_info *); +++ +++extern bfd_boolean _bfd_elf_is_function_type (unsigned int); +++ +++extern bfd_size_type _bfd_elf_maybe_function_sym (const asymbol *, asection *, +++ bfd_vma *); +++ +++extern asection *_bfd_elf_plt_get_reloc_section (bfd *, const char *); +++ +++extern int bfd_elf_get_default_section_type (flagword); +++ +++extern bfd_boolean bfd_elf_lookup_section_flags +++ (struct bfd_link_info *, struct flag_info *, asection *); +++ +++extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section +++ (bfd * abfd, asection * section); +++ +++/* PowerPC @tls opcode transform/validate. */ +++extern unsigned int _bfd_elf_ppc_at_tls_transform +++ (unsigned int, unsigned int); +++/* PowerPC @tprel opcode transform/validate. */ +++extern unsigned int _bfd_elf_ppc_at_tprel_transform +++ (unsigned int, unsigned int); +++/* PowerPC elf_object_p tweak. */ +++extern bfd_boolean _bfd_elf_ppc_set_arch (bfd *); +++/* PowerPC .gnu.attributes handling common to both 32-bit and 64-bit. */ +++extern bfd_boolean _bfd_elf_ppc_merge_fp_attributes +++ (bfd *, struct bfd_link_info *); +++ +++/* Return an upper bound on the number of bytes required to store a +++ copy of ABFD's program header table entries. Return -1 if an error +++ occurs; bfd_get_error will return an appropriate code. */ +++extern long bfd_get_elf_phdr_upper_bound +++ (bfd *abfd); +++ +++/* Copy ABFD's program header table entries to *PHDRS. The entries +++ will be stored as an array of Elf_Internal_Phdr structures, as +++ defined in include/elf/internal.h. To find out how large the +++ buffer needs to be, call bfd_get_elf_phdr_upper_bound. +++ +++ Return the number of program header table entries read, or -1 if an +++ error occurs; bfd_get_error will return an appropriate code. */ +++extern int bfd_get_elf_phdrs +++ (bfd *abfd, void *phdrs); +++ +++/* Exported interface for writing elf corefile notes. */ +++extern char *elfcore_write_note +++ (bfd *, char *, int *, const char *, int, const void *, int); +++extern char *elfcore_write_prpsinfo +++ (bfd *, char *, int *, const char *, const char *); +++extern char *elfcore_write_prstatus +++ (bfd *, char *, int *, long, int, const void *); +++extern char * elfcore_write_pstatus +++ (bfd *, char *, int *, long, int, const void *); +++extern char *elfcore_write_prfpreg +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_prxfpreg +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_xstatereg +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_vmx +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_vsx +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tar +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_ppr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_dscr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_ebb +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_pmu +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cgpr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cfpr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cvmx +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cvsx +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_spr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_ctar +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cppr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_ppc_tm_cdscr +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_timer +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_todcmp +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_todpreg +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_ctrs +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_prefix +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_last_break +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_system_call +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_tdb +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_vxrs_low +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_vxrs_high +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_gs_cb +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_s390_gs_bc +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_arm_vfp +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_aarch_tls +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_aarch_hw_break +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_aarch_hw_watch +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_aarch_sve +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_aarch_pauth +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_arc_v2 +++ (bfd *, char *, int *, const void *, int); +++extern char *elfcore_write_lwpstatus +++ (bfd *, char *, int *, long, int, const void *); +++extern char *elfcore_write_register_note +++ (bfd *, char *, int *, const char *, const void *, int); +++ +++/* Internal structure which holds information to be included in the +++ PRPSINFO section of Linux core files. +++ +++ This is an "internal" structure in the sense that it should be used +++ to pass information to BFD (via the `elfcore_write_linux_prpsinfo' +++ function), so things like endianess shouldn't be an issue. This +++ structure will eventually be converted in one of the +++ `elf_external_linux_*' structures and written out to an output bfd +++ by one of the functions declared below. */ +++ +++struct elf_internal_linux_prpsinfo +++ { +++ char pr_state; /* Numeric process state. */ +++ char pr_sname; /* Char for pr_state. */ +++ char pr_zomb; /* Zombie. */ +++ char pr_nice; /* Nice val. */ +++ unsigned long pr_flag; /* Flags. */ +++ unsigned int pr_uid; +++ unsigned int pr_gid; +++ int pr_pid, pr_ppid, pr_pgrp, pr_sid; +++ char pr_fname[16 + 1]; /* Filename of executable. */ +++ char pr_psargs[80 + 1]; /* Initial part of arg list. */ +++ }; +++ +++/* Linux/most 32-bit archs. */ +++extern char *elfcore_write_linux_prpsinfo32 +++ (bfd *, char *, int *, const struct elf_internal_linux_prpsinfo *); +++ +++/* Linux/most 64-bit archs. */ +++extern char *elfcore_write_linux_prpsinfo64 +++ (bfd *, char *, int *, const struct elf_internal_linux_prpsinfo *); +++ +++extern bfd *_bfd_elf32_bfd_from_remote_memory +++ (bfd *templ, bfd_vma ehdr_vma, bfd_size_type size, bfd_vma *loadbasep, +++ int (*target_read_memory) (bfd_vma, bfd_byte *, bfd_size_type)); +++extern bfd *_bfd_elf64_bfd_from_remote_memory +++ (bfd *templ, bfd_vma ehdr_vma, bfd_size_type size, bfd_vma *loadbasep, +++ int (*target_read_memory) (bfd_vma, bfd_byte *, bfd_size_type)); +++ +++extern bfd_vma bfd_elf_obj_attr_size (bfd *); +++extern void bfd_elf_set_obj_attr_contents (bfd *, bfd_byte *, bfd_vma); +++extern int bfd_elf_get_obj_attr_int (bfd *, int, unsigned int); +++extern void bfd_elf_add_obj_attr_int (bfd *, int, unsigned int, unsigned int); +++#define bfd_elf_add_proc_attr_int(BFD, TAG, VALUE) \ +++ bfd_elf_add_obj_attr_int ((BFD), OBJ_ATTR_PROC, (TAG), (VALUE)) +++extern void bfd_elf_add_obj_attr_string (bfd *, int, unsigned int, const char *); +++#define bfd_elf_add_proc_attr_string(BFD, TAG, VALUE) \ +++ bfd_elf_add_obj_attr_string ((BFD), OBJ_ATTR_PROC, (TAG), (VALUE)) +++extern void bfd_elf_add_obj_attr_int_string (bfd *, int, unsigned int, +++ unsigned int, const char *); +++#define bfd_elf_add_proc_attr_int_string(BFD, TAG, INTVAL, STRVAL) \ +++ bfd_elf_add_obj_attr_int_string ((BFD), OBJ_ATTR_PROC, (TAG), \ +++ (INTVAL), (STRVAL)) +++ +++extern char *_bfd_elf_attr_strdup (bfd *, const char *); +++extern void _bfd_elf_copy_obj_attributes (bfd *, bfd *); +++extern int _bfd_elf_obj_attrs_arg_type (bfd *, int, unsigned int); +++extern void _bfd_elf_parse_attributes (bfd *, Elf_Internal_Shdr *); +++extern bfd_boolean _bfd_elf_merge_object_attributes +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_merge_unknown_attribute_low (bfd *, bfd *, int); +++extern bfd_boolean _bfd_elf_merge_unknown_attribute_list (bfd *, bfd *); +++extern Elf_Internal_Shdr *_bfd_elf_single_rel_hdr (asection *sec); +++extern bfd_boolean elf_read_notes (bfd *, file_ptr, bfd_size_type, size_t); +++ +++extern bfd_boolean _bfd_elf_parse_gnu_properties +++ (bfd *, Elf_Internal_Note *); +++extern elf_property * _bfd_elf_get_property +++ (bfd *, unsigned int, unsigned int); +++extern bfd *_bfd_elf_link_setup_gnu_properties +++ (struct bfd_link_info *); +++extern bfd_size_type _bfd_elf_convert_gnu_property_size +++ (bfd *, bfd *); +++extern bfd_boolean _bfd_elf_convert_gnu_properties +++ (bfd *, asection *, bfd *, bfd_byte **, bfd_size_type *); +++ +++/* The linker may need to keep track of the number of relocs that it +++ decides to copy as dynamic relocs in check_relocs for each symbol. +++ This is so that it can later discard them if they are found to be +++ unnecessary. We can store the information in a field extending the +++ regular ELF linker hash table. */ +++ +++struct elf_dyn_relocs +++{ +++ struct elf_dyn_relocs *next; +++ +++ /* The input section of the reloc. */ +++ asection *sec; +++ +++ /* Total number of relocs copied for the input section. */ +++ bfd_size_type count; +++ +++ /* Number of pc-relative relocs copied for the input section. */ +++ bfd_size_type pc_count; +++}; +++ +++extern bfd_boolean _bfd_elf_create_ifunc_sections +++ (bfd *, struct bfd_link_info *); +++extern bfd_boolean _bfd_elf_allocate_ifunc_dyn_relocs +++ (struct bfd_link_info *, struct elf_link_hash_entry *, +++ struct elf_dyn_relocs **, unsigned int, unsigned int, +++ unsigned int, bfd_boolean); +++ +++extern void elf_append_rela (bfd *, asection *, Elf_Internal_Rela *); +++extern void elf_append_rel (bfd *, asection *, Elf_Internal_Rela *); +++ +++extern bfd_vma elf64_r_info (bfd_vma, bfd_vma); +++extern bfd_vma elf64_r_sym (bfd_vma); +++extern bfd_vma elf32_r_info (bfd_vma, bfd_vma); +++extern bfd_vma elf32_r_sym (bfd_vma); +++ +++extern bfd_boolean is_debuginfo_file (bfd *); +++ +++ +++extern bfd_boolean _bfd_elf_init_secondary_reloc_section +++ (bfd *, Elf_Internal_Shdr *, const char *, unsigned int); +++extern bfd_boolean _bfd_elf_slurp_secondary_reloc_section +++ (bfd *, asection *, asymbol **); +++extern bfd_boolean _bfd_elf_copy_special_section_fields +++ (const bfd *, bfd *, const Elf_Internal_Shdr *, Elf_Internal_Shdr *); +++extern bfd_boolean _bfd_elf_write_secondary_reloc_section +++ (bfd *, asection *); +++extern unsigned int _bfd_elf_symbol_section_index +++ (bfd *, elf_symbol_type *); +++ +++extern asection *_bfd_elf_readonly_dynrelocs +++ (struct elf_link_hash_entry *); +++extern bfd_boolean _bfd_elf_maybe_set_textrel +++ (struct elf_link_hash_entry *, void *); +++ +++extern bfd_boolean _bfd_elf_add_dynamic_tags +++ (bfd *, struct bfd_link_info *, bfd_boolean); +++ +++/* Large common section. */ +++extern asection _bfd_elf_large_com_section; +++ +++/* Hash for local symbol with the first section id, ID, in the input +++ file and the local symbol index, SYM. */ +++#define ELF_LOCAL_SYMBOL_HASH(ID, SYM) \ +++ (((((ID) & 0xffU) << 24) | (((ID) & 0xff00) << 8)) \ +++ ^ (SYM) ^ (((ID) & 0xffff0000U) >> 16)) +++ +++/* This is the condition under which finish_dynamic_symbol will be called. +++ If our finish_dynamic_symbol isn't called, we'll need to do something +++ about initializing any .plt and .got entries in relocate_section. */ +++#define WILL_CALL_FINISH_DYNAMIC_SYMBOL(DYN, SHARED, H) \ +++ ((DYN) \ +++ && ((SHARED) || !(H)->forced_local) \ +++ && ((H)->dynindx != -1 || (H)->forced_local)) +++ +++/* This macro is to avoid lots of duplicated code in the body +++ of xxx_relocate_section() in the various elfxx-xxxx.c files. */ +++#define RELOC_FOR_GLOBAL_SYMBOL(info, input_bfd, input_section, rel, \ +++ r_symndx, symtab_hdr, sym_hashes, \ +++ h, sec, relocation, \ +++ unresolved_reloc, warned, ignored) \ +++ do \ +++ { \ +++ /* It seems this can happen with erroneous or unsupported \ +++ input (mixing a.out and elf in an archive, for example.) */ \ +++ if (sym_hashes == NULL) \ +++ return FALSE; \ +++ \ +++ h = sym_hashes[r_symndx - symtab_hdr->sh_info]; \ +++ \ +++ if (info->wrap_hash != NULL \ +++ && (input_section->flags & SEC_DEBUGGING) != 0) \ +++ h = ((struct elf_link_hash_entry *) \ +++ unwrap_hash_lookup (info, input_bfd, &h->root)); \ +++ \ +++ while (h->root.type == bfd_link_hash_indirect \ +++ || h->root.type == bfd_link_hash_warning) \ +++ h = (struct elf_link_hash_entry *) h->root.u.i.link; \ +++ \ +++ warned = FALSE; \ +++ ignored = FALSE; \ +++ unresolved_reloc = FALSE; \ +++ relocation = 0; \ +++ if (h->root.type == bfd_link_hash_defined \ +++ || h->root.type == bfd_link_hash_defweak) \ +++ { \ +++ sec = h->root.u.def.section; \ +++ if (sec == NULL \ +++ || sec->output_section == NULL) \ +++ /* Set a flag that will be cleared later if we find a \ +++ relocation value for this symbol. output_section \ +++ is typically NULL for symbols satisfied by a shared \ +++ library. */ \ +++ unresolved_reloc = TRUE; \ +++ else \ +++ relocation = (h->root.u.def.value \ +++ + sec->output_section->vma \ +++ + sec->output_offset); \ +++ } \ +++ else if (h->root.type == bfd_link_hash_undefweak) \ +++ ; \ +++ else if (info->unresolved_syms_in_objects == RM_IGNORE \ +++ && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT) \ +++ ignored = TRUE; \ +++ else if (!bfd_link_relocatable (info)) \ +++ { \ +++ bfd_boolean err; \ +++ err = (info->unresolved_syms_in_objects == RM_DIAGNOSE && \ +++ !info->warn_unresolved_syms) \ +++ || ELF_ST_VISIBILITY (h->other) != STV_DEFAULT; \ +++ (*info->callbacks->undefined_symbol) (info, \ +++ h->root.root.string, \ +++ input_bfd, \ +++ input_section, \ +++ rel->r_offset, err); \ +++ warned = TRUE; \ +++ } \ +++ (void) unresolved_reloc; \ +++ (void) warned; \ +++ (void) ignored; \ +++ } \ +++ while (0) +++ +++/* This macro is to avoid lots of duplicated code in the body of the +++ loop over relocations in xxx_relocate_section() in the various +++ elfxx-xxxx.c files. +++ +++ Handle relocations against symbols from removed linkonce sections, +++ or sections discarded by a linker script. When doing a relocatable +++ link, we remove such relocations. Otherwise, we just want the +++ section contents zeroed and avoid any special processing. */ +++#define RELOC_AGAINST_DISCARDED_SECTION(info, input_bfd, input_section, \ +++ rel, count, relend, \ +++ howto, index, contents) \ +++ { \ +++ int i_; \ +++ _bfd_clear_contents (howto, input_bfd, input_section, \ +++ contents, rel[index].r_offset); \ +++ \ +++ if (bfd_link_relocatable (info) \ +++ && (input_section->flags & SEC_DEBUGGING)) \ +++ { \ +++ /* Only remove relocations in debug sections since other \ +++ sections may require relocations. */ \ +++ Elf_Internal_Shdr *rel_hdr; \ +++ \ +++ rel_hdr = _bfd_elf_single_rel_hdr (input_section->output_section); \ +++ \ +++ /* Avoid empty output section. */ \ +++ if (rel_hdr->sh_size > rel_hdr->sh_entsize) \ +++ { \ +++ rel_hdr->sh_size -= rel_hdr->sh_entsize; \ +++ rel_hdr = _bfd_elf_single_rel_hdr (input_section); \ +++ rel_hdr->sh_size -= rel_hdr->sh_entsize; \ +++ \ +++ memmove (rel, rel + count, \ +++ (relend - rel - count) * sizeof (*rel)); \ +++ \ +++ input_section->reloc_count -= count; \ +++ relend -= count; \ +++ rel--; \ +++ continue; \ +++ } \ +++ } \ +++ \ +++ for (i_ = 0; i_ < count; i_++) \ +++ { \ +++ rel[i_].r_info = 0; \ +++ rel[i_].r_addend = 0; \ +++ } \ +++ rel += count - 1; \ +++ continue; \ +++ } +++ +++/* Will a symbol be bound to the definition within the shared +++ library, if any. A unique symbol can never be bound locally. */ +++#define SYMBOLIC_BIND(INFO, H) \ +++ (!(H)->unique_global \ +++ && ((INFO)->symbolic \ +++ || (H)->start_stop \ +++ || ((INFO)->dynamic && !(H)->dynamic))) +++ +++/* Determine if a section contains CTF data, using its name. */ +++static inline bfd_boolean +++bfd_section_is_ctf (const asection *sec) +++{ +++ const char *name = bfd_section_name (sec); +++ return strncmp (name, ".ctf", 4) == 0 && (name[4] == 0 || name[4] == '.'); +++} +++ +++#ifdef __cplusplus +++} +++#endif +++#endif /* _LIBELF_H_ */ ++diff -Nuar gdb-10.2/bfd/elf.c gdb-10.2/bfd/elf.c ++--- gdb-10.2/bfd/elf.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/elf.c 2025-04-16 17:06:51.912086800 +0800 ++@@ -10921,6 +10921,7 @@ ++ ++ case bfd_arch_aarch64: ++ case bfd_arch_alpha: +++ case bfd_arch_sw_64: ++ case bfd_arch_sparc: ++ switch (note->type) ++ { ++diff -Nuar gdb-10.2/bfd/hosts/sw_64linux.h gdb-10.2/bfd/hosts/sw_64linux.h ++--- gdb-10.2/bfd/hosts/sw_64linux.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/hosts/sw_64linux.h 2025-04-16 17:06:51.922086800 +0800 ++@@ -0,0 +1,25 @@ +++/* Copyright (C) 2007-2019 Free Software Foundation, Inc. +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++/* Linux dumps "struct task_struct" at the end of the core-file. This +++ structure is currently 1080 bytes long, but we allow up to 4096 +++ bytes to allow for some future growth. */ +++#define TRAD_CORE_EXTRA_SIZE_ALLOWED 4096 +++#define TRAD_UNIX_CORE_FILE_FAILING_SIGNAL(abfd) \ +++ ((abfd)->tdata.trad_core_data->u.signal) ++diff -Nuar gdb-10.2/bfd/hosts/sw_64vms.h gdb-10.2/bfd/hosts/sw_64vms.h ++--- gdb-10.2/bfd/hosts/sw_64vms.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/hosts/sw_64vms.h 2025-04-16 17:06:51.922086800 +0800 ++@@ -0,0 +1,68 @@ +++/* alphavms.h -- BFD definitions for an openVMS host +++ Copyright (C) 1996-2019 Free Software Foundation, Inc. +++ Written by Klaus K?mpf (kkaempf@progis.de) +++ of proGIS Softwareentwicklung, Aachen, Germany +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++#ifdef PACKAGE +++#error sysdep.h must be included in lieu of config.h +++#endif +++ +++#include "config.h" +++#include "ansidecl.h" +++ +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++#include +++ +++#include "filenames.h" +++#include "fopen-vms.h" +++ +++#define NO_FCNTL 1 +++ +++#ifndef O_ACCMODE +++#define O_ACCMODE (O_RDONLY | O_WRONLY | O_RDWR) +++#endif +++ +++extern int getpagesize (void); +++extern char *stpcpy (char *, const char *); +++ +++/* No intl. */ +++#define gettext(Msgid) (Msgid) +++#define dgettext(Domainname, Msgid) (Msgid) +++#define dcgettext(Domainname, Msgid, Category) (Msgid) +++#define ngettext(Msgid1, Msgid2, n) \ +++ (n == 1 ? Msgid1 : Msgid2) +++#define dngettext(Domainname, Msgid1, Msgid2, n) \ +++ (n == 1 ? Msgid1 : Msgid2) +++#define dcngettext(Domainname, Msgid1, Msgid2, n, Category) \ +++ (n == 1 ? Msgid1 : Msgid2) +++#define textdomain(Domainname) do {} while (0) +++#define bindtextdomain(Domainname, Dirname) do {} while (0) +++#define _(String) (String) +++#define N_(String) (String) ++diff -Nuar gdb-10.2/bfd/libaout.h gdb-10.2/bfd/libaout.h ++--- gdb-10.2/bfd/libaout.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/libaout.h 2025-04-16 17:06:51.922086800 +0800 ++@@ -268,6 +268,7 @@ ++ M_PMAX_NETBSD = 139, /* NetBSD/pmax (MIPS little-endian) binary. */ ++ M_VAX_NETBSD = 140, /* NetBSD/vax binary. */ ++ M_ALPHA_NETBSD = 141, /* NetBSD/alpha binary. */ +++ M_SW_64_NETBSD = 142, /* NetBSD/sw_64 binary. */ ++ M_ARM6_NETBSD = 143, /* NetBSD/arm32 binary. */ ++ M_SPARCLET_1 = 147, /* 0x93, reserved. */ ++ M_POWERPC_NETBSD = 149, /* NetBSD/powerpc (big-endian) binary. */ ++diff -Nuar gdb-10.2/bfd/libbfd.h gdb-10.2/bfd/libbfd.h ++--- gdb-10.2/bfd/libbfd.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/libbfd.h 2025-04-16 17:06:51.922086800 +0800 ++@@ -433,10 +433,14 @@ ++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_cleanup _bfd_vms_lib_alpha_archive_p ++ (bfd *) ATTRIBUTE_HIDDEN; +++extern bfd_cleanup _bfd_vms_lib_sw_64_archive_p +++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_cleanup _bfd_vms_lib_ia64_archive_p ++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_boolean _bfd_vms_lib_alpha_mkarchive ++ (bfd *) ATTRIBUTE_HIDDEN; +++extern bfd_boolean _bfd_vms_lib_sw_64_mkarchive +++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_boolean _bfd_vms_lib_ia64_mkarchive ++ (bfd *) ATTRIBUTE_HIDDEN; ++ ++@@ -1085,6 +1089,9 @@ ++ "BFD_RELOC_8_FFnn", ++ "BFD_RELOC_32_PCREL_S2", ++ "BFD_RELOC_16_PCREL_S2", +++#ifndef XWB20200308 +++ "BFD_RELOC_20_PCREL_S2", +++#endif ++ "BFD_RELOC_23_PCREL_S2", ++ "BFD_RELOC_HI22", ++ "BFD_RELOC_LO10", ++@@ -1211,6 +1218,44 @@ ++ "BFD_RELOC_ALPHA_TPREL_HI16", ++ "BFD_RELOC_ALPHA_TPREL_LO16", ++ "BFD_RELOC_ALPHA_TPREL16", +++ "BFD_RELOC_SW_64_GPDISP_HI16", +++ "BFD_RELOC_SW_64_GPDISP_LO16", +++ "BFD_RELOC_SW_64_GPDISP", +++ "BFD_RELOC_SW_64_LITERAL", +++ "BFD_RELOC_SW_64_ELF_LITERAL", +++ "BFD_RELOC_SW_64_LITUSE", +++ "BFD_RELOC_SW_64_HINT", +++ "BFD_RELOC_SW_64_LINKAGE", +++ "BFD_RELOC_SW_64_CODEADDR", +++ "BFD_RELOC_SW_64_GPREL_HI16", +++ "BFD_RELOC_SW_64_GPREL_LO16", +++ "BFD_RELOC_SW_64_BRSGP", +++ "BFD_RELOC_SW_64_NOP", +++ "BFD_RELOC_SW_64_ELF_LITERAL", +++ "BFD_RELOC_SW_64_LITUSE", +++ "BFD_RELOC_SW_64_HINT", +++ "BFD_RELOC_SW_64_LINKAGE", +++ "BFD_RELOC_SW_64_CODEADDR", +++ "BFD_RELOC_SW_64_GPREL_HI16", +++ "BFD_RELOC_SW_64_GPREL_LO16", +++ "BFD_RELOC_SW_64_BRSGP", +++ "BFD_RELOC_SW_64_NOP", +++ "BFD_RELOC_SW_64_BSR", +++ "BFD_RELOC_SW_64_LDA", +++ "BFD_RELOC_SW_64_BOH", +++ "BFD_RELOC_SW_64_TLSGD", +++ "BFD_RELOC_SW_64_TLSLDM", +++ "BFD_RELOC_SW_64_DTPMOD64", +++ "BFD_RELOC_SW_64_GOTDTPREL16", +++ "BFD_RELOC_SW_64_DTPREL64", +++ "BFD_RELOC_SW_64_DTPREL_HI16", +++ "BFD_RELOC_SW_64_DTPREL_LO16", +++ "BFD_RELOC_SW_64_DTPREL16", +++ "BFD_RELOC_SW_64_GOTTPREL16", +++ "BFD_RELOC_SW_64_TPREL64", +++ "BFD_RELOC_SW_64_TPREL_HI16", +++ "BFD_RELOC_SW_64_TPREL_LO16", +++ "BFD_RELOC_SW_64_TPREL16", ++ "BFD_RELOC_MIPS_JMP", ++ "BFD_RELOC_MICROMIPS_JMP", ++ "BFD_RELOC_MIPS16_JMP", ++diff -Nuar gdb-10.2/bfd/libbfd-in.h gdb-10.2/bfd/libbfd-in.h ++--- gdb-10.2/bfd/libbfd-in.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/libbfd-in.h 2025-04-16 17:06:51.922086800 +0800 ++@@ -428,10 +428,14 @@ ++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_cleanup _bfd_vms_lib_alpha_archive_p ++ (bfd *) ATTRIBUTE_HIDDEN; +++extern bfd_cleanup _bfd_vms_lib_sw_64_archive_p +++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_cleanup _bfd_vms_lib_ia64_archive_p ++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_boolean _bfd_vms_lib_alpha_mkarchive ++ (bfd *) ATTRIBUTE_HIDDEN; +++extern bfd_boolean _bfd_vms_lib_sw_64_mkarchive +++ (bfd *) ATTRIBUTE_HIDDEN; ++ extern bfd_boolean _bfd_vms_lib_ia64_mkarchive ++ (bfd *) ATTRIBUTE_HIDDEN; ++ ++diff -Nuar gdb-10.2/bfd/mach-o.c gdb-10.2/bfd/mach-o.c ++--- gdb-10.2/bfd/mach-o.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/mach-o.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -609,6 +609,7 @@ ++ case BFD_MACH_O_CPU_TYPE_SPARC: return "SPARC"; ++ case BFD_MACH_O_CPU_TYPE_I860: return "I860"; ++ case BFD_MACH_O_CPU_TYPE_ALPHA: return "ALPHA"; +++ case BFD_MACH_O_CPU_TYPE_SW_64: return "SW_64"; ++ case BFD_MACH_O_CPU_TYPE_POWERPC: return "PPC"; ++ case BFD_MACH_O_CPU_TYPE_POWERPC_64: return "PPC64"; ++ case BFD_MACH_O_CPU_TYPE_X86_64: return "X86_64"; ++@@ -1181,6 +1182,9 @@ ++ case BFD_MACH_O_CPU_TYPE_ALPHA: ++ *type = bfd_arch_alpha; ++ break; +++ case BFD_MACH_O_CPU_TYPE_SW_64: +++ *type = bfd_arch_sw_64; +++ break; ++ case BFD_MACH_O_CPU_TYPE_POWERPC: ++ *type = bfd_arch_powerpc; ++ *subtype = bfd_mach_ppc; ++diff -Nuar gdb-10.2/bfd/Makefile.am gdb-10.2/bfd/Makefile.am ++--- gdb-10.2/bfd/Makefile.am 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/Makefile.am 2025-04-16 17:06:51.902086800 +0800 ++@@ -92,6 +92,7 @@ ++ ALL_MACHINES = \ ++ cpu-aarch64.lo \ ++ cpu-alpha.lo \ +++ cpu-sw_64.lo \ ++ cpu-arc.lo \ ++ cpu-arm.lo \ ++ cpu-avr.lo \ ++@@ -176,6 +177,7 @@ ++ ALL_MACHINES_CFILES = \ ++ cpu-aarch64.c \ ++ cpu-alpha.c \ +++ cpu-sw_64.c \ ++ cpu-arc.c \ ++ cpu-arm.c \ ++ cpu-avr.c \ ++@@ -536,6 +538,7 @@ ++ aix5ppc-core.lo \ ++ aout64.lo \ ++ coff-alpha.lo \ +++ coff-sw_64.lo \ ++ coff-x86_64.lo \ ++ coff64-rs6000.lo \ ++ elf32-ia64.lo \ ++@@ -543,6 +546,7 @@ ++ elf32-score.lo \ ++ elf32-score7.lo \ ++ elf64-alpha.lo \ +++ elf64-sw_64.lo \ ++ elf64-gen.lo \ ++ elf64-hppa.lo \ ++ elf64-ia64.lo \ ++@@ -572,18 +576,21 @@ ++ pei-x86_64.lo \ ++ pepigen.lo \ ++ pex64igen.lo \ ++- vms-alpha.lo +++ vms-alpha.lo \ +++ vms-sw_64.lo ++ ++ BFD64_BACKENDS_CFILES = \ ++ aix5ppc-core.c \ ++ aout64.c \ ++ coff-alpha.c \ +++ coff-sw_64.c \ ++ coff-x86_64.c \ ++ coff64-rs6000.c \ ++ elf32-mips.c \ ++ elf32-score.c \ ++ elf32-score7.c \ ++ elf64-alpha.c \ +++ elf64-sw_64.c \ ++ elf64-gen.c \ ++ elf64-hppa.c \ ++ elf64-ia64-vms.c \ ++@@ -609,7 +616,8 @@ ++ pe-x86_64.c \ ++ pei-ia64.c \ ++ pei-x86_64.c \ ++- vms-alpha.c +++ vms-alpha.c \ +++ vms-sw_64.c ++ ++ OPTIONAL_BACKENDS = \ ++ aix386-core.lo \ ++diff -Nuar gdb-10.2/bfd/Makefile.in gdb-10.2/bfd/Makefile.in ++--- gdb-10.2/bfd/Makefile.in 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/Makefile.in 2025-04-16 17:06:51.902086800 +0800 ++@@ -517,6 +517,7 @@ ++ ALL_MACHINES = \ ++ cpu-aarch64.lo \ ++ cpu-alpha.lo \ +++ cpu-sw_64.lo \ ++ cpu-arc.lo \ ++ cpu-arm.lo \ ++ cpu-avr.lo \ ++@@ -601,6 +602,7 @@ ++ ALL_MACHINES_CFILES = \ ++ cpu-aarch64.c \ ++ cpu-alpha.c \ +++ cpu-sw_64.c \ ++ cpu-arc.c \ ++ cpu-arm.c \ ++ cpu-avr.c \ ++@@ -963,6 +965,7 @@ ++ aix5ppc-core.lo \ ++ aout64.lo \ ++ coff-alpha.lo \ +++ coff-sw_64.lo \ ++ coff-x86_64.lo \ ++ coff64-rs6000.lo \ ++ elf32-ia64.lo \ ++@@ -970,6 +973,7 @@ ++ elf32-score.lo \ ++ elf32-score7.lo \ ++ elf64-alpha.lo \ +++ elf64-sw_64.lo \ ++ elf64-gen.lo \ ++ elf64-hppa.lo \ ++ elf64-ia64.lo \ ++@@ -999,18 +1003,20 @@ ++ pei-x86_64.lo \ ++ pepigen.lo \ ++ pex64igen.lo \ ++- vms-alpha.lo ++- +++ vms-alpha.lo \ +++ vms-sw_64.lo ++ BFD64_BACKENDS_CFILES = \ ++ aix5ppc-core.c \ ++ aout64.c \ ++ coff-alpha.c \ +++ coff-sw_64.c \ ++ coff-x86_64.c \ ++ coff64-rs6000.c \ ++ elf32-mips.c \ ++ elf32-score.c \ ++ elf32-score7.c \ ++ elf64-alpha.c \ +++ elf64-sw_64.c \ ++ elf64-gen.c \ ++ elf64-hppa.c \ ++ elf64-ia64-vms.c \ ++@@ -1036,8 +1042,8 @@ ++ pe-x86_64.c \ ++ pei-ia64.c \ ++ pei-x86_64.c \ ++- vms-alpha.c ++- +++ vms-alpha.c \ +++ vms-sw_64.c ++ OPTIONAL_BACKENDS = \ ++ aix386-core.lo \ ++ cisco-core.lo \ ++@@ -1303,6 +1309,7 @@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cf-i386lynx.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cisco-core.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/coff-alpha.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/coff-sw_64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/coff-bfd.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/coff-go32.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/coff-i386.Plo@am__quote@ ++@@ -1323,6 +1330,7 @@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/corefile.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-aarch64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-alpha.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-sw_64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-arc.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-arm.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/cpu-avr.Plo@am__quote@ ++@@ -1487,6 +1495,7 @@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf32.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-aarch64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-alpha.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-sw_64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-bpf.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-gen.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/elf64-hppa.Plo@am__quote@ ++@@ -1574,6 +1583,7 @@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vaxnetbsd.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/verilog.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vms-alpha.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vms-sw_64.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vms-lib.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vms-misc.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/wasm-module.Plo@am__quote@ ++diff -Nuar gdb-10.2/bfd/makefile.vms gdb-10.2/bfd/makefile.vms ++--- gdb-10.2/bfd/makefile.vms 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/makefile.vms 2025-04-16 17:06:51.922086800 +0800 ++@@ -35,7 +35,11 @@ ++ OBJS:=vms-alpha.obj,vms-lib.obj,vms-misc.obj,cpu-alpha.obj ++ DEFS=SELECT_VECS="&alpha_vms_vec",SELECT_ARCHITECTURES="&bfd_alpha_arch" ++ endif ++- +++ifeq ($(ARCH),SW_64) +++HOSTFILE=sw_64vms.h +++OBJS:=vms-sw_64.obj,vms-lib.obj,vms-misc.obj,cpu-sw_64.obj +++DEFS=SELECT_VECS="&sw_64_vms_vec",SELECT_ARCHITECTURES="&bfd_sw_64_arch" +++endif ++ OBJS:=$(OBJS),archive.obj,archive64.obj,archures.obj,bfd.obj,bfdio.obj,\ ++ binary.obj,cache.obj,coffgen.obj,compress.obj,corefile.obj,dwarf2.obj,\ ++ elf.obj,format.obj,hash.obj,ihex.obj,init.obj,libbfd.obj,linker.obj,\ ++diff -Nuar gdb-10.2/bfd/netbsd-core.c gdb-10.2/bfd/netbsd-core.c ++--- gdb-10.2/bfd/netbsd-core.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/netbsd-core.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -180,7 +180,9 @@ ++ case M_ALPHA_NETBSD: ++ bfd_default_set_arch_mach (abfd, bfd_arch_alpha, 0); ++ break; ++- +++ case M_SW_64_NETBSD: +++ bfd_default_set_arch_mach (abfd, bfd_arch_sw_64, 0); +++ break; ++ case M_ARM6_NETBSD: ++ bfd_default_set_arch_mach (abfd, bfd_arch_arm, bfd_mach_arm_3); ++ break; ++diff -Nuar gdb-10.2/bfd/targets.c gdb-10.2/bfd/targets.c ++--- gdb-10.2/bfd/targets.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/targets.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -673,6 +673,11 @@ ++ extern const bfd_target alpha_elf64_fbsd_vec; ++ extern const bfd_target alpha_vms_vec; ++ extern const bfd_target alpha_vms_lib_txt_vec; +++extern const bfd_target sw_64_ecoff_le_vec; +++extern const bfd_target sw_64_elf64_vec; +++extern const bfd_target sw_64_elf64_fbsd_vec; +++extern const bfd_target sw_64_vms_vec; +++extern const bfd_target sw_64_vms_lib_txt_vec; ++ extern const bfd_target am33_elf32_linux_vec; ++ extern const bfd_target aout_vec; ++ extern const bfd_target arc_elf32_be_vec; ++@@ -986,9 +991,14 @@ ++ &alpha_elf64_vec, ++ &alpha_elf64_fbsd_vec, ++ &alpha_vms_vec, +++ +++ &sw_64_ecoff_le_vec, +++ &sw_64_elf64_vec, +++ &sw_64_elf64_fbsd_vec, +++ &sw_64_vms_vec, ++ #endif ++ &alpha_vms_lib_txt_vec, ++- +++ &sw_64_vms_lib_txt_vec, ++ &am33_elf32_linux_vec, ++ ++ #if 0 ++diff -Nuar gdb-10.2/bfd/vms-lib.c gdb-10.2/bfd/vms-lib.c ++--- gdb-10.2/bfd/vms-lib.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/bfd/vms-lib.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -56,6 +56,7 @@ ++ { ++ vms_lib_vax, ++ vms_lib_alpha, +++ vms_lib_sw_64, ++ vms_lib_ia64, ++ vms_lib_txt ++ }; ++@@ -533,6 +534,15 @@ ++ return NULL; ++ } ++ break; +++ case vms_lib_sw_64: +++ if ((lhd.type != LBR__C_TYP_EOBJ && lhd.type != LBR__C_TYP_ESHSTB) +++ || majorid != LBR_MAJORID +++ || lhd.nindex != 2) +++ { +++ bfd_set_error (bfd_error_wrong_format); +++ return NULL; +++ } +++ break; ++ case vms_lib_ia64: ++ if ((lhd.type != LBR__C_TYP_IOBJ && lhd.type != LBR__C_TYP_ISHSTB) ++ || majorid != LBR_ELFMAJORID ++@@ -710,7 +720,13 @@ ++ { ++ return _bfd_vms_lib_archive_p (abfd, vms_lib_alpha); ++ } +++/* Standard function for sw_64 libraries. */ ++ +++const bfd_target * +++_bfd_vms_lib_sw_64_archive_p (bfd *abfd) +++{ +++ return _bfd_vms_lib_archive_p (abfd, vms_lib_sw_64); +++} ++ /* Standard function for ia64 libraries. */ ++ ++ bfd_cleanup ++@@ -749,6 +765,11 @@ ++ tdata->mhd_size = offsetof (struct vms_mhd, pad1); ++ tdata->type = LBR__C_TYP_EOBJ; ++ break; +++ case vms_lib_sw_64: +++ tdata->ver = LBR_MAJORID; +++ tdata->mhd_size = offsetof (struct vms_mhd, pad1); +++ tdata->type = LBR__C_TYP_EOBJ; +++ break; ++ case vms_lib_ia64: ++ tdata->ver = LBR_ELFMAJORID; ++ tdata->mhd_size = sizeof (struct vms_mhd); ++@@ -774,6 +795,12 @@ ++ } ++ ++ bfd_boolean +++_bfd_vms_lib_sw_64_mkarchive (bfd *abfd) +++{ +++ return _bfd_vms_lib_mkarchive (abfd, vms_lib_sw_64); +++} +++ +++bfd_boolean ++ _bfd_vms_lib_ia64_mkarchive (bfd *abfd) ++ { ++ return _bfd_vms_lib_mkarchive (abfd, vms_lib_ia64); ++@@ -2326,6 +2353,9 @@ ++ case vms_lib_alpha: ++ saneid = LHD_SANEID3; ++ break; +++ case vms_lib_sw_64: +++ saneid = LHD_SANEID3; +++ break; ++ case vms_lib_ia64: ++ saneid = LHD_SANEID6; ++ break; ++@@ -2425,6 +2455,59 @@ ++ _bfd_bool_bfd_false_error, ++ _bfd_bool_bfd_false_error, ++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error +++ }, +++ BFD_JUMP_TABLE_GENERIC (_bfd_generic), +++ BFD_JUMP_TABLE_COPY (_bfd_generic), +++ BFD_JUMP_TABLE_CORE (_bfd_nocore), +++ BFD_JUMP_TABLE_ARCHIVE (_bfd_vms_lib), +++ BFD_JUMP_TABLE_SYMBOLS (_bfd_nosymbols), +++ BFD_JUMP_TABLE_RELOCS (_bfd_norelocs), +++ BFD_JUMP_TABLE_WRITE (_bfd_nowrite), +++ BFD_JUMP_TABLE_LINK (_bfd_nolink), +++ BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic), +++ +++ NULL, +++ +++ NULL +++}; +++/* Add sw_64 target for text library. This costs almost nothing and is useful to +++ read VMS library on the host. */ +++ +++const bfd_target sw_64_vms_lib_txt_vec = +++{ +++ "vms-libtxt", /* Name. */ +++ bfd_target_unknown_flavour, +++ BFD_ENDIAN_UNKNOWN, /* byteorder */ +++ BFD_ENDIAN_UNKNOWN, /* header_byteorder */ +++ 0, /* Object flags. */ +++ 0, /* Sect flags. */ +++ 0, /* symbol_leading_char. */ +++ ' ', /* ar_pad_char. */ +++ 15, /* ar_max_namelen. */ +++ 0, /* match priority. */ +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, +++ { /* bfd_check_format. */ +++ _bfd_dummy_target, +++ _bfd_dummy_target, +++ _bfd_vms_lib_txt_archive_p, +++ _bfd_dummy_target +++ }, +++ { /* bfd_set_format. */ +++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error +++ }, +++ { /* bfd_write_contents. */ +++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error, +++ _bfd_bool_bfd_false_error, ++ _bfd_bool_bfd_false_error ++ }, ++ BFD_JUMP_TABLE_GENERIC (_bfd_generic), ++diff -Nuar gdb-10.2/bfd/vms-sw_64.c gdb-10.2/bfd/vms-sw_64.c ++--- gdb-10.2/bfd/vms-sw_64.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/bfd/vms-sw_64.c 2025-04-16 17:06:51.922086800 +0800 ++@@ -0,0 +1,9625 @@ +++/* vms.c -- BFD back-end for EVAX (openVMS/Sw_64) files. +++ Copyright (C) 1996-2018 Free Software Foundation, Inc. +++ +++ Initial version written by Klaus Kaempf (kkaempf@rmi.de) +++ Major rewrite by Adacore. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++/* TODO: +++ o overlayed sections +++ o PIC +++ o Generation of shared image +++ o Relocation optimizations +++ o EISD for the stack +++ o Vectors isect +++ o 64 bits sections +++ o Entry point +++ o LIB$INITIALIZE +++ o protected sections (for messages) +++ ... +++*/ +++ +++#include "sysdep.h" +++#include "bfd.h" +++#include "bfdlink.h" +++#include "libbfd.h" +++#include "bfdver.h" +++ +++#include "vms.h" +++#include "vms/eihd.h" +++#include "vms/eiha.h" +++#include "vms/eihi.h" +++#include "vms/eihs.h" +++#include "vms/eisd.h" +++#include "vms/dmt.h" +++#include "vms/dst.h" +++#include "vms/eihvn.h" +++#include "vms/eobjrec.h" +++#include "vms/egsd.h" +++#include "vms/egps.h" +++#include "vms/esgps.h" +++#include "vms/eeom.h" +++#include "vms/emh.h" +++#include "vms/eiaf.h" +++#include "vms/shl.h" +++#include "vms/eicp.h" +++#include "vms/etir.h" +++#include "vms/egsy.h" +++#include "vms/esdf.h" +++#include "vms/esdfm.h" +++#include "vms/esdfv.h" +++#include "vms/esrf.h" +++#include "vms/egst.h" +++#include "vms/eidc.h" +++#include "vms/dsc.h" +++#include "vms/prt.h" +++#include "vms/internal.h" +++ +++ +++#define MIN(a,b) ((a) < (b) ? (a) : (b)) +++ +++/* The r_type field in a reloc is one of the following values. */ +++#define SW_64_R_IGNORE 0 +++#define SW_64_R_REFQUAD 1 +++#define SW_64_R_BRADDR 2 +++#define SW_64_R_HINT 3 +++#define SW_64_R_SREL16 4 +++#define SW_64_R_SREL32 5 +++#define SW_64_R_SREL64 6 +++#define SW_64_R_OP_PUSH 7 +++#define SW_64_R_OP_STORE 8 +++#define SW_64_R_OP_PSUB 9 +++#define SW_64_R_OP_PRSHIFT 10 +++#define SW_64_R_LINKAGE 11 +++#define SW_64_R_REFLONG 12 +++#define SW_64_R_CODEADDR 13 +++#define SW_64_R_NOP 14 +++#define SW_64_R_BSR 15 +++#define SW_64_R_LDA 16 +++#define SW_64_R_BOH 17 +++ +++/* These are used with DST_S_C_LINE_NUM. */ +++#define DST_S_C_LINE_NUM_HEADER_SIZE 4 +++ +++/* These are used with DST_S_C_SOURCE */ +++ +++#define DST_S_B_PCLINE_UNSBYTE 1 +++#define DST_S_W_PCLINE_UNSWORD 1 +++#define DST_S_L_PCLINE_UNSLONG 1 +++ +++#define DST_S_B_MODBEG_NAME 14 +++#define DST_S_L_RTNBEG_ADDRESS 5 +++#define DST_S_B_RTNBEG_NAME 13 +++#define DST_S_L_RTNEND_SIZE 5 +++ +++/* These are used with DST_S_C_SOURCE. */ +++#define DST_S_C_SOURCE_HEADER_SIZE 4 +++ +++#define DST_S_B_SRC_DF_LENGTH 1 +++#define DST_S_W_SRC_DF_FILEID 3 +++#define DST_S_B_SRC_DF_FILENAME 20 +++#define DST_S_B_SRC_UNSBYTE 1 +++#define DST_S_W_SRC_UNSWORD 1 +++#define DST_S_L_SRC_UNSLONG 1 +++ +++/* Debugger symbol definitions. */ +++ +++#define DBG_S_L_DMT_MODBEG 0 +++#define DBG_S_L_DST_SIZE 4 +++#define DBG_S_W_DMT_PSECT_COUNT 8 +++#define DBG_S_C_DMT_HEADER_SIZE 12 +++ +++#define DBG_S_L_DMT_PSECT_START 0 +++#define DBG_S_L_DMT_PSECT_LENGTH 4 +++#define DBG_S_C_DMT_PSECT_SIZE 8 +++ +++/* VMS module header. */ +++ +++struct hdr_struct +++{ +++ char hdr_b_strlvl; +++ int hdr_l_arch1; +++ int hdr_l_arch2; +++ int hdr_l_recsiz; +++ char *hdr_t_name; +++ char *hdr_t_version; +++ char *hdr_t_date; +++ char *hdr_c_lnm; +++ char *hdr_c_src; +++ char *hdr_c_ttl; +++}; +++ +++#define EMH_DATE_LENGTH 17 +++ +++/* VMS End-Of-Module records (EOM/EEOM). */ +++ +++struct eom_struct +++{ +++ unsigned int eom_l_total_lps; +++ unsigned short eom_w_comcod; +++ bfd_boolean eom_has_transfer; +++ unsigned char eom_b_tfrflg; +++ unsigned int eom_l_psindx; +++ unsigned int eom_l_tfradr; +++}; +++ +++struct vms_symbol_entry +++{ +++ bfd *owner; +++ +++ /* Common fields. */ +++ unsigned char typ; +++ unsigned char data_type; +++ unsigned short flags; +++ +++ /* Section and offset/value of the symbol. */ +++ unsigned int value; +++ asection *section; +++ +++ /* Section and offset/value for the entry point (only for subprg). */ +++ asection *code_section; +++ unsigned int code_value; +++ +++ /* Symbol vector offset. */ +++ unsigned int symbol_vector; +++ +++ /* Length of the name. */ +++ unsigned char namelen; +++ +++ char name[1]; +++}; +++ +++/* Stack value for push/pop commands. */ +++ +++struct stack_struct +++{ +++ bfd_vma value; +++ unsigned int reloc; +++}; +++ +++#define STACKSIZE 128 +++ +++/* A minimal decoding of DST compilation units. We only decode +++ what's needed to get to the line number information. */ +++ +++struct fileinfo +++{ +++ char *name; +++ unsigned int srec; +++}; +++ +++struct srecinfo +++{ +++ struct srecinfo *next; +++ unsigned int line; +++ unsigned int sfile; +++ unsigned int srec; +++}; +++ +++struct lineinfo +++{ +++ struct lineinfo *next; +++ bfd_vma address; +++ unsigned int line; +++}; +++ +++struct funcinfo +++{ +++ struct funcinfo *next; +++ char *name; +++ bfd_vma low; +++ bfd_vma high; +++}; +++ +++struct module +++{ +++ /* Chain the previously read compilation unit. */ +++ struct module *next; +++ +++ /* The module name. */ +++ char *name; +++ +++ /* The start offset and size of debug info in the DST section. */ +++ unsigned int modbeg; +++ unsigned int size; +++ +++ /* The lowest and highest addresses contained in this compilation +++ unit as specified in the compilation unit header. */ +++ bfd_vma low; +++ bfd_vma high; +++ +++ /* The listing line table. */ +++ struct lineinfo *line_table; +++ +++ /* The source record table. */ +++ struct srecinfo *srec_table; +++ +++ /* A list of the functions found in this module. */ +++ struct funcinfo *func_table; +++ +++ /* Current allocation of file_table. */ +++ unsigned int file_table_count; +++ +++ /* An array of the files making up this module. */ +++ struct fileinfo *file_table; +++}; +++ +++/* BFD private data for sw_64-vms. */ +++ +++struct vms_private_data_struct +++{ +++ /* If true, relocs have been read. */ +++ bfd_boolean reloc_done; +++ +++ /* Record input buffer. */ +++ struct vms_rec_rd recrd; +++ struct vms_rec_wr recwr; +++ +++ struct hdr_struct hdr_data; /* data from HDR/EMH record */ +++ struct eom_struct eom_data; /* data from EOM/EEOM record */ +++ +++ /* Transfer addresses (entry points). */ +++ bfd_vma transfer_address[4]; +++ +++ /* Array of GSD sections to get the correspond BFD one. */ +++ unsigned int section_max; /* Size of the sections array. */ +++ unsigned int section_count; /* Number of GSD sections. */ +++ asection **sections; +++ +++ /* Array of raw symbols. */ +++ struct vms_symbol_entry **syms; +++ +++ /* Canonicalized symbols. */ +++ asymbol **csymbols; +++ +++ /* Number of symbols. */ +++ unsigned int gsd_sym_count; +++ /* Size of the syms array. */ +++ unsigned int max_sym_count; +++ /* Number of procedure symbols. */ +++ unsigned int norm_sym_count; +++ +++ /* Stack used to evaluate TIR/ETIR commands. */ +++ struct stack_struct *stack; +++ int stackptr; +++ +++ /* Content reading. */ +++ asection *image_section; /* section for image_ptr */ +++ file_ptr image_offset; /* Offset for image_ptr. */ +++ +++ struct module *modules; /* list of all compilation units */ +++ +++ /* The DST section. */ +++ asection *dst_section; +++ +++ unsigned int dst_ptr_offsets_count; /* # of offsets in following array */ +++ unsigned int *dst_ptr_offsets; /* array of saved image_ptr offsets */ +++ +++ /* Shared library support */ +++ bfd_vma symvva; /* relative virtual address of symbol vector */ +++ unsigned int ident; +++ unsigned char matchctl; +++ +++ /* Shared library index. This is used for input bfd while linking. */ +++ unsigned int shr_index; +++ +++ /* Used to place structures in the file. */ +++ file_ptr file_pos; +++ +++ /* Simply linked list of eisd. */ +++ struct vms_internal_eisd_map *eisd_head; +++ struct vms_internal_eisd_map *eisd_tail; +++ +++ /* Simply linked list of eisd for shared libraries. */ +++ struct vms_internal_eisd_map *gbl_eisd_head; +++ struct vms_internal_eisd_map *gbl_eisd_tail; +++ +++ /* linkage index counter used by conditional store commands */ +++ unsigned int vms_linkage_index; +++}; +++ +++#define PRIV2(abfd, name) \ +++ (((struct vms_private_data_struct *)(abfd)->tdata.any)->name) +++#define PRIV(name) PRIV2(abfd,name) +++ +++ +++/* Used to keep extra VMS specific information for a given section. +++ +++ reloc_size holds the size of the relocation stream, note this +++ is very different from the number of relocations as VMS relocations +++ are variable length. +++ +++ reloc_stream is the actual stream of relocation entries. */ +++ +++struct vms_section_data_struct +++{ +++ /* Maximnum number of entries in sec->relocation. */ +++ unsigned reloc_max; +++ +++ /* Corresponding eisd. Used only while generating executables. */ +++ struct vms_internal_eisd_map *eisd; +++ +++ /* PSC flags to be clear. */ +++ flagword no_flags; +++ +++ /* PSC flags to be set. */ +++ flagword flags; +++}; +++ +++#define vms_section_data(sec) \ +++ ((struct vms_section_data_struct *)sec->used_by_bfd) +++ +++/* To be called from the debugger. */ +++struct vms_private_data_struct *bfd_vms_get_data (bfd *); +++ +++static int vms_get_remaining_object_record (bfd *, unsigned int); +++static bfd_boolean _bfd_vms_slurp_object_records (bfd * abfd); +++static void sw_64_vms_add_fixup_lp (struct bfd_link_info *, bfd *, bfd *); +++static void sw_64_vms_add_fixup_ca (struct bfd_link_info *, bfd *, bfd *); +++static void sw_64_vms_add_fixup_qr (struct bfd_link_info *, bfd *, bfd *, +++ bfd_vma); +++static void sw_64_vms_add_fixup_lr (struct bfd_link_info *, unsigned int, +++ bfd_vma); +++static void sw_64_vms_add_lw_reloc (struct bfd_link_info *); +++static void sw_64_vms_add_qw_reloc (struct bfd_link_info *); +++ +++struct vector_type +++{ +++ unsigned int max_el; +++ unsigned int nbr_el; +++ void *els; +++}; +++ +++/* Number of elements in VEC. */ +++ +++#define VEC_COUNT(VEC) ((VEC).nbr_el) +++ +++/* Get the address of the Nth element. */ +++ +++#define VEC_EL(VEC, TYPE, N) (((TYPE *)((VEC).els))[N]) +++ +++#define VEC_INIT(VEC) \ +++ do { \ +++ (VEC).max_el = 0; \ +++ (VEC).nbr_el = 0; \ +++ (VEC).els = NULL; \ +++ } while (0) +++ +++/* Be sure there is room for a new element. */ +++ +++static void vector_grow1 (struct vector_type *vec, size_t elsz); +++ +++/* Allocate room for a new element and return its address. */ +++ +++#define VEC_APPEND(VEC, TYPE) \ +++ (vector_grow1 (&VEC, sizeof (TYPE)), &VEC_EL(VEC, TYPE, (VEC).nbr_el++)) +++ +++/* Append an element. */ +++ +++#define VEC_APPEND_EL(VEC, TYPE, EL) \ +++ (*(VEC_APPEND (VEC, TYPE)) = EL) +++ +++struct sw_64_vms_vma_ref +++{ +++ bfd_vma vma; /* Vma in the output. */ +++ bfd_vma ref; /* Reference in the input. */ +++}; +++ +++struct sw_64_vms_shlib_el +++{ +++ bfd *abfd; +++ bfd_boolean has_fixups; +++ +++ struct vector_type lp; /* Vector of bfd_vma. */ +++ struct vector_type ca; /* Vector of bfd_vma. */ +++ struct vector_type qr; /* Vector of struct sw_64_vms_vma_ref. */ +++}; +++ +++/* Sw_64 VMS linker hash table. */ +++ +++struct sw_64_vms_link_hash_table +++{ +++ struct bfd_link_hash_table root; +++ +++ /* Vector of shared libraries. */ +++ struct vector_type shrlibs; +++ +++ /* Fixup section. */ +++ asection *fixup; +++ +++ /* Base address. Used by fixups. */ +++ bfd_vma base_addr; +++}; +++ +++#define sw_64_vms_link_hash(INFO) \ +++ ((struct sw_64_vms_link_hash_table *)(INFO->hash)) +++ +++/* Sw_64 VMS linker hash table entry. */ +++ +++struct sw_64_vms_link_hash_entry +++{ +++ struct bfd_link_hash_entry root; +++ +++ /* Pointer to the original vms symbol. */ +++ struct vms_symbol_entry *sym; +++}; +++ +++/* Image reading. */ +++ +++/* Read & process EIHD record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_eihd (bfd *abfd, unsigned int *eisd_offset, +++ unsigned int *eihs_offset) +++{ +++ unsigned int imgtype, size; +++ bfd_vma symvva; +++ struct vms_eihd *eihd = (struct vms_eihd *)PRIV (recrd.rec); +++ +++ vms_debug2 ((8, "_bfd_vms_slurp_eihd\n")); +++ +++ /* PR 21813: Check for an undersized record. */ +++ if (PRIV (recrd.buf_size) < sizeof (* eihd)) +++ { +++ _bfd_error_handler (_("corrupt EIHD record - size is too small")); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ size = bfd_getl32 (eihd->size); +++ imgtype = bfd_getl32 (eihd->imgtype); +++ +++ if (imgtype == EIHD__K_EXE || imgtype == EIHD__K_LIM) +++ abfd->flags |= EXEC_P; +++ +++ symvva = bfd_getl64 (eihd->symvva); +++ if (symvva != 0) +++ { +++ PRIV (symvva) = symvva; +++ abfd->flags |= DYNAMIC; +++ } +++ +++ PRIV (ident) = bfd_getl32 (eihd->ident); +++ PRIV (matchctl) = eihd->matchctl; +++ +++ *eisd_offset = bfd_getl32 (eihd->isdoff); +++ *eihs_offset = bfd_getl32 (eihd->symdbgoff); +++ +++ vms_debug2 ((4, "EIHD size %d imgtype %d symvva 0x%lx eisd %d eihs %d\n", +++ size, imgtype, (unsigned long)symvva, +++ *eisd_offset, *eihs_offset)); +++ +++ return TRUE; +++} +++ +++/* Read & process EISD record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_eisd (bfd *abfd, unsigned int offset) +++{ +++ int section_count = 0; +++ +++ vms_debug2 ((8, "_bfd_vms_slurp_eisd\n")); +++ +++ while (1) +++ { +++ struct vms_eisd *eisd; +++ unsigned int rec_size; +++ unsigned int size; +++ bfd_uint64_t vaddr; +++ unsigned int flags; +++ unsigned int vbn; +++ char *name = NULL; +++ asection *section; +++ flagword bfd_flags; +++ +++ /* PR 17512: file: 3d9e9fe9. +++ 12 is the offset of the eisdsize field from the start of the record (8) +++ plus the size of the eisdsize field (4). */ +++ if (offset >= PRIV (recrd.rec_size) - 12) +++ return FALSE; +++ eisd = (struct vms_eisd *)(PRIV (recrd.rec) + offset); +++ rec_size = bfd_getl32 (eisd->eisdsize); +++ if (rec_size == 0) +++ break; +++ +++ /* Skip to next block if pad. */ +++ if (rec_size == 0xffffffff) +++ { +++ offset = (offset + VMS_BLOCK_SIZE) & ~(VMS_BLOCK_SIZE - 1); +++ continue; +++ } +++ +++ /* Make sure that there is enough data present in the record. */ +++ /* FIXME: Should we use sizeof (struct vms_eisd) rather than just 32 here ? */ +++ if (rec_size < 32) +++ return FALSE; +++ /* Make sure that the record is not too big either. */ +++ if (offset + rec_size >= PRIV (recrd.rec_size)) +++ return FALSE; +++ +++ offset += rec_size; +++ +++ size = bfd_getl32 (eisd->secsize); +++ vaddr = bfd_getl64 (eisd->virt_addr); +++ flags = bfd_getl32 (eisd->flags); +++ vbn = bfd_getl32 (eisd->vbn); +++ +++ vms_debug2 ((4, "EISD at 0x%x size 0x%x addr 0x%lx flags 0x%x blk %d\n", +++ offset, size, (unsigned long)vaddr, flags, vbn)); +++ +++ /* VMS combines psects from .obj files into isects in the .exe. This +++ process doesn't preserve enough information to reliably determine +++ what's in each section without examining the data. This is +++ especially true of DWARF debug sections. */ +++ bfd_flags = SEC_ALLOC; +++ if (vbn != 0) +++ bfd_flags |= SEC_HAS_CONTENTS | SEC_LOAD; +++ +++ if (flags & EISD__M_EXE) +++ bfd_flags |= SEC_CODE; +++ +++ if (flags & EISD__M_NONSHRADR) +++ bfd_flags |= SEC_DATA; +++ +++ if (!(flags & EISD__M_WRT)) +++ bfd_flags |= SEC_READONLY; +++ +++ if (flags & EISD__M_DZRO) +++ bfd_flags |= SEC_DATA; +++ +++ if (flags & EISD__M_FIXUPVEC) +++ bfd_flags |= SEC_DATA; +++ +++ if (flags & EISD__M_CRF) +++ bfd_flags |= SEC_DATA; +++ +++ if (flags & EISD__M_GBL) +++ { +++ if (rec_size < offsetof (struct vms_eisd, gblnam)) +++ return FALSE; +++ else if (rec_size < sizeof (struct vms_eisd)) +++ name = _bfd_vms_save_counted_string (eisd->gblnam, +++ rec_size - offsetof (struct vms_eisd, gblnam)); +++ else +++ name = _bfd_vms_save_counted_string (eisd->gblnam, EISD__K_GBLNAMLEN); +++ bfd_flags |= SEC_COFF_SHARED_LIBRARY; +++ bfd_flags &= ~(SEC_ALLOC | SEC_LOAD); +++ } +++ else if (flags & EISD__M_FIXUPVEC) +++ name = "$FIXUPVEC$"; +++ else if (eisd->type == EISD__K_USRSTACK) +++ name = "$STACK$"; +++ else +++ { +++ const char *pfx; +++ +++ name = (char*) bfd_alloc (abfd, 32); +++ if (flags & EISD__M_DZRO) +++ pfx = "BSS"; +++ else if (flags & EISD__M_EXE) +++ pfx = "CODE"; +++ else if (!(flags & EISD__M_WRT)) +++ pfx = "RO"; +++ else +++ pfx = "LOCAL"; +++ BFD_ASSERT (section_count < 999); +++ sprintf (name, "$%s_%03d$", pfx, section_count++); +++ } +++ +++ section = bfd_make_section (abfd, name); +++ +++ if (!section) +++ return FALSE; +++ +++ section->filepos = vbn ? VMS_BLOCK_SIZE * (vbn - 1) : 0; +++ section->size = size; +++ section->vma = vaddr; +++ +++ if (!bfd_set_section_flags (abfd, section, bfd_flags)) +++ return FALSE; +++ } +++ +++ return TRUE; +++} +++ +++/* Read & process EIHS record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_eihs (bfd *abfd, unsigned int offset) +++{ +++ unsigned char *p = PRIV (recrd.rec) + offset; +++ unsigned int gstvbn; +++ unsigned int gstsize ATTRIBUTE_UNUSED; +++ unsigned int dstvbn; +++ unsigned int dstsize; +++ unsigned int dmtvbn; +++ unsigned int dmtbytes; +++ asection *section; +++ +++ /* PR 21611: Check that offset is valid. */ +++ if (offset > PRIV (recrd.rec_size) - (EIHS__L_DMTBYTES + 4)) +++ { +++ _bfd_error_handler (_("unable to read EIHS record at offset %#x"), +++ offset); +++ bfd_set_error (bfd_error_file_truncated); +++ return FALSE; +++ } +++ +++ gstvbn = bfd_getl32 (p + EIHS__L_GSTVBN); +++ gstsize = bfd_getl32 (p + EIHS__L_GSTSIZE); +++ dstvbn = bfd_getl32 (p + EIHS__L_DSTVBN); +++ dstsize = bfd_getl32 (p + EIHS__L_DSTSIZE); +++ dmtvbn = bfd_getl32 (p + EIHS__L_DMTVBN); +++ dmtbytes = bfd_getl32 (p + EIHS__L_DMTBYTES); +++ +++#if VMS_DEBUG +++ vms_debug (8, "_bfd_vms_slurp_ihs\n"); +++ vms_debug (4, "EIHS record gstvbn %d gstsize %d dstvbn %d dstsize %d dmtvbn %d dmtbytes %d\n", +++ gstvbn, gstsize, dstvbn, dstsize, dmtvbn, dmtbytes); +++#endif +++ +++ if (dstvbn) +++ { +++ flagword bfd_flags = SEC_HAS_CONTENTS | SEC_DEBUGGING; +++ +++ section = bfd_make_section (abfd, "$DST$"); +++ if (!section) +++ return FALSE; +++ +++ section->size = dstsize; +++ section->filepos = VMS_BLOCK_SIZE * (dstvbn - 1); +++ +++ if (!bfd_set_section_flags (abfd, section, bfd_flags)) +++ return FALSE; +++ +++ PRIV (dst_section) = section; +++ abfd->flags |= (HAS_DEBUG | HAS_LINENO); +++ } +++ +++ if (dmtvbn) +++ { +++ flagword bfd_flags = SEC_HAS_CONTENTS | SEC_DEBUGGING; +++ +++ section = bfd_make_section (abfd, "$DMT$"); +++ if (!section) +++ return FALSE; +++ +++ section->size = dmtbytes; +++ section->filepos = VMS_BLOCK_SIZE * (dmtvbn - 1); +++ +++ if (!bfd_set_section_flags (abfd, section, bfd_flags)) +++ return FALSE; +++ } +++ +++ if (gstvbn) +++ { +++ if (bfd_seek (abfd, VMS_BLOCK_SIZE * (gstvbn - 1), SEEK_SET)) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return FALSE; +++ } +++ +++ if (!_bfd_vms_slurp_object_records (abfd)) +++ return FALSE; +++ +++ abfd->flags |= HAS_SYMS; +++ } +++ +++ return TRUE; +++} +++ +++/* Object file reading. */ +++ +++/* Object file input functions. */ +++ +++/* Get next record from object file to vms_buf. +++ Set PRIV(buf_size) and return it +++ +++ This is a little tricky since it should be portable. +++ +++ The openVMS object file has 'variable length' which means that +++ read() returns data in chunks of (hopefully) correct and expected +++ size. The linker (and other tools on VMS) depend on that. Unix +++ doesn't know about 'formatted' files, so reading and writing such +++ an object file in a Unix environment is not trivial. +++ +++ With the tool 'file' (available on all VMS FTP sites), one +++ can view and change the attributes of a file. Changing from +++ 'variable length' to 'fixed length, 512 bytes' reveals the +++ record size at the first 2 bytes of every record. The same +++ may happen during the transfer of object files from VMS to Unix, +++ at least with UCX, the DEC implementation of TCP/IP. +++ +++ The VMS format repeats the size at bytes 2 & 3 of every record. +++ +++ On the first call (file_format == FF_UNKNOWN) we check if +++ the first and the third byte pair (!) of the record match. +++ If they do it's an object file in an Unix environment or with +++ wrong attributes (FF_FOREIGN), else we should be in a VMS +++ environment where read() returns the record size (FF_NATIVE). +++ +++ Reading is always done in 2 steps: +++ 1. first just the record header is read and the size extracted, +++ 2. then the read buffer is adjusted and the remaining bytes are +++ read in. +++ +++ All file I/O is done on even file positions. */ +++ +++#define VMS_OBJECT_ADJUSTMENT 2 +++ +++static void +++maybe_adjust_record_pointer_for_object (bfd *abfd) +++{ +++ /* Set the file format once for all on the first invocation. */ +++ if (PRIV (recrd.file_format) == FF_UNKNOWN) +++ { +++ if (PRIV (recrd.rec)[0] == PRIV (recrd.rec)[4] +++ && PRIV (recrd.rec)[1] == PRIV (recrd.rec)[5]) +++ PRIV (recrd.file_format) = FF_FOREIGN; +++ else +++ PRIV (recrd.file_format) = FF_NATIVE; +++ } +++ +++ /* The adjustment is needed only in an Unix environment. */ +++ if (PRIV (recrd.file_format) == FF_FOREIGN) +++ PRIV (recrd.rec) += VMS_OBJECT_ADJUSTMENT; +++} +++ +++/* Implement step #1 of the object record reading procedure. +++ Return the record type or -1 on failure. */ +++ +++static int +++_bfd_vms_get_object_record (bfd *abfd) +++{ +++ unsigned int test_len = 6; +++ int type; +++ +++ vms_debug2 ((8, "_bfd_vms_get_obj_record\n")); +++ +++ /* Skip alignment byte if the current position is odd. */ +++ if (PRIV (recrd.file_format) == FF_FOREIGN && (bfd_tell (abfd) & 1)) +++ { +++ if (bfd_bread (PRIV (recrd.buf), 1, abfd) != 1) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return -1; +++ } +++ } +++ +++ /* Read the record header */ +++ if (bfd_bread (PRIV (recrd.buf), test_len, abfd) != test_len) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return -1; +++ } +++ +++ /* Reset the record pointer. */ +++ PRIV (recrd.rec) = PRIV (recrd.buf); +++ maybe_adjust_record_pointer_for_object (abfd); +++ +++ if (vms_get_remaining_object_record (abfd, test_len) <= 0) +++ return -1; +++ +++ type = bfd_getl16 (PRIV (recrd.rec)); +++ +++ vms_debug2 ((8, "_bfd_vms_get_obj_record: rec %p, size %d, type %d\n", +++ PRIV (recrd.rec), PRIV (recrd.rec_size), type)); +++ +++ return type; +++} +++ +++/* Implement step #2 of the object record reading procedure. +++ Return the size of the record or 0 on failure. */ +++ +++static int +++vms_get_remaining_object_record (bfd *abfd, unsigned int read_so_far) +++{ +++ unsigned int to_read; +++ +++ vms_debug2 ((8, "vms_get_remaining_obj_record\n")); +++ +++ /* Extract record size. */ +++ PRIV (recrd.rec_size) = bfd_getl16 (PRIV (recrd.rec) + 2); +++ +++ if (PRIV (recrd.rec_size) == 0) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return 0; +++ } +++ +++ /* That's what the linker manual says. */ +++ if (PRIV (recrd.rec_size) > EOBJ__C_MAXRECSIZ) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return 0; +++ } +++ +++ /* Take into account object adjustment. */ +++ to_read = PRIV (recrd.rec_size); +++ if (PRIV (recrd.file_format) == FF_FOREIGN) +++ to_read += VMS_OBJECT_ADJUSTMENT; +++ +++ /* Adjust the buffer. */ +++ if (to_read > PRIV (recrd.buf_size)) +++ { +++ PRIV (recrd.buf) +++ = (unsigned char *) bfd_realloc (PRIV (recrd.buf), to_read); +++ if (PRIV (recrd.buf) == NULL) +++ return 0; +++ PRIV (recrd.buf_size) = to_read; +++ } +++ /* PR 17512: file: 025-1974-0.004. */ +++ else if (to_read <= read_so_far) +++ return 0; +++ +++ /* Read the remaining record. */ +++ to_read -= read_so_far; +++ +++ vms_debug2 ((8, "vms_get_remaining_obj_record: to_read %d\n", to_read)); +++ +++ if (bfd_bread (PRIV (recrd.buf) + read_so_far, to_read, abfd) != to_read) +++ { +++ bfd_set_error (bfd_error_file_truncated); +++ return 0; +++ } +++ +++ /* Reset the record pointer. */ +++ PRIV (recrd.rec) = PRIV (recrd.buf); +++ maybe_adjust_record_pointer_for_object (abfd); +++ +++ vms_debug2 ((8, "vms_get_remaining_obj_record: size %d\n", +++ PRIV (recrd.rec_size))); +++ +++ return PRIV (recrd.rec_size); +++} +++ +++/* Read and process emh record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_ehdr (bfd *abfd) +++{ +++ unsigned char *ptr; +++ unsigned char *vms_rec; +++ unsigned char *end; +++ int subtype; +++ +++ vms_rec = PRIV (recrd.rec); +++ /* PR 17512: file: 62736583. */ +++ end = PRIV (recrd.buf) + PRIV (recrd.buf_size); +++ +++ vms_debug2 ((2, "HDR/EMH\n")); +++ +++ subtype = bfd_getl16 (vms_rec + 4); +++ +++ vms_debug2 ((3, "subtype %d\n", subtype)); +++ +++ switch (subtype) +++ { +++ case EMH__C_MHD: +++ /* Module header. */ +++ if (vms_rec + 21 >= end) +++ goto fail; +++ PRIV (hdr_data).hdr_b_strlvl = vms_rec[6]; +++ PRIV (hdr_data).hdr_l_arch1 = bfd_getl32 (vms_rec + 8); +++ PRIV (hdr_data).hdr_l_arch2 = bfd_getl32 (vms_rec + 12); +++ PRIV (hdr_data).hdr_l_recsiz = bfd_getl32 (vms_rec + 16); +++ if ((vms_rec + 20 + vms_rec[20] + 1) >= end) +++ goto fail; +++ PRIV (hdr_data).hdr_t_name = _bfd_vms_save_counted_string (vms_rec + 20, vms_rec[20]); +++ ptr = vms_rec + 20 + vms_rec[20] + 1; +++ if ((ptr + *ptr + 1) >= end) +++ goto fail; +++ PRIV (hdr_data).hdr_t_version =_bfd_vms_save_counted_string (ptr, *ptr); +++ ptr += *ptr + 1; +++ if (ptr + 17 >= end) +++ goto fail; +++ PRIV (hdr_data).hdr_t_date = _bfd_vms_save_sized_string (ptr, 17); +++ break; +++ +++ case EMH__C_LNM: +++ if (vms_rec + PRIV (recrd.rec_size - 6) > end) +++ goto fail; +++ PRIV (hdr_data).hdr_c_lnm = +++ _bfd_vms_save_sized_string (vms_rec, PRIV (recrd.rec_size - 6)); +++ break; +++ +++ case EMH__C_SRC: +++ if (vms_rec + PRIV (recrd.rec_size - 6) > end) +++ goto fail; +++ PRIV (hdr_data).hdr_c_src = +++ _bfd_vms_save_sized_string (vms_rec, PRIV (recrd.rec_size - 6)); +++ break; +++ +++ case EMH__C_TTL: +++ if (vms_rec + PRIV (recrd.rec_size - 6) > end) +++ goto fail; +++ PRIV (hdr_data).hdr_c_ttl = +++ _bfd_vms_save_sized_string (vms_rec, PRIV (recrd.rec_size - 6)); +++ break; +++ +++ case EMH__C_CPR: +++ case EMH__C_MTC: +++ case EMH__C_GTX: +++ break; +++ +++ default: +++ fail: +++ bfd_set_error (bfd_error_wrong_format); +++ return FALSE; +++ } +++ +++ return TRUE; +++} +++ +++/* Typical sections for evax object files. */ +++ +++#define EVAX_ABS_NAME "$ABS$" +++#define EVAX_CODE_NAME "$CODE$" +++#define EVAX_LINK_NAME "$LINK$" +++#define EVAX_DATA_NAME "$DATA$" +++#define EVAX_BSS_NAME "$BSS$" +++#define EVAX_READONLYADDR_NAME "$READONLY_ADDR$" +++#define EVAX_READONLY_NAME "$READONLY$" +++#define EVAX_LITERAL_NAME "$LITERAL$" +++#define EVAX_LITERALS_NAME "$LITERALS" +++#define EVAX_COMMON_NAME "$COMMON$" +++#define EVAX_LOCAL_NAME "$LOCAL$" +++ +++struct sec_flags_struct +++{ +++ const char *name; /* Name of section. */ +++ int vflags_always; +++ flagword flags_always; /* Flags we set always. */ +++ int vflags_hassize; +++ flagword flags_hassize; /* Flags we set if the section has a size > 0. */ +++}; +++ +++/* These flags are deccrtl/vaxcrtl (openVMS 6.2 Sw_64) compatible. */ +++ +++static const struct sec_flags_struct evax_section_flags[] = +++ { +++ { EVAX_ABS_NAME, +++ EGPS__V_SHR, +++ 0, +++ EGPS__V_SHR, +++ 0 }, +++ { EVAX_CODE_NAME, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_EXE, +++ SEC_CODE | SEC_READONLY, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_EXE, +++ SEC_CODE | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_LITERAL_NAME, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD | EGPS__V_NOMOD, +++ SEC_DATA | SEC_READONLY, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_LINK_NAME, +++ EGPS__V_REL | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY, +++ EGPS__V_REL | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_DATA_NAME, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD, +++ SEC_DATA, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT, +++ SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_BSS_NAME, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD, +++ SEC_NO_FLAGS, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD, +++ SEC_ALLOC }, +++ { EVAX_READONLYADDR_NAME, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_READONLY_NAME, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD | EGPS__V_NOMOD, +++ SEC_DATA | SEC_READONLY, +++ EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD, +++ SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_LOCAL_NAME, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT, +++ SEC_DATA, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT, +++ SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { EVAX_LITERALS_NAME, +++ EGPS__V_PIC | EGPS__V_OVR, +++ SEC_DATA | SEC_READONLY, +++ EGPS__V_PIC | EGPS__V_OVR, +++ SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }, +++ { NULL, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT, +++ SEC_DATA, +++ EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT, +++ SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD } +++ }; +++ +++/* Retrieve BFD section flags by name and size. */ +++ +++static flagword +++vms_secflag_by_name (const struct sec_flags_struct *section_flags, +++ const char *name, +++ int hassize) +++{ +++ int i = 0; +++ +++ while (section_flags[i].name != NULL) +++ { +++ if (strcmp (name, section_flags[i].name) == 0) +++ { +++ if (hassize) +++ return section_flags[i].flags_hassize; +++ else +++ return section_flags[i].flags_always; +++ } +++ i++; +++ } +++ if (hassize) +++ return section_flags[i].flags_hassize; +++ return section_flags[i].flags_always; +++} +++ +++/* Retrieve VMS section flags by name and size. */ +++ +++static flagword +++vms_esecflag_by_name (const struct sec_flags_struct *section_flags, +++ const char *name, +++ int hassize) +++{ +++ int i = 0; +++ +++ while (section_flags[i].name != NULL) +++ { +++ if (strcmp (name, section_flags[i].name) == 0) +++ { +++ if (hassize) +++ return section_flags[i].vflags_hassize; +++ else +++ return section_flags[i].vflags_always; +++ } +++ i++; +++ } +++ if (hassize) +++ return section_flags[i].vflags_hassize; +++ return section_flags[i].vflags_always; +++} +++ +++/* Add SYM to the symbol table of ABFD. +++ Return FALSE in case of error. */ +++ +++static bfd_boolean +++add_symbol_entry (bfd *abfd, struct vms_symbol_entry *sym) +++{ +++ if (PRIV (gsd_sym_count) >= PRIV (max_sym_count)) +++ { +++ if (PRIV (max_sym_count) == 0) +++ { +++ PRIV (max_sym_count) = 128; +++ PRIV (syms) = bfd_malloc +++ (PRIV (max_sym_count) * sizeof (struct vms_symbol_entry *)); +++ } +++ else +++ { +++ PRIV (max_sym_count) *= 2; +++ PRIV (syms) = bfd_realloc +++ (PRIV (syms), +++ (PRIV (max_sym_count) * sizeof (struct vms_symbol_entry *))); +++ } +++ if (PRIV (syms) == NULL) +++ return FALSE; +++ } +++ +++ PRIV (syms)[PRIV (gsd_sym_count)++] = sym; +++ return TRUE; +++} +++ +++/* Create a symbol whose name is ASCIC and add it to ABFD. +++ Return NULL in case of error. */ +++ +++static struct vms_symbol_entry * +++add_symbol (bfd *abfd, const unsigned char *ascic) +++{ +++ struct vms_symbol_entry *entry; +++ int len; +++ +++ len = *ascic++; +++ entry = (struct vms_symbol_entry *)bfd_zalloc (abfd, sizeof (*entry) + len); +++ if (entry == NULL) +++ return NULL; +++ entry->namelen = len; +++ memcpy (entry->name, ascic, len); +++ entry->name[len] = 0; +++ entry->owner = abfd; +++ +++ if (!add_symbol_entry (abfd, entry)) +++ return NULL; +++ return entry; +++} +++ +++/* Read and process EGSD. Return FALSE on failure. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_egsd (bfd *abfd) +++{ +++ int gsd_type; +++ unsigned int gsd_size; +++ unsigned char *vms_rec; +++ unsigned long base_addr; +++ +++ vms_debug2 ((2, "EGSD\n")); +++ +++ if (PRIV (recrd.rec_size) < 8) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: its size (%#x) is too small"), +++ PRIV (recrd.rec_size)); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ PRIV (recrd.rec) += 8; /* Skip type, size, align pad. */ +++ PRIV (recrd.rec_size) -= 8; +++ +++ /* Calculate base address for each section. */ +++ base_addr = 0L; +++ +++ while (PRIV (recrd.rec_size) > 4) +++ { +++ vms_rec = PRIV (recrd.rec); +++ +++ gsd_type = bfd_getl16 (vms_rec); +++ gsd_size = bfd_getl16 (vms_rec + 2); +++ +++ vms_debug2 ((3, "egsd_type %d\n", gsd_type)); +++ +++ /* PR 21615: Check for size overflow. */ +++ if (PRIV (recrd.rec_size) < gsd_size) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: size (%#x) is larger than remaining space (%#x)"), +++ gsd_size, PRIV (recrd.rec_size)); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ if (gsd_size < 4) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: size (%#x) is too small"), +++ gsd_size); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ switch (gsd_type) +++ { +++ case EGSD__C_PSC: +++ /* Program section definition. */ +++ { +++ struct vms_egps *egps = (struct vms_egps *)vms_rec; +++ flagword new_flags, vms_flags; +++ asection *section; +++ +++ vms_flags = bfd_getl16 (egps->flags); +++ +++ if ((vms_flags & EGPS__V_REL) == 0) +++ { +++ /* Use the global absolute section for all +++ absolute sections. */ +++ section = bfd_abs_section_ptr; +++ } +++ else +++ { +++ char *name; +++ unsigned long align_addr; +++ +++ name = _bfd_vms_save_counted_string (&egps->namlng, gsd_size - 4); +++ +++ section = bfd_make_section (abfd, name); +++ if (!section) +++ return FALSE; +++ +++ section->filepos = 0; +++ section->size = bfd_getl32 (egps->alloc); +++ section->alignment_power = egps->align; +++ +++ vms_section_data (section)->flags = vms_flags; +++ vms_section_data (section)->no_flags = 0; +++ +++ new_flags = vms_secflag_by_name (evax_section_flags, name, +++ section->size > 0); +++ if (section->size > 0) +++ new_flags |= SEC_LOAD; +++ if (!(vms_flags & EGPS__V_NOMOD) && section->size > 0) +++ { +++ /* Set RELOC and HAS_CONTENTS if the section is not +++ demand-zero and not empty. */ +++ new_flags |= SEC_HAS_CONTENTS; +++ if (vms_flags & EGPS__V_REL) +++ new_flags |= SEC_RELOC; +++ } +++ if (vms_flags & EGPS__V_EXE) +++ { +++ /* Set CODE if section is executable. */ +++ new_flags |= SEC_CODE; +++ new_flags &= ~SEC_DATA; +++ } +++ if (!bfd_set_section_flags (abfd, section, new_flags)) +++ return FALSE; +++ +++ /* Give a non-overlapping vma to non absolute sections. */ +++ align_addr = (1 << section->alignment_power); +++ if ((base_addr % align_addr) != 0) +++ base_addr += (align_addr - (base_addr % align_addr)); +++ section->vma = (bfd_vma)base_addr; +++ base_addr += section->size; +++ } +++ +++ /* Append it to the section array. */ +++ if (PRIV (section_count) >= PRIV (section_max)) +++ { +++ if (PRIV (section_max) == 0) +++ PRIV (section_max) = 16; +++ else +++ PRIV (section_max) *= 2; +++ PRIV (sections) = bfd_realloc_or_free +++ (PRIV (sections), PRIV (section_max) * sizeof (asection *)); +++ if (PRIV (sections) == NULL) +++ return FALSE; +++ } +++ +++ PRIV (sections)[PRIV (section_count)] = section; +++ PRIV (section_count)++; +++ } +++ break; +++ +++ case EGSD__C_SYM: +++ { +++ int nameoff; +++ struct vms_symbol_entry *entry; +++ struct vms_egsy *egsy = (struct vms_egsy *) vms_rec; +++ flagword old_flags; +++ +++ old_flags = bfd_getl16 (egsy->flags); +++ if (old_flags & EGSY__V_DEF) +++ nameoff = ESDF__B_NAMLNG; +++ else +++ nameoff = ESRF__B_NAMLNG; +++ +++ entry = add_symbol (abfd, vms_rec + nameoff); +++ if (entry == NULL) +++ return FALSE; +++ +++ /* Allow only duplicate reference. */ +++ if ((entry->flags & EGSY__V_DEF) && (old_flags & EGSY__V_DEF)) +++ abort (); +++ +++ if (entry->typ == 0) +++ { +++ entry->typ = gsd_type; +++ entry->data_type = egsy->datyp; +++ entry->flags = old_flags; +++ } +++ +++ if (old_flags & EGSY__V_DEF) +++ { +++ struct vms_esdf *esdf = (struct vms_esdf *)vms_rec; +++ long psindx; +++ +++ entry->value = bfd_getl64 (esdf->value); +++ if (PRIV (sections) == NULL) +++ return FALSE; +++ +++ psindx = bfd_getl32 (esdf->psindx); +++ /* PR 21813: Check for an out of range index. */ +++ if (psindx < 0 || psindx >= (int) PRIV (section_count)) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: its psindx field is too big (%#lx)"), +++ psindx); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ entry->section = PRIV (sections)[psindx]; +++ +++ if (old_flags & EGSY__V_NORM) +++ { +++ PRIV (norm_sym_count)++; +++ +++ entry->code_value = bfd_getl64 (esdf->code_address); +++ psindx = bfd_getl32 (esdf->ca_psindx); +++ /* PR 21813: Check for an out of range index. */ +++ if (psindx < 0 || psindx >= (int) PRIV (section_count)) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: its psindx field is too big (%#lx)"), +++ psindx); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ entry->code_section = PRIV (sections)[psindx]; +++ } +++ } +++ } +++ break; +++ +++ case EGSD__C_SYMG: +++ { +++ struct vms_symbol_entry *entry; +++ struct vms_egst *egst = (struct vms_egst *)vms_rec; +++ flagword old_flags; +++ +++ old_flags = bfd_getl16 (egst->header.flags); +++ +++ entry = add_symbol (abfd, &egst->namlng); +++ +++ if (entry == NULL) +++ return FALSE; +++ +++ entry->typ = gsd_type; +++ entry->data_type = egst->header.datyp; +++ entry->flags = old_flags; +++ +++ entry->symbol_vector = bfd_getl32 (egst->value); +++ +++ if (old_flags & EGSY__V_REL) +++ { +++ long psindx; +++ +++ if (PRIV (sections) == NULL) +++ return FALSE; +++ psindx = bfd_getl32 (egst->psindx); +++ /* PR 21813: Check for an out of range index. */ +++ if (psindx < 0 || psindx >= (int) PRIV (section_count)) +++ { +++ _bfd_error_handler (_("corrupt EGSD record: its psindx field is too big (%#lx)"), +++ psindx); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ entry->section = PRIV (sections)[psindx]; +++ } +++ else +++ entry->section = bfd_abs_section_ptr; +++ +++ entry->value = bfd_getl64 (egst->lp_2); +++ +++ if (old_flags & EGSY__V_NORM) +++ { +++ PRIV (norm_sym_count)++; +++ +++ entry->code_value = bfd_getl64 (egst->lp_1); +++ entry->code_section = bfd_abs_section_ptr; +++ } +++ } +++ break; +++ +++ case EGSD__C_SPSC: +++ case EGSD__C_IDC: +++ /* Currently ignored. */ +++ break; +++ case EGSD__C_SYMM: +++ case EGSD__C_SYMV: +++ default: +++ _bfd_error_handler (_("unknown EGSD subtype %d"), gsd_type); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ PRIV (recrd.rec_size) -= gsd_size; +++ PRIV (recrd.rec) += gsd_size; +++ } +++ +++ /* FIXME: Should we complain if PRIV (recrd.rec_size) is not zero ? */ +++ +++ if (PRIV (gsd_sym_count) > 0) +++ abfd->flags |= HAS_SYMS; +++ +++ return TRUE; +++} +++ +++/* Stack routines for vms ETIR commands. */ +++ +++/* Push value and section index. */ +++ +++static void +++_bfd_vms_push (bfd *abfd, bfd_vma val, unsigned int reloc) +++{ +++ vms_debug2 ((4, "\n", +++ (unsigned long)val, reloc, PRIV (stackptr))); +++ +++ PRIV (stack[PRIV (stackptr)]).value = val; +++ PRIV (stack[PRIV (stackptr)]).reloc = reloc; +++ PRIV (stackptr)++; +++ if (PRIV (stackptr) >= STACKSIZE) +++ { +++ bfd_set_error (bfd_error_bad_value); +++ _bfd_error_handler (_("stack overflow (%d) in _bfd_vms_push"), PRIV (stackptr)); +++ exit (1); +++ } +++} +++ +++/* Pop value and section index. */ +++ +++static void +++_bfd_vms_pop (bfd *abfd, bfd_vma *val, unsigned int *rel) +++{ +++ if (PRIV (stackptr) == 0) +++ { +++ bfd_set_error (bfd_error_bad_value); +++ _bfd_error_handler (_("stack underflow in _bfd_vms_pop")); +++ exit (1); +++ } +++ PRIV (stackptr)--; +++ *val = PRIV (stack[PRIV (stackptr)]).value; +++ *rel = PRIV (stack[PRIV (stackptr)]).reloc; +++ +++ vms_debug2 ((4, "\n", (unsigned long)*val, *rel)); +++} +++ +++/* Routines to fill sections contents during tir/etir read. */ +++ +++/* Initialize image buffer pointer to be filled. */ +++ +++static void +++image_set_ptr (bfd *abfd, bfd_vma vma, int sect, struct bfd_link_info *info) +++{ +++ asection *sec; +++ +++ vms_debug2 ((4, "image_set_ptr (0x%08x, sect=%d)\n", (unsigned)vma, sect)); +++ +++ if (PRIV (sections) == NULL) +++ return; +++ if (sect < 0 || sect >= (int) PRIV (section_count)) +++ return; +++ +++ sec = PRIV (sections)[sect]; +++ +++ if (info) +++ { +++ /* Reading contents to an output bfd. */ +++ +++ if (sec->output_section == NULL) +++ { +++ /* Section discarded. */ +++ vms_debug2 ((5, " section %s discarded\n", sec->name)); +++ +++ /* This is not used. */ +++ PRIV (image_section) = NULL; +++ PRIV (image_offset) = 0; +++ return; +++ } +++ PRIV (image_offset) = sec->output_offset + vma; +++ PRIV (image_section) = sec->output_section; +++ } +++ else +++ { +++ PRIV (image_offset) = vma; +++ PRIV (image_section) = sec; +++ } +++} +++ +++/* Increment image buffer pointer by offset. */ +++ +++static void +++image_inc_ptr (bfd *abfd, bfd_vma offset) +++{ +++ vms_debug2 ((4, "image_inc_ptr (%u)\n", (unsigned)offset)); +++ +++ PRIV (image_offset) += offset; +++} +++ +++/* Save current DST location counter under specified index. */ +++ +++static void +++dst_define_location (bfd *abfd, unsigned int loc) +++{ +++ vms_debug2 ((4, "dst_define_location (%d)\n", (int)loc)); +++ +++ /* Grow the ptr offset table if necessary. */ +++ if (loc + 1 > PRIV (dst_ptr_offsets_count)) +++ { +++ PRIV (dst_ptr_offsets) = bfd_realloc (PRIV (dst_ptr_offsets), +++ (loc + 1) * sizeof (unsigned int)); +++ PRIV (dst_ptr_offsets_count) = loc + 1; +++ } +++ +++ PRIV (dst_ptr_offsets)[loc] = PRIV (image_offset); +++} +++ +++/* Restore saved DST location counter from specified index. */ +++ +++static void +++dst_restore_location (bfd *abfd, unsigned int loc) +++{ +++ vms_debug2 ((4, "dst_restore_location (%d)\n", (int)loc)); +++ +++ PRIV (image_offset) = PRIV (dst_ptr_offsets)[loc]; +++} +++ +++/* Retrieve saved DST location counter from specified index. */ +++ +++static unsigned int +++dst_retrieve_location (bfd *abfd, unsigned int loc) +++{ +++ vms_debug2 ((4, "dst_retrieve_location (%d)\n", (int)loc)); +++ +++ return PRIV (dst_ptr_offsets)[loc]; +++} +++ +++/* Write multiple bytes to section image. */ +++ +++static bfd_boolean +++image_write (bfd *abfd, unsigned char *ptr, unsigned int size) +++{ +++#if VMS_DEBUG +++ _bfd_vms_debug (8, "image_write from (%p, %d) to (%ld)\n", ptr, size, +++ (long)PRIV (image_offset)); +++ _bfd_hexdump (9, ptr, size, 0); +++#endif +++ +++ if (PRIV (image_section)->contents != NULL) +++ { +++ asection *sec = PRIV (image_section); +++ file_ptr off = PRIV (image_offset); +++ +++ /* Check bounds. */ +++ if (off > (file_ptr)sec->size +++ || size > (file_ptr)sec->size +++ || off + size > (file_ptr)sec->size) +++ { +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ memcpy (sec->contents + off, ptr, size); +++ } +++ +++ PRIV (image_offset) += size; +++ return TRUE; +++} +++ +++/* Write byte to section image. */ +++ +++static bfd_boolean +++image_write_b (bfd * abfd, unsigned int value) +++{ +++ unsigned char data[1]; +++ +++ vms_debug2 ((6, "image_write_b (%02x)\n", (int) value)); +++ +++ *data = value; +++ +++ return image_write (abfd, data, sizeof (data)); +++} +++ +++/* Write 2-byte word to image. */ +++ +++static bfd_boolean +++image_write_w (bfd * abfd, unsigned int value) +++{ +++ unsigned char data[2]; +++ +++ vms_debug2 ((6, "image_write_w (%04x)\n", (int) value)); +++ +++ bfd_putl16 (value, data); +++ return image_write (abfd, data, sizeof (data)); +++} +++ +++/* Write 4-byte long to image. */ +++ +++static bfd_boolean +++image_write_l (bfd * abfd, unsigned long value) +++{ +++ unsigned char data[4]; +++ +++ vms_debug2 ((6, "image_write_l (%08lx)\n", value)); +++ +++ bfd_putl32 (value, data); +++ return image_write (abfd, data, sizeof (data)); +++} +++ +++/* Write 8-byte quad to image. */ +++ +++static bfd_boolean +++image_write_q (bfd * abfd, bfd_vma value) +++{ +++ unsigned char data[8]; +++ +++ vms_debug2 ((6, "image_write_q (%08lx)\n", (unsigned long)value)); +++ +++ bfd_putl64 (value, data); +++ return image_write (abfd, data, sizeof (data)); +++} +++ +++static const char * +++_bfd_vms_etir_name (int cmd) +++{ +++ switch (cmd) +++ { +++ case ETIR__C_STA_GBL: return "ETIR__C_STA_GBL"; +++ case ETIR__C_STA_LW: return "ETIR__C_STA_LW"; +++ case ETIR__C_STA_QW: return "ETIR__C_STA_QW"; +++ case ETIR__C_STA_PQ: return "ETIR__C_STA_PQ"; +++ case ETIR__C_STA_LI: return "ETIR__C_STA_LI"; +++ case ETIR__C_STA_MOD: return "ETIR__C_STA_MOD"; +++ case ETIR__C_STA_CKARG: return "ETIR__C_STA_CKARG"; +++ case ETIR__C_STO_B: return "ETIR__C_STO_B"; +++ case ETIR__C_STO_W: return "ETIR__C_STO_W"; +++ case ETIR__C_STO_GBL: return "ETIR__C_STO_GBL"; +++ case ETIR__C_STO_CA: return "ETIR__C_STO_CA"; +++ case ETIR__C_STO_RB: return "ETIR__C_STO_RB"; +++ case ETIR__C_STO_AB: return "ETIR__C_STO_AB"; +++ case ETIR__C_STO_OFF: return "ETIR__C_STO_OFF"; +++ case ETIR__C_STO_IMM: return "ETIR__C_STO_IMM"; +++ case ETIR__C_STO_IMMR: return "ETIR__C_STO_IMMR"; +++ case ETIR__C_STO_LW: return "ETIR__C_STO_LW"; +++ case ETIR__C_STO_QW: return "ETIR__C_STO_QW"; +++ case ETIR__C_STO_GBL_LW: return "ETIR__C_STO_GBL_LW"; +++ case ETIR__C_STO_LP_PSB: return "ETIR__C_STO_LP_PSB"; +++ case ETIR__C_STO_HINT_GBL: return "ETIR__C_STO_HINT_GBL"; +++ case ETIR__C_STO_HINT_PS: return "ETIR__C_STO_HINT_PS"; +++ case ETIR__C_OPR_ADD: return "ETIR__C_OPR_ADD"; +++ case ETIR__C_OPR_SUB: return "ETIR__C_OPR_SUB"; +++ case ETIR__C_OPR_INSV: return "ETIR__C_OPR_INSV"; +++ case ETIR__C_OPR_USH: return "ETIR__C_OPR_USH"; +++ case ETIR__C_OPR_ROT: return "ETIR__C_OPR_ROT"; +++ case ETIR__C_OPR_REDEF: return "ETIR__C_OPR_REDEF"; +++ case ETIR__C_OPR_DFLIT: return "ETIR__C_OPR_DFLIT"; +++ case ETIR__C_STC_LP: return "ETIR__C_STC_LP"; +++ case ETIR__C_STC_GBL: return "ETIR__C_STC_GBL"; +++ case ETIR__C_STC_GCA: return "ETIR__C_STC_GCA"; +++ case ETIR__C_STC_PS: return "ETIR__C_STC_PS"; +++ case ETIR__C_STC_NBH_PS: return "ETIR__C_STC_NBH_PS"; +++ case ETIR__C_STC_NOP_GBL: return "ETIR__C_STC_NOP_GBL"; +++ case ETIR__C_STC_NOP_PS: return "ETIR__C_STC_NOP_PS"; +++ case ETIR__C_STC_BSR_GBL: return "ETIR__C_STC_BSR_GBL"; +++ case ETIR__C_STC_BSR_PS: return "ETIR__C_STC_BSR_PS"; +++ case ETIR__C_STC_LDA_GBL: return "ETIR__C_STC_LDA_GBL"; +++ case ETIR__C_STC_LDA_PS: return "ETIR__C_STC_LDA_PS"; +++ case ETIR__C_STC_BOH_GBL: return "ETIR__C_STC_BOH_GBL"; +++ case ETIR__C_STC_BOH_PS: return "ETIR__C_STC_BOH_PS"; +++ case ETIR__C_STC_NBH_GBL: return "ETIR__C_STC_NBH_GBL"; +++ case ETIR__C_STC_LP_PSB: return "ETIR__C_STC_LP_PSB"; +++ case ETIR__C_CTL_SETRB: return "ETIR__C_CTL_SETRB"; +++ case ETIR__C_CTL_AUGRB: return "ETIR__C_CTL_AUGRB"; +++ case ETIR__C_CTL_DFLOC: return "ETIR__C_CTL_DFLOC"; +++ case ETIR__C_CTL_STLOC: return "ETIR__C_CTL_STLOC"; +++ case ETIR__C_CTL_STKDL: return "ETIR__C_CTL_STKDL"; +++ +++ default: +++ /* These names have not yet been added to this switch statement. */ +++ _bfd_error_handler (_("unknown ETIR command %d"), cmd); +++ } +++ +++ return NULL; +++} +++#define HIGHBIT(op) ((op & 0x80000000L) == 0x80000000L) +++ +++static void +++_bfd_vms_get_value (bfd *abfd, +++ const unsigned char *ascic, +++ const unsigned char *max_ascic, +++ struct bfd_link_info *info, +++ bfd_vma *vma, +++ struct sw_64_vms_link_hash_entry **hp) +++{ +++ char name[257]; +++ unsigned int len; +++ unsigned int i; +++ struct sw_64_vms_link_hash_entry *h; +++ +++ /* Not linking. Do not try to resolve the symbol. */ +++ if (info == NULL) +++ { +++ *vma = 0; +++ *hp = NULL; +++ return; +++ } +++ +++ len = *ascic; +++ if (ascic + len >= max_ascic) +++ { +++ _bfd_error_handler (_("corrupt vms value")); +++ *vma = 0; +++ *hp = NULL; +++ return; +++ } +++ +++ for (i = 0; i < len; i++) +++ name[i] = ascic[i + 1]; +++ name[i] = 0; +++ +++ h = (struct sw_64_vms_link_hash_entry *) +++ bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE); +++ +++ *hp = h; +++ +++ if (h != NULL +++ && (h->root.type == bfd_link_hash_defined +++ || h->root.type == bfd_link_hash_defweak)) +++ *vma = h->root.u.def.value +++ + h->root.u.def.section->output_offset +++ + h->root.u.def.section->output_section->vma; +++ else if (h && h->root.type == bfd_link_hash_undefweak) +++ *vma = 0; +++ else +++ { +++ (*info->callbacks->undefined_symbol) +++ (info, name, abfd, PRIV (image_section), PRIV (image_offset), TRUE); +++ *vma = 0; +++ } +++} +++ +++#define RELC_NONE 0 +++#define RELC_REL 1 +++#define RELC_SHR_BASE 0x10000 +++#define RELC_SEC_BASE 0x20000 +++#define RELC_MASK 0x0ffff +++ +++static unsigned int +++sw_64_vms_sym_to_ctxt (struct sw_64_vms_link_hash_entry *h) +++{ +++ /* Handle undefined symbols. */ +++ if (h == NULL || h->sym == NULL) +++ return RELC_NONE; +++ +++ if (h->sym->typ == EGSD__C_SYMG) +++ { +++ if (h->sym->flags & EGSY__V_REL) +++ return RELC_SHR_BASE + PRIV2 (h->sym->owner, shr_index); +++ else +++ { +++ /* Can this happen (non-relocatable symg) ? I'd like to see +++ an example. */ +++ abort (); +++ } +++ } +++ if (h->sym->typ == EGSD__C_SYM) +++ { +++ if (h->sym->flags & EGSY__V_REL) +++ return RELC_REL; +++ else +++ return RELC_NONE; +++ } +++ abort (); +++} +++ +++static bfd_vma +++sw_64_vms_get_sym_value (asection *sect, bfd_vma addr) +++{ +++ return sect->output_section->vma + sect->output_offset + addr; +++} +++ +++static bfd_vma +++sw_64_vms_fix_sec_rel (bfd *abfd, struct bfd_link_info *info, +++ unsigned int rel, bfd_vma vma) +++{ +++ asection *sec; +++ +++ if (PRIV (sections) == NULL) +++ return 0; +++ +++ sec = PRIV (sections)[rel & RELC_MASK]; +++ +++ if (info) +++ { +++ if (sec->output_section == NULL) +++ abort (); +++ return vma + sec->output_section->vma + sec->output_offset; +++ } +++ else +++ return vma + sec->vma; +++} +++ +++/* Read an ETIR record from ABFD. If INFO is not null, put the content into +++ the output section (used during linking). +++ Return FALSE in case of error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info) +++{ +++ unsigned char *ptr; +++ unsigned int length; +++ unsigned char *maxptr; +++ bfd_vma op1; +++ bfd_vma op2; +++ unsigned int rel1; +++ unsigned int rel2; +++ struct sw_64_vms_link_hash_entry *h; +++ +++ PRIV (recrd.rec) += ETIR__C_HEADER_SIZE; +++ PRIV (recrd.rec_size) -= ETIR__C_HEADER_SIZE; +++ +++ ptr = PRIV (recrd.rec); +++ length = PRIV (recrd.rec_size); +++ maxptr = ptr + length; +++ +++ vms_debug2 ((2, "ETIR: %d bytes\n", length)); +++ +++ while (ptr < maxptr) +++ { +++ int cmd = bfd_getl16 (ptr); +++ int cmd_length = bfd_getl16 (ptr + 2); +++ +++ ptr += 4; +++ +++ /* PR 21589 and 21579: Check for a corrupt ETIR record. */ +++ if (cmd_length < 4 || (ptr + cmd_length > maxptr + 4)) +++ { +++ corrupt_etir: +++ _bfd_error_handler (_("corrupt ETIR record encountered")); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++#if VMS_DEBUG +++ _bfd_vms_debug (4, "etir: %s(%d)\n", +++ _bfd_vms_etir_name (cmd), cmd); +++ _bfd_hexdump (8, ptr, cmd_length - 4, 0); +++#endif +++ +++ switch (cmd) +++ { +++ /* Stack global +++ arg: cs symbol name +++ +++ stack 32 bit value of symbol (high bits set to 0). */ +++ case ETIR__C_STA_GBL: +++ _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h); +++ _bfd_vms_push (abfd, op1, sw_64_vms_sym_to_ctxt (h)); +++ break; +++ +++ /* Stack longword +++ arg: lw value +++ +++ stack 32 bit value, sign extend to 64 bit. */ +++ case ETIR__C_STA_LW: +++ if (ptr + 4 >= maxptr) +++ goto corrupt_etir; +++ _bfd_vms_push (abfd, bfd_getl32 (ptr), RELC_NONE); +++ break; +++ +++ /* Stack quadword +++ arg: qw value +++ +++ stack 64 bit value of symbol. */ +++ case ETIR__C_STA_QW: +++ if (ptr + 8 >= maxptr) +++ goto corrupt_etir; +++ _bfd_vms_push (abfd, bfd_getl64 (ptr), RELC_NONE); +++ break; +++ +++ /* Stack psect base plus quadword offset +++ arg: lw section index +++ qw signed quadword offset (low 32 bits) +++ +++ Stack qw argument and section index +++ (see ETIR__C_STO_OFF, ETIR__C_CTL_SETRB). */ +++ case ETIR__C_STA_PQ: +++ { +++ int psect; +++ +++ if (ptr + 12 >= maxptr) +++ goto corrupt_etir; +++ psect = bfd_getl32 (ptr); +++ if ((unsigned int) psect >= PRIV (section_count)) +++ { +++ _bfd_error_handler (_("bad section index in %s"), +++ _bfd_vms_etir_name (cmd)); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ op1 = bfd_getl64 (ptr + 4); +++ _bfd_vms_push (abfd, op1, psect | RELC_SEC_BASE); +++ } +++ break; +++ +++ case ETIR__C_STA_LI: +++ case ETIR__C_STA_MOD: +++ case ETIR__C_STA_CKARG: +++ _bfd_error_handler (_("unsupported STA cmd %s"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ +++ /* Store byte: pop stack, write byte +++ arg: -. */ +++ case ETIR__C_STO_B: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ image_write_b (abfd, (unsigned int) op1 & 0xff); +++ break; +++ +++ /* Store word: pop stack, write word +++ arg: -. */ +++ case ETIR__C_STO_W: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ image_write_w (abfd, (unsigned int) op1 & 0xffff); +++ break; +++ +++ /* Store longword: pop stack, write longword +++ arg: -. */ +++ case ETIR__C_STO_LW: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 & RELC_SEC_BASE) +++ { +++ op1 = sw_64_vms_fix_sec_rel (abfd, info, rel1, op1); +++ rel1 = RELC_REL; +++ } +++ else if (rel1 & RELC_SHR_BASE) +++ { +++ sw_64_vms_add_fixup_lr (info, rel1 & RELC_MASK, op1); +++ rel1 = RELC_NONE; +++ } +++ if (rel1 != RELC_NONE) +++ { +++ if (rel1 != RELC_REL) +++ abort (); +++ sw_64_vms_add_lw_reloc (info); +++ } +++ image_write_l (abfd, op1); +++ break; +++ +++ /* Store quadword: pop stack, write quadword +++ arg: -. */ +++ case ETIR__C_STO_QW: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 & RELC_SEC_BASE) +++ { +++ op1 = sw_64_vms_fix_sec_rel (abfd, info, rel1, op1); +++ rel1 = RELC_REL; +++ } +++ else if (rel1 & RELC_SHR_BASE) +++ abort (); +++ if (rel1 != RELC_NONE) +++ { +++ if (rel1 != RELC_REL) +++ abort (); +++ sw_64_vms_add_qw_reloc (info); +++ } +++ image_write_q (abfd, op1); +++ break; +++ +++ /* Store immediate repeated: pop stack for repeat count +++ arg: lw byte count +++ da data. */ +++ case ETIR__C_STO_IMMR: +++ { +++ int size; +++ +++ if (ptr + 4 >= maxptr) +++ goto corrupt_etir; +++ size = bfd_getl32 (ptr); +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ while (op1-- > 0) +++ image_write (abfd, ptr + 4, size); +++ } +++ break; +++ +++ /* Store global: write symbol value +++ arg: cs global symbol name. */ +++ case ETIR__C_STO_GBL: +++ _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h); +++ if (h && h->sym) +++ { +++ if (h->sym->typ == EGSD__C_SYMG) +++ { +++ sw_64_vms_add_fixup_qr +++ (info, abfd, h->sym->owner, h->sym->symbol_vector); +++ op1 = 0; +++ } +++ else +++ { +++ op1 = sw_64_vms_get_sym_value (h->sym->section, +++ h->sym->value); +++ sw_64_vms_add_qw_reloc (info); +++ } +++ } +++ image_write_q (abfd, op1); +++ break; +++ +++ /* Store code address: write address of entry point +++ arg: cs global symbol name (procedure). */ +++ case ETIR__C_STO_CA: +++ _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h); +++ if (h && h->sym) +++ { +++ if (h->sym->flags & EGSY__V_NORM) +++ { +++ /* That's really a procedure. */ +++ if (h->sym->typ == EGSD__C_SYMG) +++ { +++ sw_64_vms_add_fixup_ca (info, abfd, h->sym->owner); +++ op1 = h->sym->symbol_vector; +++ } +++ else +++ { +++ op1 = sw_64_vms_get_sym_value (h->sym->code_section, +++ h->sym->code_value); +++ sw_64_vms_add_qw_reloc (info); +++ } +++ } +++ else +++ { +++ /* Symbol is not a procedure. */ +++ abort (); +++ } +++ } +++ image_write_q (abfd, op1); +++ break; +++ +++ /* Store offset to psect: pop stack, add low 32 bits to base of psect +++ arg: none. */ +++ case ETIR__C_STO_OFF: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ +++ if (!(rel1 & RELC_SEC_BASE)) +++ abort (); +++ +++ op1 = sw_64_vms_fix_sec_rel (abfd, info, rel1, op1); +++ rel1 = RELC_REL; +++ image_write_q (abfd, op1); +++ break; +++ +++ /* Store immediate +++ arg: lw count of bytes +++ da data. */ +++ case ETIR__C_STO_IMM: +++ { +++ unsigned int size; +++ +++ if (ptr + 4 >= maxptr) +++ goto corrupt_etir; +++ size = bfd_getl32 (ptr); +++ image_write (abfd, ptr + 4, size); +++ } +++ break; +++ +++ /* This code is 'reserved to digital' according to the openVMS +++ linker manual, however it is generated by the DEC C compiler +++ and defined in the include file. +++ FIXME, since the following is just a guess +++ store global longword: store 32bit value of symbol +++ arg: cs symbol name. */ +++ case ETIR__C_STO_GBL_LW: +++ _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h); +++#if 0 +++ abort (); +++#endif +++ image_write_l (abfd, op1); +++ break; +++ +++ case ETIR__C_STO_RB: +++ case ETIR__C_STO_AB: +++ case ETIR__C_STO_LP_PSB: +++ _bfd_error_handler (_("%s: not supported"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ case ETIR__C_STO_HINT_GBL: +++ case ETIR__C_STO_HINT_PS: +++ _bfd_error_handler (_("%s: not implemented"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ +++ /* 200 Store-conditional Linkage Pair +++ arg: none. */ +++ case ETIR__C_STC_LP: +++ +++ /* 202 Store-conditional Address at global address +++ lw linkage index +++ cs global name. */ +++ +++ case ETIR__C_STC_GBL: +++ +++ /* 203 Store-conditional Code Address at global address +++ lw linkage index +++ cs procedure name. */ +++ case ETIR__C_STC_GCA: +++ +++ /* 204 Store-conditional Address at psect + offset +++ lw linkage index +++ lw psect index +++ qw offset. */ +++ case ETIR__C_STC_PS: +++ _bfd_error_handler (_("%s: not supported"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ +++ /* 201 Store-conditional Linkage Pair with Procedure Signature +++ lw linkage index +++ cs procedure name +++ by signature length +++ da signature. */ +++ +++ case ETIR__C_STC_LP_PSB: +++ _bfd_vms_get_value (abfd, ptr + 4, maxptr, info, &op1, &h); +++ if (h && h->sym) +++ { +++ if (h->sym->typ == EGSD__C_SYMG) +++ { +++ sw_64_vms_add_fixup_lp (info, abfd, h->sym->owner); +++ op1 = h->sym->symbol_vector; +++ op2 = 0; +++ } +++ else +++ { +++ op1 = sw_64_vms_get_sym_value (h->sym->code_section, +++ h->sym->code_value); +++ op2 = sw_64_vms_get_sym_value (h->sym->section, +++ h->sym->value); +++ } +++ } +++ else +++ { +++ /* Undefined symbol. */ +++ op1 = 0; +++ op2 = 0; +++ } +++ image_write_q (abfd, op1); +++ image_write_q (abfd, op2); +++ break; +++ +++ /* 205 Store-conditional NOP at address of global +++ arg: none. */ +++ case ETIR__C_STC_NOP_GBL: +++ /* SW_64_R_NOP */ +++ +++ /* 207 Store-conditional BSR at global address +++ arg: none. */ +++ +++ case ETIR__C_STC_BSR_GBL: +++ /* SW_64_R_BSR */ +++ +++ /* 209 Store-conditional LDA at global address +++ arg: none. */ +++ +++ case ETIR__C_STC_LDA_GBL: +++ /* SW_64_R_LDA */ +++ +++ /* 211 Store-conditional BSR or Hint at global address +++ arg: none. */ +++ +++ case ETIR__C_STC_BOH_GBL: +++ /* Currentl ignored. */ +++ break; +++ +++ /* 213 Store-conditional NOP,BSR or HINT at global address +++ arg: none. */ +++ +++ case ETIR__C_STC_NBH_GBL: +++ +++ /* 206 Store-conditional NOP at pect + offset +++ arg: none. */ +++ +++ case ETIR__C_STC_NOP_PS: +++ +++ /* 208 Store-conditional BSR at pect + offset +++ arg: none. */ +++ +++ case ETIR__C_STC_BSR_PS: +++ +++ /* 210 Store-conditional LDA at psect + offset +++ arg: none. */ +++ +++ case ETIR__C_STC_LDA_PS: +++ +++ /* 212 Store-conditional BSR or Hint at pect + offset +++ arg: none. */ +++ +++ case ETIR__C_STC_BOH_PS: +++ +++ /* 214 Store-conditional NOP, BSR or HINT at psect + offset +++ arg: none. */ +++ case ETIR__C_STC_NBH_PS: +++ _bfd_error_handler (_("%s: not supported"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ +++ /* Det relocation base: pop stack, set image location counter +++ arg: none. */ +++ case ETIR__C_CTL_SETRB: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (!(rel1 & RELC_SEC_BASE)) +++ abort (); +++ image_set_ptr (abfd, op1, rel1 & RELC_MASK, info); +++ break; +++ +++ /* Augment relocation base: increment image location counter by offset +++ arg: lw offset value. */ +++ case ETIR__C_CTL_AUGRB: +++ if (ptr + 4 >= maxptr) +++ goto corrupt_etir; +++ op1 = bfd_getl32 (ptr); +++ image_inc_ptr (abfd, op1); +++ break; +++ +++ /* Define location: pop index, save location counter under index +++ arg: none. */ +++ case ETIR__C_CTL_DFLOC: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ dst_define_location (abfd, op1); +++ break; +++ +++ /* Set location: pop index, restore location counter from index +++ arg: none. */ +++ case ETIR__C_CTL_STLOC: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ dst_restore_location (abfd, op1); +++ break; +++ +++ /* Stack defined location: pop index, push location counter from index +++ arg: none. */ +++ case ETIR__C_CTL_STKDL: +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, dst_retrieve_location (abfd, op1), RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_NOP: /* No-op. */ +++ break; +++ +++ case ETIR__C_OPR_ADD: /* Add. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 == RELC_NONE && rel2 != RELC_NONE) +++ rel1 = rel2; +++ else if (rel1 != RELC_NONE && rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op1 + op2, rel1); +++ break; +++ +++ case ETIR__C_OPR_SUB: /* Subtract. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 == RELC_NONE && rel2 != RELC_NONE) +++ rel1 = rel2; +++ else if ((rel1 & RELC_SEC_BASE) && (rel2 & RELC_SEC_BASE)) +++ { +++ op1 = sw_64_vms_fix_sec_rel (abfd, info, rel1, op1); +++ op2 = sw_64_vms_fix_sec_rel (abfd, info, rel2, op2); +++ rel1 = RELC_NONE; +++ } +++ else if (rel1 != RELC_NONE && rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op2 - op1, rel1); +++ break; +++ +++ case ETIR__C_OPR_MUL: /* Multiply. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op1 * op2, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_DIV: /* Divide. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ goto bad_context; +++ if (op2 == 0) +++ _bfd_vms_push (abfd, 0, RELC_NONE); +++ else +++ _bfd_vms_push (abfd, op2 / op1, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_AND: /* Logical AND. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op1 & op2, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_IOR: /* Logical inclusive OR. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op1 | op2, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_EOR: /* Logical exclusive OR. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, op1 ^ op2, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_NEG: /* Negate. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, -op1, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_COM: /* Complement. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (rel1 != RELC_NONE) +++ goto bad_context; +++ _bfd_vms_push (abfd, ~op1, RELC_NONE); +++ break; +++ +++ case ETIR__C_OPR_ASH: /* Arithmetic shift. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ if (rel1 != RELC_NONE || rel2 != RELC_NONE) +++ { +++ bad_context: +++ _bfd_error_handler (_("invalid use of %s with contexts"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ } +++ if ((int)op2 < 0) /* Shift right. */ +++ op1 >>= -(int)op2; +++ else /* Shift left. */ +++ op1 <<= (int)op2; +++ _bfd_vms_push (abfd, op1, RELC_NONE); /* FIXME: sym. */ +++ break; +++ +++ case ETIR__C_OPR_INSV: /* Insert field. */ +++ case ETIR__C_OPR_USH: /* Unsigned shift. */ +++ case ETIR__C_OPR_ROT: /* Rotate. */ +++ case ETIR__C_OPR_REDEF: /* Redefine symbol to current location. */ +++ case ETIR__C_OPR_DFLIT: /* Define a literal. */ +++ _bfd_error_handler (_("%s: not supported"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ break; +++ +++ case ETIR__C_OPR_SEL: /* Select. */ +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ if (op1 & 0x01L) +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ else +++ { +++ _bfd_vms_pop (abfd, &op1, &rel1); +++ _bfd_vms_pop (abfd, &op2, &rel2); +++ _bfd_vms_push (abfd, op1, rel1); +++ } +++ break; +++ +++ default: +++ _bfd_error_handler (_("reserved cmd %d"), cmd); +++ return FALSE; +++ break; +++ } +++ +++ ptr += cmd_length - 4; +++ } +++ +++ return TRUE; +++} +++ +++/* Process EDBG/ETBT record. +++ Return TRUE on success, FALSE on error */ +++ +++static bfd_boolean +++vms_slurp_debug (bfd *abfd) +++{ +++ asection *section = PRIV (dst_section); +++ +++ if (section == NULL) +++ { +++ /* We have no way to find out beforehand how much debug info there +++ is in an object file, so pick an initial amount and grow it as +++ needed later. */ +++ flagword flags = SEC_HAS_CONTENTS | SEC_DEBUGGING | SEC_RELOC +++ | SEC_IN_MEMORY; +++ +++ section = bfd_make_section (abfd, "$DST$"); +++ if (!section) +++ return FALSE; +++ if (!bfd_set_section_flags (abfd, section, flags)) +++ return FALSE; +++ PRIV (dst_section) = section; +++ } +++ +++ PRIV (image_section) = section; +++ PRIV (image_offset) = section->size; +++ +++ if (!_bfd_vms_slurp_etir (abfd, NULL)) +++ return FALSE; +++ +++ section->size = PRIV (image_offset); +++ return TRUE; +++} +++ +++/* Process EDBG record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_edbg (bfd *abfd) +++{ +++ vms_debug2 ((2, "EDBG\n")); +++ +++ abfd->flags |= HAS_DEBUG | HAS_LINENO; +++ +++ return vms_slurp_debug (abfd); +++} +++ +++/* Process ETBT record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_etbt (bfd *abfd) +++{ +++ vms_debug2 ((2, "ETBT\n")); +++ +++ abfd->flags |= HAS_LINENO; +++ +++ return vms_slurp_debug (abfd); +++} +++ +++/* Process EEOM record. +++ Return TRUE on success, FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_eeom (bfd *abfd) +++{ +++ struct vms_eeom *eeom = (struct vms_eeom *) PRIV (recrd.rec); +++ +++ vms_debug2 ((2, "EEOM\n")); +++ +++ /* PR 21813: Check for an undersized record. */ +++ if (PRIV (recrd.buf_size) < sizeof (* eeom)) +++ { +++ _bfd_error_handler (_("corrupt EEOM record - size is too small")); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ PRIV (eom_data).eom_l_total_lps = bfd_getl32 (eeom->total_lps); +++ PRIV (eom_data).eom_w_comcod = bfd_getl16 (eeom->comcod); +++ if (PRIV (eom_data).eom_w_comcod > 1) +++ { +++ _bfd_error_handler (_("object module not error-free !")); +++ bfd_set_error (bfd_error_bad_value); +++ return FALSE; +++ } +++ +++ PRIV (eom_data).eom_has_transfer = FALSE; +++ if (PRIV (recrd.rec_size) > 10) +++ { +++ PRIV (eom_data).eom_has_transfer = TRUE; +++ PRIV (eom_data).eom_b_tfrflg = eeom->tfrflg; +++ PRIV (eom_data).eom_l_psindx = bfd_getl32 (eeom->psindx); +++ PRIV (eom_data).eom_l_tfradr = bfd_getl32 (eeom->tfradr); +++ +++ abfd->start_address = PRIV (eom_data).eom_l_tfradr; +++ } +++ return TRUE; +++} +++ +++/* Slurp an ordered set of VMS object records. Return FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_slurp_object_records (bfd * abfd) +++{ +++ bfd_boolean err; +++ int type; +++ +++ do +++ { +++ vms_debug2 ((7, "reading at %08lx\n", (unsigned long)bfd_tell (abfd))); +++ +++ type = _bfd_vms_get_object_record (abfd); +++ if (type < 0) +++ { +++ vms_debug2 ((2, "next_record failed\n")); +++ return FALSE; +++ } +++ +++ switch (type) +++ { +++ case EOBJ__C_EMH: +++ err = _bfd_vms_slurp_ehdr (abfd); +++ break; +++ case EOBJ__C_EEOM: +++ err = _bfd_vms_slurp_eeom (abfd); +++ break; +++ case EOBJ__C_EGSD: +++ err = _bfd_vms_slurp_egsd (abfd); +++ break; +++ case EOBJ__C_ETIR: +++ err = TRUE; /* _bfd_vms_slurp_etir (abfd); */ +++ break; +++ case EOBJ__C_EDBG: +++ err = _bfd_vms_slurp_edbg (abfd); +++ break; +++ case EOBJ__C_ETBT: +++ err = _bfd_vms_slurp_etbt (abfd); +++ break; +++ default: +++ err = FALSE; +++ } +++ if (!err) +++ { +++ vms_debug2 ((2, "slurp type %d failed\n", type)); +++ return FALSE; +++ } +++ } +++ while (type != EOBJ__C_EEOM); +++ +++ return TRUE; +++} +++ +++/* Initialize private data */ +++static bfd_boolean +++vms_initialize (bfd * abfd) +++{ +++ bfd_size_type amt; +++ +++ amt = sizeof (struct vms_private_data_struct); +++ abfd->tdata.any = bfd_zalloc (abfd, amt); +++ if (abfd->tdata.any == NULL) +++ return FALSE; +++ +++ PRIV (recrd.file_format) = FF_UNKNOWN; +++ +++ amt = sizeof (struct stack_struct) * STACKSIZE; +++ PRIV (stack) = bfd_alloc (abfd, amt); +++ if (PRIV (stack) == NULL) +++ goto error_ret1; +++ +++ return TRUE; +++ +++ error_ret1: +++ bfd_release (abfd, abfd->tdata.any); +++ abfd->tdata.any = NULL; +++ return FALSE; +++} +++ +++/* Check the format for a file being read. +++ Return a (bfd_target *) if it's an object file or zero if not. */ +++ +++static const struct bfd_target * +++sw_64_vms_object_p (bfd *abfd) +++{ +++ void *tdata_save = abfd->tdata.any; +++ unsigned int test_len; +++ unsigned char *buf; +++ +++ vms_debug2 ((1, "vms_object_p(%p)\n", abfd)); +++ +++ /* Allocate sw_64-vms specific data. */ +++ if (!vms_initialize (abfd)) +++ goto error_ret; +++ +++ if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET)) +++ goto err_wrong_format; +++ +++ /* The first challenge with VMS is to discover the kind of the file. +++ +++ Image files (executable or shared images) are stored as a raw +++ stream of bytes (like on UNIX), but there is no magic number. +++ +++ Object files are written with RMS (record management service), ie +++ each records are preceeded by its length (on a word - 2 bytes), and +++ padded for word-alignment. That would be simple but when files +++ are transfered to a UNIX filesystem (using ftp), records are lost. +++ Only the raw content of the records are transfered. Fortunately, +++ the Sw_64 Object file format also store the length of the record +++ in the records. Is that clear ? */ +++ +++ /* Minimum is 6 bytes for objects (2 bytes size, 2 bytes record id, +++ 2 bytes size repeated) and 12 bytes for images (4 bytes major id, +++ 4 bytes minor id, 4 bytes length). */ +++ test_len = 12; +++ +++ /* Size the main buffer. */ +++ buf = (unsigned char *) bfd_malloc (test_len); +++ if (buf == NULL) +++ goto error_ret; +++ PRIV (recrd.buf) = buf; +++ PRIV (recrd.buf_size) = test_len; +++ +++ /* Initialize the record pointer. */ +++ PRIV (recrd.rec) = buf; +++ +++ if (bfd_bread (buf, test_len, abfd) != test_len) +++ goto err_wrong_format; +++ +++ /* Is it an image? */ +++ if ((bfd_getl32 (buf) == EIHD__K_MAJORID) +++ && (bfd_getl32 (buf + 4) == EIHD__K_MINORID)) +++ { +++ unsigned int to_read; +++ unsigned int read_so_far; +++ unsigned int remaining; +++ unsigned int eisd_offset, eihs_offset; +++ +++ /* Extract the header size. */ +++ PRIV (recrd.rec_size) = bfd_getl32 (buf + EIHD__L_SIZE); +++ +++ /* The header size is 0 for DSF files. */ +++ if (PRIV (recrd.rec_size) == 0) +++ PRIV (recrd.rec_size) = sizeof (struct vms_eihd); +++ +++ if (PRIV (recrd.rec_size) > PRIV (recrd.buf_size)) +++ { +++ buf = bfd_realloc_or_free (buf, PRIV (recrd.rec_size)); +++ +++ if (buf == NULL) +++ { +++ PRIV (recrd.buf) = NULL; +++ goto error_ret; +++ } +++ PRIV (recrd.buf) = buf; +++ PRIV (recrd.buf_size) = PRIV (recrd.rec_size); +++ } +++ +++ /* PR 21813: Check for a truncated record. */ +++ if (PRIV (recrd.rec_size < test_len)) +++ goto error_ret; +++ /* Read the remaining record. */ +++ remaining = PRIV (recrd.rec_size) - test_len; +++ to_read = MIN (VMS_BLOCK_SIZE - test_len, remaining); +++ read_so_far = test_len; +++ +++ while (remaining > 0) +++ { +++ if (bfd_bread (buf + read_so_far, to_read, abfd) != to_read) +++ goto err_wrong_format; +++ +++ read_so_far += to_read; +++ remaining -= to_read; +++ +++ to_read = MIN (VMS_BLOCK_SIZE, remaining); +++ } +++ +++ /* Reset the record pointer. */ +++ PRIV (recrd.rec) = buf; +++ +++ /* PR 17512: file: 7d7c57c2. */ +++ if (PRIV (recrd.rec_size) < sizeof (struct vms_eihd)) +++ goto error_ret; +++ vms_debug2 ((2, "file type is image\n")); +++ +++ if (!_bfd_vms_slurp_eihd (abfd, &eisd_offset, &eihs_offset)) +++ goto err_wrong_format; +++ +++ if (!_bfd_vms_slurp_eisd (abfd, eisd_offset)) +++ goto err_wrong_format; +++ +++ /* EIHS is optional. */ +++ if (eihs_offset != 0 && !_bfd_vms_slurp_eihs (abfd, eihs_offset)) +++ goto err_wrong_format; +++ } +++ else +++ { +++ int type; +++ +++ /* Assume it's a module and adjust record pointer if necessary. */ +++ maybe_adjust_record_pointer_for_object (abfd); +++ +++ /* But is it really a module? */ +++ if (bfd_getl16 (PRIV (recrd.rec)) <= EOBJ__C_MAXRECTYP +++ && bfd_getl16 (PRIV (recrd.rec) + 2) <= EOBJ__C_MAXRECSIZ) +++ { +++ if (vms_get_remaining_object_record (abfd, test_len) <= 0) +++ goto err_wrong_format; +++ +++ vms_debug2 ((2, "file type is module\n")); +++ +++ type = bfd_getl16 (PRIV (recrd.rec)); +++ if (type != EOBJ__C_EMH || !_bfd_vms_slurp_ehdr (abfd)) +++ goto err_wrong_format; +++ +++ if (!_bfd_vms_slurp_object_records (abfd)) +++ goto err_wrong_format; +++ } +++ else +++ goto err_wrong_format; +++ } +++ +++ /* Set arch_info to sw_64. */ +++ +++ if (! bfd_default_set_arch_mach (abfd, bfd_arch_sw_64, 0)) +++ goto err_wrong_format; +++ +++ return abfd->xvec; +++ +++ err_wrong_format: +++ bfd_set_error (bfd_error_wrong_format); +++ +++ error_ret: +++ if (PRIV (recrd.buf)) +++ free (PRIV (recrd.buf)); +++ if (abfd->tdata.any != tdata_save && abfd->tdata.any != NULL) +++ bfd_release (abfd, abfd->tdata.any); +++ abfd->tdata.any = tdata_save; +++ return NULL; +++} +++ +++/* Image write. */ +++ +++/* Write an EMH/MHD record. */ +++ +++static void +++_bfd_vms_write_emh (bfd *abfd) +++{ +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ _bfd_vms_output_alignment (recwr, 2); +++ +++ /* EMH. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EMH); +++ _bfd_vms_output_short (recwr, EMH__C_MHD); +++ _bfd_vms_output_short (recwr, EOBJ__C_STRLVL); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_long (recwr, MAX_OUTREC_SIZE); +++ +++ /* Create module name from filename. */ +++ if (bfd_get_filename (abfd) != 0) +++ { +++ char *module = vms_get_module_name (bfd_get_filename (abfd), TRUE); +++ _bfd_vms_output_counted (recwr, module); +++ free (module); +++ } +++ else +++ _bfd_vms_output_counted (recwr, "NONAME"); +++ +++ _bfd_vms_output_counted (recwr, BFD_VERSION_STRING); +++ _bfd_vms_output_dump (recwr, get_vms_time_string (), EMH_DATE_LENGTH); +++ _bfd_vms_output_fill (recwr, 0, EMH_DATE_LENGTH); +++ _bfd_vms_output_end (abfd, recwr); +++} +++ +++/* Write an EMH/LMN record. */ +++ +++static void +++_bfd_vms_write_lmn (bfd *abfd, const char *name) +++{ +++ char version [64]; +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ unsigned int ver = BFD_VERSION / 10000; +++ +++ /* LMN. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EMH); +++ _bfd_vms_output_short (recwr, EMH__C_LNM); +++ snprintf (version, sizeof (version), "%s %d.%d.%d", name, +++ ver / 10000, (ver / 100) % 100, ver % 100); +++ _bfd_vms_output_dump (recwr, (unsigned char *)version, strlen (version)); +++ _bfd_vms_output_end (abfd, recwr); +++} +++ +++ +++/* Write eom record for bfd abfd. Return FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_write_eeom (bfd *abfd) +++{ +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ vms_debug2 ((2, "vms_write_eeom\n")); +++ +++ _bfd_vms_output_alignment (recwr, 2); +++ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EEOM); +++ _bfd_vms_output_long (recwr, PRIV (vms_linkage_index + 1) >> 1); +++ _bfd_vms_output_byte (recwr, 0); /* Completion code. */ +++ _bfd_vms_output_byte (recwr, 0); /* Fill byte. */ +++ +++ if ((abfd->flags & EXEC_P) == 0 +++ && bfd_get_start_address (abfd) != (bfd_vma)-1) +++ { +++ asection *section; +++ +++ section = bfd_get_section_by_name (abfd, ".link"); +++ if (section == 0) +++ { +++ bfd_set_error (bfd_error_nonrepresentable_section); +++ return FALSE; +++ } +++ _bfd_vms_output_short (recwr, 0); +++ _bfd_vms_output_long (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_long (recwr, +++ (unsigned long) bfd_get_start_address (abfd)); +++ _bfd_vms_output_long (recwr, 0); +++ } +++ +++ _bfd_vms_output_end (abfd, recwr); +++ return TRUE; +++} +++ +++static void +++vector_grow1 (struct vector_type *vec, size_t elsz) +++{ +++ if (vec->nbr_el + 1 < vec->max_el) +++ return; +++ +++ if (vec->max_el == 0) +++ { +++ vec->max_el = 16; +++ vec->els = bfd_malloc2 (vec->max_el, elsz); +++ } +++ else +++ { +++ vec->max_el *= 2; +++ vec->els = bfd_realloc2 (vec->els, vec->max_el, elsz); +++ } +++} +++ +++/* Bump ABFD file position to next block. */ +++ +++static void +++sw_64_vms_file_position_block (bfd *abfd) +++{ +++ /* Next block. */ +++ PRIV (file_pos) += VMS_BLOCK_SIZE - 1; +++ PRIV (file_pos) -= (PRIV (file_pos) % VMS_BLOCK_SIZE); +++} +++ +++/* Convert from internal structure SRC to external structure DST. */ +++ +++static void +++sw_64_vms_swap_eisd_out (struct vms_internal_eisd_map *src, +++ struct vms_eisd *dst) +++{ +++ bfd_putl32 (src->u.eisd.majorid, dst->majorid); +++ bfd_putl32 (src->u.eisd.minorid, dst->minorid); +++ bfd_putl32 (src->u.eisd.eisdsize, dst->eisdsize); +++ if (src->u.eisd.eisdsize <= EISD__K_LENEND) +++ return; +++ bfd_putl32 (src->u.eisd.secsize, dst->secsize); +++ bfd_putl64 (src->u.eisd.virt_addr, dst->virt_addr); +++ bfd_putl32 (src->u.eisd.flags, dst->flags); +++ bfd_putl32 (src->u.eisd.vbn, dst->vbn); +++ dst->pfc = src->u.eisd.pfc; +++ dst->matchctl = src->u.eisd.matchctl; +++ dst->type = src->u.eisd.type; +++ dst->fill_1 = 0; +++ if (src->u.eisd.flags & EISD__M_GBL) +++ { +++ bfd_putl32 (src->u.gbl_eisd.ident, dst->ident); +++ memcpy (dst->gblnam, src->u.gbl_eisd.gblnam, +++ src->u.gbl_eisd.gblnam[0] + 1); +++ } +++} +++ +++/* Append EISD to the list of extra eisd for ABFD. */ +++ +++static void +++sw_64_vms_append_extra_eisd (bfd *abfd, struct vms_internal_eisd_map *eisd) +++{ +++ eisd->next = NULL; +++ if (PRIV (gbl_eisd_head) == NULL) +++ PRIV (gbl_eisd_head) = eisd; +++ else +++ PRIV (gbl_eisd_tail)->next = eisd; +++ PRIV (gbl_eisd_tail) = eisd; +++} +++ +++/* Create an EISD for shared image SHRIMG. +++ Return FALSE in case of error. */ +++ +++static bfd_boolean +++sw_64_vms_create_eisd_for_shared (bfd *abfd, bfd *shrimg) +++{ +++ struct vms_internal_eisd_map *eisd; +++ int namlen; +++ +++ namlen = strlen (PRIV2 (shrimg, hdr_data.hdr_t_name)); +++ if (namlen + 5 > EISD__K_GBLNAMLEN) +++ { +++ /* Won't fit. */ +++ return FALSE; +++ } +++ +++ eisd = bfd_alloc (abfd, sizeof (*eisd)); +++ if (eisd == NULL) +++ return FALSE; +++ +++ /* Fill the fields. */ +++ eisd->u.gbl_eisd.common.majorid = EISD__K_MAJORID; +++ eisd->u.gbl_eisd.common.minorid = EISD__K_MINORID; +++ eisd->u.gbl_eisd.common.eisdsize = (EISD__K_LEN + 4 + namlen + 5 + 3) & ~3; +++ eisd->u.gbl_eisd.common.secsize = VMS_BLOCK_SIZE; /* Must not be 0. */ +++ eisd->u.gbl_eisd.common.virt_addr = 0; +++ eisd->u.gbl_eisd.common.flags = EISD__M_GBL; +++ eisd->u.gbl_eisd.common.vbn = 0; +++ eisd->u.gbl_eisd.common.pfc = 0; +++ eisd->u.gbl_eisd.common.matchctl = PRIV2 (shrimg, matchctl); +++ eisd->u.gbl_eisd.common.type = EISD__K_SHRPIC; +++ +++ eisd->u.gbl_eisd.ident = PRIV2 (shrimg, ident); +++ eisd->u.gbl_eisd.gblnam[0] = namlen + 4; +++ memcpy (eisd->u.gbl_eisd.gblnam + 1, PRIV2 (shrimg, hdr_data.hdr_t_name), +++ namlen); +++ memcpy (eisd->u.gbl_eisd.gblnam + 1 + namlen, "_001", 4); +++ +++ /* Append it to the list. */ +++ sw_64_vms_append_extra_eisd (abfd, eisd); +++ +++ return TRUE; +++} +++ +++/* Create an EISD for section SEC. +++ Return FALSE in case of failure. */ +++ +++static bfd_boolean +++sw_64_vms_create_eisd_for_section (bfd *abfd, asection *sec) +++{ +++ struct vms_internal_eisd_map *eisd; +++ +++ /* Only for allocating section. */ +++ if (!(sec->flags & SEC_ALLOC)) +++ return TRUE; +++ +++ BFD_ASSERT (vms_section_data (sec)->eisd == NULL); +++ eisd = bfd_alloc (abfd, sizeof (*eisd)); +++ if (eisd == NULL) +++ return FALSE; +++ vms_section_data (sec)->eisd = eisd; +++ +++ /* Fill the fields. */ +++ eisd->u.eisd.majorid = EISD__K_MAJORID; +++ eisd->u.eisd.minorid = EISD__K_MINORID; +++ eisd->u.eisd.eisdsize = EISD__K_LEN; +++ eisd->u.eisd.secsize = +++ (sec->size + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1); +++ eisd->u.eisd.virt_addr = sec->vma; +++ eisd->u.eisd.flags = 0; +++ eisd->u.eisd.vbn = 0; /* To be later defined. */ +++ eisd->u.eisd.pfc = 0; /* Default. */ +++ eisd->u.eisd.matchctl = EISD__K_MATALL; +++ eisd->u.eisd.type = EISD__K_NORMAL; +++ +++ if (sec->flags & SEC_CODE) +++ eisd->u.eisd.flags |= EISD__M_EXE; +++ if (!(sec->flags & SEC_READONLY)) +++ eisd->u.eisd.flags |= EISD__M_WRT | EISD__M_CRF; +++ +++ /* If relocations or fixup will be applied, make this isect writeable. */ +++ if (sec->flags & SEC_RELOC) +++ eisd->u.eisd.flags |= EISD__M_WRT | EISD__M_CRF; +++ +++ if (!(sec->flags & SEC_HAS_CONTENTS)) +++ { +++ eisd->u.eisd.flags |= EISD__M_DZRO; +++ eisd->u.eisd.flags &= ~EISD__M_CRF; +++ } +++ if (sec->flags & SEC_LINKER_CREATED) +++ { +++ if (strcmp (sec->name, "$FIXUP$") == 0) +++ eisd->u.eisd.flags |= EISD__M_FIXUPVEC; +++ } +++ +++ /* Append it to the list. */ +++ eisd->next = NULL; +++ if (PRIV (eisd_head) == NULL) +++ PRIV (eisd_head) = eisd; +++ else +++ PRIV (eisd_tail)->next = eisd; +++ PRIV (eisd_tail) = eisd; +++ +++ return TRUE; +++} +++ +++/* Layout executable ABFD and write it to the disk. +++ Return FALSE in case of failure. */ +++ +++static bfd_boolean +++sw_64_vms_write_exec (bfd *abfd) +++{ +++ struct vms_eihd eihd; +++ struct vms_eiha *eiha; +++ struct vms_eihi *eihi; +++ struct vms_eihs *eihs = NULL; +++ asection *sec; +++ struct vms_internal_eisd_map *first_eisd; +++ struct vms_internal_eisd_map *eisd; +++ asection *dst; +++ asection *dmt; +++ file_ptr gst_filepos = 0; +++ unsigned int lnkflags = 0; +++ +++ /* Build the EIHD. */ +++ PRIV (file_pos) = EIHD__C_LENGTH; +++ +++ memset (&eihd, 0, sizeof (eihd)); +++ memset (eihd.fill_2, 0xff, sizeof (eihd.fill_2)); +++ +++ bfd_putl32 (EIHD__K_MAJORID, eihd.majorid); +++ bfd_putl32 (EIHD__K_MINORID, eihd.minorid); +++ +++ bfd_putl32 (sizeof (eihd), eihd.size); +++ bfd_putl32 (0, eihd.isdoff); +++ bfd_putl32 (0, eihd.activoff); +++ bfd_putl32 (0, eihd.symdbgoff); +++ bfd_putl32 (0, eihd.imgidoff); +++ bfd_putl32 (0, eihd.patchoff); +++ bfd_putl64 (0, eihd.iafva); +++ bfd_putl32 (0, eihd.version_array_off); +++ +++ bfd_putl32 (EIHD__K_EXE, eihd.imgtype); +++ bfd_putl32 (0, eihd.subtype); +++ +++ bfd_putl32 (0, eihd.imgiocnt); +++ bfd_putl32 (-1, eihd.privreqs); +++ bfd_putl32 (-1, eihd.privreqs + 4); +++ +++ bfd_putl32 ((sizeof (eihd) + VMS_BLOCK_SIZE - 1) / VMS_BLOCK_SIZE, +++ eihd.hdrblkcnt); +++ bfd_putl32 (0, eihd.ident); +++ bfd_putl32 (0, eihd.sysver); +++ +++ eihd.matchctl = 0; +++ bfd_putl32 (0, eihd.symvect_size); +++ bfd_putl32 (16, eihd.virt_mem_block_size); +++ bfd_putl32 (0, eihd.ext_fixup_off); +++ bfd_putl32 (0, eihd.noopt_psect_off); +++ bfd_putl32 (-1, eihd.alias); +++ +++ /* Alloc EIHA. */ +++ eiha = (struct vms_eiha *)((char *) &eihd + PRIV (file_pos)); +++ bfd_putl32 (PRIV (file_pos), eihd.activoff); +++ PRIV (file_pos) += sizeof (struct vms_eiha); +++ +++ bfd_putl32 (sizeof (struct vms_eiha), eiha->size); +++ bfd_putl32 (0, eiha->spare); +++ bfd_putl64 (PRIV (transfer_address[0]), eiha->tfradr1); +++ bfd_putl64 (PRIV (transfer_address[1]), eiha->tfradr2); +++ bfd_putl64 (PRIV (transfer_address[2]), eiha->tfradr3); +++ bfd_putl64 (PRIV (transfer_address[3]), eiha->tfradr4); +++ bfd_putl64 (0, eiha->inishr); +++ +++ /* Alloc EIHI. */ +++ eihi = (struct vms_eihi *)((char *) &eihd + PRIV (file_pos)); +++ bfd_putl32 (PRIV (file_pos), eihd.imgidoff); +++ PRIV (file_pos) += sizeof (struct vms_eihi); +++ +++ bfd_putl32 (EIHI__K_MAJORID, eihi->majorid); +++ bfd_putl32 (EIHI__K_MINORID, eihi->minorid); +++ { +++ char *module; +++ unsigned int len; +++ +++ /* Set module name. */ +++ module = vms_get_module_name (bfd_get_filename (abfd), TRUE); +++ len = strlen (module); +++ if (len > sizeof (eihi->imgnam) - 1) +++ len = sizeof (eihi->imgnam) - 1; +++ eihi->imgnam[0] = len; +++ memcpy (eihi->imgnam + 1, module, len); +++ free (module); +++ } +++ { +++ unsigned int lo; +++ unsigned int hi; +++ +++ /* Set time. */ +++ vms_get_time (&hi, &lo); +++ bfd_putl32 (lo, eihi->linktime + 0); +++ bfd_putl32 (hi, eihi->linktime + 4); +++ } +++ eihi->imgid[0] = 0; +++ eihi->linkid[0] = 0; +++ eihi->imgbid[0] = 0; +++ +++ /* Alloc EIHS. */ +++ dst = PRIV (dst_section); +++ dmt = bfd_get_section_by_name (abfd, "$DMT$"); +++ if (dst != NULL && dst->size != 0) +++ { +++ eihs = (struct vms_eihs *)((char *) &eihd + PRIV (file_pos)); +++ bfd_putl32 (PRIV (file_pos), eihd.symdbgoff); +++ PRIV (file_pos) += sizeof (struct vms_eihs); +++ +++ bfd_putl32 (EIHS__K_MAJORID, eihs->majorid); +++ bfd_putl32 (EIHS__K_MINORID, eihs->minorid); +++ bfd_putl32 (0, eihs->dstvbn); +++ bfd_putl32 (0, eihs->dstsize); +++ bfd_putl32 (0, eihs->gstvbn); +++ bfd_putl32 (0, eihs->gstsize); +++ bfd_putl32 (0, eihs->dmtvbn); +++ bfd_putl32 (0, eihs->dmtsize); +++ } +++ +++ /* One EISD per section. */ +++ for (sec = abfd->sections; sec; sec = sec->next) +++ { +++ if (!sw_64_vms_create_eisd_for_section (abfd, sec)) +++ return FALSE; +++ } +++ +++ /* Merge section EIDS which extra ones. */ +++ if (PRIV (eisd_tail)) +++ PRIV (eisd_tail)->next = PRIV (gbl_eisd_head); +++ else +++ PRIV (eisd_head) = PRIV (gbl_eisd_head); +++ if (PRIV (gbl_eisd_tail)) +++ PRIV (eisd_tail) = PRIV (gbl_eisd_tail); +++ +++ first_eisd = PRIV (eisd_head); +++ +++ /* Add end of eisd. */ +++ if (first_eisd) +++ { +++ eisd = bfd_zalloc (abfd, sizeof (*eisd)); +++ if (eisd == NULL) +++ return FALSE; +++ eisd->u.eisd.majorid = 0; +++ eisd->u.eisd.minorid = 0; +++ eisd->u.eisd.eisdsize = 0; +++ sw_64_vms_append_extra_eisd (abfd, eisd); +++ } +++ +++ /* Place EISD in the file. */ +++ for (eisd = first_eisd; eisd; eisd = eisd->next) +++ { +++ file_ptr room = VMS_BLOCK_SIZE - (PRIV (file_pos) % VMS_BLOCK_SIZE); +++ +++ /* First block is a little bit special: there is a word at the end. */ +++ if (PRIV (file_pos) < VMS_BLOCK_SIZE && room > 2) +++ room -= 2; +++ if (room < eisd->u.eisd.eisdsize + EISD__K_LENEND) +++ sw_64_vms_file_position_block (abfd); +++ +++ eisd->file_pos = PRIV (file_pos); +++ PRIV (file_pos) += eisd->u.eisd.eisdsize; +++ +++ if (eisd->u.eisd.flags & EISD__M_FIXUPVEC) +++ bfd_putl64 (eisd->u.eisd.virt_addr, eihd.iafva); +++ } +++ +++ if (first_eisd != NULL) +++ { +++ bfd_putl32 (first_eisd->file_pos, eihd.isdoff); +++ /* Real size of end of eisd marker. */ +++ PRIV (file_pos) += EISD__K_LENEND; +++ } +++ +++ bfd_putl32 (PRIV (file_pos), eihd.size); +++ bfd_putl32 ((PRIV (file_pos) + VMS_BLOCK_SIZE - 1) / VMS_BLOCK_SIZE, +++ eihd.hdrblkcnt); +++ +++ /* Place sections. */ +++ for (sec = abfd->sections; sec; sec = sec->next) +++ { +++ if (!(sec->flags & SEC_HAS_CONTENTS)) +++ continue; +++ +++ eisd = vms_section_data (sec)->eisd; +++ +++ /* Align on a block. */ +++ sw_64_vms_file_position_block (abfd); +++ sec->filepos = PRIV (file_pos); +++ +++ if (eisd != NULL) +++ eisd->u.eisd.vbn = (sec->filepos / VMS_BLOCK_SIZE) + 1; +++ +++ PRIV (file_pos) += sec->size; +++ } +++ +++ /* Update EIHS. */ +++ if (eihs != NULL && dst != NULL) +++ { +++ bfd_putl32 ((dst->filepos / VMS_BLOCK_SIZE) + 1, eihs->dstvbn); +++ bfd_putl32 (dst->size, eihs->dstsize); +++ +++ if (dmt != NULL) +++ { +++ lnkflags |= EIHD__M_DBGDMT; +++ bfd_putl32 ((dmt->filepos / VMS_BLOCK_SIZE) + 1, eihs->dmtvbn); +++ bfd_putl32 (dmt->size, eihs->dmtsize); +++ } +++ if (PRIV (gsd_sym_count) != 0) +++ { +++ sw_64_vms_file_position_block (abfd); +++ gst_filepos = PRIV (file_pos); +++ bfd_putl32 ((gst_filepos / VMS_BLOCK_SIZE) + 1, eihs->gstvbn); +++ bfd_putl32 ((PRIV (gsd_sym_count) + 4) / 5 + 4, eihs->gstsize); +++ } +++ } +++ +++ /* Write EISD in hdr. */ +++ for (eisd = first_eisd; eisd && eisd->file_pos < VMS_BLOCK_SIZE; +++ eisd = eisd->next) +++ sw_64_vms_swap_eisd_out +++ (eisd, (struct vms_eisd *)((char *)&eihd + eisd->file_pos)); +++ +++ /* Write first block. */ +++ bfd_putl32 (lnkflags, eihd.lnkflags); +++ if (bfd_bwrite (&eihd, sizeof (eihd), abfd) != sizeof (eihd)) +++ return FALSE; +++ +++ /* Write remaining eisd. */ +++ if (eisd != NULL) +++ { +++ unsigned char blk[VMS_BLOCK_SIZE]; +++ struct vms_internal_eisd_map *next_eisd; +++ +++ memset (blk, 0xff, sizeof (blk)); +++ while (eisd != NULL) +++ { +++ sw_64_vms_swap_eisd_out +++ (eisd, +++ (struct vms_eisd *)(blk + (eisd->file_pos % VMS_BLOCK_SIZE))); +++ +++ next_eisd = eisd->next; +++ if (next_eisd == NULL +++ || (next_eisd->file_pos / VMS_BLOCK_SIZE +++ != eisd->file_pos / VMS_BLOCK_SIZE)) +++ { +++ if (bfd_bwrite (blk, sizeof (blk), abfd) != sizeof (blk)) +++ return FALSE; +++ +++ memset (blk, 0xff, sizeof (blk)); +++ } +++ eisd = next_eisd; +++ } +++ } +++ +++ /* Write sections. */ +++ for (sec = abfd->sections; sec; sec = sec->next) +++ { +++ unsigned char blk[VMS_BLOCK_SIZE]; +++ bfd_size_type len; +++ +++ if (sec->size == 0 || !(sec->flags & SEC_HAS_CONTENTS)) +++ continue; +++ if (bfd_bwrite (sec->contents, sec->size, abfd) != sec->size) +++ return FALSE; +++ +++ /* Pad. */ +++ len = VMS_BLOCK_SIZE - sec->size % VMS_BLOCK_SIZE; +++ if (len != VMS_BLOCK_SIZE) +++ { +++ memset (blk, 0, len); +++ if (bfd_bwrite (blk, len, abfd) != len) +++ return FALSE; +++ } +++ } +++ +++ /* Write GST. */ +++ if (gst_filepos != 0) +++ { +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ unsigned int i; +++ +++ _bfd_vms_write_emh (abfd); +++ _bfd_vms_write_lmn (abfd, "GNU LD"); +++ +++ /* PSC for the absolute section. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EGSD); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC); +++ _bfd_vms_output_short (recwr, 0); +++ _bfd_vms_output_short (recwr, EGPS__V_PIC | EGPS__V_LIB | EGPS__V_RD); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_counted (recwr, ".$$ABS$$."); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_end (abfd, recwr); +++ +++ for (i = 0; i < PRIV (gsd_sym_count); i++) +++ { +++ struct vms_symbol_entry *sym = PRIV (syms)[i]; +++ bfd_vma val; +++ bfd_vma ep; +++ +++ if ((i % 5) == 0) +++ { +++ _bfd_vms_output_alignment (recwr, 8); +++ _bfd_vms_output_begin (recwr, EOBJ__C_EGSD); +++ _bfd_vms_output_long (recwr, 0); +++ } +++ _bfd_vms_output_begin_subrec (recwr, EGSD__C_SYMG); +++ _bfd_vms_output_short (recwr, 0); /* Data type, alignment. */ +++ _bfd_vms_output_short (recwr, sym->flags); +++ +++ if (sym->code_section) +++ ep = sw_64_vms_get_sym_value (sym->code_section, sym->code_value); +++ else +++ { +++ BFD_ASSERT (sym->code_value == 0); +++ ep = 0; +++ } +++ val = sw_64_vms_get_sym_value (sym->section, sym->value); +++ _bfd_vms_output_quad +++ (recwr, sym->typ == EGSD__C_SYMG ? sym->symbol_vector : val); +++ _bfd_vms_output_quad (recwr, ep); +++ _bfd_vms_output_quad (recwr, val); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ if ((i % 5) == 4) +++ _bfd_vms_output_end (abfd, recwr); +++ } +++ if ((i % 5) != 0) +++ _bfd_vms_output_end (abfd, recwr); +++ +++ if (!_bfd_vms_write_eeom (abfd)) +++ return FALSE; +++ } +++ return TRUE; +++} +++ +++/* Object write. */ +++ +++/* Write section and symbol directory of bfd abfd. Return FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_write_egsd (bfd *abfd) +++{ +++ asection *section; +++ asymbol *symbol; +++ unsigned int symnum; +++ const char *sname; +++ flagword new_flags, old_flags; +++ int abs_section_index = -1; +++ unsigned int target_index = 0; +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ vms_debug2 ((2, "vms_write_egsd\n")); +++ +++ /* Egsd is quadword aligned. */ +++ _bfd_vms_output_alignment (recwr, 8); +++ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EGSD); +++ _bfd_vms_output_long (recwr, 0); +++ +++ /* Number sections. */ +++ for (section = abfd->sections; section != NULL; section = section->next) +++ { +++ if (section->flags & SEC_DEBUGGING) +++ continue; +++ if (!strcmp (section->name, ".vmsdebug")) +++ { +++ section->flags |= SEC_DEBUGGING; +++ continue; +++ } +++ section->target_index = target_index++; +++ } +++ +++ for (section = abfd->sections; section != NULL; section = section->next) +++ { +++ vms_debug2 ((3, "Section #%d %s, %d bytes\n", +++ section->target_index, section->name, (int)section->size)); +++ +++ /* Don't write out the VMS debug info section since it is in the +++ ETBT and EDBG sections in etir. */ +++ if (section->flags & SEC_DEBUGGING) +++ continue; +++ +++ /* 13 bytes egsd, max 31 chars name -> should be 44 bytes. */ +++ if (_bfd_vms_output_check (recwr, 64) < 0) +++ { +++ _bfd_vms_output_end (abfd, recwr); +++ _bfd_vms_output_begin (recwr, EOBJ__C_EGSD); +++ _bfd_vms_output_long (recwr, 0); +++ } +++ +++ /* Don't know if this is necessary for the linker but for now it keeps +++ vms_slurp_gsd happy. */ +++ sname = section->name; +++ if (*sname == '.') +++ { +++ /* Remove leading dot. */ +++ sname++; +++ if ((*sname == 't') && (strcmp (sname, "text") == 0)) +++ sname = EVAX_CODE_NAME; +++ else if ((*sname == 'd') && (strcmp (sname, "data") == 0)) +++ sname = EVAX_DATA_NAME; +++ else if ((*sname == 'b') && (strcmp (sname, "bss") == 0)) +++ sname = EVAX_BSS_NAME; +++ else if ((*sname == 'l') && (strcmp (sname, "link") == 0)) +++ sname = EVAX_LINK_NAME; +++ else if ((*sname == 'r') && (strcmp (sname, "rdata") == 0)) +++ sname = EVAX_READONLY_NAME; +++ else if ((*sname == 'l') && (strcmp (sname, "literal") == 0)) +++ sname = EVAX_LITERAL_NAME; +++ else if ((*sname == 'l') && (strcmp (sname, "literals") == 0)) +++ sname = EVAX_LITERALS_NAME; +++ else if ((*sname == 'c') && (strcmp (sname, "comm") == 0)) +++ sname = EVAX_COMMON_NAME; +++ else if ((*sname == 'l') && (strcmp (sname, "lcomm") == 0)) +++ sname = EVAX_LOCAL_NAME; +++ } +++ +++ if (bfd_is_com_section (section)) +++ new_flags = (EGPS__V_OVR | EGPS__V_REL | EGPS__V_GBL | EGPS__V_RD +++ | EGPS__V_WRT | EGPS__V_NOMOD | EGPS__V_COM); +++ else +++ new_flags = vms_esecflag_by_name (evax_section_flags, sname, +++ section->size > 0); +++ +++ /* Modify them as directed. */ +++ if (section->flags & SEC_READONLY) +++ new_flags &= ~EGPS__V_WRT; +++ +++ new_flags &= ~vms_section_data (section)->no_flags; +++ new_flags |= vms_section_data (section)->flags; +++ +++ vms_debug2 ((3, "sec flags %x\n", section->flags)); +++ vms_debug2 ((3, "new_flags %x, _raw_size %lu\n", +++ new_flags, (unsigned long)section->size)); +++ +++ _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC); +++ _bfd_vms_output_short (recwr, section->alignment_power & 0xff); +++ _bfd_vms_output_short (recwr, new_flags); +++ _bfd_vms_output_long (recwr, (unsigned long) section->size); +++ _bfd_vms_output_counted (recwr, sname); +++ _bfd_vms_output_end_subrec (recwr); +++ +++ /* If the section is an obsolute one, remind its index as it will be +++ used later for absolute symbols. */ +++ if ((new_flags & EGPS__V_REL) == 0 && abs_section_index < 0) +++ abs_section_index = section->target_index; +++ } +++ +++ /* Output symbols. */ +++ vms_debug2 ((3, "%d symbols found\n", abfd->symcount)); +++ +++ bfd_set_start_address (abfd, (bfd_vma) -1); +++ +++ for (symnum = 0; symnum < abfd->symcount; symnum++) +++ { +++ symbol = abfd->outsymbols[symnum]; +++ old_flags = symbol->flags; +++ +++ /* Work-around a missing feature: consider __main as the main entry +++ point. */ +++ if (symbol->name[0] == '_' && strcmp (symbol->name, "__main") == 0) +++ bfd_set_start_address (abfd, (bfd_vma)symbol->value); +++ +++ /* Only put in the GSD the global and the undefined symbols. */ +++ if (old_flags & BSF_FILE) +++ continue; +++ +++ if ((old_flags & BSF_GLOBAL) == 0 && !bfd_is_und_section (symbol->section)) +++ { +++ /* If the LIB$INITIIALIZE section is present, add a reference to +++ LIB$INITIALIZE symbol. FIXME: this should be done explicitely +++ in the assembly file. */ +++ if (!((old_flags & BSF_SECTION_SYM) != 0 +++ && strcmp (symbol->section->name, "LIB$INITIALIZE") == 0)) +++ continue; +++ } +++ +++ /* 13 bytes egsd, max 64 chars name -> should be 77 bytes. Add 16 more +++ bytes for a possible ABS section. */ +++ if (_bfd_vms_output_check (recwr, 80 + 16) < 0) +++ { +++ _bfd_vms_output_end (abfd, recwr); +++ _bfd_vms_output_begin (recwr, EOBJ__C_EGSD); +++ _bfd_vms_output_long (recwr, 0); +++ } +++ +++ if ((old_flags & BSF_GLOBAL) != 0 +++ && bfd_is_abs_section (symbol->section) +++ && abs_section_index <= 0) +++ { +++ /* Create an absolute section if none was defined. It is highly +++ unlikely that the name $ABS$ clashes with a user defined +++ non-absolute section name. */ +++ _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC); +++ _bfd_vms_output_short (recwr, 4); +++ _bfd_vms_output_short (recwr, EGPS__V_SHR); +++ _bfd_vms_output_long (recwr, 0); +++ _bfd_vms_output_counted (recwr, "$ABS$"); +++ _bfd_vms_output_end_subrec (recwr); +++ +++ abs_section_index = target_index++; +++ } +++ +++ _bfd_vms_output_begin_subrec (recwr, EGSD__C_SYM); +++ +++ /* Data type, alignment. */ +++ _bfd_vms_output_short (recwr, 0); +++ +++ new_flags = 0; +++ +++ if (old_flags & BSF_WEAK) +++ new_flags |= EGSY__V_WEAK; +++ if (bfd_is_com_section (symbol->section)) /* .comm */ +++ new_flags |= (EGSY__V_WEAK | EGSY__V_COMM); +++ +++ if (old_flags & BSF_FUNCTION) +++ { +++ new_flags |= EGSY__V_NORM; +++ new_flags |= EGSY__V_REL; +++ } +++ if (old_flags & BSF_GLOBAL) +++ { +++ new_flags |= EGSY__V_DEF; +++ if (!bfd_is_abs_section (symbol->section)) +++ new_flags |= EGSY__V_REL; +++ } +++ _bfd_vms_output_short (recwr, new_flags); +++ +++ if (old_flags & BSF_GLOBAL) +++ { +++ /* Symbol definition. */ +++ bfd_vma code_address = 0; +++ unsigned long ca_psindx = 0; +++ unsigned long psindx; +++ +++ if ((old_flags & BSF_FUNCTION) && symbol->udata.p != NULL) +++ { +++ asymbol *sym; +++ +++ sym = +++ ((struct evax_private_udata_struct *)symbol->udata.p)->enbsym; +++ code_address = sym->value; +++ ca_psindx = sym->section->target_index; +++ } +++ if (bfd_is_abs_section (symbol->section)) +++ psindx = abs_section_index; +++ else +++ psindx = symbol->section->target_index; +++ +++ _bfd_vms_output_quad (recwr, symbol->value); +++ _bfd_vms_output_quad (recwr, code_address); +++ _bfd_vms_output_long (recwr, ca_psindx); +++ _bfd_vms_output_long (recwr, psindx); +++ } +++ _bfd_vms_output_counted (recwr, symbol->name); +++ +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ +++ _bfd_vms_output_alignment (recwr, 8); +++ _bfd_vms_output_end (abfd, recwr); +++ +++ return TRUE; +++} +++ +++/* Write object header for bfd abfd. Return FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_write_ehdr (bfd *abfd) +++{ +++ asymbol *symbol; +++ unsigned int symnum; +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ vms_debug2 ((2, "vms_write_ehdr (%p)\n", abfd)); +++ +++ _bfd_vms_output_alignment (recwr, 2); +++ +++ _bfd_vms_write_emh (abfd); +++ _bfd_vms_write_lmn (abfd, "GNU AS"); +++ +++ /* SRC. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EMH); +++ _bfd_vms_output_short (recwr, EMH__C_SRC); +++ +++ for (symnum = 0; symnum < abfd->symcount; symnum++) +++ { +++ symbol = abfd->outsymbols[symnum]; +++ +++ if (symbol->flags & BSF_FILE) +++ { +++ _bfd_vms_output_dump (recwr, (unsigned char *) symbol->name, +++ (int) strlen (symbol->name)); +++ break; +++ } +++ } +++ +++ if (symnum == abfd->symcount) +++ _bfd_vms_output_dump (recwr, (unsigned char *) STRING_COMMA_LEN ("noname")); +++ +++ _bfd_vms_output_end (abfd, recwr); +++ +++ /* TTL. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EMH); +++ _bfd_vms_output_short (recwr, EMH__C_TTL); +++ _bfd_vms_output_dump (recwr, (unsigned char *) STRING_COMMA_LEN ("TTL")); +++ _bfd_vms_output_end (abfd, recwr); +++ +++ /* CPR. */ +++ _bfd_vms_output_begin (recwr, EOBJ__C_EMH); +++ _bfd_vms_output_short (recwr, EMH__C_CPR); +++ _bfd_vms_output_dump (recwr, +++ (unsigned char *)"GNU BFD ported by Klaus Kämpf 1994-1996", +++ 39); +++ _bfd_vms_output_end (abfd, recwr); +++ +++ return TRUE; +++} +++ +++/* Part 4.6, relocations. */ +++ +++ +++/* WRITE ETIR SECTION +++ +++ This is still under construction and therefore not documented. */ +++ +++/* Close the etir/etbt record. */ +++ +++static void +++end_etir_record (bfd * abfd) +++{ +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ _bfd_vms_output_end (abfd, recwr); +++} +++ +++static void +++start_etir_or_etbt_record (bfd *abfd, asection *section, bfd_vma offset) +++{ +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ if (section->flags & SEC_DEBUGGING) +++ { +++ _bfd_vms_output_begin (recwr, EOBJ__C_ETBT); +++ +++ if (offset == 0) +++ { +++ /* Push start offset. */ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW); +++ _bfd_vms_output_long (recwr, (unsigned long) 0); +++ _bfd_vms_output_end_subrec (recwr); +++ +++ /* Set location. */ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_CTL_DFLOC); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ } +++ else +++ { +++ _bfd_vms_output_begin (recwr, EOBJ__C_ETIR); +++ +++ if (offset == 0) +++ { +++ /* Push start offset. */ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ); +++ _bfd_vms_output_long (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, offset); +++ _bfd_vms_output_end_subrec (recwr); +++ +++ /* Start = pop (). */ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_CTL_SETRB); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ } +++} +++ +++/* Output a STO_IMM command for SSIZE bytes of data from CPR at virtual +++ address VADDR in section specified by SEC_INDEX and NAME. */ +++ +++static void +++sto_imm (bfd *abfd, asection *section, +++ bfd_size_type ssize, unsigned char *cptr, bfd_vma vaddr) +++{ +++ bfd_size_type size; +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++#if VMS_DEBUG +++ _bfd_vms_debug (8, "sto_imm %d bytes\n", (int) ssize); +++ _bfd_hexdump (9, cptr, (int) ssize, (int) vaddr); +++#endif +++ +++ while (ssize > 0) +++ { +++ /* Try all the rest. */ +++ size = ssize; +++ +++ if (_bfd_vms_output_check (recwr, size) < 0) +++ { +++ /* Doesn't fit, split ! */ +++ end_etir_record (abfd); +++ +++ start_etir_or_etbt_record (abfd, section, vaddr); +++ +++ size = _bfd_vms_output_check (recwr, 0); /* get max size */ +++ if (size > ssize) /* more than what's left ? */ +++ size = ssize; +++ } +++ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_IMM); +++ _bfd_vms_output_long (recwr, (unsigned long) (size)); +++ _bfd_vms_output_dump (recwr, cptr, size); +++ _bfd_vms_output_end_subrec (recwr); +++ +++#if VMS_DEBUG +++ _bfd_vms_debug (10, "dumped %d bytes\n", (int) size); +++ _bfd_hexdump (10, cptr, (int) size, (int) vaddr); +++#endif +++ +++ vaddr += size; +++ cptr += size; +++ ssize -= size; +++ } +++} +++ +++static void +++etir_output_check (bfd *abfd, asection *section, bfd_vma vaddr, int checklen) +++{ +++ if (_bfd_vms_output_check (&PRIV (recwr), checklen) < 0) +++ { +++ /* Not enough room in this record. Close it and open a new one. */ +++ end_etir_record (abfd); +++ start_etir_or_etbt_record (abfd, section, vaddr); +++ } +++} +++ +++/* Return whether RELOC must be deferred till the end. */ +++ +++static bfd_boolean +++defer_reloc_p (arelent *reloc) +++{ +++ switch (reloc->howto->type) +++ { +++ case SW_64_R_NOP: +++ case SW_64_R_LDA: +++ case SW_64_R_BSR: +++ case SW_64_R_BOH: +++ return TRUE; +++ +++ default: +++ return FALSE; +++ } +++} +++ +++/* Write section contents for bfd abfd. Return FALSE on error. */ +++ +++static bfd_boolean +++_bfd_vms_write_etir (bfd * abfd, int objtype ATTRIBUTE_UNUSED) +++{ +++ asection *section; +++ struct vms_rec_wr *recwr = &PRIV (recwr); +++ +++ vms_debug2 ((2, "vms_write_tir (%p, %d)\n", abfd, objtype)); +++ +++ _bfd_vms_output_alignment (recwr, 4); +++ +++ PRIV (vms_linkage_index) = 0; +++ +++ for (section = abfd->sections; section; section = section->next) +++ { +++ vms_debug2 ((4, "writing %d. section '%s' (%d bytes)\n", +++ section->target_index, section->name, (int) (section->size))); +++ +++ if (!(section->flags & SEC_HAS_CONTENTS) +++ || bfd_is_com_section (section)) +++ continue; +++ +++ if (!section->contents) +++ { +++ bfd_set_error (bfd_error_no_contents); +++ return FALSE; +++ } +++ +++ start_etir_or_etbt_record (abfd, section, 0); +++ +++ if (section->flags & SEC_RELOC) +++ { +++ bfd_vma curr_addr = 0; +++ unsigned char *curr_data = section->contents; +++ bfd_size_type size; +++ int pass2_needed = 0; +++ int pass2_in_progress = 0; +++ unsigned int irel; +++ +++ if (section->reloc_count == 0) +++ _bfd_error_handler +++ (_("SEC_RELOC with no relocs in section %pA"), section); +++ +++#if VMS_DEBUG +++ else +++ { +++ int i = section->reloc_count; +++ arelent **rptr = section->orelocation; +++ _bfd_vms_debug (4, "%d relocations:\n", i); +++ while (i-- > 0) +++ { +++ _bfd_vms_debug (4, "sym %s in sec %s, value %08lx, " +++ "addr %08lx, off %08lx, len %d: %s\n", +++ (*(*rptr)->sym_ptr_ptr)->name, +++ (*(*rptr)->sym_ptr_ptr)->section->name, +++ (long) (*(*rptr)->sym_ptr_ptr)->value, +++ (unsigned long)(*rptr)->address, +++ (unsigned long)(*rptr)->addend, +++ bfd_get_reloc_size ((*rptr)->howto), +++ ( *rptr)->howto->name); +++ rptr++; +++ } +++ } +++#endif +++ +++ new_pass: +++ for (irel = 0; irel < section->reloc_count; irel++) +++ { +++ struct evax_private_udata_struct *udata; +++ arelent *rptr = section->orelocation [irel]; +++ bfd_vma addr = rptr->address; +++ asymbol *sym = *rptr->sym_ptr_ptr; +++ asection *sec = sym->section; +++ bfd_boolean defer = defer_reloc_p (rptr); +++ unsigned int slen; +++ +++ if (pass2_in_progress) +++ { +++ /* Non-deferred relocs have already been output. */ +++ if (!defer) +++ continue; +++ } +++ else +++ { +++ /* Deferred relocs must be output at the very end. */ +++ if (defer) +++ { +++ pass2_needed = 1; +++ continue; +++ } +++ +++ /* Regular relocs are intertwined with binary data. */ +++ if (curr_addr > addr) +++ _bfd_error_handler (_("size error in section %pA"), +++ section); +++ size = addr - curr_addr; +++ sto_imm (abfd, section, size, curr_data, curr_addr); +++ curr_data += size; +++ curr_addr += size; +++ } +++ +++ size = bfd_get_reloc_size (rptr->howto); +++ +++ switch (rptr->howto->type) +++ { +++ case SW_64_R_IGNORE: +++ break; +++ +++ case SW_64_R_REFLONG: +++ if (bfd_is_und_section (sym->section)) +++ { +++ bfd_vma addend = rptr->addend; +++ slen = strlen ((char *) sym->name); +++ etir_output_check (abfd, section, curr_addr, slen); +++ if (addend) +++ { +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_GBL); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW); +++ _bfd_vms_output_long (recwr, (unsigned long) addend); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_OPR_ADD); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ else +++ { +++ _bfd_vms_output_begin_subrec +++ (recwr, ETIR__C_STO_GBL_LW); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ } +++ else if (bfd_is_abs_section (sym->section)) +++ { +++ etir_output_check (abfd, section, curr_addr, 16); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW); +++ _bfd_vms_output_long (recwr, (unsigned long) sym->value); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ else +++ { +++ etir_output_check (abfd, section, curr_addr, 32); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ); +++ _bfd_vms_output_long (recwr, +++ (unsigned long) sec->target_index); +++ _bfd_vms_output_quad (recwr, rptr->addend + sym->value); +++ _bfd_vms_output_end_subrec (recwr); +++ /* ??? Table B-8 of the OpenVMS Linker Utilily Manual +++ says that we should have a ETIR__C_STO_OFF here. +++ But the relocation would not be BFD_RELOC_32 then. +++ This case is very likely unreachable. */ +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ break; +++ +++ case SW_64_R_REFQUAD: +++ if (bfd_is_und_section (sym->section)) +++ { +++ bfd_vma addend = rptr->addend; +++ slen = strlen ((char *) sym->name); +++ etir_output_check (abfd, section, curr_addr, slen); +++ if (addend) +++ { +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_GBL); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_QW); +++ _bfd_vms_output_quad (recwr, addend); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_OPR_ADD); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_QW); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ else +++ { +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_GBL); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ } +++ else if (bfd_is_abs_section (sym->section)) +++ { +++ etir_output_check (abfd, section, curr_addr, 16); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_QW); +++ _bfd_vms_output_quad (recwr, sym->value); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_QW); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ else +++ { +++ etir_output_check (abfd, section, curr_addr, 32); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ); +++ _bfd_vms_output_long (recwr, +++ (unsigned long) sec->target_index); +++ _bfd_vms_output_quad (recwr, rptr->addend + sym->value); +++ _bfd_vms_output_end_subrec (recwr); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_OFF); +++ _bfd_vms_output_end_subrec (recwr); +++ } +++ break; +++ +++ case SW_64_R_HINT: +++ sto_imm (abfd, section, size, curr_data, curr_addr); +++ break; +++ +++ case SW_64_R_LINKAGE: +++ etir_output_check (abfd, section, curr_addr, 64); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_LP_PSB); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) rptr->addend); +++ if (rptr->addend > PRIV (vms_linkage_index)) +++ PRIV (vms_linkage_index) = rptr->addend; +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_byte (recwr, 0); +++ _bfd_vms_output_end_subrec (recwr); +++ break; +++ +++ case SW_64_R_CODEADDR: +++ slen = strlen ((char *) sym->name); +++ etir_output_check (abfd, section, curr_addr, slen); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_CA); +++ _bfd_vms_output_counted (recwr, sym->name); +++ _bfd_vms_output_end_subrec (recwr); +++ break; +++ +++ case SW_64_R_NOP: +++ udata +++ = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr; +++ etir_output_check (abfd, section, curr_addr, +++ 32 + 1 + strlen (udata->origname)); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_NOP_GBL); +++ _bfd_vms_output_long (recwr, (unsigned long) udata->lkindex); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->address); +++ _bfd_vms_output_long (recwr, (unsigned long) 0x47ff041f); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->addend); +++ _bfd_vms_output_counted (recwr, udata->origname); +++ _bfd_vms_output_end_subrec (recwr); +++ break; +++ +++ case SW_64_R_BSR: +++ _bfd_error_handler (_("spurious SW_64_R_BSR reloc")); +++ break; +++ +++ case SW_64_R_LDA: +++ udata +++ = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr; +++ etir_output_check (abfd, section, curr_addr, +++ 32 + 1 + strlen (udata->origname)); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_LDA_GBL); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) udata->lkindex + 1); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->address); +++ _bfd_vms_output_long (recwr, (unsigned long) 0x237B0000); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) udata->bsym->section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->addend); +++ _bfd_vms_output_counted (recwr, udata->origname); +++ _bfd_vms_output_end_subrec (recwr); +++ break; +++ +++ case SW_64_R_BOH: +++ udata +++ = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr; +++ etir_output_check (abfd, section, curr_addr, +++ 32 + 1 + strlen (udata->origname)); +++ _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_BOH_GBL); +++ _bfd_vms_output_long (recwr, (unsigned long) udata->lkindex); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->address); +++ _bfd_vms_output_long (recwr, (unsigned long) 0xD3400000); +++ _bfd_vms_output_long +++ (recwr, (unsigned long) section->target_index); +++ _bfd_vms_output_quad (recwr, rptr->addend); +++ _bfd_vms_output_counted (recwr, udata->origname); +++ _bfd_vms_output_end_subrec (recwr); +++ break; +++ +++ default: +++ _bfd_error_handler (_("unhandled relocation %s"), +++ rptr->howto->name); +++ break; +++ } +++ +++ curr_data += size; +++ curr_addr += size; +++ } /* End of relocs loop. */ +++ +++ if (!pass2_in_progress) +++ { +++ /* Output rest of section. */ +++ if (curr_addr > section->size) +++ _bfd_error_handler (_("size error in section %pA"), section); +++ size = section->size - curr_addr; +++ sto_imm (abfd, section, size, curr_data, curr_addr); +++ curr_data += size; +++ curr_addr += size; +++ +++ if (pass2_needed) +++ { +++ pass2_in_progress = 1; +++ goto new_pass; +++ } +++ } +++ } +++ +++ else /* (section->flags & SEC_RELOC) */ +++ sto_imm (abfd, section, section->size, section->contents, 0); +++ +++ end_etir_record (abfd); +++ } +++ +++ _bfd_vms_output_alignment (recwr, 2); +++ return TRUE; +++} +++ +++/* Write cached information into a file being written, at bfd_close. */ +++ +++static bfd_boolean +++sw_64_vms_write_object_contents (bfd *abfd) +++{ +++ vms_debug2 ((1, "vms_write_object_contents (%p)\n", abfd)); +++ +++ if (abfd->flags & (EXEC_P | DYNAMIC)) +++ { +++ return sw_64_vms_write_exec (abfd); +++ } +++ else +++ { +++ if (abfd->section_count > 0) /* we have sections */ +++ { +++ if (!_bfd_vms_write_ehdr (abfd)) +++ return FALSE; +++ if (!_bfd_vms_write_egsd (abfd)) +++ return FALSE; +++ if (!_bfd_vms_write_etir (abfd, EOBJ__C_ETIR)) +++ return FALSE; +++ if (!_bfd_vms_write_eeom (abfd)) +++ return FALSE; +++ } +++ } +++ return TRUE; +++} +++ +++/* Debug stuff: nearest line. */ +++ +++#define SET_MODULE_PARSED(m) \ +++ do { if ((m)->name == NULL) (m)->name = ""; } while (0) +++#define IS_MODULE_PARSED(m) ((m)->name != NULL) +++ +++/* Build a new module for the specified BFD. */ +++ +++static struct module * +++new_module (bfd *abfd) +++{ +++ struct module *module +++ = (struct module *) bfd_zalloc (abfd, sizeof (struct module)); +++ module->file_table_count = 16; /* Arbitrary. */ +++ module->file_table +++ = bfd_malloc (module->file_table_count * sizeof (struct fileinfo)); +++ return module; +++} +++ +++/* Parse debug info for a module and internalize it. */ +++ +++static void +++parse_module (bfd *abfd, struct module *module, unsigned char *ptr, +++ int length) +++{ +++ unsigned char *maxptr = ptr + length; +++ unsigned char *src_ptr, *pcl_ptr; +++ unsigned int prev_linum = 0, curr_linenum = 0; +++ bfd_vma prev_pc = 0, curr_pc = 0; +++ struct srecinfo *curr_srec, *srec; +++ struct lineinfo *curr_line, *line; +++ struct funcinfo *funcinfo; +++ +++ /* Initialize tables with zero element. */ +++ curr_srec = (struct srecinfo *) bfd_zalloc (abfd, sizeof (struct srecinfo)); +++ module->srec_table = curr_srec; +++ +++ curr_line = (struct lineinfo *) bfd_zalloc (abfd, sizeof (struct lineinfo)); +++ module->line_table = curr_line; +++ +++ while (length == -1 || ptr < maxptr) +++ { +++ /* The first byte is not counted in the recorded length. */ +++ int rec_length = bfd_getl16 (ptr) + 1; +++ int rec_type = bfd_getl16 (ptr + 2); +++ +++ vms_debug2 ((2, "DST record: leng %d, type %d\n", rec_length, rec_type)); +++ +++ if (length == -1 && rec_type == DST__K_MODEND) +++ break; +++ +++ switch (rec_type) +++ { +++ case DST__K_MODBEG: +++ module->name +++ = _bfd_vms_save_counted_string (ptr + DST_S_B_MODBEG_NAME, +++ maxptr - (ptr + DST_S_B_MODBEG_NAME)); +++ +++ curr_pc = 0; +++ prev_pc = 0; +++ curr_linenum = 0; +++ prev_linum = 0; +++ +++ vms_debug2 ((3, "module: %s\n", module->name)); +++ break; +++ +++ case DST__K_MODEND: +++ break; +++ +++ case DST__K_RTNBEG: +++ funcinfo = (struct funcinfo *) +++ bfd_zalloc (abfd, sizeof (struct funcinfo)); +++ funcinfo->name +++ = _bfd_vms_save_counted_string (ptr + DST_S_B_RTNBEG_NAME, +++ maxptr - (ptr + DST_S_B_RTNBEG_NAME)); +++ funcinfo->low = bfd_getl32 (ptr + DST_S_L_RTNBEG_ADDRESS); +++ funcinfo->next = module->func_table; +++ module->func_table = funcinfo; +++ +++ vms_debug2 ((3, "routine: %s at 0x%lx\n", +++ funcinfo->name, (unsigned long) funcinfo->low)); +++ break; +++ +++ case DST__K_RTNEND: +++ module->func_table->high = module->func_table->low +++ + bfd_getl32 (ptr + DST_S_L_RTNEND_SIZE) - 1; +++ +++ if (module->func_table->high > module->high) +++ module->high = module->func_table->high; +++ +++ vms_debug2 ((3, "end routine\n")); +++ break; +++ +++ case DST__K_PROLOG: +++ vms_debug2 ((3, "prologue\n")); +++ break; +++ +++ case DST__K_EPILOG: +++ vms_debug2 ((3, "epilog\n")); +++ break; +++ +++ case DST__K_BLKBEG: +++ vms_debug2 ((3, "block\n")); +++ break; +++ +++ case DST__K_BLKEND: +++ vms_debug2 ((3, "end block\n")); +++ break; +++ +++ case DST__K_SOURCE: +++ src_ptr = ptr + DST_S_C_SOURCE_HEADER_SIZE; +++ +++ vms_debug2 ((3, "source info\n")); +++ +++ while (src_ptr < ptr + rec_length) +++ { +++ int cmd = src_ptr[0], cmd_length, data; +++ +++ switch (cmd) +++ { +++ case DST__K_SRC_DECLFILE: +++ { +++ unsigned int fileid +++ = bfd_getl16 (src_ptr + DST_S_W_SRC_DF_FILEID); +++ char *filename +++ = _bfd_vms_save_counted_string (src_ptr + DST_S_B_SRC_DF_FILENAME, +++ (ptr + rec_length) - +++ (src_ptr + DST_S_B_SRC_DF_FILENAME) +++ ); +++ +++ while (fileid >= module->file_table_count) +++ { +++ module->file_table_count *= 2; +++ module->file_table +++ = bfd_realloc (module->file_table, +++ module->file_table_count +++ * sizeof (struct fileinfo)); +++ } +++ +++ module->file_table [fileid].name = filename; +++ module->file_table [fileid].srec = 1; +++ cmd_length = src_ptr[DST_S_B_SRC_DF_LENGTH] + 2; +++ vms_debug2 ((4, "DST_S_C_SRC_DECLFILE: %d, %s\n", +++ fileid, module->file_table [fileid].name)); +++ } +++ break; +++ +++ case DST__K_SRC_DEFLINES_B: +++ /* Perform the association and set the next higher index +++ to the limit. */ +++ data = src_ptr[DST_S_B_SRC_UNSBYTE]; +++ srec = (struct srecinfo *) +++ bfd_zalloc (abfd, sizeof (struct srecinfo)); +++ srec->line = curr_srec->line + data; +++ srec->srec = curr_srec->srec + data; +++ srec->sfile = curr_srec->sfile; +++ curr_srec->next = srec; +++ curr_srec = srec; +++ cmd_length = 2; +++ vms_debug2 ((4, "DST_S_C_SRC_DEFLINES_B: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_DEFLINES_W: +++ /* Perform the association and set the next higher index +++ to the limit. */ +++ data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD); +++ srec = (struct srecinfo *) +++ bfd_zalloc (abfd, sizeof (struct srecinfo)); +++ srec->line = curr_srec->line + data; +++ srec->srec = curr_srec->srec + data, +++ srec->sfile = curr_srec->sfile; +++ curr_srec->next = srec; +++ curr_srec = srec; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST_S_C_SRC_DEFLINES_W: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_INCRLNUM_B: +++ data = src_ptr[DST_S_B_SRC_UNSBYTE]; +++ curr_srec->line += data; +++ cmd_length = 2; +++ vms_debug2 ((4, "DST_S_C_SRC_INCRLNUM_B: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_SETFILE: +++ data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD); +++ curr_srec->sfile = data; +++ curr_srec->srec = module->file_table[data].srec; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST_S_C_SRC_SETFILE: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_SETLNUM_L: +++ data = bfd_getl32 (src_ptr + DST_S_L_SRC_UNSLONG); +++ curr_srec->line = data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST_S_C_SRC_SETLNUM_L: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_SETLNUM_W: +++ data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD); +++ curr_srec->line = data; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST_S_C_SRC_SETLNUM_W: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_SETREC_L: +++ data = bfd_getl32 (src_ptr + DST_S_L_SRC_UNSLONG); +++ curr_srec->srec = data; +++ module->file_table[curr_srec->sfile].srec = data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST_S_C_SRC_SETREC_L: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_SETREC_W: +++ data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD); +++ curr_srec->srec = data; +++ module->file_table[curr_srec->sfile].srec = data; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST_S_C_SRC_SETREC_W: %d\n", data)); +++ break; +++ +++ case DST__K_SRC_FORMFEED: +++ cmd_length = 1; +++ vms_debug2 ((4, "DST_S_C_SRC_FORMFEED\n")); +++ break; +++ +++ default: +++ _bfd_error_handler (_("unknown source command %d"), +++ cmd); +++ cmd_length = 2; +++ break; +++ } +++ +++ src_ptr += cmd_length; +++ } +++ break; +++ +++ case DST__K_LINE_NUM: +++ pcl_ptr = ptr + DST_S_C_LINE_NUM_HEADER_SIZE; +++ +++ vms_debug2 ((3, "line info\n")); +++ +++ while (pcl_ptr < ptr + rec_length) +++ { +++ /* The command byte is signed so we must sign-extend it. */ +++ int cmd = ((signed char *)pcl_ptr)[0], cmd_length, data; +++ +++ switch (cmd) +++ { +++ case DST__K_DELTA_PC_W: +++ data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD); +++ curr_pc += data; +++ curr_linenum += 1; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST__K_DELTA_PC_W: %d\n", data)); +++ break; +++ +++ case DST__K_DELTA_PC_L: +++ data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG); +++ curr_pc += data; +++ curr_linenum += 1; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST__K_DELTA_PC_L: %d\n", data)); +++ break; +++ +++ case DST__K_INCR_LINUM: +++ data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE]; +++ curr_linenum += data; +++ cmd_length = 2; +++ vms_debug2 ((4, "DST__K_INCR_LINUM: %d\n", data)); +++ break; +++ +++ case DST__K_INCR_LINUM_W: +++ data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD); +++ curr_linenum += data; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST__K_INCR_LINUM_W: %d\n", data)); +++ break; +++ +++ case DST__K_INCR_LINUM_L: +++ data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG); +++ curr_linenum += data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST__K_INCR_LINUM_L: %d\n", data)); +++ break; +++ +++ case DST__K_SET_LINUM_INCR: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_LINUM_INCR"); +++ cmd_length = 2; +++ break; +++ +++ case DST__K_SET_LINUM_INCR_W: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_LINUM_INCR_W"); +++ cmd_length = 3; +++ break; +++ +++ case DST__K_RESET_LINUM_INCR: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_RESET_LINUM_INCR"); +++ cmd_length = 1; +++ break; +++ +++ case DST__K_BEG_STMT_MODE: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_BEG_STMT_MODE"); +++ cmd_length = 1; +++ break; +++ +++ case DST__K_END_STMT_MODE: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_END_STMT_MODE"); +++ cmd_length = 1; +++ break; +++ +++ case DST__K_SET_LINUM_B: +++ data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE]; +++ curr_linenum = data; +++ cmd_length = 2; +++ vms_debug2 ((4, "DST__K_SET_LINUM_B: %d\n", data)); +++ break; +++ +++ case DST__K_SET_LINUM: +++ data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD); +++ curr_linenum = data; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST__K_SET_LINE_NUM: %d\n", data)); +++ break; +++ +++ case DST__K_SET_LINUM_L: +++ data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG); +++ curr_linenum = data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST__K_SET_LINUM_L: %d\n", data)); +++ break; +++ +++ case DST__K_SET_PC: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_PC"); +++ cmd_length = 2; +++ break; +++ +++ case DST__K_SET_PC_W: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_PC_W"); +++ cmd_length = 3; +++ break; +++ +++ case DST__K_SET_PC_L: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_PC_L"); +++ cmd_length = 5; +++ break; +++ +++ case DST__K_SET_STMTNUM: +++ _bfd_error_handler +++ (_("%s not implemented"), "DST__K_SET_STMTNUM"); +++ cmd_length = 2; +++ break; +++ +++ case DST__K_TERM: +++ data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE]; +++ curr_pc += data; +++ cmd_length = 2; +++ vms_debug2 ((4, "DST__K_TERM: %d\n", data)); +++ break; +++ +++ case DST__K_TERM_W: +++ data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD); +++ curr_pc += data; +++ cmd_length = 3; +++ vms_debug2 ((4, "DST__K_TERM_W: %d\n", data)); +++ break; +++ +++ case DST__K_TERM_L: +++ data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG); +++ curr_pc += data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST__K_TERM_L: %d\n", data)); +++ break; +++ +++ case DST__K_SET_ABS_PC: +++ data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG); +++ curr_pc = data; +++ cmd_length = 5; +++ vms_debug2 ((4, "DST__K_SET_ABS_PC: 0x%x\n", data)); +++ break; +++ +++ default: +++ if (cmd <= 0) +++ { +++ curr_pc -= cmd; +++ curr_linenum += 1; +++ cmd_length = 1; +++ vms_debug2 ((4, "bump pc to 0x%lx and line to %d\n", +++ (unsigned long)curr_pc, curr_linenum)); +++ } +++ else +++ { +++ _bfd_error_handler (_("unknown line command %d"), cmd); +++ cmd_length = 2; +++ } +++ break; +++ } +++ +++ if ((curr_linenum != prev_linum && curr_pc != prev_pc) +++ || cmd <= 0 +++ || cmd == DST__K_DELTA_PC_L +++ || cmd == DST__K_DELTA_PC_W) +++ { +++ line = (struct lineinfo *) +++ bfd_zalloc (abfd, sizeof (struct lineinfo)); +++ line->address = curr_pc; +++ line->line = curr_linenum; +++ +++ curr_line->next = line; +++ curr_line = line; +++ +++ prev_linum = curr_linenum; +++ prev_pc = curr_pc; +++ vms_debug2 ((4, "-> correlate pc 0x%lx with line %d\n", +++ (unsigned long)curr_pc, curr_linenum)); +++ } +++ +++ pcl_ptr += cmd_length; +++ } +++ break; +++ +++ case 0x17: /* Undocumented type used by DEC C to declare equates. */ +++ vms_debug2 ((3, "undocumented type 0x17\n")); +++ break; +++ +++ default: +++ vms_debug2 ((3, "ignoring record\n")); +++ break; +++ +++ } +++ +++ ptr += rec_length; +++ } +++ +++ /* Finalize tables with EOL marker. */ +++ srec = (struct srecinfo *) bfd_zalloc (abfd, sizeof (struct srecinfo)); +++ srec->line = (unsigned int) -1; +++ srec->srec = (unsigned int) -1; +++ curr_srec->next = srec; +++ +++ line = (struct lineinfo *) bfd_zalloc (abfd, sizeof (struct lineinfo)); +++ line->line = (unsigned int) -1; +++ line->address = (bfd_vma) -1; +++ curr_line->next = line; +++ +++ /* Advertise that this module has been parsed. This is needed +++ because parsing can be either performed at module creation +++ or deferred until debug info is consumed. */ +++ SET_MODULE_PARSED (module); +++} +++ +++/* Build the list of modules for the specified BFD. */ +++ +++static struct module * +++build_module_list (bfd *abfd) +++{ +++ struct module *module, *list = NULL; +++ asection *dmt; +++ +++ if ((dmt = bfd_get_section_by_name (abfd, "$DMT$"))) +++ { +++ /* We have a DMT section so this must be an image. Parse the +++ section and build the list of modules. This is sufficient +++ since we can compute the start address and the end address +++ of every module from the section contents. */ +++ bfd_size_type size = bfd_get_section_size (dmt); +++ unsigned char *ptr, *end; +++ +++ ptr = (unsigned char *) bfd_alloc (abfd, size); +++ if (! ptr) +++ return NULL; +++ +++ if (! bfd_get_section_contents (abfd, dmt, ptr, 0, size)) +++ return NULL; +++ +++ vms_debug2 ((2, "DMT\n")); +++ +++ end = ptr + size; +++ +++ while (ptr < end) +++ { +++ /* Each header declares a module with its start offset and size +++ of debug info in the DST section, as well as the count of +++ program sections (i.e. address spans) it contains. */ +++ int modbeg = bfd_getl32 (ptr + DBG_S_L_DMT_MODBEG); +++ int msize = bfd_getl32 (ptr + DBG_S_L_DST_SIZE); +++ int count = bfd_getl16 (ptr + DBG_S_W_DMT_PSECT_COUNT); +++ ptr += DBG_S_C_DMT_HEADER_SIZE; +++ +++ vms_debug2 ((3, "module: modbeg = %d, size = %d, count = %d\n", +++ modbeg, msize, count)); +++ +++ /* We create a 'module' structure for each program section since +++ we only support contiguous addresses in a 'module' structure. +++ As a consequence, the actual debug info in the DST section is +++ shared and can be parsed multiple times; that doesn't seem to +++ cause problems in practice. */ +++ while (count-- > 0) +++ { +++ int start = bfd_getl32 (ptr + DBG_S_L_DMT_PSECT_START); +++ int length = bfd_getl32 (ptr + DBG_S_L_DMT_PSECT_LENGTH); +++ module = new_module (abfd); +++ module->modbeg = modbeg; +++ module->size = msize; +++ module->low = start; +++ module->high = start + length; +++ module->next = list; +++ list = module; +++ ptr += DBG_S_C_DMT_PSECT_SIZE; +++ +++ vms_debug2 ((4, "section: start = 0x%x, length = %d\n", +++ start, length)); +++ } +++ } +++ } +++ else +++ { +++ /* We don't have a DMT section so this must be an object. Parse +++ the module right now in order to compute its start address and +++ end address. */ +++ void *dst = PRIV (dst_section)->contents; +++ +++ if (dst == NULL) +++ return NULL; +++ +++ module = new_module (abfd); +++ parse_module (abfd, module, PRIV (dst_section)->contents, -1); +++ list = module; +++ } +++ +++ return list; +++} +++ +++/* Calculate and return the name of the source file and the line nearest +++ to the wanted location in the specified module. */ +++ +++static bfd_boolean +++module_find_nearest_line (bfd *abfd, struct module *module, bfd_vma addr, +++ const char **file, const char **func, +++ unsigned int *line) +++{ +++ struct funcinfo *funcinfo; +++ struct lineinfo *lineinfo; +++ struct srecinfo *srecinfo; +++ bfd_boolean ret = FALSE; +++ +++ /* Parse this module if that was not done at module creation. */ +++ if (! IS_MODULE_PARSED (module)) +++ { +++ unsigned int size = module->size; +++ unsigned int modbeg = PRIV (dst_section)->filepos + module->modbeg; +++ unsigned char *buffer = (unsigned char *) bfd_malloc (module->size); +++ +++ if (bfd_seek (abfd, modbeg, SEEK_SET) != 0 +++ || bfd_bread (buffer, size, abfd) != size) +++ { +++ bfd_set_error (bfd_error_no_debug_section); +++ return FALSE; +++ } +++ +++ parse_module (abfd, module, buffer, size); +++ free (buffer); +++ } +++ +++ /* Find out the function (if any) that contains the address. */ +++ for (funcinfo = module->func_table; funcinfo; funcinfo = funcinfo->next) +++ if (addr >= funcinfo->low && addr <= funcinfo->high) +++ { +++ *func = funcinfo->name; +++ ret = TRUE; +++ break; +++ } +++ +++ /* Find out the source file and the line nearest to the address. */ +++ for (lineinfo = module->line_table; lineinfo; lineinfo = lineinfo->next) +++ if (lineinfo->next && addr < lineinfo->next->address) +++ { +++ for (srecinfo = module->srec_table; srecinfo; srecinfo = srecinfo->next) +++ if (srecinfo->next && lineinfo->line < srecinfo->next->line) +++ { +++ if (srecinfo->sfile > 0) +++ { +++ *file = module->file_table[srecinfo->sfile].name; +++ *line = srecinfo->srec + lineinfo->line - srecinfo->line; +++ } +++ else +++ { +++ *file = module->name; +++ *line = lineinfo->line; +++ } +++ return TRUE; +++ } +++ +++ break; +++ } +++ +++ return ret; +++} +++ +++/* Provided a BFD, a section and an offset into the section, calculate and +++ return the name of the source file and the line nearest to the wanted +++ location. */ +++ +++static bfd_boolean +++_bfd_vms_find_nearest_line (bfd *abfd, +++ asymbol **symbols ATTRIBUTE_UNUSED, +++ asection *section, +++ bfd_vma offset, +++ const char **file, +++ const char **func, +++ unsigned int *line, +++ unsigned int *discriminator) +++{ +++ struct module *module; +++ +++ /* What address are we looking for? */ +++ bfd_vma addr = section->vma + offset; +++ +++ *file = NULL; +++ *func = NULL; +++ *line = 0; +++ if (discriminator) +++ *discriminator = 0; +++ +++ /* We can't do anything if there is no DST (debug symbol table). */ +++ if (PRIV (dst_section) == NULL) +++ return FALSE; +++ +++ /* Create the module list - if not already done. */ +++ if (PRIV (modules) == NULL) +++ { +++ PRIV (modules) = build_module_list (abfd); +++ if (PRIV (modules) == NULL) +++ return FALSE; +++ } +++ +++ for (module = PRIV (modules); module; module = module->next) +++ if (addr >= module->low && addr <= module->high) +++ return module_find_nearest_line (abfd, module, addr, file, func, line); +++ +++ return FALSE; +++} +++ +++/* Canonicalizations. */ +++/* Set name, value, section and flags of SYM from E. */ +++ +++static bfd_boolean +++sw_64_vms_convert_symbol (bfd *abfd, struct vms_symbol_entry *e, asymbol *sym) +++{ +++ flagword flags; +++ symvalue value; +++ asection *sec; +++ const char *name; +++ +++ name = e->name; +++ value = 0; +++ flags = BSF_NO_FLAGS; +++ sec = NULL; +++ +++ switch (e->typ) +++ { +++ case EGSD__C_SYM: +++ if (e->flags & EGSY__V_WEAK) +++ flags |= BSF_WEAK; +++ +++ if (e->flags & EGSY__V_DEF) +++ { +++ /* Symbol definition. */ +++ flags |= BSF_GLOBAL; +++ if (e->flags & EGSY__V_NORM) +++ flags |= BSF_FUNCTION; +++ value = e->value; +++ sec = e->section; +++ } +++ else +++ { +++ /* Symbol reference. */ +++ sec = bfd_und_section_ptr; +++ } +++ break; +++ +++ case EGSD__C_SYMG: +++ /* A universal symbol is by definition global... */ +++ flags |= BSF_GLOBAL; +++ +++ /* ...and dynamic in shared libraries. */ +++ if (abfd->flags & DYNAMIC) +++ flags |= BSF_DYNAMIC; +++ +++ if (e->flags & EGSY__V_WEAK) +++ flags |= BSF_WEAK; +++ +++ if (!(e->flags & EGSY__V_DEF)) +++ abort (); +++ +++ if (e->flags & EGSY__V_NORM) +++ flags |= BSF_FUNCTION; +++ +++ value = e->value; +++ /* sec = e->section; */ +++ sec = bfd_abs_section_ptr; +++ break; +++ +++ default: +++ return FALSE; +++ } +++ +++ sym->name = name; +++ sym->section = sec; +++ sym->flags = flags; +++ sym->value = value; +++ return TRUE; +++} +++ +++ +++/* Return the number of bytes required to store a vector of pointers +++ to asymbols for all the symbols in the BFD abfd, including a +++ terminal NULL pointer. If there are no symbols in the BFD, +++ then return 0. If an error occurs, return -1. */ +++ +++static long +++sw_64_vms_get_symtab_upper_bound (bfd *abfd) +++{ +++ vms_debug2 ((1, "sw_64_vms_get_symtab_upper_bound (%p), %d symbols\n", +++ abfd, PRIV (gsd_sym_count))); +++ +++ return (PRIV (gsd_sym_count) + 1) * sizeof (asymbol *); +++} +++ +++/* Read the symbols from the BFD abfd, and fills in the vector +++ location with pointers to the symbols and a trailing NULL. +++ +++ Return number of symbols read. */ +++ +++static long +++sw_64_vms_canonicalize_symtab (bfd *abfd, asymbol **symbols) +++{ +++ unsigned int i; +++ +++ vms_debug2 ((1, "sw_64_vms_canonicalize_symtab (%p, )\n", abfd)); +++ +++ if (PRIV (csymbols) == NULL) +++ { +++ PRIV (csymbols) = (asymbol **) bfd_alloc +++ (abfd, PRIV (gsd_sym_count) * sizeof (asymbol *)); +++ +++ /* Traverse table and fill symbols vector. */ +++ for (i = 0; i < PRIV (gsd_sym_count); i++) +++ { +++ struct vms_symbol_entry *e = PRIV (syms)[i]; +++ asymbol *sym; +++ +++ sym = bfd_make_empty_symbol (abfd); +++ if (sym == NULL || !sw_64_vms_convert_symbol (abfd, e, sym)) +++ { +++ bfd_release (abfd, PRIV (csymbols)); +++ PRIV (csymbols) = NULL; +++ return -1; +++ } +++ +++ PRIV (csymbols)[i] = sym; +++ } +++ } +++ +++ if (symbols != NULL) +++ { +++ for (i = 0; i < PRIV (gsd_sym_count); i++) +++ symbols[i] = PRIV (csymbols)[i]; +++ symbols[i] = NULL; +++ } +++ +++ return PRIV (gsd_sym_count); +++} +++ +++/* Read and convert relocations from ETIR. We do it once for all sections. */ +++ +++static bfd_boolean +++sw_64_vms_slurp_relocs (bfd *abfd) +++{ +++ int cur_psect = -1; +++ +++ vms_debug2 ((3, "sw_64_vms_slurp_relocs\n")); +++ +++ /* We slurp relocs only once, for all sections. */ +++ if (PRIV (reloc_done)) +++ return TRUE; +++ PRIV (reloc_done) = TRUE; +++ +++ if (sw_64_vms_canonicalize_symtab (abfd, NULL) < 0) +++ return FALSE; +++ +++ if (bfd_seek (abfd, 0, SEEK_SET) != 0) +++ return FALSE; +++ +++ while (1) +++ { +++ unsigned char *begin; +++ unsigned char *end; +++ unsigned char *ptr; +++ bfd_reloc_code_real_type reloc_code; +++ int type; +++ bfd_vma vaddr = 0; +++ +++ int length; +++ +++ bfd_vma cur_address; +++ int cur_psidx = -1; +++ unsigned char *cur_sym = NULL; +++ int prev_cmd = -1; +++ bfd_vma cur_addend = 0; +++ +++ /* Skip non-ETIR records. */ +++ type = _bfd_vms_get_object_record (abfd); +++ if (type == EOBJ__C_EEOM) +++ break; +++ if (type != EOBJ__C_ETIR) +++ continue; +++ +++ begin = PRIV (recrd.rec) + 4; +++ end = PRIV (recrd.rec) + PRIV (recrd.rec_size); +++ +++ for (ptr = begin; ptr < end; ptr += length) +++ { +++ int cmd; +++ +++ cmd = bfd_getl16 (ptr); +++ length = bfd_getl16 (ptr + 2); +++ +++ cur_address = vaddr; +++ +++ vms_debug2 ((4, "sw_64_vms_slurp_relocs: etir %s\n", +++ _bfd_vms_etir_name (cmd))); +++ +++ switch (cmd) +++ { +++ case ETIR__C_STA_GBL: /* SW_64_R_REFLONG und_section, step 1 */ +++ /* SW_64_R_REFQUAD und_section, step 1 */ +++ cur_sym = ptr + 4; +++ prev_cmd = cmd; +++ continue; +++ +++ case ETIR__C_STA_PQ: /* SW_64_R_REF{LONG|QUAD}, others part 1 */ +++ cur_psidx = bfd_getl32 (ptr + 4); +++ cur_addend = bfd_getl64 (ptr + 8); +++ prev_cmd = cmd; +++ continue; +++ +++ case ETIR__C_CTL_SETRB: +++ if (prev_cmd != ETIR__C_STA_PQ) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("unknown reloc %s + %s"), _bfd_vms_etir_name (prev_cmd), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ } +++ cur_psect = cur_psidx; +++ vaddr = cur_addend; +++ cur_psidx = -1; +++ cur_addend = 0; +++ continue; +++ +++ case ETIR__C_STA_LW: /* SW_64_R_REFLONG abs_section, step 1 */ +++ /* SW_64_R_REFLONG und_section, step 2 */ +++ if (prev_cmd != -1) +++ { +++ if (prev_cmd != ETIR__C_STA_GBL) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("unknown reloc %s + %s"), _bfd_vms_etir_name (cmd), +++ _bfd_vms_etir_name (ETIR__C_STA_LW)); +++ return FALSE; +++ } +++ } +++ cur_addend = bfd_getl32 (ptr + 4); +++ prev_cmd = cmd; +++ continue; +++ +++ case ETIR__C_STA_QW: /* SW_64_R_REFQUAD abs_section, step 1 */ +++ /* SW_64_R_REFQUAD und_section, step 2 */ +++ if (prev_cmd != -1 && prev_cmd != ETIR__C_STA_GBL) +++ { +++ _bfd_error_handler +++ /* xgettext:c-format */ +++ (_("unknown reloc %s + %s"), _bfd_vms_etir_name (cmd), +++ _bfd_vms_etir_name (ETIR__C_STA_QW)); +++ return FALSE; +++ } +++ cur_addend = bfd_getl64 (ptr + 4); +++ prev_cmd = cmd; +++ continue; +++ +++ case ETIR__C_STO_LW: /* SW_64_R_REFLONG und_section, step 4 */ +++ /* SW_64_R_REFLONG abs_section, step 2 */ +++ /* SW_64_R_REFLONG others, step 2 */ +++ if (prev_cmd != ETIR__C_OPR_ADD +++ && prev_cmd != ETIR__C_STA_LW +++ && prev_cmd != ETIR__C_STA_PQ) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("unknown reloc %s + %s"), +++ _bfd_vms_etir_name (prev_cmd), +++ _bfd_vms_etir_name (ETIR__C_STO_LW)); +++ return FALSE; +++ } +++ reloc_code = BFD_RELOC_32; +++ break; +++ +++ case ETIR__C_STO_QW: /* SW_64_R_REFQUAD und_section, step 4 */ +++ /* SW_64_R_REFQUAD abs_section, step 2 */ +++ if (prev_cmd != ETIR__C_OPR_ADD && prev_cmd != ETIR__C_STA_QW) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("unknown reloc %s + %s"), +++ _bfd_vms_etir_name (prev_cmd), +++ _bfd_vms_etir_name (ETIR__C_STO_QW)); +++ return FALSE; +++ } +++ reloc_code = BFD_RELOC_64; +++ break; +++ +++ case ETIR__C_STO_OFF: /* SW_64_R_REFQUAD others, step 2 */ +++ if (prev_cmd != ETIR__C_STA_PQ) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("unknown reloc %s + %s"), +++ _bfd_vms_etir_name (prev_cmd), +++ _bfd_vms_etir_name (ETIR__C_STO_OFF)); +++ return FALSE; +++ } +++ reloc_code = BFD_RELOC_64; +++ break; +++ +++ case ETIR__C_OPR_ADD: /* SW_64_R_REFLONG und_section, step 3 */ +++ /* SW_64_R_REFQUAD und_section, step 3 */ +++ if (prev_cmd != ETIR__C_STA_LW && prev_cmd != ETIR__C_STA_QW) +++ { +++ /* xgettext:c-format */ +++ _bfd_error_handler (_("unknown reloc %s + %s"), +++ _bfd_vms_etir_name (prev_cmd), +++ _bfd_vms_etir_name (ETIR__C_OPR_ADD)); +++ return FALSE; +++ } +++ prev_cmd = ETIR__C_OPR_ADD; +++ continue; +++ +++ case ETIR__C_STO_CA: /* SW_64_R_CODEADDR */ +++ reloc_code = BFD_RELOC_SW_64_CODEADDR; +++ cur_sym = ptr + 4; +++ break; +++ +++ case ETIR__C_STO_GBL: /* SW_64_R_REFQUAD und_section */ +++ reloc_code = BFD_RELOC_64; +++ cur_sym = ptr + 4; +++ break; +++ +++ case ETIR__C_STO_GBL_LW: /* SW_64_R_REFLONG und_section */ +++ reloc_code = BFD_RELOC_32; +++ cur_sym = ptr + 4; +++ break; +++ +++ case ETIR__C_STC_LP_PSB: /* SW_64_R_LINKAGE */ +++ reloc_code = BFD_RELOC_SW_64_LINKAGE; +++ cur_sym = ptr + 8; +++ break; +++ +++ case ETIR__C_STC_NOP_GBL: /* SW_64_R_NOP */ +++ reloc_code = BFD_RELOC_SW_64_NOP; +++ goto call_reloc; +++ +++ case ETIR__C_STC_BSR_GBL: /* SW_64_R_BSR */ +++ reloc_code = BFD_RELOC_SW_64_BSR; +++ goto call_reloc; +++ +++ case ETIR__C_STC_LDA_GBL: /* SW_64_R_LDA */ +++ reloc_code = BFD_RELOC_SW_64_LDA; +++ goto call_reloc; +++ +++ case ETIR__C_STC_BOH_GBL: /* SW_64_R_BOH */ +++ reloc_code = BFD_RELOC_SW_64_BOH; +++ goto call_reloc; +++ +++ call_reloc: +++ cur_sym = ptr + 4 + 32; +++ cur_address = bfd_getl64 (ptr + 4 + 8); +++ cur_addend = bfd_getl64 (ptr + 4 + 24); +++ break; +++ +++ case ETIR__C_STO_IMM: +++ vaddr += bfd_getl32 (ptr + 4); +++ continue; +++ +++ default: +++ _bfd_error_handler (_("unknown reloc %s"), +++ _bfd_vms_etir_name (cmd)); +++ return FALSE; +++ } +++ +++ { +++ asection *sec; +++ struct vms_section_data_struct *vms_sec; +++ arelent *reloc; +++ +++ /* Get section to which the relocation applies. */ +++ if (cur_psect < 0 || cur_psect > (int)PRIV (section_count)) +++ { +++ _bfd_error_handler (_("invalid section index in ETIR")); +++ return FALSE; +++ } +++ +++ if (PRIV (sections) == NULL) +++ return FALSE; +++ sec = PRIV (sections)[cur_psect]; +++ if (sec == bfd_abs_section_ptr) +++ { +++ _bfd_error_handler (_("relocation for non-REL psect")); +++ return FALSE; +++ } +++ +++ vms_sec = vms_section_data (sec); +++ +++ /* Allocate a reloc entry. */ +++ if (sec->reloc_count >= vms_sec->reloc_max) +++ { +++ if (vms_sec->reloc_max == 0) +++ { +++ vms_sec->reloc_max = 64; +++ sec->relocation = bfd_zmalloc +++ (vms_sec->reloc_max * sizeof (arelent)); +++ } +++ else +++ { +++ vms_sec->reloc_max *= 2; +++ sec->relocation = bfd_realloc +++ (sec->relocation, vms_sec->reloc_max * sizeof (arelent)); +++ } +++ } +++ reloc = &sec->relocation[sec->reloc_count]; +++ sec->reloc_count++; +++ +++ reloc->howto = bfd_reloc_type_lookup (abfd, reloc_code); +++ +++ if (cur_sym != NULL) +++ { +++ unsigned int j; +++ unsigned int symlen = *cur_sym; +++ asymbol **sym; +++ +++ /* Linear search. */ +++ symlen = *cur_sym; +++ cur_sym++; +++ sym = NULL; +++ +++ for (j = 0; j < PRIV (gsd_sym_count); j++) +++ if (PRIV (syms)[j]->namelen == symlen +++ && memcmp (PRIV (syms)[j]->name, cur_sym, symlen) == 0) +++ { +++ sym = &PRIV (csymbols)[j]; +++ break; +++ } +++ if (sym == NULL) +++ { +++ _bfd_error_handler (_("unknown symbol in command %s"), +++ _bfd_vms_etir_name (cmd)); +++ reloc->sym_ptr_ptr = NULL; +++ } +++ else +++ reloc->sym_ptr_ptr = sym; +++ } +++ else if (cur_psidx >= 0) +++ { +++ if (PRIV (sections) == NULL || cur_psidx >= (int) PRIV (section_count)) +++ return FALSE; +++ reloc->sym_ptr_ptr = +++ PRIV (sections)[cur_psidx]->symbol_ptr_ptr; +++ } +++ else +++ reloc->sym_ptr_ptr = NULL; +++ +++ reloc->address = cur_address; +++ reloc->addend = cur_addend; +++ +++ vaddr += bfd_get_reloc_size (reloc->howto); +++ } +++ +++ cur_addend = 0; +++ prev_cmd = -1; +++ cur_sym = NULL; +++ cur_psidx = -1; +++ } +++ } +++ vms_debug2 ((3, "sw_64_vms_slurp_relocs: result = TRUE\n")); +++ +++ return TRUE; +++} +++ +++/* Return the number of bytes required to store the relocation +++ information associated with the given section. */ +++ +++static long +++sw_64_vms_get_reloc_upper_bound (bfd *abfd ATTRIBUTE_UNUSED, asection *section) +++{ +++ sw_64_vms_slurp_relocs (abfd); +++ +++ return (section->reloc_count + 1) * sizeof (arelent *); +++} +++ +++/* Convert relocations from VMS (external) form into BFD internal +++ form. Return the number of relocations. */ +++ +++static long +++sw_64_vms_canonicalize_reloc (bfd *abfd, asection *section, arelent **relptr, +++ asymbol **symbols ATTRIBUTE_UNUSED) +++{ +++ arelent *tblptr; +++ int count; +++ +++ if (!sw_64_vms_slurp_relocs (abfd)) +++ return -1; +++ +++ count = section->reloc_count; +++ tblptr = section->relocation; +++ +++ while (count--) +++ *relptr++ = tblptr++; +++ +++ *relptr = (arelent *) NULL; +++ return section->reloc_count; +++} +++ +++/* Install a new set of internal relocs. */ +++ +++#define sw_64_vms_set_reloc _bfd_generic_set_reloc +++ +++ +++/* This is just copied from ecoff-sw_64, needs to be fixed probably. */ +++ +++/* How to process the various reloc types. */ +++ +++static bfd_reloc_status_type +++reloc_nil (bfd * abfd ATTRIBUTE_UNUSED, +++ arelent *reloc ATTRIBUTE_UNUSED, +++ asymbol *sym ATTRIBUTE_UNUSED, +++ void * data ATTRIBUTE_UNUSED, +++ asection *sec ATTRIBUTE_UNUSED, +++ bfd *output_bfd ATTRIBUTE_UNUSED, +++ char **error_message ATTRIBUTE_UNUSED) +++{ +++#if VMS_DEBUG +++ vms_debug (1, "reloc_nil (abfd %p, output_bfd %p)\n", abfd, output_bfd); +++ vms_debug (2, "In section %s, symbol %s\n", +++ sec->name, sym->name); +++ vms_debug (2, "reloc sym %s, addr %08lx, addend %08lx, reloc is a %s\n", +++ reloc->sym_ptr_ptr[0]->name, +++ (unsigned long)reloc->address, +++ (unsigned long)reloc->addend, reloc->howto->name); +++ vms_debug (2, "data at %p\n", data); +++ /* _bfd_hexdump (2, data, bfd_get_reloc_size (reloc->howto), 0); */ +++#endif +++ +++ return bfd_reloc_ok; +++} +++ +++/* In case we're on a 32-bit machine, construct a 64-bit "-1" value +++ from smaller values. Start with zero, widen, *then* decrement. */ +++#define MINUS_ONE (((bfd_vma)0) - 1) +++ +++static reloc_howto_type sw_64_howto_table[] = +++{ +++ HOWTO (SW_64_R_IGNORE, /* Type. */ +++ 0, /* Rightshift. */ +++ 0, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 8, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "IGNORE", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0, /* Source mask */ +++ 0, /* Dest mask. */ +++ TRUE), /* PC rel offset. */ +++ +++ /* A 64 bit reference to a symbol. */ +++ HOWTO (SW_64_R_REFQUAD, /* Type. */ +++ 0, /* Rightshift. */ +++ 4, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 64, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_bitfield, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "REFQUAD", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ MINUS_ONE, /* Source mask. */ +++ MINUS_ONE, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* A 21 bit branch. The native assembler generates these for +++ branches within the text segment, and also fills in the PC +++ relative offset in the instruction. */ +++ HOWTO (SW_64_R_BRADDR, /* Type. */ +++ 2, /* Rightshift. */ +++ 2, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 21, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_signed, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "BRADDR", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0x1fffff, /* Source mask. */ +++ 0x1fffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* A hint for a jump to a register. */ +++ HOWTO (SW_64_R_HINT, /* Type. */ +++ 2, /* Rightshift. */ +++ 1, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 14, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "HINT", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0x3fff, /* Source mask. */ +++ 0x3fff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* 16 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL16, /* Type. */ +++ 0, /* Rightshift. */ +++ 1, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 16, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_signed, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "SREL16", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0xffff, /* Source mask. */ +++ 0xffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* 32 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL32, /* Type. */ +++ 0, /* Rightshift. */ +++ 2, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 32, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_signed, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "SREL32", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* A 64 bit PC relative offset. */ +++ HOWTO (SW_64_R_SREL64, /* Type. */ +++ 0, /* Rightshift. */ +++ 4, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 64, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_signed, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "SREL64", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ MINUS_ONE, /* Source mask. */ +++ MINUS_ONE, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* Push a value on the reloc evaluation stack. */ +++ HOWTO (SW_64_R_OP_PUSH, /* Type. */ +++ 0, /* Rightshift. */ +++ 0, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "OP_PUSH", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0, /* Source mask. */ +++ 0, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* Store the value from the stack at the given address. Store it in +++ a bitfield of size r_size starting at bit position r_offset. */ +++ HOWTO (SW_64_R_OP_STORE, /* Type. */ +++ 0, /* Rightshift. */ +++ 4, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 64, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "OP_STORE", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0, /* Source mask. */ +++ MINUS_ONE, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* Subtract the reloc address from the value on the top of the +++ relocation stack. */ +++ HOWTO (SW_64_R_OP_PSUB, /* Type. */ +++ 0, /* Rightshift. */ +++ 0, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "OP_PSUB", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0, /* Source mask. */ +++ 0, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* Shift the value on the top of the relocation stack right by the +++ given value. */ +++ HOWTO (SW_64_R_OP_PRSHIFT, /* Type. */ +++ 0, /* Rightshift. */ +++ 0, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "OP_PRSHIFT", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0, /* Source mask. */ +++ 0, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* Hack. Linkage is done by linker. */ +++ HOWTO (SW_64_R_LINKAGE, /* Type. */ +++ 0, /* Rightshift. */ +++ 8, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 256, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "LINKAGE", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0, /* Source mask. */ +++ 0, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* A 32 bit reference to a symbol. */ +++ HOWTO (SW_64_R_REFLONG, /* Type. */ +++ 0, /* Rightshift. */ +++ 2, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 32, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_bitfield, /* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "REFLONG", /* Name. */ +++ TRUE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ /* A 64 bit reference to a procedure, written as 32 bit value. */ +++ HOWTO (SW_64_R_CODEADDR, /* Type. */ +++ 0, /* Rightshift. */ +++ 4, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 64, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_signed,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "CODEADDR", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ HOWTO (SW_64_R_NOP, /* Type. */ +++ 0, /* Rightshift. */ +++ 3, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ /* The following value must match that of SW_64_R_BSR/SW_64_R_BOH +++ because the calculations for the 3 relocations are the same. +++ See B.4.5.2 of the OpenVMS Linker Utility Manual. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "NOP", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ HOWTO (SW_64_R_BSR, /* Type. */ +++ 0, /* Rightshift. */ +++ 3, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "BSR", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ HOWTO (SW_64_R_LDA, /* Type. */ +++ 0, /* Rightshift. */ +++ 3, /* Size (0 = byte, 1 = short, 2 = long). */ +++ 0, /* Bitsize. */ +++ FALSE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "LDA", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++ +++ HOWTO (SW_64_R_BOH, /* Type. */ +++ 0, /* Rightshift. */ +++ 3, /* Size (0 = byte, 1 = short, 2 = long, 3 = nil). */ +++ 0, /* Bitsize. */ +++ TRUE, /* PC relative. */ +++ 0, /* Bitpos. */ +++ complain_overflow_dont,/* Complain_on_overflow. */ +++ reloc_nil, /* Special_function. */ +++ "BOH", /* Name. */ +++ FALSE, /* Partial_inplace. */ +++ 0xffffffff, /* Source mask. */ +++ 0xffffffff, /* Dest mask. */ +++ FALSE), /* PC rel offset. */ +++}; +++ +++/* Return a pointer to a howto structure which, when invoked, will perform +++ the relocation code on data from the architecture noted. */ +++ +++static const struct reloc_howto_struct * +++sw_64_vms_bfd_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED, +++ bfd_reloc_code_real_type code) +++{ +++ int sw_64_type; +++ +++ vms_debug2 ((1, "vms_bfd_reloc_type_lookup (%p, %d)\t", abfd, code)); +++ +++ switch (code) +++ { +++ case BFD_RELOC_16: sw_64_type = SW_64_R_SREL16; break; +++ case BFD_RELOC_32: sw_64_type = SW_64_R_REFLONG; break; +++ case BFD_RELOC_64: sw_64_type = SW_64_R_REFQUAD; break; +++ case BFD_RELOC_CTOR: sw_64_type = SW_64_R_REFQUAD; break; +++#ifndef XWB20200308 +++ case BFD_RELOC_20_PCREL_S2: alpha_type = SW_64_R_BR18ADDR; break; +++#endif +++ case BFD_RELOC_23_PCREL_S2: sw_64_type = SW_64_R_BRADDR; break; +++ case BFD_RELOC_SW_64_HINT: sw_64_type = SW_64_R_HINT; break; +++ case BFD_RELOC_16_PCREL: sw_64_type = SW_64_R_SREL16; break; +++ case BFD_RELOC_32_PCREL: sw_64_type = SW_64_R_SREL32; break; +++ case BFD_RELOC_64_PCREL: sw_64_type = SW_64_R_SREL64; break; +++ case BFD_RELOC_SW_64_LINKAGE: sw_64_type = SW_64_R_LINKAGE; break; +++ case BFD_RELOC_SW_64_CODEADDR: sw_64_type = SW_64_R_CODEADDR; break; +++ case BFD_RELOC_SW_64_NOP: sw_64_type = SW_64_R_NOP; break; +++ case BFD_RELOC_SW_64_BSR: sw_64_type = SW_64_R_BSR; break; +++ case BFD_RELOC_SW_64_LDA: sw_64_type = SW_64_R_LDA; break; +++ case BFD_RELOC_SW_64_BOH: sw_64_type = SW_64_R_BOH; break; +++ default: +++ _bfd_error_handler (_("reloc (%d) is *UNKNOWN*"), code); +++ return NULL; +++ } +++ vms_debug2 ((2, "reloc is %s\n", sw_64_howto_table[sw_64_type].name)); +++ return & sw_64_howto_table[sw_64_type]; +++} +++ +++static reloc_howto_type * +++sw_64_vms_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED, +++ const char *r_name) +++{ +++ unsigned int i; +++ +++ for (i = 0; +++ i < sizeof (sw_64_howto_table) / sizeof (sw_64_howto_table[0]); +++ i++) +++ if (sw_64_howto_table[i].name != NULL +++ && strcasecmp (sw_64_howto_table[i].name, r_name) == 0) +++ return &sw_64_howto_table[i]; +++ +++ return NULL; +++} +++ +++static long +++sw_64_vms_get_synthetic_symtab (bfd *abfd, +++ long symcount ATTRIBUTE_UNUSED, +++ asymbol **usyms ATTRIBUTE_UNUSED, +++ long dynsymcount ATTRIBUTE_UNUSED, +++ asymbol **dynsyms ATTRIBUTE_UNUSED, +++ asymbol **ret) +++{ +++ asymbol *syms; +++ unsigned int i; +++ unsigned int n = 0; +++ +++ syms = (asymbol *) bfd_malloc (PRIV (norm_sym_count) * sizeof (asymbol)); +++ *ret = syms; +++ if (syms == NULL) +++ return -1; +++ +++ for (i = 0; i < PRIV (gsd_sym_count); i++) +++ { +++ struct vms_symbol_entry *e = PRIV (syms)[i]; +++ asymbol *sym; +++ flagword flags; +++ symvalue value; +++ asection *sec; +++ const char *name; +++ char *sname; +++ int l; +++ +++ name = e->name; +++ value = 0; +++ flags = BSF_LOCAL | BSF_SYNTHETIC; +++ sec = NULL; +++ +++ switch (e->typ) +++ { +++ case EGSD__C_SYM: +++ case EGSD__C_SYMG: +++ if ((e->flags & EGSY__V_DEF) && (e->flags & EGSY__V_NORM)) +++ { +++ value = e->code_value; +++ sec = e->code_section; +++ } +++ else +++ continue; +++ break; +++ +++ default: +++ continue; +++ } +++ +++ l = strlen (name); +++ sname = bfd_alloc (abfd, l + 5); +++ if (sname == NULL) +++ return FALSE; +++ memcpy (sname, name, l); +++ memcpy (sname + l, "..en", 5); +++ +++ sym = &syms[n++]; +++ sym->name = sname; +++ sym->section = sec; +++ sym->flags = flags; +++ sym->value = value; +++ sym->udata.p = NULL; +++ } +++ +++ return n; +++} +++ +++/* Private dump. */ +++ +++static const char * +++vms_time_to_str (unsigned char *buf) +++{ +++ time_t t = vms_rawtime_to_time_t (buf); +++ char *res = ctime (&t); +++ +++ if (!res) +++ res = "*invalid time*"; +++ else +++ res[24] = 0; +++ return res; +++} +++ +++static void +++evax_bfd_print_emh (FILE *file, unsigned char *rec, unsigned int rec_len) +++{ +++ struct vms_emh_common *emh = (struct vms_emh_common *)rec; +++ unsigned int subtype; +++ int extra; +++ +++ subtype = (unsigned) bfd_getl16 (emh->subtyp); +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" EMH %u (len=%u): "), subtype, rec_len); +++ +++ /* PR 21618: Check for invalid lengths. */ +++ if (rec_len < sizeof (* emh)) +++ { +++ fprintf (file, _(" Error: The length is less than the length of an EMH record\n")); +++ return; +++ } +++ extra = rec_len - sizeof (struct vms_emh_common); +++ +++ switch (subtype) +++ { +++ case EMH__C_MHD: +++ { +++ struct vms_emh_mhd *mhd = (struct vms_emh_mhd *) rec; +++ const char * name; +++ const char * nextname; +++ const char * maxname; +++ +++ /* PR 21840: Check for invalid lengths. */ +++ if (rec_len < sizeof (* mhd)) +++ { +++ fprintf (file, _(" Error: The record length is less than the size of an EMH_MHD record\n")); +++ return; +++ } +++ fprintf (file, _("Module header\n")); +++ fprintf (file, _(" structure level: %u\n"), mhd->strlvl); +++ fprintf (file, _(" max record size: %u\n"), +++ (unsigned) bfd_getl32 (mhd->recsiz)); +++ name = (char *)(mhd + 1); +++ maxname = (char *) rec + rec_len; +++ if (name > maxname - 2) +++ { +++ fprintf (file, _(" Error: The module name is missing\n")); +++ return; +++ } +++ nextname = name + name[0] + 1; +++ if (nextname >= maxname) +++ { +++ fprintf (file, _(" Error: The module name is too long\n")); +++ return; +++ } +++ fprintf (file, _(" module name : %.*s\n"), name[0], name + 1); +++ name = nextname; +++ if (name > maxname - 2) +++ { +++ fprintf (file, _(" Error: The module version is missing\n")); +++ return; +++ } +++ nextname = name + name[0] + 1; +++ if (nextname >= maxname) +++ { +++ fprintf (file, _(" Error: The module version is too long\n")); +++ return; +++ } +++ fprintf (file, _(" module version : %.*s\n"), name[0], name + 1); +++ name = nextname; +++ if ((maxname - name) < 17 && maxname[-1] != 0) +++ fprintf (file, _(" Error: The compile date is truncated\n")); +++ else +++ fprintf (file, _(" compile date : %.17s\n"), name); +++ } +++ break; +++ +++ case EMH__C_LNM: +++ fprintf (file, _("Language Processor Name\n")); +++ fprintf (file, _(" language name: %.*s\n"), extra, (char *)(emh + 1)); +++ break; +++ +++ case EMH__C_SRC: +++ fprintf (file, _("Source Files Header\n")); +++ fprintf (file, _(" file: %.*s\n"), extra, (char *)(emh + 1)); +++ break; +++ +++ case EMH__C_TTL: +++ fprintf (file, _("Title Text Header\n")); +++ fprintf (file, _(" title: %.*s\n"), extra, (char *)(emh + 1)); +++ break; +++ +++ case EMH__C_CPR: +++ fprintf (file, _("Copyright Header\n")); +++ fprintf (file, _(" copyright: %.*s\n"), extra, (char *)(emh + 1)); +++ break; +++ +++ default: +++ fprintf (file, _("unhandled emh subtype %u\n"), subtype); +++ break; +++ } +++} +++ +++static void +++evax_bfd_print_eeom (FILE *file, unsigned char *rec, unsigned int rec_len) +++{ +++ struct vms_eeom *eeom = (struct vms_eeom *)rec; +++ +++ fprintf (file, _(" EEOM (len=%u):\n"), rec_len); +++ +++ /* PR 21618: Check for invalid lengths. */ +++ if (rec_len < sizeof (* eeom)) +++ { +++ fprintf (file, _(" Error: The length is less than the length of an EEOM record\n")); +++ return; +++ } +++ +++ fprintf (file, _(" number of cond linkage pairs: %u\n"), +++ (unsigned)bfd_getl32 (eeom->total_lps)); +++ fprintf (file, _(" completion code: %u\n"), +++ (unsigned)bfd_getl16 (eeom->comcod)); +++ if (rec_len > 10) +++ { +++ fprintf (file, _(" transfer addr flags: 0x%02x\n"), eeom->tfrflg); +++ fprintf (file, _(" transfer addr psect: %u\n"), +++ (unsigned)bfd_getl32 (eeom->psindx)); +++ fprintf (file, _(" transfer address : 0x%08x\n"), +++ (unsigned)bfd_getl32 (eeom->tfradr)); +++ } +++} +++ +++static void +++exav_bfd_print_egsy_flags (unsigned int flags, FILE *file) +++{ +++ if (flags & EGSY__V_WEAK) +++ fputs (_(" WEAK"), file); +++ if (flags & EGSY__V_DEF) +++ fputs (_(" DEF"), file); +++ if (flags & EGSY__V_UNI) +++ fputs (_(" UNI"), file); +++ if (flags & EGSY__V_REL) +++ fputs (_(" REL"), file); +++ if (flags & EGSY__V_COMM) +++ fputs (_(" COMM"), file); +++ if (flags & EGSY__V_VECEP) +++ fputs (_(" VECEP"), file); +++ if (flags & EGSY__V_NORM) +++ fputs (_(" NORM"), file); +++ if (flags & EGSY__V_QUAD_VAL) +++ fputs (_(" QVAL"), file); +++} +++ +++static void +++evax_bfd_print_egsd_flags (FILE *file, unsigned int flags) +++{ +++ if (flags & EGPS__V_PIC) +++ fputs (_(" PIC"), file); +++ if (flags & EGPS__V_LIB) +++ fputs (_(" LIB"), file); +++ if (flags & EGPS__V_OVR) +++ fputs (_(" OVR"), file); +++ if (flags & EGPS__V_REL) +++ fputs (_(" REL"), file); +++ if (flags & EGPS__V_GBL) +++ fputs (_(" GBL"), file); +++ if (flags & EGPS__V_SHR) +++ fputs (_(" SHR"), file); +++ if (flags & EGPS__V_EXE) +++ fputs (_(" EXE"), file); +++ if (flags & EGPS__V_RD) +++ fputs (_(" RD"), file); +++ if (flags & EGPS__V_WRT) +++ fputs (_(" WRT"), file); +++ if (flags & EGPS__V_VEC) +++ fputs (_(" VEC"), file); +++ if (flags & EGPS__V_NOMOD) +++ fputs (_(" NOMOD"), file); +++ if (flags & EGPS__V_COM) +++ fputs (_(" COM"), file); +++ if (flags & EGPS__V_ALLOC_64BIT) +++ fputs (_(" 64B"), file); +++} +++ +++static void +++evax_bfd_print_egsd (FILE *file, unsigned char *rec, unsigned int rec_len) +++{ +++ unsigned int off = sizeof (struct vms_egsd); +++ unsigned int n; +++ +++ fprintf (file, _(" EGSD (len=%u):\n"), rec_len); +++ +++ n = 0; +++ for (off = sizeof (struct vms_egsd); off < rec_len; ) +++ { +++ struct vms_egsd_entry *e = (struct vms_egsd_entry *)(rec + off); +++ unsigned int type; +++ unsigned int len; +++ +++ type = (unsigned)bfd_getl16 (e->gsdtyp); +++ len = (unsigned)bfd_getl16 (e->gsdsiz); +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" EGSD entry %2u (type: %u, len: %u): "), +++ n, type, len); +++ n++; +++ +++ if (off + len > rec_len || off + len < off) +++ { +++ fprintf (file, _(" Error: length larger than remaining space in record\n")); +++ return; +++ } +++ +++ switch (type) +++ { +++ case EGSD__C_PSC: +++ { +++ struct vms_egps *egps = (struct vms_egps *)e; +++ unsigned int flags = bfd_getl16 (egps->flags); +++ unsigned int l; +++ +++ fprintf (file, _("PSC - Program section definition\n")); +++ fprintf (file, _(" alignment : 2**%u\n"), egps->align); +++ fprintf (file, _(" flags : 0x%04x"), flags); +++ evax_bfd_print_egsd_flags (file, flags); +++ fputc ('\n', file); +++ l = bfd_getl32 (egps->alloc); +++ fprintf (file, _(" alloc (len): %u (0x%08x)\n"), l, l); +++ fprintf (file, _(" name : %.*s\n"), +++ egps->namlng, egps->name); +++ } +++ break; +++ case EGSD__C_SPSC: +++ { +++ struct vms_esgps *esgps = (struct vms_esgps *)e; +++ unsigned int flags = bfd_getl16 (esgps->flags); +++ unsigned int l; +++ +++ fprintf (file, _("SPSC - Shared Image Program section def\n")); +++ fprintf (file, _(" alignment : 2**%u\n"), esgps->align); +++ fprintf (file, _(" flags : 0x%04x"), flags); +++ evax_bfd_print_egsd_flags (file, flags); +++ fputc ('\n', file); +++ l = bfd_getl32 (esgps->alloc); +++ fprintf (file, _(" alloc (len) : %u (0x%08x)\n"), l, l); +++ fprintf (file, _(" image offset : 0x%08x\n"), +++ (unsigned int)bfd_getl32 (esgps->base)); +++ fprintf (file, _(" symvec offset : 0x%08x\n"), +++ (unsigned int)bfd_getl32 (esgps->value)); +++ fprintf (file, _(" name : %.*s\n"), +++ esgps->namlng, esgps->name); +++ } +++ break; +++ case EGSD__C_SYM: +++ { +++ struct vms_egsy *egsy = (struct vms_egsy *)e; +++ unsigned int flags = bfd_getl16 (egsy->flags); +++ +++ if (flags & EGSY__V_DEF) +++ { +++ struct vms_esdf *esdf = (struct vms_esdf *)e; +++ +++ fprintf (file, _("SYM - Global symbol definition\n")); +++ fprintf (file, _(" flags: 0x%04x"), flags); +++ exav_bfd_print_egsy_flags (flags, file); +++ fputc ('\n', file); +++ fprintf (file, _(" psect offset: 0x%08x\n"), +++ (unsigned)bfd_getl32 (esdf->value)); +++ if (flags & EGSY__V_NORM) +++ { +++ fprintf (file, _(" code address: 0x%08x\n"), +++ (unsigned)bfd_getl32 (esdf->code_address)); +++ fprintf (file, _(" psect index for entry point : %u\n"), +++ (unsigned)bfd_getl32 (esdf->ca_psindx)); +++ } +++ fprintf (file, _(" psect index : %u\n"), +++ (unsigned)bfd_getl32 (esdf->psindx)); +++ fprintf (file, _(" name : %.*s\n"), +++ esdf->namlng, esdf->name); +++ } +++ else +++ { +++ struct vms_esrf *esrf = (struct vms_esrf *)e; +++ +++ fprintf (file, _("SYM - Global symbol reference\n")); +++ fprintf (file, _(" name : %.*s\n"), +++ esrf->namlng, esrf->name); +++ } +++ } +++ break; +++ case EGSD__C_IDC: +++ { +++ struct vms_eidc *eidc = (struct vms_eidc *)e; +++ unsigned int flags = bfd_getl32 (eidc->flags); +++ unsigned char *p; +++ +++ fprintf (file, _("IDC - Ident Consistency check\n")); +++ fprintf (file, _(" flags : 0x%08x"), flags); +++ if (flags & EIDC__V_BINIDENT) +++ fputs (" BINDENT", file); +++ fputc ('\n', file); +++ fprintf (file, _(" id match : %x\n"), +++ (flags >> EIDC__V_IDMATCH_SH) & EIDC__V_IDMATCH_MASK); +++ fprintf (file, _(" error severity: %x\n"), +++ (flags >> EIDC__V_ERRSEV_SH) & EIDC__V_ERRSEV_MASK); +++ p = eidc->name; +++ fprintf (file, _(" entity name : %.*s\n"), p[0], p + 1); +++ p += 1 + p[0]; +++ fprintf (file, _(" object name : %.*s\n"), p[0], p + 1); +++ p += 1 + p[0]; +++ if (flags & EIDC__V_BINIDENT) +++ fprintf (file, _(" binary ident : 0x%08x\n"), +++ (unsigned)bfd_getl32 (p + 1)); +++ else +++ fprintf (file, _(" ascii ident : %.*s\n"), p[0], p + 1); +++ } +++ break; +++ case EGSD__C_SYMG: +++ { +++ struct vms_egst *egst = (struct vms_egst *)e; +++ unsigned int flags = bfd_getl16 (egst->header.flags); +++ +++ fprintf (file, _("SYMG - Universal symbol definition\n")); +++ fprintf (file, _(" flags: 0x%04x"), flags); +++ exav_bfd_print_egsy_flags (flags, file); +++ fputc ('\n', file); +++ fprintf (file, _(" symbol vector offset: 0x%08x\n"), +++ (unsigned)bfd_getl32 (egst->value)); +++ fprintf (file, _(" entry point: 0x%08x\n"), +++ (unsigned)bfd_getl32 (egst->lp_1)); +++ fprintf (file, _(" proc descr : 0x%08x\n"), +++ (unsigned)bfd_getl32 (egst->lp_2)); +++ fprintf (file, _(" psect index: %u\n"), +++ (unsigned)bfd_getl32 (egst->psindx)); +++ fprintf (file, _(" name : %.*s\n"), +++ egst->namlng, egst->name); +++ } +++ break; +++ case EGSD__C_SYMV: +++ { +++ struct vms_esdfv *esdfv = (struct vms_esdfv *)e; +++ unsigned int flags = bfd_getl16 (esdfv->flags); +++ +++ fprintf (file, _("SYMV - Vectored symbol definition\n")); +++ fprintf (file, _(" flags: 0x%04x"), flags); +++ exav_bfd_print_egsy_flags (flags, file); +++ fputc ('\n', file); +++ fprintf (file, _(" vector : 0x%08x\n"), +++ (unsigned)bfd_getl32 (esdfv->vector)); +++ fprintf (file, _(" psect offset: %u\n"), +++ (unsigned)bfd_getl32 (esdfv->value)); +++ fprintf (file, _(" psect index : %u\n"), +++ (unsigned)bfd_getl32 (esdfv->psindx)); +++ fprintf (file, _(" name : %.*s\n"), +++ esdfv->namlng, esdfv->name); +++ } +++ break; +++ case EGSD__C_SYMM: +++ { +++ struct vms_esdfm *esdfm = (struct vms_esdfm *)e; +++ unsigned int flags = bfd_getl16 (esdfm->flags); +++ +++ fprintf (file, _("SYMM - Global symbol definition with version\n")); +++ fprintf (file, _(" flags: 0x%04x"), flags); +++ exav_bfd_print_egsy_flags (flags, file); +++ fputc ('\n', file); +++ fprintf (file, _(" version mask: 0x%08x\n"), +++ (unsigned)bfd_getl32 (esdfm->version_mask)); +++ fprintf (file, _(" psect offset: %u\n"), +++ (unsigned)bfd_getl32 (esdfm->value)); +++ fprintf (file, _(" psect index : %u\n"), +++ (unsigned)bfd_getl32 (esdfm->psindx)); +++ fprintf (file, _(" name : %.*s\n"), +++ esdfm->namlng, esdfm->name); +++ } +++ break; +++ default: +++ fprintf (file, _("unhandled egsd entry type %u\n"), type); +++ break; +++ } +++ off += len; +++ } +++} +++ +++static void +++evax_bfd_print_hex (FILE *file, const char *pfx, +++ const unsigned char *buf, unsigned int len) +++{ +++ unsigned int i; +++ unsigned int n; +++ +++ n = 0; +++ for (i = 0; i < len; i++) +++ { +++ if (n == 0) +++ fputs (pfx, file); +++ fprintf (file, " %02x", buf[i]); +++ n++; +++ if (n == 16) +++ { +++ n = 0; +++ fputc ('\n', file); +++ } +++ } +++ if (n != 0) +++ fputc ('\n', file); +++} +++ +++static void +++evax_bfd_print_etir_stc_ir (FILE *file, const unsigned char *buf, int is_ps) +++{ +++ /* xgettext:c-format */ +++ fprintf (file, _(" linkage index: %u, replacement insn: 0x%08x\n"), +++ (unsigned)bfd_getl32 (buf), +++ (unsigned)bfd_getl32 (buf + 16)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" psect idx 1: %u, offset 1: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf + 4), +++ (unsigned)bfd_getl32 (buf + 12), +++ (unsigned)bfd_getl32 (buf + 8)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" psect idx 2: %u, offset 2: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf + 20), +++ (unsigned)bfd_getl32 (buf + 28), +++ (unsigned)bfd_getl32 (buf + 24)); +++ if (is_ps) +++ /* xgettext:c-format */ +++ fprintf (file, _(" psect idx 3: %u, offset 3: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf + 32), +++ (unsigned)bfd_getl32 (buf + 40), +++ (unsigned)bfd_getl32 (buf + 36)); +++ else +++ fprintf (file, _(" global name: %.*s\n"), buf[32], buf + 33); +++} +++ +++static void +++evax_bfd_print_etir (FILE *file, const char *name, +++ unsigned char *rec, unsigned int rec_len) +++{ +++ unsigned int off = sizeof (struct vms_egsd); +++ unsigned int sec_len = 0; +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" %s (len=%u+%u):\n"), name, +++ (unsigned)(rec_len - sizeof (struct vms_eobjrec)), +++ (unsigned)sizeof (struct vms_eobjrec)); +++ +++ for (off = sizeof (struct vms_eobjrec); off < rec_len; ) +++ { +++ struct vms_etir *etir = (struct vms_etir *)(rec + off); +++ unsigned char *buf; +++ unsigned int type; +++ unsigned int size; +++ +++ type = bfd_getl16 (etir->rectyp); +++ size = bfd_getl16 (etir->size); +++ buf = rec + off + sizeof (struct vms_etir); +++ +++ if (off + size > rec_len || off + size < off) +++ { +++ fprintf (file, _(" Error: length larger than remaining space in record\n")); +++ return; +++ } +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" (type: %3u, size: 4+%3u): "), type, size - 4); +++ switch (type) +++ { +++ case ETIR__C_STA_GBL: +++ fprintf (file, _("STA_GBL (stack global) %.*s\n"), +++ buf[0], buf + 1); +++ break; +++ case ETIR__C_STA_LW: +++ fprintf (file, _("STA_LW (stack longword) 0x%08x\n"), +++ (unsigned)bfd_getl32 (buf)); +++ break; +++ case ETIR__C_STA_QW: +++ fprintf (file, _("STA_QW (stack quadword) 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf + 4), +++ (unsigned)bfd_getl32 (buf + 0)); +++ break; +++ case ETIR__C_STA_PQ: +++ fprintf (file, _("STA_PQ (stack psect base + offset)\n")); +++ /* xgettext:c-format */ +++ fprintf (file, _(" psect: %u, offset: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf + 0), +++ (unsigned)bfd_getl32 (buf + 8), +++ (unsigned)bfd_getl32 (buf + 4)); +++ break; +++ case ETIR__C_STA_LI: +++ fprintf (file, _("STA_LI (stack literal)\n")); +++ break; +++ case ETIR__C_STA_MOD: +++ fprintf (file, _("STA_MOD (stack module)\n")); +++ break; +++ case ETIR__C_STA_CKARG: +++ fprintf (file, _("STA_CKARG (compare procedure argument)\n")); +++ break; +++ +++ case ETIR__C_STO_B: +++ fprintf (file, _("STO_B (store byte)\n")); +++ break; +++ case ETIR__C_STO_W: +++ fprintf (file, _("STO_W (store word)\n")); +++ break; +++ case ETIR__C_STO_LW: +++ fprintf (file, _("STO_LW (store longword)\n")); +++ break; +++ case ETIR__C_STO_QW: +++ fprintf (file, _("STO_QW (store quadword)\n")); +++ break; +++ case ETIR__C_STO_IMMR: +++ { +++ unsigned int len = bfd_getl32 (buf); +++ fprintf (file, +++ _("STO_IMMR (store immediate repeat) %u bytes\n"), +++ len); +++ evax_bfd_print_hex (file, " ", buf + 4, len); +++ sec_len += len; +++ } +++ break; +++ case ETIR__C_STO_GBL: +++ fprintf (file, _("STO_GBL (store global) %.*s\n"), +++ buf[0], buf + 1); +++ break; +++ case ETIR__C_STO_CA: +++ fprintf (file, _("STO_CA (store code address) %.*s\n"), +++ buf[0], buf + 1); +++ break; +++ case ETIR__C_STO_RB: +++ fprintf (file, _("STO_RB (store relative branch)\n")); +++ break; +++ case ETIR__C_STO_AB: +++ fprintf (file, _("STO_AB (store absolute branch)\n")); +++ break; +++ case ETIR__C_STO_OFF: +++ fprintf (file, _("STO_OFF (store offset to psect)\n")); +++ break; +++ case ETIR__C_STO_IMM: +++ { +++ unsigned int len = bfd_getl32 (buf); +++ fprintf (file, +++ _("STO_IMM (store immediate) %u bytes\n"), +++ len); +++ evax_bfd_print_hex (file, " ", buf + 4, len); +++ sec_len += len; +++ } +++ break; +++ case ETIR__C_STO_GBL_LW: +++ fprintf (file, _("STO_GBL_LW (store global longword) %.*s\n"), +++ buf[0], buf + 1); +++ break; +++ case ETIR__C_STO_LP_PSB: +++ fprintf (file, _("STO_OFF (store LP with procedure signature)\n")); +++ break; +++ case ETIR__C_STO_HINT_GBL: +++ fprintf (file, _("STO_BR_GBL (store branch global) *todo*\n")); +++ break; +++ case ETIR__C_STO_HINT_PS: +++ fprintf (file, _("STO_BR_PS (store branch psect + offset) *todo*\n")); +++ break; +++ +++ case ETIR__C_OPR_NOP: +++ fprintf (file, _("OPR_NOP (no-operation)\n")); +++ break; +++ case ETIR__C_OPR_ADD: +++ fprintf (file, _("OPR_ADD (add)\n")); +++ break; +++ case ETIR__C_OPR_SUB: +++ fprintf (file, _("OPR_SUB (subtract)\n")); +++ break; +++ case ETIR__C_OPR_MUL: +++ fprintf (file, _("OPR_MUL (multiply)\n")); +++ break; +++ case ETIR__C_OPR_DIV: +++ fprintf (file, _("OPR_DIV (divide)\n")); +++ break; +++ case ETIR__C_OPR_AND: +++ fprintf (file, _("OPR_AND (logical and)\n")); +++ break; +++ case ETIR__C_OPR_IOR: +++ fprintf (file, _("OPR_IOR (logical inclusive or)\n")); +++ break; +++ case ETIR__C_OPR_EOR: +++ fprintf (file, _("OPR_EOR (logical exclusive or)\n")); +++ break; +++ case ETIR__C_OPR_NEG: +++ fprintf (file, _("OPR_NEG (negate)\n")); +++ break; +++ case ETIR__C_OPR_COM: +++ fprintf (file, _("OPR_COM (complement)\n")); +++ break; +++ case ETIR__C_OPR_INSV: +++ fprintf (file, _("OPR_INSV (insert field)\n")); +++ break; +++ case ETIR__C_OPR_ASH: +++ fprintf (file, _("OPR_ASH (arithmetic shift)\n")); +++ break; +++ case ETIR__C_OPR_USH: +++ fprintf (file, _("OPR_USH (unsigned shift)\n")); +++ break; +++ case ETIR__C_OPR_ROT: +++ fprintf (file, _("OPR_ROT (rotate)\n")); +++ break; +++ case ETIR__C_OPR_SEL: +++ fprintf (file, _("OPR_SEL (select)\n")); +++ break; +++ case ETIR__C_OPR_REDEF: +++ fprintf (file, _("OPR_REDEF (redefine symbol to curr location)\n")); +++ break; +++ case ETIR__C_OPR_DFLIT: +++ fprintf (file, _("OPR_REDEF (define a literal)\n")); +++ break; +++ +++ case ETIR__C_STC_LP: +++ fprintf (file, _("STC_LP (store cond linkage pair)\n")); +++ break; +++ case ETIR__C_STC_LP_PSB: +++ fprintf (file, +++ _("STC_LP_PSB (store cond linkage pair + signature)\n")); +++ /* xgettext:c-format */ +++ fprintf (file, _(" linkage index: %u, procedure: %.*s\n"), +++ (unsigned)bfd_getl32 (buf), buf[4], buf + 5); +++ buf += 4 + 1 + buf[4]; +++ fprintf (file, _(" signature: %.*s\n"), buf[0], buf + 1); +++ break; +++ case ETIR__C_STC_GBL: +++ fprintf (file, _("STC_GBL (store cond global)\n")); +++ /* xgettext:c-format */ +++ fprintf (file, _(" linkage index: %u, global: %.*s\n"), +++ (unsigned)bfd_getl32 (buf), buf[4], buf + 5); +++ break; +++ case ETIR__C_STC_GCA: +++ fprintf (file, _("STC_GCA (store cond code address)\n")); +++ /* xgettext:c-format */ +++ fprintf (file, _(" linkage index: %u, procedure name: %.*s\n"), +++ (unsigned)bfd_getl32 (buf), buf[4], buf + 5); +++ break; +++ case ETIR__C_STC_PS: +++ fprintf (file, _("STC_PS (store cond psect + offset)\n")); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _(" linkage index: %u, psect: %u, offset: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (buf), +++ (unsigned)bfd_getl32 (buf + 4), +++ (unsigned)bfd_getl32 (buf + 12), +++ (unsigned)bfd_getl32 (buf + 8)); +++ break; +++ case ETIR__C_STC_NOP_GBL: +++ fprintf (file, _("STC_NOP_GBL (store cond NOP at global addr)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 0); +++ break; +++ case ETIR__C_STC_NOP_PS: +++ fprintf (file, _("STC_NOP_PS (store cond NOP at psect + offset)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 1); +++ break; +++ case ETIR__C_STC_BSR_GBL: +++ fprintf (file, _("STC_BSR_GBL (store cond BSR at global addr)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 0); +++ break; +++ case ETIR__C_STC_BSR_PS: +++ fprintf (file, _("STC_BSR_PS (store cond BSR at psect + offset)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 1); +++ break; +++ case ETIR__C_STC_LDA_GBL: +++ fprintf (file, _("STC_LDA_GBL (store cond LDA at global addr)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 0); +++ break; +++ case ETIR__C_STC_LDA_PS: +++ fprintf (file, _("STC_LDA_PS (store cond LDA at psect + offset)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 1); +++ break; +++ case ETIR__C_STC_BOH_GBL: +++ fprintf (file, _("STC_BOH_GBL (store cond BOH at global addr)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 0); +++ break; +++ case ETIR__C_STC_BOH_PS: +++ fprintf (file, _("STC_BOH_PS (store cond BOH at psect + offset)\n")); +++ evax_bfd_print_etir_stc_ir (file, buf, 1); +++ break; +++ case ETIR__C_STC_NBH_GBL: +++ fprintf (file, +++ _("STC_NBH_GBL (store cond or hint at global addr)\n")); +++ break; +++ case ETIR__C_STC_NBH_PS: +++ fprintf (file, +++ _("STC_NBH_PS (store cond or hint at psect + offset)\n")); +++ break; +++ +++ case ETIR__C_CTL_SETRB: +++ fprintf (file, _("CTL_SETRB (set relocation base)\n")); +++ sec_len += 4; +++ break; +++ case ETIR__C_CTL_AUGRB: +++ { +++ unsigned int val = bfd_getl32 (buf); +++ fprintf (file, _("CTL_AUGRB (augment relocation base) %u\n"), val); +++ } +++ break; +++ case ETIR__C_CTL_DFLOC: +++ fprintf (file, _("CTL_DFLOC (define location)\n")); +++ break; +++ case ETIR__C_CTL_STLOC: +++ fprintf (file, _("CTL_STLOC (set location)\n")); +++ break; +++ case ETIR__C_CTL_STKDL: +++ fprintf (file, _("CTL_STKDL (stack defined location)\n")); +++ break; +++ default: +++ fprintf (file, _("*unhandled*\n")); +++ break; +++ } +++ off += size; +++ } +++} +++ +++static void +++evax_bfd_print_eobj (struct bfd *abfd, FILE *file) +++{ +++ bfd_boolean is_first = TRUE; +++ bfd_boolean has_records = FALSE; +++ +++ while (1) +++ { +++ unsigned int rec_len; +++ unsigned int pad_len; +++ unsigned char *rec; +++ unsigned int hdr_size; +++ unsigned int type; +++ +++ if (is_first) +++ { +++ unsigned char buf[6]; +++ +++ is_first = FALSE; +++ +++ /* Read 6 bytes. */ +++ if (bfd_bread (buf, sizeof (buf), abfd) != sizeof (buf)) +++ { +++ fprintf (file, _("cannot read GST record length\n")); +++ return; +++ } +++ rec_len = bfd_getl16 (buf + 0); +++ if (rec_len == bfd_getl16 (buf + 4) +++ && bfd_getl16 (buf + 2) == EOBJ__C_EMH) +++ { +++ /* The format is raw: record-size, type, record-size. */ +++ has_records = TRUE; +++ pad_len = (rec_len + 1) & ~1U; +++ hdr_size = 4; +++ } +++ else if (rec_len == EOBJ__C_EMH) +++ { +++ has_records = FALSE; +++ pad_len = bfd_getl16 (buf + 2); +++ hdr_size = 6; +++ } +++ else +++ { +++ /* Ill-formed. */ +++ fprintf (file, _("cannot find EMH in first GST record\n")); +++ return; +++ } +++ rec = bfd_malloc (pad_len); +++ memcpy (rec, buf + sizeof (buf) - hdr_size, hdr_size); +++ } +++ else +++ { +++ unsigned int rec_len2 = 0; +++ unsigned char hdr[4]; +++ +++ if (has_records) +++ { +++ unsigned char buf_len[2]; +++ +++ if (bfd_bread (buf_len, sizeof (buf_len), abfd) +++ != sizeof (buf_len)) +++ { +++ fprintf (file, _("cannot read GST record length\n")); +++ return; +++ } +++ rec_len2 = (unsigned)bfd_getl16 (buf_len); +++ } +++ +++ if (bfd_bread (hdr, sizeof (hdr), abfd) != sizeof (hdr)) +++ { +++ fprintf (file, _("cannot read GST record header\n")); +++ return; +++ } +++ rec_len = (unsigned)bfd_getl16 (hdr + 2); +++ if (has_records) +++ pad_len = (rec_len + 1) & ~1U; +++ else +++ pad_len = rec_len; +++ rec = bfd_malloc (pad_len); +++ memcpy (rec, hdr, sizeof (hdr)); +++ hdr_size = sizeof (hdr); +++ if (has_records && rec_len2 != rec_len) +++ { +++ fprintf (file, _(" corrupted GST\n")); +++ break; +++ } +++ } +++ +++ if (bfd_bread (rec + hdr_size, pad_len - hdr_size, abfd) +++ != pad_len - hdr_size) +++ { +++ fprintf (file, _("cannot read GST record\n")); +++ return; +++ } +++ +++ type = (unsigned)bfd_getl16 (rec); +++ +++ switch (type) +++ { +++ case EOBJ__C_EMH: +++ evax_bfd_print_emh (file, rec, rec_len); +++ break; +++ case EOBJ__C_EGSD: +++ evax_bfd_print_egsd (file, rec, rec_len); +++ break; +++ case EOBJ__C_EEOM: +++ evax_bfd_print_eeom (file, rec, rec_len); +++ free (rec); +++ return; +++ break; +++ case EOBJ__C_ETIR: +++ evax_bfd_print_etir (file, "ETIR", rec, rec_len); +++ break; +++ case EOBJ__C_EDBG: +++ evax_bfd_print_etir (file, "EDBG", rec, rec_len); +++ break; +++ case EOBJ__C_ETBT: +++ evax_bfd_print_etir (file, "ETBT", rec, rec_len); +++ break; +++ default: +++ fprintf (file, _(" unhandled EOBJ record type %u\n"), type); +++ break; +++ } +++ free (rec); +++ } +++} +++ +++static void +++evax_bfd_print_relocation_records (FILE *file, const unsigned char *rel, +++ unsigned int stride) +++{ +++ while (1) +++ { +++ unsigned int base; +++ unsigned int count; +++ unsigned int j; +++ +++ count = bfd_getl32 (rel + 0); +++ +++ if (count == 0) +++ break; +++ base = bfd_getl32 (rel + 4); +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" bitcount: %u, base addr: 0x%08x\n"), +++ count, base); +++ +++ rel += 8; +++ for (j = 0; count > 0; j += 4, count -= 32) +++ { +++ unsigned int k; +++ unsigned int n = 0; +++ unsigned int val; +++ +++ val = bfd_getl32 (rel); +++ rel += 4; +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" bitmap: 0x%08x (count: %u):\n"), val, count); +++ +++ for (k = 0; k < 32; k++) +++ if (val & (1 << k)) +++ { +++ if (n == 0) +++ fputs (" ", file); +++ fprintf (file, _(" %08x"), base + (j * 8 + k) * stride); +++ n++; +++ if (n == 8) +++ { +++ fputs ("\n", file); +++ n = 0; +++ } +++ } +++ if (n) +++ fputs ("\n", file); +++ } +++ } +++} +++ +++static void +++evax_bfd_print_address_fixups (FILE *file, const unsigned char *rel) +++{ +++ while (1) +++ { +++ unsigned int j; +++ unsigned int count; +++ +++ count = bfd_getl32 (rel + 0); +++ if (count == 0) +++ return; +++ /* xgettext:c-format */ +++ fprintf (file, _(" image %u (%u entries)\n"), +++ (unsigned)bfd_getl32 (rel + 4), count); +++ rel += 8; +++ for (j = 0; j < count; j++) +++ { +++ /* xgettext:c-format */ +++ fprintf (file, _(" offset: 0x%08x, val: 0x%08x\n"), +++ (unsigned)bfd_getl32 (rel + 0), +++ (unsigned)bfd_getl32 (rel + 4)); +++ rel += 8; +++ } +++ } +++} +++ +++static void +++evax_bfd_print_reference_fixups (FILE *file, const unsigned char *rel) +++{ +++ unsigned int count; +++ +++ while (1) +++ { +++ unsigned int j; +++ unsigned int n = 0; +++ +++ count = bfd_getl32 (rel + 0); +++ if (count == 0) +++ break; +++ /* xgettext:c-format */ +++ fprintf (file, _(" image %u (%u entries), offsets:\n"), +++ (unsigned)bfd_getl32 (rel + 4), count); +++ rel += 8; +++ for (j = 0; j < count; j++) +++ { +++ if (n == 0) +++ fputs (" ", file); +++ fprintf (file, _(" 0x%08x"), (unsigned)bfd_getl32 (rel)); +++ n++; +++ if (n == 7) +++ { +++ fputs ("\n", file); +++ n = 0; +++ } +++ rel += 4; +++ } +++ if (n) +++ fputs ("\n", file); +++ } +++} +++ +++static void +++evax_bfd_print_indent (int indent, FILE *file) +++{ +++ for (; indent; indent--) +++ fputc (' ', file); +++} +++ +++static const char * +++evax_bfd_get_dsc_name (unsigned int v) +++{ +++ switch (v) +++ { +++ case DSC__K_DTYPE_Z: +++ return "Z (Unspecified)"; +++ case DSC__K_DTYPE_V: +++ return "V (Bit)"; +++ case DSC__K_DTYPE_BU: +++ return "BU (Byte logical)"; +++ case DSC__K_DTYPE_WU: +++ return "WU (Word logical)"; +++ case DSC__K_DTYPE_LU: +++ return "LU (Longword logical)"; +++ case DSC__K_DTYPE_QU: +++ return "QU (Quadword logical)"; +++ case DSC__K_DTYPE_B: +++ return "B (Byte integer)"; +++ case DSC__K_DTYPE_W: +++ return "W (Word integer)"; +++ case DSC__K_DTYPE_L: +++ return "L (Longword integer)"; +++ case DSC__K_DTYPE_Q: +++ return "Q (Quadword integer)"; +++ case DSC__K_DTYPE_F: +++ return "F (Single-precision floating)"; +++ case DSC__K_DTYPE_D: +++ return "D (Double-precision floating)"; +++ case DSC__K_DTYPE_FC: +++ return "FC (Complex)"; +++ case DSC__K_DTYPE_DC: +++ return "DC (Double-precision Complex)"; +++ case DSC__K_DTYPE_T: +++ return "T (ASCII text string)"; +++ case DSC__K_DTYPE_NU: +++ return "NU (Numeric string, unsigned)"; +++ case DSC__K_DTYPE_NL: +++ return "NL (Numeric string, left separate sign)"; +++ case DSC__K_DTYPE_NLO: +++ return "NLO (Numeric string, left overpunched sign)"; +++ case DSC__K_DTYPE_NR: +++ return "NR (Numeric string, right separate sign)"; +++ case DSC__K_DTYPE_NRO: +++ return "NRO (Numeric string, right overpunched sig)"; +++ case DSC__K_DTYPE_NZ: +++ return "NZ (Numeric string, zoned sign)"; +++ case DSC__K_DTYPE_P: +++ return "P (Packed decimal string)"; +++ case DSC__K_DTYPE_ZI: +++ return "ZI (Sequence of instructions)"; +++ case DSC__K_DTYPE_ZEM: +++ return "ZEM (Procedure entry mask)"; +++ case DSC__K_DTYPE_DSC: +++ return "DSC (Descriptor, used for arrays of dyn strings)"; +++ case DSC__K_DTYPE_OU: +++ return "OU (Octaword logical)"; +++ case DSC__K_DTYPE_O: +++ return "O (Octaword integer)"; +++ case DSC__K_DTYPE_G: +++ return "G (Double precision G floating, 64 bit)"; +++ case DSC__K_DTYPE_H: +++ return "H (Quadruple precision floating, 128 bit)"; +++ case DSC__K_DTYPE_GC: +++ return "GC (Double precision complex, G floating)"; +++ case DSC__K_DTYPE_HC: +++ return "HC (Quadruple precision complex, H floating)"; +++ case DSC__K_DTYPE_CIT: +++ return "CIT (COBOL intermediate temporary)"; +++ case DSC__K_DTYPE_BPV: +++ return "BPV (Bound Procedure Value)"; +++ case DSC__K_DTYPE_BLV: +++ return "BLV (Bound Label Value)"; +++ case DSC__K_DTYPE_VU: +++ return "VU (Bit Unaligned)"; +++ case DSC__K_DTYPE_ADT: +++ return "ADT (Absolute Date-Time)"; +++ case DSC__K_DTYPE_VT: +++ return "VT (Varying Text)"; +++ case DSC__K_DTYPE_T2: +++ return "T2 (16-bit char)"; +++ case DSC__K_DTYPE_VT2: +++ return "VT2 (16-bit varying char)"; +++ default: +++ return "?? (unknown)"; +++ } +++} +++ +++static void +++evax_bfd_print_desc (const unsigned char *buf, int indent, FILE *file) +++{ +++ unsigned char bclass = buf[3]; +++ unsigned char dtype = buf[2]; +++ unsigned int len = (unsigned)bfd_getl16 (buf); +++ unsigned int pointer = (unsigned)bfd_getl32 (buf + 4); +++ +++ evax_bfd_print_indent (indent, file); +++ +++ if (len == 1 && pointer == 0xffffffffUL) +++ { +++ /* 64 bits. */ +++ fprintf (file, _("64 bits *unhandled*\n")); +++ } +++ else +++ { +++ /* xgettext:c-format */ +++ fprintf (file, _("class: %u, dtype: %u, length: %u, pointer: 0x%08x\n"), +++ bclass, dtype, len, pointer); +++ switch (bclass) +++ { +++ case DSC__K_CLASS_NCA: +++ { +++ const struct vms_dsc_nca *dsc = (const void *)buf; +++ unsigned int i; +++ const unsigned char *b; +++ +++ evax_bfd_print_indent (indent, file); +++ fprintf (file, _("non-contiguous array of %s\n"), +++ evax_bfd_get_dsc_name (dsc->dtype)); +++ evax_bfd_print_indent (indent + 1, file); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _("dimct: %u, aflags: 0x%02x, digits: %u, scale: %u\n"), +++ dsc->dimct, dsc->aflags, dsc->digits, dsc->scale); +++ evax_bfd_print_indent (indent + 1, file); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _("arsize: %u, a0: 0x%08x\n"), +++ (unsigned)bfd_getl32 (dsc->arsize), +++ (unsigned)bfd_getl32 (dsc->a0)); +++ evax_bfd_print_indent (indent + 1, file); +++ fprintf (file, _("Strides:\n")); +++ b = buf + sizeof (*dsc); +++ for (i = 0; i < dsc->dimct; i++) +++ { +++ evax_bfd_print_indent (indent + 2, file); +++ fprintf (file, "[%u]: %u\n", i + 1, +++ (unsigned)bfd_getl32 (b)); +++ b += 4; +++ } +++ evax_bfd_print_indent (indent + 1, file); +++ fprintf (file, _("Bounds:\n")); +++ b = buf + sizeof (*dsc); +++ for (i = 0; i < dsc->dimct; i++) +++ { +++ evax_bfd_print_indent (indent + 2, file); +++ /* xgettext:c-format */ +++ fprintf (file, _("[%u]: Lower: %u, upper: %u\n"), i + 1, +++ (unsigned)bfd_getl32 (b + 0), +++ (unsigned)bfd_getl32 (b + 4)); +++ b += 8; +++ } +++ } +++ break; +++ case DSC__K_CLASS_UBS: +++ { +++ const struct vms_dsc_ubs *ubs = (const void *)buf; +++ +++ evax_bfd_print_indent (indent, file); +++ fprintf (file, _("unaligned bit-string of %s\n"), +++ evax_bfd_get_dsc_name (ubs->dtype)); +++ evax_bfd_print_indent (indent + 1, file); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _("base: %u, pos: %u\n"), +++ (unsigned)bfd_getl32 (ubs->base), +++ (unsigned)bfd_getl32 (ubs->pos)); +++ } +++ break; +++ default: +++ fprintf (file, _("*unhandled*\n")); +++ break; +++ } +++ } +++} +++ +++static unsigned int +++evax_bfd_print_valspec (const unsigned char *buf, int indent, FILE *file) +++{ +++ unsigned int vflags = buf[0]; +++ unsigned int value = (unsigned)bfd_getl32 (buf + 1); +++ unsigned int len = 5; +++ +++ evax_bfd_print_indent (indent, file); +++ /* xgettext:c-format */ +++ fprintf (file, _("vflags: 0x%02x, value: 0x%08x "), vflags, value); +++ buf += 5; +++ +++ switch (vflags) +++ { +++ case DST__K_VFLAGS_NOVAL: +++ fprintf (file, _("(no value)\n")); +++ break; +++ case DST__K_VFLAGS_NOTACTIVE: +++ fprintf (file, _("(not active)\n")); +++ break; +++ case DST__K_VFLAGS_UNALLOC: +++ fprintf (file, _("(not allocated)\n")); +++ break; +++ case DST__K_VFLAGS_DSC: +++ fprintf (file, _("(descriptor)\n")); +++ evax_bfd_print_desc (buf + value, indent + 1, file); +++ break; +++ case DST__K_VFLAGS_TVS: +++ fprintf (file, _("(trailing value)\n")); +++ break; +++ case DST__K_VS_FOLLOWS: +++ fprintf (file, _("(value spec follows)\n")); +++ break; +++ case DST__K_VFLAGS_BITOFFS: +++ fprintf (file, _("(at bit offset %u)\n"), value); +++ break; +++ default: +++ /* xgettext:c-format */ +++ fprintf (file, _("(reg: %u, disp: %u, indir: %u, kind: "), +++ (vflags & DST__K_REGNUM_MASK) >> DST__K_REGNUM_SHIFT, +++ vflags & DST__K_DISP ? 1 : 0, +++ vflags & DST__K_INDIR ? 1 : 0); +++ switch (vflags & DST__K_VALKIND_MASK) +++ { +++ case DST__K_VALKIND_LITERAL: +++ fputs (_("literal"), file); +++ break; +++ case DST__K_VALKIND_ADDR: +++ fputs (_("address"), file); +++ break; +++ case DST__K_VALKIND_DESC: +++ fputs (_("desc"), file); +++ break; +++ case DST__K_VALKIND_REG: +++ fputs (_("reg"), file); +++ break; +++ } +++ fputs (")\n", file); +++ break; +++ } +++ return len; +++} +++ +++static void +++evax_bfd_print_typspec (const unsigned char *buf, int indent, FILE *file) +++{ +++ unsigned char kind = buf[2]; +++ unsigned int len = (unsigned)bfd_getl16 (buf); +++ +++ evax_bfd_print_indent (indent, file); +++ /* xgettext:c-format */ +++ fprintf (file, _("len: %2u, kind: %2u "), len, kind); +++ buf += 3; +++ switch (kind) +++ { +++ case DST__K_TS_ATOM: +++ /* xgettext:c-format */ +++ fprintf (file, _("atomic, type=0x%02x %s\n"), +++ buf[0], evax_bfd_get_dsc_name (buf[0])); +++ break; +++ case DST__K_TS_IND: +++ fprintf (file, _("indirect, defined at 0x%08x\n"), +++ (unsigned)bfd_getl32 (buf)); +++ break; +++ case DST__K_TS_TPTR: +++ fprintf (file, _("typed pointer\n")); +++ evax_bfd_print_typspec (buf, indent + 1, file); +++ break; +++ case DST__K_TS_PTR: +++ fprintf (file, _("pointer\n")); +++ break; +++ case DST__K_TS_ARRAY: +++ { +++ const unsigned char *vs; +++ unsigned int vec_len; +++ unsigned int i; +++ +++ fprintf (file, _("array, dim: %u, bitmap: "), buf[0]); +++ vec_len = (buf[0] + 1 + 7) / 8; +++ for (i = 0; i < vec_len; i++) +++ fprintf (file, " %02x", buf[i + 1]); +++ fputc ('\n', file); +++ vs = buf + 1 + vec_len; +++ evax_bfd_print_indent (indent, file); +++ fprintf (file, _("array descriptor:\n")); +++ vs += evax_bfd_print_valspec (vs, indent + 1, file); +++ for (i = 0; i < buf[0] + 1U; i++) +++ if (buf[1 + i / 8] & (1 << (i % 8))) +++ { +++ evax_bfd_print_indent (indent, file); +++ if (i == 0) +++ fprintf (file, _("type spec for element:\n")); +++ else +++ fprintf (file, _("type spec for subscript %u:\n"), i); +++ evax_bfd_print_typspec (vs, indent + 1, file); +++ vs += bfd_getl16 (vs); +++ } +++ } +++ break; +++ default: +++ fprintf (file, _("*unhandled*\n")); +++ } +++} +++ +++static void +++evax_bfd_print_dst (struct bfd *abfd, unsigned int dst_size, FILE *file) +++{ +++ unsigned int off = 0; +++ unsigned int pc = 0; +++ unsigned int line = 0; +++ +++ fprintf (file, _("Debug symbol table:\n")); +++ +++ while (dst_size > 0) +++ { +++ struct vms_dst_header dsth; +++ unsigned int len; +++ unsigned int type; +++ unsigned char *buf; +++ +++ if (bfd_bread (&dsth, sizeof (dsth), abfd) != sizeof (dsth)) +++ { +++ fprintf (file, _("cannot read DST header\n")); +++ return; +++ } +++ len = bfd_getl16 (dsth.length); +++ type = bfd_getl16 (dsth.type); +++ /* xgettext:c-format */ +++ fprintf (file, _(" type: %3u, len: %3u (at 0x%08x): "), +++ type, len, off); +++ if (len == 0) +++ { +++ fputc ('\n', file); +++ break; +++ } +++ len++; +++ dst_size -= len; +++ off += len; +++ len -= sizeof (dsth); +++ buf = bfd_malloc (len); +++ if (bfd_bread (buf, len, abfd) != len) +++ { +++ fprintf (file, _("cannot read DST symbol\n")); +++ return; +++ } +++ switch (type) +++ { +++ case DSC__K_DTYPE_V: +++ case DSC__K_DTYPE_BU: +++ case DSC__K_DTYPE_WU: +++ case DSC__K_DTYPE_LU: +++ case DSC__K_DTYPE_QU: +++ case DSC__K_DTYPE_B: +++ case DSC__K_DTYPE_W: +++ case DSC__K_DTYPE_L: +++ case DSC__K_DTYPE_Q: +++ case DSC__K_DTYPE_F: +++ case DSC__K_DTYPE_D: +++ case DSC__K_DTYPE_FC: +++ case DSC__K_DTYPE_DC: +++ case DSC__K_DTYPE_T: +++ case DSC__K_DTYPE_NU: +++ case DSC__K_DTYPE_NL: +++ case DSC__K_DTYPE_NLO: +++ case DSC__K_DTYPE_NR: +++ case DSC__K_DTYPE_NRO: +++ case DSC__K_DTYPE_NZ: +++ case DSC__K_DTYPE_P: +++ case DSC__K_DTYPE_ZI: +++ case DSC__K_DTYPE_ZEM: +++ case DSC__K_DTYPE_DSC: +++ case DSC__K_DTYPE_OU: +++ case DSC__K_DTYPE_O: +++ case DSC__K_DTYPE_G: +++ case DSC__K_DTYPE_H: +++ case DSC__K_DTYPE_GC: +++ case DSC__K_DTYPE_HC: +++ case DSC__K_DTYPE_CIT: +++ case DSC__K_DTYPE_BPV: +++ case DSC__K_DTYPE_BLV: +++ case DSC__K_DTYPE_VU: +++ case DSC__K_DTYPE_ADT: +++ case DSC__K_DTYPE_VT: +++ case DSC__K_DTYPE_T2: +++ case DSC__K_DTYPE_VT2: +++ fprintf (file, _("standard data: %s\n"), +++ evax_bfd_get_dsc_name (type)); +++ evax_bfd_print_valspec (buf, 4, file); +++ fprintf (file, _(" name: %.*s\n"), buf[5], buf + 6); +++ break; +++ case DST__K_MODBEG: +++ { +++ struct vms_dst_modbeg *dst = (void *)buf; +++ const char *name = (const char *)buf + sizeof (*dst); +++ +++ fprintf (file, _("modbeg\n")); +++ /* xgettext:c-format */ +++ fprintf (file, _(" flags: %d, language: %u, " +++ "major: %u, minor: %u\n"), +++ dst->flags, +++ (unsigned)bfd_getl32 (dst->language), +++ (unsigned)bfd_getl16 (dst->major), +++ (unsigned)bfd_getl16 (dst->minor)); +++ fprintf (file, _(" module name: %.*s\n"), +++ name[0], name + 1); +++ name += name[0] + 1; +++ fprintf (file, _(" compiler : %.*s\n"), +++ name[0], name + 1); +++ } +++ break; +++ case DST__K_MODEND: +++ fprintf (file, _("modend\n")); +++ break; +++ case DST__K_RTNBEG: +++ { +++ struct vms_dst_rtnbeg *dst = (void *)buf; +++ const char *name = (const char *)buf + sizeof (*dst); +++ +++ fputs (_("rtnbeg\n"), file); +++ /* xgettext:c-format */ +++ fprintf (file, _(" flags: %u, address: 0x%08x, " +++ "pd-address: 0x%08x\n"), +++ dst->flags, +++ (unsigned)bfd_getl32 (dst->address), +++ (unsigned)bfd_getl32 (dst->pd_address)); +++ fprintf (file, _(" routine name: %.*s\n"), +++ name[0], name + 1); +++ } +++ break; +++ case DST__K_RTNEND: +++ { +++ struct vms_dst_rtnend *dst = (void *)buf; +++ +++ fprintf (file, _("rtnend: size 0x%08x\n"), +++ (unsigned)bfd_getl32 (dst->size)); +++ } +++ break; +++ case DST__K_PROLOG: +++ { +++ struct vms_dst_prolog *dst = (void *)buf; +++ +++ fprintf (file, _("prolog: bkpt address 0x%08x\n"), +++ (unsigned)bfd_getl32 (dst->bkpt_addr)); +++ } +++ break; +++ case DST__K_EPILOG: +++ { +++ struct vms_dst_epilog *dst = (void *)buf; +++ +++ /* xgettext:c-format */ +++ fprintf (file, _("epilog: flags: %u, count: %u\n"), +++ dst->flags, (unsigned)bfd_getl32 (dst->count)); +++ } +++ break; +++ case DST__K_BLKBEG: +++ { +++ struct vms_dst_blkbeg *dst = (void *)buf; +++ const char *name = (const char *)buf + sizeof (*dst); +++ +++ /* xgettext:c-format */ +++ fprintf (file, _("blkbeg: address: 0x%08x, name: %.*s\n"), +++ (unsigned)bfd_getl32 (dst->address), +++ name[0], name + 1); +++ } +++ break; +++ case DST__K_BLKEND: +++ { +++ struct vms_dst_blkend *dst = (void *)buf; +++ +++ fprintf (file, _("blkend: size: 0x%08x\n"), +++ (unsigned)bfd_getl32 (dst->size)); +++ } +++ break; +++ case DST__K_TYPSPEC: +++ { +++ fprintf (file, _("typspec (len: %u)\n"), len); +++ fprintf (file, _(" name: %.*s\n"), buf[0], buf + 1); +++ evax_bfd_print_typspec (buf + 1 + buf[0], 5, file); +++ } +++ break; +++ case DST__K_SEPTYP: +++ { +++ fprintf (file, _("septyp, name: %.*s\n"), buf[5], buf + 6); +++ evax_bfd_print_valspec (buf, 4, file); +++ } +++ break; +++ case DST__K_RECBEG: +++ { +++ struct vms_dst_recbeg *recbeg = (void *)buf; +++ const char *name = (const char *)buf + sizeof (*recbeg); +++ +++ fprintf (file, _("recbeg: name: %.*s\n"), name[0], name + 1); +++ evax_bfd_print_valspec (buf, 4, file); +++ fprintf (file, _(" len: %u bits\n"), +++ (unsigned)bfd_getl32 (name + 1 + name[0])); +++ } +++ break; +++ case DST__K_RECEND: +++ fprintf (file, _("recend\n")); +++ break; +++ case DST__K_ENUMBEG: +++ /* xgettext:c-format */ +++ fprintf (file, _("enumbeg, len: %u, name: %.*s\n"), +++ buf[0], buf[1], buf + 2); +++ break; +++ case DST__K_ENUMELT: +++ fprintf (file, _("enumelt, name: %.*s\n"), buf[5], buf + 6); +++ evax_bfd_print_valspec (buf, 4, file); +++ break; +++ case DST__K_ENUMEND: +++ fprintf (file, _("enumend\n")); +++ break; +++ case DST__K_LABEL: +++ { +++ struct vms_dst_label *lab = (void *)buf; +++ fprintf (file, _("label, name: %.*s\n"), +++ lab->name[0], lab->name + 1); +++ fprintf (file, _(" address: 0x%08x\n"), +++ (unsigned)bfd_getl32 (lab->value)); +++ } +++ break; +++ case DST__K_DIS_RANGE: +++ { +++ unsigned int cnt = bfd_getl32 (buf); +++ unsigned char *rng = buf + 4; +++ unsigned int i; +++ +++ fprintf (file, _("discontiguous range (nbr: %u)\n"), cnt); +++ for (i = 0; i < cnt; i++, rng += 8) +++ /* xgettext:c-format */ +++ fprintf (file, _(" address: 0x%08x, size: %u\n"), +++ (unsigned)bfd_getl32 (rng), +++ (unsigned)bfd_getl32 (rng + 4)); +++ +++ } +++ break; +++ case DST__K_LINE_NUM: +++ { +++ unsigned char *buf_orig = buf; +++ +++ fprintf (file, _("line num (len: %u)\n"), len); +++ +++ while (len > 0) +++ { +++ signed char cmd; +++ unsigned char cmdlen; +++ unsigned int val; +++ +++ cmd = buf[0]; +++ cmdlen = 0; +++ +++ fputs (" ", file); +++ +++ switch (cmd) +++ { +++ case DST__K_DELTA_PC_W: +++ val = bfd_getl16 (buf + 1); +++ fprintf (file, _("delta_pc_w %u\n"), val); +++ pc += val; +++ line++; +++ cmdlen = 3; +++ break; +++ case DST__K_INCR_LINUM: +++ val = buf[1]; +++ fprintf (file, _("incr_linum(b): +%u\n"), val); +++ line += val; +++ cmdlen = 2; +++ break; +++ case DST__K_INCR_LINUM_W: +++ val = bfd_getl16 (buf + 1); +++ fprintf (file, _("incr_linum_w: +%u\n"), val); +++ line += val; +++ cmdlen = 3; +++ break; +++ case DST__K_INCR_LINUM_L: +++ val = bfd_getl32 (buf + 1); +++ fprintf (file, _("incr_linum_l: +%u\n"), val); +++ line += val; +++ cmdlen = 5; +++ break; +++ case DST__K_SET_LINUM: +++ line = bfd_getl16 (buf + 1); +++ fprintf (file, _("set_line_num(w) %u\n"), line); +++ cmdlen = 3; +++ break; +++ case DST__K_SET_LINUM_B: +++ line = buf[1]; +++ fprintf (file, _("set_line_num_b %u\n"), line); +++ cmdlen = 2; +++ break; +++ case DST__K_SET_LINUM_L: +++ line = bfd_getl32 (buf + 1); +++ fprintf (file, _("set_line_num_l %u\n"), line); +++ cmdlen = 5; +++ break; +++ case DST__K_SET_ABS_PC: +++ pc = bfd_getl32 (buf + 1); +++ fprintf (file, _("set_abs_pc: 0x%08x\n"), pc); +++ cmdlen = 5; +++ break; +++ case DST__K_DELTA_PC_L: +++ fprintf (file, _("delta_pc_l: +0x%08x\n"), +++ (unsigned)bfd_getl32 (buf + 1)); +++ cmdlen = 5; +++ break; +++ case DST__K_TERM: +++ fprintf (file, _("term(b): 0x%02x"), buf[1]); +++ pc += buf[1]; +++ fprintf (file, _(" pc: 0x%08x\n"), pc); +++ cmdlen = 2; +++ break; +++ case DST__K_TERM_W: +++ val = bfd_getl16 (buf + 1); +++ fprintf (file, _("term_w: 0x%04x"), val); +++ pc += val; +++ fprintf (file, _(" pc: 0x%08x\n"), pc); +++ cmdlen = 3; +++ break; +++ default: +++ if (cmd <= 0) +++ { +++ fprintf (file, _("delta pc +%-4d"), -cmd); +++ line++; /* FIXME: curr increment. */ +++ pc += -cmd; +++ /* xgettext:c-format */ +++ fprintf (file, _(" pc: 0x%08x line: %5u\n"), +++ pc, line); +++ cmdlen = 1; +++ } +++ else +++ fprintf (file, _(" *unhandled* cmd %u\n"), cmd); +++ break; +++ } +++ if (cmdlen == 0) +++ break; +++ len -= cmdlen; +++ buf += cmdlen; +++ } +++ buf = buf_orig; +++ } +++ break; +++ case DST__K_SOURCE: +++ { +++ unsigned char *buf_orig = buf; +++ +++ fprintf (file, _("source (len: %u)\n"), len); +++ +++ while (len > 0) +++ { +++ signed char cmd = buf[0]; +++ unsigned char cmdlen = 0; +++ +++ switch (cmd) +++ { +++ case DST__K_SRC_DECLFILE: +++ { +++ struct vms_dst_src_decl_src *src = (void *)(buf + 1); +++ const char *name; +++ +++ /* xgettext:c-format */ +++ fprintf (file, _(" declfile: len: %u, flags: %u, " +++ "fileid: %u\n"), +++ src->length, src->flags, +++ (unsigned)bfd_getl16 (src->fileid)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" rms: cdt: 0x%08x %08x, " +++ "ebk: 0x%08x, ffb: 0x%04x, " +++ "rfo: %u\n"), +++ (unsigned)bfd_getl32 (src->rms_cdt + 4), +++ (unsigned)bfd_getl32 (src->rms_cdt + 0), +++ (unsigned)bfd_getl32 (src->rms_ebk), +++ (unsigned)bfd_getl16 (src->rms_ffb), +++ src->rms_rfo); +++ name = (const char *)buf + 1 + sizeof (*src); +++ fprintf (file, _(" filename : %.*s\n"), +++ name[0], name + 1); +++ name += name[0] + 1; +++ fprintf (file, _(" module name: %.*s\n"), +++ name[0], name + 1); +++ cmdlen = 2 + src->length; +++ } +++ break; +++ case DST__K_SRC_SETFILE: +++ fprintf (file, _(" setfile %u\n"), +++ (unsigned)bfd_getl16 (buf + 1)); +++ cmdlen = 3; +++ break; +++ case DST__K_SRC_SETREC_W: +++ fprintf (file, _(" setrec %u\n"), +++ (unsigned)bfd_getl16 (buf + 1)); +++ cmdlen = 3; +++ break; +++ case DST__K_SRC_SETREC_L: +++ fprintf (file, _(" setrec %u\n"), +++ (unsigned)bfd_getl32 (buf + 1)); +++ cmdlen = 5; +++ break; +++ case DST__K_SRC_SETLNUM_W: +++ fprintf (file, _(" setlnum %u\n"), +++ (unsigned)bfd_getl16 (buf + 1)); +++ cmdlen = 3; +++ break; +++ case DST__K_SRC_SETLNUM_L: +++ fprintf (file, _(" setlnum %u\n"), +++ (unsigned)bfd_getl32 (buf + 1)); +++ cmdlen = 5; +++ break; +++ case DST__K_SRC_DEFLINES_W: +++ fprintf (file, _(" deflines %u\n"), +++ (unsigned)bfd_getl16 (buf + 1)); +++ cmdlen = 3; +++ break; +++ case DST__K_SRC_DEFLINES_B: +++ fprintf (file, _(" deflines %u\n"), buf[1]); +++ cmdlen = 2; +++ break; +++ case DST__K_SRC_FORMFEED: +++ fprintf (file, _(" formfeed\n")); +++ cmdlen = 1; +++ break; +++ default: +++ fprintf (file, _(" *unhandled* cmd %u\n"), cmd); +++ break; +++ } +++ if (cmdlen == 0) +++ break; +++ len -= cmdlen; +++ buf += cmdlen; +++ } +++ buf = buf_orig; +++ } +++ break; +++ default: +++ fprintf (file, _("*unhandled* dst type %u\n"), type); +++ break; +++ } +++ free (buf); +++ } +++} +++ +++static void +++evax_bfd_print_image (bfd *abfd, FILE *file) +++{ +++ struct vms_eihd eihd; +++ const char *name; +++ unsigned int val; +++ unsigned int eiha_off; +++ unsigned int eihi_off; +++ unsigned int eihs_off; +++ unsigned int eisd_off; +++ unsigned int eihef_off = 0; +++ unsigned int eihnp_off = 0; +++ unsigned int dmt_vbn = 0; +++ unsigned int dmt_size = 0; +++ unsigned int dst_vbn = 0; +++ unsigned int dst_size = 0; +++ unsigned int gst_vbn = 0; +++ unsigned int gst_size = 0; +++ unsigned int eiaf_vbn = 0; +++ unsigned int eiaf_size = 0; +++ unsigned int eihvn_off; +++ +++ if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) +++ || bfd_bread (&eihd, sizeof (eihd), abfd) != sizeof (eihd)) +++ { +++ fprintf (file, _("cannot read EIHD\n")); +++ return; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _("EIHD: (size: %u, nbr blocks: %u)\n"), +++ (unsigned)bfd_getl32 (eihd.size), +++ (unsigned)bfd_getl32 (eihd.hdrblkcnt)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" majorid: %u, minorid: %u\n"), +++ (unsigned)bfd_getl32 (eihd.majorid), +++ (unsigned)bfd_getl32 (eihd.minorid)); +++ +++ val = (unsigned)bfd_getl32 (eihd.imgtype); +++ switch (val) +++ { +++ case EIHD__K_EXE: +++ name = _("executable"); +++ break; +++ case EIHD__K_LIM: +++ name = _("linkable image"); +++ break; +++ default: +++ name = _("unknown"); +++ break; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _(" image type: %u (%s)"), val, name); +++ +++ val = (unsigned)bfd_getl32 (eihd.subtype); +++ switch (val) +++ { +++ case EIHD__C_NATIVE: +++ name = _("native"); +++ break; +++ case EIHD__C_CLI: +++ name = _("CLI"); +++ break; +++ default: +++ name = _("unknown"); +++ break; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _(", subtype: %u (%s)\n"), val, name); +++ +++ eisd_off = bfd_getl32 (eihd.isdoff); +++ eiha_off = bfd_getl32 (eihd.activoff); +++ eihi_off = bfd_getl32 (eihd.imgidoff); +++ eihs_off = bfd_getl32 (eihd.symdbgoff); +++ /* xgettext:c-format */ +++ fprintf (file, _(" offsets: isd: %u, activ: %u, symdbg: %u, " +++ "imgid: %u, patch: %u\n"), +++ eisd_off, eiha_off, eihs_off, eihi_off, +++ (unsigned)bfd_getl32 (eihd.patchoff)); +++ fprintf (file, _(" fixup info rva: ")); +++ bfd_fprintf_vma (abfd, file, bfd_getl64 (eihd.iafva)); +++ fprintf (file, _(", symbol vector rva: ")); +++ bfd_fprintf_vma (abfd, file, bfd_getl64 (eihd.symvva)); +++ eihvn_off = bfd_getl32 (eihd.version_array_off); +++ fprintf (file, _("\n" +++ " version array off: %u\n"), +++ eihvn_off); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _(" img I/O count: %u, nbr channels: %u, req pri: %08x%08x\n"), +++ (unsigned)bfd_getl32 (eihd.imgiocnt), +++ (unsigned)bfd_getl32 (eihd.iochancnt), +++ (unsigned)bfd_getl32 (eihd.privreqs + 4), +++ (unsigned)bfd_getl32 (eihd.privreqs + 0)); +++ val = (unsigned)bfd_getl32 (eihd.lnkflags); +++ fprintf (file, _(" linker flags: %08x:"), val); +++ if (val & EIHD__M_LNKDEBUG) +++ fprintf (file, " LNKDEBUG"); +++ if (val & EIHD__M_LNKNOTFR) +++ fprintf (file, " LNKNOTFR"); +++ if (val & EIHD__M_NOP0BUFS) +++ fprintf (file, " NOP0BUFS"); +++ if (val & EIHD__M_PICIMG) +++ fprintf (file, " PICIMG"); +++ if (val & EIHD__M_P0IMAGE) +++ fprintf (file, " P0IMAGE"); +++ if (val & EIHD__M_DBGDMT) +++ fprintf (file, " DBGDMT"); +++ if (val & EIHD__M_INISHR) +++ fprintf (file, " INISHR"); +++ if (val & EIHD__M_XLATED) +++ fprintf (file, " XLATED"); +++ if (val & EIHD__M_BIND_CODE_SEC) +++ fprintf (file, " BIND_CODE_SEC"); +++ if (val & EIHD__M_BIND_DATA_SEC) +++ fprintf (file, " BIND_DATA_SEC"); +++ if (val & EIHD__M_MKTHREADS) +++ fprintf (file, " MKTHREADS"); +++ if (val & EIHD__M_UPCALLS) +++ fprintf (file, " UPCALLS"); +++ if (val & EIHD__M_OMV_READY) +++ fprintf (file, " OMV_READY"); +++ if (val & EIHD__M_EXT_BIND_SECT) +++ fprintf (file, " EXT_BIND_SECT"); +++ fprintf (file, "\n"); +++ /* xgettext:c-format */ +++ fprintf (file, _(" ident: 0x%08x, sysver: 0x%08x, " +++ "match ctrl: %u, symvect_size: %u\n"), +++ (unsigned)bfd_getl32 (eihd.ident), +++ (unsigned)bfd_getl32 (eihd.sysver), +++ eihd.matchctl, +++ (unsigned)bfd_getl32 (eihd.symvect_size)); +++ fprintf (file, _(" BPAGE: %u"), +++ (unsigned)bfd_getl32 (eihd.virt_mem_block_size)); +++ if (val & (EIHD__M_OMV_READY | EIHD__M_EXT_BIND_SECT)) +++ { +++ eihef_off = bfd_getl32 (eihd.ext_fixup_off); +++ eihnp_off = bfd_getl32 (eihd.noopt_psect_off); +++ /* xgettext:c-format */ +++ fprintf (file, _(", ext fixup offset: %u, no_opt psect off: %u"), +++ eihef_off, eihnp_off); +++ } +++ fprintf (file, _(", alias: %u\n"), (unsigned)bfd_getl16 (eihd.alias)); +++ +++ if (eihvn_off != 0) +++ { +++ struct vms_eihvn eihvn; +++ unsigned int mask; +++ unsigned int j; +++ +++ fprintf (file, _("system version array information:\n")); +++ if (bfd_seek (abfd, (file_ptr) eihvn_off, SEEK_SET) +++ || bfd_bread (&eihvn, sizeof (eihvn), abfd) != sizeof (eihvn)) +++ { +++ fprintf (file, _("cannot read EIHVN header\n")); +++ return; +++ } +++ mask = bfd_getl32 (eihvn.subsystem_mask); +++ for (j = 0; j < 32; j++) +++ if (mask & (1 << j)) +++ { +++ struct vms_eihvn_subversion ver; +++ if (bfd_bread (&ver, sizeof (ver), abfd) != sizeof (ver)) +++ { +++ fprintf (file, _("cannot read EIHVN version\n")); +++ return; +++ } +++ fprintf (file, _(" %02u "), j); +++ switch (j) +++ { +++ case EIHVN__BASE_IMAGE_BIT: +++ fputs (_("BASE_IMAGE "), file); +++ break; +++ case EIHVN__MEMORY_MANAGEMENT_BIT: +++ fputs (_("MEMORY_MANAGEMENT"), file); +++ break; +++ case EIHVN__IO_BIT: +++ fputs (_("IO "), file); +++ break; +++ case EIHVN__FILES_VOLUMES_BIT: +++ fputs (_("FILES_VOLUMES "), file); +++ break; +++ case EIHVN__PROCESS_SCHED_BIT: +++ fputs (_("PROCESS_SCHED "), file); +++ break; +++ case EIHVN__SYSGEN_BIT: +++ fputs (_("SYSGEN "), file); +++ break; +++ case EIHVN__CLUSTERS_LOCKMGR_BIT: +++ fputs (_("CLUSTERS_LOCKMGR "), file); +++ break; +++ case EIHVN__LOGICAL_NAMES_BIT: +++ fputs (_("LOGICAL_NAMES "), file); +++ break; +++ case EIHVN__SECURITY_BIT: +++ fputs (_("SECURITY "), file); +++ break; +++ case EIHVN__IMAGE_ACTIVATOR_BIT: +++ fputs (_("IMAGE_ACTIVATOR "), file); +++ break; +++ case EIHVN__NETWORKS_BIT: +++ fputs (_("NETWORKS "), file); +++ break; +++ case EIHVN__COUNTERS_BIT: +++ fputs (_("COUNTERS "), file); +++ break; +++ case EIHVN__STABLE_BIT: +++ fputs (_("STABLE "), file); +++ break; +++ case EIHVN__MISC_BIT: +++ fputs (_("MISC "), file); +++ break; +++ case EIHVN__CPU_BIT: +++ fputs (_("CPU "), file); +++ break; +++ case EIHVN__VOLATILE_BIT: +++ fputs (_("VOLATILE "), file); +++ break; +++ case EIHVN__SHELL_BIT: +++ fputs (_("SHELL "), file); +++ break; +++ case EIHVN__POSIX_BIT: +++ fputs (_("POSIX "), file); +++ break; +++ case EIHVN__MULTI_PROCESSING_BIT: +++ fputs (_("MULTI_PROCESSING "), file); +++ break; +++ case EIHVN__GALAXY_BIT: +++ fputs (_("GALAXY "), file); +++ break; +++ default: +++ fputs (_("*unknown* "), file); +++ break; +++ } +++ fprintf (file, ": %u.%u\n", +++ (unsigned)bfd_getl16 (ver.major), +++ (unsigned)bfd_getl16 (ver.minor)); +++ } +++ } +++ +++ if (eiha_off != 0) +++ { +++ struct vms_eiha eiha; +++ +++ if (bfd_seek (abfd, (file_ptr) eiha_off, SEEK_SET) +++ || bfd_bread (&eiha, sizeof (eiha), abfd) != sizeof (eiha)) +++ { +++ fprintf (file, _("cannot read EIHA\n")); +++ return; +++ } +++ fprintf (file, _("Image activation: (size=%u)\n"), +++ (unsigned)bfd_getl32 (eiha.size)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" First address : 0x%08x 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiha.tfradr1_h), +++ (unsigned)bfd_getl32 (eiha.tfradr1)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" Second address: 0x%08x 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiha.tfradr2_h), +++ (unsigned)bfd_getl32 (eiha.tfradr2)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" Third address : 0x%08x 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiha.tfradr3_h), +++ (unsigned)bfd_getl32 (eiha.tfradr3)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" Fourth address: 0x%08x 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiha.tfradr4_h), +++ (unsigned)bfd_getl32 (eiha.tfradr4)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" Shared image : 0x%08x 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiha.inishr_h), +++ (unsigned)bfd_getl32 (eiha.inishr)); +++ } +++ if (eihi_off != 0) +++ { +++ struct vms_eihi eihi; +++ +++ if (bfd_seek (abfd, (file_ptr) eihi_off, SEEK_SET) +++ || bfd_bread (&eihi, sizeof (eihi), abfd) != sizeof (eihi)) +++ { +++ fprintf (file, _("cannot read EIHI\n")); +++ return; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _("Image identification: (major: %u, minor: %u)\n"), +++ (unsigned)bfd_getl32 (eihi.majorid), +++ (unsigned)bfd_getl32 (eihi.minorid)); +++ fprintf (file, _(" image name : %.*s\n"), +++ eihi.imgnam[0], eihi.imgnam + 1); +++ fprintf (file, _(" link time : %s\n"), +++ vms_time_to_str (eihi.linktime)); +++ fprintf (file, _(" image ident : %.*s\n"), +++ eihi.imgid[0], eihi.imgid + 1); +++ fprintf (file, _(" linker ident : %.*s\n"), +++ eihi.linkid[0], eihi.linkid + 1); +++ fprintf (file, _(" image build ident: %.*s\n"), +++ eihi.imgbid[0], eihi.imgbid + 1); +++ } +++ if (eihs_off != 0) +++ { +++ struct vms_eihs eihs; +++ +++ if (bfd_seek (abfd, (file_ptr) eihs_off, SEEK_SET) +++ || bfd_bread (&eihs, sizeof (eihs), abfd) != sizeof (eihs)) +++ { +++ fprintf (file, _("cannot read EIHS\n")); +++ return; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _("Image symbol & debug table: (major: %u, minor: %u)\n"), +++ (unsigned)bfd_getl32 (eihs.majorid), +++ (unsigned)bfd_getl32 (eihs.minorid)); +++ dst_vbn = bfd_getl32 (eihs.dstvbn); +++ dst_size = bfd_getl32 (eihs.dstsize); +++ /* xgettext:c-format */ +++ fprintf (file, _(" debug symbol table : vbn: %u, size: %u (0x%x)\n"), +++ dst_vbn, dst_size, dst_size); +++ gst_vbn = bfd_getl32 (eihs.gstvbn); +++ gst_size = bfd_getl32 (eihs.gstsize); +++ /* xgettext:c-format */ +++ fprintf (file, _(" global symbol table: vbn: %u, records: %u\n"), +++ gst_vbn, gst_size); +++ dmt_vbn = bfd_getl32 (eihs.dmtvbn); +++ dmt_size = bfd_getl32 (eihs.dmtsize); +++ /* xgettext:c-format */ +++ fprintf (file, _(" debug module table : vbn: %u, size: %u\n"), +++ dmt_vbn, dmt_size); +++ } +++ while (eisd_off != 0) +++ { +++ struct vms_eisd eisd; +++ unsigned int len; +++ +++ while (1) +++ { +++ if (bfd_seek (abfd, (file_ptr) eisd_off, SEEK_SET) +++ || bfd_bread (&eisd, sizeof (eisd), abfd) != sizeof (eisd)) +++ { +++ fprintf (file, _("cannot read EISD\n")); +++ return; +++ } +++ len = (unsigned)bfd_getl32 (eisd.eisdsize); +++ if (len != (unsigned)-1) +++ break; +++ +++ /* Next block. */ +++ eisd_off = (eisd_off + VMS_BLOCK_SIZE) & ~(VMS_BLOCK_SIZE - 1); +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _("Image section descriptor: (major: %u, minor: %u, " +++ "size: %u, offset: %u)\n"), +++ (unsigned)bfd_getl32 (eisd.majorid), +++ (unsigned)bfd_getl32 (eisd.minorid), +++ len, eisd_off); +++ if (len == 0) +++ break; +++ /* xgettext:c-format */ +++ fprintf (file, _(" section: base: 0x%08x%08x size: 0x%08x\n"), +++ (unsigned)bfd_getl32 (eisd.virt_addr + 4), +++ (unsigned)bfd_getl32 (eisd.virt_addr + 0), +++ (unsigned)bfd_getl32 (eisd.secsize)); +++ val = (unsigned)bfd_getl32 (eisd.flags); +++ fprintf (file, _(" flags: 0x%04x"), val); +++ if (val & EISD__M_GBL) +++ fprintf (file, " GBL"); +++ if (val & EISD__M_CRF) +++ fprintf (file, " CRF"); +++ if (val & EISD__M_DZRO) +++ fprintf (file, " DZRO"); +++ if (val & EISD__M_WRT) +++ fprintf (file, " WRT"); +++ if (val & EISD__M_INITALCODE) +++ fprintf (file, " INITALCODE"); +++ if (val & EISD__M_BASED) +++ fprintf (file, " BASED"); +++ if (val & EISD__M_FIXUPVEC) +++ fprintf (file, " FIXUPVEC"); +++ if (val & EISD__M_RESIDENT) +++ fprintf (file, " RESIDENT"); +++ if (val & EISD__M_VECTOR) +++ fprintf (file, " VECTOR"); +++ if (val & EISD__M_PROTECT) +++ fprintf (file, " PROTECT"); +++ if (val & EISD__M_LASTCLU) +++ fprintf (file, " LASTCLU"); +++ if (val & EISD__M_EXE) +++ fprintf (file, " EXE"); +++ if (val & EISD__M_NONSHRADR) +++ fprintf (file, " NONSHRADR"); +++ if (val & EISD__M_QUAD_LENGTH) +++ fprintf (file, " QUAD_LENGTH"); +++ if (val & EISD__M_ALLOC_64BIT) +++ fprintf (file, " ALLOC_64BIT"); +++ fprintf (file, "\n"); +++ if (val & EISD__M_FIXUPVEC) +++ { +++ eiaf_vbn = bfd_getl32 (eisd.vbn); +++ eiaf_size = bfd_getl32 (eisd.secsize); +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _(" vbn: %u, pfc: %u, matchctl: %u type: %u ("), +++ (unsigned)bfd_getl32 (eisd.vbn), +++ eisd.pfc, eisd.matchctl, eisd.type); +++ switch (eisd.type) +++ { +++ case EISD__K_NORMAL: +++ fputs (_("NORMAL"), file); +++ break; +++ case EISD__K_SHRFXD: +++ fputs (_("SHRFXD"), file); +++ break; +++ case EISD__K_PRVFXD: +++ fputs (_("PRVFXD"), file); +++ break; +++ case EISD__K_SHRPIC: +++ fputs (_("SHRPIC"), file); +++ break; +++ case EISD__K_PRVPIC: +++ fputs (_("PRVPIC"), file); +++ break; +++ case EISD__K_USRSTACK: +++ fputs (_("USRSTACK"), file); +++ break; +++ default: +++ fputs (_("*unknown*"), file); +++ break; +++ } +++ fputs (_(")\n"), file); +++ if (val & EISD__M_GBL) +++ /* xgettext:c-format */ +++ fprintf (file, _(" ident: 0x%08x, name: %.*s\n"), +++ (unsigned)bfd_getl32 (eisd.ident), +++ eisd.gblnam[0], eisd.gblnam + 1); +++ eisd_off += len; +++ } +++ +++ if (dmt_vbn != 0) +++ { +++ if (bfd_seek (abfd, (file_ptr) (dmt_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET)) +++ { +++ fprintf (file, _("cannot read DMT\n")); +++ return; +++ } +++ +++ fprintf (file, _("Debug module table:\n")); +++ +++ while (dmt_size > 0) +++ { +++ struct vms_dmt_header dmth; +++ unsigned int count; +++ +++ if (bfd_bread (&dmth, sizeof (dmth), abfd) != sizeof (dmth)) +++ { +++ fprintf (file, _("cannot read DMT header\n")); +++ return; +++ } +++ count = bfd_getl16 (dmth.psect_count); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _(" module offset: 0x%08x, size: 0x%08x, (%u psects)\n"), +++ (unsigned)bfd_getl32 (dmth.modbeg), +++ (unsigned)bfd_getl32 (dmth.size), count); +++ dmt_size -= sizeof (dmth); +++ while (count > 0) +++ { +++ struct vms_dmt_psect dmtp; +++ +++ if (bfd_bread (&dmtp, sizeof (dmtp), abfd) != sizeof (dmtp)) +++ { +++ fprintf (file, _("cannot read DMT psect\n")); +++ return; +++ } +++ /* xgettext:c-format */ +++ fprintf (file, _(" psect start: 0x%08x, length: %u\n"), +++ (unsigned)bfd_getl32 (dmtp.start), +++ (unsigned)bfd_getl32 (dmtp.length)); +++ count--; +++ dmt_size -= sizeof (dmtp); +++ } +++ } +++ } +++ +++ if (dst_vbn != 0) +++ { +++ if (bfd_seek (abfd, (file_ptr) (dst_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET)) +++ { +++ fprintf (file, _("cannot read DST\n")); +++ return; +++ } +++ +++ evax_bfd_print_dst (abfd, dst_size, file); +++ } +++ if (gst_vbn != 0) +++ { +++ if (bfd_seek (abfd, (file_ptr) (gst_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET)) +++ { +++ fprintf (file, _("cannot read GST\n")); +++ return; +++ } +++ +++ fprintf (file, _("Global symbol table:\n")); +++ evax_bfd_print_eobj (abfd, file); +++ } +++ if (eiaf_vbn != 0) +++ { +++ unsigned char *buf; +++ struct vms_eiaf *eiaf; +++ unsigned int qrelfixoff; +++ unsigned int lrelfixoff; +++ unsigned int qdotadroff; +++ unsigned int ldotadroff; +++ unsigned int shrimgcnt; +++ unsigned int shlstoff; +++ unsigned int codeadroff; +++ unsigned int lpfixoff; +++ unsigned int chgprtoff; +++ +++ buf = bfd_malloc (eiaf_size); +++ +++ if (bfd_seek (abfd, (file_ptr) (eiaf_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET) +++ || bfd_bread (buf, eiaf_size, abfd) != eiaf_size) +++ { +++ fprintf (file, _("cannot read EIHA\n")); +++ free (buf); +++ return; +++ } +++ eiaf = (struct vms_eiaf *)buf; +++ fprintf (file, +++ /* xgettext:c-format */ +++ _("Image activator fixup: (major: %u, minor: %u)\n"), +++ (unsigned)bfd_getl32 (eiaf->majorid), +++ (unsigned)bfd_getl32 (eiaf->minorid)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" iaflink : 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (eiaf->iaflink + 0), +++ (unsigned)bfd_getl32 (eiaf->iaflink + 4)); +++ /* xgettext:c-format */ +++ fprintf (file, _(" fixuplnk: 0x%08x %08x\n"), +++ (unsigned)bfd_getl32 (eiaf->fixuplnk + 0), +++ (unsigned)bfd_getl32 (eiaf->fixuplnk + 4)); +++ fprintf (file, _(" size : %u\n"), +++ (unsigned)bfd_getl32 (eiaf->size)); +++ fprintf (file, _(" flags: 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiaf->flags)); +++ qrelfixoff = bfd_getl32 (eiaf->qrelfixoff); +++ lrelfixoff = bfd_getl32 (eiaf->lrelfixoff); +++ /* xgettext:c-format */ +++ fprintf (file, _(" qrelfixoff: %5u, lrelfixoff: %5u\n"), +++ qrelfixoff, lrelfixoff); +++ qdotadroff = bfd_getl32 (eiaf->qdotadroff); +++ ldotadroff = bfd_getl32 (eiaf->ldotadroff); +++ /* xgettext:c-format */ +++ fprintf (file, _(" qdotadroff: %5u, ldotadroff: %5u\n"), +++ qdotadroff, ldotadroff); +++ codeadroff = bfd_getl32 (eiaf->codeadroff); +++ lpfixoff = bfd_getl32 (eiaf->lpfixoff); +++ /* xgettext:c-format */ +++ fprintf (file, _(" codeadroff: %5u, lpfixoff : %5u\n"), +++ codeadroff, lpfixoff); +++ chgprtoff = bfd_getl32 (eiaf->chgprtoff); +++ fprintf (file, _(" chgprtoff : %5u\n"), chgprtoff); +++ shrimgcnt = bfd_getl32 (eiaf->shrimgcnt); +++ shlstoff = bfd_getl32 (eiaf->shlstoff); +++ /* xgettext:c-format */ +++ fprintf (file, _(" shlstoff : %5u, shrimgcnt : %5u\n"), +++ shlstoff, shrimgcnt); +++ /* xgettext:c-format */ +++ fprintf (file, _(" shlextra : %5u, permctx : %5u\n"), +++ (unsigned)bfd_getl32 (eiaf->shlextra), +++ (unsigned)bfd_getl32 (eiaf->permctx)); +++ fprintf (file, _(" base_va : 0x%08x\n"), +++ (unsigned)bfd_getl32 (eiaf->base_va)); +++ fprintf (file, _(" lppsbfixoff: %5u\n"), +++ (unsigned)bfd_getl32 (eiaf->lppsbfixoff)); +++ +++ if (shlstoff) +++ { +++ struct vms_shl *shl = (struct vms_shl *)(buf + shlstoff); +++ unsigned int j; +++ +++ fprintf (file, _(" Shareable images:\n")); +++ for (j = 0; j < shrimgcnt; j++, shl++) +++ { +++ fprintf (file, +++ /* xgettext:c-format */ +++ _(" %u: size: %u, flags: 0x%02x, name: %.*s\n"), +++ j, shl->size, shl->flags, +++ shl->imgnam[0], shl->imgnam + 1); +++ } +++ } +++ if (qrelfixoff != 0) +++ { +++ fprintf (file, _(" quad-word relocation fixups:\n")); +++ evax_bfd_print_relocation_records (file, buf + qrelfixoff, 8); +++ } +++ if (lrelfixoff != 0) +++ { +++ fprintf (file, _(" long-word relocation fixups:\n")); +++ evax_bfd_print_relocation_records (file, buf + lrelfixoff, 4); +++ } +++ if (qdotadroff != 0) +++ { +++ fprintf (file, _(" quad-word .address reference fixups:\n")); +++ evax_bfd_print_address_fixups (file, buf + qdotadroff); +++ } +++ if (ldotadroff != 0) +++ { +++ fprintf (file, _(" long-word .address reference fixups:\n")); +++ evax_bfd_print_address_fixups (file, buf + ldotadroff); +++ } +++ if (codeadroff != 0) +++ { +++ fprintf (file, _(" Code Address Reference Fixups:\n")); +++ evax_bfd_print_reference_fixups (file, buf + codeadroff); +++ } +++ if (lpfixoff != 0) +++ { +++ fprintf (file, _(" Linkage Pairs Reference Fixups:\n")); +++ evax_bfd_print_reference_fixups (file, buf + lpfixoff); +++ } +++ if (chgprtoff) +++ { +++ unsigned int count = (unsigned)bfd_getl32 (buf + chgprtoff); +++ struct vms_eicp *eicp = (struct vms_eicp *)(buf + chgprtoff + 4); +++ unsigned int j; +++ +++ fprintf (file, _(" Change Protection (%u entries):\n"), count); +++ for (j = 0; j < count; j++, eicp++) +++ { +++ unsigned int prot = bfd_getl32 (eicp->newprt); +++ fprintf (file, +++ /* xgettext:c-format */ +++ _(" base: 0x%08x %08x, size: 0x%08x, prot: 0x%08x "), +++ (unsigned)bfd_getl32 (eicp->baseva + 4), +++ (unsigned)bfd_getl32 (eicp->baseva + 0), +++ (unsigned)bfd_getl32 (eicp->size), +++ (unsigned)bfd_getl32 (eicp->newprt)); +++ switch (prot) +++ { +++ case PRT__C_NA: +++ fprintf (file, "NA"); +++ break; +++ case PRT__C_RESERVED: +++ fprintf (file, "RES"); +++ break; +++ case PRT__C_KW: +++ fprintf (file, "KW"); +++ break; +++ case PRT__C_KR: +++ fprintf (file, "KR"); +++ break; +++ case PRT__C_UW: +++ fprintf (file, "UW"); +++ break; +++ case PRT__C_EW: +++ fprintf (file, "EW"); +++ break; +++ case PRT__C_ERKW: +++ fprintf (file, "ERKW"); +++ break; +++ case PRT__C_ER: +++ fprintf (file, "ER"); +++ break; +++ case PRT__C_SW: +++ fprintf (file, "SW"); +++ break; +++ case PRT__C_SREW: +++ fprintf (file, "SREW"); +++ break; +++ case PRT__C_SRKW: +++ fprintf (file, "SRKW"); +++ break; +++ case PRT__C_SR: +++ fprintf (file, "SR"); +++ break; +++ case PRT__C_URSW: +++ fprintf (file, "URSW"); +++ break; +++ case PRT__C_UREW: +++ fprintf (file, "UREW"); +++ break; +++ case PRT__C_URKW: +++ fprintf (file, "URKW"); +++ break; +++ case PRT__C_UR: +++ fprintf (file, "UR"); +++ break; +++ default: +++ fputs ("??", file); +++ break; +++ } +++ fputc ('\n', file); +++ } +++ } +++ free (buf); +++ } +++} +++ +++static bfd_boolean +++vms_bfd_print_private_bfd_data (bfd *abfd, void *ptr) +++{ +++ FILE *file = (FILE *)ptr; +++ +++ if (bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC)) +++ evax_bfd_print_image (abfd, file); +++ else +++ { +++ if (bfd_seek (abfd, 0, SEEK_SET)) +++ return FALSE; +++ evax_bfd_print_eobj (abfd, file); +++ } +++ return TRUE; +++} +++ +++/* Linking. */ +++ +++/* Slurp ETIR/EDBG/ETBT VMS object records. */ +++ +++static bfd_boolean +++sw_64_vms_read_sections_content (bfd *abfd, struct bfd_link_info *info) +++{ +++ asection *cur_section; +++ file_ptr cur_offset; +++ asection *dst_section; +++ file_ptr dst_offset; +++ +++ if (bfd_seek (abfd, 0, SEEK_SET) != 0) +++ return FALSE; +++ +++ cur_section = NULL; +++ cur_offset = 0; +++ +++ dst_section = PRIV (dst_section); +++ dst_offset = 0; +++ if (info) +++ { +++ if (info->strip == strip_all || info->strip == strip_debugger) +++ { +++ /* Discard the DST section. */ +++ dst_offset = 0; +++ dst_section = NULL; +++ } +++ else if (dst_section) +++ { +++ dst_offset = dst_section->output_offset; +++ dst_section = dst_section->output_section; +++ } +++ } +++ +++ while (1) +++ { +++ int type; +++ bfd_boolean res; +++ +++ type = _bfd_vms_get_object_record (abfd); +++ if (type < 0) +++ { +++ vms_debug2 ((2, "next_record failed\n")); +++ return FALSE; +++ } +++ switch (type) +++ { +++ case EOBJ__C_ETIR: +++ PRIV (image_section) = cur_section; +++ PRIV (image_offset) = cur_offset; +++ res = _bfd_vms_slurp_etir (abfd, info); +++ cur_section = PRIV (image_section); +++ cur_offset = PRIV (image_offset); +++ break; +++ case EOBJ__C_EDBG: +++ case EOBJ__C_ETBT: +++ if (dst_section == NULL) +++ continue; +++ PRIV (image_section) = dst_section; +++ PRIV (image_offset) = dst_offset; +++ res = _bfd_vms_slurp_etir (abfd, info); +++ dst_offset = PRIV (image_offset); +++ break; +++ case EOBJ__C_EEOM: +++ return TRUE; +++ default: +++ continue; +++ } +++ if (!res) +++ { +++ vms_debug2 ((2, "slurp eobj type %d failed\n", type)); +++ return FALSE; +++ } +++ } +++} +++ +++static int +++sw_64_vms_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED, +++ struct bfd_link_info *info ATTRIBUTE_UNUSED) +++{ +++ return 0; +++} +++ +++/* Add a linkage pair fixup at address SECT + OFFSET to SHLIB. */ +++ +++static void +++sw_64_vms_add_fixup_lp (struct bfd_link_info *info, bfd *src, bfd *shlib) +++{ +++ struct sw_64_vms_shlib_el *sl; +++ asection *sect = PRIV2 (src, image_section); +++ file_ptr offset = PRIV2 (src, image_offset); +++ +++ sl = &VEC_EL (sw_64_vms_link_hash (info)->shrlibs, +++ struct sw_64_vms_shlib_el, PRIV2 (shlib, shr_index)); +++ sl->has_fixups = TRUE; +++ VEC_APPEND_EL (sl->lp, bfd_vma, +++ sect->output_section->vma + sect->output_offset + offset); +++ sect->output_section->flags |= SEC_RELOC; +++} +++ +++/* Add a code address fixup at address SECT + OFFSET to SHLIB. */ +++ +++static void +++sw_64_vms_add_fixup_ca (struct bfd_link_info *info, bfd *src, bfd *shlib) +++{ +++ struct sw_64_vms_shlib_el *sl; +++ asection *sect = PRIV2 (src, image_section); +++ file_ptr offset = PRIV2 (src, image_offset); +++ +++ sl = &VEC_EL (sw_64_vms_link_hash (info)->shrlibs, +++ struct sw_64_vms_shlib_el, PRIV2 (shlib, shr_index)); +++ sl->has_fixups = TRUE; +++ VEC_APPEND_EL (sl->ca, bfd_vma, +++ sect->output_section->vma + sect->output_offset + offset); +++ sect->output_section->flags |= SEC_RELOC; +++} +++ +++/* Add a quad word relocation fixup at address SECT + OFFSET to SHLIB. */ +++ +++static void +++sw_64_vms_add_fixup_qr (struct bfd_link_info *info, bfd *src, +++ bfd *shlib, bfd_vma vec) +++{ +++ struct sw_64_vms_shlib_el *sl; +++ struct sw_64_vms_vma_ref *r; +++ asection *sect = PRIV2 (src, image_section); +++ file_ptr offset = PRIV2 (src, image_offset); +++ +++ sl = &VEC_EL (sw_64_vms_link_hash (info)->shrlibs, +++ struct sw_64_vms_shlib_el, PRIV2 (shlib, shr_index)); +++ sl->has_fixups = TRUE; +++ r = VEC_APPEND (sl->qr, struct sw_64_vms_vma_ref); +++ r->vma = sect->output_section->vma + sect->output_offset + offset; +++ r->ref = vec; +++ sect->output_section->flags |= SEC_RELOC; +++} +++ +++static void +++sw_64_vms_add_fixup_lr (struct bfd_link_info *info ATTRIBUTE_UNUSED, +++ unsigned int shr ATTRIBUTE_UNUSED, +++ bfd_vma vec ATTRIBUTE_UNUSED) +++{ +++ /* Not yet supported. */ +++ abort (); +++} +++ +++/* Add relocation. FIXME: Not yet emitted. */ +++ +++static void +++sw_64_vms_add_lw_reloc (struct bfd_link_info *info ATTRIBUTE_UNUSED) +++{ +++} +++ +++static void +++sw_64_vms_add_qw_reloc (struct bfd_link_info *info ATTRIBUTE_UNUSED) +++{ +++} +++ +++static struct bfd_hash_entry * +++sw_64_vms_link_hash_newfunc (struct bfd_hash_entry *entry, +++ struct bfd_hash_table *table, +++ const char *string) +++{ +++ struct sw_64_vms_link_hash_entry *ret = +++ (struct sw_64_vms_link_hash_entry *) entry; +++ +++ /* Allocate the structure if it has not already been allocated by a +++ subclass. */ +++ if (ret == NULL) +++ ret = ((struct sw_64_vms_link_hash_entry *) +++ bfd_hash_allocate (table, +++ sizeof (struct sw_64_vms_link_hash_entry))); +++ if (ret == NULL) +++ return NULL; +++ +++ /* Call the allocation method of the superclass. */ +++ ret = ((struct sw_64_vms_link_hash_entry *) +++ _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret, +++ table, string)); +++ +++ ret->sym = NULL; +++ +++ return (struct bfd_hash_entry *) ret; +++} +++ +++/* Create an Sw_64/VMS link hash table. */ +++ +++static struct bfd_link_hash_table * +++sw_64_vms_bfd_link_hash_table_create (bfd *abfd) +++{ +++ struct sw_64_vms_link_hash_table *ret; +++ bfd_size_type amt = sizeof (struct sw_64_vms_link_hash_table); +++ +++ ret = (struct sw_64_vms_link_hash_table *) bfd_malloc (amt); +++ if (ret == NULL) +++ return NULL; +++ if (!_bfd_link_hash_table_init (&ret->root, abfd, +++ sw_64_vms_link_hash_newfunc, +++ sizeof (struct sw_64_vms_link_hash_entry))) +++ { +++ free (ret); +++ return NULL; +++ } +++ +++ VEC_INIT (ret->shrlibs); +++ ret->fixup = NULL; +++ +++ return &ret->root; +++} +++ +++static bfd_boolean +++sw_64_vms_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) +++{ +++ unsigned int i; +++ +++ for (i = 0; i < PRIV (gsd_sym_count); i++) +++ { +++ struct vms_symbol_entry *e = PRIV (syms)[i]; +++ struct sw_64_vms_link_hash_entry *h; +++ struct bfd_link_hash_entry *h_root; +++ asymbol sym; +++ +++ if (!sw_64_vms_convert_symbol (abfd, e, &sym)) +++ return FALSE; +++ +++ if ((e->flags & EGSY__V_DEF) && abfd->selective_search) +++ { +++ /* In selective_search mode, only add definition that are +++ required. */ +++ h = (struct sw_64_vms_link_hash_entry *)bfd_link_hash_lookup +++ (info->hash, sym.name, FALSE, FALSE, FALSE); +++ if (h == NULL || h->root.type != bfd_link_hash_undefined) +++ continue; +++ } +++ else +++ h = NULL; +++ +++ h_root = (struct bfd_link_hash_entry *) h; +++ if (!_bfd_generic_link_add_one_symbol (info, abfd, sym.name, sym.flags, +++ sym.section, sym.value, NULL, +++ FALSE, FALSE, &h_root)) +++ return FALSE; +++ h = (struct sw_64_vms_link_hash_entry *) h_root; +++ +++ if ((e->flags & EGSY__V_DEF) +++ && h->sym == NULL +++ && abfd->xvec == info->output_bfd->xvec) +++ h->sym = e; +++ } +++ +++ if (abfd->flags & DYNAMIC) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ +++ /* We do not want to include any of the sections in a dynamic +++ object in the output file. See comment in elflink.c. */ +++ bfd_section_list_clear (abfd); +++ +++ shlib = VEC_APPEND (sw_64_vms_link_hash (info)->shrlibs, +++ struct sw_64_vms_shlib_el); +++ shlib->abfd = abfd; +++ VEC_INIT (shlib->ca); +++ VEC_INIT (shlib->lp); +++ VEC_INIT (shlib->qr); +++ PRIV (shr_index) = VEC_COUNT (sw_64_vms_link_hash (info)->shrlibs) - 1; +++ } +++ +++ return TRUE; +++} +++ +++static bfd_boolean +++sw_64_vms_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info) +++{ +++ int pass; +++ struct bfd_link_hash_entry **pundef; +++ struct bfd_link_hash_entry **next_pundef; +++ +++ /* We only accept VMS libraries. */ +++ if (info->output_bfd->xvec != abfd->xvec) +++ { +++ bfd_set_error (bfd_error_wrong_format); +++ return FALSE; +++ } +++ +++ /* The archive_pass field in the archive itself is used to +++ initialize PASS, since we may search the same archive multiple +++ times. */ +++ pass = ++abfd->archive_pass; +++ +++ /* Look through the list of undefined symbols. */ +++ for (pundef = &info->hash->undefs; *pundef != NULL; pundef = next_pundef) +++ { +++ struct bfd_link_hash_entry *h; +++ symindex symidx; +++ bfd *element; +++ bfd *orig_element; +++ +++ h = *pundef; +++ next_pundef = &(*pundef)->u.undef.next; +++ +++ /* When a symbol is defined, it is not necessarily removed from +++ the list. */ +++ if (h->type != bfd_link_hash_undefined +++ && h->type != bfd_link_hash_common) +++ { +++ /* Remove this entry from the list, for general cleanliness +++ and because we are going to look through the list again +++ if we search any more libraries. We can't remove the +++ entry if it is the tail, because that would lose any +++ entries we add to the list later on. */ +++ if (*pundef != info->hash->undefs_tail) +++ { +++ *pundef = *next_pundef; +++ next_pundef = pundef; +++ } +++ continue; +++ } +++ +++ /* Look for this symbol in the archive hash table. */ +++ symidx = _bfd_vms_lib_find_symbol (abfd, h->root.string); +++ if (symidx == BFD_NO_MORE_SYMBOLS) +++ { +++ /* Nothing in this slot. */ +++ continue; +++ } +++ +++ element = bfd_get_elt_at_index (abfd, symidx); +++ if (element == NULL) +++ return FALSE; +++ +++ if (element->archive_pass == -1 || element->archive_pass == pass) +++ { +++ /* Next symbol if this archive is wrong or already handled. */ +++ continue; +++ } +++ +++ if (! bfd_check_format (element, bfd_object)) +++ { +++ element->archive_pass = -1; +++ return FALSE; +++ } +++ +++ orig_element = element; +++ if (bfd_is_thin_archive (abfd)) +++ { +++ element = _bfd_vms_lib_get_imagelib_file (element); +++ if (element == NULL || !bfd_check_format (element, bfd_object)) +++ { +++ orig_element->archive_pass = -1; +++ return FALSE; +++ } +++ } +++ +++ /* Unlike the generic linker, we know that this element provides +++ a definition for an undefined symbol and we know that we want +++ to include it. We don't need to check anything. */ +++ if (!(*info->callbacks +++ ->add_archive_element) (info, element, h->root.string, &element)) +++ continue; +++ if (!sw_64_vms_link_add_object_symbols (element, info)) +++ return FALSE; +++ +++ orig_element->archive_pass = pass; +++ } +++ +++ return TRUE; +++} +++ +++static bfd_boolean +++sw_64_vms_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info) +++{ +++ switch (bfd_get_format (abfd)) +++ { +++ case bfd_object: +++ vms_debug2 ((2, "vms_link_add_symbols for object %s\n", +++ abfd->filename)); +++ return sw_64_vms_link_add_object_symbols (abfd, info); +++ break; +++ case bfd_archive: +++ vms_debug2 ((2, "vms_link_add_symbols for archive %s\n", +++ abfd->filename)); +++ return sw_64_vms_link_add_archive_symbols (abfd, info); +++ break; +++ default: +++ bfd_set_error (bfd_error_wrong_format); +++ return FALSE; +++ } +++} +++ +++static bfd_boolean +++sw_64_vms_build_fixups (struct bfd_link_info *info) +++{ +++ struct sw_64_vms_link_hash_table *t = sw_64_vms_link_hash (info); +++ unsigned char *content; +++ unsigned int i; +++ unsigned int sz = 0; +++ unsigned int lp_sz = 0; +++ unsigned int ca_sz = 0; +++ unsigned int qr_sz = 0; +++ unsigned int shrimg_cnt = 0; +++ unsigned int chgprt_num = 0; +++ unsigned int chgprt_sz = 0; +++ struct vms_eiaf *eiaf; +++ unsigned int off; +++ asection *sec; +++ +++ /* Shared libraries. */ +++ for (i = 0; i < VEC_COUNT (t->shrlibs); i++) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ +++ shlib = &VEC_EL (t->shrlibs, struct sw_64_vms_shlib_el, i); +++ +++ if (!shlib->has_fixups) +++ continue; +++ +++ shrimg_cnt++; +++ +++ if (VEC_COUNT (shlib->ca) > 0) +++ { +++ /* Header + entries. */ +++ ca_sz += 8; +++ ca_sz += VEC_COUNT (shlib->ca) * 4; +++ } +++ if (VEC_COUNT (shlib->lp) > 0) +++ { +++ /* Header + entries. */ +++ lp_sz += 8; +++ lp_sz += VEC_COUNT (shlib->lp) * 4; +++ } +++ if (VEC_COUNT (shlib->qr) > 0) +++ { +++ /* Header + entries. */ +++ qr_sz += 8; +++ qr_sz += VEC_COUNT (shlib->qr) * 8; +++ } +++ } +++ /* Add markers. */ +++ if (ca_sz > 0) +++ ca_sz += 8; +++ if (lp_sz > 0) +++ lp_sz += 8; +++ if (qr_sz > 0) +++ qr_sz += 8; +++ +++ /* Finish now if there is no content. */ +++ if (ca_sz + lp_sz + qr_sz == 0) +++ return TRUE; +++ +++ /* Add an eicp entry for the fixup itself. */ +++ chgprt_num = 1; +++ for (sec = info->output_bfd->sections; sec != NULL; sec = sec->next) +++ { +++ /* This isect could be made RO or EXE after relocations are applied. */ +++ if ((sec->flags & SEC_RELOC) != 0 +++ && (sec->flags & (SEC_CODE | SEC_READONLY)) != 0) +++ chgprt_num++; +++ } +++ chgprt_sz = 4 + chgprt_num * sizeof (struct vms_eicp); +++ +++ /* Allocate section content (round-up size) */ +++ sz = sizeof (struct vms_eiaf) + shrimg_cnt * sizeof (struct vms_shl) +++ + ca_sz + lp_sz + qr_sz + chgprt_sz; +++ sz = (sz + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1); +++ content = bfd_zalloc (info->output_bfd, sz); +++ if (content == NULL) +++ return FALSE; +++ +++ sec = sw_64_vms_link_hash (info)->fixup; +++ sec->contents = content; +++ sec->size = sz; +++ +++ eiaf = (struct vms_eiaf *)content; +++ off = sizeof (struct vms_eiaf); +++ bfd_putl32 (0, eiaf->majorid); +++ bfd_putl32 (0, eiaf->minorid); +++ bfd_putl32 (0, eiaf->iaflink); +++ bfd_putl32 (0, eiaf->fixuplnk); +++ bfd_putl32 (sizeof (struct vms_eiaf), eiaf->size); +++ bfd_putl32 (0, eiaf->flags); +++ bfd_putl32 (0, eiaf->qrelfixoff); +++ bfd_putl32 (0, eiaf->lrelfixoff); +++ bfd_putl32 (0, eiaf->qdotadroff); +++ bfd_putl32 (0, eiaf->ldotadroff); +++ bfd_putl32 (0, eiaf->codeadroff); +++ bfd_putl32 (0, eiaf->lpfixoff); +++ bfd_putl32 (0, eiaf->chgprtoff); +++ bfd_putl32 (shrimg_cnt ? off : 0, eiaf->shlstoff); +++ bfd_putl32 (shrimg_cnt, eiaf->shrimgcnt); +++ bfd_putl32 (0, eiaf->shlextra); +++ bfd_putl32 (0, eiaf->permctx); +++ bfd_putl32 (0, eiaf->base_va); +++ bfd_putl32 (0, eiaf->lppsbfixoff); +++ +++ if (shrimg_cnt) +++ { +++ shrimg_cnt = 0; +++ +++ /* Write shl. */ +++ for (i = 0; i < VEC_COUNT (t->shrlibs); i++) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ struct vms_shl *shl; +++ +++ shlib = &VEC_EL (t->shrlibs, struct sw_64_vms_shlib_el, i); +++ +++ if (!shlib->has_fixups) +++ continue; +++ +++ /* Renumber shared images. */ +++ PRIV2 (shlib->abfd, shr_index) = shrimg_cnt++; +++ +++ shl = (struct vms_shl *)(content + off); +++ bfd_putl32 (0, shl->baseva); +++ bfd_putl32 (0, shl->shlptr); +++ bfd_putl32 (0, shl->ident); +++ bfd_putl32 (0, shl->permctx); +++ shl->size = sizeof (struct vms_shl); +++ bfd_putl16 (0, shl->fill_1); +++ shl->flags = 0; +++ bfd_putl32 (0, shl->icb); +++ shl->imgnam[0] = strlen (PRIV2 (shlib->abfd, hdr_data.hdr_t_name)); +++ memcpy (shl->imgnam + 1, PRIV2 (shlib->abfd, hdr_data.hdr_t_name), +++ shl->imgnam[0]); +++ +++ off += sizeof (struct vms_shl); +++ } +++ +++ /* CA fixups. */ +++ if (ca_sz != 0) +++ { +++ bfd_putl32 (off, eiaf->codeadroff); +++ +++ for (i = 0; i < VEC_COUNT (t->shrlibs); i++) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ unsigned int j; +++ +++ shlib = &VEC_EL (t->shrlibs, struct sw_64_vms_shlib_el, i); +++ +++ if (VEC_COUNT (shlib->ca) == 0) +++ continue; +++ +++ bfd_putl32 (VEC_COUNT (shlib->ca), content + off); +++ bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4); +++ off += 8; +++ +++ for (j = 0; j < VEC_COUNT (shlib->ca); j++) +++ { +++ bfd_putl32 (VEC_EL (shlib->ca, bfd_vma, j) - t->base_addr, +++ content + off); +++ off += 4; +++ } +++ } +++ +++ bfd_putl32 (0, content + off); +++ bfd_putl32 (0, content + off + 4); +++ off += 8; +++ } +++ +++ /* LP fixups. */ +++ if (lp_sz != 0) +++ { +++ bfd_putl32 (off, eiaf->lpfixoff); +++ +++ for (i = 0; i < VEC_COUNT (t->shrlibs); i++) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ unsigned int j; +++ +++ shlib = &VEC_EL (t->shrlibs, struct sw_64_vms_shlib_el, i); +++ +++ if (VEC_COUNT (shlib->lp) == 0) +++ continue; +++ +++ bfd_putl32 (VEC_COUNT (shlib->lp), content + off); +++ bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4); +++ off += 8; +++ +++ for (j = 0; j < VEC_COUNT (shlib->lp); j++) +++ { +++ bfd_putl32 (VEC_EL (shlib->lp, bfd_vma, j) - t->base_addr, +++ content + off); +++ off += 4; +++ } +++ } +++ +++ bfd_putl32 (0, content + off); +++ bfd_putl32 (0, content + off + 4); +++ off += 8; +++ } +++ +++ /* QR fixups. */ +++ if (qr_sz != 0) +++ { +++ bfd_putl32 (off, eiaf->qdotadroff); +++ +++ for (i = 0; i < VEC_COUNT (t->shrlibs); i++) +++ { +++ struct sw_64_vms_shlib_el *shlib; +++ unsigned int j; +++ +++ shlib = &VEC_EL (t->shrlibs, struct sw_64_vms_shlib_el, i); +++ +++ if (VEC_COUNT (shlib->qr) == 0) +++ continue; +++ +++ bfd_putl32 (VEC_COUNT (shlib->qr), content + off); +++ bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4); +++ off += 8; +++ +++ for (j = 0; j < VEC_COUNT (shlib->qr); j++) +++ { +++ struct sw_64_vms_vma_ref *r; +++ r = &VEC_EL (shlib->qr, struct sw_64_vms_vma_ref, j); +++ bfd_putl32 (r->vma - t->base_addr, content + off); +++ bfd_putl32 (r->ref, content + off + 4); +++ off += 8; +++ } +++ } +++ +++ bfd_putl32 (0, content + off); +++ bfd_putl32 (0, content + off + 4); +++ off += 8; +++ } +++ } +++ +++ /* Write the change protection table. */ +++ bfd_putl32 (off, eiaf->chgprtoff); +++ bfd_putl32 (chgprt_num, content + off); +++ off += 4; +++ +++ for (sec = info->output_bfd->sections; sec != NULL; sec = sec->next) +++ { +++ struct vms_eicp *eicp; +++ unsigned int prot; +++ +++ if ((sec->flags & SEC_LINKER_CREATED) != 0 && +++ strcmp (sec->name, "$FIXUP$") == 0) +++ prot = PRT__C_UREW; +++ else if ((sec->flags & SEC_RELOC) != 0 +++ && (sec->flags & (SEC_CODE | SEC_READONLY)) != 0) +++ prot = PRT__C_UR; +++ else +++ continue; +++ +++ eicp = (struct vms_eicp *)(content + off); +++ bfd_putl64 (sec->vma - t->base_addr, eicp->baseva); +++ bfd_putl32 ((sec->size + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1), +++ eicp->size); +++ bfd_putl32 (prot, eicp->newprt); +++ off += sizeof (struct vms_eicp); +++ } +++ +++ return TRUE; +++} +++ +++/* Called by bfd_hash_traverse to fill the symbol table. +++ Return FALSE in case of failure. */ +++ +++static bfd_boolean +++sw_64_vms_link_output_symbol (struct bfd_hash_entry *bh, void *infov) +++{ +++ struct bfd_link_hash_entry *hc = (struct bfd_link_hash_entry *) bh; +++ struct bfd_link_info *info = (struct bfd_link_info *)infov; +++ struct sw_64_vms_link_hash_entry *h; +++ struct vms_symbol_entry *sym; +++ +++ if (hc->type == bfd_link_hash_warning) +++ { +++ hc = hc->u.i.link; +++ if (hc->type == bfd_link_hash_new) +++ return TRUE; +++ } +++ h = (struct sw_64_vms_link_hash_entry *) hc; +++ +++ switch (h->root.type) +++ { +++ case bfd_link_hash_undefined: +++ return TRUE; +++ case bfd_link_hash_new: +++ case bfd_link_hash_warning: +++ abort (); +++ case bfd_link_hash_undefweak: +++ return TRUE; +++ case bfd_link_hash_defined: +++ case bfd_link_hash_defweak: +++ { +++ asection *sec = h->root.u.def.section; +++ +++ /* FIXME: this is certainly a symbol from a dynamic library. */ +++ if (bfd_is_abs_section (sec)) +++ return TRUE; +++ +++ if (sec->owner->flags & DYNAMIC) +++ return TRUE; +++ } +++ break; +++ case bfd_link_hash_common: +++ break; +++ case bfd_link_hash_indirect: +++ return TRUE; +++ } +++ +++ /* Do not write not kept symbols. */ +++ if (info->strip == strip_some +++ && bfd_hash_lookup (info->keep_hash, h->root.root.string, +++ FALSE, FALSE) != NULL) +++ return TRUE; +++ +++ if (h->sym == NULL) +++ { +++ /* This symbol doesn't come from a VMS object. So we suppose it is +++ a data. */ +++ int len = strlen (h->root.root.string); +++ +++ sym = (struct vms_symbol_entry *)bfd_zalloc (info->output_bfd, +++ sizeof (*sym) + len); +++ if (sym == NULL) +++ abort (); +++ sym->namelen = len; +++ memcpy (sym->name, h->root.root.string, len); +++ sym->name[len] = 0; +++ sym->owner = info->output_bfd; +++ +++ sym->typ = EGSD__C_SYMG; +++ sym->data_type = 0; +++ sym->flags = EGSY__V_DEF | EGSY__V_REL; +++ sym->symbol_vector = h->root.u.def.value; +++ sym->section = h->root.u.def.section; +++ sym->value = h->root.u.def.value; +++ } +++ else +++ sym = h->sym; +++ +++ if (!add_symbol_entry (info->output_bfd, sym)) +++ return FALSE; +++ +++ return TRUE; +++} +++ +++static bfd_boolean +++sw_64_vms_bfd_final_link (bfd *abfd, struct bfd_link_info *info) +++{ +++ asection *o; +++ struct bfd_link_order *p; +++ bfd *sub; +++ asection *fixupsec; +++ bfd_vma base_addr; +++ bfd_vma last_addr; +++ asection *dst; +++ asection *dmt; +++ +++ if (bfd_link_relocatable (info)) +++ { +++ /* FIXME: we do not yet support relocatable link. It is not obvious +++ how to do it for debug infos. */ +++ (*info->callbacks->einfo)(_("%P: relocatable link is not supported\n")); +++ return FALSE; +++ } +++ +++ bfd_get_outsymbols (abfd) = NULL; +++ bfd_get_symcount (abfd) = 0; +++ +++ /* Mark all sections which will be included in the output file. */ +++ for (o = abfd->sections; o != NULL; o = o->next) +++ for (p = o->map_head.link_order; p != NULL; p = p->next) +++ if (p->type == bfd_indirect_link_order) +++ p->u.indirect.section->linker_mark = TRUE; +++ +++#if 0 +++ /* Handle all the link order information for the sections. */ +++ for (o = abfd->sections; o != NULL; o = o->next) +++ { +++ printf ("For section %s (at 0x%08x, flags=0x%08x):\n", +++ o->name, (unsigned)o->vma, (unsigned)o->flags); +++ +++ for (p = o->map_head.link_order; p != NULL; p = p->next) +++ { +++ printf (" at 0x%08x - 0x%08x: ", +++ (unsigned)p->offset, (unsigned)(p->offset + p->size - 1)); +++ switch (p->type) +++ { +++ case bfd_section_reloc_link_order: +++ case bfd_symbol_reloc_link_order: +++ printf (" section/symbol reloc\n"); +++ break; +++ case bfd_indirect_link_order: +++ printf (" section %s of %s\n", +++ p->u.indirect.section->name, +++ p->u.indirect.section->owner->filename); +++ break; +++ case bfd_data_link_order: +++ printf (" explicit data\n"); +++ break; +++ default: +++ printf (" *unknown* type %u\n", p->type); +++ break; +++ } +++ } +++ } +++#endif +++ +++ /* Generate the symbol table. */ +++ BFD_ASSERT (PRIV (syms) == NULL); +++ if (info->strip != strip_all) +++ bfd_hash_traverse (&info->hash->table, sw_64_vms_link_output_symbol, info); +++ +++ /* Find the entry point. */ +++ if (bfd_get_start_address (abfd) == 0) +++ { +++ bfd *startbfd = NULL; +++ +++ for (sub = info->input_bfds; sub != NULL; sub = sub->link.next) +++ { +++ /* Consider only VMS object files. */ +++ if (sub->xvec != abfd->xvec) +++ continue; +++ +++ if (!PRIV2 (sub, eom_data).eom_has_transfer) +++ continue; +++ if ((PRIV2 (sub, eom_data).eom_b_tfrflg & EEOM__M_WKTFR) && startbfd) +++ continue; +++ if (startbfd != NULL +++ && !(PRIV2 (sub, eom_data).eom_b_tfrflg & EEOM__M_WKTFR)) +++ { +++ (*info->callbacks->einfo) +++ /* xgettext:c-format */ +++ (_("%P: multiple entry points: in modules %pB and %pB\n"), +++ startbfd, sub); +++ continue; +++ } +++ startbfd = sub; +++ } +++ +++ if (startbfd) +++ { +++ unsigned int ps_idx = PRIV2 (startbfd, eom_data).eom_l_psindx; +++ bfd_vma tfradr = PRIV2 (startbfd, eom_data).eom_l_tfradr; +++ asection *sec; +++ +++ sec = PRIV2 (startbfd, sections)[ps_idx]; +++ +++ bfd_set_start_address +++ (abfd, sec->output_section->vma + sec->output_offset + tfradr); +++ } +++ } +++ +++ /* Set transfer addresses. */ +++ { +++ int i; +++ struct bfd_link_hash_entry *h; +++ +++ i = 0; +++ PRIV (transfer_address[i++]) = 0xffffffff00000340ULL; /* SYS$IMGACT */ +++ h = bfd_link_hash_lookup (info->hash, "LIB$INITIALIZE", FALSE, FALSE, TRUE); +++ if (h != NULL && h->type == bfd_link_hash_defined) +++ PRIV (transfer_address[i++]) = +++ sw_64_vms_get_sym_value (h->u.def.section, h->u.def.value); +++ PRIV (transfer_address[i++]) = bfd_get_start_address (abfd); +++ while (i < 4) +++ PRIV (transfer_address[i++]) = 0; +++ } +++ +++ /* Allocate contents. +++ Also compute the virtual base address. */ +++ base_addr = (bfd_vma)-1; +++ last_addr = 0; +++ for (o = abfd->sections; o != NULL; o = o->next) +++ { +++ if (o->flags & SEC_HAS_CONTENTS) +++ { +++ o->contents = bfd_alloc (abfd, o->size); +++ if (o->contents == NULL) +++ return FALSE; +++ } +++ if (o->flags & SEC_LOAD) +++ { +++ if (o->vma < base_addr) +++ base_addr = o->vma; +++ if (o->vma + o->size > last_addr) +++ last_addr = o->vma + o->size; +++ } +++ /* Clear the RELOC flags. Currently we don't support incremental +++ linking. We use the RELOC flag for computing the eicp entries. */ +++ o->flags &= ~SEC_RELOC; +++ } +++ +++ /* Create the fixup section. */ +++ fixupsec = bfd_make_section_anyway_with_flags +++ (info->output_bfd, "$FIXUP$", +++ SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_LINKER_CREATED); +++ if (fixupsec == NULL) +++ return FALSE; +++ last_addr = (last_addr + 0xffff) & ~0xffff; +++ fixupsec->vma = last_addr; +++ +++ sw_64_vms_link_hash (info)->fixup = fixupsec; +++ sw_64_vms_link_hash (info)->base_addr = base_addr; +++ +++ /* Create the DMT section, if necessary. */ +++ BFD_ASSERT (PRIV (dst_section) == NULL); +++ dst = bfd_get_section_by_name (abfd, "$DST$"); +++ if (dst != NULL && dst->size == 0) +++ dst = NULL; +++ if (dst != NULL) +++ { +++ PRIV (dst_section) = dst; +++ dmt = bfd_make_section_anyway_with_flags +++ (info->output_bfd, "$DMT$", +++ SEC_DEBUGGING | SEC_HAS_CONTENTS | SEC_LINKER_CREATED); +++ if (dmt == NULL) +++ return FALSE; +++ } +++ else +++ dmt = NULL; +++ +++ /* Read all sections from the inputs. */ +++ for (sub = info->input_bfds; sub != NULL; sub = sub->link.next) +++ { +++ if (sub->flags & DYNAMIC) +++ { +++ sw_64_vms_create_eisd_for_shared (abfd, sub); +++ continue; +++ } +++ +++ if (!sw_64_vms_read_sections_content (sub, info)) +++ return FALSE; +++ } +++ +++ /* Handle all the link order information for the sections. +++ Note: past this point, it is not possible to create new sections. */ +++ for (o = abfd->sections; o != NULL; o = o->next) +++ { +++ for (p = o->map_head.link_order; p != NULL; p = p->next) +++ { +++ switch (p->type) +++ { +++ case bfd_section_reloc_link_order: +++ case bfd_symbol_reloc_link_order: +++ abort (); +++ return FALSE; +++ case bfd_indirect_link_order: +++ /* Already done. */ +++ break; +++ default: +++ if (! _bfd_default_link_order (abfd, info, o, p)) +++ return FALSE; +++ break; +++ } +++ } +++ } +++ +++ /* Compute fixups. */ +++ if (!sw_64_vms_build_fixups (info)) +++ return FALSE; +++ +++ /* Compute the DMT. */ +++ if (dmt != NULL) +++ { +++ int pass; +++ unsigned char *contents = NULL; +++ +++ /* In pass 1, compute the size. In pass 2, write the DMT contents. */ +++ for (pass = 0; pass < 2; pass++) +++ { +++ unsigned int off = 0; +++ +++ /* For each object file (ie for each module). */ +++ for (sub = info->input_bfds; sub != NULL; sub = sub->link.next) +++ { +++ asection *sub_dst; +++ struct vms_dmt_header *dmth = NULL; +++ unsigned int psect_count; +++ +++ /* Skip this module if it has no DST. */ +++ sub_dst = PRIV2 (sub, dst_section); +++ if (sub_dst == NULL || sub_dst->size == 0) +++ continue; +++ +++ if (pass == 1) +++ { +++ /* Write the header. */ +++ dmth = (struct vms_dmt_header *)(contents + off); +++ bfd_putl32 (sub_dst->output_offset, dmth->modbeg); +++ bfd_putl32 (sub_dst->size, dmth->size); +++ } +++ +++ off += sizeof (struct vms_dmt_header); +++ psect_count = 0; +++ +++ /* For each section (ie for each psect). */ +++ for (o = sub->sections; o != NULL; o = o->next) +++ { +++ /* Only consider interesting sections. */ +++ if (!(o->flags & SEC_ALLOC)) +++ continue; +++ if (o->flags & SEC_LINKER_CREATED) +++ continue; +++ +++ if (pass == 1) +++ { +++ /* Write an entry. */ +++ struct vms_dmt_psect *dmtp; +++ +++ dmtp = (struct vms_dmt_psect *)(contents + off); +++ bfd_putl32 (o->output_offset + o->output_section->vma, +++ dmtp->start); +++ bfd_putl32 (o->size, dmtp->length); +++ psect_count++; +++ } +++ off += sizeof (struct vms_dmt_psect); +++ } +++ if (pass == 1) +++ bfd_putl32 (psect_count, dmth->psect_count); +++ } +++ +++ if (pass == 0) +++ { +++ contents = bfd_zalloc (info->output_bfd, off); +++ if (contents == NULL) +++ return FALSE; +++ dmt->contents = contents; +++ dmt->size = off; +++ } +++ else +++ { +++ BFD_ASSERT (off == dmt->size); +++ } +++ } +++ } +++ +++ return TRUE; +++} +++ +++/* Read the contents of a section. +++ buf points to a buffer of buf_size bytes to be filled with +++ section data (starting at offset into section) */ +++ +++static bfd_boolean +++sw_64_vms_get_section_contents (bfd *abfd, asection *section, +++ void *buf, file_ptr offset, +++ bfd_size_type count) +++{ +++ asection *sec; +++ +++ /* Image are easy. */ +++ if (bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC)) +++ return _bfd_generic_get_section_contents (abfd, section, +++ buf, offset, count); +++ +++ /* Safety check. */ +++ if (offset + count < count +++ || offset + count > section->size) +++ { +++ bfd_set_error (bfd_error_invalid_operation); +++ return FALSE; +++ } +++ +++ /* If the section is already in memory, just copy it. */ +++ if (section->flags & SEC_IN_MEMORY) +++ { +++ BFD_ASSERT (section->contents != NULL); +++ memcpy (buf, section->contents + offset, count); +++ return TRUE; +++ } +++ if (section->size == 0) +++ return TRUE; +++ +++ /* Alloc in memory and read ETIRs. */ +++ for (sec = abfd->sections; sec; sec = sec->next) +++ { +++ BFD_ASSERT (sec->contents == NULL); +++ +++ if (sec->size != 0 && (sec->flags & SEC_HAS_CONTENTS)) +++ { +++ sec->contents = bfd_alloc (abfd, sec->size); +++ if (sec->contents == NULL) +++ return FALSE; +++ } +++ } +++ if (!sw_64_vms_read_sections_content (abfd, NULL)) +++ return FALSE; +++ for (sec = abfd->sections; sec; sec = sec->next) +++ if (sec->contents) +++ sec->flags |= SEC_IN_MEMORY; +++ memcpy (buf, section->contents + offset, count); +++ return TRUE; +++} +++ +++ +++/* Set the format of a file being written. */ +++ +++static bfd_boolean +++sw_64_vms_mkobject (bfd * abfd) +++{ +++ const bfd_arch_info_type *arch; +++ +++ vms_debug2 ((1, "sw_64_vms_mkobject (%p)\n", abfd)); +++ +++ if (!vms_initialize (abfd)) +++ return FALSE; +++ +++ PRIV (recwr.buf) = bfd_alloc (abfd, MAX_OUTREC_SIZE); +++ if (PRIV (recwr.buf) == NULL) +++ return FALSE; +++ +++ arch = bfd_scan_arch ("sw_64"); +++ +++ if (arch == 0) +++ { +++ bfd_set_error (bfd_error_wrong_format); +++ return FALSE; +++ } +++ +++ abfd->arch_info = arch; +++ return TRUE; +++} +++ +++ +++/* 4.1, generic. */ +++ +++/* Called when the BFD is being closed to do any necessary cleanup. */ +++ +++static bfd_boolean +++vms_close_and_cleanup (bfd * abfd) +++{ +++ vms_debug2 ((1, "vms_close_and_cleanup (%p)\n", abfd)); +++ +++ if (abfd == NULL || abfd->tdata.any == NULL) +++ return TRUE; +++ +++ if (abfd->format == bfd_archive) +++ { +++ bfd_release (abfd, abfd->tdata.any); +++ abfd->tdata.any = NULL; +++ return TRUE; +++ } +++ +++ if (PRIV (recrd.buf) != NULL) +++ free (PRIV (recrd.buf)); +++ +++ if (PRIV (sections) != NULL) +++ free (PRIV (sections)); +++ +++ bfd_release (abfd, abfd->tdata.any); +++ abfd->tdata.any = NULL; +++ +++#ifdef VMS +++ if (abfd->direction == write_direction) +++ { +++ /* Last step on VMS is to convert the file to variable record length +++ format. */ +++ if (!bfd_cache_close (abfd)) +++ return FALSE; +++ if (!_bfd_vms_convert_to_var_unix_filename (abfd->filename)) +++ return FALSE; +++ } +++#endif +++ +++ return TRUE; +++} +++ +++/* Called when a new section is created. */ +++ +++static bfd_boolean +++vms_new_section_hook (bfd * abfd, asection *section) +++{ +++ bfd_size_type amt; +++ +++ vms_debug2 ((1, "vms_new_section_hook (%p, [%u]%s)\n", +++ abfd, section->index, section->name)); +++ +++ if (! bfd_set_section_alignment (abfd, section, 0)) +++ return FALSE; +++ +++ vms_debug2 ((7, "%u: %s\n", section->index, section->name)); +++ +++ amt = sizeof (struct vms_section_data_struct); +++ section->used_by_bfd = bfd_zalloc (abfd, amt); +++ if (section->used_by_bfd == NULL) +++ return FALSE; +++ +++ /* Create the section symbol. */ +++ return _bfd_generic_new_section_hook (abfd, section); +++} +++ +++/* Part 4.5, symbols. */ +++ +++/* Print symbol to file according to how. how is one of +++ bfd_print_symbol_name just print the name +++ bfd_print_symbol_more print more (???) +++ bfd_print_symbol_all print all we know, which is not much right now :-). */ +++ +++static void +++vms_print_symbol (bfd * abfd, +++ void * file, +++ asymbol *symbol, +++ bfd_print_symbol_type how) +++{ +++ vms_debug2 ((1, "vms_print_symbol (%p, %p, %p, %d)\n", +++ abfd, file, symbol, how)); +++ +++ switch (how) +++ { +++ case bfd_print_symbol_name: +++ case bfd_print_symbol_more: +++ fprintf ((FILE *)file," %s", symbol->name); +++ break; +++ +++ case bfd_print_symbol_all: +++ { +++ const char *section_name = symbol->section->name; +++ +++ bfd_print_symbol_vandf (abfd, file, symbol); +++ +++ fprintf ((FILE *) file," %-8s %s", section_name, symbol->name); +++ } +++ break; +++ } +++} +++ +++/* Return information about symbol in ret. +++ +++ fill type, value and name +++ type: +++ A absolute +++ B bss segment symbol +++ C common symbol +++ D data segment symbol +++ f filename +++ t a static function symbol +++ T text segment symbol +++ U undefined +++ - debug. */ +++ +++static void +++vms_get_symbol_info (bfd * abfd ATTRIBUTE_UNUSED, +++ asymbol *symbol, +++ symbol_info *ret) +++{ +++ asection *sec; +++ +++ vms_debug2 ((1, "vms_get_symbol_info (%p, %p, %p)\n", abfd, symbol, ret)); +++ +++ sec = symbol->section; +++ +++ if (ret == NULL) +++ return; +++ +++ if (sec == NULL) +++ ret->type = 'U'; +++ else if (bfd_is_com_section (sec)) +++ ret->type = 'C'; +++ else if (bfd_is_abs_section (sec)) +++ ret->type = 'A'; +++ else if (bfd_is_und_section (sec)) +++ ret->type = 'U'; +++ else if (bfd_is_ind_section (sec)) +++ ret->type = 'I'; +++ else if ((symbol->flags & BSF_FUNCTION) +++ || (bfd_get_section_flags (abfd, sec) & SEC_CODE)) +++ ret->type = 'T'; +++ else if (bfd_get_section_flags (abfd, sec) & SEC_DATA) +++ ret->type = 'D'; +++ else if (bfd_get_section_flags (abfd, sec) & SEC_ALLOC) +++ ret->type = 'B'; +++ else +++ ret->type = '?'; +++ +++ if (ret->type != 'U') +++ ret->value = symbol->value + symbol->section->vma; +++ else +++ ret->value = 0; +++ ret->name = symbol->name; +++} +++ +++/* Return TRUE if the given symbol sym in the BFD abfd is +++ a compiler generated local label, else return FALSE. */ +++ +++static bfd_boolean +++vms_bfd_is_local_label_name (bfd * abfd ATTRIBUTE_UNUSED, +++ const char *name) +++{ +++ return name[0] == '$'; +++} +++ +++/* Part 4.7, writing an object file. */ +++ +++/* Sets the contents of the section section in BFD abfd to the data starting +++ in memory at LOCATION. The data is written to the output section starting +++ at offset offset for count bytes. +++ +++ Normally TRUE is returned, else FALSE. Possible error returns are: +++ o bfd_error_no_contents - The output section does not have the +++ SEC_HAS_CONTENTS attribute, so nothing can be written to it. +++ o and some more too */ +++ +++static bfd_boolean +++_bfd_vms_set_section_contents (bfd * abfd, +++ asection *section, +++ const void * location, +++ file_ptr offset, +++ bfd_size_type count) +++{ +++ if (section->contents == NULL) +++ { +++ section->contents = bfd_alloc (abfd, section->size); +++ if (section->contents == NULL) +++ return FALSE; +++ +++ memcpy (section->contents + offset, location, (size_t) count); +++ } +++ +++ return TRUE; +++} +++ +++/* Set the architecture and machine type in BFD abfd to arch and mach. +++ Find the correct pointer to a structure and insert it into the arch_info +++ pointer. */ +++ +++static bfd_boolean +++sw_64_vms_set_arch_mach (bfd *abfd, +++ enum bfd_architecture arch, unsigned long mach) +++{ +++ if (arch != bfd_arch_sw_64 +++ && arch != bfd_arch_unknown) +++ return FALSE; +++ +++ return bfd_default_set_arch_mach (abfd, arch, mach); +++} +++ +++/* Set section VMS flags. Clear NO_FLAGS and set FLAGS. */ +++ +++void +++bfd_vms_set_section_flags (bfd *abfd ATTRIBUTE_UNUSED, +++ asection *sec, flagword no_flags, flagword flags) +++{ +++ vms_section_data (sec)->no_flags = no_flags; +++ vms_section_data (sec)->flags = flags; +++} +++ +++struct vms_private_data_struct * +++bfd_vms_get_data (bfd *abfd) +++{ +++ return (struct vms_private_data_struct *)abfd->tdata.any; +++} +++ +++#define vms_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false +++#define vms_bfd_link_just_syms _bfd_generic_link_just_syms +++#define vms_bfd_copy_link_hash_symbol_type \ +++ _bfd_generic_copy_link_hash_symbol_type +++#define vms_bfd_is_group_section bfd_generic_is_group_section +++#define vms_bfd_discard_group bfd_generic_discard_group +++#define vms_section_already_linked _bfd_generic_section_already_linked +++#define vms_bfd_define_common_symbol bfd_generic_define_common_symbol +++#define vms_bfd_link_hide_symbol _bfd_generic_link_hide_symbol +++#define vms_bfd_define_start_stop bfd_generic_define_start_stop +++#define vms_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data +++ +++#define vms_bfd_copy_private_bfd_data _bfd_generic_bfd_copy_private_bfd_data +++#define vms_bfd_free_cached_info _bfd_generic_bfd_free_cached_info +++#define vms_bfd_copy_private_section_data _bfd_generic_bfd_copy_private_section_data +++#define vms_bfd_copy_private_symbol_data _bfd_generic_bfd_copy_private_symbol_data +++#define vms_bfd_set_private_flags _bfd_generic_bfd_set_private_flags +++#define vms_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data +++ +++/* Symbols table. */ +++#define sw_64_vms_make_empty_symbol _bfd_generic_make_empty_symbol +++#define sw_64_vms_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false +++#define sw_64_vms_print_symbol vms_print_symbol +++#define sw_64_vms_get_symbol_info vms_get_symbol_info +++#define sw_64_vms_get_symbol_version_string \ +++ _bfd_nosymbols_get_symbol_version_string +++ +++#define sw_64_vms_read_minisymbols _bfd_generic_read_minisymbols +++#define sw_64_vms_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol +++#define sw_64_vms_get_lineno _bfd_nosymbols_get_lineno +++#define sw_64_vms_find_inliner_info _bfd_nosymbols_find_inliner_info +++#define sw_64_vms_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol +++#define sw_64_vms_find_nearest_line _bfd_vms_find_nearest_line +++#define sw_64_vms_find_line _bfd_nosymbols_find_line +++#define sw_64_vms_bfd_is_local_label_name vms_bfd_is_local_label_name +++ +++/* Generic table. */ +++#define sw_64_vms_close_and_cleanup vms_close_and_cleanup +++#define sw_64_vms_bfd_free_cached_info vms_bfd_free_cached_info +++#define sw_64_vms_new_section_hook vms_new_section_hook +++#define sw_64_vms_set_section_contents _bfd_vms_set_section_contents +++#define sw_64_vms_get_section_contents_in_window _bfd_generic_get_section_contents_in_window +++ +++#define sw_64_vms_bfd_get_relocated_section_contents \ +++ bfd_generic_get_relocated_section_contents +++ +++#define sw_64_vms_bfd_relax_section bfd_generic_relax_section +++#define sw_64_vms_bfd_gc_sections bfd_generic_gc_sections +++#define sw_64_vms_bfd_lookup_section_flags bfd_generic_lookup_section_flags +++#define sw_64_vms_bfd_merge_sections bfd_generic_merge_sections +++#define sw_64_vms_bfd_is_group_section bfd_generic_is_group_section +++#define sw_64_vms_bfd_discard_group bfd_generic_discard_group +++#define sw_64_vms_section_already_linked \ +++ _bfd_generic_section_already_linked +++ +++#define sw_64_vms_bfd_define_common_symbol bfd_generic_define_common_symbol +++#define sw_64_vms_bfd_link_hide_symbol _bfd_generic_link_hide_symbol +++#define sw_64_vms_bfd_define_start_stop bfd_generic_define_start_stop +++#define sw_64_vms_bfd_link_just_syms _bfd_generic_link_just_syms +++#define sw_64_vms_bfd_copy_link_hash_symbol_type \ +++ _bfd_generic_copy_link_hash_symbol_type +++ +++#define sw_64_vms_bfd_link_split_section _bfd_generic_link_split_section +++ +++#define sw_64_vms_get_dynamic_symtab_upper_bound \ +++ _bfd_nodynamic_get_dynamic_symtab_upper_bound +++#define sw_64_vms_canonicalize_dynamic_symtab \ +++ _bfd_nodynamic_canonicalize_dynamic_symtab +++#define sw_64_vms_get_dynamic_reloc_upper_bound \ +++ _bfd_nodynamic_get_dynamic_reloc_upper_bound +++#define sw_64_vms_canonicalize_dynamic_reloc \ +++ _bfd_nodynamic_canonicalize_dynamic_reloc +++#define sw_64_vms_bfd_link_check_relocs _bfd_generic_link_check_relocs +++ +++const bfd_target sw_64_vms_vec = +++{ +++ "vms-sw_64", /* Name. */ +++ bfd_target_evax_flavour, +++ BFD_ENDIAN_LITTLE, /* Data byte order is little. */ +++ BFD_ENDIAN_LITTLE, /* Header byte order is little. */ +++ +++ (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS +++ | WP_TEXT | D_PAGED), /* Object flags. */ +++ (SEC_ALLOC | SEC_LOAD | SEC_RELOC +++ | SEC_READONLY | SEC_CODE | SEC_DATA +++ | SEC_HAS_CONTENTS | SEC_IN_MEMORY), /* Sect flags. */ +++ 0, /* symbol_leading_char. */ +++ ' ', /* ar_pad_char. */ +++ 15, /* ar_max_namelen. */ +++ 0, /* match priority. */ +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, +++ bfd_getl64, bfd_getl_signed_64, bfd_putl64, +++ bfd_getl32, bfd_getl_signed_32, bfd_putl32, +++ bfd_getl16, bfd_getl_signed_16, bfd_putl16, +++ +++ { /* bfd_check_format. */ +++ _bfd_dummy_target, +++ sw_64_vms_object_p, +++ _bfd_vms_lib_sw_64_archive_p, +++ _bfd_dummy_target +++ }, +++ { /* bfd_set_format. */ +++ _bfd_bool_bfd_false_error, +++ sw_64_vms_mkobject, +++ _bfd_vms_lib_sw_64_mkarchive, +++ _bfd_bool_bfd_false_error +++ }, +++ { /* bfd_write_contents. */ +++ _bfd_bool_bfd_false_error, +++ sw_64_vms_write_object_contents, +++ _bfd_vms_lib_write_archive_contents, +++ _bfd_bool_bfd_false_error +++ }, +++ +++ BFD_JUMP_TABLE_GENERIC (sw_64_vms), +++ BFD_JUMP_TABLE_COPY (vms), +++ BFD_JUMP_TABLE_CORE (_bfd_nocore), +++ BFD_JUMP_TABLE_ARCHIVE (_bfd_vms_lib), +++ BFD_JUMP_TABLE_SYMBOLS (sw_64_vms), +++ BFD_JUMP_TABLE_RELOCS (sw_64_vms), +++ BFD_JUMP_TABLE_WRITE (sw_64_vms), +++ BFD_JUMP_TABLE_LINK (sw_64_vms), +++ BFD_JUMP_TABLE_DYNAMIC (sw_64_vms), +++ +++ NULL, +++ +++ NULL +++}; ++diff -Nuar gdb-10.2/build.sh gdb-10.2/build.sh ++--- gdb-10.2/build.sh 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/build.sh 2025-04-16 17:06:51.932086800 +0800 ++@@ -0,0 +1,51 @@ +++#!/bin/sh +++ +++cd ../ +++ +++# step 1: install dependency package +++install_package() +++{ +++ if [ `dpkg -l | grep $1 | wc -l` -ne 0 ] +++ then +++ echo "package $1 already exists." +++ else +++ sudo apt-get install $1 -y +++ echo "package $1 installed successfully." +++ fi +++} +++ +++install_package texinfo +++install_package expat +++install_package libexpat1-dev +++install_package python2.7-dev +++ +++# step 2: install gdb +++build_gdb_release() +++{ +++ rm -rf build +++ mkdir build +++ current_dir=$(pwd) +++ cd build +++ CFLAGS="-D_SW64_ -DSCORE" CXXFLAGS="-D_SW64_ -DCORE" \ +++ ../gdb-10.2/configure --host=sw_64-sunway-linux-gnu --build=sw_64-sunway-linux-gnu --prefix=$current_dir/install --with-guile=no --with-python --with-expat +++ make -j$(nproc) +++ make install +++ cd ../ +++} +++ +++build_gdb_debug() +++{ +++ rm -rf build-debug +++ mkdir build-debug +++ current_dir=$(pwd) +++ cd build-debug +++ CFLAGS="-g3 -O0 -D_SW64_ -DSCORE" CXXFLAGS="-g3 -O0 -D_SW64_ -DCORE" \ +++ ../gdb/configure --host=sw_64-sunway-linux-gnu --build=sw_64-sunway-linux-gnu --prefix=$current_dir/install-debug --with-guile=no --with-python --with-expat +++ make -j$(nproc) +++ make install +++ cd ../ +++} +++ +++ +++build_gdb_release +++#build_gdb_debug ++diff -Nuar gdb-10.2/config.guess gdb-10.2/config.guess ++--- gdb-10.2/config.guess 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/config.guess 2025-04-16 17:06:51.932086800 +0800 ++@@ -925,6 +925,9 @@ ++ UNAME_MACHINE=aarch64_be ++ echo "$UNAME_MACHINE"-unknown-linux-"$LIBC" ++ exit ;; +++sw_64*:Linux:*:*) +++ echo ${UNAME_MACHINE}-unknown-linux-${LIBC} +++ exit ;; ++ alpha:Linux:*:*) ++ case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' /proc/cpuinfo 2>/dev/null` in ++ EV5) UNAME_MACHINE=alphaev5 ;; ++diff -Nuar gdb-10.2/config.sub gdb-10.2/config.sub ++--- gdb-10.2/config.sub 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/config.sub 2025-04-16 17:06:51.932086800 +0800 ++@@ -1161,6 +1161,7 @@ ++ | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] \ ++ | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] \ ++ | alphapca5[67] | alpha64pca5[67] \ +++ | sw_64 | sw_64sw6a | sw_64sw6b \ ++ | am33_2.0 \ ++ | amdgcn \ ++ | arc | arceb \ ++diff -Nuar gdb-10.2/gdb/ada-lang.c gdb-10.2/gdb/ada-lang.c ++--- gdb-10.2/gdb/ada-lang.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/ada-lang.c 2025-04-16 17:06:41.952086800 +0800 ++@@ -997,7 +997,7 @@ ++ int len = name.size (); ++ GROW_VECT (fold_buffer, fold_buffer_size, len + 1); ++ ++- if (name[0] == '\'') +++ if (!name.empty () && name[0] == '\'') ++ { ++ strncpy (fold_buffer, name.data () + 1, len - 2); ++ fold_buffer[len - 2] = '\000'; ++@@ -1006,8 +1006,9 @@ ++ { ++ int i; ++ ++- for (i = 0; i <= len; i += 1) +++ for (i = 0; i < len; i += 1) ++ fold_buffer[i] = tolower (name[i]); +++ fold_buffer[i] = '\0'; ++ } ++ ++ return fold_buffer; ++@@ -1157,7 +1158,7 @@ ++ i -= 1; ++ if (i > 1 && encoded[i] == '_' && encoded[i - 1] == '_') ++ len0 = i - 1; ++- else if (encoded[i] == '$') +++ else if (i >= 0 && encoded[i] == '$') ++ len0 = i; ++ } ++ ++@@ -13596,7 +13597,7 @@ ++ { ++ gdb::string_view user_name = lookup_name.name (); ++ ++- if (user_name[0] == '<') +++ if (!user_name.empty () && user_name[0] == '<') ++ { ++ if (user_name.back () == '>') ++ m_encoded_name ++diff -Nuar gdb-10.2/gdb/arch/sw_64.h gdb-10.2/gdb/arch/sw_64.h ++--- gdb-10.2/gdb/arch/sw_64.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/arch/sw_64.h 2025-04-16 17:06:51.932086800 +0800 ++@@ -0,0 +1,193 @@ +++/* Common target dependent code for GDB on SW systems. +++ Copyright (C) 1988-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#ifndef ARCH_SW_64_H +++#define ARCH_SW_64_H +++ +++#include "gdbsupport/tdesc.h" +++ +++/* Register numbers of various important registers. */ +++ +++enum gdb_regnum { +++ SW_A1_REGNUM = 0, /* first integer-like argument */ +++ SW_A4_REGNUM = 3, /* last integer-like argument */ +++ SW_AP_REGNUM = 11, +++ SW_IP_REGNUM = 12, +++ SW_SP_REGNUM = 13, /* Contains address of top of stack */ +++ SW_LR_REGNUM = 14, /* address to return to from a function call */ +++ SW_PC_REGNUM = 15, /* Contains program counter */ +++ /* F0..F7 are the fp registers for the (obsolete) FPA architecture. */ +++ SW_F0_REGNUM = 16, /* first floating point register */ +++ SW_F3_REGNUM = 19, /* last floating point argument register */ +++ SW_F7_REGNUM = 23, /* last floating point register */ +++ SW_FPS_REGNUM = 24, /* floating point status register */ +++ SW_PS_REGNUM = 25, /* Contains processor status */ +++ SW_WR0_REGNUM, /* WMMX data registers. */ +++ SW_WR15_REGNUM = SW_WR0_REGNUM + 15, +++ SW_WC0_REGNUM, /* WMMX control registers. */ +++ SW_WCSSF_REGNUM = SW_WC0_REGNUM + 2, +++ SW_WCASF_REGNUM = SW_WC0_REGNUM + 3, +++ SW_WC7_REGNUM = SW_WC0_REGNUM + 7, +++ SW_WCGR0_REGNUM, /* WMMX general purpose registers. */ +++ SW_WCGR3_REGNUM = SW_WCGR0_REGNUM + 3, +++ SW_WCGR7_REGNUM = SW_WCGR0_REGNUM + 7, +++ SW_D0_REGNUM, /* VFP double-precision registers. */ +++ SW_D31_REGNUM = SW_D0_REGNUM + 31, +++ SW_FPSCR_REGNUM, +++ +++ SW_NUM_REGS, +++ +++ /* Other useful registers. */ +++ SW_FP_REGNUM = 11, /* Frame register in SW code, if used. */ +++ THUMB_FP_REGNUM = 7, /* Frame register in Thumb code, if used. */ +++ SW_NUM_ARG_REGS = 4, +++ SW_LAST_ARG_REGNUM = SW_A4_REGNUM, +++ SW_NUM_FP_ARG_REGS = 4, +++ SW_LAST_FP_ARG_REGNUM = SW_F3_REGNUM +++}; +++ +++/* Enum describing the different kinds of breakpoints. */ +++enum sw_64_breakpoint_kinds +++{ +++ SW_BP_KIND_THUMB = 2, +++ SW_BP_KIND_THUMB2 = 3, +++ SW_BP_KIND_SW = 4, +++}; +++ +++/* Supported Arm FP hardware types. */ +++enum sw_64_fp_type { +++ SW_FP_TYPE_NONE = 0, +++ SW_FP_TYPE_VFPV2, +++ SW_FP_TYPE_VFPV3, +++ SW_FP_TYPE_IWMMXT, +++ SW_FP_TYPE_INVALID +++}; +++ +++/* Supported M-profile Arm types. */ +++enum sw_64_m_profile_type { +++ SW_M_TYPE_M_PROFILE, +++ SW_M_TYPE_VFP_D16, +++ SW_M_TYPE_WITH_FPA, +++ SW_M_TYPE_INVALID +++}; +++ +++/* Instruction condition field values. */ +++#define INST_EQ 0x0 +++#define INST_NE 0x1 +++#define INST_CS 0x2 +++#define INST_CC 0x3 +++#define INST_MI 0x4 +++#define INST_PL 0x5 +++#define INST_VS 0x6 +++#define INST_VC 0x7 +++#define INST_HI 0x8 +++#define INST_LS 0x9 +++#define INST_GE 0xa +++#define INST_LT 0xb +++#define INST_GT 0xc +++#define INST_LE 0xd +++#define INST_AL 0xe +++#define INST_NV 0xf +++ +++#define FLAG_N 0x80000000 +++#define FLAG_Z 0x40000000 +++#define FLAG_C 0x20000000 +++#define FLAG_V 0x10000000 +++ +++#define CPSR_T 0x20 +++ +++#define XPSR_T 0x01000000 +++ +++/* Size of registers. */ +++ +++#define SW_INT_REGISTER_SIZE 4 +++/* IEEE extended doubles are 80 bits. DWORD aligned they use 96 bits. */ +++#define SW_FP_REGISTER_SIZE 12 +++#define SW_VFP_REGISTER_SIZE 8 +++#define IWMMXT_VEC_REGISTER_SIZE 8 +++ +++/* Size of register sets. */ +++ +++/* r0-r12,sp,lr,pc,cpsr. */ +++#define SW_CORE_REGS_SIZE (17 * SW_INT_REGISTER_SIZE) +++/* f0-f8,fps. */ +++#define SW_FP_REGS_SIZE (8 * SW_FP_REGISTER_SIZE + SW_INT_REGISTER_SIZE) +++/* d0-d15,fpscr. */ +++#define SW_VFP2_REGS_SIZE (16 * SW_VFP_REGISTER_SIZE + SW_INT_REGISTER_SIZE) +++/* d0-d31,fpscr. */ +++#define SW_VFP3_REGS_SIZE (32 * SW_VFP_REGISTER_SIZE + SW_INT_REGISTER_SIZE) +++/* wR0-wR15,fpscr. */ +++#define IWMMXT_REGS_SIZE (16 * IWMMXT_VEC_REGISTER_SIZE \ +++ + 6 * SW_INT_REGISTER_SIZE) +++ +++/* Addresses for calling Thumb functions have the bit 0 set. +++ Here are some macros to test, set, or clear bit 0 of addresses. */ +++#define IS_THUMB_ADDR(addr) ((addr) & 1) +++#define MAKE_THUMB_ADDR(addr) ((addr) | 1) +++#define UNMAKE_THUMB_ADDR(addr) ((addr) & ~1) +++ +++/* Support routines for instruction parsing. */ +++#define submask(x) ((1L << ((x) + 1)) - 1) +++#define bits(obj,st,fn) (((obj) >> (st)) & submask ((fn) - (st))) +++#define bit(obj,st) (((obj) >> (st)) & 1) +++#define sbits(obj,st,fn) \ +++ ((long) (bits(obj,st,fn) | ((long) bit(obj,fn) * ~ submask (fn - st)))) +++#define BranchDest(addr,instr) \ +++ ((CORE_ADDR) (((unsigned long) (addr)) + 8 + (sbits (instr, 0, 23) << 2))) +++ +++/* Forward declaration. */ +++struct regcache; +++ +++/* Return the size in bytes of the complete Thumb instruction whose +++ first halfword is INST1. */ +++int thumb_insn_size (unsigned short inst1); +++ +++/* Returns true if the condition evaluates to true. */ +++int condition_true (unsigned long cond, unsigned long status_reg); +++ +++/* Return 1 if THIS_INSTR might change control flow, 0 otherwise. */ +++int sw_64_instruction_changes_pc (uint32_t this_instr); +++ +++/* Return 1 if the 16-bit Thumb instruction INST might change +++ control flow, 0 otherwise. */ +++int thumb_instruction_changes_pc (unsigned short inst); +++ +++/* Return 1 if the 32-bit Thumb instruction in INST1 and INST2 +++ might change control flow, 0 otherwise. */ +++int thumb2_instruction_changes_pc (unsigned short inst1, unsigned short inst2); +++ +++/* Advance the state of the IT block and return that state. */ +++int thumb_advance_itstate (unsigned int itstate); +++ +++/* Decode shifted register value. */ +++ +++unsigned long shifted_reg_val (struct regcache *regcache, +++ unsigned long inst, +++ int carry, +++ unsigned long pc_val, +++ unsigned long status_reg); +++ +++/* Create an Arm target description with the given FP hardware type. */ +++ +++target_desc *sw_64_create_target_description (sw_64_fp_type fp_type); +++ +++/* Create an Arm M-profile target description with the given hardware type. */ +++ +++target_desc *sw_64_create_mprofile_target_description (sw_64_m_profile_type m_type); +++ +++#endif /* ARCH_SW_H */ ++diff -Nuar gdb-10.2/gdb/cli/cli-cmds.c gdb-10.2/gdb/cli/cli-cmds.c ++--- gdb-10.2/gdb/cli/cli-cmds.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/cli/cli-cmds.c 2025-04-16 17:06:41.892086800 +0800 ++@@ -435,6 +435,11 @@ ++ } ++ } ++ +++#ifdef CRASH_MERGE +++static int crash_from_tty = 0; +++extern "C" void untrusted_file(FILE *, char *); +++#endif +++ ++ int ++ is_complete_command (struct cmd_list_element *c) ++ { ++@@ -654,8 +659,32 @@ ++ close (fd); ++ errno = save_errno; ++ } ++- else ++- opened.emplace (gdb_file_up (result), std::move (full_path)); +++#ifdef CRASH_MERGE +++ /* +++ * Only allow trusted versions of .gdbinit files to be +++ * sourced during session initialization. +++ */ +++ if (crash_from_tty == -1) +++ { +++ struct stat statbuf; +++ FILE *stream = result; +++ int _fd = fileno (stream); +++ if (fstat (_fd, &statbuf) < 0) +++ { +++ perror_with_name (full_path.get()); +++ fclose (stream); +++ return opened; +++ } +++ if (statbuf.st_uid != getuid () || (statbuf.st_mode & S_IWOTH)) +++ { +++ untrusted_file(NULL, full_path.get()); +++ fclose (stream); +++ return opened; +++ } +++ } +++#endif +++ opened.emplace (gdb_file_up (result), std::move (full_path)); +++ ++ ++ return opened; ++ } ++@@ -719,7 +748,11 @@ ++ If the source command was invoked interactively, throw an ++ error. Otherwise (e.g. if it was invoked by a script), ++ just emit a warning, rather than cause an error. */ +++#ifdef CRASH_MERGE +++ if (from_tty > 0) +++#else ++ if (from_tty) +++#endif ++ perror_with_name (file); ++ else ++ { ++@@ -743,7 +776,14 @@ ++ void ++ source_script (const char *file, int from_tty) ++ { +++#ifdef CRASH_MERGE +++ crash_from_tty = from_tty; +++#endif ++ source_script_with_search (file, from_tty, 0); +++#ifdef CRASH_MERGE +++ crash_from_tty = 0; +++#endif +++ ++ } ++ ++ static void ++diff -Nuar gdb-10.2/gdb/coffread.c gdb-10.2/gdb/coffread.c ++--- gdb-10.2/gdb/coffread.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/coffread.c 2025-04-16 17:06:41.952086800 +0800 ++@@ -159,6 +159,7 @@ ++ static unsigned long linetab_size; ++ ++ static char *stringtab = NULL; +++static long stringtab_length = 0; ++ ++ extern void stabsread_clear_cache (void); ++ ++@@ -1297,6 +1298,7 @@ ++ /* This is in target format (probably not very useful, and not ++ currently used), not host format. */ ++ memcpy (stringtab, lengthbuf, sizeof lengthbuf); +++ stringtab_length = length; ++ if (length == sizeof length) /* Empty table -- just the count. */ ++ return 0; ++ ++@@ -1316,8 +1318,9 @@ ++ ++ if (symbol_entry->_n._n_n._n_zeroes == 0) ++ { ++- /* FIXME: Probably should be detecting corrupt symbol files by ++- seeing whether offset points to within the stringtab. */ +++ if (symbol_entry->_n._n_n._n_offset > stringtab_length) +++ error (_("COFF Error: string table offset (%ld) outside string table (length %ld)"), +++ symbol_entry->_n._n_n._n_offset, stringtab_length); ++ result = stringtab + symbol_entry->_n._n_n._n_offset; ++ } ++ else ++diff -Nuar gdb-10.2/gdb/completer.c gdb-10.2/gdb/completer.c ++--- gdb-10.2/gdb/completer.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/completer.c 2025-04-16 17:06:41.922086800 +0800 ++@@ -2949,6 +2949,8 @@ ++ ++ /* How many items of MAX length can we fit in the screen window? */ ++ cols = gdb_complete_get_screenwidth (displayer); +++ rl_reset_screen_size(); +++ rl_get_screen_size(NULL, &cols); ++ max += 2; ++ limit = cols / max; ++ if (limit != 1 && (limit * max == cols)) ++diff -Nuar gdb-10.2/gdb/configure.host gdb-10.2/gdb/configure.host ++--- gdb-10.2/gdb/configure.host 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/configure.host 2025-04-16 17:06:51.932086800 +0800 ++@@ -60,6 +60,7 @@ ++ ++ aarch64*) gdb_host_cpu=aarch64 ;; ++ alpha*) gdb_host_cpu=alpha ;; +++sw_64*) gdb_host_cpu=sw_64 ;; ++ arm*) gdb_host_cpu=arm ;; ++ hppa*) gdb_host_cpu=pa ;; ++ i[34567]86*) gdb_host_cpu=i386 ;; ++@@ -165,7 +166,7 @@ ++ sparc-*-solaris2* | sparcv9-*-solaris2* | sparc64-*-solaris2*) ++ gdb_host=sol2 ++ ;; ++- +++sw_64*-*-linux*) gdb_host=sw_64-linux ;; ++ tilegx-*-linux*) gdb_host=linux ;; ++ ++ vax-*-netbsdelf* | vax-*-knetbsd*-gnu) ++diff -Nuar gdb-10.2/gdb/configure.nat gdb-10.2/gdb/configure.nat ++--- gdb-10.2/gdb/configure.nat 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/configure.nat 2025-04-16 17:06:51.932086800 +0800 ++@@ -1,5 +1,5 @@ ++ # ; -*- mode: sh ; -*- ++-# Copyright (C) 2013-2021 Free Software Foundation, Inc. +++# Copyright (C) 2013-2020 Free Software Foundation, Inc. ++ # ++ # This file is part of GDB. ++ # ++@@ -123,6 +123,18 @@ ++ ;; ++ esac ++ ;; +++ sw_64-linux) +++ case ${gdb_host_cpu} in +++ sw_64) +++ # Host: Little-endian Sw_64 running Linux +++ NATDEPFILES="${NATDEPFILES} linux-nat-trad.o sw_64-linux-nat.o nat/sw_64-linux-watch.o" +++ # doublest.c currently assumes some properties of FP arithmetic +++ # on the host which require this. +++ #MH_CFLAGS='-mieee' +++ MH_CFLAGS='-mieee' +++ ;; +++ esac +++ ;; ++ cygwin) ++ case ${gdb_host_cpu} in ++ i386) ++@@ -266,6 +278,11 @@ ++ NATDEPFILES="${NATDEPFILES} linux-nat-trad.o \ ++ mips-linux-nat.o nat/mips-linux-watch.o" ++ ;; +++ sw_64) +++ # Host: Linux/sw_64 +++ NATDEPFILES="${NATDEPFILES} linux-nat-trad.o \ +++ sw_64-linux-nat.o nat/sw_64-linux-watch.o" +++ ;; ++ pa) ++ # Host: Hewlett-Packard PA-RISC machine, running Linux ++ NATDEPFILES="${NATDEPFILES} hppa-linux-nat.o" ++diff -Nuar gdb-10.2/gdb/configure.tgt gdb-10.2/gdb/configure.tgt ++--- gdb-10.2/gdb/configure.tgt 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/configure.tgt 2025-04-16 17:06:51.932086800 +0800 ++@@ -94,6 +94,10 @@ ++ # Target: Tensilica Xtensa processors ++ cpu_obs="xtensa-tdep.o xtensa-config.o solib-svr4.o" ++ ;; +++sw_64*-*-*) +++ # Target: sw_64 +++ cpu_obs="sw_64-tdep.o" +++ ;; ++ ++ esac ++ ++@@ -146,6 +150,12 @@ ++ alpha-nbsd-tdep.o alpha-obsd-tdep.o nbsd-tdep.o" ++ ;; ++ +++sw_64*-*-linux*) +++ # Target: Little-endian sw_64 running Linux +++ gdb_target_obs="sw_64-mdebug-tdep.o sw_64-linux-tdep.o \ +++ linux-tdep.o solib-svr4.o linux-record.o" +++ ;; +++ ++ am33_2.0*-*-linux*) ++ # Target: Matsushita mn10300 (AM33) running Linux ++ gdb_target_obs="mn10300-tdep.o mn10300-linux-tdep.o linux-tdep.o \ ++diff -Nuar gdb-10.2/gdb/c-typeprint.c gdb-10.2/gdb/c-typeprint.c ++--- gdb-10.2/gdb/c-typeprint.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/c-typeprint.c 2025-04-16 17:06:41.922086800 +0800 ++@@ -1202,6 +1202,9 @@ ++ = podata->end_bitpos ++ - TYPE_LENGTH (type->field (i).type ()) * TARGET_CHAR_BIT; ++ } +++ else if (strlen(TYPE_FIELD_NAME (type, i)) == 0) +++ /* crash: Print details for unnamed struct and union. */ +++ newshow = show; ++ ++ c_print_type_1 (type->field (i).type (), ++ TYPE_FIELD_NAME (type, i), ++diff -Nuar gdb-10.2/gdb/data-directory/Makefile.in gdb-10.2/gdb/data-directory/Makefile.in ++--- gdb-10.2/gdb/data-directory/Makefile.in 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdb/data-directory/Makefile.in 2025-04-16 17:06:51.932086800 +0800 ++@@ -1,4 +1,4 @@ ++-# Copyright (C) 2010-2021 Free Software Foundation, Inc. +++# Copyright (C) 2010-2020 Free Software Foundation, Inc. ++ ++ # Makefile for building a staged copy of the data-directory. ++ # This file is part of GDB. ++@@ -61,7 +61,8 @@ ++ s390-linux.xml \ ++ s390x-linux.xml \ ++ sparc-linux.xml \ ++- sparc64-linux.xml +++ sparc64-linux.xml \ +++ sw_64-linux.xml ++ ++ SYSCALLS_FILES = gdb-syscalls.dtd freebsd.xml netbsd.xml $(GEN_SYSCALLS_FILES) ++ ++diff -Nuar gdb-10.2/gdb/defs.h gdb-10.2/gdb/defs.h ++--- gdb-10.2/gdb/defs.h 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdb/defs.h 2025-04-16 17:06:41.892086800 +0800 ++@@ -629,4 +629,7 @@ ++ ++ #include "utils.h" ++ +++#ifdef CRASH_MERGE +++extern "C" int gdb_main_entry(int, char **); +++#endif ++ #endif /* #ifndef DEFS_H */ ++diff -Nuar gdb-10.2/gdb/dwarf2/read.c gdb-10.2/gdb/dwarf2/read.c ++--- gdb-10.2/gdb/dwarf2/read.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/dwarf2/read.c 2025-04-16 17:06:41.952086800 +0800 ++@@ -3015,7 +3015,11 @@ ++ indices. */ ++ if (version < 4) ++ { +++#ifdef CRASH_MERGE +++ static int warning_printed = 1; +++#else ++ static int warning_printed = 0; +++#endif ++ if (!warning_printed) ++ { ++ warning (_("Skipping obsolete .gdb_index section in %s."), ++@@ -3034,7 +3038,11 @@ ++ "set use-deprecated-index-sections on". */ ++ if (version < 6 && !deprecated_ok) ++ { +++#ifdef CRASH_MERGE +++ static int warning_printed = 1; +++#else ++ static int warning_printed = 0; +++#endif ++ if (!warning_printed) ++ { ++ warning (_("\ ++@@ -4917,7 +4925,10 @@ ++ result = recursively_find_pc_sect_compunit_symtab ++ (dw2_instantiate_symtab (data, per_objfile, false), pc); ++ ++- gdb_assert (result != NULL); +++ if (warn_if_readin && result == nullptr) +++ warning (_("(Error: pc %s in address map, but not in symtab.)"), +++ paddress (objfile->arch (), pc)); +++ ++ return result; ++ } ++ ++diff -Nuar gdb-10.2/gdb/findvar.c gdb-10.2/gdb/findvar.c ++--- gdb-10.2/gdb/findvar.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/findvar.c 2025-04-16 17:06:51.932086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Find a variable's value in memory, for GDB, the GNU debugger. ++ ++- Copyright (C) 1986-2021 Free Software Foundation, Inc. +++ Copyright (C) 1986-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -790,7 +790,25 @@ ++ /* Determine address of TLS variable. */ ++ if (obj_section ++ && (obj_section->the_bfd_section->flags & SEC_THREAD_LOCAL) != 0) ++- addr = target_translate_tls_address (obj_section->objfile, addr); +++#ifndef XWB20200308 +++ { +++ struct bfd_section *sect; +++ +++ /* here, addr same as output of swnm */ +++ sect = obj_section->the_bfd_section; +++ +++ /* all for slave */ +++ if ( !strcmp(sect->name, ".tdata")) +++ addr = target_translate_tls_address (obj_section->objfile, addr ); +++ +++ sect = bfd_get_section_by_name (obj_section->objfile->obfd, ".tdata_ local"); +++ if (sect) +++ addr += 1L<alignment_power; +++ //debug("%s address %#lx", SYMBOL_PRINT_NAME (var), addr); +++ } +++#else +++ addr = target_translate_tls_address (obj_section->objfile, addr); +++#endif ++ } ++ break; ++ ++diff -Nuar gdb-10.2/gdb/fnchange.lst gdb-10.2/gdb/fnchange.lst ++--- gdb-10.2/gdb/fnchange.lst 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/fnchange.lst 2025-04-16 17:06:51.932086800 +0800 ++@@ -0,0 +1,730 @@ +++@V@/COPYING.LIBGLOSS @V@/COPYING.GLOSS +++@V@/bfd/ChangeLog-9193 @V@/bfd/ChangeLog.9193 +++@V@/bfd/ChangeLog-9495 @V@/bfd/ChangeLog.9495 +++@V@/bfd/ChangeLog-9697 @V@/bfd/ChangeLog.9697 +++@V@/bfd/ChangeLog-9899 @V@/bfd/ChangeLog.9899 +++@V@/bfd/ChangeLog-0001 @V@/bfd/ChangeLog.0001 +++@V@/bfd/ChangeLog-0203 @V@/bfd/ChangeLog.0203 +++@V@/bfd/ChangeLog-2004 @V@/bfd/ChangeLog.004 +++@V@/bfd/ChangeLog-2005 @V@/bfd/ChangeLog.005 +++@V@/bfd/ChangeLog-2006 @V@/bfd/ChangeLog.006 +++@V@/bfd/ChangeLog-2007 @V@/bfd/ChangeLog.007 +++@V@/bfd/ChangeLog-2008 @V@/bfd/ChangeLog.008 +++@V@/bfd/doc/ChangeLog-9103 @V@/bfd/ChangeLog.9103 +++@V@/bfd/coff-tic30.c @V@/bfd/cofftic30.c +++@V@/bfd/coff-tic4x.c @V@/bfd/cofftic40.c +++@V@/bfd/coff-tic54x.c @V@/bfd/cofftic54x.c +++@V@/bfd/coff-tic80.c @V@/bfd/cofftic80.c +++@V@/bfd/cpu-cr16.c @V@/bfd/cpucr16.c +++@V@/bfd/cpu-cr16c.c @V@/bfd/cpucr16c.c +++@V@/bfd/cpu-ia64-opc.c @V@/bfd/cpuia64-opc.c +++@V@/bfd/cpu-microblaze.c @V@/bfd/cpumb.c +++@V@/bfd/cpu-m68hc11.c @V@/bfd/cm68hc11.c +++@V@/bfd/cpu-m68hc12.c @V@/bfd/cm68hc12.c +++@V@/bfd/efi-app-ia32.c @V@/bfd/efiia32app.c +++@V@/bfd/efi-app-ia64.c @V@/bfd/efiia64app.c +++@V@/bfd/efi-bsdrv-ia32.c @V@/bfd/efiia32bsdrv.c +++@V@/bfd/efi-bsdrv-ia64.c @V@/bfd/efiia64bsdrv.c +++@V@/bfd/efi-rtdrv-ia32.c @V@/bfd/efiia32rtdrv.c +++@V@/bfd/efi-rtdrv-ia64.c @V@/bfd/efiia64rtdrv.c +++@V@/bfd/elf32-arc.c @V@/bfd/elf32arc.c +++@V@/bfd/elf32-crx.c @V@/bfd/elf32crx.c +++@V@/bfd/elf32-cris.c @V@/bfd/elf32cris.c +++@V@/bfd/elf32-cr16c.c @V@/bfd/elf32cr16c.c +++@V@/bfd/elf32-fr30.c @V@/bfd/elf32f30.c +++@V@/bfd/elf32-frv.c @V@/bfd/elf32fv.c +++@V@/bfd/elf32-i370.c @V@/bfd/e32i370.c +++@V@/bfd/elf32-i386.c @V@/bfd/e32i86.c +++@V@/bfd/elf32-microblaze.c @V@e32mb.c +++@V@/bfd/elf32-m32c.c @V@/bfd/em32c.c +++@V@/bfd/elf32-m32r.c @V@/bfd/em32r.c +++@V@/bfd/elf32-m68hc11.c @V@/bfd/em68hc11.c +++@V@/bfd/elf32-m68hc12.c @V@/bfd/em68hc12.c +++@V@/bfd/elf32-m68hc1x.c @V@/bfd/em68hc1x.c +++@V@/bfd/elf32-m68k.c @V@/bfd/em68k.c +++@V@/bfd/elf32-microblaze.c @V@/bfd/emicroblaze.c +++@V@/bfd/elf32-ppc.c @V@/bfd/e32ppc.c +++@V@/bfd/elf32-sh.c @V@/bfd/e32sh.c +++@V@/bfd/elf32-score.c @V@/bfd/e32score.c +++@V@/bfd/elf32-sh64.c @V@/bfd/e32sh64.c +++@V@/bfd/elf32-sh-relocs.c @V@/bfd/e32sh-relocs.c +++@V@/bfd/elf32-sh-relocs.h @V@/bfd/e32sh-relocs.h +++@V@/bfd/elf32-sh-symbian.c @V@/bfd/e32sh-symbian.c +++@V@/bfd/elf32-sh64-com.c @V@/bfd/e32sh64-com.c +++@V@/bfd/elf32-sparc.c @V@/bfd/e32sparc.c +++@V@/bfd/elf32-spu.c @V@/bfd/e32spu.c +++@V@/bfd/elf64-alpha.c @V@/bfd/e64alphf.c +++@V@/bfd/elf64-sw_64.c @V@/bfd/e64alphf.c +++@V@/bfd/elf64-sh64.c @V@/bfd/e64sh64.c +++@V@/config/bootstrap-O1.mk @V@/config/boot-O1.mk +++@V@/config/bootstrap-O3.mk @V@/config/boot-O3.mk +++@V@/config/bootstrap-debug-big.mk @V@/config/boot-dbig.mk +++@V@/config/bootstrap-debug-ckovw.mk @V@/config/boot-bckovw.mk +++@V@/config/bootstrap-debug-lean.mk @V@/config/boot-dlean.mk +++@V@/config/bootstrap-debug-lib.mk @V@/config/boot-dlib.mk +++@V@/config/bootstrap-debug.mk @V@/config/boot-debug.mk +++@V@/config/bootstrap-time.mk @V@/config/boot-time.mk +++@V@/config/inttypes-pri.m4 @V@/config/pri-inttypes.m4 +++@V@/config/inttypes_h.m4 @V@/config/uintmax-inttypes.m4 +++@V@/config/mt-mips-elfoabi @V@/config/mt-elfoabi-mips +++@V@/config/mt-mips-gnu @V@/config/mt-gnu-mips +++@V@/dejagnu/baseboards/mn10200-cygmon.exp @V@/dejagnu/baseboards/mn10200cygmon.exp +++@V@/dejagnu/baseboards/mn10200-sim.exp @V@/dejagnu/baseboards/mn10200sim.exp +++@V@/dejagnu/baseboards/mn10300-cygmon.exp @V@/dejagnu/baseboards/mn10300cygmon.exp +++@V@/dejagnu/baseboards/mn10300-sim.exp @V@/dejagnu/baseboards/mn10300sim.exp +++@V@/dejagnu/baseboards/powerpc-bug1.exp @V@/dejagnu/baseboards/powerpc1-bug.exp +++@V@/dejagnu/baseboards/powerpc-sim.exp @V@/dejagnu/baseboards/powerpcsim.exp +++@V@/dejagnu/baseboards/sparclite-coff.exp @V@/dejagnu/baseboards/sl-coff.exp +++@V@/dejagnu/baseboards/sparclite-cygmon.exp @V@/dejagnu/baseboards/sl-cygmon.exp +++@V@/dejagnu/baseboards/sparclite-sim-le.exp @V@/dejagnu/baseboards/sl-sim-le.exp +++@V@/dejagnu/baseboards/sparclite-sim.exp @V@/dejagnu/baseboards/sl-sim.exp +++@V@/dejagnu/contrib/test-g++ @V@/dejagnu/contrib/test-gxx +++@V@/dejagnu/example/calc/calc.h.in @V@/dejagnu/example/calc/calc.h-in +++@V@/expect/Dbg_cf.h.in @V@/expect/Dbg_cf.h-in +++@V@/expect/example/beer.exp.out @V@/expect/example/beer_exp.out +++@V@/expect/example/chesslib++.c @V@/expect/example/chesslibxx.c +++@V@/expect/example/chesslib.c @V@/expect/example/chesslb.c +++@V@/expect/example/chesslib2.c @V@/expect/example/chesslb2.c +++@V@/expect/example/chesslibxx.c @V@/expect/example/chesslbxx.c +++@V@/expect/exp_main_sub.c @V@/expect/exp_m_sub.c +++@V@/expect/exp_main_tk.c @V@/expect/exp_m_tk.c +++@V@/expect/expect_cf.h.in @V@/expect/expect_cf.h-in +++@V@/gdb/ChangeLog-1990 @V@/gdb/ChangeLog.90 +++@V@/gdb/ChangeLog-1991 @V@/gdb/ChangeLog.91 +++@V@/gdb/ChangeLog-1992 @V@/gdb/ChangeLog.92 +++@V@/gdb/ChangeLog-1993 @V@/gdb/ChangeLog.93 +++@V@/gdb/ChangeLog-1994 @V@/gdb/ChangeLog.94 +++@V@/gdb/ChangeLog-1995 @V@/gdb/ChangeLog.95 +++@V@/gdb/ChangeLog-1996 @V@/gdb/ChangeLog.96 +++@V@/gdb/ChangeLog-1997 @V@/gdb/ChangeLog.97 +++@V@/gdb/ChangeLog-1998 @V@/gdb/ChangeLog.98 +++@V@/gdb/ChangeLog-1999 @V@/gdb/ChangeLog.99 +++@V@/gdb/ChangeLog-2000 @V@/gdb/ChangeLog.000 +++@V@/gdb/ChangeLog-2001 @V@/gdb/ChangeLog.001 +++@V@/gdb/ChangeLog-2002 @V@/gdb/ChangeLog.002 +++@V@/gdb/ChangeLog-2003 @V@/gdb/ChangeLog.003 +++@V@/gdb/ChangeLog-2004 @V@/gdb/ChangeLog.004 +++@V@/gdb/ChangeLog-2005 @V@/gdb/ChangeLog.005 +++@V@/gdb/ChangeLog-2006 @V@/gdb/ChangeLog.006 +++@V@/gdb/ChangeLog-2007 @V@/gdb/ChangeLog.007 +++@V@/gdb/ChangeLog-2008 @V@/gdb/ChangeLog.008 +++@V@/gdb/ChangeLog-2009 @V@/gdb/ChangeLog.009 +++@V@/gdb/ChangeLog-2010 @V@/gdb/ChangeLog.010 +++@V@/gdb/ChangeLog-2011 @V@/gdb/ChangeLog.011 +++@V@/gdb/ChangeLog-2012 @V@/gdb/ChangeLog.012 +++@V@/gdb/ChangeLog-2013 @V@/gdb/ChangeLog.013 +++@V@/gdb/ChangeLog-2014 @V@/gdb/ChangeLog.014 +++@V@/gdb/ChangeLog-2015 @V@/gdb/ChangeLog.015 +++@V@/gdb/ChangeLog-2016 @V@/gdb/ChangeLog.016 +++@V@/gdb/ChangeLog-2017 @V@/gdb/ChangeLog.017 +++@V@/gdb/ChangeLog-2018 @V@/gdb/ChangeLog.018 +++@V@/gdb/ChangeLog-2019 @V@/gdb/ChangeLog.019 +++@V@/gdb/ChangeLog-3.x @V@/gdb/ChangeLog.3-x +++@V@/gdb/ada-exp.tab.c @V@/gdb/ada-exp_tab.c +++@V@/gdb/amd64-windows-nat.c @V@/gdb/a64w-nat.c +++@V@/gdb/amd64-windows-tdep.c @V@/gdb/a64w-tdep.c +++@V@/gdb/amd64-fbsd-nat.c @V@/gdb/a64fb-nat.c +++@V@/gdb/amd64-fbsd-tdep.c @V@/gdb/a64fb-tdep.c +++@V@/gdb/amd64-nbsd-nat.c @V@/gdb/a64nb-nat.c +++@V@/gdb/amd64-nbsd-tdep.c @V@/gdb/a64nb-tdep.c +++@V@/gdb/amd64-obsd-nat.c @V@/gdb/a64ob-nat.c +++@V@/gdb/amd64-obsd-tdep.c @V@/gdb/a64ob-tdep.c +++@V@/gdb/alpha-bsd-nat.c @V@/gdb/alphb-nat.c +++@V@/gdb/alpha-bsd-tdep.c @V@/gdb/alphb-tdep.c +++@V@/gdb/alpha-nbsd-tdep.c @V@/gdb/alphnb-tdep.c +++@V@/gdb/alpha-linux-nat.c @V@/gdb/alphl-nat.c +++@V@/gdb/alpha-linux-tdep.c @V@/gdb/alphl-tdep.c +++@V@/gdb/sw_64-bsd-nat.c @V@/gdb/sw_6b-nat.c +++@V@/gdb/sw_64-linux-nat.c @V@/gdb/sw_6l-nat.c +++@V@/gdb/sw_64-linux-tdep.c @V@/gdb/sw_6l-tdep.c +++@V@/gdb/arm-linux-nat.c @V@/gdb/armlin-nat.c +++@V@/gdb/arm-linux-tdep.c @V@/gdb/armlin-tdep.c +++@V@/gdb/arm-nbsd-nat.c @V@/gdb/armnbd-nat.c +++@V@/gdb/arm-nbsd-tdep.c @V@/gdb/armnbd-tdep.c +++@V@/gdb/c-exp.tab.c @V@/gdb/c-exp_tab.c +++@V@/gdb/config/alpha/tm-alphalinux.h @V@/gdb/config/alpha/tm-alplinux.h +++@V@/gdb/config/i386/nm-cygwin64.h @V@/gdb/config/i386/nm-cyg64.h +++@V@/gdb/config/i386/nm-linux64.h @V@/gdb/config/i386/nm-lx64.h +++@V@/gdb/config/i386/nm-i386sco4.h @V@/gdb/config/i386/nm-sco4.h +++@V@/gdb/config/i386/nm-i386sco5.h @V@/gdb/config/i386/nm-sco5.h +++@V@/gdb/config/i386/nm-i386v4.h @V@/gdb/config/i386/nm-v4.h +++@V@/gdb/config/i386/nm-i386v42mp.h @V@/gdb/config/i386/nm-v42mp.h +++@V@/gdb/config/i386/tm-i386sol2.h @V@/gdb/config/i386/tm-sol2.h +++@V@/gdb/config/i386/xm-i386v4.h @V@/gdb/config/i386/xm-v4.h +++@V@/gdb/config/m88k/xm-delta88v4.h @V@/gdb/config/m88k/xm-d88v4.h +++@V@/gdb/config/mips/tm-linux.h @V@/gdb/config/mips/tm-lx.h +++@V@/gdb/config/pa/nm-hppah11.h @V@/gdb/config/pa/nm-hppa11.h +++@V@/gdb/config/rs6000/tm-rs6000.h @V@/gdb/config/rs6000/tm-rs6k.h +++@V@/gdb/config/rs6000/tm-rs6000ly.h @V@/gdb/config/rs6000/tm-rs6kly.h +++@V@/gdb/config/sparc/tm-sparclynx.h @V@/gdb/config/sparc/tm-splynx.h +++@V@/gdb/cp-names.c @V@/gdb/cpnames.c +++@V@/gdb/darwin-nat.c @V@/gdb/drw-nat.c +++@V@/gdb/darwin-nat-info.c @V@/gdb/drw-nat-info.c +++@V@/gdb/features/mips64-cp0.xml @V@/gdb/features/mips64-0cp.xml +++@V@/gdb/features/arm-vfpv2.xml @V@/gdb/features/armvfpv2.xml +++@V@/gdb/features/arm-vfpv3.xml @V@/gdb/features/armvfpv3.xml +++@V@/gdb/features/arm-with-iwmmxt.xml @V@/gdb/features/arm-iwmmxt.xml +++@V@/gdb/features/arm-with-neon.xml @V@/gdb/features/arm-neon.xml +++@V@/gdb/features/arm-with-iwmmxt.c @V@/gdb/features/arm-iwmmxt.c +++@V@/gdb/features/arm-with-neon.c @V@/gdb/features/arm-neon.c +++@V@/gdb/features/arm-with-vfpv2.xml @V@/gdb/features/arm-wv2.xml +++@V@/gdb/features/arm-with-vfpv3.xml @V@/gdb/features/arm-wv3.xml +++@V@/gdb/features/arm-with-vfpv2.c @V@/gdb/features/arm-wv2.c +++@V@/gdb/features/arm-with-vfpv3.c @V@/gdb/features/arm-wv3.c +++@V@/gdb/features/rs6000/power-fpu-isa205.xml @V@/gdb/features/rs6000/power-isa205.xml +++@V@/gdb/features/rs6000/power64-core.xml @V@/gdb/features/rs6000/power64core.xml +++@V@/gdb/features/rs6000/power64-linux.xml @V@/gdb/features/rs6000/power64linux.xml +++@V@/gdb/features/rs6000/powerpc-32.c @V@/gdb/features/rs6000/ppc-32.c +++@V@/gdb/features/rs6000/powerpc-32l.c @V@/gdb/features/rs6000/ppc-32l.c +++@V@/gdb/features/rs6000/powerpc-403.c @V@/gdb/features/rs6000/ppc-403.c +++@V@/gdb/features/rs6000/powerpc-403gc.c @V@/gdb/features/rs6000/ppc-403gc.c +++@V@/gdb/features/rs6000/powerpc-505.c @V@/gdb/features/rs6000/ppc-505.c +++@V@/gdb/features/rs6000/powerpc-601.c @V@/gdb/features/rs6000/ppc-601.c +++@V@/gdb/features/rs6000/powerpc-602.c @V@/gdb/features/rs6000/ppc-602.c +++@V@/gdb/features/rs6000/powerpc-603.c @V@/gdb/features/rs6000/ppc-603.c +++@V@/gdb/features/rs6000/powerpc-604.c @V@/gdb/features/rs6000/ppc-604.c +++@V@/gdb/features/rs6000/powerpc-64.c @V@/gdb/features/rs6000/ppc-64.c +++@V@/gdb/features/rs6000/powerpc-64l.c @V@/gdb/features/rs6000/ppc-64l.c +++@V@/gdb/features/rs6000/powerpc-7400.c @V@/gdb/features/rs6000/ppc-7400.c +++@V@/gdb/features/rs6000/powerpc-750.c @V@/gdb/features/rs6000/ppc-7500.c +++@V@/gdb/features/rs6000/powerpc-860.c @V@/gdb/features/rs6000/ppc-860.c +++@V@/gdb/features/rs6000/powerpc-altivec32.c @V@/gdb/features/rs6000/ppc-a32.c +++@V@/gdb/features/rs6000/powerpc-altivec32l.c @V@/gdb/features/rs6000/ppc-a32l.c +++@V@/gdb/features/rs6000/powerpc-altivec64.c @V@/gdb/features/rs6000/ppc-a64.c +++@V@/gdb/features/rs6000/powerpc-altivec64l.c @V@/gdb/features/rs6000/ppc-a64l.c +++@V@/gdb/features/rs6000/powerpc-e500.c @V@/gdb/features/rs6000/ppc-e5h.c +++@V@/gdb/features/rs6000/powerpc-e500l.c @V@/gdb/features/rs6000/ppc-e5hl.c +++@V@/gdb/features/rs6000/powerpc-isa205-32l.c @V@/gdb/features/rs6000/ppc-is32.c +++@V@/gdb/features/rs6000/powerpc-isa205-64l.c @V@/gdb/features/rs6000/ppc-is64.c +++@V@/gdb/features/rs6000/powerpc-isa205-altivec32l.c @V@/gdb/features/rs6000/ppcia32l.c +++@V@/gdb/features/rs6000/powerpc-isa205-altivec64l.c @V@/gdb/features/rs6000/ppcia64l.c +++@V@/gdb/features/rs6000/powerpc-isa205-vsx32l.c @V@/gdb/features/rs6000/ppciv32l.c +++@V@/gdb/features/rs6000/powerpc-isa205-vsx64l.c @V@/gdb/features/rs6000/ppciv64l.c +++@V@/gdb/features/rs6000/powerpc-vsx32.c @V@/gdb/features/rs6000/ppc-v32.c +++@V@/gdb/features/rs6000/powerpc-vsx32l.c @V@/gdb/features/rs6000/ppc-v32l.c +++@V@/gdb/features/rs6000/powerpc-vsx64.c @V@/gdb/features/rs6000/ppc-v64.c +++@V@/gdb/features/rs6000/powerpc-vsx64l.c @V@/gdb/features/rs6000/ppc-v64l.c +++@V@/gdb/features/rs6000/powerpc-32.xml @V@/gdb/features/rs6000/ppc-32.xml +++@V@/gdb/features/rs6000/powerpc-32l.xml @V@/gdb/features/rs6000/ppc-32l.xml +++@V@/gdb/features/rs6000/powerpc-403.xml @V@/gdb/features/rs6000/ppc-403.xml +++@V@/gdb/features/rs6000/powerpc-403gc.xml @V@/gdb/features/rs6000/ppc-403gc.xml +++@V@/gdb/features/rs6000/powerpc-505.xml @V@/gdb/features/rs6000/ppc-505.xml +++@V@/gdb/features/rs6000/powerpc-601.xml @V@/gdb/features/rs6000/ppc-601.xml +++@V@/gdb/features/rs6000/powerpc-602.xml @V@/gdb/features/rs6000/ppc-602.xml +++@V@/gdb/features/rs6000/powerpc-603.xml @V@/gdb/features/rs6000/ppc-603.xml +++@V@/gdb/features/rs6000/powerpc-604.xml @V@/gdb/features/rs6000/ppc-604.xml +++@V@/gdb/features/rs6000/powerpc-64.xml @V@/gdb/features/rs6000/ppc-64.xml +++@V@/gdb/features/rs6000/powerpc-64l.xml @V@/gdb/features/rs6000/ppc-64l.xml +++@V@/gdb/features/rs6000/powerpc-7400.xml @V@/gdb/features/rs6000/ppc-7400.xml +++@V@/gdb/features/rs6000/powerpc-750.xml @V@/gdb/features/rs6000/ppc-7500.xml +++@V@/gdb/features/rs6000/powerpc-860.xml @V@/gdb/features/rs6000/ppc-860.xml +++@V@/gdb/features/rs6000/powerpc-altivec32.xml @V@/gdb/features/rs6000/ppc-a32.xml +++@V@/gdb/features/rs6000/powerpc-altivec32l.xml @V@/gdb/features/rs6000/ppc-a32l.xml +++@V@/gdb/features/rs6000/powerpc-altivec64.xml @V@/gdb/features/rs6000/ppc-a64.xml +++@V@/gdb/features/rs6000/powerpc-altivec64l.xml @V@/gdb/features/rs6000/ppc-a64l.xml +++@V@/gdb/features/rs6000/powerpc-e500.xml @V@/gdb/features/rs6000/ppc-e5h.xml +++@V@/gdb/features/rs6000/powerpc-e500l.xml @V@/gdb/features/rs6000/ppc-e5hl.xml +++@V@/gdb/features/rs6000/powerpc-isa205-32l.xml @V@/gdb/features/rs6000/ppc-is32.xml +++@V@/gdb/features/rs6000/powerpc-isa205-64l.xml @V@/gdb/features/rs6000/ppc-is64.xml +++@V@/gdb/features/rs6000/powerpc-isa205-altivec32l.xml @V@/gdb/features/rs6000/ppcia32l.xml +++@V@/gdb/features/rs6000/powerpc-isa205-altivec64l.xml @V@/gdb/features/rs6000/ppcia64l.xml +++@V@/gdb/features/rs6000/powerpc-isa205-vsx32l.xml @V@/gdb/features/rs6000/ppciv32l.xml +++@V@/gdb/features/rs6000/powerpc-isa205-vsx64l.xml @V@/gdb/features/rs6000/ppciv64l.xml +++@V@/gdb/features/rs6000/powerpc-vsx32.xml @V@/gdb/features/rs6000/ppc-v32.xml +++@V@/gdb/features/rs6000/powerpc-vsx32l.xml @V@/gdb/features/rs6000/ppc-v32l.xml +++@V@/gdb/features/rs6000/powerpc-vsx64.xml @V@/gdb/features/rs6000/ppc-v64.xml +++@V@/gdb/features/rs6000/powerpc-vsx64l.xml @V@/gdb/features/rs6000/ppc-v64l.xml +++@V@/gdb/features/i386/amd64-avx-linux.c @V@/gdb/features/i386/a64-al.c +++@V@/gdb/features/i386/amd64-avx.c @V@/gdb/features/i386/a64-a.c +++@V@/gdb/features/i386/amd64-avx-linux.xml @V@/gdb/features/i386/a64-al.xml +++@V@/gdb/features/i386/amd64-avx.xml @V@/gdb/features/i386/a64-a.xml +++@V@/gdb/features/i386/i386-avx-linux.c @V@/features/i386/i32-al.c +++@V@/gdb/features/i386/i386-avx.c @V@/gdb/features/i386/i32-a.c +++@V@/gdb/features/i386/i386-avx-linux.xml @V@/gdb/features/i386/i32-al.xml +++@V@/gdb/features/i386/i386-avx.xml @V@/gdb/features/i386/i32-a.xml +++@V@/gdb/features/i386/i386-mmx-linux.c @V@/features/i386/i32-ml.c +++@V@/gdb/features/i386/i386-mmx.c @V@/gdb/features/i386/i32-m.c +++@V@/gdb/features/i386/i386-mmx-linux.xml @V@/gdb/features/i386/i32-ml.xml +++@V@/gdb/features/i386/i386-mmx.xml @V@/gdb/features/i386/i32-m.xml +++@V@/gdb/features/tic6x-core.xml @V@/gdb/features/c6x-core.xml +++@V@/gdb/features/tic6x-gp.xml @V@/gdb/features/c6x-gp.xml +++@V@/gdb/features/tic6x-c6xp.xml @V@/gdb/features/c6x-c6xp.xml +++@V@/gdb/features/tic6x-c62x.xml @V@/gdb/features/c6x-62x.xml +++@V@/gdb/features/tic6x-c64x.xml @V@/gdb/features/c6x-64x.xml +++@V@/gdb/features/tic6x-c64xp.xml @V@/gdb/features/c6xc64xp.xml +++@V@/gdb/features/tic6x-c64xp.c @V@/gdb/features/c6xc64xp.c +++@V@/gdb/features/tic6x-c64x.c @V@/gdb/features/c6x-64x.c +++@V@/gdb/features/tic6x-c62x.c @V@/gdb/features/c6x-62x.c +++@V@/gdb/features/tic6x-c62x-linux.xml @V@/gdb/features/c6x-62xl.xml +++@V@/gdb/features/tic6x-c64x-linux.xml @V@/gdb/features/c6x-64xl.xml +++@V@/gdb/features/tic6x-c64xp-linux.xml @V@/gdb/features/c6x64xpl.xml +++@V@/gdb/features/tic6x-c64xp-linux.c @V@/gdb/features/c6x64xpl.c +++@V@/gdb/features/tic6x-c64x-linux.c @V@/gdb/features/c6x-64xl.c +++@V@/gdb/features/tic6x-c62x-linux.c @V@/gdb/features/c6x-62xl.c +++@V@/gdb/f-exp.tab.c @V@/gdb/f-exp_tab.c +++@V@/gdb/gdbserver/linux-cris-low.c @V@/gdb/gdbserver/lx-cris.c +++@V@/gdb/gdbserver/linux-crisv32-low.c @V@/gdb/gdbserver/lx-cris32.c +++@V@/gdb/gdbserver/linux-ppc-low.c @V@/gdb/gdbserver/lx-ppc-low.c +++@V@/gdb/gdbserver/linux-ppc64-low.c @V@/gdb/gdbserver/lx-ppc64-low.c +++@V@/gdb/gdbtk/ChangeLog-2001 @V@/gdb/gdbtk/ChangeLog.001 +++@V@/gdb/gdbtk/ChangeLog-2002 @V@/gdb/gdbtk/ChangeLog.002 +++@V@/gdb/gdbtk/ChangeLog-2003 @V@/gdb/gdbtk/ChangeLog.003 +++@V@/gdb/gdbtk/generic/ChangeLog-1997 @V@/gdb/gdbtk/generic/ChangeLog.97 +++@V@/gdb/gdbtk/generic/ChangeLog-1998 @V@/gdb/gdbtk/generic/ChangeLog.98 +++@V@/gdb/gdbtk/generic/ChangeLog-1999 @V@/gdb/gdbtk/generic/ChangeLog.99 +++@V@/gdb/gdbtk/generic/ChangeLog-2000 @V@/gdb/gdbtk/generic/ChangeLog.000 +++@V@/gdb/gdbtk/generic/gdbtk-varobj.c @V@/gdb/gdbtk/generic/gdbtk-vobj.c +++@V@/gdb/gdbtk/library/ChangeLog-1997 @V@/gdb/gdbtk/library/ChangeLog.97 +++@V@/gdb/gdbtk/library/ChangeLog-1998 @V@/gdb/gdbtk/library/ChangeLog.98 +++@V@/gdb/gdbtk/library/ChangeLog-1999 @V@/gdb/gdbtk/library/ChangeLog.99 +++@V@/gdb/gdbtk/library/ChangeLog-2000 @V@/gdb/gdbtk/library/ChangeLog.000 +++@V@/gdb/gdbtk/plugins/intel-pentium/intel-pentium.tcl.in @V@/gdb/gdbtk/plugins/intel-pentium/intel-pentium.t-in +++@V@/gdb/gdbtk/plugins/rhabout/rhabout.tcl.in @V@/gdb/gdbtk/plugins/rhabout/rhabout.t-in +++@V@/gdb/hppa-bsd-nat.c @V@/gdb/hppab-nat.c +++@V@/gdb/hppa-bsd-tdep.c @V@/gdb/hppab-tdep.c +++@V@/gdb/hpp-nbsd-nat.c @V@/gdb/hppnb-nat.c +++@V@/gdb/hpp-nbsd-tdep.c @V@/gdb/hppnb-tdep.c +++@V@/gdb/i386-darwin-nat.c @V@/gdb/i386dw-nat.c +++@V@/gdb/i386-darwin-tdep.c @V@/gdb/i386dw-tdep.c +++@V@/gdb/i386-linux-tdep.c @V@/gdb/i386lx-tdep.c +++@V@/gdb/i386-linux-nat.c @V@/gdb/i386lx-nat.c +++@V@/gdb/i386-bsd-nat.c @V@/gdb/i3bsd-nat.c +++@V@/gdb/i386-bsd-tdep.c @V@/gdb/i3bsd-tdep.c +++@V@/gdb/i386-fbsd-nat.c @V@/gdb/i3fbsd-nat.c +++@V@/gdb/i386-fbsd-tdep.c @V@/gdb/i3fbsd-tdep.c +++@V@/gdb/i386-gnu-nat.c @V@/gdb/i3gnu-nat.c +++@V@/gdb/i386-gnu-tdep.c @V@/gdb/i3gnu-tdep.c +++@V@/gdb/i386-nbsd-tdep.c @V@/gdb/i3nbsd-tdep.c +++@V@/gdb/i386-obsd-nat.c @V@/gdb/i3obsd-nat.c +++@V@/gdb/i386-obsd-tdep.c @V@/gdb/i3obsd-tdep.c +++@V@/gdb/i386-sol2-nat.c @V@/gdb/i3sol2-nat.c +++@V@/gdb/i386-sol2-tdep.c @V@/gdb/i3sol2-tdep.c +++@V@/gdb/ia64-aix-nat.c @V@/gdb/ia64ax-nat.c +++@V@/gdb/ia64-aix-tdep.c @V@/gdb/ia64ax-tdep.c +++@V@/gdb/ia64-linux-nat.c @V@/gdb/ia64lx-nat.c +++@V@/gdb/ia64-linux-tdep.c @V@/gdb/ia64lx-tdep.c +++@V@/gdb/jv-exp.tab.c @V@/gdb/jv-exp_tab.c +++@V@/gdb/m2-exp.tab.c @V@/gdb/m2-exp_tab.c +++@V@/gdb/m32r-linux-nat.c @V@/gdb/m32rlnxnat.c +++@V@/gdb/m32r-linux-tdep.c @V@/gdb/m32rlnxtdep.c +++@V@/gdb/m68k-linux-nat.c @V@/gdb/m68kl-nat.c +++@V@/gdb/m68k-linux-tdep.c @V@/gdb/m68kl-tdep.c +++@V@/gdb/m68k-bsd-nat.c @V@/gdb/m68bsd-nat.c +++@V@/gdb/m68k-bsd-tdep.c @V@/gdb/m68bsd-tdep.c +++@V@/gdb/m68k-nbsd-nat.c @V@/gdb/m6nbsd-nat.c +++@V@/gdb/m68k-nbsd-tdep.c @V@/gdb/m6nbsd-tdep.c +++@V@/gdb/microblaze-rom.c @V@/gdb/mb-rom.c +++@V@/gdb/microblaze-linux-tdep.c @V@/gdb/mbl-tdep.c +++@V@/gdb/microblaze-tdep.h @V@/gdb/mb-tdep.h +++@V@/gdb/microblaze-tdep.c @V@/gdb/mb-tdep.c +++@V@/gdb/mips-linux-nat.c @V@/gdb/mipslnxnat.c +++@V@/gdb/mips-linux-tdep.c @V@/gdb/mipslnxtdep.c +++@V@/gdb/mips-nbsd-nat.c @V@/gdb/mipsnbnat.c +++@V@/gdb/mips-nbsd-tdep.c @V@/gdb/mipsnbtdep.c +++@V@/gdb/mips64-obsd-nat.c @V@/gdb/mipsobnat.c +++@V@/gdb/mips64-obsd-tdep.c @V@/gdb/mipsobtdep.c +++@V@/gdb/mn10300-linux-tdep.c @V@/gdb/mn10300linux-tdep.c +++@V@/gdb/ns32k-nbsd-nat.c @V@/gdb/ns32nb-nat.c +++@V@/gdb/ns32k-nbsd-tdep.c @V@/gdb/ns32nb-tdep.c +++@V@/gdb/objc-exp.tab.c @V@/gdb/objc-exp_tab.c +++@V@/gdb/p-exp.tab.c @V@/gdb/p-exp_tab.c +++@V@/gdb/ppc-linux-tdep.c @V@/gdb/ppc-lx-tdep.c +++@V@/gdb/ppc-linux-nat.c @V@/gdb/ppc-lx-nat.c +++@V@/gdb/ppc-nbsd-nat.c @V@/gdb/ppcnb-nat.c +++@V@/gdb/ppc-nbsd-tdep.c @V@/gdb/ppcnb-tdep.c +++@V@/gdb/ppc-obsd-nat.c @V@/gdb/ppcob-nat.c +++@V@/gdb/ppc-obsd-tdep.c @V@/gdb/ppcob-tdep.c +++@V@/gdb/regformats/arm-with-vfpv2.dat @V@/gdb/regformats/arm-wv2.dat +++@V@/gdb/regformats/arm-with-vfpv3.dat @V@/gdb/regformats/arm-wv3.dat +++@V@/gdb/regformats/arm-with-iwmmxt.dat @V@/gdb/regformats/arm-iwmmxt.dat +++@V@/gdb/regformats/arm-with-neon.dat @V@/gdb/regformats/arm-neon.dat +++@V@/gdb/regformats/reg-i386-linux.dat @V@/gdb/regformats/r-i386-lnx.dat +++@V@/gdb/regformats/reg-x86-64-linux.dat @V@/gdb/regformats/r-x8664-linux.dat +++@V@/gdb/regformats/reg-x86-64.dat @V@/gdb/regformats/r-x8664.dat +++@V@/gdb/regformats/reg-s390x.dat @V@/gdb/regformats/r-s390x.dat +++@V@/gdb/regformats/reg-cris.dat @V@/gdb/regformats/r-cris.dat +++@V@/gdb/regformats/reg-crisv32.dat @V@/gdb/regformats/r-crisv32.dat +++@V@/gdb/regformats/rs6000/powerpc-32l.dat @V@/gdb/regformats/rs6000/ppc-32l.dat +++@V@/gdb/regformats/rs6000/powerpc-64l.dat @V@/gdb/regformats/rs6000/ppc-64l.dat +++@V@/gdb/regformats/rs6000/powerpc-altivec32l.dat @V@/gdb/regformats/rs6000/ppc-a32l.dat +++@V@/gdb/regformats/rs6000/powerpc-altivec64l.dat @V@/gdb/regformats/rs6000/ppc-a64l.dat +++@V@/gdb/regformats/rs6000/powerpc-e500l.dat @V@/gdb/regformats/rs6000/ppc-e5hl.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-32l.dat @V@/gdb/regformats/rs6000/ppc-i32l.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-64l.dat @V@/gdb/regformats/rs6000/ppc-i64l.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-altivec32l.dat @V@/gdb/regformats/rs6000/ppcia32l.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-altivec64l.dat @V@/gdb/regformats/rs6000/ppcia64l.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-vsx32l.dat @V@/gdb/regformats/rs6000/ppciv32l.dat +++@V@/gdb/regformats/rs6000/powerpc-isa205-vsx64l.dat @V@/gdb/regformats/rs6000/ppciv64l.dat +++@V@/gdb/regformats/rs6000/powerpc-vsx32l.dat @V@/gdb/regformats/rs6000/ppc-v32l.dat +++@V@/gdb/regformats/rs6000/powerpc-vsx64l.dat @V@/gdb/regformats/rs6000/ppc-v64l.dat +++@V@/gdb/regformats/tic6x-c62x.dat @V@/gdb/regformats/c6x-62x.dat +++@V@/gdb/regformats/tic6x-c64x.dat @V@/gdb/regformats/c6x-64x.dat +++@V@/gdb/regformats/tic6x-c64xp.dat @V@/gdb/regformats/c6xc64xp.dat +++@V@/gdb/regformats/tic6x-c62x-linux.dat @V@/gdb/regformats/c6x-62xl.dat +++@V@/gdb/regformats/tic6x-c64x-linux.dat @V@/gdb/regformats/c6x-64xl.dat +++@V@/gdb/regformats/tic6x-c64xp-linux.dat @V@/gdb/regformats/c6x64xpl.dat +++@V@/gdb/remote-e7000.c @V@/gdb/rmt-e7000.c +++@V@/gdb/remote-est.c @V@/gdb/rmt-est.c +++@V@/gdb/remote-mips.c @V@/gdb/rmt-mips.c +++@V@/gdb/remote-rdi.c @V@/gdb/rmt-rdi.c +++@V@/gdb/remote-rdp.c @V@/gdb/rmt-rdp.c +++@V@/gdb/remote-sds.c @V@/gdb/rmt-sds.c +++@V@/gdb/remote-sim.c @V@/gdb/rmt-sim.c +++@V@/gdb/remote-st.c @V@/gdb/rmt-st.c +++@V@/gdb/remote-vx.c @V@/gdb/rmt-vx.c +++@V@/gdb/remote-vx68.c @V@/gdb/rmt-vx68.c +++@V@/gdb/remote-vxmips.c @V@/gdb/rmt-vxmips.c +++@V@/gdb/remote-vxsparc.c @V@/gdb/rmt-vxsparc.c +++@V@/gdb/sparc64-fbsd-nat.c @V@/gdb/sp64fb-nat.c +++@V@/gdb/sparc64-fbsd-tdep.c @V@/gdb/sp64fb-tdep.c +++@V@/gdb/sparc64-nbsd-nat.c @V@/gdb/sp64nb-nat.c +++@V@/gdb/sparc64-nbsd-tdep.c @V@/gdb/sp64nb-tdep.c +++@V@/gdb/sparc64-linux-nat.c @V@/gdb/sp64lx-nat.c +++@V@/gdb/sparc64-linux-tdep.c @V@/gdb/sp64lx-tdep.c +++@V@/gdb/sparc64-nat.c @V@/gdb/sp64-nat.c +++@V@/gdb/sparc64-tdep.c @V@/gdb/sp64-tdep.c +++@V@/gdb/sparc64-sol2-tdep.c @V@/gdb/sp64s2-tdep.c +++@V@/gdb/sparc-nbsd-nat.c @V@/gdb/spnb-nat.c +++@V@/gdb/sparc-nbsd-tdep.c @V@/gdb/spnb-tdep.c +++@V@/gdb/sparc-linux-nat.c @V@/gdb/splx-nat.c +++@V@/gdb/sparc-linux-tdep.c @V@/gdb/splx-tdep.c +++@V@/gdb/sparc-sol2-nat.c @V@/gdb/spsol2-nat.c +++@V@/gdb/sparc-sol2-tdep.c @V@/gdb/spsol2-tdep.c +++@V@/gdb/tic6x-tdep.c @V@/gdb/c6x-tdep.c +++@V@/gdb/tic6x-tdep.h @V@/gdb/c6x-tdep.h +++@V@/gdb/tic6x-linux-tdep.c @V@/gdb/c6xl-tdep.c +++@V@/gdb/testsuite/.gdbinit @V@/gdb/testsuite/gdb.ini +++@V@/gdb/testsuite/gdb.arch/altivec-abi.c @V@/gdb/testsuite/gdb.arch/av-abi.c +++@V@/gdb/testsuite/gdb.arch/altivec-abi.exp @V@/gdb/testsuite/gdb.arch/av-abi.exp +++@V@/gdb/testsuite/gdb.arch/altivec-regs.c @V@/gdb/testsuite/gdb.arch/av-regs.c +++@V@/gdb/testsuite/gdb.arch/altivec-regs.exp @V@/gdb/testsuite/gdb.arch/av-regs.exp +++@V@/gdb/testsuite/gdb.arch/i386-size-overlap.c @V@/gdb/testsuite/gdb.arch/i386-overlap-size.c +++@V@/gdb/testsuite/gdb.arch/i386-size-overlap.exp @V@/gdb/testsuite/gdb.arch/i386-overlap-size.exp +++@V@/gdb/testsuite/gdb.arch/powerpc-aix-prologue.exp @V@/gdb/testsuite/gdb.arch/ppcaprol.exp +++@V@/gdb/testsuite/gdb.arch/powerpc-aix-prologue.c @V@/gdb/testsuite/gdb.arch/ppcaprol.c +++@V@/gdb/testsuite/gdb.arch/powerpc-d128-regs.c @V@/gdb/testsuite/gdb.arch/ppc-d128-regs.c +++@V@/gdb/testsuite/gdb.arch/powerpc-prologue.c @V@/gdb/testsuite/gdb.arch/ppc-prologue.c +++@V@/gdb/testsuite/gdb.arch/powerpc-d128-regs.exp @V@/gdb/testsuite/gdb.arch/ppc-d128-regs.exp +++@V@/gdb/testsuite/gdb.arch/powerpc-prologue.exp @V@/gdb/testsuite/gdb.arch/ppc-prologue.exp +++@V@/gdb/testsuite/gdb.base/bitfields2.c @V@/gdb/testsuite/gdb.base/bitfiel2.c +++@V@/gdb/testsuite/gdb.base/bitfields2.exp @V@/gdb/testsuite/gdb.base/bitfiel2.exp +++@V@/gdb/testsuite/gdb.base/break-entry.exp @V@/gdb/testsuite/gdb.base/brkentry.exp +++@V@/gdb/testsuite/gdb.base/break-fun-addr1.c @V@/gdb/testsuite/gdb.base/b-f-a1.c +++@V@/gdb/testsuite/gdb.base/break-fun-addr2.c @V@/gdb/testsuite/gdb.base/b-f-a2.c +++@V@/gdb/testsuite/gdb.base/coremaker2.c @V@/gdb/testsuite/gdb.base/core2maker.c +++@V@/gdb/testsuite/gdb.base/hashline1.exp @V@/gdb/testsuite/gdb.base/hash1line.exp +++@V@/gdb/testsuite/gdb.base/hashline2.exp @V@/gdb/testsuite/gdb.base/hash2line.exp +++@V@/gdb/testsuite/gdb.base/hashline3.exp @V@/gdb/testsuite/gdb.base/hash3line.exp +++@V@/gdb/testsuite/gdb.base/hook-stop-continue.c @V@/gdb/testsuite/gdb.base/hstop-continue.c +++@V@/gdb/testsuite/gdb.base/hook-stop-frame.c @V@/gdb/testsuite/gdb.base/hstop-frame.c +++@V@/gdb/testsuite/gdb.base/hook-stop-continue.exp @V@/gdb/testsuite/gdb.base/hstop-continue.exp +++@V@/gdb/testsuite/gdb.base/hook-stop-frame.exp @V@/gdb/testsuite/gdb.base/hstop-frame.exp +++@V@/gdb/testsuite/gdb.base/print-file-var-lib1.c @V@/gdb/testsuite/gdb.base/pfv-lib1.c +++@V@/gdb/testsuite/gdb.base/print-file-var-lib2.c @V@/gdb/testsuite/gdb.base/pfv-lib2.c +++@V@/gdb/testsuite/gdb.base/print-file-var-main.c @V@/gdb/testsuite/gdb.base/pfv-main.c +++@V@/gdb/testsuite/gdb.base/print-file-var.exp @V@/gdb/testsuite/gdb.base/pfv.exp +++@V@/gdb/testsuite/gdb.base/return-nodebug1.c @V@/gdb/testsuite/gdb.base/return-1nodebug.c +++@V@/gdb/testsuite/gdb.base/siginfo-addr.c @V@/gdb/testsuite/gdb.base/si-addr.c +++@V@/gdb/testsuite/gdb.base/siginfo-obj.c @V@/gdb/testsuite/gdb.base/si-obj.c +++@V@/gdb/testsuite/gdb.base/siginfo-addr.exp @V@/gdb/testsuite/gdb.base/si-addr.exp +++@V@/gdb/testsuite/gdb.base/siginfo-obj.exp @V@/gdb/testsuite/gdb.base/si-obj.exp +++@V@/gdb/testsuite/gdb.base/solib-corrupted.exp @V@/gdb/testsuite/gdb.base/so-crptd.exp +++@V@/gdb/testsuite/gdb.base/solib-disc.c @V@/gdb/testsuite/gdb.base/so-disc.c +++@V@/gdb/testsuite/gdb.base/solib-display-lib.c @V@/gdb/testsuite/gdb.base/so-displib.c +++@V@/gdb/testsuite/gdb.base/solib-display-main.c @V@/gdb/testsuite/gdb.base/so-dispmain.c +++@V@/gdb/testsuite/gdb.base/solib-disc.exp @V@/gdb/testsuite/gdb.base/so-disc.exp +++@V@/gdb/testsuite/gdb.base/solib-display-lib.exp @V@/gdb/testsuite/gdb.base/so-displib.exp +++@V@/gdb/testsuite/gdb.base/solib-display-main.exp @V@/gdb/testsuite/gdb.base/so-dispmain.exp +++@V@/gdb/testsuite/gdb.base/solib-symbol-lib.c @V@/gdb/testsuite/gdb.base/so-symlib.c +++@V@/gdb/testsuite/gdb.base/solib-symbol-main.c @V@/gdb/testsuite/gdb.base/so-symmain.c +++@V@/gdb/testsuite/gdb.base/solib-overlap-lib.c @V@/gdb/testsuite/gdb.base/so-ovrlib.c +++@V@/gdb/testsuite/gdb.base/solib-overlap-main.c @V@/gdb/testsuite/gdb.base/so-ovrmain.c +++@V@/gdb/testsuite/gdb.base/symbol-without-target_section.exp @V@/gdb/testsuite/gdb.base/symnosec.exp +++@V@/gdb/testsuite/gdb.base/symbol-without-target_section.c @V@/gdb/testsuite/gdb.base/symnosec.c +++@V@/gdb/testsuite/gdb.base/type-opaque-lib.c @V@/gdb/testsuite/gdb.base/ty-opqlib.c +++@V@/gdb/testsuite/gdb.base/type-opaque-main.c @V@/gdb/testsuite/gdb.base/ty-opqmain.c +++@V@/gdb/testsuite/gdb.base/watchpoint-hw.c @V@/gdb/testsuite/gdb.base/wp-hw.c +++@V@/gdb/testsuite/gdb.base/watchpoint-solib-shr.c @V@/gdb/testsuite/gdb.base/wp-shr-solib.c +++@V@/gdb/testsuite/gdb.base/watchpoint-solib.c @V@/gdb/testsuite/gdb.base/wp-solib.c +++@V@/gdb/testsuite/gdb.base/watchpoint-hw.exp @V@/gdb/testsuite/gdb.base/wp-hw.exp +++@V@/gdb/testsuite/gdb.base/watchpoint-solib.exp @V@/gdb/testsuite/gdb.base/wp-solib.exp +++@V@/gdb/testsuite/gdb.base/watchpoint-cond-gone.exp @V@/gdb/testsuite/gdb.base/wpcondg.exp +++@V@/gdb/testsuite/gdb.base/watchpoint-cond-gone.c @V@/gdb/testsuite/gdb.base/wpcondg.c +++@V@/gdb/testsuite/gdb.base/watchpoint-cond-gone-stripped.c @V@/gdb/testsuite/gdb.base/wpcondgs.c +++@V@/gdb/testsuite/gdb.cp/m-static1.cc @V@/gdb/testsuite/gdb.cp/m-stat1.cc +++@V@/gdb/testsuite/gdb.cp/namespace1.cc @V@/gdb/testsuite/gdb.cp/namesp1.cc +++@V@/gdb/testsuite/gdb.cp/namespace-nested-import.cc @V@/gdb/testsuite/gdb.cp/nnested.cc +++@V@/gdb/testsuite/gdb.cp/namespace-using.cc @V@/gdb/testsuite/gdb.cp/nusing.cc +++@V@/gdb/testsuite/gdb.cp/namespace-nested-import.exp @V@/gdb/testsuite/gdb.cp/nnested.exp +++@V@/gdb/testsuite/gdb.cp/namespace-using.exp @V@/gdb/testsuite/gdb.cp/nusing.exp +++@V@/gdb/testsuite/gdb.cp/mb-inline1.cc @V@/gdb/testsuite/gdb.cp/mb-inln1.cc +++@V@/gdb/testsuite/gdb.cp/mb-inline2.cc @V@/gdb/testsuite/gdb.cp/mb-inln2.cc +++@V@/gdb/testsuite/gdb.dwarf2/dw2-intermix.exp @V@/gdb/testsuite/gdb.dwarf2/dw2-intmix.exp +++@V@/gdb/testsuite/gdb.dwarf2/dw2-intermix.S @V@/gdb/testsuite/gdb.dwarf2/dw2-intmix.S +++@V@/gdb/testsuite/gdb.dwarf2/dw2-ranges.S @V@/gdb/testsuite/gdb.dwarf2/dw2-rng.S +++@V@/gdb/testsuite/gdb.dwarf2/dw2-ranges2.S @V@/gdb/testsuite/gdb.dwarf2/dw2-rng2.S +++@V@/gdb/testsuite/gdb.dwarf2/dw2-ranges3.S @V@/gdb/testsuite/gdb.dwarf2/dw2-rng3.S +++@V@/gdb/testsuite/gdb.gdbtk/ChangeLog @V@/gdb/testsuite/gdb.tk/ChangeLog +++@V@/gdb/testsuite/gdb.gdbtk/Makefile.in @V@/gdb/testsuite/gdb.tk/Makefile.in +++@V@/gdb/testsuite/gdb.gdbtk/browser.exp @V@/gdb/testsuite/gdb.tk/browser.exp +++@V@/gdb/testsuite/gdb.gdbtk/browser.test @V@/gdb/testsuite/gdb.tk/browser.test +++@V@/gdb/testsuite/gdb.gdbtk/c_variable.c @V@/gdb/testsuite/gdb.tk/c_variable.c +++@V@/gdb/testsuite/gdb.gdbtk/c_variable.exp @V@/gdb/testsuite/gdb.tk/c_variable.exp +++@V@/gdb/testsuite/gdb.gdbtk/c_variable.test @V@/gdb/testsuite/gdb.tk/c_variable.test +++@V@/gdb/testsuite/gdb.gdbtk/configure @V@/gdb/testsuite/gdb.tk/configure +++@V@/gdb/testsuite/gdb.gdbtk/configure.in @V@/gdb/testsuite/gdb.tk/configure.in +++@V@/gdb/testsuite/gdb.gdbtk/console.exp @V@/gdb/testsuite/gdb.tk/console.exp +++@V@/gdb/testsuite/gdb.gdbtk/console.test @V@/gdb/testsuite/gdb.tk/console.test +++@V@/gdb/testsuite/gdb.gdbtk/cpp_variable.cc @V@/gdb/testsuite/gdb.tk/cpp_variable.cc +++@V@/gdb/testsuite/gdb.gdbtk/cpp_variable.exp @V@/gdb/testsuite/gdb.tk/cpp_variable.exp +++@V@/gdb/testsuite/gdb.gdbtk/cpp_variable.h @V@/gdb/testsuite/gdb.tk/cpp_variable.h +++@V@/gdb/testsuite/gdb.gdbtk/cpp_variable.test @V@/gdb/testsuite/gdb.tk/cpp_variable.test +++@V@/gdb/testsuite/gdb.gdbtk/defs @V@/gdb/testsuite/gdb.tk/defs +++@V@/gdb/testsuite/gdb.gdbtk/list0.c @V@/gdb/testsuite/gdb.tk/list0.c +++@V@/gdb/testsuite/gdb.gdbtk/list0.h @V@/gdb/testsuite/gdb.tk/list0.h +++@V@/gdb/testsuite/gdb.gdbtk/list1.c @V@/gdb/testsuite/gdb.tk/list1.c +++@V@/gdb/testsuite/gdb.gdbtk/README @V@/gdb/testsuite/gdb.tk/README +++@V@/gdb/testsuite/gdb.gdbtk/simple.c @V@/gdb/testsuite/gdb.tk/simple.c +++@V@/gdb/testsuite/gdb.gdbtk/srcwin.exp @V@/gdb/testsuite/gdb.tk/srcwin.exp +++@V@/gdb/testsuite/gdb.gdbtk/srcwin.test @V@/gdb/testsuite/gdb.tk/srcwin.test +++@V@/gdb/testsuite/gdb.gdbtk/srcwin2.test @V@/gdb/testsuite/gdb.tk/srcwin2.test +++@V@/gdb/testsuite/gdb.gdbtk/srcwin3.test @V@/gdb/testsuite/gdb.tk/srcwin3.test +++@V@/gdb/testsuite/gdb.gdbtk/stack1.c @V@/gdb/testsuite/gdb.tk/stack1.c +++@V@/gdb/testsuite/gdb.gdbtk/stack2.c @V@/gdb/testsuite/gdb.tk/stack2.c +++@V@/gdb/testsuite/gdb.gdbtk/windows.exp @V@/gdb/testsuite/gdb.tk/windows.exp +++@V@/gdb/testsuite/gdb.gdbtk/windows.test @V@/gdb/testsuite/gdb.tk/windows.test +++@V@/gdb/testsuite/gdb.mi/mi-var-cmd.exp @V@/gdb/testsuite/gdb.mi/mi-varcmd.exp +++@V@/gdb/testsuite/gdb.mi/mi-var-child.exp @V@/gdb/testsuite/gdb.mi/mi-varchild.exp +++@V@/gdb/testsuite/gdb.mi/mi-var-child-f.exp @V@/gdb/testsuite/gdb.mi/mi-fvarchild.exp +++@V@/gdb/testsuite/gdb.mi/mi1-var-block.exp @V@/gdb/testsuite/gdb.mi/mi1varblock.exp +++@V@/gdb/testsuite/gdb.mi/mi1-var-child.exp @V@/gdb/testsuite/gdb.mi/mi1varchild.exp +++@V@/gdb/testsuite/gdb.mi/mi1-var-cmd.exp @V@/gdb/testsuite/gdb.mi/mi1varcmd.exp +++@V@/gdb/testsuite/gdb.mi/mi1-var-display.exp @V@/gdb/testsuite/gdb.mi/mi1vardisplay.exp +++@V@/gdb/testsuite/gdb.mi/mi2-var-block.exp @V@/gdb/testsuite/gdb.mi/mi2varblock.exp +++@V@/gdb/testsuite/gdb.mi/mi2-var-child.exp @V@/gdb/testsuite/gdb.mi/mi2varchild.exp +++@V@/gdb/testsuite/gdb.mi/mi2-var-cmd.exp @V@/gdb/testsuite/gdb.mi/mi2varcmd.exp +++@V@/gdb/testsuite/gdb.mi/mi2-var-display.exp @V@/gdb/testsuite/gdb.mi/mi2vardisplay.exp +++@V@/gdb/testsuite/gdb.mi/mi-nonstop-exit.exp @V@/gdb/testsuite/gdb.mi/minonstop-exit.exp +++@V@/gdb/testsuite/gdb.mi/non-stop-exit.c @V@/gdb/testsuite/gdb.mi/nonstop-exit.c +++@V@/gdb/testsuite/gdb.threads/watchthreads2.c @V@/gdb/testsuite/gdb.threads/watchth2.c +++@V@/gdb/testsuite/gdb.threads/watchthreads2.exp @V@/gdb/testsuite/gdb.threads/watchth2.exp +++@V@/gdb/amd64-linux-tdep.c @V@/gdb/amd64-ltdep.c +++@V@/gdb/amd64-linux-nat.c @V@/gdb/amd64-lnat.c +++@V@/gdb/hppa-linux-tdep.c @V@/gdb/palnxtdep.c +++@V@/gdb/hppa-linux-nat.c @V@/gdb/palnxnat.c +++@V@/gdb/hppa-nbsd-nat.c @V@/gdb/panbsd-nat.c +++@V@/gdb/hppa-nbsd-tdep.c @V@/gdb/panbsd-tdep.c +++@V@/gdb/amd64-windows-nat.c @V@/gdb/amd64-wnat.c +++@V@/gdb/amd64-windows-tdep.c @V@/gdb/amd64-wtdep.c +++@V@/gdb/i386-windows-nat.c @V@/gdb/i386-wnat.c +++@V@/gdb/windows-nat.c @V@/gdb/win-nat.c +++@V@/gdb/windows-nat.h @V@/gdb/win-nat.h +++@V@/gdb/windows-tdep.c @V@/gdb/win-tdep.c +++@V@/gdb/windows-tdep.h @V@/gdb/win-tdep.h +++@V@/gdb/windows-termcap.c @V@/gdb/win-tcap.c +++@V@/gdb/xtensa-linux-nat.c @V@/gdb/xtlinuxnat.c +++@V@/gdb/xtensa-linux-tdep.c @V@/gdb/xtlinuxtdep.c +++@V@/include/ChangeLog-9103 @V@/include/ChangeLog.9103 +++@V@/include/coff/ChangeLog-9103 @V@/include/coff/ChangeLog.9103 +++@V@/include/elf/ChangeLog-9103 @V@/include/elf/ChangeLog.9103 +++@V@/include/opcode/ChangeLog-9103 @V@/include/opcode/ChangeLog.9103 +++@V@/include/xtensa-isa-internal.h @V@/include/xt-internal.h +++@V@/include/xtensa-isa.h @V@/include/xt-isa.h +++@V@/intl/intlh.inst.in @V@/intl/intlh_inst.in +++@V@/intl/po2tbl.sed.in @V@/intl/po2tblsed.in +++@V@/intl/config.intl.in @V@/intl/config_intl.in +++@V@/intl/config.h.in @V@/intl/config.h-in +++@V@/itcl/itcl/itclConfig.sh.in @V@/itcl/itcl/itclConfig.sh-in +++@V@/itcl/itcl/unix/pkgIndex.tcl.in @V@/itcl/itcl/unix/pkgIndex.t-in +++@V@/itcl/itk/itkConfig.sh.in @V@/itcl/itk/itkConfig.sh-in +++@V@/itcl/itk/unix/pkgIndex.tcl.in @V@/itcl/itk/unix/pkgIndex.t-in +++@V@/itcl/iwidgets3.0.0 @V@/itcl/iwidgets3.0-0 +++@V@/libgui/config.h.in @V@/libgui/config.h-in +++@V@/libgui/src/tkTableCell.c @V@/libgui/src/tkTabCell.c +++@V@/libgui/src/tkTableCmd.c @V@/libgui/src/tkTabCmd.c +++@V@/libgui/src/tkWinPrintCanvas.c @V@/libgui/src/tkWPrtCanvas.c +++@V@/libgui/src/tkWinPrintText.c @V@/libgui/src/tkWPrtText.c +++@V@/opcodes/ChangeLog-9297 @V@/opcodes/ChangeLog.9297 +++@V@/opcodes/ChangeLog-9899 @V@/opcodes/ChangeLog.9899 +++@V@/opcodes/ChangeLog-0001 @V@/opcodes/ChangeLog.0001 +++@V@/opcodes/ChangeLog-0203 @V@/opcodes/ChangeLog.0203 +++@V@/opcodes/ChangeLog-2004 @V@/opcodes/ChangeLog.004 +++@V@/opcodes/ChangeLog-2005 @V@/opcodes/ChangeLog.005 +++@V@/opcodes/ChangeLog-2006 @V@/opcodes/ChangeLog.006 +++@V@/opcodes/ChangeLog-2007 @V@/opcodes/ChangeLog.007 +++@V@/opcodes/ChangeLog-2008 @V@/opcodes/ChangeLog.008 +++@V@/opcodes/ia64-opc-a.c @V@/opcodes/ia64opca.c +++@V@/opcodes/ia64-opc-b.c @V@/opcodes/ia64opcb.c +++@V@/opcodes/ia64-opc-d.c @V@/opcodes/ia64opcd.c +++@V@/opcodes/ia64-opc-f.c @V@/opcodes/ia64opcf.c +++@V@/opcodes/ia64-opc-i.c @V@/opcodes/ia64opci.c +++@V@/opcodes/ia64-opc-m.c @V@/opcodes/ia64opcm.c +++@V@/opcodes/ia64-opc-x.c @V@/opcodes/ia64opcx.c +++@V@/opcodes/ia64-opc.c @V@/opcodes/ia64-opc.c +++@V@/opcodes/iq2000-desc.c @V@/opcodes/iq2000desc.c +++@V@/opcodes/iq2000-dis.c @V@/opcodes/iq2000dis.c +++@V@/opcodes/microblaze-opc.h @V@/opcodes/mb-opc.h +++@V@/opcodes/microblaze-dis.c @V@/opcodes/mb-dis.c +++@V@/opcodes/microblaze-dis.h @V@/opcodes/mb-dis.h +++@V@/opcodes/microblaze-opcm.h @V@/opcodes/mb-opcm.h +++@V@/opcodes/m68hc11-dis.c @V@/opcodes/m68hc11dis.c +++@V@/opcodes/m68hc11-opc.c @V@/opcodes/m68hc11opc.c +++@V@/opcodes/microblaze-opc.h @V@/opcodes/mbl-opc.h +++@V@/opcodes/microblaze-opcm.h @V@/opcodes/mbl-opcm.h +++@V@/opcodes/openrisc-asm.c @V@/opcodes/orisc-asm.c +++@V@/opcodes/openrisc-desc.c @V@/opcodes/orisc-desc.c +++@V@/opcodes/openrisc-dis.c @V@/opcodes/orisc-dis.c +++@V@/opcodes/openrisc-ibld.c @V@/opcodes/orisc-ibld.c +++@V@/opcodes/openrisc-opc.c @V@/opcodes/orisc-opc.c +++@V@/opcodes/openrisc-opc.h @V@/opcodes/orisc-opc.h +++@V@/opcodes/openrisc-desc.h @V@/opcodes/orisc-desc.h +++@V@/opcodes/xstormy16-asm.c @V@/opcodes/xst16asm.c +++@V@/opcodes/xstormy16-desc.c @V@/opcodes/xst16dsc.c +++@V@/opcodes/xstormy16-desc.h @V@/opcodes/xst16dsc.h +++@V@/opcodes/xstormy16-dis.c @V@/opcodes/xst16dis.c +++@V@/opcodes/xstormy16-ibld.c @V@/opcodes/xst16ibd.c +++@V@/opcodes/xstormy16-opc.c @V@/opcodes/xst16opc.c +++@V@/opcodes/xstormy16-opc.h @V@/opcodes/xst16opc.h +++@V@/readline/config.h.bot @V@/readline/config.h-bot +++@V@/readline/config.h.in @V@/readline/config.h-in +++@V@/readline/examples/rlfe/config.h.in @V@/readline/examples/rlfe/config.h-in +++@V@/sim/frv/profile-fr400.c @V@/sim/frv/fr400-profile.c +++@V@/sim/cris/semcrisv10f-switch.c @V@/sim/cris/scrisv10f.c +++@V@/sim/cris/semcrisv32f-switch.c @V@/sim/cris/scrisv32f.c +++@V@/sim/frv/profile-fr400.h @V@/sim/frv/fr400-profile.h +++@V@/sim/frv/profile-fr500.c @V@/sim/frv/fr500-profile.c +++@V@/sim/frv/profile-fr500.h @V@/sim/frv/fr500-profile.h +++@V@/sim/frv/profile-fr550.c @V@/sim/frv/fr550-profile.c +++@V@/sim/frv/profile-fr550.h @V@/sim/frv/fr550-profile.h +++@V@/sim/microblaze @V@/sim/mb +++@V@/sim/microblaze/microblaze.h @V@/sim/mb/mb.h +++@V@/sim/microblaze/microblaze.isa @V@/sim/mb/mb.isa +++@V@/sim/m68hc11/dv-m68hc11eepr.c @V@/sim/m68hc11/dv-eepr.c +++@V@/sim/m68hc11/dv-m68hc11sio.c @V@/sim/m68hc11/dv-sio.c +++@V@/sim/m68hc11/dv-m68hc11spi.c @V@/sim/m68hc11/dv-spi.c +++@V@/sim/m68hc11/dv-m68hc11tim.c @V@/sim/m68hc11/dv-tim.c +++@V@/sim/mips/dv-tx3904irc.c @V@/sim/mips/dv-tx3irc.c +++@V@/sim/mips/dv-tx3904sio.c @V@/sim/mips/dv-tx3sio.c +++@V@/sim/mips/dv-tx3904tmr.c @V@/sim/mips/dv-tx3tmr.c +++@V@/sim/mn10300/dv-mn103int.c @V@/sim/mn10300/dv-mn1int.c +++@V@/sim/mn10300/dv-mn103iop.c @V@/sim/mn10300/dv-mn1iop.c +++@V@/sim/mn10300/dv-mn103ser.c @V@/sim/mn10300/dv-mn1ser.c +++@V@/sim/mn10300/dv-mn103tim.c @V@/sim/mn10300/dv-mn1tim.c +++@V@/sim/ppc/.gdbinit @V@/sim/ppc/gdb.ini +++@V@/sim/ppc/corefile-n.h @V@/sim/ppc/corefle-n.h +++@V@/sim/ppc/altivec_expression.h @V@/sim/ppc/av_expression.h +++@V@/sim/ppc/altivec_registers.h @V@/sim/ppc/av_registers.h +++@V@/sim/ppc/idecode_branch.h @V@/sim/ppc/idec_branch.h +++@V@/sim/ppc/idecode_expression.h @V@/sim/ppc/idec_expression.h +++@V@/sim/ppc/idecode_fields.h @V@/sim/ppc/idec_fields.h +++@V@/sim/ppc/sim-endian-n.h @V@/sim/ppc/sim-endn.h +++@V@/sim/sh64/sem-compact-switch.c @V@/sim/sh64/sem-cswitch.c +++@V@/sim/sh64/sem-media-switch.c @V@/sim/sh64/sem-mswitch.c +++@V@/sim/testsuite/d10v-elf/t-ae-ld-d.s @V@/sim/testsuite/d10v-elf/t-ld-d.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld-i.s @V@/sim/testsuite/d10v-elf/t-ld-i.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld-id.s @V@/sim/testsuite/d10v-elf/t-ld-id.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld-im.s @V@/sim/testsuite/d10v-elf/t-ld-im.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld-ip.s @V@/sim/testsuite/d10v-elf/t-ld-ip.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld2w-d.s @V@/sim/testsuite/d10v-elf/t-ld2-d.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld2w-i.s @V@/sim/testsuite/d10v-elf/t-ld2-i.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld2w-id.s @V@/sim/testsuite/d10v-elf/t-ld2-id.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld2w-im.s @V@/sim/testsuite/d10v-elf/t-ld2-im.s +++@V@/sim/testsuite/d10v-elf/t-ae-ld2w-ip.s @V@/sim/testsuite/d10v-elf/t-ld2-ip.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-d.s @V@/sim/testsuite/d10v-elf/t-st-d.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-i.s @V@/sim/testsuite/d10v-elf/t-st-i.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-id.s @V@/sim/testsuite/d10v-elf/t-st-id.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-im.s @V@/sim/testsuite/d10v-elf/t-st-im.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-ip.s @V@/sim/testsuite/d10v-elf/t-st-ip.s +++@V@/sim/testsuite/d10v-elf/t-ae-st-is.s @V@/sim/testsuite/d10v-elf/t-st-is.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-d.s @V@/sim/testsuite/d10v-elf/t-st2-d.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-i.s @V@/sim/testsuite/d10v-elf/t-st2-i.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-id.s @V@/sim/testsuite/d10v-elf/t-st2-id.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-im.s @V@/sim/testsuite/d10v-elf/t-st2-im.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-ip.s @V@/sim/testsuite/d10v-elf/t-st2-ip.s +++@V@/sim/testsuite/d10v-elf/t-ae-st2w-is.s @V@/sim/testsuite/d10v-elf/t-st2-is.s +++@V@/sim/testsuite/d30v-elf/ls-ld4bhu.S @V@/sim/testsuite/d30v-elf/ls-ld4bu.S +++@V@/sim/testsuite/sim/arm/misaligned1.ms @V@/sim/testsuite/sim/arm/mis1.ms +++@V@/sim/testsuite/sim/arm/misaligned2.ms @V@/sim/testsuite/sim/arm/mis2.ms +++@V@/sim/testsuite/sim/arm/misaligned3.ms @V@/sim/testsuite/sim/arm/mis3.ms +++@V@/sim/testsuite/sim/cris/asm/tjmpsrv32-2.ms @V@/sim/testsuite/sim/cris/tjmp32-2.ms +++@V@/sim/testsuite/sim/cris/asm/tjmpsrv32.ms @V@/sim/testsuite/sim/cris/tjmp32.ms +++@V@/sim/testsuite/sim/cris/c/ftruncate1.c @V@/sim/testsuite/sim/cris/ftrunc1.c +++@V@/sim/testsuite/sim/cris/c/ftruncate2.c @V@/sim/testsuite/sim/cris/ftrunc2.c +++@V@/sim/testsuite/sim/cris/c/hellodyn2.c @V@/sim/testsuite/sim/cris/c/hello2dyn.c +++@V@/sim/testsuite/sim/cris/c/hellodyn3.c @V@/sim/testsuite/sim/cris/c/hello3dyn.c +++@V@/sim/testsuite/sim/cris/c/mprotect1.c @V@/sim/testsuite/sim/cris/c/mprot1.c +++@V@/sim/testsuite/sim/cris/c/mprotect2.c @V@/sim/testsuite/sim/cris/c/mprot2.c +++@V@/sim/testsuite/sim/cris/c/readlink1.c @V@/sim/testsuite/sim/cris/rdlink1.c +++@V@/sim/testsuite/sim/cris/c/readlink2.c @V@/sim/testsuite/sim/cris/rdlink2.c +++@V@/sim/testsuite/sim/cris/c/readlink3.c @V@/sim/testsuite/sim/cris/rdlink3.c +++@V@/sim/testsuite/sim/cris/c/readlink4.c @V@/sim/testsuite/sim/cris/rdlink4.c +++@V@/sim/testsuite/sim/cris/c/readlink5.c @V@/sim/testsuite/sim/cris/rdlink5.c +++@V@/sim/testsuite/sim/cris/c/readlink6.c @V@/sim/testsuite/sim/cris/rdlink6.c +++@V@/sim/testsuite/sim/cris/c/readlink7.c @V@/sim/testsuite/sim/cris/rdlink7.c +++@V@/sim/testsuite/sim/cris/c/readlink8.c @V@/sim/testsuite/sim/cris/rdlink8.c +++@V@/sim/testsuite/sim/cris/c/readlink9.c @V@/sim/testsuite/sim/cris/rdlink9.c +++@V@/sim/testsuite/sim/cris/c/readlink10.c @V@/sim/testsuite/sim/cris/rdlink10.c +++@V@/sim/testsuite/sim/cris/c/rtsigprocmask1.c @V@/sim/testsuite/sim/cris/c/rtsig1procmask.c +++@V@/sim/testsuite/sim/cris/c/rtsigprocmask2.c @V@/sim/testsuite/sim/cris/c/rtsig2procmask.c +++@V@/sim/testsuite/sim/cris/c/rtsigsuspend1.c @V@/sim/testsuite/sim/cris/c/rtsig1suspend.c +++@V@/sim/testsuite/sim/cris/c/rtsigsuspend2.c @V@/sim/testsuite/sim/cris/c/rtsig2suspend.c +++@V@/sim/testsuite/sim/cris/c/sigreturn1.c @V@/sim/testsuite/sim/cris/sigret1.c +++@V@/sim/testsuite/sim/cris/c/sigreturn2.c @V@/sim/testsuite/sim/cris/sigret2.c +++@V@/sim/testsuite/sim/cris/c/sigreturn3.c @V@/sim/testsuite/sim/cris/sigret3.c +++@V@/sim/testsuite/sim/cris/c/sigreturn4.c @V@/sim/testsuite/sim/cris/sigret4.c +++@V@/sim/testsuite/sim/cris/c/truncate1.c @V@/sim/testsuite/sim/cris/trunc1.c +++@V@/sim/testsuite/sim/cris/c/truncate2.c @V@/sim/testsuite/sim/cris/trunc2.c +++@V@/sim/testsuite/sim/mips/fpu64-ps-sb1.s @V@/sim/testsuite/sim/mips/fpu64ps-sb1.s +++@V@/sim/testsuite/sim/mips/mips32-dsp2.s @V@/sim/testsuite/sim/mips/mips32-2dsp.s +++@V@/sim/testsuite/sim/frv/interrupts/Ipipe-fr400.cgs @V@/sim/testsuite/sim/frv/interrupts/Ip-fr400.cgs +++@V@/sim/testsuite/sim/frv/interrupts/Ipipe-fr500.cgs @V@/sim/testsuite/sim/frv/interrupts/Ip-fr500.cgs +++@V@/sim/testsuite/sim/frv/interrupts/badalign-fr550.cgs @V@/sim/testsuite/sim/frv/interrupts/fr550-badalign.cgs +++@V@/sim/testsuite/sim/frv/interrupts/compound-fr550.cgs @V@/sim/testsuite/sim/frv/interrupts/fr550-compound.cgs +++@V@/sim/testsuite/sim/frv/interrupts/data_store_error-fr550.cgs @V@/sim/testsuite/sim/frv/interrupts/fr550-data_store_error.cgs +++@V@/sim/testsuite/sim/frv/interrupts/fp_exception-fr550.cgs @V@/sim/testsuite/sim/frv/interrupts/fr550-fp_exception.cgs +++@V@/sim/testsuite/sim/frv/interrupts/insn_access_error-fr550.cgs @V@/sim/testsuite/sim/frv/interrupts/fr550-insn_access_error.cgs +++@V@/sim/testsuite/sim/mips/hilo-hazard-1.s @V@/sim/testsuite/sim/mips/hilo-hz1.s +++@V@/sim/testsuite/sim/mips/hilo-hazard-2.s @V@/sim/testsuite/sim/mips/hilo-hz2.s +++@V@/sim/testsuite/sim/mips/hilo-hazard-3.s @V@/sim/testsuite/sim/mips/hilo-hz3.s +++@V@/sim/testsuite/sim/sh64/compact/ldsl-mach.cgs @V@/sim/testsuite/sim/sh64/compact/mach-ldsl.cgs +++@V@/sim/testsuite/sim/sh64/compact/ldsl-macl.cgs @V@/sim/testsuite/sim/sh64/compact/macl-ldsl.cgs +++@V@/sim/testsuite/sim/sh64/compact/stsl-mach.cgs @V@/sim/testsuite/sim/sh64/compact/mach-stsl.cgs +++@V@/sim/testsuite/sim/sh64/compact/stsl-macl.cgs @V@/sim/testsuite/sim/sh64/compact/macl-stsl.cgs +++@V@/tcl/cygwin/tclConfig.sh.in @V@/tcl/cygwin/tclConfig.sh-in +++@V@/tcl/doc/ExprLongObj.3 @V@/tcl/doc/ExprLObj.3 +++@V@/tcl/mac/tclMacBOAAppInit.c @V@/tcl/mac/tclBOAAppInit.c +++@V@/tcl/mac/tclMacBOAMain.c @V@/tcl/mac/tclBOAMain.c +++@V@/tcl/mac/tclMacInit.c @V@/tcl/mac/tclInit.c +++@V@/tcl/mac/tclMacInterupt.c @V@/tcl/mac/tclInterupt.c +++@V@/tcl/mac/tclMacProjects.sea.hqx @V@/tcl/mac/tclMacProjects.shqx +++@V@/tcl/tests/namespace-old.test @V@/tcl/tests/namespace.otest +++@V@/tcl/unix/tclConfig.sh.in @V@/tcl/unix/tclConfig.sh-in +++@V@/tcl/unix/tclLoadAix.c @V@/tcl/unix/tclLdAix.c +++@V@/tcl/unix/tclLoadAout.c @V@/tcl/unix/tclLdAout.c +++@V@/tcl/unix/tclLoadDl.c @V@/tcl/unix/tclLdDl.c +++@V@/tcl/unix/tclLoadDld.c @V@/tcl/unix/tclLdDld.c +++@V@/tcl/unix/tclUnixFCmd.c @V@/tcl/unix/tclFCmd.c +++@V@/tcl/unix/tclUnixFile.c @V@/tcl/unix/tclFile.c +++@V@/tcl/unix/tclUnixTest.c @V@/tcl/unix/tclTest.c +++@V@/tcl/unix/tclUnixTime.c @V@/tcl/unix/tclTime.c +++@V@/tk/doc/ConfigWidg.3 @V@/tk/doc/CfgWidg.3 +++@V@/tk/doc/ConfigWind.3 @V@/tk/doc/CfgWind.3 +++@V@/tk/library/images/pwrdLogo100.gif @V@/tk/library/images/pwLogo100.gif +++@V@/tk/library/images/pwrdLogo150.gif @V@/tk/library/images/pwLogo150.gif +++@V@/tk/library/images/pwrdLogo175.gif @V@/tk/library/images/pwLogo175.gif +++@V@/tk/library/images/pwrdLogo200.gif @V@/tk/library/images/pwLogo200.gif +++@V@/tk/library/images/pwrdLogo75.gif @V@/tk/library/images/pwLogo75.gif +++@V@/tk/mac/tkMacMenu.c @V@/tk/mac/tkMenu.c +++@V@/tk/mac/tkMacMenubutton.c @V@/tk/mac/tkMenubutton.c +++@V@/tk/mac/tkMacMenus.c @V@/tk/mac/tkMenus.c +++@V@/tk/tests/option.file1 @V@/tk/tests/option1.file +++@V@/tk/tests/option.file2 @V@/tk/tests/option2.file +++@V@/tk/unix/tkConfig.sh.in @V@/tk/unix/tkConfig.sh-in +++@V@/tk/unix/tkUnixFocus.c @V@/tk/unix/tkFocus.c +++@V@/tk/unix/tkUnixFont.c @V@/tk/unix/tkFont.c +++@V@/tk/unix/tkUnixMenu.c @V@/tk/unix/tkMenu.c +++@V@/tk/unix/tkUnixMenubu.c @V@/tk/unix/tkMenubu.c +++@V@/tk/unix/tkUnixScale.c @V@/tk/unix/tkScale.c +++@V@/tk/unix/tkUnixScrlbr.c @V@/tk/unix/tkScrlbr.c +++@V@/tk/unix/tkUnixSelect.c @V@/tk/unix/tkSelect.c +++@V@/tk/unix/tkUnixSend.c @V@/tk/unix/tkSend.c ++diff -Nuar gdb-10.2/gdb/gdb.info-6 gdb-10.2/gdb/gdb.info-6 ++--- gdb-10.2/gdb/gdb.info-6 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/gdb.info-6 2025-04-16 17:06:51.942086800 +0800 ++@@ -0,0 +1,7652 @@ +++This is gdb.info, produced by makeinfo version 6.7 from gdb.texinfo. +++ +++Copyright (C) 1988-2020 Free Software Foundation, Inc. +++ +++ Permission is granted to copy, distribute and/or modify this document +++under the terms of the GNU Free Documentation License, Version 1.3 or +++any later version published by the Free Software Foundation; with the +++Invariant Sections being "Free Software" and "Free Software Needs Free +++Documentation", with the Front-Cover Texts being "A GNU Manual," and +++with the Back-Cover Texts as in (a) below. +++ +++ (a) The FSF's Back-Cover Text is: "You are free to copy and modify +++this GNU Manual. Buying copies from GNU Press supports the FSF in +++developing GNU and promoting software freedom." +++INFO-DIR-SECTION Software development +++START-INFO-DIR-ENTRY +++* Gdb: (gdb). The GNU debugger. +++* gdbserver: (gdb) Server. The GNU debugging server. +++END-INFO-DIR-ENTRY +++ +++ This file documents the GNU debugger GDB. +++ +++ This is the Tenth Edition, of 'Debugging with GDB: the GNU +++Source-Level Debugger' for GDB (GDB) Version 10.1. +++ +++ Copyright (C) 1988-2020 Free Software Foundation, Inc. +++ +++ Permission is granted to copy, distribute and/or modify this document +++under the terms of the GNU Free Documentation License, Version 1.3 or +++any later version published by the Free Software Foundation; with the +++Invariant Sections being "Free Software" and "Free Software Needs Free +++Documentation", with the Front-Cover Texts being "A GNU Manual," and +++with the Back-Cover Texts as in (a) below. +++ +++ (a) The FSF's Back-Cover Text is: "You are free to copy and modify +++this GNU Manual. Buying copies from GNU Press supports the FSF in +++developing GNU and promoting software freedom." +++ +++ +++File: gdb.info, Node: GDB/MI Data Manipulation, Next: GDB/MI Tracepoint Commands, Prev: GDB/MI Variable Objects, Up: GDB/MI +++ +++27.16 GDB/MI Data Manipulation +++============================== +++ +++This section describes the GDB/MI commands that manipulate data: examine +++memory and registers, evaluate expressions, etc. +++ +++ For details about what an addressable memory unit is, *note +++addressable memory unit::. +++ +++The '-data-disassemble' Command +++------------------------------- +++ +++Synopsis +++........ +++ +++ -data-disassemble +++ [ -s START-ADDR -e END-ADDR ] +++ | [ -a ADDR ] +++ | [ -f FILENAME -l LINENUM [ -n LINES ] ] +++ -- MODE +++ +++Where: +++ +++'START-ADDR' +++ is the beginning address (or '$pc') +++'END-ADDR' +++ is the end address +++'ADDR' +++ is an address anywhere within (or the name of) the function to +++ disassemble. If an address is specified, the whole function +++ surrounding that address will be disassembled. If a name is +++ specified, the whole function with that name will be disassembled. +++'FILENAME' +++ is the name of the file to disassemble +++'LINENUM' +++ is the line number to disassemble around +++'LINES' +++ is the number of disassembly lines to be produced. If it is -1, +++ the whole function will be disassembled, in case no END-ADDR is +++ specified. If END-ADDR is specified as a non-zero value, and LINES +++ is lower than the number of disassembly lines between START-ADDR +++ and END-ADDR, only LINES lines are displayed; if LINES is higher +++ than the number of lines between START-ADDR and END-ADDR, only the +++ lines up to END-ADDR are displayed. +++'MODE' +++ is one of: +++ * 0 disassembly only +++ * 1 mixed source and disassembly (deprecated) +++ * 2 disassembly with raw opcodes +++ * 3 mixed source and disassembly with raw opcodes (deprecated) +++ * 4 mixed source and disassembly +++ * 5 mixed source and disassembly with raw opcodes +++ +++ Modes 1 and 3 are deprecated. The output is "source centric" which +++ hasn't proved useful in practice. *Note Machine Code::, for a +++ discussion of the difference between '/m' and '/s' output of the +++ 'disassemble' command. +++ +++Result +++...... +++ +++The result of the '-data-disassemble' command will be a list named +++'asm_insns', the contents of this list depend on the MODE used with the +++'-data-disassemble' command. +++ +++ For modes 0 and 2 the 'asm_insns' list contains tuples with the +++following fields: +++ +++'address' +++ The address at which this instruction was disassembled. +++ +++'func-name' +++ The name of the function this instruction is within. +++ +++'offset' +++ The decimal offset in bytes from the start of 'func-name'. +++ +++'inst' +++ The text disassembly for this 'address'. +++ +++'opcodes' +++ This field is only present for modes 2, 3 and 5. This contains the +++ raw opcode bytes for the 'inst' field. +++ +++ For modes 1, 3, 4 and 5 the 'asm_insns' list contains tuples named +++'src_and_asm_line', each of which has the following fields: +++ +++'line' +++ The line number within 'file'. +++ +++'file' +++ The file name from the compilation unit. This might be an absolute +++ file name or a relative file name depending on the compile command +++ used. +++ +++'fullname' +++ Absolute file name of 'file'. It is converted to a canonical form +++ using the source file search path (*note Specifying Source +++ Directories: Source Path.) and after resolving all the symbolic +++ links. +++ +++ If the source file is not found this field will contain the path as +++ present in the debug information. +++ +++'line_asm_insn' +++ This is a list of tuples containing the disassembly for 'line' in +++ 'file'. The fields of each tuple are the same as for +++ '-data-disassemble' in MODE 0 and 2, so 'address', 'func-name', +++ 'offset', 'inst', and optionally 'opcodes'. +++ +++ Note that whatever included in the 'inst' field, is not manipulated +++directly by GDB/MI, i.e., it is not possible to adjust its format. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'disassemble'. +++ +++Example +++....... +++ +++Disassemble from the current value of '$pc' to '$pc + 20': +++ +++ (gdb) +++ -data-disassemble -s $pc -e "$pc + 20" -- 0 +++ ^done, +++ asm_insns=[ +++ {address="0x000107c0",func-name="main",offset="4", +++ inst="mov 2, %o0"}, +++ {address="0x000107c4",func-name="main",offset="8", +++ inst="sethi %hi(0x11800), %o2"}, +++ {address="0x000107c8",func-name="main",offset="12", +++ inst="or %o2, 0x140, %o1\t! 0x11940 <_lib_version+8>"}, +++ {address="0x000107cc",func-name="main",offset="16", +++ inst="sethi %hi(0x11800), %o2"}, +++ {address="0x000107d0",func-name="main",offset="20", +++ inst="or %o2, 0x168, %o4\t! 0x11968 <_lib_version+48>"}] +++ (gdb) +++ +++ Disassemble the whole 'main' function. Line 32 is part of 'main'. +++ +++ -data-disassemble -f basics.c -l 32 -- 0 +++ ^done,asm_insns=[ +++ {address="0x000107bc",func-name="main",offset="0", +++ inst="save %sp, -112, %sp"}, +++ {address="0x000107c0",func-name="main",offset="4", +++ inst="mov 2, %o0"}, +++ {address="0x000107c4",func-name="main",offset="8", +++ inst="sethi %hi(0x11800), %o2"}, +++ [...] +++ {address="0x0001081c",func-name="main",offset="96",inst="ret "}, +++ {address="0x00010820",func-name="main",offset="100",inst="restore "}] +++ (gdb) +++ +++ Disassemble 3 instructions from the start of 'main': +++ +++ (gdb) +++ -data-disassemble -f basics.c -l 32 -n 3 -- 0 +++ ^done,asm_insns=[ +++ {address="0x000107bc",func-name="main",offset="0", +++ inst="save %sp, -112, %sp"}, +++ {address="0x000107c0",func-name="main",offset="4", +++ inst="mov 2, %o0"}, +++ {address="0x000107c4",func-name="main",offset="8", +++ inst="sethi %hi(0x11800), %o2"}] +++ (gdb) +++ +++ Disassemble 3 instructions from the start of 'main' in mixed mode: +++ +++ (gdb) +++ -data-disassemble -f basics.c -l 32 -n 3 -- 1 +++ ^done,asm_insns=[ +++ src_and_asm_line={line="31", +++ file="../../../src/gdb/testsuite/gdb.mi/basics.c", +++ fullname="/absolute/path/to/src/gdb/testsuite/gdb.mi/basics.c", +++ line_asm_insn=[{address="0x000107bc", +++ func-name="main",offset="0",inst="save %sp, -112, %sp"}]}, +++ src_and_asm_line={line="32", +++ file="../../../src/gdb/testsuite/gdb.mi/basics.c", +++ fullname="/absolute/path/to/src/gdb/testsuite/gdb.mi/basics.c", +++ line_asm_insn=[{address="0x000107c0", +++ func-name="main",offset="4",inst="mov 2, %o0"}, +++ {address="0x000107c4",func-name="main",offset="8", +++ inst="sethi %hi(0x11800), %o2"}]}] +++ (gdb) +++ +++The '-data-evaluate-expression' Command +++--------------------------------------- +++ +++Synopsis +++........ +++ +++ -data-evaluate-expression EXPR +++ +++ Evaluate EXPR as an expression. The expression could contain an +++inferior function call. The function call will execute synchronously. +++If the expression contains spaces, it must be enclosed in double quotes. +++ +++GDB Command +++........... +++ +++The corresponding GDB commands are 'print', 'output', and 'call'. In +++'gdbtk' only, there's a corresponding 'gdb_eval' command. +++ +++Example +++....... +++ +++In the following example, the numbers that precede the commands are the +++"tokens" described in *note GDB/MI Command Syntax: GDB/MI Command +++Syntax. Notice how GDB/MI returns the same tokens in its output. +++ +++ 211-data-evaluate-expression A +++ 211^done,value="1" +++ (gdb) +++ 311-data-evaluate-expression &A +++ 311^done,value="0xefffeb7c" +++ (gdb) +++ 411-data-evaluate-expression A+3 +++ 411^done,value="4" +++ (gdb) +++ 511-data-evaluate-expression "A + 3" +++ 511^done,value="4" +++ (gdb) +++ +++The '-data-list-changed-registers' Command +++------------------------------------------ +++ +++Synopsis +++........ +++ +++ -data-list-changed-registers +++ +++ Display a list of the registers that have changed. +++ +++GDB Command +++........... +++ +++GDB doesn't have a direct analog for this command; 'gdbtk' has the +++corresponding command 'gdb_changed_register_list'. +++ +++Example +++....... +++ +++On a PPC MBX board: +++ +++ (gdb) +++ -exec-continue +++ ^running +++ +++ (gdb) +++ *stopped,reason="breakpoint-hit",disp="keep",bkptno="1",frame={ +++ func="main",args=[],file="try.c",fullname="/home/foo/bar/try.c", +++ line="5",arch="powerpc"} +++ (gdb) +++ -data-list-changed-registers +++ ^done,changed-registers=["0","1","2","4","5","6","7","8","9", +++ "10","11","13","14","15","16","17","18","19","20","21","22","23", +++ "24","25","26","27","28","30","31","64","65","66","67","69"] +++ (gdb) +++ +++The '-data-list-register-names' Command +++--------------------------------------- +++ +++Synopsis +++........ +++ +++ -data-list-register-names [ ( REGNO )+ ] +++ +++ Show a list of register names for the current target. If no +++arguments are given, it shows a list of the names of all the registers. +++If integer numbers are given as arguments, it will print a list of the +++names of the registers corresponding to the arguments. To ensure +++consistency between a register name and its number, the output list may +++include empty register names. +++ +++GDB Command +++........... +++ +++GDB does not have a command which corresponds to +++'-data-list-register-names'. In 'gdbtk' there is a corresponding +++command 'gdb_regnames'. +++ +++Example +++....... +++ +++For the PPC MBX board: +++ (gdb) +++ -data-list-register-names +++ ^done,register-names=["r0","r1","r2","r3","r4","r5","r6","r7", +++ "r8","r9","r10","r11","r12","r13","r14","r15","r16","r17","r18", +++ "r19","r20","r21","r22","r23","r24","r25","r26","r27","r28","r29", +++ "r30","r31","f0","f1","f2","f3","f4","f5","f6","f7","f8","f9", +++ "f10","f11","f12","f13","f14","f15","f16","f17","f18","f19","f20", +++ "f21","f22","f23","f24","f25","f26","f27","f28","f29","f30","f31", +++ "", "pc","ps","cr","lr","ctr","xer"] +++ (gdb) +++ -data-list-register-names 1 2 3 +++ ^done,register-names=["r1","r2","r3"] +++ (gdb) +++ +++The '-data-list-register-values' Command +++---------------------------------------- +++ +++Synopsis +++........ +++ +++ -data-list-register-values +++ [ --skip-unavailable ] FMT [ ( REGNO )*] +++ +++ Display the registers' contents. The format according to which the +++registers' contents are to be returned is given by FMT, followed by an +++optional list of numbers specifying the registers to display. A missing +++list of numbers indicates that the contents of all the registers must be +++returned. The '--skip-unavailable' option indicates that only the +++available registers are to be returned. +++ +++ Allowed formats for FMT are: +++ +++'x' +++ Hexadecimal +++'o' +++ Octal +++'t' +++ Binary +++'d' +++ Decimal +++'r' +++ Raw +++'N' +++ Natural +++ +++GDB Command +++........... +++ +++The corresponding GDB commands are 'info reg', 'info all-reg', and (in +++'gdbtk') 'gdb_fetch_registers'. +++ +++Example +++....... +++ +++For a PPC MBX board (note: line breaks are for readability only, they +++don't appear in the actual output): +++ +++ (gdb) +++ -data-list-register-values r 64 65 +++ ^done,register-values=[{number="64",value="0xfe00a300"}, +++ {number="65",value="0x00029002"}] +++ (gdb) +++ -data-list-register-values x +++ ^done,register-values=[{number="0",value="0xfe0043c8"}, +++ {number="1",value="0x3fff88"},{number="2",value="0xfffffffe"}, +++ {number="3",value="0x0"},{number="4",value="0xa"}, +++ {number="5",value="0x3fff68"},{number="6",value="0x3fff58"}, +++ {number="7",value="0xfe011e98"},{number="8",value="0x2"}, +++ {number="9",value="0xfa202820"},{number="10",value="0xfa202808"}, +++ {number="11",value="0x1"},{number="12",value="0x0"}, +++ {number="13",value="0x4544"},{number="14",value="0xffdfffff"}, +++ {number="15",value="0xffffffff"},{number="16",value="0xfffffeff"}, +++ {number="17",value="0xefffffed"},{number="18",value="0xfffffffe"}, +++ {number="19",value="0xffffffff"},{number="20",value="0xffffffff"}, +++ {number="21",value="0xffffffff"},{number="22",value="0xfffffff7"}, +++ {number="23",value="0xffffffff"},{number="24",value="0xffffffff"}, +++ {number="25",value="0xffffffff"},{number="26",value="0xfffffffb"}, +++ {number="27",value="0xffffffff"},{number="28",value="0xf7bfffff"}, +++ {number="29",value="0x0"},{number="30",value="0xfe010000"}, +++ {number="31",value="0x0"},{number="32",value="0x0"}, +++ {number="33",value="0x0"},{number="34",value="0x0"}, +++ {number="35",value="0x0"},{number="36",value="0x0"}, +++ {number="37",value="0x0"},{number="38",value="0x0"}, +++ {number="39",value="0x0"},{number="40",value="0x0"}, +++ {number="41",value="0x0"},{number="42",value="0x0"}, +++ {number="43",value="0x0"},{number="44",value="0x0"}, +++ {number="45",value="0x0"},{number="46",value="0x0"}, +++ {number="47",value="0x0"},{number="48",value="0x0"}, +++ {number="49",value="0x0"},{number="50",value="0x0"}, +++ {number="51",value="0x0"},{number="52",value="0x0"}, +++ {number="53",value="0x0"},{number="54",value="0x0"}, +++ {number="55",value="0x0"},{number="56",value="0x0"}, +++ {number="57",value="0x0"},{number="58",value="0x0"}, +++ {number="59",value="0x0"},{number="60",value="0x0"}, +++ {number="61",value="0x0"},{number="62",value="0x0"}, +++ {number="63",value="0x0"},{number="64",value="0xfe00a300"}, +++ {number="65",value="0x29002"},{number="66",value="0x202f04b5"}, +++ {number="67",value="0xfe0043b0"},{number="68",value="0xfe00b3e4"}, +++ {number="69",value="0x20002b03"}] +++ (gdb) +++ +++The '-data-read-memory' Command +++------------------------------- +++ +++This command is deprecated, use '-data-read-memory-bytes' instead. +++ +++Synopsis +++........ +++ +++ -data-read-memory [ -o BYTE-OFFSET ] +++ ADDRESS WORD-FORMAT WORD-SIZE +++ NR-ROWS NR-COLS [ ASCHAR ] +++ +++where: +++ +++'ADDRESS' +++ An expression specifying the address of the first memory word to be +++ read. Complex expressions containing embedded white space should +++ be quoted using the C convention. +++ +++'WORD-FORMAT' +++ The format to be used to print the memory words. The notation is +++ the same as for GDB's 'print' command (*note Output Formats: Output +++ Formats.). +++ +++'WORD-SIZE' +++ The size of each memory word in bytes. +++ +++'NR-ROWS' +++ The number of rows in the output table. +++ +++'NR-COLS' +++ The number of columns in the output table. +++ +++'ASCHAR' +++ If present, indicates that each row should include an ASCII dump. +++ The value of ASCHAR is used as a padding character when a byte is +++ not a member of the printable ASCII character set (printable ASCII +++ characters are those whose code is between 32 and 126, +++ inclusively). +++ +++'BYTE-OFFSET' +++ An offset to add to the ADDRESS before fetching memory. +++ +++ This command displays memory contents as a table of NR-ROWS by +++NR-COLS words, each word being WORD-SIZE bytes. In total, 'NR-ROWS * +++NR-COLS * WORD-SIZE' bytes are read (returned as 'total-bytes'). Should +++less than the requested number of bytes be returned by the target, the +++missing words are identified using 'N/A'. The number of bytes read from +++the target is returned in 'nr-bytes' and the starting address used to +++read memory in 'addr'. +++ +++ The address of the next/previous row or page is available in +++'next-row' and 'prev-row', 'next-page' and 'prev-page'. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'x'. 'gdbtk' has 'gdb_get_mem' memory +++read command. +++ +++Example +++....... +++ +++Read six bytes of memory starting at 'bytes+6' but then offset by '-6' +++bytes. Format as three rows of two columns. One byte per word. +++Display each word in hex. +++ +++ (gdb) +++ 9-data-read-memory -o -6 -- bytes+6 x 1 3 2 +++ 9^done,addr="0x00001390",nr-bytes="6",total-bytes="6", +++ next-row="0x00001396",prev-row="0x0000138e",next-page="0x00001396", +++ prev-page="0x0000138a",memory=[ +++ {addr="0x00001390",data=["0x00","0x01"]}, +++ {addr="0x00001392",data=["0x02","0x03"]}, +++ {addr="0x00001394",data=["0x04","0x05"]}] +++ (gdb) +++ +++ Read two bytes of memory starting at address 'shorts + 64' and +++display as a single word formatted in decimal. +++ +++ (gdb) +++ 5-data-read-memory shorts+64 d 2 1 1 +++ 5^done,addr="0x00001510",nr-bytes="2",total-bytes="2", +++ next-row="0x00001512",prev-row="0x0000150e", +++ next-page="0x00001512",prev-page="0x0000150e",memory=[ +++ {addr="0x00001510",data=["128"]}] +++ (gdb) +++ +++ Read thirty two bytes of memory starting at 'bytes+16' and format as +++eight rows of four columns. Include a string encoding with 'x' used as +++the non-printable character. +++ +++ (gdb) +++ 4-data-read-memory bytes+16 x 1 8 4 x +++ 4^done,addr="0x000013a0",nr-bytes="32",total-bytes="32", +++ next-row="0x000013c0",prev-row="0x0000139c", +++ next-page="0x000013c0",prev-page="0x00001380",memory=[ +++ {addr="0x000013a0",data=["0x10","0x11","0x12","0x13"],ascii="xxxx"}, +++ {addr="0x000013a4",data=["0x14","0x15","0x16","0x17"],ascii="xxxx"}, +++ {addr="0x000013a8",data=["0x18","0x19","0x1a","0x1b"],ascii="xxxx"}, +++ {addr="0x000013ac",data=["0x1c","0x1d","0x1e","0x1f"],ascii="xxxx"}, +++ {addr="0x000013b0",data=["0x20","0x21","0x22","0x23"],ascii=" !\"#"}, +++ {addr="0x000013b4",data=["0x24","0x25","0x26","0x27"],ascii="$%&'"}, +++ {addr="0x000013b8",data=["0x28","0x29","0x2a","0x2b"],ascii="()*+"}, +++ {addr="0x000013bc",data=["0x2c","0x2d","0x2e","0x2f"],ascii=",-./"}] +++ (gdb) +++ +++The '-data-read-memory-bytes' Command +++------------------------------------- +++ +++Synopsis +++........ +++ +++ -data-read-memory-bytes [ -o OFFSET ] +++ ADDRESS COUNT +++ +++where: +++ +++'ADDRESS' +++ An expression specifying the address of the first addressable +++ memory unit to be read. Complex expressions containing embedded +++ white space should be quoted using the C convention. +++ +++'COUNT' +++ The number of addressable memory units to read. This should be an +++ integer literal. +++ +++'OFFSET' +++ The offset relative to ADDRESS at which to start reading. This +++ should be an integer literal. This option is provided so that a +++ frontend is not required to first evaluate address and then perform +++ address arithmetics itself. +++ +++ This command attempts to read all accessible memory regions in the +++specified range. First, all regions marked as unreadable in the memory +++map (if one is defined) will be skipped. *Note Memory Region +++Attributes::. Second, GDB will attempt to read the remaining regions. +++For each one, if reading full region results in an errors, GDB will try +++to read a subset of the region. +++ +++ In general, every single memory unit in the region may be readable or +++not, and the only way to read every readable unit is to try a read at +++every address, which is not practical. Therefore, GDB will attempt to +++read all accessible memory units at either beginning or the end of the +++region, using a binary division scheme. This heuristic works well for +++reading across a memory map boundary. Note that if a region has a +++readable range that is neither at the beginning or the end, GDB will not +++read it. +++ +++ The result record (*note GDB/MI Result Records::) that is output of +++the command includes a field named 'memory' whose content is a list of +++tuples. Each tuple represent a successfully read memory block and has +++the following fields: +++ +++'begin' +++ The start address of the memory block, as hexadecimal literal. +++ +++'end' +++ The end address of the memory block, as hexadecimal literal. +++ +++'offset' +++ The offset of the memory block, as hexadecimal literal, relative to +++ the start address passed to '-data-read-memory-bytes'. +++ +++'contents' +++ The contents of the memory block, in hex. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'x'. +++ +++Example +++....... +++ +++ (gdb) +++ -data-read-memory-bytes &a 10 +++ ^done,memory=[{begin="0xbffff154",offset="0x00000000", +++ end="0xbffff15e", +++ contents="01000000020000000300"}] +++ (gdb) +++ +++The '-data-write-memory-bytes' Command +++-------------------------------------- +++ +++Synopsis +++........ +++ +++ -data-write-memory-bytes ADDRESS CONTENTS +++ -data-write-memory-bytes ADDRESS CONTENTS [COUNT] +++ +++where: +++ +++'ADDRESS' +++ An expression specifying the address of the first addressable +++ memory unit to be written. Complex expressions containing embedded +++ white space should be quoted using the C convention. +++ +++'CONTENTS' +++ The hex-encoded data to write. It is an error if CONTENTS does not +++ represent an integral number of addressable memory units. +++ +++'COUNT' +++ Optional argument indicating the number of addressable memory units +++ to be written. If COUNT is greater than CONTENTS' length, GDB will +++ repeatedly write CONTENTS until it fills COUNT memory units. +++ +++GDB Command +++........... +++ +++There's no corresponding GDB command. +++ +++Example +++....... +++ +++ (gdb) +++ -data-write-memory-bytes &a "aabbccdd" +++ ^done +++ (gdb) +++ +++ (gdb) +++ -data-write-memory-bytes &a "aabbccdd" 16e +++ ^done +++ (gdb) +++ +++ +++File: gdb.info, Node: GDB/MI Tracepoint Commands, Next: GDB/MI Symbol Query, Prev: GDB/MI Data Manipulation, Up: GDB/MI +++ +++27.17 GDB/MI Tracepoint Commands +++================================ +++ +++The commands defined in this section implement MI support for +++tracepoints. For detailed introduction, see *note Tracepoints::. +++ +++The '-trace-find' Command +++------------------------- +++ +++Synopsis +++........ +++ +++ -trace-find MODE [PARAMETERS...] +++ +++ Find a trace frame using criteria defined by MODE and PARAMETERS. +++The following table lists permissible modes and their parameters. For +++details of operation, see *note tfind::. +++ +++'none' +++ No parameters are required. Stops examining trace frames. +++ +++'frame-number' +++ An integer is required as parameter. Selects tracepoint frame with +++ that index. +++ +++'tracepoint-number' +++ An integer is required as parameter. Finds next trace frame that +++ corresponds to tracepoint with the specified number. +++ +++'pc' +++ An address is required as parameter. Finds next trace frame that +++ corresponds to any tracepoint at the specified address. +++ +++'pc-inside-range' +++ Two addresses are required as parameters. Finds next trace frame +++ that corresponds to a tracepoint at an address inside the specified +++ range. Both bounds are considered to be inside the range. +++ +++'pc-outside-range' +++ Two addresses are required as parameters. Finds next trace frame +++ that corresponds to a tracepoint at an address outside the +++ specified range. Both bounds are considered to be inside the +++ range. +++ +++'line' +++ Line specification is required as parameter. *Note Specify +++ Location::. Finds next trace frame that corresponds to a +++ tracepoint at the specified location. +++ +++ If 'none' was passed as MODE, the response does not have fields. +++Otherwise, the response may have the following fields: +++ +++'found' +++ This field has either '0' or '1' as the value, depending on whether +++ a matching tracepoint was found. +++ +++'traceframe' +++ The index of the found traceframe. This field is present iff the +++ 'found' field has value of '1'. +++ +++'tracepoint' +++ The index of the found tracepoint. This field is present iff the +++ 'found' field has value of '1'. +++ +++'frame' +++ The information about the frame corresponding to the found trace +++ frame. This field is present only if a trace frame was found. +++ *Note GDB/MI Frame Information::, for description of this field. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tfind'. +++ +++-trace-define-variable +++---------------------- +++ +++Synopsis +++........ +++ +++ -trace-define-variable NAME [ VALUE ] +++ +++ Create trace variable NAME if it does not exist. If VALUE is +++specified, sets the initial value of the specified trace variable to +++that value. Note that the NAME should start with the '$' character. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tvariable'. +++ +++The '-trace-frame-collected' Command +++------------------------------------ +++ +++Synopsis +++........ +++ +++ -trace-frame-collected +++ [--var-print-values VAR_PVAL] +++ [--comp-print-values COMP_PVAL] +++ [--registers-format REGFORMAT] +++ [--memory-contents] +++ +++ This command returns the set of collected objects, register names, +++trace state variable names, memory ranges and computed expressions that +++have been collected at a particular trace frame. The optional +++parameters to the command affect the output format in different ways. +++See the output description table below for more details. +++ +++ The reported names can be used in the normal manner to create varobjs +++and inspect the objects themselves. The items returned by this command +++are categorized so that it is clear which is a variable, which is a +++register, which is a trace state variable, which is a memory range and +++which is a computed expression. +++ +++ For instance, if the actions were +++ collect myVar, myArray[myIndex], myObj.field, myPtr->field, myCount + 2 +++ collect *(int*)0xaf02bef0@40 +++ +++the object collected in its entirety would be 'myVar'. The object +++'myArray' would be partially collected, because only the element at +++index 'myIndex' would be collected. The remaining objects would be +++computed expressions. +++ +++ An example output would be: +++ +++ (gdb) +++ -trace-frame-collected +++ ^done, +++ explicit-variables=[{name="myVar",value="1"}], +++ computed-expressions=[{name="myArray[myIndex]",value="0"}, +++ {name="myObj.field",value="0"}, +++ {name="myPtr->field",value="1"}, +++ {name="myCount + 2",value="3"}, +++ {name="$tvar1 + 1",value="43970027"}], +++ registers=[{number="0",value="0x7fe2c6e79ec8"}, +++ {number="1",value="0x0"}, +++ {number="2",value="0x4"}, +++ ... +++ {number="125",value="0x0"}], +++ tvars=[{name="$tvar1",current="43970026"}], +++ memory=[{address="0x0000000000602264",length="4"}, +++ {address="0x0000000000615bc0",length="4"}] +++ (gdb) +++ +++ Where: +++ +++'explicit-variables' +++ The set of objects that have been collected in their entirety (as +++ opposed to collecting just a few elements of an array or a few +++ struct members). For each object, its name and value are printed. +++ The '--var-print-values' option affects how or whether the value +++ field is output. If VAR_PVAL is 0, then print only the names; if +++ it is 1, print also their values; and if it is 2, print the name, +++ type and value for simple data types, and the name and type for +++ arrays, structures and unions. +++ +++'computed-expressions' +++ The set of computed expressions that have been collected at the +++ current trace frame. The '--comp-print-values' option affects this +++ set like the '--var-print-values' option affects the +++ 'explicit-variables' set. See above. +++ +++'registers' +++ The registers that have been collected at the current trace frame. +++ For each register collected, the name and current value are +++ returned. The value is formatted according to the +++ '--registers-format' option. See the '-data-list-register-values' +++ command for a list of the allowed formats. The default is 'x'. +++ +++'tvars' +++ The trace state variables that have been collected at the current +++ trace frame. For each trace state variable collected, the name and +++ current value are returned. +++ +++'memory' +++ The set of memory ranges that have been collected at the current +++ trace frame. Its content is a list of tuples. Each tuple +++ represents a collected memory range and has the following fields: +++ +++ 'address' +++ The start address of the memory range, as hexadecimal literal. +++ +++ 'length' +++ The length of the memory range, as decimal literal. +++ +++ 'contents' +++ The contents of the memory block, in hex. This field is only +++ present if the '--memory-contents' option is specified. +++ +++GDB Command +++........... +++ +++There is no corresponding GDB command. +++ +++Example +++....... +++ +++-trace-list-variables +++--------------------- +++ +++Synopsis +++........ +++ +++ -trace-list-variables +++ +++ Return a table of all defined trace variables. Each element of the +++table has the following fields: +++ +++'name' +++ The name of the trace variable. This field is always present. +++ +++'initial' +++ The initial value. This is a 64-bit signed integer. This field is +++ always present. +++ +++'current' +++ The value the trace variable has at the moment. This is a 64-bit +++ signed integer. This field is absent iff current value is not +++ defined, for example if the trace was never run, or is presently +++ running. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tvariables'. +++ +++Example +++....... +++ +++ (gdb) +++ -trace-list-variables +++ ^done,trace-variables={nr_rows="1",nr_cols="3", +++ hdr=[{width="15",alignment="-1",col_name="name",colhdr="Name"}, +++ {width="11",alignment="-1",col_name="initial",colhdr="Initial"}, +++ {width="11",alignment="-1",col_name="current",colhdr="Current"}], +++ body=[variable={name="$trace_timestamp",initial="0"} +++ variable={name="$foo",initial="10",current="15"}]} +++ (gdb) +++ +++-trace-save +++----------- +++ +++Synopsis +++........ +++ +++ -trace-save [ -r ] [ -ctf ] FILENAME +++ +++ Saves the collected trace data to FILENAME. Without the '-r' option, +++the data is downloaded from the target and saved in a local file. With +++the '-r' option the target is asked to perform the save. +++ +++ By default, this command will save the trace in the tfile format. +++You can supply the optional '-ctf' argument to save it the CTF format. +++See *note Trace Files:: for more information about CTF. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tsave'. +++ +++-trace-start +++------------ +++ +++Synopsis +++........ +++ +++ -trace-start +++ +++ Starts a tracing experiment. The result of this command does not +++have any fields. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tstart'. +++ +++-trace-status +++------------- +++ +++Synopsis +++........ +++ +++ -trace-status +++ +++ Obtains the status of a tracing experiment. The result may include +++the following fields: +++ +++'supported' +++ May have a value of either '0', when no tracing operations are +++ supported, '1', when all tracing operations are supported, or +++ 'file' when examining trace file. In the latter case, examining of +++ trace frame is possible but new tracing experiement cannot be +++ started. This field is always present. +++ +++'running' +++ May have a value of either '0' or '1' depending on whether tracing +++ experiement is in progress on target. This field is present if +++ 'supported' field is not '0'. +++ +++'stop-reason' +++ Report the reason why the tracing was stopped last time. This +++ field may be absent iff tracing was never stopped on target yet. +++ The value of 'request' means the tracing was stopped as result of +++ the '-trace-stop' command. The value of 'overflow' means the +++ tracing buffer is full. The value of 'disconnection' means tracing +++ was automatically stopped when GDB has disconnected. The value of +++ 'passcount' means tracing was stopped when a tracepoint was passed +++ a maximal number of times for that tracepoint. This field is +++ present if 'supported' field is not '0'. +++ +++'stopping-tracepoint' +++ The number of tracepoint whose passcount as exceeded. This field +++ is present iff the 'stop-reason' field has the value of +++ 'passcount'. +++ +++'frames' +++'frames-created' +++ The 'frames' field is a count of the total number of trace frames +++ in the trace buffer, while 'frames-created' is the total created +++ during the run, including ones that were discarded, such as when a +++ circular trace buffer filled up. Both fields are optional. +++ +++'buffer-size' +++'buffer-free' +++ These fields tell the current size of the tracing buffer and the +++ remaining space. These fields are optional. +++ +++'circular' +++ The value of the circular trace buffer flag. '1' means that the +++ trace buffer is circular and old trace frames will be discarded if +++ necessary to make room, '0' means that the trace buffer is linear +++ and may fill up. +++ +++'disconnected' +++ The value of the disconnected tracing flag. '1' means that tracing +++ will continue after GDB disconnects, '0' means that the trace run +++ will stop. +++ +++'trace-file' +++ The filename of the trace file being examined. This field is +++ optional, and only present when examining a trace file. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tstatus'. +++ +++-trace-stop +++----------- +++ +++Synopsis +++........ +++ +++ -trace-stop +++ +++ Stops a tracing experiment. The result of this command has the same +++fields as '-trace-status', except that the 'supported' and 'running' +++fields are not output. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'tstop'. +++ +++ +++File: gdb.info, Node: GDB/MI Symbol Query, Next: GDB/MI File Commands, Prev: GDB/MI Tracepoint Commands, Up: GDB/MI +++ +++27.18 GDB/MI Symbol Query Commands +++================================== +++ +++The '-symbol-info-functions' Command +++------------------------------------ +++ +++Synopsis +++........ +++ +++ -symbol-info-functions [--include-nondebug] +++ [--type TYPE_REGEXP] +++ [--name NAME_REGEXP] +++ [--max-results LIMIT] +++ +++Return a list containing the names and types for all global functions +++taken from the debug information. The functions are grouped by source +++file, and shown with the line number on which each function is defined. +++ +++ The '--include-nondebug' option causes the output to include code +++symbols from the symbol table. +++ +++ The options '--type' and '--name' allow the symbols returned to be +++filtered based on either the name of the function, or the type signature +++of the function. +++ +++ The option '--max-results' restricts the command to return no more +++than LIMIT results. If exactly LIMIT results are returned then there +++might be additional results available if a higher limit is used. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info functions'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-functions +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"}, +++ {line="42", name="main", type="int ()", +++ description="int main();"}, +++ {line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="33", name="f2", type="float (another_float_t)", +++ description="float f2(another_float_t);"}, +++ {line="39", name="f3", type="int (another_int_t)", +++ description="int f3(another_int_t);"}, +++ {line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"}]}]} +++ (gdb) +++ -symbol-info-functions --name f1 +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"}]}]} +++ (gdb) +++ -symbol-info-functions --type void +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"}]}]} +++ (gdb) +++ -symbol-info-functions --include-nondebug +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"}, +++ {line="42", name="main", type="int ()", +++ description="int main();"}, +++ {line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="33", name="f2", type="float (another_float_t)", +++ description="float f2(another_float_t);"}, +++ {line="39", name="f3", type="int (another_int_t)", +++ description="int f3(another_int_t);"}, +++ {line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"}]}], +++ nondebug= +++ [{address="0x0000000000400398",name="_init"}, +++ {address="0x00000000004003b0",name="_start"}, +++ ... +++ ]} +++ +++The '-symbol-info-module-functions' Command +++------------------------------------------- +++ +++Synopsis +++........ +++ +++ -symbol-info-module-functions [--module MODULE_REGEXP] +++ [--name NAME_REGEXP] +++ [--type TYPE_REGEXP] +++ +++Return a list containing the names of all known functions within all +++know Fortran modules. The functions are grouped by source file and +++containing module, and shown with the line number on which each function +++is defined. +++ +++ The option '--module' only returns results for modules matching +++MODULE_REGEXP. The option '--name' only returns functions whose name +++matches NAME_REGEXP, and '--type' only returns functions whose type +++matches TYPE_REGEXP. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info module functions'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-module-functions +++ ^done,symbols= +++ [{module="mod1", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="21",name="mod1::check_all",type="void (void)", +++ description="void mod1::check_all(void);"}]}]}, +++ {module="mod2", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="30",name="mod2::check_var_i",type="void (void)", +++ description="void mod2::check_var_i(void);"}]}]}, +++ {module="mod3", +++ files=[{filename="/projec/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/projec/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="21",name="mod3::check_all",type="void (void)", +++ description="void mod3::check_all(void);"}, +++ {line="27",name="mod3::check_mod2",type="void (void)", +++ description="void mod3::check_mod2(void);"}]}]}, +++ {module="modmany", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="35",name="modmany::check_some",type="void (void)", +++ description="void modmany::check_some(void);"}]}]}, +++ {module="moduse", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="44",name="moduse::check_all",type="void (void)", +++ description="void moduse::check_all(void);"}, +++ {line="49",name="moduse::check_var_x",type="void (void)", +++ description="void moduse::check_var_x(void);"}]}]}] +++ +++The '-symbol-info-module-variables' Command +++------------------------------------------- +++ +++Synopsis +++........ +++ +++ -symbol-info-module-variables [--module MODULE_REGEXP] +++ [--name NAME_REGEXP] +++ [--type TYPE_REGEXP] +++ +++Return a list containing the names of all known variables within all +++know Fortran modules. The variables are grouped by source file and +++containing module, and shown with the line number on which each variable +++is defined. +++ +++ The option '--module' only returns results for modules matching +++MODULE_REGEXP. The option '--name' only returns variables whose name +++matches NAME_REGEXP, and '--type' only returns variables whose type +++matches TYPE_REGEXP. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info module variables'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-module-variables +++ ^done,symbols= +++ [{module="mod1", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="18",name="mod1::var_const",type="integer(kind=4)", +++ description="integer(kind=4) mod1::var_const;"}, +++ {line="17",name="mod1::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod1::var_i;"}]}]}, +++ {module="mod2", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="28",name="mod2::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod2::var_i;"}]}]}, +++ {module="mod3", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="18",name="mod3::mod1",type="integer(kind=4)", +++ description="integer(kind=4) mod3::mod1;"}, +++ {line="17",name="mod3::mod2",type="integer(kind=4)", +++ description="integer(kind=4) mod3::mod2;"}, +++ {line="19",name="mod3::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod3::var_i;"}]}]}, +++ {module="modmany", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="33",name="modmany::var_a",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_a;"}, +++ {line="33",name="modmany::var_b",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_b;"}, +++ {line="33",name="modmany::var_c",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_c;"}, +++ {line="33",name="modmany::var_i",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_i;"}]}]}, +++ {module="moduse", +++ files=[{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="42",name="moduse::var_x",type="integer(kind=4)", +++ description="integer(kind=4) moduse::var_x;"}, +++ {line="42",name="moduse::var_y",type="integer(kind=4)", +++ description="integer(kind=4) moduse::var_y;"}]}]}] +++ +++The '-symbol-info-modules' Command +++---------------------------------- +++ +++Synopsis +++........ +++ +++ -symbol-info-modules [--name NAME_REGEXP] +++ [--max-results LIMIT] +++ +++ +++Return a list containing the names of all known Fortran modules. The +++modules are grouped by source file, and shown with the line number on +++which each modules is defined. +++ +++ The option '--name' allows the modules returned to be filtered based +++the name of the module. +++ +++ The option '--max-results' restricts the command to return no more +++than LIMIT results. If exactly LIMIT results are returned then there +++might be additional results available if a higher limit is used. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info modules'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-modules +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="16",name="mod1"}, +++ {line="22",name="mod2"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="16",name="mod3"}, +++ {line="22",name="modmany"}, +++ {line="26",name="moduse"}]}]} +++ (gdb) +++ -symbol-info-modules --name mod[123] +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[{line="16",name="mod1"}, +++ {line="22",name="mod2"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[{line="16",name="mod3"}]}]} +++ +++The '-symbol-info-types' Command +++-------------------------------- +++ +++Synopsis +++........ +++ +++ -symbol-info-types [--name NAME_REGEXP] +++ [--max-results LIMIT] +++ +++ +++Return a list of all defined types. The types are grouped by source +++file, and shown with the line number on which each user defined type is +++defined. Some base types are not defined in the source code but are +++added to the debug information by the compiler, for example 'int', +++'float', etc.; these types do not have an associated line number. +++ +++ The option '--name' allows the list of types returned to be filtered +++by name. +++ +++ The option '--max-results' restricts the command to return no more +++than LIMIT results. If exactly LIMIT results are returned then there +++might be additional results available if a higher limit is used. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info types'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-types +++ ^done,symbols= +++ {debug= +++ [{filename="gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{name="float"}, +++ {name="int"}, +++ {line="27",name="typedef int my_int_t;"}]}, +++ {filename="gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="24",name="typedef float another_float_t;"}, +++ {line="23",name="typedef int another_int_t;"}, +++ {name="float"}, +++ {name="int"}]}]} +++ (gdb) +++ -symbol-info-types --name _int_ +++ ^done,symbols= +++ {debug= +++ [{filename="gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="27",name="typedef int my_int_t;"}]}, +++ {filename="gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="23",name="typedef int another_int_t;"}]}]} +++ +++The '-symbol-info-variables' Command +++------------------------------------ +++ +++Synopsis +++........ +++ +++ -symbol-info-variables [--include-nondebug] +++ [--type TYPE_REGEXP] +++ [--name NAME_REGEXP] +++ [--max-results LIMIT] +++ +++ +++Return a list containing the names and types for all global variables +++taken from the debug information. The variables are grouped by source +++file, and shown with the line number on which each variable is defined. +++ +++ The '--include-nondebug' option causes the output to include data +++symbols from the symbol table. +++ +++ The options '--type' and '--name' allow the symbols returned to be +++filtered based on either the name of the variable, or the type of the +++variable. +++ +++ The option '--max-results' restricts the command to return no more +++than LIMIT results. If exactly LIMIT results are returned then there +++might be additional results available if a higher limit is used. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info variables'. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-info-variables +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="25",name="global_f1",type="float", +++ description="static float global_f1;"}, +++ {line="24",name="global_i1",type="int", +++ description="static int global_i1;"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="21",name="global_f2",type="int", +++ description="int global_f2;"}, +++ {line="20",name="global_i2",type="int", +++ description="int global_i2;"}, +++ {line="19",name="global_f1",type="float", +++ description="static float global_f1;"}, +++ {line="18",name="global_i1",type="int", +++ description="static int global_i1;"}]}]} +++ (gdb) +++ -symbol-info-variables --name f1 +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="25",name="global_f1",type="float", +++ description="static float global_f1;"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="19",name="global_f1",type="float", +++ description="static float global_f1;"}]}]} +++ (gdb) +++ -symbol-info-variables --type float +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="25",name="global_f1",type="float", +++ description="static float global_f1;"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="19",name="global_f1",type="float", +++ description="static float global_f1;"}]}]} +++ (gdb) +++ -symbol-info-variables --include-nondebug +++ ^done,symbols= +++ {debug= +++ [{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[{line="25",name="global_f1",type="float", +++ description="static float global_f1;"}, +++ {line="24",name="global_i1",type="int", +++ description="static int global_i1;"}]}, +++ {filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[{line="21",name="global_f2",type="int", +++ description="int global_f2;"}, +++ {line="20",name="global_i2",type="int", +++ description="int global_i2;"}, +++ {line="19",name="global_f1",type="float", +++ description="static float global_f1;"}, +++ {line="18",name="global_i1",type="int", +++ description="static int global_i1;"}]}], +++ nondebug= +++ [{address="0x00000000004005d0",name="_IO_stdin_used"}, +++ {address="0x00000000004005d8",name="__dso_handle"} +++ ... +++ ]} +++ +++The '-symbol-list-lines' Command +++-------------------------------- +++ +++Synopsis +++........ +++ +++ -symbol-list-lines FILENAME +++ +++ Print the list of lines that contain code and their associated +++program addresses for the given source filename. The entries are sorted +++in ascending PC order. +++ +++GDB Command +++........... +++ +++There is no corresponding GDB command. +++ +++Example +++....... +++ +++ (gdb) +++ -symbol-list-lines basics.c +++ ^done,lines=[{pc="0x08048554",line="7"},{pc="0x0804855a",line="8"}] +++ (gdb) +++ +++ +++File: gdb.info, Node: GDB/MI File Commands, Next: GDB/MI Target Manipulation, Prev: GDB/MI Symbol Query, Up: GDB/MI +++ +++27.19 GDB/MI File Commands +++========================== +++ +++This section describes the GDB/MI commands to specify executable file +++names and to read in and obtain symbol table information. +++ +++The '-file-exec-and-symbols' Command +++------------------------------------ +++ +++Synopsis +++........ +++ +++ -file-exec-and-symbols FILE +++ +++ Specify the executable file to be debugged. This file is the one +++from which the symbol table is also read. If no file is specified, the +++command clears the executable and symbol information. If breakpoints +++are set when using this command with no arguments, GDB will produce +++error messages. Otherwise, no output is produced, except a completion +++notification. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'file'. +++ +++Example +++....... +++ +++ (gdb) +++ -file-exec-and-symbols /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++ ^done +++ (gdb) +++ +++The '-file-exec-file' Command +++----------------------------- +++ +++Synopsis +++........ +++ +++ -file-exec-file FILE +++ +++ Specify the executable file to be debugged. Unlike +++'-file-exec-and-symbols', the symbol table is _not_ read from this file. +++If used without argument, GDB clears the information about the +++executable file. No output is produced, except a completion +++notification. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'exec-file'. +++ +++Example +++....... +++ +++ (gdb) +++ -file-exec-file /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++ ^done +++ (gdb) +++ +++The '-file-list-exec-source-file' Command +++----------------------------------------- +++ +++Synopsis +++........ +++ +++ -file-list-exec-source-file +++ +++ List the line number, the current source file, and the absolute path +++to the current source file for the current executable. The macro +++information field has a value of '1' or '0' depending on whether or not +++the file includes preprocessor macro information. +++ +++GDB Command +++........... +++ +++The GDB equivalent is 'info source' +++ +++Example +++....... +++ +++ (gdb) +++ 123-file-list-exec-source-file +++ 123^done,line="1",file="foo.c",fullname="/home/bar/foo.c,macro-info="1" +++ (gdb) +++ +++The '-file-list-exec-source-files' Command +++------------------------------------------ +++ +++Synopsis +++........ +++ +++ -file-list-exec-source-files +++ +++ List the source files for the current executable. +++ +++ It will always output both the filename and fullname (absolute file +++name) of a source file. +++ +++GDB Command +++........... +++ +++The GDB equivalent is 'info sources'. 'gdbtk' has an analogous command +++'gdb_listfiles'. +++ +++Example +++....... +++ +++ (gdb) +++ -file-list-exec-source-files +++ ^done,files=[ +++ {file=foo.c,fullname=/home/foo.c}, +++ {file=/home/bar.c,fullname=/home/bar.c}, +++ {file=gdb_could_not_find_fullpath.c}] +++ (gdb) +++ +++The '-file-list-shared-libraries' Command +++----------------------------------------- +++ +++Synopsis +++........ +++ +++ -file-list-shared-libraries [ REGEXP ] +++ +++ List the shared libraries in the program. With a regular expression +++REGEXP, only those libraries whose names match REGEXP are listed. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info shared'. The fields have a +++similar meaning to the '=library-loaded' notification. The 'ranges' +++field specifies the multiple segments belonging to this library. Each +++range has the following fields: +++ +++'from' +++ The address defining the inclusive lower bound of the segment. +++'to' +++ The address defining the exclusive upper bound of the segment. +++ +++Example +++....... +++ +++ (gdb) +++ -file-list-exec-source-files +++ ^done,shared-libraries=[ +++ {id="/lib/libfoo.so",target-name="/lib/libfoo.so",host-name="/lib/libfoo.so",symbols-loaded="1",thread-group="i1",ranges=[{from="0x72815989",to="0x728162c0"}]}, +++ {id="/lib/libbar.so",target-name="/lib/libbar.so",host-name="/lib/libbar.so",symbols-loaded="1",thread-group="i1",ranges=[{from="0x76ee48c0",to="0x76ee9160"}]}] +++ (gdb) +++ +++The '-file-symbol-file' Command +++------------------------------- +++ +++Synopsis +++........ +++ +++ -file-symbol-file FILE +++ +++ Read symbol table info from the specified FILE argument. When used +++without arguments, clears GDB's symbol table info. No output is +++produced, except for a completion notification. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'symbol-file'. +++ +++Example +++....... +++ +++ (gdb) +++ -file-symbol-file /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++ ^done +++ (gdb) +++ +++ +++File: gdb.info, Node: GDB/MI Target Manipulation, Next: GDB/MI File Transfer Commands, Prev: GDB/MI File Commands, Up: GDB/MI +++ +++27.20 GDB/MI Target Manipulation Commands +++========================================= +++ +++The '-target-attach' Command +++---------------------------- +++ +++Synopsis +++........ +++ +++ -target-attach PID | GID | FILE +++ +++ Attach to a process PID or a file FILE outside of GDB, or a thread +++group GID. If attaching to a thread group, the id previously returned +++by '-list-thread-groups --available' must be used. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'attach'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-attach 34 +++ =thread-created,id="1" +++ *stopped,thread-id="1",frame={addr="0xb7f7e410",func="bar",args=[]} +++ ^done +++ (gdb) +++ +++The '-target-detach' Command +++---------------------------- +++ +++Synopsis +++........ +++ +++ -target-detach [ PID | GID ] +++ +++ Detach from the remote target which normally resumes its execution. +++If either PID or GID is specified, detaches from either the specified +++process, or specified thread group. There's no output. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'detach'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-detach +++ ^done +++ (gdb) +++ +++The '-target-disconnect' Command +++-------------------------------- +++ +++Synopsis +++........ +++ +++ -target-disconnect +++ +++ Disconnect from the remote target. There's no output and the target +++is generally not resumed. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'disconnect'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-disconnect +++ ^done +++ (gdb) +++ +++The '-target-download' Command +++------------------------------ +++ +++Synopsis +++........ +++ +++ -target-download +++ +++ Loads the executable onto the remote target. It prints out an update +++message every half second, which includes the fields: +++ +++'section' +++ The name of the section. +++'section-sent' +++ The size of what has been sent so far for that section. +++'section-size' +++ The size of the section. +++'total-sent' +++ The total size of what was sent so far (the current and the +++ previous sections). +++'total-size' +++ The size of the overall executable to download. +++ +++Each message is sent as status record (*note GDB/MI Output Syntax: +++GDB/MI Output Syntax.). +++ +++ In addition, it prints the name and size of the sections, as they are +++downloaded. These messages include the following fields: +++ +++'section' +++ The name of the section. +++'section-size' +++ The size of the section. +++'total-size' +++ The size of the overall executable to download. +++ +++At the end, a summary is printed. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'load'. +++ +++Example +++....... +++ +++Note: each status message appears on a single line. Here the messages +++have been broken down so that they can fit onto a page. +++ +++ (gdb) +++ -target-download +++ +download,{section=".text",section-size="6668",total-size="9880"} +++ +download,{section=".text",section-sent="512",section-size="6668", +++ total-sent="512",total-size="9880"} +++ +download,{section=".text",section-sent="1024",section-size="6668", +++ total-sent="1024",total-size="9880"} +++ +download,{section=".text",section-sent="1536",section-size="6668", +++ total-sent="1536",total-size="9880"} +++ +download,{section=".text",section-sent="2048",section-size="6668", +++ total-sent="2048",total-size="9880"} +++ +download,{section=".text",section-sent="2560",section-size="6668", +++ total-sent="2560",total-size="9880"} +++ +download,{section=".text",section-sent="3072",section-size="6668", +++ total-sent="3072",total-size="9880"} +++ +download,{section=".text",section-sent="3584",section-size="6668", +++ total-sent="3584",total-size="9880"} +++ +download,{section=".text",section-sent="4096",section-size="6668", +++ total-sent="4096",total-size="9880"} +++ +download,{section=".text",section-sent="4608",section-size="6668", +++ total-sent="4608",total-size="9880"} +++ +download,{section=".text",section-sent="5120",section-size="6668", +++ total-sent="5120",total-size="9880"} +++ +download,{section=".text",section-sent="5632",section-size="6668", +++ total-sent="5632",total-size="9880"} +++ +download,{section=".text",section-sent="6144",section-size="6668", +++ total-sent="6144",total-size="9880"} +++ +download,{section=".text",section-sent="6656",section-size="6668", +++ total-sent="6656",total-size="9880"} +++ +download,{section=".init",section-size="28",total-size="9880"} +++ +download,{section=".fini",section-size="28",total-size="9880"} +++ +download,{section=".data",section-size="3156",total-size="9880"} +++ +download,{section=".data",section-sent="512",section-size="3156", +++ total-sent="7236",total-size="9880"} +++ +download,{section=".data",section-sent="1024",section-size="3156", +++ total-sent="7748",total-size="9880"} +++ +download,{section=".data",section-sent="1536",section-size="3156", +++ total-sent="8260",total-size="9880"} +++ +download,{section=".data",section-sent="2048",section-size="3156", +++ total-sent="8772",total-size="9880"} +++ +download,{section=".data",section-sent="2560",section-size="3156", +++ total-sent="9284",total-size="9880"} +++ +download,{section=".data",section-sent="3072",section-size="3156", +++ total-sent="9796",total-size="9880"} +++ ^done,address="0x10004",load-size="9880",transfer-rate="6586", +++ write-rate="429" +++ (gdb) +++ +++GDB Command +++........... +++ +++No equivalent. +++ +++Example +++....... +++ +++N.A. +++ +++The '-target-flash-erase' Command +++--------------------------------- +++ +++Synopsis +++........ +++ +++ -target-flash-erase +++ +++ Erases all known flash memory regions on the target. +++ +++ The corresponding GDB command is 'flash-erase'. +++ +++ The output is a list of flash regions that have been erased, with +++starting addresses and memory region sizes. +++ +++ (gdb) +++ -target-flash-erase +++ ^done,erased-regions={address="0x0",size="0x40000"} +++ (gdb) +++ +++The '-target-select' Command +++---------------------------- +++ +++Synopsis +++........ +++ +++ -target-select TYPE PARAMETERS ... +++ +++ Connect GDB to the remote target. This command takes two args: +++ +++'TYPE' +++ The type of target, for instance 'remote', etc. +++'PARAMETERS' +++ Device names, host names and the like. *Note Commands for Managing +++ Targets: Target Commands, for more details. +++ +++ The output is a connection notification, followed by the address at +++which the target program is, in the following form: +++ +++ ^connected,addr="ADDRESS",func="FUNCTION NAME", +++ args=[ARG LIST] +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'target'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-select remote /dev/ttya +++ ^connected,addr="0xfe00a300",func="??",args=[] +++ (gdb) +++ +++ +++File: gdb.info, Node: GDB/MI File Transfer Commands, Next: GDB/MI Ada Exceptions Commands, Prev: GDB/MI Target Manipulation, Up: GDB/MI +++ +++27.21 GDB/MI File Transfer Commands +++=================================== +++ +++The '-target-file-put' Command +++------------------------------ +++ +++Synopsis +++........ +++ +++ -target-file-put HOSTFILE TARGETFILE +++ +++ Copy file HOSTFILE from the host system (the machine running GDB) to +++TARGETFILE on the target system. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'remote put'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-file-put localfile remotefile +++ ^done +++ (gdb) +++ +++The '-target-file-get' Command +++------------------------------ +++ +++Synopsis +++........ +++ +++ -target-file-get TARGETFILE HOSTFILE +++ +++ Copy file TARGETFILE from the target system to HOSTFILE on the host +++system. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'remote get'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-file-get remotefile localfile +++ ^done +++ (gdb) +++ +++The '-target-file-delete' Command +++--------------------------------- +++ +++Synopsis +++........ +++ +++ -target-file-delete TARGETFILE +++ +++ Delete TARGETFILE from the target system. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'remote delete'. +++ +++Example +++....... +++ +++ (gdb) +++ -target-file-delete remotefile +++ ^done +++ (gdb) +++ +++ +++File: gdb.info, Node: GDB/MI Ada Exceptions Commands, Next: GDB/MI Support Commands, Prev: GDB/MI File Transfer Commands, Up: GDB/MI +++ +++27.22 Ada Exceptions GDB/MI Commands +++==================================== +++ +++The '-info-ada-exceptions' Command +++---------------------------------- +++ +++Synopsis +++........ +++ +++ -info-ada-exceptions [ REGEXP] +++ +++ List all Ada exceptions defined within the program being debugged. +++With a regular expression REGEXP, only those exceptions whose names +++match REGEXP are listed. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info exceptions'. +++ +++Result +++...... +++ +++The result is a table of Ada exceptions. The following columns are +++defined for each exception: +++ +++'name' +++ The name of the exception. +++ +++'address' +++ The address of the exception. +++ +++Example +++....... +++ +++ -info-ada-exceptions aint +++ ^done,ada-exceptions={nr_rows="2",nr_cols="2", +++ hdr=[{width="1",alignment="-1",col_name="name",colhdr="Name"}, +++ {width="1",alignment="-1",col_name="address",colhdr="Address"}], +++ body=[{name="constraint_error",address="0x0000000000613da0"}, +++ {name="const.aint_global_e",address="0x0000000000613b00"}]} +++ +++Catching Ada Exceptions +++----------------------- +++ +++The commands describing how to ask GDB to stop when a program raises an +++exception are described at *note Ada Exception GDB/MI Catchpoint +++Commands::. +++ +++ +++File: gdb.info, Node: GDB/MI Support Commands, Next: GDB/MI Miscellaneous Commands, Prev: GDB/MI Ada Exceptions Commands, Up: GDB/MI +++ +++27.23 GDB/MI Support Commands +++============================= +++ +++Since new commands and features get regularly added to GDB/MI, some +++commands are available to help front-ends query the debugger about +++support for these capabilities. Similarly, it is also possible to query +++GDB about target support of certain features. +++ +++The '-info-gdb-mi-command' Command +++---------------------------------- +++ +++Synopsis +++........ +++ +++ -info-gdb-mi-command CMD_NAME +++ +++ Query support for the GDB/MI command named CMD_NAME. +++ +++ Note that the dash ('-') starting all GDB/MI commands is technically +++not part of the command name (*note GDB/MI Input Syntax::), and thus +++should be omitted in CMD_NAME. However, for ease of use, this command +++also accepts the form with the leading dash. +++ +++GDB Command +++........... +++ +++There is no corresponding GDB command. +++ +++Result +++...... +++ +++The result is a tuple. There is currently only one field: +++ +++'exists' +++ This field is equal to '"true"' if the GDB/MI command exists, +++ '"false"' otherwise. +++ +++Example +++....... +++ +++Here is an example where the GDB/MI command does not exist: +++ +++ -info-gdb-mi-command unsupported-command +++ ^done,command={exists="false"} +++ +++And here is an example where the GDB/MI command is known to the +++debugger: +++ +++ -info-gdb-mi-command symbol-list-lines +++ ^done,command={exists="true"} +++ +++The '-list-features' Command +++---------------------------- +++ +++Returns a list of particular features of the MI protocol that this +++version of gdb implements. A feature can be a command, or a new field +++in an output of some command, or even an important bugfix. While a +++frontend can sometimes detect presence of a feature at runtime, it is +++easier to perform detection at debugger startup. +++ +++ The command returns a list of strings, with each string naming an +++available feature. Each returned string is just a name, it does not +++have any internal structure. The list of possible feature names is +++given below. +++ +++ Example output: +++ +++ (gdb) -list-features +++ ^done,result=["feature1","feature2"] +++ +++ The current list of features is: +++ +++'frozen-varobjs' +++ Indicates support for the '-var-set-frozen' command, as well as +++ possible presence of the 'frozen' field in the output of +++ '-varobj-create'. +++'pending-breakpoints' +++ Indicates support for the '-f' option to the '-break-insert' +++ command. +++'python' +++ Indicates Python scripting support, Python-based pretty-printing +++ commands, and possible presence of the 'display_hint' field in the +++ output of '-var-list-children' +++'thread-info' +++ Indicates support for the '-thread-info' command. +++'data-read-memory-bytes' +++ Indicates support for the '-data-read-memory-bytes' and the +++ '-data-write-memory-bytes' commands. +++'breakpoint-notifications' +++ Indicates that changes to breakpoints and breakpoints created via +++ the CLI will be announced via async records. +++'ada-task-info' +++ Indicates support for the '-ada-task-info' command. +++'language-option' +++ Indicates that all GDB/MI commands accept the '--language' option +++ (*note Context management::). +++'info-gdb-mi-command' +++ Indicates support for the '-info-gdb-mi-command' command. +++'undefined-command-error-code' +++ Indicates support for the "undefined-command" error code in error +++ result records, produced when trying to execute an undefined GDB/MI +++ command (*note GDB/MI Result Records::). +++'exec-run-start-option' +++ Indicates that the '-exec-run' command supports the '--start' +++ option (*note GDB/MI Program Execution::). +++'data-disassemble-a-option' +++ Indicates that the '-data-disassemble' command supports the '-a' +++ option (*note GDB/MI Data Manipulation::). +++ +++The '-list-target-features' Command +++----------------------------------- +++ +++Returns a list of particular features that are supported by the target. +++Those features affect the permitted MI commands, but unlike the features +++reported by the '-list-features' command, the features depend on which +++target GDB is using at the moment. Whenever a target can change, due to +++commands such as '-target-select', '-target-attach' or '-exec-run', the +++list of target features may change, and the frontend should obtain it +++again. Example output: +++ +++ (gdb) -list-target-features +++ ^done,result=["async"] +++ +++ The current list of features is: +++ +++'async' +++ Indicates that the target is capable of asynchronous command +++ execution, which means that GDB will accept further commands while +++ the target is running. +++ +++'reverse' +++ Indicates that the target is capable of reverse execution. *Note +++ Reverse Execution::, for more information. +++ +++ +++File: gdb.info, Node: GDB/MI Miscellaneous Commands, Prev: GDB/MI Support Commands, Up: GDB/MI +++ +++27.24 Miscellaneous GDB/MI Commands +++=================================== +++ +++The '-gdb-exit' Command +++----------------------- +++ +++Synopsis +++........ +++ +++ -gdb-exit +++ +++ Exit GDB immediately. +++ +++GDB Command +++........... +++ +++Approximately corresponds to 'quit'. +++ +++Example +++....... +++ +++ (gdb) +++ -gdb-exit +++ ^exit +++ +++The '-gdb-set' Command +++---------------------- +++ +++Synopsis +++........ +++ +++ -gdb-set +++ +++ Set an internal GDB variable. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'set'. +++ +++Example +++....... +++ +++ (gdb) +++ -gdb-set $foo=3 +++ ^done +++ (gdb) +++ +++The '-gdb-show' Command +++----------------------- +++ +++Synopsis +++........ +++ +++ -gdb-show +++ +++ Show the current value of a GDB variable. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'show'. +++ +++Example +++....... +++ +++ (gdb) +++ -gdb-show annotate +++ ^done,value="0" +++ (gdb) +++ +++The '-gdb-version' Command +++-------------------------- +++ +++Synopsis +++........ +++ +++ -gdb-version +++ +++ Show version information for GDB. Used mostly in testing. +++ +++GDB Command +++........... +++ +++The GDB equivalent is 'show version'. GDB by default shows this +++information when you start an interactive session. +++ +++Example +++....... +++ +++ (gdb) +++ -gdb-version +++ ~GNU gdb 5.2.1 +++ ~Copyright 2000 Free Software Foundation, Inc. +++ ~GDB is free software, covered by the GNU General Public License, and +++ ~you are welcome to change it and/or distribute copies of it under +++ ~ certain conditions. +++ ~Type "show copying" to see the conditions. +++ ~There is absolutely no warranty for GDB. Type "show warranty" for +++ ~ details. +++ ~This GDB was configured as +++ "--host=sparc-sun-solaris2.5.1 --target=ppc-eabi". +++ ^done +++ (gdb) +++ +++The '-list-thread-groups' Command +++--------------------------------- +++ +++Synopsis +++-------- +++ +++ -list-thread-groups [ --available ] [ --recurse 1 ] [ GROUP ... ] +++ +++ Lists thread groups (*note Thread groups::). When a single thread +++group is passed as the argument, lists the children of that group. When +++several thread group are passed, lists information about those thread +++groups. Without any parameters, lists information about all top-level +++thread groups. +++ +++ Normally, thread groups that are being debugged are reported. With +++the '--available' option, GDB reports thread groups available on the +++target. +++ +++ The output of this command may have either a 'threads' result or a +++'groups' result. The 'thread' result has a list of tuples as value, +++with each tuple describing a thread (*note GDB/MI Thread Information::). +++The 'groups' result has a list of tuples as value, each tuple describing +++a thread group. If top-level groups are requested (that is, no +++parameter is passed), or when several groups are passed, the output +++always has a 'groups' result. The format of the 'group' result is +++described below. +++ +++ To reduce the number of roundtrips it's possible to list thread +++groups together with their children, by passing the '--recurse' option +++and the recursion depth. Presently, only recursion depth of 1 is +++permitted. If this option is present, then every reported thread group +++will also include its children, either as 'group' or 'threads' field. +++ +++ In general, any combination of option and parameters is permitted, +++with the following caveats: +++ +++ * When a single thread group is passed, the output will typically be +++ the 'threads' result. Because threads may not contain anything, +++ the 'recurse' option will be ignored. +++ +++ * When the '--available' option is passed, limited information may be +++ available. In particular, the list of threads of a process might +++ be inaccessible. Further, specifying specific thread groups might +++ not give any performance advantage over listing all thread groups. +++ The frontend should assume that '-list-thread-groups --available' +++ is always an expensive operation and cache the results. +++ +++ The 'groups' result is a list of tuples, where each tuple may have +++the following fields: +++ +++'id' +++ Identifier of the thread group. This field is always present. The +++ identifier is an opaque string; frontends should not try to convert +++ it to an integer, even though it might look like one. +++ +++'type' +++ The type of the thread group. At present, only 'process' is a +++ valid type. +++ +++'pid' +++ The target-specific process identifier. This field is only present +++ for thread groups of type 'process' and only if the process exists. +++ +++'exit-code' +++ The exit code of this group's last exited thread, formatted in +++ octal. This field is only present for thread groups of type +++ 'process' and only if the process is not running. +++ +++'num_children' +++ The number of children this thread group has. This field may be +++ absent for an available thread group. +++ +++'threads' +++ This field has a list of tuples as value, each tuple describing a +++ thread. It may be present if the '--recurse' option is specified, +++ and it's actually possible to obtain the threads. +++ +++'cores' +++ This field is a list of integers, each identifying a core that one +++ thread of the group is running on. This field may be absent if +++ such information is not available. +++ +++'executable' +++ The name of the executable file that corresponds to this thread +++ group. The field is only present for thread groups of type +++ 'process', and only if there is a corresponding executable file. +++ +++Example +++------- +++ +++ gdb +++ -list-thread-groups +++ ^done,groups=[{id="17",type="process",pid="yyy",num_children="2"}] +++ -list-thread-groups 17 +++ ^done,threads=[{id="2",target-id="Thread 0xb7e14b90 (LWP 21257)", +++ frame={level="0",addr="0xffffe410",func="__kernel_vsyscall",args=[]},state="running"}, +++ {id="1",target-id="Thread 0xb7e156b0 (LWP 21254)", +++ frame={level="0",addr="0x0804891f",func="foo",args=[{name="i",value="10"}], +++ file="/tmp/a.c",fullname="/tmp/a.c",line="158",arch="i386:x86_64"},state="running"}]] +++ -list-thread-groups --available +++ ^done,groups=[{id="17",type="process",pid="yyy",num_children="2",cores=[1,2]}] +++ -list-thread-groups --available --recurse 1 +++ ^done,groups=[{id="17", types="process",pid="yyy",num_children="2",cores=[1,2], +++ threads=[{id="1",target-id="Thread 0xb7e14b90",cores=[1]}, +++ {id="2",target-id="Thread 0xb7e14b90",cores=[2]}]},..] +++ -list-thread-groups --available --recurse 1 17 18 +++ ^done,groups=[{id="17", types="process",pid="yyy",num_children="2",cores=[1,2], +++ threads=[{id="1",target-id="Thread 0xb7e14b90",cores=[1]}, +++ {id="2",target-id="Thread 0xb7e14b90",cores=[2]}]},...] +++ +++The '-info-os' Command +++---------------------- +++ +++Synopsis +++........ +++ +++ -info-os [ TYPE ] +++ +++ If no argument is supplied, the command returns a table of available +++operating-system-specific information types. If one of these types is +++supplied as an argument TYPE, then the command returns a table of data +++of that type. +++ +++ The types of information available depend on the target operating +++system. +++ +++GDB Command +++........... +++ +++The corresponding GDB command is 'info os'. +++ +++Example +++....... +++ +++When run on a GNU/Linux system, the output will look something like +++this: +++ +++ gdb +++ -info-os +++ ^done,OSDataTable={nr_rows="10",nr_cols="3", +++ hdr=[{width="10",alignment="-1",col_name="col0",colhdr="Type"}, +++ {width="10",alignment="-1",col_name="col1",colhdr="Description"}, +++ {width="10",alignment="-1",col_name="col2",colhdr="Title"}], +++ body=[item={col0="cpus",col1="Listing of all cpus/cores on the system", +++ col2="CPUs"}, +++ item={col0="files",col1="Listing of all file descriptors", +++ col2="File descriptors"}, +++ item={col0="modules",col1="Listing of all loaded kernel modules", +++ col2="Kernel modules"}, +++ item={col0="msg",col1="Listing of all message queues", +++ col2="Message queues"}, +++ item={col0="processes",col1="Listing of all processes", +++ col2="Processes"}, +++ item={col0="procgroups",col1="Listing of all process groups", +++ col2="Process groups"}, +++ item={col0="semaphores",col1="Listing of all semaphores", +++ col2="Semaphores"}, +++ item={col0="shm",col1="Listing of all shared-memory regions", +++ col2="Shared-memory regions"}, +++ item={col0="sockets",col1="Listing of all internet-domain sockets", +++ col2="Sockets"}, +++ item={col0="threads",col1="Listing of all threads", +++ col2="Threads"}] +++ gdb +++ -info-os processes +++ ^done,OSDataTable={nr_rows="190",nr_cols="4", +++ hdr=[{width="10",alignment="-1",col_name="col0",colhdr="pid"}, +++ {width="10",alignment="-1",col_name="col1",colhdr="user"}, +++ {width="10",alignment="-1",col_name="col2",colhdr="command"}, +++ {width="10",alignment="-1",col_name="col3",colhdr="cores"}], +++ body=[item={col0="1",col1="root",col2="/sbin/init",col3="0"}, +++ item={col0="2",col1="root",col2="[kthreadd]",col3="1"}, +++ item={col0="3",col1="root",col2="[ksoftirqd/0]",col3="0"}, +++ ... +++ item={col0="26446",col1="stan",col2="bash",col3="0"}, +++ item={col0="28152",col1="stan",col2="bash",col3="1"}]} +++ (gdb) +++ +++ (Note that the MI output here includes a '"Title"' column that does +++not appear in command-line 'info os'; this column is useful for MI +++clients that want to enumerate the types of data, such as in a popup +++menu, but is needless clutter on the command line, and 'info os' omits +++it.) +++ +++The '-add-inferior' Command +++--------------------------- +++ +++Synopsis +++-------- +++ +++ -add-inferior +++ +++ Creates a new inferior (*note Inferiors Connections and Programs::). +++The created inferior is not associated with any executable. Such +++association may be established with the '-file-exec-and-symbols' command +++(*note GDB/MI File Commands::). The command response has a single +++field, 'inferior', whose value is the identifier of the thread group +++corresponding to the new inferior. +++ +++Example +++------- +++ +++ gdb +++ -add-inferior +++ ^done,inferior="i3" +++ +++The '-interpreter-exec' Command +++------------------------------- +++ +++Synopsis +++-------- +++ +++ -interpreter-exec INTERPRETER COMMAND +++ +++ Execute the specified COMMAND in the given INTERPRETER. +++ +++GDB Command +++----------- +++ +++The corresponding GDB command is 'interpreter-exec'. +++ +++Example +++------- +++ +++ (gdb) +++ -interpreter-exec console "break main" +++ &"During symbol reading, couldn't parse type; debugger out of date?.\n" +++ &"During symbol reading, bad structure-type format.\n" +++ ~"Breakpoint 1 at 0x8074fc6: file ../../src/gdb/main.c, line 743.\n" +++ ^done +++ (gdb) +++ +++The '-inferior-tty-set' Command +++------------------------------- +++ +++Synopsis +++-------- +++ +++ -inferior-tty-set /dev/pts/1 +++ +++ Set terminal for future runs of the program being debugged. +++ +++GDB Command +++----------- +++ +++The corresponding GDB command is 'set inferior-tty' /dev/pts/1. +++ +++Example +++------- +++ +++ (gdb) +++ -inferior-tty-set /dev/pts/1 +++ ^done +++ (gdb) +++ +++The '-inferior-tty-show' Command +++-------------------------------- +++ +++Synopsis +++-------- +++ +++ -inferior-tty-show +++ +++ Show terminal for future runs of program being debugged. +++ +++GDB Command +++----------- +++ +++The corresponding GDB command is 'show inferior-tty'. +++ +++Example +++------- +++ +++ (gdb) +++ -inferior-tty-set /dev/pts/1 +++ ^done +++ (gdb) +++ -inferior-tty-show +++ ^done,inferior_tty_terminal="/dev/pts/1" +++ (gdb) +++ +++The '-enable-timings' Command +++----------------------------- +++ +++Synopsis +++-------- +++ +++ -enable-timings [yes | no] +++ +++ Toggle the printing of the wallclock, user and system times for an MI +++command as a field in its output. This command is to help frontend +++developers optimize the performance of their code. No argument is +++equivalent to 'yes'. +++ +++GDB Command +++----------- +++ +++No equivalent. +++ +++Example +++------- +++ +++ (gdb) +++ -enable-timings +++ ^done +++ (gdb) +++ -break-insert main +++ ^done,bkpt={number="1",type="breakpoint",disp="keep",enabled="y", +++ addr="0x080484ed",func="main",file="myprog.c", +++ fullname="/home/nickrob/myprog.c",line="73",thread-groups=["i1"], +++ times="0"}, +++ time={wallclock="0.05185",user="0.00800",system="0.00000"} +++ (gdb) +++ -enable-timings no +++ ^done +++ (gdb) +++ -exec-run +++ ^running +++ (gdb) +++ *stopped,reason="breakpoint-hit",disp="keep",bkptno="1",thread-id="0", +++ frame={addr="0x080484ed",func="main",args=[{name="argc",value="1"}, +++ {name="argv",value="0xbfb60364"}],file="myprog.c", +++ fullname="/home/nickrob/myprog.c",line="73",arch="i386:x86_64"} +++ (gdb) +++ +++The '-complete' Command +++----------------------- +++ +++Synopsis +++-------- +++ +++ -complete COMMAND +++ +++ Show a list of completions for partially typed CLI COMMAND. +++ +++ This command is intended for GDB/MI frontends that cannot use two +++separate CLI and MI channels -- for example: because of lack of PTYs +++like on Windows or because GDB is used remotely via a SSH connection. +++ +++Result +++------ +++ +++The result consists of two or three fields: +++ +++'completion' +++ This field contains the completed COMMAND. If COMMAND has no known +++ completions, this field is omitted. +++ +++'matches' +++ This field contains a (possibly empty) array of matches. It is +++ always present. +++ +++'max_completions_reached' +++ This field contains '1' if number of known completions is above +++ 'max-completions' limit (*note Completion::), otherwise it contains +++ '0'. It is always present. +++ +++GDB Command +++----------- +++ +++The corresponding GDB command is 'complete'. +++ +++Example +++------- +++ +++ (gdb) +++ -complete br +++ ^done,completion="break", +++ matches=["break","break-range"], +++ max_completions_reached="0" +++ (gdb) +++ -complete "b ma" +++ ^done,completion="b ma", +++ matches=["b madvise","b main"],max_completions_reached="0" +++ (gdb) +++ -complete "b push_b" +++ ^done,completion="b push_back(", +++ matches=[ +++ "b A::push_back(void*)", +++ "b std::string::push_back(char)", +++ "b std::vector >::push_back(int&&)"], +++ max_completions_reached="0" +++ (gdb) +++ -complete "nonexist" +++ ^done,matches=[],max_completions_reached="0" +++ (gdb) +++ +++ +++ +++File: gdb.info, Node: Annotations, Next: JIT Interface, Prev: GDB/MI, Up: Top +++ +++28 GDB Annotations +++****************** +++ +++This chapter describes annotations in GDB. Annotations were designed to +++interface GDB to graphical user interfaces or other similar programs +++which want to interact with GDB at a relatively high level. +++ +++ The annotation mechanism has largely been superseded by GDB/MI (*note +++GDB/MI::). +++ +++* Menu: +++ +++* Annotations Overview:: What annotations are; the general syntax. +++* Server Prefix:: Issuing a command without affecting user state. +++* Prompting:: Annotations marking GDB's need for input. +++* Errors:: Annotations for error messages. +++* Invalidation:: Some annotations describe things now invalid. +++* Annotations for Running:: +++ Whether the program is running, how it stopped, etc. +++* Source Annotations:: Annotations describing source code. +++ +++ +++File: gdb.info, Node: Annotations Overview, Next: Server Prefix, Up: Annotations +++ +++28.1 What is an Annotation? +++=========================== +++ +++Annotations start with a newline character, two 'control-z' characters, +++and the name of the annotation. If there is no additional information +++associated with this annotation, the name of the annotation is followed +++immediately by a newline. If there is additional information, the name +++of the annotation is followed by a space, the additional information, +++and a newline. The additional information cannot contain newline +++characters. +++ +++ Any output not beginning with a newline and two 'control-z' +++characters denotes literal output from GDB. Currently there is no need +++for GDB to output a newline followed by two 'control-z' characters, but +++if there was such a need, the annotations could be extended with an +++'escape' annotation which means those three characters as output. +++ +++ The annotation LEVEL, which is specified using the '--annotate' +++command line option (*note Mode Options::), controls how much +++information GDB prints together with its prompt, values of expressions, +++source lines, and other types of output. Level 0 is for no annotations, +++level 1 is for use when GDB is run as a subprocess of GNU Emacs, level 3 +++is the maximum annotation suitable for programs that control GDB, and +++level 2 annotations have been made obsolete (*note Limitations of the +++Annotation Interface: (annotate)Limitations.). +++ +++'set annotate LEVEL' +++ The GDB command 'set annotate' sets the level of annotations to the +++ specified LEVEL. +++ +++'show annotate' +++ Show the current annotation level. +++ +++ This chapter describes level 3 annotations. +++ +++ A simple example of starting up GDB with annotations is: +++ +++ $ gdb --annotate=3 +++ GNU gdb 6.0 +++ Copyright 2003 Free Software Foundation, Inc. +++ GDB is free software, covered by the GNU General Public License, +++ and you are welcome to change it and/or distribute copies of it +++ under certain conditions. +++ Type "show copying" to see the conditions. +++ There is absolutely no warranty for GDB. Type "show warranty" +++ for details. +++ This GDB was configured as "i386-pc-linux-gnu" +++ +++ ^Z^Zpre-prompt +++ (gdb) +++ ^Z^Zprompt +++ quit +++ +++ ^Z^Zpost-prompt +++ $ +++ +++ Here 'quit' is input to GDB; the rest is output from GDB. The three +++lines beginning '^Z^Z' (where '^Z' denotes a 'control-z' character) are +++annotations; the rest is output from GDB. +++ +++ +++File: gdb.info, Node: Server Prefix, Next: Prompting, Prev: Annotations Overview, Up: Annotations +++ +++28.2 The Server Prefix +++====================== +++ +++If you prefix a command with 'server ' then it will not affect the +++command history, nor will it affect GDB's notion of which command to +++repeat if is pressed on a line by itself. This means that +++commands can be run behind a user's back by a front-end in a transparent +++manner. +++ +++ The 'server ' prefix does not affect the recording of values into the +++value history; to print a value without recording it into the value +++history, use the 'output' command instead of the 'print' command. +++ +++ Using this prefix also disables confirmation requests (*note +++confirmation requests::). +++ +++ +++File: gdb.info, Node: Prompting, Next: Errors, Prev: Server Prefix, Up: Annotations +++ +++28.3 Annotation for GDB Input +++============================= +++ +++When GDB prompts for input, it annotates this fact so it is possible to +++know when to send output, when the output from a given command is over, +++etc. +++ +++ Different kinds of input each have a different "input type". Each +++input type has three annotations: a 'pre-' annotation, which denotes the +++beginning of any prompt which is being output, a plain annotation, which +++denotes the end of the prompt, and then a 'post-' annotation which +++denotes the end of any echo which may (or may not) be associated with +++the input. For example, the 'prompt' input type features the following +++annotations: +++ +++ ^Z^Zpre-prompt +++ ^Z^Zprompt +++ ^Z^Zpost-prompt +++ +++ The input types are +++ +++'prompt' +++ When GDB is prompting for a command (the main GDB prompt). +++ +++'commands' +++ When GDB prompts for a set of commands, like in the 'commands' +++ command. The annotations are repeated for each command which is +++ input. +++ +++'overload-choice' +++ When GDB wants the user to select between various overloaded +++ functions. +++ +++'query' +++ When GDB wants the user to confirm a potentially dangerous +++ operation. +++ +++'prompt-for-continue' +++ When GDB is asking the user to press return to continue. Note: +++ Don't expect this to work well; instead use 'set height 0' to +++ disable prompting. This is because the counting of lines is buggy +++ in the presence of annotations. +++ +++ +++File: gdb.info, Node: Errors, Next: Invalidation, Prev: Prompting, Up: Annotations +++ +++28.4 Errors +++=========== +++ +++ ^Z^Zquit +++ +++ This annotation occurs right before GDB responds to an interrupt. +++ +++ ^Z^Zerror +++ +++ This annotation occurs right before GDB responds to an error. +++ +++ Quit and error annotations indicate that any annotations which GDB +++was in the middle of may end abruptly. For example, if a +++'value-history-begin' annotation is followed by a 'error', one cannot +++expect to receive the matching 'value-history-end'. One cannot expect +++not to receive it either, however; an error annotation does not +++necessarily mean that GDB is immediately returning all the way to the +++top level. +++ +++ A quit or error annotation may be preceded by +++ +++ ^Z^Zerror-begin +++ +++ Any output between that and the quit or error annotation is the error +++message. +++ +++ Warning messages are not yet annotated. +++ +++ +++File: gdb.info, Node: Invalidation, Next: Annotations for Running, Prev: Errors, Up: Annotations +++ +++28.5 Invalidation Notices +++========================= +++ +++The following annotations say that certain pieces of state may have +++changed. +++ +++'^Z^Zframes-invalid' +++ +++ The frames (for example, output from the 'backtrace' command) may +++ have changed. +++ +++'^Z^Zbreakpoints-invalid' +++ +++ The breakpoints may have changed. For example, the user just added +++ or deleted a breakpoint. +++ +++ +++File: gdb.info, Node: Annotations for Running, Next: Source Annotations, Prev: Invalidation, Up: Annotations +++ +++28.6 Running the Program +++======================== +++ +++When the program starts executing due to a GDB command such as 'step' or +++'continue', +++ +++ ^Z^Zstarting +++ +++ is output. When the program stops, +++ +++ ^Z^Zstopped +++ +++ is output. Before the 'stopped' annotation, a variety of annotations +++describe how the program stopped. +++ +++'^Z^Zexited EXIT-STATUS' +++ The program exited, and EXIT-STATUS is the exit status (zero for +++ successful exit, otherwise nonzero). +++ +++'^Z^Zsignalled' +++ The program exited with a signal. After the '^Z^Zsignalled', the +++ annotation continues: +++ +++ INTRO-TEXT +++ ^Z^Zsignal-name +++ NAME +++ ^Z^Zsignal-name-end +++ MIDDLE-TEXT +++ ^Z^Zsignal-string +++ STRING +++ ^Z^Zsignal-string-end +++ END-TEXT +++ +++ where NAME is the name of the signal, such as 'SIGILL' or +++ 'SIGSEGV', and STRING is the explanation of the signal, such as +++ 'Illegal Instruction' or 'Segmentation fault'. The arguments +++ INTRO-TEXT, MIDDLE-TEXT, and END-TEXT are for the user's benefit +++ and have no particular format. +++ +++'^Z^Zsignal' +++ The syntax of this annotation is just like 'signalled', but GDB is +++ just saying that the program received the signal, not that it was +++ terminated with it. +++ +++'^Z^Zbreakpoint NUMBER' +++ The program hit breakpoint number NUMBER. +++ +++'^Z^Zwatchpoint NUMBER' +++ The program hit watchpoint number NUMBER. +++ +++ +++File: gdb.info, Node: Source Annotations, Prev: Annotations for Running, Up: Annotations +++ +++28.7 Displaying Source +++====================== +++ +++The following annotation is used instead of displaying source code: +++ +++ ^Z^Zsource FILENAME:LINE:CHARACTER:MIDDLE:ADDR +++ +++ where FILENAME is an absolute file name indicating which source file, +++LINE is the line number within that file (where 1 is the first line in +++the file), CHARACTER is the character position within the file (where 0 +++is the first character in the file) (for most debug formats this will +++necessarily point to the beginning of a line), MIDDLE is 'middle' if +++ADDR is in the middle of the line, or 'beg' if ADDR is at the beginning +++of the line, and ADDR is the address in the target program associated +++with the source which is being displayed. The ADDR is in the form '0x' +++followed by one or more lowercase hex digits (note that this does not +++depend on the language). +++ +++ +++File: gdb.info, Node: JIT Interface, Next: In-Process Agent, Prev: Annotations, Up: Top +++ +++29 JIT Compilation Interface +++**************************** +++ +++This chapter documents GDB's "just-in-time" (JIT) compilation interface. +++A JIT compiler is a program or library that generates native executable +++code at runtime and executes it, usually in order to achieve good +++performance while maintaining platform independence. +++ +++ Programs that use JIT compilation are normally difficult to debug +++because portions of their code are generated at runtime, instead of +++being loaded from object files, which is where GDB normally finds the +++program's symbols and debug information. In order to debug programs +++that use JIT compilation, GDB has an interface that allows the program +++to register in-memory symbol files with GDB at runtime. +++ +++ If you are using GDB to debug a program that uses this interface, +++then it should work transparently so long as you have not stripped the +++binary. If you are developing a JIT compiler, then the interface is +++documented in the rest of this chapter. At this time, the only known +++client of this interface is the LLVM JIT. +++ +++ Broadly speaking, the JIT interface mirrors the dynamic loader +++interface. The JIT compiler communicates with GDB by writing data into +++a global variable and calling a function at a well-known symbol. When +++GDB attaches, it reads a linked list of symbol files from the global +++variable to find existing code, and puts a breakpoint in the function so +++that it can find out about additional code. +++ +++* Menu: +++ +++* Declarations:: Relevant C struct declarations +++* Registering Code:: Steps to register code +++* Unregistering Code:: Steps to unregister code +++* Custom Debug Info:: Emit debug information in a custom format +++ +++ +++File: gdb.info, Node: Declarations, Next: Registering Code, Up: JIT Interface +++ +++29.1 JIT Declarations +++===================== +++ +++These are the relevant struct declarations that a C program should +++include to implement the interface: +++ +++ typedef enum +++ { +++ JIT_NOACTION = 0, +++ JIT_REGISTER_FN, +++ JIT_UNREGISTER_FN +++ } jit_actions_t; +++ +++ struct jit_code_entry +++ { +++ struct jit_code_entry *next_entry; +++ struct jit_code_entry *prev_entry; +++ const char *symfile_addr; +++ uint64_t symfile_size; +++ }; +++ +++ struct jit_descriptor +++ { +++ uint32_t version; +++ /* This type should be jit_actions_t, but we use uint32_t +++ to be explicit about the bitwidth. */ +++ uint32_t action_flag; +++ struct jit_code_entry *relevant_entry; +++ struct jit_code_entry *first_entry; +++ }; +++ +++ /* GDB puts a breakpoint in this function. */ +++ void __attribute__((noinline)) __jit_debug_register_code() { }; +++ +++ /* Make sure to specify the version statically, because the +++ debugger may check the version before we can set it. */ +++ struct jit_descriptor __jit_debug_descriptor = { 1, 0, 0, 0 }; +++ +++ If the JIT is multi-threaded, then it is important that the JIT +++synchronize any modifications to this global data properly, which can +++easily be done by putting a global mutex around modifications to these +++structures. +++ +++ +++File: gdb.info, Node: Registering Code, Next: Unregistering Code, Prev: Declarations, Up: JIT Interface +++ +++29.2 Registering Code +++===================== +++ +++To register code with GDB, the JIT should follow this protocol: +++ +++ * Generate an object file in memory with symbols and other desired +++ debug information. The file must include the virtual addresses of +++ the sections. +++ +++ * Create a code entry for the file, which gives the start and size of +++ the symbol file. +++ +++ * Add it to the linked list in the JIT descriptor. +++ +++ * Point the relevant_entry field of the descriptor at the entry. +++ +++ * Set 'action_flag' to 'JIT_REGISTER' and call +++ '__jit_debug_register_code'. +++ +++ When GDB is attached and the breakpoint fires, GDB uses the +++'relevant_entry' pointer so it doesn't have to walk the list looking for +++new code. However, the linked list must still be maintained in order to +++allow GDB to attach to a running process and still find the symbol +++files. +++ +++ +++File: gdb.info, Node: Unregistering Code, Next: Custom Debug Info, Prev: Registering Code, Up: JIT Interface +++ +++29.3 Unregistering Code +++======================= +++ +++If code is freed, then the JIT should use the following protocol: +++ +++ * Remove the code entry corresponding to the code from the linked +++ list. +++ +++ * Point the 'relevant_entry' field of the descriptor at the code +++ entry. +++ +++ * Set 'action_flag' to 'JIT_UNREGISTER' and call +++ '__jit_debug_register_code'. +++ +++ If the JIT frees or recompiles code without unregistering it, then +++GDB and the JIT will leak the memory used for the associated symbol +++files. +++ +++ +++File: gdb.info, Node: Custom Debug Info, Prev: Unregistering Code, Up: JIT Interface +++ +++29.4 Custom Debug Info +++====================== +++ +++Generating debug information in platform-native file formats (like ELF +++or COFF) may be an overkill for JIT compilers; especially if all the +++debug info is used for is displaying a meaningful backtrace. The issue +++can be resolved by having the JIT writers decide on a debug info format +++and also provide a reader that parses the debug info generated by the +++JIT compiler. This section gives a brief overview on writing such a +++parser. More specific details can be found in the source file +++'gdb/jit-reader.in', which is also installed as a header at +++'INCLUDEDIR/gdb/jit-reader.h' for easy inclusion. +++ +++ The reader is implemented as a shared object (so this functionality +++is not available on platforms which don't allow loading shared objects +++at runtime). Two GDB commands, 'jit-reader-load' and +++'jit-reader-unload' are provided, to be used to load and unload the +++readers from a preconfigured directory. Once loaded, the shared object +++is used the parse the debug information emitted by the JIT compiler. +++ +++* Menu: +++ +++* Using JIT Debug Info Readers:: How to use supplied readers correctly +++* Writing JIT Debug Info Readers:: Creating a debug-info reader +++ +++ +++File: gdb.info, Node: Using JIT Debug Info Readers, Next: Writing JIT Debug Info Readers, Up: Custom Debug Info +++ +++29.4.1 Using JIT Debug Info Readers +++----------------------------------- +++ +++Readers can be loaded and unloaded using the 'jit-reader-load' and +++'jit-reader-unload' commands. +++ +++'jit-reader-load READER' +++ Load the JIT reader named READER, which is a shared object +++ specified as either an absolute or a relative file name. In the +++ latter case, GDB will try to load the reader from a pre-configured +++ directory, usually 'LIBDIR/gdb/' on a UNIX system (here LIBDIR is +++ the system library directory, often '/usr/local/lib'). +++ +++ Only one reader can be active at a time; trying to load a second +++ reader when one is already loaded will result in GDB reporting an +++ error. A new JIT reader can be loaded by first unloading the +++ current one using 'jit-reader-unload' and then invoking +++ 'jit-reader-load'. +++ +++'jit-reader-unload' +++ Unload the currently loaded JIT reader. +++ +++ +++File: gdb.info, Node: Writing JIT Debug Info Readers, Prev: Using JIT Debug Info Readers, Up: Custom Debug Info +++ +++29.4.2 Writing JIT Debug Info Readers +++------------------------------------- +++ +++As mentioned, a reader is essentially a shared object conforming to a +++certain ABI. This ABI is described in 'jit-reader.h'. +++ +++ 'jit-reader.h' defines the structures, macros and functions required +++to write a reader. It is installed (along with GDB), in +++'INCLUDEDIR/gdb' where INCLUDEDIR is the system include directory. +++ +++ Readers need to be released under a GPL compatible license. A reader +++can be declared as released under such a license by placing the macro +++'GDB_DECLARE_GPL_COMPATIBLE_READER' in a source file. +++ +++ The entry point for readers is the symbol 'gdb_init_reader', which is +++expected to be a function with the prototype +++ +++ extern struct gdb_reader_funcs *gdb_init_reader (void); +++ +++ 'struct gdb_reader_funcs' contains a set of pointers to callback +++functions. These functions are executed to read the debug info +++generated by the JIT compiler ('read'), to unwind stack frames +++('unwind') and to create canonical frame IDs ('get_frame_id'). It also +++has a callback that is called when the reader is being unloaded +++('destroy'). The struct looks like this +++ +++ struct gdb_reader_funcs +++ { +++ /* Must be set to GDB_READER_INTERFACE_VERSION. */ +++ int reader_version; +++ +++ /* For use by the reader. */ +++ void *priv_data; +++ +++ gdb_read_debug_info *read; +++ gdb_unwind_frame *unwind; +++ gdb_get_frame_id *get_frame_id; +++ gdb_destroy_reader *destroy; +++ }; +++ +++ The callbacks are provided with another set of callbacks by GDB to do +++their job. For 'read', these callbacks are passed in a 'struct +++gdb_symbol_callbacks' and for 'unwind' and 'get_frame_id', in a 'struct +++gdb_unwind_callbacks'. 'struct gdb_symbol_callbacks' has callbacks to +++create new object files and new symbol tables inside those object files. +++'struct gdb_unwind_callbacks' has callbacks to read registers off the +++current frame and to write out the values of the registers in the +++previous frame. Both have a callback ('target_read') to read bytes off +++the target's address space. +++ +++ +++File: gdb.info, Node: In-Process Agent, Next: GDB Bugs, Prev: JIT Interface, Up: Top +++ +++30 In-Process Agent +++******************* +++ +++The traditional debugging model is conceptually low-speed, but works +++fine, because most bugs can be reproduced in debugging-mode execution. +++However, as multi-core or many-core processors are becoming mainstream, +++and multi-threaded programs become more and more popular, there should +++be more and more bugs that only manifest themselves at normal-mode +++execution, for example, thread races, because debugger's interference +++with the program's timing may conceal the bugs. On the other hand, in +++some applications, it is not feasible for the debugger to interrupt the +++program's execution long enough for the developer to learn anything +++helpful about its behavior. If the program's correctness depends on its +++real-time behavior, delays introduced by a debugger might cause the +++program to fail, even when the code itself is correct. It is useful to +++be able to observe the program's behavior without interrupting it. +++ +++ Therefore, traditional debugging model is too intrusive to reproduce +++some bugs. In order to reduce the interference with the program, we can +++reduce the number of operations performed by debugger. The "In-Process +++Agent", a shared library, is running within the same process with +++inferior, and is able to perform some debugging operations itself. As a +++result, debugger is only involved when necessary, and performance of +++debugging can be improved accordingly. Note that interference with +++program can be reduced but can't be removed completely, because the +++in-process agent will still stop or slow down the program. +++ +++ The in-process agent can interpret and execute Agent Expressions +++(*note Agent Expressions::) during performing debugging operations. The +++agent expressions can be used for different purposes, such as collecting +++data in tracepoints, and condition evaluation in breakpoints. +++ +++ You can control whether the in-process agent is used as an aid for +++debugging with the following commands: +++ +++'set agent on' +++ Causes the in-process agent to perform some operations on behalf of +++ the debugger. Just which operations requested by the user will be +++ done by the in-process agent depends on the its capabilities. For +++ example, if you request to evaluate breakpoint conditions in the +++ in-process agent, and the in-process agent has such capability as +++ well, then breakpoint conditions will be evaluated in the +++ in-process agent. +++ +++'set agent off' +++ Disables execution of debugging operations by the in-process agent. +++ All of the operations will be performed by GDB. +++ +++'show agent' +++ Display the current setting of execution of debugging operations by +++ the in-process agent. +++ +++* Menu: +++ +++* In-Process Agent Protocol:: +++ +++ +++File: gdb.info, Node: In-Process Agent Protocol, Up: In-Process Agent +++ +++30.1 In-Process Agent Protocol +++============================== +++ +++The in-process agent is able to communicate with both GDB and GDBserver +++(*note In-Process Agent::). This section documents the protocol used +++for communications between GDB or GDBserver and the IPA. In general, GDB +++or GDBserver sends commands (*note IPA Protocol Commands::) and data to +++in-process agent, and then in-process agent replies back with the return +++result of the command, or some other information. The data sent to +++in-process agent is composed of primitive data types, such as 4-byte or +++8-byte type, and composite types, which are called objects (*note IPA +++Protocol Objects::). +++ +++* Menu: +++ +++* IPA Protocol Objects:: +++* IPA Protocol Commands:: +++ +++ +++File: gdb.info, Node: IPA Protocol Objects, Next: IPA Protocol Commands, Up: In-Process Agent Protocol +++ +++30.1.1 IPA Protocol Objects +++--------------------------- +++ +++The commands sent to and results received from agent may contain some +++complex data types called "objects". +++ +++ The in-process agent is running on the same machine with GDB or +++GDBserver, so it doesn't have to handle as much differences between two +++ends as remote protocol (*note Remote Protocol::) tries to handle. +++However, there are still some differences of two ends in two processes: +++ +++ 1. word size. On some 64-bit machines, GDB or GDBserver can be +++ compiled as a 64-bit executable, while in-process agent is a 32-bit +++ one. +++ 2. ABI. Some machines may have multiple types of ABI, GDB or GDBserver +++ is compiled with one, and in-process agent is compiled with the +++ other one. +++ +++ Here are the IPA Protocol Objects: +++ +++ 1. agent expression object. It represents an agent expression (*note +++ Agent Expressions::). +++ 2. tracepoint action object. It represents a tracepoint action (*note +++ Tracepoint Action Lists: Tracepoint Actions.) to collect registers, +++ memory, static trace data and to evaluate expression. +++ 3. tracepoint object. It represents a tracepoint (*note +++ Tracepoints::). +++ +++ The following table describes important attributes of each IPA +++protocol object: +++ +++Name Size Description +++--------------------------------------------------------------------------- +++_agent expression +++object_ +++length 4 length of bytes code +++byte code LENGTH contents of byte code +++_tracepoint action +++for collecting +++memory_ +++'M' 1 type of tracepoint action +++addr 8 if BASEREG is '-1', ADDR is the +++ address of the lowest byte to +++ collect, otherwise ADDR is the +++ offset of BASEREG for memory +++ collecting. +++len 8 length of memory for collecting +++basereg 4 the register number containing the +++ starting memory address for +++ collecting. +++_tracepoint action +++for collecting +++registers_ +++'R' 1 type of tracepoint action +++_tracepoint action +++for collecting +++static trace data_ +++'L' 1 type of tracepoint action +++_tracepoint action +++for expression +++evaluation_ +++'X' 1 type of tracepoint action +++agent expression length of *note agent expression object:: +++_tracepoint object_ +++number 4 number of tracepoint +++address 8 address of tracepoint inserted on +++type 4 type of tracepoint +++enabled 1 enable or disable of tracepoint +++step_count 8 step +++pass_count 8 pass +++numactions 4 number of tracepoint actions +++hit count 8 hit count +++trace frame usage 8 trace frame usage +++compiled_cond 8 compiled condition +++orig_size 8 orig size +++condition 4 if zero if condition is NULL, +++ condition is otherwise is +++ NULL *note agent expression object:: +++ otherwise +++ length of +++ *note agent expression object:: +++actions variable numactions number of +++ *note tracepoint action object:: +++ +++ +++File: gdb.info, Node: IPA Protocol Commands, Prev: IPA Protocol Objects, Up: In-Process Agent Protocol +++ +++30.1.2 IPA Protocol Commands +++---------------------------- +++ +++The spaces in each command are delimiters to ease reading this commands +++specification. They don't exist in real commands. +++ +++'FastTrace:TRACEPOINT_OBJECT GDB_JUMP_PAD_HEAD' +++ Installs a new fast tracepoint described by TRACEPOINT_OBJECT +++ (*note tracepoint object::). The GDB_JUMP_PAD_HEAD, 8-byte long, +++ is the head of "jumppad", which is used to jump to data collection +++ routine in IPA finally. +++ +++ Replies: +++ 'OK TARGET_ADDRESS GDB_JUMP_PAD_HEAD FJUMP_SIZE FJUMP' +++ TARGET_ADDRESS is address of tracepoint in the inferior. The +++ GDB_JUMP_PAD_HEAD is updated head of jumppad. Both of +++ TARGET_ADDRESS and GDB_JUMP_PAD_HEAD are 8-byte long. The +++ FJUMP contains a sequence of instructions jump to jumppad +++ entry. The FJUMP_SIZE, 4-byte long, is the size of FJUMP. +++ 'E NN' +++ for an error +++ +++'close' +++ Closes the in-process agent. This command is sent when GDB or +++ GDBserver is about to kill inferiors. +++ +++'qTfSTM' +++ *Note qTfSTM::. +++'qTsSTM' +++ *Note qTsSTM::. +++'qTSTMat' +++ *Note qTSTMat::. +++'probe_marker_at:ADDRESS' +++ Asks in-process agent to probe the marker at ADDRESS. +++ +++ Replies: +++ 'E NN' +++ for an error +++'unprobe_marker_at:ADDRESS' +++ Asks in-process agent to unprobe the marker at ADDRESS. +++ +++ +++File: gdb.info, Node: GDB Bugs, Next: Command Line Editing, Prev: In-Process Agent, Up: Top +++ +++31 Reporting Bugs in GDB +++************************ +++ +++Your bug reports play an essential role in making GDB reliable. +++ +++ Reporting a bug may help you by bringing a solution to your problem, +++or it may not. But in any case the principal function of a bug report +++is to help the entire community by making the next version of GDB work +++better. Bug reports are your contribution to the maintenance of GDB. +++ +++ In order for a bug report to serve its purpose, you must include the +++information that enables us to fix the bug. +++ +++* Menu: +++ +++* Bug Criteria:: Have you found a bug? +++* Bug Reporting:: How to report bugs +++ +++ +++File: gdb.info, Node: Bug Criteria, Next: Bug Reporting, Up: GDB Bugs +++ +++31.1 Have You Found a Bug? +++========================== +++ +++If you are not sure whether you have found a bug, here are some +++guidelines: +++ +++ * If the debugger gets a fatal signal, for any input whatever, that +++ is a GDB bug. Reliable debuggers never crash. +++ +++ * If GDB produces an error message for valid input, that is a bug. +++ (Note that if you're cross debugging, the problem may also be +++ somewhere in the connection to the target.) +++ +++ * If GDB does not produce an error message for invalid input, that is +++ a bug. However, you should note that your idea of "invalid input" +++ might be our idea of "an extension" or "support for traditional +++ practice". +++ +++ * If you are an experienced user of debugging tools, your suggestions +++ for improvement of GDB are welcome in any case. +++ +++ +++File: gdb.info, Node: Bug Reporting, Prev: Bug Criteria, Up: GDB Bugs +++ +++31.2 How to Report Bugs +++======================= +++ +++A number of companies and individuals offer support for GNU products. +++If you obtained GDB from a support organization, we recommend you +++contact that organization first. +++ +++ You can find contact information for many support companies and +++individuals in the file 'etc/SERVICE' in the GNU Emacs distribution. +++ +++ In any event, we also recommend that you submit bug reports for GDB +++to . +++ +++ The fundamental principle of reporting bugs usefully is this: *report +++all the facts*. If you are not sure whether to state a fact or leave it +++out, state it! +++ +++ Often people omit facts because they think they know what causes the +++problem and assume that some details do not matter. Thus, you might +++assume that the name of the variable you use in an example does not +++matter. Well, probably it does not, but one cannot be sure. Perhaps +++the bug is a stray memory reference which happens to fetch from the +++location where that name is stored in memory; perhaps, if the name were +++different, the contents of that location would fool the debugger into +++doing the right thing despite the bug. Play it safe and give a +++specific, complete example. That is the easiest thing for you to do, +++and the most helpful. +++ +++ Keep in mind that the purpose of a bug report is to enable us to fix +++the bug. It may be that the bug has been reported previously, but +++neither you nor we can know that unless your bug report is complete and +++self-contained. +++ +++ Sometimes people give a few sketchy facts and ask, "Does this ring a +++bell?" Those bug reports are useless, and we urge everyone to _refuse +++to respond to them_ except to chide the sender to report bugs properly. +++ +++ To enable us to fix the bug, you should include all these things: +++ +++ * The version of GDB. GDB announces it if you start with no +++ arguments; you can also print it at any time using 'show version'. +++ +++ Without this, we will not know whether there is any point in +++ looking for the bug in the current version of GDB. +++ +++ * The type of machine you are using, and the operating system name +++ and version number. +++ +++ * The details of the GDB build-time configuration. GDB shows these +++ details if you invoke it with the '--configuration' command-line +++ option, or if you type 'show configuration' at GDB's prompt. +++ +++ * What compiler (and its version) was used to compile GDB--e.g. +++ "gcc-2.8.1". +++ +++ * What compiler (and its version) was used to compile the program you +++ are debugging--e.g. "gcc-2.8.1", or "HP92453-01 A.10.32.03 HP C +++ Compiler". For GCC, you can say 'gcc --version' to get this +++ information; for other compilers, see the documentation for those +++ compilers. +++ +++ * The command arguments you gave the compiler to compile your example +++ and observe the bug. For example, did you use '-O'? To guarantee +++ you will not omit something important, list them all. A copy of +++ the Makefile (or the output from make) is sufficient. +++ +++ If we were to try to guess the arguments, we would probably guess +++ wrong and then we might not encounter the bug. +++ +++ * A complete input script, and all necessary source files, that will +++ reproduce the bug. +++ +++ * A description of what behavior you observe that you believe is +++ incorrect. For example, "It gets a fatal signal." +++ +++ Of course, if the bug is that GDB gets a fatal signal, then we will +++ certainly notice it. But if the bug is incorrect output, we might +++ not notice unless it is glaringly wrong. You might as well not +++ give us a chance to make a mistake. +++ +++ Even if the problem you experience is a fatal signal, you should +++ still say so explicitly. Suppose something strange is going on, +++ such as, your copy of GDB is out of synch, or you have encountered +++ a bug in the C library on your system. (This has happened!) Your +++ copy might crash and ours would not. If you told us to expect a +++ crash, then when ours fails to crash, we would know that the bug +++ was not happening for us. If you had not told us to expect a +++ crash, then we would not be able to draw any conclusion from our +++ observations. +++ +++ To collect all this information, you can use a session recording +++ program such as 'script', which is available on many Unix systems. +++ Just run your GDB session inside 'script' and then include the +++ 'typescript' file with your bug report. +++ +++ Another way to record a GDB session is to run GDB inside Emacs and +++ then save the entire buffer to a file. +++ +++ * If you wish to suggest changes to the GDB source, send us context +++ diffs. If you even discuss something in the GDB source, refer to +++ it by context, not by line number. +++ +++ The line numbers in our development sources will not match those in +++ your sources. Your line numbers would convey no useful information +++ to us. +++ +++ Here are some things that are not necessary: +++ +++ * A description of the envelope of the bug. +++ +++ Often people who encounter a bug spend a lot of time investigating +++ which changes to the input file will make the bug go away and which +++ changes will not affect it. +++ +++ This is often time consuming and not very useful, because the way +++ we will find the bug is by running a single example under the +++ debugger with breakpoints, not by pure deduction from a series of +++ examples. We recommend that you save your time for something else. +++ +++ Of course, if you can find a simpler example to report _instead_ of +++ the original one, that is a convenience for us. Errors in the +++ output will be easier to spot, running under the debugger will take +++ less time, and so on. +++ +++ However, simplification is not vital; if you do not want to do +++ this, report the bug anyway and send us the entire test case you +++ used. +++ +++ * A patch for the bug. +++ +++ A patch for the bug does help us if it is a good one. But do not +++ omit the necessary information, such as the test case, on the +++ assumption that a patch is all we need. We might see problems with +++ your patch and decide to fix the problem another way, or we might +++ not understand it at all. +++ +++ Sometimes with a program as complicated as GDB it is very hard to +++ construct an example that will make the program follow a certain +++ path through the code. If you do not send us the example, we will +++ not be able to construct one, so we will not be able to verify that +++ the bug is fixed. +++ +++ And if we cannot understand what bug you are trying to fix, or why +++ your patch should be an improvement, we will not install it. A +++ test case will help us to understand. +++ +++ * A guess about what the bug is or what it depends on. +++ +++ Such guesses are usually wrong. Even we cannot guess right about +++ such things without first using the debugger to find the facts. +++ +++ +++File: gdb.info, Node: Command Line Editing, Next: Using History Interactively, Prev: GDB Bugs, Up: Top +++ +++32 Command Line Editing +++*********************** +++ +++This chapter describes the basic features of the GNU command line +++editing interface. +++ +++* Menu: +++ +++* Introduction and Notation:: Notation used in this text. +++* Readline Interaction:: The minimum set of commands for editing a line. +++* Readline Init File:: Customizing Readline from a user's view. +++* Bindable Readline Commands:: A description of most of the Readline commands +++ available for binding +++* Readline vi Mode:: A short description of how to make Readline +++ behave like the vi editor. +++ +++ +++File: gdb.info, Node: Introduction and Notation, Next: Readline Interaction, Up: Command Line Editing +++ +++32.1 Introduction to Line Editing +++================================= +++ +++The following paragraphs describe the notation used to represent +++keystrokes. +++ +++ The text 'C-k' is read as 'Control-K' and describes the character +++produced when the key is pressed while the Control key is depressed. +++ +++ The text 'M-k' is read as 'Meta-K' and describes the character +++produced when the Meta key (if you have one) is depressed, and the +++key is pressed. The Meta key is labeled on many keyboards. On +++keyboards with two keys labeled (usually to either side of the +++space bar), the on the left side is generally set to work as a +++Meta key. The key on the right may also be configured to work as +++a Meta key or may be configured as some other modifier, such as a +++Compose key for typing accented characters. +++ +++ If you do not have a Meta or key, or another key working as a +++Meta key, the identical keystroke can be generated by typing +++_first_, and then typing . Either process is known as "metafying" +++the key. +++ +++ The text 'M-C-k' is read as 'Meta-Control-k' and describes the +++character produced by "metafying" 'C-k'. +++ +++ In addition, several keys have their own names. Specifically, , +++, , , , and all stand for themselves when seen +++in this text, or in an init file (*note Readline Init File::). If your +++keyboard lacks a key, typing will produce the desired +++character. The key may be labeled or on some +++keyboards. +++ +++ +++File: gdb.info, Node: Readline Interaction, Next: Readline Init File, Prev: Introduction and Notation, Up: Command Line Editing +++ +++32.2 Readline Interaction +++========================= +++ +++Often during an interactive session you type in a long line of text, +++only to notice that the first word on the line is misspelled. The +++Readline library gives you a set of commands for manipulating the text +++as you type it in, allowing you to just fix your typo, and not forcing +++you to retype the majority of the line. Using these editing commands, +++you move the cursor to the place that needs correction, and delete or +++insert the text of the corrections. Then, when you are satisfied with +++the line, you simply press . You do not have to be at the end of +++the line to press ; the entire line is accepted regardless of the +++location of the cursor within the line. +++ +++* Menu: +++ +++* Readline Bare Essentials:: The least you need to know about Readline. +++* Readline Movement Commands:: Moving about the input line. +++* Readline Killing Commands:: How to delete text, and how to get it back! +++* Readline Arguments:: Giving numeric arguments to commands. +++* Searching:: Searching through previous lines. +++ +++ +++File: gdb.info, Node: Readline Bare Essentials, Next: Readline Movement Commands, Up: Readline Interaction +++ +++32.2.1 Readline Bare Essentials +++------------------------------- +++ +++In order to enter characters into the line, simply type them. The typed +++character appears where the cursor was, and then the cursor moves one +++space to the right. If you mistype a character, you can use your erase +++character to back up and delete the mistyped character. +++ +++ Sometimes you may mistype a character, and not notice the error until +++you have typed several other characters. In that case, you can type +++'C-b' to move the cursor to the left, and then correct your mistake. +++Afterwards, you can move the cursor to the right with 'C-f'. +++ +++ When you add text in the middle of a line, you will notice that +++characters to the right of the cursor are 'pushed over' to make room for +++the text that you have inserted. Likewise, when you delete text behind +++the cursor, characters to the right of the cursor are 'pulled back' to +++fill in the blank space created by the removal of the text. A list of +++the bare essentials for editing the text of an input line follows. +++ +++'C-b' +++ Move back one character. +++'C-f' +++ Move forward one character. +++ or +++ Delete the character to the left of the cursor. +++'C-d' +++ Delete the character underneath the cursor. +++Printing characters +++ Insert the character into the line at the cursor. +++'C-_' or 'C-x C-u' +++ Undo the last editing command. You can undo all the way back to an +++ empty line. +++ +++(Depending on your configuration, the key be set to delete +++the character to the left of the cursor and the key set to delete +++the character underneath the cursor, like 'C-d', rather than the +++character to the left of the cursor.) +++ +++ +++File: gdb.info, Node: Readline Movement Commands, Next: Readline Killing Commands, Prev: Readline Bare Essentials, Up: Readline Interaction +++ +++32.2.2 Readline Movement Commands +++--------------------------------- +++ +++The above table describes the most basic keystrokes that you need in +++order to do editing of the input line. For your convenience, many other +++commands have been added in addition to 'C-b', 'C-f', 'C-d', and . +++Here are some commands for moving more rapidly about the line. +++ +++'C-a' +++ Move to the start of the line. +++'C-e' +++ Move to the end of the line. +++'M-f' +++ Move forward a word, where a word is composed of letters and +++ digits. +++'M-b' +++ Move backward a word. +++'C-l' +++ Clear the screen, reprinting the current line at the top. +++ +++ Notice how 'C-f' moves forward a character, while 'M-f' moves forward +++a word. It is a loose convention that control keystrokes operate on +++characters while meta keystrokes operate on words. +++ +++ +++File: gdb.info, Node: Readline Killing Commands, Next: Readline Arguments, Prev: Readline Movement Commands, Up: Readline Interaction +++ +++32.2.3 Readline Killing Commands +++-------------------------------- +++ +++"Killing" text means to delete the text from the line, but to save it +++away for later use, usually by "yanking" (re-inserting) it back into the +++line. ('Cut' and 'paste' are more recent jargon for 'kill' and 'yank'.) +++ +++ If the description for a command says that it 'kills' text, then you +++can be sure that you can get the text back in a different (or the same) +++place later. +++ +++ When you use a kill command, the text is saved in a "kill-ring". Any +++number of consecutive kills save all of the killed text together, so +++that when you yank it back, you get it all. The kill ring is not line +++specific; the text that you killed on a previously typed line is +++available to be yanked back later, when you are typing another line. +++ +++ Here is the list of commands for killing text. +++ +++'C-k' +++ Kill the text from the current cursor position to the end of the +++ line. +++ +++'M-d' +++ Kill from the cursor to the end of the current word, or, if between +++ words, to the end of the next word. Word boundaries are the same +++ as those used by 'M-f'. +++ +++'M-' +++ Kill from the cursor the start of the current word, or, if between +++ words, to the start of the previous word. Word boundaries are the +++ same as those used by 'M-b'. +++ +++'C-w' +++ Kill from the cursor to the previous whitespace. This is different +++ than 'M-' because the word boundaries differ. +++ +++ Here is how to "yank" the text back into the line. Yanking means to +++copy the most-recently-killed text from the kill buffer. +++ +++'C-y' +++ Yank the most recently killed text back into the buffer at the +++ cursor. +++ +++'M-y' +++ Rotate the kill-ring, and yank the new top. You can only do this +++ if the prior command is 'C-y' or 'M-y'. +++ +++ +++File: gdb.info, Node: Readline Arguments, Next: Searching, Prev: Readline Killing Commands, Up: Readline Interaction +++ +++32.2.4 Readline Arguments +++------------------------- +++ +++You can pass numeric arguments to Readline commands. Sometimes the +++argument acts as a repeat count, other times it is the sign of the +++argument that is significant. If you pass a negative argument to a +++command which normally acts in a forward direction, that command will +++act in a backward direction. For example, to kill text back to the +++start of the line, you might type 'M-- C-k'. +++ +++ The general way to pass numeric arguments to a command is to type +++meta digits before the command. If the first 'digit' typed is a minus +++sign ('-'), then the sign of the argument will be negative. Once you +++have typed one meta digit to get the argument started, you can type the +++remainder of the digits, and then the command. For example, to give the +++'C-d' command an argument of 10, you could type 'M-1 0 C-d', which will +++delete the next ten characters on the input line. +++ +++ +++File: gdb.info, Node: Searching, Prev: Readline Arguments, Up: Readline Interaction +++ +++32.2.5 Searching for Commands in the History +++-------------------------------------------- +++ +++Readline provides commands for searching through the command history for +++lines containing a specified string. There are two search modes: +++"incremental" and "non-incremental". +++ +++ Incremental searches begin before the user has finished typing the +++search string. As each character of the search string is typed, +++Readline displays the next entry from the history matching the string +++typed so far. An incremental search requires only as many characters as +++needed to find the desired history entry. To search backward in the +++history for a particular string, type 'C-r'. Typing 'C-s' searches +++forward through the history. The characters present in the value of the +++'isearch-terminators' variable are used to terminate an incremental +++search. If that variable has not been assigned a value, the and +++'C-J' characters will terminate an incremental search. 'C-g' will abort +++an incremental search and restore the original line. When the search is +++terminated, the history entry containing the search string becomes the +++current line. +++ +++ To find other matching entries in the history list, type 'C-r' or +++'C-s' as appropriate. This will search backward or forward in the +++history for the next entry matching the search string typed so far. Any +++other key sequence bound to a Readline command will terminate the search +++and execute that command. For instance, a will terminate the +++search and accept the line, thereby executing the command from the +++history list. A movement command will terminate the search, make the +++last line found the current line, and begin editing. +++ +++ Readline remembers the last incremental search string. If two 'C-r's +++are typed without any intervening characters defining a new search +++string, any remembered search string is used. +++ +++ Non-incremental searches read the entire search string before +++starting to search for matching history lines. The search string may be +++typed by the user or be part of the contents of the current line. +++ +++ +++File: gdb.info, Node: Readline Init File, Next: Bindable Readline Commands, Prev: Readline Interaction, Up: Command Line Editing +++ +++32.3 Readline Init File +++======================= +++ +++Although the Readline library comes with a set of Emacs-like keybindings +++installed by default, it is possible to use a different set of +++keybindings. Any user can customize programs that use Readline by +++putting commands in an "inputrc" file, conventionally in his home +++directory. The name of this file is taken from the value of the +++environment variable 'INPUTRC'. If that variable is unset, the default +++is '~/.inputrc'. If that file does not exist or cannot be read, the +++ultimate default is '/etc/inputrc'. +++ +++ When a program which uses the Readline library starts up, the init +++file is read, and the key bindings are set. +++ +++ In addition, the 'C-x C-r' command re-reads this init file, thus +++incorporating any changes that you might have made to it. +++ +++* Menu: +++ +++* Readline Init File Syntax:: Syntax for the commands in the inputrc file. +++ +++* Conditional Init Constructs:: Conditional key bindings in the inputrc file. +++ +++* Sample Init File:: An example inputrc file. +++ +++ +++File: gdb.info, Node: Readline Init File Syntax, Next: Conditional Init Constructs, Up: Readline Init File +++ +++32.3.1 Readline Init File Syntax +++-------------------------------- +++ +++There are only a few basic constructs allowed in the Readline init file. +++Blank lines are ignored. Lines beginning with a '#' are comments. +++Lines beginning with a '$' indicate conditional constructs (*note +++Conditional Init Constructs::). Other lines denote variable settings +++and key bindings. +++ +++Variable Settings +++ You can modify the run-time behavior of Readline by altering the +++ values of variables in Readline using the 'set' command within the +++ init file. The syntax is simple: +++ +++ set VARIABLE VALUE +++ +++ Here, for example, is how to change from the default Emacs-like key +++ binding to use 'vi' line editing commands: +++ +++ set editing-mode vi +++ +++ Variable names and values, where appropriate, are recognized +++ without regard to case. Unrecognized variable names are ignored. +++ +++ Boolean variables (those that can be set to on or off) are set to +++ on if the value is null or empty, ON (case-insensitive), or 1. Any +++ other value results in the variable being set to off. +++ +++ A great deal of run-time behavior is changeable with the following +++ variables. +++ +++ 'bell-style' +++ Controls what happens when Readline wants to ring the terminal +++ bell. If set to 'none', Readline never rings the bell. If +++ set to 'visible', Readline uses a visible bell if one is +++ available. If set to 'audible' (the default), Readline +++ attempts to ring the terminal's bell. +++ +++ 'bind-tty-special-chars' +++ If set to 'on' (the default), Readline attempts to bind the +++ control characters treated specially by the kernel's terminal +++ driver to their Readline equivalents. +++ +++ 'blink-matching-paren' +++ If set to 'on', Readline attempts to briefly move the cursor +++ to an opening parenthesis when a closing parenthesis is +++ inserted. The default is 'off'. +++ +++ 'colored-completion-prefix' +++ If set to 'on', when listing completions, Readline displays +++ the common prefix of the set of possible completions using a +++ different color. The color definitions are taken from the +++ value of the 'LS_COLORS' environment variable. The default is +++ 'off'. +++ +++ 'colored-stats' +++ If set to 'on', Readline displays possible completions using +++ different colors to indicate their file type. The color +++ definitions are taken from the value of the 'LS_COLORS' +++ environment variable. The default is 'off'. +++ +++ 'comment-begin' +++ The string to insert at the beginning of the line when the +++ 'insert-comment' command is executed. The default value is +++ '"#"'. +++ +++ 'completion-display-width' +++ The number of screen columns used to display possible matches +++ when performing completion. The value is ignored if it is +++ less than 0 or greater than the terminal screen width. A +++ value of 0 will cause matches to be displayed one per line. +++ The default value is -1. +++ +++ 'completion-ignore-case' +++ If set to 'on', Readline performs filename matching and +++ completion in a case-insensitive fashion. The default value +++ is 'off'. +++ +++ 'completion-map-case' +++ If set to 'on', and COMPLETION-IGNORE-CASE is enabled, +++ Readline treats hyphens ('-') and underscores ('_') as +++ equivalent when performing case-insensitive filename matching +++ and completion. The default value is 'off'. +++ +++ 'completion-prefix-display-length' +++ The length in characters of the common prefix of a list of +++ possible completions that is displayed without modification. +++ When set to a value greater than zero, common prefixes longer +++ than this value are replaced with an ellipsis when displaying +++ possible completions. +++ +++ 'completion-query-items' +++ The number of possible completions that determines when the +++ user is asked whether the list of possibilities should be +++ displayed. If the number of possible completions is greater +++ than this value, Readline will ask the user whether or not he +++ wishes to view them; otherwise, they are simply listed. This +++ variable must be set to an integer value greater than or equal +++ to 0. A negative value means Readline should never ask. The +++ default limit is '100'. +++ +++ 'convert-meta' +++ If set to 'on', Readline will convert characters with the +++ eighth bit set to an ASCII key sequence by stripping the +++ eighth bit and prefixing an character, converting them +++ to a meta-prefixed key sequence. The default value is 'on', +++ but will be set to 'off' if the locale is one that contains +++ eight-bit characters. +++ +++ 'disable-completion' +++ If set to 'On', Readline will inhibit word completion. +++ Completion characters will be inserted into the line as if +++ they had been mapped to 'self-insert'. The default is 'off'. +++ +++ 'echo-control-characters' +++ When set to 'on', on operating systems that indicate they +++ support it, readline echoes a character corresponding to a +++ signal generated from the keyboard. The default is 'on'. +++ +++ 'editing-mode' +++ The 'editing-mode' variable controls which default set of key +++ bindings is used. By default, Readline starts up in Emacs +++ editing mode, where the keystrokes are most similar to Emacs. +++ This variable can be set to either 'emacs' or 'vi'. +++ +++ 'emacs-mode-string' +++ If the SHOW-MODE-IN-PROMPT variable is enabled, this string is +++ displayed immediately before the last line of the primary +++ prompt when emacs editing mode is active. The value is +++ expanded like a key binding, so the standard set of meta- and +++ control prefixes and backslash escape sequences is available. +++ Use the '\1' and '\2' escapes to begin and end sequences of +++ non-printing characters, which can be used to embed a terminal +++ control sequence into the mode string. The default is '@'. +++ +++ 'enable-bracketed-paste' +++ When set to 'On', Readline will configure the terminal in a +++ way that will enable it to insert each paste into the editing +++ buffer as a single string of characters, instead of treating +++ each character as if it had been read from the keyboard. This +++ can prevent pasted characters from being interpreted as +++ editing commands. The default is 'off'. +++ +++ 'enable-keypad' +++ When set to 'on', Readline will try to enable the application +++ keypad when it is called. Some systems need this to enable +++ the arrow keys. The default is 'off'. +++ +++ 'enable-meta-key' +++ When set to 'on', Readline will try to enable any meta +++ modifier key the terminal claims to support when it is called. +++ On many terminals, the meta key is used to send eight-bit +++ characters. The default is 'on'. +++ +++ 'expand-tilde' +++ If set to 'on', tilde expansion is performed when Readline +++ attempts word completion. The default is 'off'. +++ +++ 'history-preserve-point' +++ If set to 'on', the history code attempts to place the point +++ (the current cursor position) at the same location on each +++ history line retrieved with 'previous-history' or +++ 'next-history'. The default is 'off'. +++ +++ 'history-size' +++ Set the maximum number of history entries saved in the history +++ list. If set to zero, any existing history entries are +++ deleted and no new entries are saved. If set to a value less +++ than zero, the number of history entries is not limited. By +++ default, the number of history entries is not limited. If an +++ attempt is made to set HISTORY-SIZE to a non-numeric value, +++ the maximum number of history entries will be set to 500. +++ +++ 'horizontal-scroll-mode' +++ This variable can be set to either 'on' or 'off'. Setting it +++ to 'on' means that the text of the lines being edited will +++ scroll horizontally on a single screen line when they are +++ longer than the width of the screen, instead of wrapping onto +++ a new screen line. By default, this variable is set to 'off'. +++ +++ 'input-meta' +++ If set to 'on', Readline will enable eight-bit input (it will +++ not clear the eighth bit in the characters it reads), +++ regardless of what the terminal claims it can support. The +++ default value is 'off', but Readline will set it to 'on' if +++ the locale contains eight-bit characters. The name +++ 'meta-flag' is a synonym for this variable. +++ +++ 'isearch-terminators' +++ The string of characters that should terminate an incremental +++ search without subsequently executing the character as a +++ command (*note Searching::). If this variable has not been +++ given a value, the characters and 'C-J' will terminate +++ an incremental search. +++ +++ 'keymap' +++ Sets Readline's idea of the current keymap for key binding +++ commands. Built-in 'keymap' names are 'emacs', +++ 'emacs-standard', 'emacs-meta', 'emacs-ctlx', 'vi', 'vi-move', +++ 'vi-command', and 'vi-insert'. 'vi' is equivalent to +++ 'vi-command' ('vi-move' is also a synonym); 'emacs' is +++ equivalent to 'emacs-standard'. Applications may add +++ additional names. The default value is 'emacs'. The value of +++ the 'editing-mode' variable also affects the default keymap. +++ +++ 'keyseq-timeout' +++ Specifies the duration Readline will wait for a character when +++ reading an ambiguous key sequence (one that can form a +++ complete key sequence using the input read so far, or can take +++ additional input to complete a longer key sequence). If no +++ input is received within the timeout, Readline will use the +++ shorter but complete key sequence. Readline uses this value +++ to determine whether or not input is available on the current +++ input source ('rl_instream' by default). The value is +++ specified in milliseconds, so a value of 1000 means that +++ Readline will wait one second for additional input. If this +++ variable is set to a value less than or equal to zero, or to a +++ non-numeric value, Readline will wait until another key is +++ pressed to decide which key sequence to complete. The default +++ value is '500'. +++ +++ 'mark-directories' +++ If set to 'on', completed directory names have a slash +++ appended. The default is 'on'. +++ +++ 'mark-modified-lines' +++ This variable, when set to 'on', causes Readline to display an +++ asterisk ('*') at the start of history lines which have been +++ modified. This variable is 'off' by default. +++ +++ 'mark-symlinked-directories' +++ If set to 'on', completed names which are symbolic links to +++ directories have a slash appended (subject to the value of +++ 'mark-directories'). The default is 'off'. +++ +++ 'match-hidden-files' +++ This variable, when set to 'on', causes Readline to match +++ files whose names begin with a '.' (hidden files) when +++ performing filename completion. If set to 'off', the leading +++ '.' must be supplied by the user in the filename to be +++ completed. This variable is 'on' by default. +++ +++ 'menu-complete-display-prefix' +++ If set to 'on', menu completion displays the common prefix of +++ the list of possible completions (which may be empty) before +++ cycling through the list. The default is 'off'. +++ +++ 'output-meta' +++ If set to 'on', Readline will display characters with the +++ eighth bit set directly rather than as a meta-prefixed escape +++ sequence. The default is 'off', but Readline will set it to +++ 'on' if the locale contains eight-bit characters. +++ +++ 'page-completions' +++ If set to 'on', Readline uses an internal 'more'-like pager to +++ display a screenful of possible completions at a time. This +++ variable is 'on' by default. +++ +++ 'print-completions-horizontally' +++ If set to 'on', Readline will display completions with matches +++ sorted horizontally in alphabetical order, rather than down +++ the screen. The default is 'off'. +++ +++ 'revert-all-at-newline' +++ If set to 'on', Readline will undo all changes to history +++ lines before returning when 'accept-line' is executed. By +++ default, history lines may be modified and retain individual +++ undo lists across calls to 'readline'. The default is 'off'. +++ +++ 'show-all-if-ambiguous' +++ This alters the default behavior of the completion functions. +++ If set to 'on', words which have more than one possible +++ completion cause the matches to be listed immediately instead +++ of ringing the bell. The default value is 'off'. +++ +++ 'show-all-if-unmodified' +++ This alters the default behavior of the completion functions +++ in a fashion similar to SHOW-ALL-IF-AMBIGUOUS. If set to +++ 'on', words which have more than one possible completion +++ without any possible partial completion (the possible +++ completions don't share a common prefix) cause the matches to +++ be listed immediately instead of ringing the bell. The +++ default value is 'off'. +++ +++ 'show-mode-in-prompt' +++ If set to 'on', add a string to the beginning of the prompt +++ indicating the editing mode: emacs, vi command, or vi +++ insertion. The mode strings are user-settable (e.g., +++ EMACS-MODE-STRING). The default value is 'off'. +++ +++ 'skip-completed-text' +++ If set to 'on', this alters the default completion behavior +++ when inserting a single match into the line. It's only active +++ when performing completion in the middle of a word. If +++ enabled, readline does not insert characters from the +++ completion that match characters after point in the word being +++ completed, so portions of the word following the cursor are +++ not duplicated. For instance, if this is enabled, attempting +++ completion when the cursor is after the 'e' in 'Makefile' will +++ result in 'Makefile' rather than 'Makefilefile', assuming +++ there is a single possible completion. The default value is +++ 'off'. +++ +++ 'vi-cmd-mode-string' +++ If the SHOW-MODE-IN-PROMPT variable is enabled, this string is +++ displayed immediately before the last line of the primary +++ prompt when vi editing mode is active and in command mode. +++ The value is expanded like a key binding, so the standard set +++ of meta- and control prefixes and backslash escape sequences +++ is available. Use the '\1' and '\2' escapes to begin and end +++ sequences of non-printing characters, which can be used to +++ embed a terminal control sequence into the mode string. The +++ default is '(cmd)'. +++ +++ 'vi-ins-mode-string' +++ If the SHOW-MODE-IN-PROMPT variable is enabled, this string is +++ displayed immediately before the last line of the primary +++ prompt when vi editing mode is active and in insertion mode. +++ The value is expanded like a key binding, so the standard set +++ of meta- and control prefixes and backslash escape sequences +++ is available. Use the '\1' and '\2' escapes to begin and end +++ sequences of non-printing characters, which can be used to +++ embed a terminal control sequence into the mode string. The +++ default is '(ins)'. +++ +++ 'visible-stats' +++ If set to 'on', a character denoting a file's type is appended +++ to the filename when listing possible completions. The +++ default is 'off'. +++ +++Key Bindings +++ The syntax for controlling key bindings in the init file is simple. +++ First you need to find the name of the command that you want to +++ change. The following sections contain tables of the command name, +++ the default keybinding, if any, and a short description of what the +++ command does. +++ +++ Once you know the name of the command, simply place on a line in +++ the init file the name of the key you wish to bind the command to, +++ a colon, and then the name of the command. There can be no space +++ between the key name and the colon - that will be interpreted as +++ part of the key name. The name of the key can be expressed in +++ different ways, depending on what you find most comfortable. +++ +++ In addition to command names, readline allows keys to be bound to a +++ string that is inserted when the key is pressed (a MACRO). +++ +++ KEYNAME: FUNCTION-NAME or MACRO +++ KEYNAME is the name of a key spelled out in English. For +++ example: +++ Control-u: universal-argument +++ Meta-Rubout: backward-kill-word +++ Control-o: "> output" +++ +++ In the example above, 'C-u' is bound to the function +++ 'universal-argument', 'M-DEL' is bound to the function +++ 'backward-kill-word', and 'C-o' is bound to run the macro +++ expressed on the right hand side (that is, to insert the text +++ '> output' into the line). +++ +++ A number of symbolic character names are recognized while +++ processing this key binding syntax: DEL, ESC, ESCAPE, LFD, +++ NEWLINE, RET, RETURN, RUBOUT, SPACE, SPC, and TAB. +++ +++ "KEYSEQ": FUNCTION-NAME or MACRO +++ KEYSEQ differs from KEYNAME above in that strings denoting an +++ entire key sequence can be specified, by placing the key +++ sequence in double quotes. Some GNU Emacs style key escapes +++ can be used, as in the following example, but the special +++ character names are not recognized. +++ +++ "\C-u": universal-argument +++ "\C-x\C-r": re-read-init-file +++ "\e[11~": "Function Key 1" +++ +++ In the above example, 'C-u' is again bound to the function +++ 'universal-argument' (just as it was in the first example), +++ ''C-x' 'C-r'' is bound to the function 're-read-init-file', +++ and ' <[> <1> <1> <~>' is bound to insert the text +++ 'Function Key 1'. +++ +++ The following GNU Emacs style escape sequences are available when +++ specifying key sequences: +++ +++ '\C-' +++ control prefix +++ '\M-' +++ meta prefix +++ '\e' +++ an escape character +++ '\\' +++ backslash +++ '\"' +++ <">, a double quotation mark +++ '\'' +++ <'>, a single quote or apostrophe +++ +++ In addition to the GNU Emacs style escape sequences, a second set +++ of backslash escapes is available: +++ +++ '\a' +++ alert (bell) +++ '\b' +++ backspace +++ '\d' +++ delete +++ '\f' +++ form feed +++ '\n' +++ newline +++ '\r' +++ carriage return +++ '\t' +++ horizontal tab +++ '\v' +++ vertical tab +++ '\NNN' +++ the eight-bit character whose value is the octal value NNN +++ (one to three digits) +++ '\xHH' +++ the eight-bit character whose value is the hexadecimal value +++ HH (one or two hex digits) +++ +++ When entering the text of a macro, single or double quotes must be +++ used to indicate a macro definition. Unquoted text is assumed to +++ be a function name. In the macro body, the backslash escapes +++ described above are expanded. Backslash will quote any other +++ character in the macro text, including '"' and '''. For example, +++ the following binding will make ''C-x' \' insert a single '\' into +++ the line: +++ "\C-x\\": "\\" +++ +++ +++File: gdb.info, Node: Conditional Init Constructs, Next: Sample Init File, Prev: Readline Init File Syntax, Up: Readline Init File +++ +++32.3.2 Conditional Init Constructs +++---------------------------------- +++ +++Readline implements a facility similar in spirit to the conditional +++compilation features of the C preprocessor which allows key bindings and +++variable settings to be performed as the result of tests. There are +++four parser directives used. +++ +++'$if' +++ The '$if' construct allows bindings to be made based on the editing +++ mode, the terminal being used, or the application using Readline. +++ The text of the test, after any comparison operator, extends to the +++ end of the line; unless otherwise noted, no characters are required +++ to isolate it. +++ +++ 'mode' +++ The 'mode=' form of the '$if' directive is used to test +++ whether Readline is in 'emacs' or 'vi' mode. This may be used +++ in conjunction with the 'set keymap' command, for instance, to +++ set bindings in the 'emacs-standard' and 'emacs-ctlx' keymaps +++ only if Readline is starting out in 'emacs' mode. +++ +++ 'term' +++ The 'term=' form may be used to include terminal-specific key +++ bindings, perhaps to bind the key sequences output by the +++ terminal's function keys. The word on the right side of the +++ '=' is tested against both the full name of the terminal and +++ the portion of the terminal name before the first '-'. This +++ allows 'sun' to match both 'sun' and 'sun-cmd', for instance. +++ +++ 'version' +++ The 'version' test may be used to perform comparisons against +++ specific Readline versions. The 'version' expands to the +++ current Readline version. The set of comparison operators +++ includes '=' (and '=='), '!=', '<=', '>=', '<', and '>'. The +++ version number supplied on the right side of the operator +++ consists of a major version number, an optional decimal point, +++ and an optional minor version (e.g., '7.1'). If the minor +++ version is omitted, it is assumed to be '0'. The operator may +++ be separated from the string 'version' and from the version +++ number argument by whitespace. The following example sets a +++ variable if the Readline version being used is 7.0 or newer: +++ $if version >= 7.0 +++ set show-mode-in-prompt on +++ $endif +++ +++ 'application' +++ The APPLICATION construct is used to include +++ application-specific settings. Each program using the +++ Readline library sets the APPLICATION NAME, and you can test +++ for a particular value. This could be used to bind key +++ sequences to functions useful for a specific program. For +++ instance, the following command adds a key sequence that +++ quotes the current or previous word in Bash: +++ $if Bash +++ # Quote the current or previous word +++ "\C-xq": "\eb\"\ef\"" +++ $endif +++ +++ 'variable' +++ The VARIABLE construct provides simple equality tests for +++ Readline variables and values. The permitted comparison +++ operators are '=', '==', and '!='. The variable name must be +++ separated from the comparison operator by whitespace; the +++ operator may be separated from the value on the right hand +++ side by whitespace. Both string and boolean variables may be +++ tested. Boolean variables must be tested against the values +++ ON and OFF. The following example is equivalent to the +++ 'mode=emacs' test described above: +++ $if editing-mode == emacs +++ set show-mode-in-prompt on +++ $endif +++ +++'$endif' +++ This command, as seen in the previous example, terminates an '$if' +++ command. +++ +++'$else' +++ Commands in this branch of the '$if' directive are executed if the +++ test fails. +++ +++'$include' +++ This directive takes a single filename as an argument and reads +++ commands and bindings from that file. For example, the following +++ directive reads from '/etc/inputrc': +++ $include /etc/inputrc +++ +++ +++File: gdb.info, Node: Sample Init File, Prev: Conditional Init Constructs, Up: Readline Init File +++ +++32.3.3 Sample Init File +++----------------------- +++ +++Here is an example of an INPUTRC file. This illustrates key binding, +++variable assignment, and conditional syntax. +++ +++ # This file controls the behaviour of line input editing for +++ # programs that use the GNU Readline library. Existing +++ # programs include FTP, Bash, and GDB. +++ # +++ # You can re-read the inputrc file with C-x C-r. +++ # Lines beginning with '#' are comments. +++ # +++ # First, include any system-wide bindings and variable +++ # assignments from /etc/Inputrc +++ $include /etc/Inputrc +++ +++ # +++ # Set various bindings for emacs mode. +++ +++ set editing-mode emacs +++ +++ $if mode=emacs +++ +++ Meta-Control-h: backward-kill-word Text after the function name is ignored +++ +++ # +++ # Arrow keys in keypad mode +++ # +++ #"\M-OD": backward-char +++ #"\M-OC": forward-char +++ #"\M-OA": previous-history +++ #"\M-OB": next-history +++ # +++ # Arrow keys in ANSI mode +++ # +++ "\M-[D": backward-char +++ "\M-[C": forward-char +++ "\M-[A": previous-history +++ "\M-[B": next-history +++ # +++ # Arrow keys in 8 bit keypad mode +++ # +++ #"\M-\C-OD": backward-char +++ #"\M-\C-OC": forward-char +++ #"\M-\C-OA": previous-history +++ #"\M-\C-OB": next-history +++ # +++ # Arrow keys in 8 bit ANSI mode +++ # +++ #"\M-\C-[D": backward-char +++ #"\M-\C-[C": forward-char +++ #"\M-\C-[A": previous-history +++ #"\M-\C-[B": next-history +++ +++ C-q: quoted-insert +++ +++ $endif +++ +++ # An old-style binding. This happens to be the default. +++ TAB: complete +++ +++ # Macros that are convenient for shell interaction +++ $if Bash +++ # edit the path +++ "\C-xp": "PATH=${PATH}\e\C-e\C-a\ef\C-f" +++ # prepare to type a quoted word -- +++ # insert open and close double quotes +++ # and move to just after the open quote +++ "\C-x\"": "\"\"\C-b" +++ # insert a backslash (testing backslash escapes +++ # in sequences and macros) +++ "\C-x\\": "\\" +++ # Quote the current or previous word +++ "\C-xq": "\eb\"\ef\"" +++ # Add a binding to refresh the line, which is unbound +++ "\C-xr": redraw-current-line +++ # Edit variable on current line. +++ "\M-\C-v": "\C-a\C-k$\C-y\M-\C-e\C-a\C-y=" +++ $endif +++ +++ # use a visible bell if one is available +++ set bell-style visible +++ +++ # don't strip characters to 7 bits when reading +++ set input-meta on +++ +++ # allow iso-latin1 characters to be inserted rather +++ # than converted to prefix-meta sequences +++ set convert-meta off +++ +++ # display characters with the eighth bit set directly +++ # rather than as meta-prefixed characters +++ set output-meta on +++ +++ # if there are more than 150 possible completions for +++ # a word, ask the user if he wants to see all of them +++ set completion-query-items 150 +++ +++ # For FTP +++ $if Ftp +++ "\C-xg": "get \M-?" +++ "\C-xt": "put \M-?" +++ "\M-.": yank-last-arg +++ $endif +++ +++ +++File: gdb.info, Node: Bindable Readline Commands, Next: Readline vi Mode, Prev: Readline Init File, Up: Command Line Editing +++ +++32.4 Bindable Readline Commands +++=============================== +++ +++* Menu: +++ +++* Commands For Moving:: Moving about the line. +++* Commands For History:: Getting at previous lines. +++* Commands For Text:: Commands for changing text. +++* Commands For Killing:: Commands for killing and yanking. +++* Numeric Arguments:: Specifying numeric arguments, repeat counts. +++* Commands For Completion:: Getting Readline to do the typing for you. +++* Keyboard Macros:: Saving and re-executing typed characters +++* Miscellaneous Commands:: Other miscellaneous commands. +++ +++This section describes Readline commands that may be bound to key +++sequences. Command names without an accompanying key sequence are +++unbound by default. +++ +++ In the following descriptions, "point" refers to the current cursor +++position, and "mark" refers to a cursor position saved by the 'set-mark' +++command. The text between the point and mark is referred to as the +++"region". +++ +++ +++File: gdb.info, Node: Commands For Moving, Next: Commands For History, Up: Bindable Readline Commands +++ +++32.4.1 Commands For Moving +++-------------------------- +++ +++'beginning-of-line (C-a)' +++ Move to the start of the current line. +++ +++'end-of-line (C-e)' +++ Move to the end of the line. +++ +++'forward-char (C-f)' +++ Move forward a character. +++ +++'backward-char (C-b)' +++ Move back a character. +++ +++'forward-word (M-f)' +++ Move forward to the end of the next word. Words are composed of +++ letters and digits. +++ +++'backward-word (M-b)' +++ Move back to the start of the current or previous word. Words are +++ composed of letters and digits. +++ +++'previous-screen-line ()' +++ Attempt to move point to the same physical screen column on the +++ previous physical screen line. This will not have the desired +++ effect if the current Readline line does not take up more than one +++ physical line or if point is not greater than the length of the +++ prompt plus the screen width. +++ +++'next-screen-line ()' +++ Attempt to move point to the same physical screen column on the +++ next physical screen line. This will not have the desired effect +++ if the current Readline line does not take up more than one +++ physical line or if the length of the current Readline line is not +++ greater than the length of the prompt plus the screen width. +++ +++'clear-screen (C-l)' +++ Clear the screen and redraw the current line, leaving the current +++ line at the top of the screen. +++ +++'redraw-current-line ()' +++ Refresh the current line. By default, this is unbound. +++ +++ +++File: gdb.info, Node: Commands For History, Next: Commands For Text, Prev: Commands For Moving, Up: Bindable Readline Commands +++ +++32.4.2 Commands For Manipulating The History +++-------------------------------------------- +++ +++'accept-line (Newline or Return)' +++ Accept the line regardless of where the cursor is. If this line is +++ non-empty, it may be added to the history list for future recall +++ with 'add_history()'. If this line is a modified history line, the +++ history line is restored to its original state. +++ +++'previous-history (C-p)' +++ Move 'back' through the history list, fetching the previous +++ command. +++ +++'next-history (C-n)' +++ Move 'forward' through the history list, fetching the next command. +++ +++'beginning-of-history (M-<)' +++ Move to the first line in the history. +++ +++'end-of-history (M->)' +++ Move to the end of the input history, i.e., the line currently +++ being entered. +++ +++'reverse-search-history (C-r)' +++ Search backward starting at the current line and moving 'up' +++ through the history as necessary. This is an incremental search. +++ +++'forward-search-history (C-s)' +++ Search forward starting at the current line and moving 'down' +++ through the history as necessary. This is an incremental search. +++ +++'non-incremental-reverse-search-history (M-p)' +++ Search backward starting at the current line and moving 'up' +++ through the history as necessary using a non-incremental search for +++ a string supplied by the user. The search string may match +++ anywhere in a history line. +++ +++'non-incremental-forward-search-history (M-n)' +++ Search forward starting at the current line and moving 'down' +++ through the history as necessary using a non-incremental search for +++ a string supplied by the user. The search string may match +++ anywhere in a history line. +++ +++'history-search-forward ()' +++ Search forward through the history for the string of characters +++ between the start of the current line and the point. The search +++ string must match at the beginning of a history line. This is a +++ non-incremental search. By default, this command is unbound. +++ +++'history-search-backward ()' +++ Search backward through the history for the string of characters +++ between the start of the current line and the point. The search +++ string must match at the beginning of a history line. This is a +++ non-incremental search. By default, this command is unbound. +++ +++'history-substring-search-forward ()' +++ Search forward through the history for the string of characters +++ between the start of the current line and the point. The search +++ string may match anywhere in a history line. This is a +++ non-incremental search. By default, this command is unbound. +++ +++'history-substring-search-backward ()' +++ Search backward through the history for the string of characters +++ between the start of the current line and the point. The search +++ string may match anywhere in a history line. This is a +++ non-incremental search. By default, this command is unbound. +++ +++'yank-nth-arg (M-C-y)' +++ Insert the first argument to the previous command (usually the +++ second word on the previous line) at point. With an argument N, +++ insert the Nth word from the previous command (the words in the +++ previous command begin with word 0). A negative argument inserts +++ the Nth word from the end of the previous command. Once the +++ argument N is computed, the argument is extracted as if the '!N' +++ history expansion had been specified. +++ +++'yank-last-arg (M-. or M-_)' +++ Insert last argument to the previous command (the last word of the +++ previous history entry). With a numeric argument, behave exactly +++ like 'yank-nth-arg'. Successive calls to 'yank-last-arg' move back +++ through the history list, inserting the last word (or the word +++ specified by the argument to the first call) of each line in turn. +++ Any numeric argument supplied to these successive calls determines +++ the direction to move through the history. A negative argument +++ switches the direction through the history (back or forward). The +++ history expansion facilities are used to extract the last argument, +++ as if the '!$' history expansion had been specified. +++ +++ +++File: gdb.info, Node: Commands For Text, Next: Commands For Killing, Prev: Commands For History, Up: Bindable Readline Commands +++ +++32.4.3 Commands For Changing Text +++--------------------------------- +++ +++'end-of-file (usually C-d)' +++ The character indicating end-of-file as set, for example, by +++ 'stty'. If this character is read when there are no characters on +++ the line, and point is at the beginning of the line, Readline +++ interprets it as the end of input and returns EOF. +++ +++'delete-char (C-d)' +++ Delete the character at point. If this function is bound to the +++ same character as the tty EOF character, as 'C-d' commonly is, see +++ above for the effects. +++ +++'backward-delete-char (Rubout)' +++ Delete the character behind the cursor. A numeric argument means +++ to kill the characters instead of deleting them. +++ +++'forward-backward-delete-char ()' +++ Delete the character under the cursor, unless the cursor is at the +++ end of the line, in which case the character behind the cursor is +++ deleted. By default, this is not bound to a key. +++ +++'quoted-insert (C-q or C-v)' +++ Add the next character typed to the line verbatim. This is how to +++ insert key sequences like 'C-q', for example. +++ +++'tab-insert (M-)' +++ Insert a tab character. +++ +++'self-insert (a, b, A, 1, !, ...)' +++ Insert yourself. +++ +++'bracketed-paste-begin ()' +++ This function is intended to be bound to the "bracketed paste" +++ escape sequence sent by some terminals, and such a binding is +++ assigned by default. It allows Readline to insert the pasted text +++ as a single unit without treating each character as if it had been +++ read from the keyboard. The characters are inserted as if each one +++ was bound to 'self-insert' instead of executing any editing +++ commands. +++ +++'transpose-chars (C-t)' +++ Drag the character before the cursor forward over the character at +++ the cursor, moving the cursor forward as well. If the insertion +++ point is at the end of the line, then this transposes the last two +++ characters of the line. Negative arguments have no effect. +++ +++'transpose-words (M-t)' +++ Drag the word before point past the word after point, moving point +++ past that word as well. If the insertion point is at the end of +++ the line, this transposes the last two words on the line. +++ +++'upcase-word (M-u)' +++ Uppercase the current (or following) word. With a negative +++ argument, uppercase the previous word, but do not move the cursor. +++ +++'downcase-word (M-l)' +++ Lowercase the current (or following) word. With a negative +++ argument, lowercase the previous word, but do not move the cursor. +++ +++'capitalize-word (M-c)' +++ Capitalize the current (or following) word. With a negative +++ argument, capitalize the previous word, but do not move the cursor. +++ +++'overwrite-mode ()' +++ Toggle overwrite mode. With an explicit positive numeric argument, +++ switches to overwrite mode. With an explicit non-positive numeric +++ argument, switches to insert mode. This command affects only +++ 'emacs' mode; 'vi' mode does overwrite differently. Each call to +++ 'readline()' starts in insert mode. +++ +++ In overwrite mode, characters bound to 'self-insert' replace the +++ text at point rather than pushing the text to the right. +++ Characters bound to 'backward-delete-char' replace the character +++ before point with a space. +++ +++ By default, this command is unbound. +++ +++ +++File: gdb.info, Node: Commands For Killing, Next: Numeric Arguments, Prev: Commands For Text, Up: Bindable Readline Commands +++ +++32.4.4 Killing And Yanking +++-------------------------- +++ +++'kill-line (C-k)' +++ Kill the text from point to the end of the line. +++ +++'backward-kill-line (C-x Rubout)' +++ Kill backward from the cursor to the beginning of the current line. +++ +++'unix-line-discard (C-u)' +++ Kill backward from the cursor to the beginning of the current line. +++ +++'kill-whole-line ()' +++ Kill all characters on the current line, no matter where point is. +++ By default, this is unbound. +++ +++'kill-word (M-d)' +++ Kill from point to the end of the current word, or if between +++ words, to the end of the next word. Word boundaries are the same +++ as 'forward-word'. +++ +++'backward-kill-word (M-)' +++ Kill the word behind point. Word boundaries are the same as +++ 'backward-word'. +++ +++'unix-word-rubout (C-w)' +++ Kill the word behind point, using white space as a word boundary. +++ The killed text is saved on the kill-ring. +++ +++'unix-filename-rubout ()' +++ Kill the word behind point, using white space and the slash +++ character as the word boundaries. The killed text is saved on the +++ kill-ring. +++ +++'delete-horizontal-space ()' +++ Delete all spaces and tabs around point. By default, this is +++ unbound. +++ +++'kill-region ()' +++ Kill the text in the current region. By default, this command is +++ unbound. +++ +++'copy-region-as-kill ()' +++ Copy the text in the region to the kill buffer, so it can be yanked +++ right away. By default, this command is unbound. +++ +++'copy-backward-word ()' +++ Copy the word before point to the kill buffer. The word boundaries +++ are the same as 'backward-word'. By default, this command is +++ unbound. +++ +++'copy-forward-word ()' +++ Copy the word following point to the kill buffer. The word +++ boundaries are the same as 'forward-word'. By default, this +++ command is unbound. +++ +++'yank (C-y)' +++ Yank the top of the kill ring into the buffer at point. +++ +++'yank-pop (M-y)' +++ Rotate the kill-ring, and yank the new top. You can only do this +++ if the prior command is 'yank' or 'yank-pop'. +++ +++ +++File: gdb.info, Node: Numeric Arguments, Next: Commands For Completion, Prev: Commands For Killing, Up: Bindable Readline Commands +++ +++32.4.5 Specifying Numeric Arguments +++----------------------------------- +++ +++'digit-argument (M-0, M-1, ... M--)' +++ Add this digit to the argument already accumulating, or start a new +++ argument. 'M--' starts a negative argument. +++ +++'universal-argument ()' +++ This is another way to specify an argument. If this command is +++ followed by one or more digits, optionally with a leading minus +++ sign, those digits define the argument. If the command is followed +++ by digits, executing 'universal-argument' again ends the numeric +++ argument, but is otherwise ignored. As a special case, if this +++ command is immediately followed by a character that is neither a +++ digit nor minus sign, the argument count for the next command is +++ multiplied by four. The argument count is initially one, so +++ executing this function the first time makes the argument count +++ four, a second time makes the argument count sixteen, and so on. +++ By default, this is not bound to a key. +++ +++ +++File: gdb.info, Node: Commands For Completion, Next: Keyboard Macros, Prev: Numeric Arguments, Up: Bindable Readline Commands +++ +++32.4.6 Letting Readline Type For You +++------------------------------------ +++ +++'complete ()' +++ Attempt to perform completion on the text before point. The actual +++ completion performed is application-specific. The default is +++ filename completion. +++ +++'possible-completions (M-?)' +++ List the possible completions of the text before point. When +++ displaying completions, Readline sets the number of columns used +++ for display to the value of 'completion-display-width', the value +++ of the environment variable 'COLUMNS', or the screen width, in that +++ order. +++ +++'insert-completions (M-*)' +++ Insert all completions of the text before point that would have +++ been generated by 'possible-completions'. +++ +++'menu-complete ()' +++ Similar to 'complete', but replaces the word to be completed with a +++ single match from the list of possible completions. Repeated +++ execution of 'menu-complete' steps through the list of possible +++ completions, inserting each match in turn. At the end of the list +++ of completions, the bell is rung (subject to the setting of +++ 'bell-style') and the original text is restored. An argument of N +++ moves N positions forward in the list of matches; a negative +++ argument may be used to move backward through the list. This +++ command is intended to be bound to , but is unbound by +++ default. +++ +++'menu-complete-backward ()' +++ Identical to 'menu-complete', but moves backward through the list +++ of possible completions, as if 'menu-complete' had been given a +++ negative argument. +++ +++'delete-char-or-list ()' +++ Deletes the character under the cursor if not at the beginning or +++ end of the line (like 'delete-char'). If at the end of the line, +++ behaves identically to 'possible-completions'. This command is +++ unbound by default. +++ +++ +++File: gdb.info, Node: Keyboard Macros, Next: Miscellaneous Commands, Prev: Commands For Completion, Up: Bindable Readline Commands +++ +++32.4.7 Keyboard Macros +++---------------------- +++ +++'start-kbd-macro (C-x ()' +++ Begin saving the characters typed into the current keyboard macro. +++ +++'end-kbd-macro (C-x ))' +++ Stop saving the characters typed into the current keyboard macro +++ and save the definition. +++ +++'call-last-kbd-macro (C-x e)' +++ Re-execute the last keyboard macro defined, by making the +++ characters in the macro appear as if typed at the keyboard. +++ +++'print-last-kbd-macro ()' +++ Print the last keboard macro defined in a format suitable for the +++ INPUTRC file. +++ +++ +++File: gdb.info, Node: Miscellaneous Commands, Prev: Keyboard Macros, Up: Bindable Readline Commands +++ +++32.4.8 Some Miscellaneous Commands +++---------------------------------- +++ +++'re-read-init-file (C-x C-r)' +++ Read in the contents of the INPUTRC file, and incorporate any +++ bindings or variable assignments found there. +++ +++'abort (C-g)' +++ Abort the current editing command and ring the terminal's bell +++ (subject to the setting of 'bell-style'). +++ +++'do-lowercase-version (M-A, M-B, M-X, ...)' +++ If the metafied character X is upper case, run the command that is +++ bound to the corresponding metafied lower case character. The +++ behavior is undefined if X is already lower case. +++ +++'prefix-meta ()' +++ Metafy the next character typed. This is for keyboards without a +++ meta key. Typing ' f' is equivalent to typing 'M-f'. +++ +++'undo (C-_ or C-x C-u)' +++ Incremental undo, separately remembered for each line. +++ +++'revert-line (M-r)' +++ Undo all changes made to this line. This is like executing the +++ 'undo' command enough times to get back to the beginning. +++ +++'tilde-expand (M-~)' +++ Perform tilde expansion on the current word. +++ +++'set-mark (C-@)' +++ Set the mark to the point. If a numeric argument is supplied, the +++ mark is set to that position. +++ +++'exchange-point-and-mark (C-x C-x)' +++ Swap the point with the mark. The current cursor position is set +++ to the saved position, and the old cursor position is saved as the +++ mark. +++ +++'character-search (C-])' +++ A character is read and point is moved to the next occurrence of +++ that character. A negative count searches for previous +++ occurrences. +++ +++'character-search-backward (M-C-])' +++ A character is read and point is moved to the previous occurrence +++ of that character. A negative count searches for subsequent +++ occurrences. +++ +++'skip-csi-sequence ()' +++ Read enough characters to consume a multi-key sequence such as +++ those defined for keys like Home and End. Such sequences begin +++ with a Control Sequence Indicator (CSI), usually ESC-[. If this +++ sequence is bound to "\e[", keys producing such sequences will have +++ no effect unless explicitly bound to a readline command, instead of +++ inserting stray characters into the editing buffer. This is +++ unbound by default, but usually bound to ESC-[. +++ +++'insert-comment (M-#)' +++ Without a numeric argument, the value of the 'comment-begin' +++ variable is inserted at the beginning of the current line. If a +++ numeric argument is supplied, this command acts as a toggle: if the +++ characters at the beginning of the line do not match the value of +++ 'comment-begin', the value is inserted, otherwise the characters in +++ 'comment-begin' are deleted from the beginning of the line. In +++ either case, the line is accepted as if a newline had been typed. +++ +++'dump-functions ()' +++ Print all of the functions and their key bindings to the Readline +++ output stream. If a numeric argument is supplied, the output is +++ formatted in such a way that it can be made part of an INPUTRC +++ file. This command is unbound by default. +++ +++'dump-variables ()' +++ Print all of the settable variables and their values to the +++ Readline output stream. If a numeric argument is supplied, the +++ output is formatted in such a way that it can be made part of an +++ INPUTRC file. This command is unbound by default. +++ +++'dump-macros ()' +++ Print all of the Readline key sequences bound to macros and the +++ strings they output. If a numeric argument is supplied, the output +++ is formatted in such a way that it can be made part of an INPUTRC +++ file. This command is unbound by default. +++ +++'emacs-editing-mode (C-e)' +++ When in 'vi' command mode, this causes a switch to 'emacs' editing +++ mode. +++ +++'vi-editing-mode (M-C-j)' +++ When in 'emacs' editing mode, this causes a switch to 'vi' editing +++ mode. +++ +++ +++File: gdb.info, Node: Readline vi Mode, Prev: Bindable Readline Commands, Up: Command Line Editing +++ +++32.5 Readline vi Mode +++===================== +++ +++While the Readline library does not have a full set of 'vi' editing +++functions, it does contain enough to allow simple editing of the line. +++The Readline 'vi' mode behaves as specified in the POSIX standard. +++ +++ In order to switch interactively between 'emacs' and 'vi' editing +++modes, use the command 'M-C-j' (bound to emacs-editing-mode when in 'vi' +++mode and to vi-editing-mode in 'emacs' mode). The Readline default is +++'emacs' mode. +++ +++ When you enter a line in 'vi' mode, you are already placed in +++'insertion' mode, as if you had typed an 'i'. Pressing switches +++you into 'command' mode, where you can edit the text of the line with +++the standard 'vi' movement keys, move to previous history lines with 'k' +++and subsequent lines with 'j', and so forth. +++ +++ +++File: gdb.info, Node: Using History Interactively, Next: In Memoriam, Prev: Command Line Editing, Up: Top +++ +++33 Using History Interactively +++****************************** +++ +++This chapter describes how to use the GNU History Library interactively, +++from a user's standpoint. It should be considered a user's guide. For +++information on using the GNU History Library in your own programs, *note +++(history)Programming with GNU History::. +++ +++* Menu: +++ +++* History Interaction:: What it feels like using History as a user. +++ +++ +++File: gdb.info, Node: History Interaction, Up: Using History Interactively +++ +++33.1 History Expansion +++====================== +++ +++The History library provides a history expansion feature that is similar +++to the history expansion provided by 'csh'. This section describes the +++syntax used to manipulate the history information. +++ +++ History expansions introduce words from the history list into the +++input stream, making it easy to repeat commands, insert the arguments to +++a previous command into the current input line, or fix errors in +++previous commands quickly. +++ +++ History expansion takes place in two parts. The first is to +++determine which line from the history list should be used during +++substitution. The second is to select portions of that line for +++inclusion into the current one. The line selected from the history is +++called the "event", and the portions of that line that are acted upon +++are called "words". Various "modifiers" are available to manipulate the +++selected words. The line is broken into words in the same fashion that +++Bash does, so that several words surrounded by quotes are considered one +++word. History expansions are introduced by the appearance of the +++history expansion character, which is '!' by default. +++ +++ History expansion implements shell-like quoting conventions: a +++backslash can be used to remove the special handling for the next +++character; single quotes enclose verbatim sequences of characters, and +++can be used to inhibit history expansion; and characters enclosed within +++double quotes may be subject to history expansion, since backslash can +++escape the history expansion character, but single quotes may not, since +++they are not treated specially within double quotes. +++ +++* Menu: +++ +++* Event Designators:: How to specify which history line to use. +++* Word Designators:: Specifying which words are of interest. +++* Modifiers:: Modifying the results of substitution. +++ +++ +++File: gdb.info, Node: Event Designators, Next: Word Designators, Up: History Interaction +++ +++33.1.1 Event Designators +++------------------------ +++ +++An event designator is a reference to a command line entry in the +++history list. Unless the reference is absolute, events are relative to +++the current position in the history list. +++ +++'!' +++ Start a history substitution, except when followed by a space, tab, +++ the end of the line, or '='. +++ +++'!N' +++ Refer to command line N. +++ +++'!-N' +++ Refer to the command N lines back. +++ +++'!!' +++ Refer to the previous command. This is a synonym for '!-1'. +++ +++'!STRING' +++ Refer to the most recent command preceding the current position in +++ the history list starting with STRING. +++ +++'!?STRING[?]' +++ Refer to the most recent command preceding the current position in +++ the history list containing STRING. The trailing '?' may be +++ omitted if the STRING is followed immediately by a newline. +++ +++'^STRING1^STRING2^' +++ Quick Substitution. Repeat the last command, replacing STRING1 +++ with STRING2. Equivalent to '!!:s/STRING1/STRING2/'. +++ +++'!#' +++ The entire command line typed so far. +++ +++ +++File: gdb.info, Node: Word Designators, Next: Modifiers, Prev: Event Designators, Up: History Interaction +++ +++33.1.2 Word Designators +++----------------------- +++ +++Word designators are used to select desired words from the event. A ':' +++separates the event specification from the word designator. It may be +++omitted if the word designator begins with a '^', '$', '*', '-', or '%'. +++Words are numbered from the beginning of the line, with the first word +++being denoted by 0 (zero). Words are inserted into the current line +++separated by single spaces. +++ +++ For example, +++ +++'!!' +++ designates the preceding command. When you type this, the +++ preceding command is repeated in toto. +++ +++'!!:$' +++ designates the last argument of the preceding command. This may be +++ shortened to '!$'. +++ +++'!fi:2' +++ designates the second argument of the most recent command starting +++ with the letters 'fi'. +++ +++ Here are the word designators: +++ +++'0 (zero)' +++ The '0'th word. For many applications, this is the command word. +++ +++'N' +++ The Nth word. +++ +++'^' +++ The first argument; that is, word 1. +++ +++'$' +++ The last argument. +++ +++'%' +++ The word matched by the most recent '?STRING?' search. +++ +++'X-Y' +++ A range of words; '-Y' abbreviates '0-Y'. +++ +++'*' +++ All of the words, except the '0'th. This is a synonym for '1-$'. +++ It is not an error to use '*' if there is just one word in the +++ event; the empty string is returned in that case. +++ +++'X*' +++ Abbreviates 'X-$' +++ +++'X-' +++ Abbreviates 'X-$' like 'X*', but omits the last word. +++ +++ If a word designator is supplied without an event specification, the +++previous command is used as the event. +++ +++ +++File: gdb.info, Node: Modifiers, Prev: Word Designators, Up: History Interaction +++ +++33.1.3 Modifiers +++---------------- +++ +++After the optional word designator, you can add a sequence of one or +++more of the following modifiers, each preceded by a ':'. +++ +++'h' +++ Remove a trailing pathname component, leaving only the head. +++ +++'t' +++ Remove all leading pathname components, leaving the tail. +++ +++'r' +++ Remove a trailing suffix of the form '.SUFFIX', leaving the +++ basename. +++ +++'e' +++ Remove all but the trailing suffix. +++ +++'p' +++ Print the new command but do not execute it. +++ +++'s/OLD/NEW/' +++ Substitute NEW for the first occurrence of OLD in the event line. +++ Any delimiter may be used in place of '/'. The delimiter may be +++ quoted in OLD and NEW with a single backslash. If '&' appears in +++ NEW, it is replaced by OLD. A single backslash will quote the '&'. +++ The final delimiter is optional if it is the last character on the +++ input line. +++ +++'&' +++ Repeat the previous substitution. +++ +++'g' +++'a' +++ Cause changes to be applied over the entire event line. Used in +++ conjunction with 's', as in 'gs/OLD/NEW/', or with '&'. +++ +++'G' +++ Apply the following 's' modifier once to each word in the event. +++ +++ +++File: gdb.info, Node: In Memoriam, Next: Formatting Documentation, Prev: Using History Interactively, Up: Top +++ +++Appendix A In Memoriam +++********************** +++ +++The GDB project mourns the loss of the following long-time contributors: +++ +++'Fred Fish' +++ Fred was a long-standing contributor to GDB (1991-2006), and to +++ Free Software in general. Outside of GDB, he was known in the +++ Amiga world for his series of Fish Disks, and the GeekGadget +++ project. +++ +++'Michael Snyder' +++ Michael was one of the Global Maintainers of the GDB project, with +++ contributions recorded as early as 1996, until 2011. In addition +++ to his day to day participation, he was a large driving force +++ behind adding Reverse Debugging to GDB. +++ +++ Beyond their technical contributions to the project, they were also +++enjoyable members of the Free Software Community. We will miss them. +++ +++ +++File: gdb.info, Node: Formatting Documentation, Next: Installing GDB, Prev: In Memoriam, Up: Top +++ +++Appendix B Formatting Documentation +++*********************************** +++ +++The GDB 4 release includes an already-formatted reference card, ready +++for printing with PostScript or Ghostscript, in the 'gdb' subdirectory +++of the main source directory(1). If you can use PostScript or +++Ghostscript with your printer, you can print the reference card +++immediately with 'refcard.ps'. +++ +++ The release also includes the source for the reference card. You can +++format it, using TeX, by typing: +++ +++ make refcard.dvi +++ +++ The GDB reference card is designed to print in "landscape" mode on US +++"letter" size paper; that is, on a sheet 11 inches wide by 8.5 inches +++high. You will need to specify this form of printing as an option to +++your DVI output program. +++ +++ All the documentation for GDB comes as part of the machine-readable +++distribution. The documentation is written in Texinfo format, which is +++a documentation system that uses a single source file to produce both +++on-line information and a printed manual. You can use one of the Info +++formatting commands to create the on-line version of the documentation +++and TeX (or 'texi2roff') to typeset the printed version. +++ +++ GDB includes an already formatted copy of the on-line Info version of +++this manual in the 'gdb' subdirectory. The main Info file is +++'gdb-10.1/gdb/gdb.info', and it refers to subordinate files matching +++'gdb.info*' in the same directory. If necessary, you can print out +++these files, or read them with any editor; but they are easier to read +++using the 'info' subsystem in GNU Emacs or the standalone 'info' +++program, available as part of the GNU Texinfo distribution. +++ +++ If you want to format these Info files yourself, you need one of the +++Info formatting programs, such as 'texinfo-format-buffer' or 'makeinfo'. +++ +++ If you have 'makeinfo' installed, and are in the top level GDB source +++directory ('gdb-10.1', in the case of version 10.1), you can make the +++Info file by typing: +++ +++ cd gdb +++ make gdb.info +++ +++ If you want to typeset and print copies of this manual, you need TeX, +++a program to print its DVI output files, and 'texinfo.tex', the Texinfo +++definitions file. +++ +++ TeX is a typesetting program; it does not print files directly, but +++produces output files called DVI files. To print a typeset document, +++you need a program to print DVI files. If your system has TeX +++installed, chances are it has such a program. The precise command to +++use depends on your system; 'lpr -d' is common; another (for PostScript +++devices) is 'dvips'. The DVI print command may require a file name +++without any extension or a '.dvi' extension. +++ +++ TeX also requires a macro definitions file called 'texinfo.tex'. +++This file tells TeX how to typeset a document written in Texinfo format. +++On its own, TeX cannot either read or typeset a Texinfo file. +++'texinfo.tex' is distributed with GDB and is located in the +++'gdb-VERSION-NUMBER/texinfo' directory. +++ +++ If you have TeX and a DVI printer program installed, you can typeset +++and print this manual. First switch to the 'gdb' subdirectory of the +++main source directory (for example, to 'gdb-10.1/gdb') and type: +++ +++ make gdb.dvi +++ +++ Then give 'gdb.dvi' to your DVI printing program. +++ +++ ---------- Footnotes ---------- +++ +++ (1) In 'gdb-10.1/gdb/refcard.ps' of the version 10.1 release. +++ +++ +++File: gdb.info, Node: Installing GDB, Next: Maintenance Commands, Prev: Formatting Documentation, Up: Top +++ +++Appendix C Installing GDB +++************************* +++ +++* Menu: +++ +++* Requirements:: Requirements for building GDB +++* Running Configure:: Invoking the GDB 'configure' script +++* Separate Objdir:: Compiling GDB in another directory +++* Config Names:: Specifying names for hosts and targets +++* Configure Options:: Summary of options for configure +++* System-wide configuration:: Having a system-wide init file +++ +++ +++File: gdb.info, Node: Requirements, Next: Running Configure, Up: Installing GDB +++ +++C.1 Requirements for Building GDB +++================================= +++ +++Building GDB requires various tools and packages to be available. Other +++packages will be used only if they are found. +++ +++Tools/Packages Necessary for Building GDB +++========================================= +++ +++C++11 compiler +++ GDB is written in C++11. It should be buildable with any recent +++ C++11 compiler, e.g. GCC. +++ +++GNU make +++ GDB's build system relies on features only found in the GNU make +++ program. Other variants of 'make' will not work. +++ +++Tools/Packages Optional for Building GDB +++======================================== +++ +++Expat +++ GDB can use the Expat XML parsing library. This library may be +++ included with your operating system distribution; if it is not, you +++ can get the latest version from . +++ The 'configure' script will search for this library in several +++ standard locations; if it is installed in an unusual path, you can +++ use the '--with-libexpat-prefix' option to specify its location. +++ +++ Expat is used for: +++ +++ * Remote protocol memory maps (*note Memory Map Format::) +++ * Target descriptions (*note Target Descriptions::) +++ * Remote shared library lists (*Note Library List Format::, or +++ alternatively *note Library List Format for SVR4 Targets::) +++ * MS-Windows shared libraries (*note Shared Libraries::) +++ * Traceframe info (*note Traceframe Info Format::) +++ * Branch trace (*note Branch Trace Format::, *note Branch Trace +++ Configuration Format::) +++ +++Guile +++ GDB can be scripted using GNU Guile. *Note Guile::. By default, +++ GDB will be compiled if the Guile libraries are installed and are +++ found by 'configure'. You can use the '--with-guile' option to +++ request Guile, and pass either the Guile version number or the file +++ name of the relevant 'pkg-config' program to choose a particular +++ version of Guile. +++ +++iconv +++ GDB's features related to character sets (*note Character Sets::) +++ require a functioning 'iconv' implementation. If you are on a GNU +++ system, then this is provided by the GNU C Library. Some other +++ systems also provide a working 'iconv'. +++ +++ If GDB is using the 'iconv' program which is installed in a +++ non-standard place, you will need to tell GDB where to find it. +++ This is done with '--with-iconv-bin' which specifies the directory +++ that contains the 'iconv' program. This program is run in order to +++ make a list of the available character sets. +++ +++ On systems without 'iconv', you can install GNU Libiconv. If +++ Libiconv is installed in a standard place, GDB will automatically +++ use it if it is needed. If you have previously installed Libiconv +++ in a non-standard place, you can use the '--with-libiconv-prefix' +++ option to 'configure'. +++ +++ GDB's top-level 'configure' and 'Makefile' will arrange to build +++ Libiconv if a directory named 'libiconv' appears in the top-most +++ source directory. If Libiconv is built this way, and if the +++ operating system does not provide a suitable 'iconv' +++ implementation, then the just-built library will automatically be +++ used by GDB. One easy way to set this up is to download GNU +++ Libiconv, unpack it inside the top-level directory of the GDB +++ source tree, and then rename the directory holding the Libiconv +++ source code to 'libiconv'. +++ +++lzma +++ GDB can support debugging sections that are compressed with the +++ LZMA library. *Note MiniDebugInfo::. If this library is not +++ included with your operating system, you can find it in the xz +++ package at . If the LZMA library is +++ available in the usual place, then the 'configure' script will use +++ it automatically. If it is installed in an unusual path, you can +++ use the '--with-lzma-prefix' option to specify its location. +++ +++MPFR +++ GDB can use the GNU MPFR multiple-precision floating-point library. +++ This library may be included with your operating system +++ distribution; if it is not, you can get the latest version from +++ . The 'configure' script will search for this +++ library in several standard locations; if it is installed in an +++ unusual path, you can use the '--with-libmpfr-prefix' option to +++ specify its location. +++ +++ GNU MPFR is used to emulate target floating-point arithmetic during +++ expression evaluation when the target uses different floating-point +++ formats than the host. If GNU MPFR it is not available, GDB will +++ fall back to using host floating-point arithmetic. +++ +++Python +++ GDB can be scripted using Python language. *Note Python::. By +++ default, GDB will be compiled if the Python libraries are installed +++ and are found by 'configure'. You can use the '--with-python' +++ option to request Python, and pass either the file name of the +++ relevant 'python' executable, or the name of the directory in which +++ Python is installed, to choose a particular installation of Python. +++ +++zlib +++ GDB will use the 'zlib' library, if available, to read compressed +++ debug sections. Some linkers, such as GNU gold, are capable of +++ producing binaries with compressed debug sections. If GDB is +++ compiled with 'zlib', it will be able to read the debug information +++ in such binaries. +++ +++ The 'zlib' library is likely included with your operating system +++ distribution; if it is not, you can get the latest version from +++ . +++ +++ +++File: gdb.info, Node: Running Configure, Next: Separate Objdir, Prev: Requirements, Up: Installing GDB +++ +++C.2 Invoking the GDB 'configure' Script +++======================================= +++ +++GDB comes with a 'configure' script that automates the process of +++preparing GDB for installation; you can then use 'make' to build the +++'gdb' program. +++ +++ The GDB distribution includes all the source code you need for GDB in +++a single directory, whose name is usually composed by appending the +++version number to 'gdb'. +++ +++ For example, the GDB version 10.1 distribution is in the 'gdb-10.1' +++directory. That directory contains: +++ +++'gdb-10.1/configure (and supporting files)' +++ script for configuring GDB and all its supporting libraries +++ +++'gdb-10.1/gdb' +++ the source specific to GDB itself +++ +++'gdb-10.1/bfd' +++ source for the Binary File Descriptor library +++ +++'gdb-10.1/include' +++ GNU include files +++ +++'gdb-10.1/libiberty' +++ source for the '-liberty' free software library +++ +++'gdb-10.1/opcodes' +++ source for the library of opcode tables and disassemblers +++ +++'gdb-10.1/readline' +++ source for the GNU command-line interface +++ +++ There may be other subdirectories as well. +++ +++ The simplest way to configure and build GDB is to run 'configure' +++from the 'gdb-VERSION-NUMBER' source directory, which in this example is +++the 'gdb-10.1' directory. +++ +++ First switch to the 'gdb-VERSION-NUMBER' source directory if you are +++not already in it; then run 'configure'. Pass the identifier for the +++platform on which GDB will run as an argument. +++ +++ For example: +++ +++ cd gdb-10.1 +++ ./configure +++ make +++ +++ Running 'configure' and then running 'make' builds the included +++supporting libraries, then 'gdb' itself. The configured source files, +++and the binaries, are left in the corresponding source directories. +++ +++ 'configure' is a Bourne-shell ('/bin/sh') script; if your system does +++not recognize this automatically when you run a different shell, you may +++need to run 'sh' on it explicitly: +++ +++ sh configure +++ +++ You should run the 'configure' script from the top directory in the +++source tree, the 'gdb-VERSION-NUMBER' directory. If you run 'configure' +++from one of the subdirectories, you will configure only that +++subdirectory. That is usually not what you want. In particular, if you +++run the first 'configure' from the 'gdb' subdirectory of the +++'gdb-VERSION-NUMBER' directory, you will omit the configuration of +++'bfd', 'readline', and other sibling directories of the 'gdb' +++subdirectory. This leads to build errors about missing include files +++such as 'bfd/bfd.h'. +++ +++ You can install 'GDB' anywhere. The best way to do this is to pass +++the '--prefix' option to 'configure', and then install it with 'make +++install'. +++ +++ +++File: gdb.info, Node: Separate Objdir, Next: Config Names, Prev: Running Configure, Up: Installing GDB +++ +++C.3 Compiling GDB in Another Directory +++====================================== +++ +++If you want to run GDB versions for several host or target machines, you +++need a different 'gdb' compiled for each combination of host and target. +++'configure' is designed to make this easy by allowing you to generate +++each configuration in a separate subdirectory, rather than in the source +++directory. If your 'make' program handles the 'VPATH' feature (GNU +++'make' does), running 'make' in each of these directories builds the +++'gdb' program specified there. +++ +++ To build 'gdb' in a separate directory, run 'configure' with the +++'--srcdir' option to specify where to find the source. (You also need +++to specify a path to find 'configure' itself from your working +++directory. If the path to 'configure' would be the same as the argument +++to '--srcdir', you can leave out the '--srcdir' option; it is assumed.) +++ +++ For example, with version 10.1, you can build GDB in a separate +++directory for a Sun 4 like this: +++ +++ cd gdb-10.1 +++ mkdir ../gdb-sun4 +++ cd ../gdb-sun4 +++ ../gdb-10.1/configure +++ make +++ +++ When 'configure' builds a configuration using a remote source +++directory, it creates a tree for the binaries with the same structure +++(and using the same names) as the tree under the source directory. In +++the example, you'd find the Sun 4 library 'libiberty.a' in the directory +++'gdb-sun4/libiberty', and GDB itself in 'gdb-sun4/gdb'. +++ +++ Make sure that your path to the 'configure' script has just one +++instance of 'gdb' in it. If your path to 'configure' looks like +++'../gdb-10.1/gdb/configure', you are configuring only one subdirectory +++of GDB, not the whole package. This leads to build errors about missing +++include files such as 'bfd/bfd.h'. +++ +++ One popular reason to build several GDB configurations in separate +++directories is to configure GDB for cross-compiling (where GDB runs on +++one machine--the "host"--while debugging programs that run on another +++machine--the "target"). You specify a cross-debugging target by giving +++the '--target=TARGET' option to 'configure'. +++ +++ When you run 'make' to build a program or library, you must run it in +++a configured directory--whatever directory you were in when you called +++'configure' (or one of its subdirectories). +++ +++ The 'Makefile' that 'configure' generates in each source directory +++also runs recursively. If you type 'make' in a source directory such as +++'gdb-10.1' (or in a separate configured directory configured with +++'--srcdir=DIRNAME/gdb-10.1'), you will build all the required libraries, +++and then build GDB. +++ +++ When you have multiple hosts or targets configured in separate +++directories, you can run 'make' on them in parallel (for example, if +++they are NFS-mounted on each of the hosts); they will not interfere with +++each other. +++ +++ +++File: gdb.info, Node: Config Names, Next: Configure Options, Prev: Separate Objdir, Up: Installing GDB +++ +++C.4 Specifying Names for Hosts and Targets +++========================================== +++ +++The specifications used for hosts and targets in the 'configure' script +++are based on a three-part naming scheme, but some short predefined +++aliases are also supported. The full naming scheme encodes three pieces +++of information in the following pattern: +++ +++ ARCHITECTURE-VENDOR-OS +++ +++ For example, you can use the alias 'sun4' as a HOST argument, or as +++the value for TARGET in a '--target=TARGET' option. The equivalent full +++name is 'sparc-sun-sunos4'. +++ +++ The 'configure' script accompanying GDB does not provide any query +++facility to list all supported host and target names or aliases. +++'configure' calls the Bourne shell script 'config.sub' to map +++abbreviations to full names; you can read the script, if you wish, or +++you can use it to test your guesses on abbreviations--for example: +++ +++ % sh config.sub i386-linux +++ i386-pc-linux-gnu +++ % sh config.sub alpha-linux +++ alpha-unknown-linux-gnu +++ % sh config.sub sw_64-linux +++ sw_64-unknown-linux-gnu +++ % sh config.sub hp9k700 +++ hppa1.1-hp-hpux +++ % sh config.sub sun4 +++ sparc-sun-sunos4.1.1 +++ % sh config.sub sun3 +++ m68k-sun-sunos4.1.1 +++ % sh config.sub i986v +++ Invalid configuration `i986v': machine `i986v' not recognized +++ +++'config.sub' is also distributed in the GDB source directory +++('gdb-10.1', for version 10.1). +++ +++ +++File: gdb.info, Node: Configure Options, Next: System-wide configuration, Prev: Config Names, Up: Installing GDB +++ +++C.5 'configure' Options +++======================= +++ +++Here is a summary of the 'configure' options and arguments that are most +++often useful for building GDB. 'configure' also has several other +++options not listed here. *note (autoconf.info)Running configure +++scripts::, for a full explanation of 'configure'. +++ +++ configure [--help] +++ [--prefix=DIR] +++ [--exec-prefix=DIR] +++ [--srcdir=DIRNAME] +++ [--target=TARGET] +++ +++You may introduce options with a single '-' rather than '--' if you +++prefer; but you may abbreviate option names if you use '--'. +++ +++'--help' +++ Display a quick summary of how to invoke 'configure'. +++ +++'--prefix=DIR' +++ Configure the source to install programs and files under directory +++ 'DIR'. +++ +++'--exec-prefix=DIR' +++ Configure the source to install programs under directory 'DIR'. +++ +++'--srcdir=DIRNAME' +++ Use this option to make configurations in directories separate from +++ the GDB source directories. Among other things, you can use this +++ to build (or maintain) several configurations simultaneously, in +++ separate directories. 'configure' writes configuration-specific +++ files in the current directory, but arranges for them to use the +++ source in the directory DIRNAME. 'configure' creates directories +++ under the working directory in parallel to the source directories +++ below DIRNAME. +++ +++'--target=TARGET' +++ Configure GDB for cross-debugging programs running on the specified +++ TARGET. Without this option, GDB is configured to debug programs +++ that run on the same machine (HOST) as GDB itself. +++ +++ There is no convenient way to generate a list of all available +++ targets. Also see the '--enable-targets' option, below. +++ +++ There are many other options that are specific to GDB. This lists +++just the most common ones; there are some very specialized options not +++described here. +++ +++'--enable-targets=[TARGET]...' +++'--enable-targets=all' +++ Configure GDB for cross-debugging programs running on the specified +++ list of targets. The special value 'all' configures GDB for +++ debugging programs running on any target it supports. +++ +++'--with-gdb-datadir=PATH' +++ Set the GDB-specific data directory. GDB will look here for +++ certain supporting files or scripts. This defaults to the 'gdb' +++ subdirectory of 'datadir' (which can be set using '--datadir'). +++ +++'--with-relocated-sources=DIR' +++ Sets up the default source path substitution rule so that directory +++ names recorded in debug information will be automatically adjusted +++ for any directory under DIR. DIR should be a subdirectory of GDB's +++ configured prefix, the one mentioned in the '--prefix' or +++ '--exec-prefix' options to configure. This option is useful if GDB +++ is supposed to be moved to a different place after it is built. +++ +++'--enable-64-bit-bfd' +++ Enable 64-bit support in BFD on 32-bit hosts. +++ +++'--disable-gdbmi' +++ Build GDB without the GDB/MI machine interface (*note GDB/MI::). +++ +++'--enable-tui' +++ Build GDB with the text-mode full-screen user interface (TUI). +++ Requires a curses library (ncurses and cursesX are also supported). +++ +++'--with-curses' +++ Use the curses library instead of the termcap library, for +++ text-mode terminal operations. +++ +++'--with-debuginfod' +++ Build GDB with libdebuginfod, the debuginfod client library. Used +++ to automatically fetch source files and separate debug files from +++ debuginfod servers using the associated executable's build ID. +++ Enabled by default if libdebuginfod is installed and found at +++ configure time. debuginfod is packaged with elfutils, starting +++ with version 0.178. You can get the latest version from +++ 'https://sourceware.org/elfutils/'. +++ +++'--with-libunwind-ia64' +++ Use the libunwind library for unwinding function call stack on ia64 +++ target platforms. See http://www.nongnu.org/libunwind/index.html +++ for details. +++ +++'--with-system-readline' +++ Use the readline library installed on the host, rather than the +++ library supplied as part of GDB. Readline 7 or newer is required; +++ this is enforced by the build system. +++ +++'--with-system-zlib' +++ Use the zlib library installed on the host, rather than the library +++ supplied as part of GDB. +++ +++'--with-expat' +++ Build GDB with Expat, a library for XML parsing. (Done by default +++ if libexpat is installed and found at configure time.) This +++ library is used to read XML files supplied with GDB. If it is +++ unavailable, some features, such as remote protocol memory maps, +++ target descriptions, and shared library lists, that are based on +++ XML files, will not be available in GDB. If your host does not +++ have libexpat installed, you can get the latest version from +++ 'http://expat.sourceforge.net'. +++ +++'--with-libiconv-prefix[=DIR]' +++ +++ Build GDB with GNU libiconv, a character set encoding conversion +++ library. This is not done by default, as on GNU systems the +++ 'iconv' that is built in to the C library is sufficient. If your +++ host does not have a working 'iconv', you can get the latest +++ version of GNU iconv from 'https://www.gnu.org/software/libiconv/'. +++ +++ GDB's build system also supports building GNU libiconv as part of +++ the overall build. *Note Requirements::. +++ +++'--with-lzma' +++ Build GDB with LZMA, a compression library. (Done by default if +++ liblzma is installed and found at configure time.) LZMA is used by +++ GDB's "mini debuginfo" feature, which is only useful on platforms +++ using the ELF object file format. If your host does not have +++ liblzma installed, you can get the latest version from +++ 'https://tukaani.org/xz/'. +++ +++'--with-mpfr' +++ Build GDB with GNU MPFR, a library for multiple-precision +++ floating-point computation with correct rounding. (Done by default +++ if GNU MPFR is installed and found at configure time.) This +++ library is used to emulate target floating-point arithmetic during +++ expression evaluation when the target uses different floating-point +++ formats than the host. If GNU MPFR is not available, GDB will fall +++ back to using host floating-point arithmetic. If your host does +++ not have GNU MPFR installed, you can get the latest version from +++ 'http://www.mpfr.org'. +++ +++'--with-python[=PYTHON]' +++ Build GDB with Python scripting support. (Done by default if +++ libpython is present and found at configure time.) Python makes +++ GDB scripting much more powerful than the restricted CLI scripting +++ language. If your host does not have Python installed, you can +++ find it on 'http://www.python.org/download/'. The oldest version +++ of Python supported by GDB is 2.6. The optional argument PYTHON is +++ used to find the Python headers and libraries. It can be either +++ the name of a Python executable, or the name of the directory in +++ which Python is installed. +++ +++'--with-guile[=GUILE]'' +++ Build GDB with GNU Guile scripting support. (Done by default if +++ libguile is present and found at configure time.) If your host +++ does not have Guile installed, you can find it at +++ 'https://www.gnu.org/software/guile/'. The optional argument GUILE +++ can be a version number, which will cause 'configure' to try to use +++ that version of Guile; or the file name of a 'pkg-config' +++ executable, which will be queried to find the information needed to +++ compile and link against Guile. +++ +++'--without-included-regex' +++ Don't use the regex library included with GDB (as part of the +++ libiberty library). This is the default on hosts with version 2 of +++ the GNU C library. +++ +++'--with-sysroot=DIR' +++ Use DIR as the default system root directory for libraries whose +++ file names begin with '/lib'' or '/usr/lib''. (The value of DIR +++ can be modified at run time by using the 'set sysroot' command.) +++ If DIR is under the GDB configured prefix (set with '--prefix' or +++ '--exec-prefix options', the default system root will be +++ automatically adjusted if and when GDB is moved to a different +++ location. +++ +++'--with-system-gdbinit=FILE' +++ Configure GDB to automatically load a system-wide init file. FILE +++ should be an absolute file name. If FILE is in a directory under +++ the configured prefix, and GDB is moved to another location after +++ being built, the location of the system-wide init file will be +++ adjusted accordingly. +++ +++'--with-system-gdbinit-dir=DIRECTORY' +++ Configure GDB to automatically load init files from a system-wide +++ directory. DIRECTORY should be an absolute directory name. If +++ DIRECTORY is in a directory under the configured prefix, and GDB is +++ moved to another location after being built, the location of the +++ system-wide init directory will be adjusted accordingly. +++ +++'--enable-build-warnings' +++ When building the GDB sources, ask the compiler to warn about any +++ code which looks even vaguely suspicious. It passes many different +++ warning flags, depending on the exact version of the compiler you +++ are using. +++ +++'--enable-werror' +++ Treat compiler warnings as werrors. It adds the '-Werror' flag to +++ the compiler, which will fail the compilation if the compiler +++ outputs any warning messages. +++ +++'--enable-ubsan' +++ Enable the GCC undefined behavior sanitizer. This is disabled by +++ default, but passing '--enable-ubsan=yes' or '--enable-ubsan=auto' +++ to 'configure' will enable it. The undefined behavior sanitizer +++ checks for C++ undefined behavior. It has a performance cost, so +++ if you are looking at GDB's performance, you should disable it. +++ The undefined behavior sanitizer was first introduced in GCC 4.9. +++ +++ +++File: gdb.info, Node: System-wide configuration, Prev: Configure Options, Up: Installing GDB +++ +++C.6 System-wide configuration and settings +++========================================== +++ +++GDB can be configured to have a system-wide init file and a system-wide +++init file directory; this file and files in that directory (if they have +++a recognized file extension) will be read and executed at startup (*note +++What GDB does during startup: Startup.). +++ +++ Here are the corresponding configure options: +++ +++'--with-system-gdbinit=FILE' +++ Specify that the default location of the system-wide init file is +++ FILE. +++'--with-system-gdbinit-dir=DIRECTORY' +++ Specify that the default location of the system-wide init file +++ directory is DIRECTORY. +++ +++ If GDB has been configured with the option '--prefix=$prefix', they +++may be subject to relocation. Two possible cases: +++ +++ * If the default location of this init file/directory contains +++ '$prefix', it will be subject to relocation. Suppose that the +++ configure options are '--prefix=$prefix +++ --with-system-gdbinit=$prefix/etc/gdbinit'; if GDB is moved from +++ '$prefix' to '$install', the system init file is looked for as +++ '$install/etc/gdbinit' instead of '$prefix/etc/gdbinit'. +++ +++ * By contrast, if the default location does not contain the prefix, +++ it will not be relocated. E.g. if GDB has been configured with +++ '--prefix=/usr/local --with-system-gdbinit=/usr/share/gdb/gdbinit', +++ then GDB will always look for '/usr/share/gdb/gdbinit', wherever +++ GDB is installed. +++ +++ If the configured location of the system-wide init file (as given by +++the '--with-system-gdbinit' option at configure time) is in the +++data-directory (as specified by '--with-gdb-datadir' at configure time) +++or in one of its subdirectories, then GDB will look for the system-wide +++init file in the directory specified by the '--data-directory' +++command-line option. Note that the system-wide init file is only read +++once, during GDB initialization. If the data-directory is changed after +++GDB has started with the 'set data-directory' command, the file will not +++be reread. +++ +++ This applies similarly to the system-wide directory specified in +++'--with-system-gdbinit-dir'. +++ +++ Any supported scripting language can be used for these init files, as +++long as the file extension matches the scripting language. To be +++interpreted as regular GDB commands, the files needs to have a '.gdb' +++extension. +++ +++* Menu: +++ +++* System-wide Configuration Scripts:: Installed System-wide Configuration Scripts +++ +++ +++File: gdb.info, Node: System-wide Configuration Scripts, Up: System-wide configuration +++ +++C.6.1 Installed System-wide Configuration Scripts +++------------------------------------------------- +++ +++The 'system-gdbinit' directory, located inside the data-directory (as +++specified by '--with-gdb-datadir' at configure time) contains a number +++of scripts which can be used as system-wide init files. To +++automatically source those scripts at startup, GDB should be configured +++with '--with-system-gdbinit'. Otherwise, any user should be able to +++source them by hand as needed. +++ +++ The following scripts are currently available: +++ +++ * 'elinos.py' This script is useful when debugging a program on an +++ ELinOS target. It takes advantage of the environment variables +++ defined in a standard ELinOS environment in order to determine the +++ location of the system shared libraries, and then sets the +++ 'solib-absolute-prefix' and 'solib-search-path' variables +++ appropriately. +++ +++ * 'wrs-linux.py' This script is useful when debugging a program on a +++ target running Wind River Linux. It expects the 'ENV_PREFIX' to be +++ set to the host-side sysroot used by the target system. +++ +++ +++File: gdb.info, Node: Maintenance Commands, Next: Remote Protocol, Prev: Installing GDB, Up: Top +++ +++Appendix D Maintenance Commands +++******************************* +++ +++In addition to commands intended for GDB users, GDB includes a number of +++commands intended for GDB developers, that are not documented elsewhere +++in this manual. These commands are provided here for reference. (For +++commands that turn on debugging messages, see *note Debugging Output::.) +++ +++'maint agent [-at LOCATION,] EXPRESSION' +++'maint agent-eval [-at LOCATION,] EXPRESSION' +++ Translate the given EXPRESSION into remote agent bytecodes. This +++ command is useful for debugging the Agent Expression mechanism +++ (*note Agent Expressions::). The 'agent' version produces an +++ expression useful for data collection, such as by tracepoints, +++ while 'maint agent-eval' produces an expression that evaluates +++ directly to a result. For instance, a collection expression for +++ 'globa + globb' will include bytecodes to record four bytes of +++ memory at each of the addresses of 'globa' and 'globb', while +++ discarding the result of the addition, while an evaluation +++ expression will do the addition and return the sum. If '-at' is +++ given, generate remote agent bytecode for LOCATION. If not, +++ generate remote agent bytecode for current frame PC address. +++ +++'maint agent-printf FORMAT,EXPR,...' +++ Translate the given format string and list of argument expressions +++ into remote agent bytecodes and display them as a disassembled +++ list. This command is useful for debugging the agent version of +++ dynamic printf (*note Dynamic Printf::). +++ +++'maint info breakpoints' +++ Using the same format as 'info breakpoints', display both the +++ breakpoints you've set explicitly, and those GDB is using for +++ internal purposes. Internal breakpoints are shown with negative +++ breakpoint numbers. The type column identifies what kind of +++ breakpoint is shown: +++ +++ 'breakpoint' +++ Normal, explicitly set breakpoint. +++ +++ 'watchpoint' +++ Normal, explicitly set watchpoint. +++ +++ 'longjmp' +++ Internal breakpoint, used to handle correctly stepping through +++ 'longjmp' calls. +++ +++ 'longjmp resume' +++ Internal breakpoint at the target of a 'longjmp'. +++ +++ 'until' +++ Temporary internal breakpoint used by the GDB 'until' command. +++ +++ 'finish' +++ Temporary internal breakpoint used by the GDB 'finish' +++ command. +++ +++ 'shlib events' +++ Shared library events. +++ +++'maint info btrace' +++ Pint information about raw branch tracing data. +++ +++'maint btrace packet-history' +++ Print the raw branch trace packets that are used to compute the +++ execution history for the 'record btrace' command. Both the +++ information and the format in which it is printed depend on the +++ btrace recording format. +++ +++ 'bts' +++ For the BTS recording format, print a list of blocks of +++ sequential code. For each block, the following information is +++ printed: +++ +++ Block number +++ Newer blocks have higher numbers. The oldest block has +++ number zero. +++ Lowest 'PC' +++ Highest 'PC' +++ +++ 'pt' +++ For the Intel Processor Trace recording format, print a list +++ of Intel Processor Trace packets. For each packet, the +++ following information is printed: +++ +++ Packet number +++ Newer packets have higher numbers. The oldest packet has +++ number zero. +++ Trace offset +++ The packet's offset in the trace stream. +++ Packet opcode and payload +++ +++'maint btrace clear-packet-history' +++ Discards the cached packet history printed by the 'maint btrace +++ packet-history' command. The history will be computed again when +++ needed. +++ +++'maint btrace clear' +++ Discard the branch trace data. The data will be fetched anew and +++ the branch trace will be recomputed when needed. +++ +++ This implicitly truncates the branch trace to a single branch trace +++ buffer. When updating branch trace incrementally, the branch trace +++ available to GDB may be bigger than a single branch trace buffer. +++ +++'maint set btrace pt skip-pad' +++'maint show btrace pt skip-pad' +++ Control whether GDB will skip PAD packets when computing the packet +++ history. +++ +++'set displaced-stepping' +++'show displaced-stepping' +++ Control whether or not GDB will do "displaced stepping" if the +++ target supports it. Displaced stepping is a way to single-step +++ over breakpoints without removing them from the inferior, by +++ executing an out-of-line copy of the instruction that was +++ originally at the breakpoint location. It is also known as +++ out-of-line single-stepping. +++ +++ 'set displaced-stepping on' +++ If the target architecture supports it, GDB will use displaced +++ stepping to step over breakpoints. +++ +++ 'set displaced-stepping off' +++ GDB will not use displaced stepping to step over breakpoints, +++ even if such is supported by the target architecture. +++ +++ 'set displaced-stepping auto' +++ This is the default mode. GDB will use displaced stepping +++ only if non-stop mode is active (*note Non-Stop Mode::) and +++ the target architecture supports displaced stepping. +++ +++'maint check-psymtabs' +++ Check the consistency of currently expanded psymtabs versus +++ symtabs. Use this to check, for example, whether a symbol is in +++ one but not the other. +++ +++'maint check-symtabs' +++ Check the consistency of currently expanded symtabs. +++ +++'maint expand-symtabs [REGEXP]' +++ Expand symbol tables. If REGEXP is specified, only expand symbol +++ tables for file names matching REGEXP. +++ +++'maint set catch-demangler-crashes [on|off]' +++'maint show catch-demangler-crashes' +++ Control whether GDB should attempt to catch crashes in the symbol +++ name demangler. The default is to attempt to catch crashes. If +++ enabled, the first time a crash is caught, a core file is created, +++ the offending symbol is displayed and the user is presented with +++ the option to terminate the current session. +++ +++'maint cplus first_component NAME' +++ Print the first C++ class/namespace component of NAME. +++ +++'maint cplus namespace' +++ Print the list of possible C++ namespaces. +++ +++'maint deprecate COMMAND [REPLACEMENT]' +++'maint undeprecate COMMAND' +++ Deprecate or undeprecate the named COMMAND. Deprecated commands +++ cause GDB to issue a warning when you use them. The optional +++ argument REPLACEMENT says which newer command should be used in +++ favor of the deprecated one; if it is given, GDB will mention the +++ replacement as part of the warning. +++ +++'maint dump-me' +++ Cause a fatal signal in the debugger and force it to dump its core. +++ This is supported only on systems which support aborting a program +++ with the 'SIGQUIT' signal. +++ +++'maint internal-error [MESSAGE-TEXT]' +++'maint internal-warning [MESSAGE-TEXT]' +++'maint demangler-warning [MESSAGE-TEXT]' +++ +++ Cause GDB to call the internal function 'internal_error', +++ 'internal_warning' or 'demangler_warning' and hence behave as +++ though an internal problem has been detected. In addition to +++ reporting the internal problem, these functions give the user the +++ opportunity to either quit GDB or (for 'internal_error' and +++ 'internal_warning') create a core file of the current GDB session. +++ +++ These commands take an optional parameter MESSAGE-TEXT that is used +++ as the text of the error or warning message. +++ +++ Here's an example of using 'internal-error': +++ +++ (gdb) maint internal-error testing, 1, 2 +++ .../maint.c:121: internal-error: testing, 1, 2 +++ A problem internal to GDB has been detected. Further +++ debugging may prove unreliable. +++ Quit this debugging session? (y or n) n +++ Create a core file? (y or n) n +++ (gdb) +++ +++'maint set internal-error ACTION [ask|yes|no]' +++'maint show internal-error ACTION' +++'maint set internal-warning ACTION [ask|yes|no]' +++'maint show internal-warning ACTION' +++'maint set demangler-warning ACTION [ask|yes|no]' +++'maint show demangler-warning ACTION' +++ When GDB reports an internal problem (error or warning) it gives +++ the user the opportunity to both quit GDB and create a core file of +++ the current GDB session. These commands let you override the +++ default behaviour for each particular ACTION, described in the +++ table below. +++ +++ 'quit' +++ You can specify that GDB should always (yes) or never (no) +++ quit. The default is to ask the user what to do. +++ +++ 'corefile' +++ You can specify that GDB should always (yes) or never (no) +++ create a core file. The default is to ask the user what to +++ do. Note that there is no 'corefile' option for +++ 'demangler-warning': demangler warnings always create a core +++ file and this cannot be disabled. +++ +++'maint packet TEXT' +++ If GDB is talking to an inferior via the serial protocol, then this +++ command sends the string TEXT to the inferior, and displays the +++ response packet. GDB supplies the initial '$' character, the +++ terminating '#' character, and the checksum. +++ +++'maint print architecture [FILE]' +++ Print the entire architecture configuration. The optional argument +++ FILE names the file where the output goes. +++ +++'maint print c-tdesc' +++ Print the target description (*note Target Descriptions::) as a C +++ source file. By default, the target description is for the current +++ target, but if the optional argument FILE is provided, that file is +++ used to produce the description. The FILE should be an XML +++ document, of the form described in *note Target Description +++ Format::. The created source file is built into GDB when GDB is +++ built again. This command is used by developers after they add or +++ modify XML target descriptions. +++ +++'maint print xml-tdesc [FILE]' +++ Print the target description (*note Target Descriptions::) as an +++ XML file. By default print the target description for the current +++ target, but if the optional argument FILE is provided, then that +++ file is read in by GDB and then used to produce the description. +++ The FILE should be an XML document, of the form described in *note +++ Target Description Format::. +++ +++'maint check xml-descriptions DIR' +++ Check that the target descriptions dynamically created by GDB equal +++ the descriptions created from XML files found in DIR. +++ +++'maint check libthread-db' +++ Run integrity checks on the current inferior's thread debugging +++ library. This exercises all 'libthread_db' functionality used by +++ GDB on GNU/Linux systems, and by extension also exercises the +++ 'proc_service' functions provided by GDB that 'libthread_db' uses. +++ Note that parts of the test may be skipped on some platforms when +++ debugging core files. +++ +++'maint print core-file-backed-mappings' +++ Print the file-backed mappings which were loaded from a core file +++ note. This output represents state internal to GDB and should be +++ similar to the mappings displayed by the 'info proc mappings' +++ command. +++ +++'maint print dummy-frames' +++ Prints the contents of GDB's internal dummy-frame stack. +++ +++ (gdb) b add +++ ... +++ (gdb) print add(2,3) +++ Breakpoint 2, add (a=2, b=3) at ... +++ 58 return (a + b); +++ The program being debugged stopped while in a function called from GDB. +++ ... +++ (gdb) maint print dummy-frames +++ 0xa8206d8: id={stack=0xbfffe734,code=0xbfffe73f,!special}, ptid=process 9353 +++ (gdb) +++ +++ Takes an optional file parameter. +++ +++'maint print registers [FILE]' +++'maint print raw-registers [FILE]' +++'maint print cooked-registers [FILE]' +++'maint print register-groups [FILE]' +++'maint print remote-registers [FILE]' +++ Print GDB's internal register data structures. +++ +++ The command 'maint print raw-registers' includes the contents of +++ the raw register cache; the command 'maint print cooked-registers' +++ includes the (cooked) value of all registers, including registers +++ which aren't available on the target nor visible to user; the +++ command 'maint print register-groups' includes the groups that each +++ register is a member of; and the command 'maint print +++ remote-registers' includes the remote target's register numbers and +++ offsets in the 'G' packets. +++ +++ These commands take an optional parameter, a file name to which to +++ write the information. +++ +++'maint print reggroups [FILE]' +++ Print GDB's internal register group data structures. The optional +++ argument FILE tells to what file to write the information. +++ +++ The register groups info looks like this: +++ +++ (gdb) maint print reggroups +++ Group Type +++ general user +++ float user +++ all user +++ vector user +++ system user +++ save internal +++ restore internal +++ +++'flushregs' +++ This command forces GDB to flush its internal register cache. +++ +++'maint print objfiles [REGEXP]' +++ Print a dump of all known object files. If REGEXP is specified, +++ only print object files whose names match REGEXP. For each object +++ file, this command prints its name, address in memory, and all of +++ its psymtabs and symtabs. +++ +++'maint print user-registers' +++ List all currently available "user registers". User registers +++ typically provide alternate names for actual hardware registers. +++ They include the four "standard" registers '$fp', '$pc', '$sp', and +++ '$ps'. *Note standard registers::. User registers can be used in +++ expressions in the same way as the canonical register names, but +++ only the latter are listed by the 'info registers' and 'maint print +++ registers' commands. +++ +++'maint print section-scripts [REGEXP]' +++ Print a dump of scripts specified in the '.debug_gdb_section' +++ section. If REGEXP is specified, only print scripts loaded by +++ object files matching REGEXP. For each script, this command prints +++ its name as specified in the objfile, and the full path if known. +++ *Note dotdebug_gdb_scripts section::. +++ +++'maint print statistics' +++ This command prints, for each object file in the program, various +++ data about that object file followed by the byte cache ("bcache") +++ statistics for the object file. The objfile data includes the +++ number of minimal, partial, full, and stabs symbols, the number of +++ types defined by the objfile, the number of as yet unexpanded psym +++ tables, the number of line tables and string tables, and the amount +++ of memory used by the various tables. The bcache statistics +++ include the counts, sizes, and counts of duplicates of all and +++ unique objects, max, average, and median entry size, total memory +++ used and its overhead and savings, and various measures of the hash +++ table size and chain lengths. +++ +++'maint print target-stack' +++ A "target" is an interface between the debugger and a particular +++ kind of file or process. Targets can be stacked in "strata", so +++ that more than one target can potentially respond to a request. In +++ particular, memory accesses will walk down the stack of targets +++ until they find a target that is interested in handling that +++ particular address. +++ +++ This command prints a short description of each layer that was +++ pushed on the "target stack", starting from the top layer down to +++ the bottom one. +++ +++'maint print type EXPR' +++ Print the type chain for a type specified by EXPR. The argument +++ can be either a type name or a symbol. If it is a symbol, the type +++ of that symbol is described. The type chain produced by this +++ command is a recursive definition of the data type as stored in +++ GDB's data structures, including its flags and contained types. +++ +++'maint selftest [FILTER]' +++ Run any self tests that were compiled in to GDB. This will print a +++ message showing how many tests were run, and how many failed. If a +++ FILTER is passed, only the tests with FILTER in their name will by +++ ran. +++ +++'maint info selftests' +++ List the selftests compiled in to GDB. +++ +++'maint set dwarf always-disassemble' +++'maint show dwarf always-disassemble' +++ Control the behavior of 'info address' when using DWARF debugging +++ information. +++ +++ The default is 'off', which means that GDB should try to describe a +++ variable's location in an easily readable format. When 'on', GDB +++ will instead display the DWARF location expression in an +++ assembly-like format. Note that some locations are too complex for +++ GDB to describe simply; in this case you will always see the +++ disassembly form. +++ +++ Here is an example of the resulting disassembly: +++ +++ (gdb) info addr argc +++ Symbol "argc" is a complex DWARF expression: +++ 1: DW_OP_fbreg 0 +++ +++ For more information on these expressions, see the DWARF standard +++ (http://www.dwarfstd.org/). +++ +++'maint set dwarf max-cache-age' +++'maint show dwarf max-cache-age' +++ Control the DWARF compilation unit cache. +++ +++ In object files with inter-compilation-unit references, such as +++ those produced by the GCC option '-feliminate-dwarf2-dups', the +++ DWARF reader needs to frequently refer to previously read +++ compilation units. This setting controls how long a compilation +++ unit will remain in the cache if it is not referenced. A higher +++ limit means that cached compilation units will be stored in memory +++ longer, and more total memory will be used. Setting it to zero +++ disables caching, which will slow down GDB startup, but reduce +++ memory consumption. +++ +++'maint set dwarf unwinders' +++'maint show dwarf unwinders' +++ Control use of the DWARF frame unwinders. +++ +++ Many targets that support DWARF debugging use GDB's DWARF frame +++ unwinders to build the backtrace. Many of these targets will also +++ have a second mechanism for building the backtrace for use in cases +++ where DWARF information is not available, this second mechanism is +++ often an analysis of a function's prologue. +++ +++ In order to extend testing coverage of the second level stack +++ unwinding mechanisms it is helpful to be able to disable the DWARF +++ stack unwinders, this can be done with this switch. +++ +++ In normal use of GDB disabling the DWARF unwinders is not +++ advisable, there are cases that are better handled through DWARF +++ than prologue analysis, and the debug experience is likely to be +++ better with the DWARF frame unwinders enabled. +++ +++ If DWARF frame unwinders are not supported for a particular target +++ architecture, then enabling this flag does not cause them to be +++ used. +++ +++'maint set worker-threads' +++'maint show worker-threads' +++ Control the number of worker threads that may be used by GDB. On +++ capable hosts, GDB may use multiple threads to speed up certain +++ CPU-intensive operations, such as demangling symbol names. While +++ the number of threads used by GDB may vary, this command can be +++ used to set an upper bound on this number. The default is +++ 'unlimited', which lets GDB choose a reasonable number. Note that +++ this only controls worker threads started by GDB itself; libraries +++ used by GDB may start threads of their own. +++ +++'maint set profile' +++'maint show profile' +++ Control profiling of GDB. +++ +++ Profiling will be disabled until you use the 'maint set profile' +++ command to enable it. When you enable profiling, the system will +++ begin collecting timing and execution count data; when you disable +++ profiling or exit GDB, the results will be written to a log file. +++ Remember that if you use profiling, GDB will overwrite the +++ profiling log file (often called 'gmon.out'). If you have a record +++ of important profiling data in a 'gmon.out' file, be sure to move +++ it to a safe location. +++ +++ Configuring with '--enable-profiling' arranges for GDB to be +++ compiled with the '-pg' compiler option. +++ +++'maint set show-debug-regs' +++'maint show show-debug-regs' +++ Control whether to show variables that mirror the hardware debug +++ registers. Use 'on' to enable, 'off' to disable. If enabled, the +++ debug registers values are shown when GDB inserts or removes a +++ hardware breakpoint or watchpoint, and when the inferior triggers a +++ hardware-assisted breakpoint or watchpoint. +++ +++'maint set show-all-tib' +++'maint show show-all-tib' +++ Control whether to show all non zero areas within a 1k block +++ starting at thread local base, when using the 'info w32 +++ thread-information-block' command. +++ +++'maint set target-async' +++'maint show target-async' +++ This controls whether GDB targets operate in synchronous or +++ asynchronous mode (*note Background Execution::). Normally the +++ default is asynchronous, if it is available; but this can be +++ changed to more easily debug problems occurring only in synchronous +++ mode. +++ +++'maint set target-non-stop' +++'maint show target-non-stop' +++ +++ This controls whether GDB targets always operate in non-stop mode +++ even if 'set non-stop' is 'off' (*note Non-Stop Mode::). The +++ default is 'auto', meaning non-stop mode is enabled if supported by +++ the target. +++ +++ 'maint set target-non-stop auto' +++ This is the default mode. GDB controls the target in non-stop +++ mode if the target supports it. +++ +++ 'maint set target-non-stop on' +++ GDB controls the target in non-stop mode even if the target +++ does not indicate support. +++ +++ 'maint set target-non-stop off' +++ GDB does not control the target in non-stop mode even if the +++ target supports it. +++ +++'maint set tui-resize-message' +++'maint show tui-resize-message' +++ Control whether GDB displays a message each time the terminal is +++ resized when in TUI mode. The default is 'off', which means that +++ GDB is silent during resizes. When 'on', GDB will display a +++ message after a resize is completed; the message will include a +++ number indicating how many times the terminal has been resized. +++ This setting is intended for use by the test suite, where it would +++ otherwise be difficult to determine when a resize and refresh has +++ been completed. +++ +++'maint set per-command' +++'maint show per-command' +++ +++ GDB can display the resources used by each command. This is useful +++ in debugging performance problems. +++ +++ 'maint set per-command space [on|off]' +++ 'maint show per-command space' +++ Enable or disable the printing of the memory used by GDB for +++ each command. If enabled, GDB will display how much memory +++ each command took, following the command's own output. This +++ can also be requested by invoking GDB with the '--statistics' +++ command-line switch (*note Mode Options::). +++ +++ 'maint set per-command time [on|off]' +++ 'maint show per-command time' +++ Enable or disable the printing of the execution time of GDB +++ for each command. If enabled, GDB will display how much time +++ it took to execute each command, following the command's own +++ output. Both CPU time and wallclock time are printed. +++ Printing both is useful when trying to determine whether the +++ cost is CPU or, e.g., disk/network latency. Note that the CPU +++ time printed is for GDB only, it does not include the +++ execution time of the inferior because there's no mechanism +++ currently to compute how much time was spent by GDB and how +++ much time was spent by the program been debugged. This can +++ also be requested by invoking GDB with the '--statistics' +++ command-line switch (*note Mode Options::). +++ +++ 'maint set per-command symtab [on|off]' +++ 'maint show per-command symtab' +++ Enable or disable the printing of basic symbol table +++ statistics for each command. If enabled, GDB will display the +++ following information: +++ +++ a. number of symbol tables +++ b. number of primary symbol tables +++ c. number of blocks in the blockvector +++ +++'maint set check-libthread-db [on|off]' +++'maint show check-libthread-db' +++ Control whether GDB should run integrity checks on inferior +++ specific thread debugging libraries as they are loaded. The +++ default is not to perform such checks. If any check fails GDB will +++ unload the library and continue searching for a suitable candidate +++ as described in *note set libthread-db-search-path::. For more +++ information about the tests, see *note maint check libthread-db::. +++ +++'maint space VALUE' +++ An alias for 'maint set per-command space'. A non-zero value +++ enables it, zero disables it. +++ +++'maint time VALUE' +++ An alias for 'maint set per-command time'. A non-zero value +++ enables it, zero disables it. +++ +++'maint translate-address [SECTION] ADDR' +++ Find the symbol stored at the location specified by the address +++ ADDR and an optional section name SECTION. If found, GDB prints +++ the name of the closest symbol and an offset from the symbol's +++ location to the specified address. This is similar to the 'info +++ address' command (*note Symbols::), except that this command also +++ allows to find symbols in other sections. +++ +++ If section was not specified, the section in which the symbol was +++ found is also printed. For dynamically linked executables, the +++ name of executable or shared library containing the symbol is +++ printed as well. +++ +++'maint test-options require-delimiter' +++'maint test-options unknown-is-error' +++'maint test-options unknown-is-operand' +++ These commands are used by the testsuite to validate the command +++ options framework. The 'require-delimiter' variant requires a +++ double-dash delimiter to indicate end of options. The +++ 'unknown-is-error' and 'unknown-is-operand' do not. The +++ 'unknown-is-error' variant throws an error on unknown option, while +++ 'unknown-is-operand' treats unknown options as the start of the +++ command's operands. When run, the commands output the result of +++ the processed options. When completed, the commands store the +++ internal result of completion in a variable exposed by the 'maint +++ show test-options-completion-result' command. +++ +++'maint show test-options-completion-result' +++ Shows the result of completing the 'maint test-options' +++ subcommands. This is used by the testsuite to validate completion +++ support in the command options framework. +++ +++'maint set test-settings KIND' +++'maint show test-settings KIND' +++ These are representative commands for each KIND of setting type GDB +++ supports. They are used by the testsuite for exercising the +++ settings infrastructure. +++ +++'maint with SETTING [VALUE] [-- COMMAND]' +++ Like the 'with' command, but works with 'maintenance set' +++ variables. This is used by the testsuite to exercise the 'with' +++ command's infrastructure. +++ +++ The following command is useful for non-interactive invocations of +++GDB, such as in the test suite. +++ +++'set watchdog NSEC' +++ Set the maximum number of seconds GDB will wait for the target +++ operation to finish. If this time expires, GDB reports and error +++ and the command is aborted. +++ +++'show watchdog' +++ Show the current setting of the target wait timeout. +++ +++ +++File: gdb.info, Node: Remote Protocol, Next: Agent Expressions, Prev: Maintenance Commands, Up: Top +++ +++Appendix E GDB Remote Serial Protocol +++************************************* +++ +++* Menu: +++ +++* Overview:: +++* Packets:: +++* Stop Reply Packets:: +++* General Query Packets:: +++* Architecture-Specific Protocol Details:: +++* Tracepoint Packets:: +++* Host I/O Packets:: +++* Interrupts:: +++* Notification Packets:: +++* Remote Non-Stop:: +++* Packet Acknowledgment:: +++* Examples:: +++* File-I/O Remote Protocol Extension:: +++* Library List Format:: +++* Library List Format for SVR4 Targets:: +++* Memory Map Format:: +++* Thread List Format:: +++* Traceframe Info Format:: +++* Branch Trace Format:: +++* Branch Trace Configuration Format:: +++ +++ +++File: gdb.info, Node: Overview, Next: Packets, Up: Remote Protocol +++ +++E.1 Overview +++============ +++ +++There may be occasions when you need to know something about the +++protocol--for example, if there is only one serial port to your target +++machine, you might want your program to do something special if it +++recognizes a packet meant for GDB. +++ +++ In the examples below, '->' and '<-' are used to indicate transmitted +++and received data, respectively. +++ +++ All GDB commands and responses (other than acknowledgments and +++notifications, see *note Notification Packets::) are sent as a PACKET. +++A PACKET is introduced with the character '$', the actual PACKET-DATA, +++and the terminating character '#' followed by a two-digit CHECKSUM: +++ +++ $PACKET-DATA#CHECKSUM +++ +++The two-digit CHECKSUM is computed as the modulo 256 sum of all +++characters between the leading '$' and the trailing '#' (an eight bit +++unsigned checksum). +++ +++ Implementors should note that prior to GDB 5.0 the protocol +++specification also included an optional two-digit SEQUENCE-ID: +++ +++ $SEQUENCE-ID:PACKET-DATA#CHECKSUM +++ +++That SEQUENCE-ID was appended to the acknowledgment. GDB has never +++output SEQUENCE-IDs. Stubs that handle packets added since GDB 5.0 must +++not accept SEQUENCE-ID. +++ +++ When either the host or the target machine receives a packet, the +++first response expected is an acknowledgment: either '+' (to indicate +++the package was received correctly) or '-' (to request retransmission): +++ +++ -> $PACKET-DATA#CHECKSUM +++ <- + +++ +++ The '+'/'-' acknowledgments can be disabled once a connection is +++established. *Note Packet Acknowledgment::, for details. +++ +++ The host (GDB) sends COMMANDs, and the target (the debugging stub +++incorporated in your program) sends a RESPONSE. In the case of step and +++continue COMMANDs, the response is only sent when the operation has +++completed, and the target has again stopped all threads in all attached +++processes. This is the default all-stop mode behavior, but the remote +++protocol also supports GDB's non-stop execution mode; see *note Remote +++Non-Stop::, for details. +++ +++ PACKET-DATA consists of a sequence of characters with the exception +++of '#' and '$' (see 'X' packet for additional exceptions). +++ +++ Fields within the packet should be separated using ',' ';' or ':'. +++Except where otherwise noted all numbers are represented in HEX with +++leading zeros suppressed. +++ +++ Implementors should note that prior to GDB 5.0, the character ':' +++could not appear as the third character in a packet (as it would +++potentially conflict with the SEQUENCE-ID). +++ +++ Binary data in most packets is encoded either as two hexadecimal +++digits per byte of binary data. This allowed the traditional remote +++protocol to work over connections which were only seven-bit clean. Some +++packets designed more recently assume an eight-bit clean connection, and +++use a more efficient encoding to send and receive binary data. +++ +++ The binary data representation uses '7d' (ASCII '}') as an escape +++character. Any escaped byte is transmitted as the escape character +++followed by the original character XORed with '0x20'. For example, the +++byte '0x7d' would be transmitted as the two bytes '0x7d 0x5d'. The +++bytes '0x23' (ASCII '#'), '0x24' (ASCII '$'), and '0x7d' (ASCII '}') +++must always be escaped. Responses sent by the stub must also escape +++'0x2a' (ASCII '*'), so that it is not interpreted as the start of a +++run-length encoded sequence (described next). +++ +++ Response DATA can be run-length encoded to save space. Run-length +++encoding replaces runs of identical characters with one instance of the +++repeated character, followed by a '*' and a repeat count. The repeat +++count is itself sent encoded, to avoid binary characters in DATA: a +++value of N is sent as 'N+29'. For a repeat count greater or equal to 3, +++this produces a printable ASCII character, e.g. a space (ASCII code 32) +++for a repeat count of 3. (This is because run-length encoding starts to +++win for counts 3 or more.) Thus, for example, '0* ' is a run-length +++encoding of "0000": the space character after '*' means repeat the +++leading '0' '32 - 29 = 3' more times. +++ +++ The printable characters '#' and '$' or with a numeric value greater +++than 126 must not be used. Runs of six repeats ('#') or seven repeats +++('$') can be expanded using a repeat count of only five ('"'). For +++example, '00000000' can be encoded as '0*"00'. +++ +++ The error response returned for some packets includes a two character +++error number. That number is not well defined. +++ +++ For any COMMAND not supported by the stub, an empty response ('$#00') +++should be returned. That way it is possible to extend the protocol. A +++newer GDB can tell if a packet is supported based on that response. +++ +++ At a minimum, a stub is required to support the '?' command to tell +++GDB the reason for halting, 'g' and 'G' commands for register access, +++and the 'm' and 'M' commands for memory access. Stubs that only control +++single-threaded targets can implement run control with the 'c' +++(continue) command, and if the target architecture supports +++hardware-assisted single-stepping, the 's' (step) command. Stubs that +++support multi-threading targets should support the 'vCont' command. All +++other commands are optional. +++ +++ +++File: gdb.info, Node: Packets, Next: Stop Reply Packets, Prev: Overview, Up: Remote Protocol +++ +++E.2 Packets +++=========== +++ +++The following table provides a complete list of all currently defined +++COMMANDs and their corresponding response DATA. *Note File-I/O Remote +++Protocol Extension::, for details about the File I/O extension of the +++remote protocol. +++ +++ Each packet's description has a template showing the packet's overall +++syntax, followed by an explanation of the packet's meaning. We include +++spaces in some of the templates for clarity; these are not part of the +++packet's syntax. No GDB packet uses spaces to separate its components. +++For example, a template like 'foo BAR BAZ' describes a packet beginning +++with the three ASCII bytes 'foo', followed by a BAR, followed directly +++by a BAZ. GDB does not transmit a space character between the 'foo' and +++the BAR, or between the BAR and the BAZ. +++ +++ Several packets and replies include a THREAD-ID field to identify a +++thread. Normally these are positive numbers with a target-specific +++interpretation, formatted as big-endian hex strings. A THREAD-ID can +++also be a literal '-1' to indicate all threads, or '0' to pick any +++thread. +++ +++ In addition, the remote protocol supports a multiprocess feature in +++which the THREAD-ID syntax is extended to optionally include both +++process and thread ID fields, as 'pPID.TID'. The PID (process) and TID +++(thread) components each have the format described above: a positive +++number with target-specific interpretation formatted as a big-endian hex +++string, literal '-1' to indicate all processes or threads +++(respectively), or '0' to indicate an arbitrary process or thread. +++Specifying just a process, as 'pPID', is equivalent to 'pPID.-1'. It is +++an error to specify all processes but a specific thread, such as +++'p-1.TID'. Note that the 'p' prefix is _not_ used for those packets and +++replies explicitly documented to include a process ID, rather than a +++THREAD-ID. +++ +++ The multiprocess THREAD-ID syntax extensions are only used if both +++GDB and the stub report support for the 'multiprocess' feature using +++'qSupported'. *Note multiprocess extensions::, for more information. +++ +++ Note that all packet forms beginning with an upper- or lower-case +++letter, other than those described here, are reserved for future use. +++ +++ Here are the packet descriptions. +++ +++'!' +++ Enable extended mode. In extended mode, the remote server is made +++ persistent. The 'R' packet is used to restart the program being +++ debugged. +++ +++ Reply: +++ 'OK' +++ The remote target both supports and has enabled extended mode. +++ +++'?' +++ Indicate the reason the target halted. The reply is the same as +++ for step and continue. This packet has a special interpretation +++ when the target is in non-stop mode; see *note Remote Non-Stop::. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'A ARGLEN,ARGNUM,ARG,...' +++ Initialized 'argv[]' array passed into program. ARGLEN specifies +++ the number of bytes in the hex encoded byte stream ARG. See +++ 'gdbserver' for more details. +++ +++ Reply: +++ 'OK' +++ The arguments were set. +++ 'E NN' +++ An error occurred. +++ +++'b BAUD' +++ (Don't use this packet; its behavior is not well-defined.) Change +++ the serial line speed to BAUD. +++ +++ JTC: _When does the transport layer state change? When it's +++ received, or after the ACK is transmitted. In either case, there +++ are problems if the command or the acknowledgment packet is +++ dropped._ +++ +++ Stan: _If people really wanted to add something like this, and get +++ it working for the first time, they ought to modify ser-unix.c to +++ send some kind of out-of-band message to a specially-setup stub and +++ have the switch happen "in between" packets, so that from remote +++ protocol's point of view, nothing actually happened._ +++ +++'B ADDR,MODE' +++ Set (MODE is 'S') or clear (MODE is 'C') a breakpoint at ADDR. +++ +++ Don't use this packet. Use the 'Z' and 'z' packets instead (*note +++ insert breakpoint or watchpoint packet::). +++ +++'bc' +++ Backward continue. Execute the target system in reverse. No +++ parameter. *Note Reverse Execution::, for more information. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'bs' +++ Backward single step. Execute one instruction in reverse. No +++ parameter. *Note Reverse Execution::, for more information. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'c [ADDR]' +++ Continue at ADDR, which is the address to resume. If ADDR is +++ omitted, resume at current address. +++ +++ This packet is deprecated for multi-threading support. *Note vCont +++ packet::. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'C SIG[;ADDR]' +++ Continue with signal SIG (hex signal number). If ';ADDR' is +++ omitted, resume at same address. +++ +++ This packet is deprecated for multi-threading support. *Note vCont +++ packet::. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'d' +++ Toggle debug flag. +++ +++ Don't use this packet; instead, define a general set packet (*note +++ General Query Packets::). +++ +++'D' +++'D;PID' +++ The first form of the packet is used to detach GDB from the remote +++ system. It is sent to the remote target before GDB disconnects via +++ the 'detach' command. +++ +++ The second form, including a process ID, is used when multiprocess +++ protocol extensions are enabled (*note multiprocess extensions::), +++ to detach only a specific process. The PID is specified as a +++ big-endian hex string. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'F RC,EE,CF;XX' +++ A reply from GDB to an 'F' packet sent by the target. This is part +++ of the File-I/O protocol extension. *Note File-I/O Remote Protocol +++ Extension::, for the specification. +++ +++'g' +++ Read general registers. +++ +++ Reply: +++ 'XX...' +++ Each byte of register data is described by two hex digits. +++ The bytes with the register are transmitted in target byte +++ order. The size of each register and their position within +++ the 'g' packet are determined by the GDB internal gdbarch +++ functions 'DEPRECATED_REGISTER_RAW_SIZE' and +++ 'gdbarch_register_name'. +++ +++ When reading registers from a trace frame (*note Using the +++ Collected Data: Analyze Collected Data.), the stub may also +++ return a string of literal 'x''s in place of the register data +++ digits, to indicate that the corresponding register has not +++ been collected, thus its value is unavailable. For example, +++ for an architecture with 4 registers of 4 bytes each, the +++ following reply indicates to GDB that registers 0 and 2 have +++ not been collected, while registers 1 and 3 have been +++ collected, and both have zero value: +++ +++ -> g +++ <- xxxxxxxx00000000xxxxxxxx00000000 +++ +++ 'E NN' +++ for an error. +++ +++'G XX...' +++ Write general registers. *Note read registers packet::, for a +++ description of the XX... data. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'H OP THREAD-ID' +++ Set thread for subsequent operations ('m', 'M', 'g', 'G', et.al.). +++ Depending on the operation to be performed, OP should be 'c' for +++ step and continue operations (note that this is deprecated, +++ supporting the 'vCont' command is a better option), and 'g' for +++ other operations. The thread designator THREAD-ID has the format +++ and interpretation described in *note thread-id syntax::. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'i [ADDR[,NNN]]' +++ Step the remote target by a single clock cycle. If ',NNN' is +++ present, cycle step NNN cycles. If ADDR is present, cycle step +++ starting at that address. +++ +++'I' +++ Signal, then cycle step. *Note step with signal packet::. *Note +++ cycle step packet::. +++ +++'k' +++ Kill request. +++ +++ The exact effect of this packet is not specified. +++ +++ For a bare-metal target, it may power cycle or reset the target +++ system. For that reason, the 'k' packet has no reply. +++ +++ For a single-process target, it may kill that process if possible. +++ +++ A multiple-process target may choose to kill just one process, or +++ all that are under GDB's control. For more precise control, use +++ the vKill packet (*note vKill packet::). +++ +++ If the target system immediately closes the connection in response +++ to 'k', GDB does not consider the lack of packet acknowledgment to +++ be an error, and assumes the kill was successful. +++ +++ If connected using 'target extended-remote', and the target does +++ not close the connection in response to a kill request, GDB probes +++ the target state as if a new connection was opened (*note ? +++ packet::). +++ +++'m ADDR,LENGTH' +++ Read LENGTH addressable memory units starting at address ADDR +++ (*note addressable memory unit::). Note that ADDR may not be +++ aligned to any particular boundary. +++ +++ The stub need not use any particular size or alignment when +++ gathering data from memory for the response; even if ADDR is +++ word-aligned and LENGTH is a multiple of the word size, the stub is +++ free to use byte accesses, or not. For this reason, this packet +++ may not be suitable for accessing memory-mapped I/O devices. +++ +++ Reply: +++ 'XX...' +++ Memory contents; each byte is transmitted as a two-digit +++ hexadecimal number. The reply may contain fewer addressable +++ memory units than requested if the server was able to read +++ only part of the region of memory. +++ 'E NN' +++ NN is errno +++ +++'M ADDR,LENGTH:XX...' +++ Write LENGTH addressable memory units starting at address ADDR +++ (*note addressable memory unit::). The data is given by XX...; +++ each byte is transmitted as a two-digit hexadecimal number. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error (this includes the case where only part of the +++ data was written). +++ +++'p N' +++ Read the value of register N; N is in hex. *Note read registers +++ packet::, for a description of how the returned register value is +++ encoded. +++ +++ Reply: +++ 'XX...' +++ the register's value +++ 'E NN' +++ for an error +++ '' +++ Indicating an unrecognized QUERY. +++ +++'P N...=R...' +++ Write register N... with value R.... The register number N is in +++ hexadecimal, and R... contains two hex digits for each byte in the +++ register (target byte order). +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'q NAME PARAMS...' +++'Q NAME PARAMS...' +++ General query ('q') and set ('Q'). These packets are described +++ fully in *note General Query Packets::. +++ +++'r' +++ Reset the entire system. +++ +++ Don't use this packet; use the 'R' packet instead. +++ +++'R XX' +++ Restart the program being debugged. The XX, while needed, is +++ ignored. This packet is only available in extended mode (*note +++ extended mode::). +++ +++ The 'R' packet has no reply. +++ +++'s [ADDR]' +++ Single step, resuming at ADDR. If ADDR is omitted, resume at same +++ address. +++ +++ This packet is deprecated for multi-threading support. *Note vCont +++ packet::. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'S SIG[;ADDR]' +++ Step with signal. This is analogous to the 'C' packet, but +++ requests a single-step, rather than a normal resumption of +++ execution. +++ +++ This packet is deprecated for multi-threading support. *Note vCont +++ packet::. +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'t ADDR:PP,MM' +++ Search backwards starting at address ADDR for a match with pattern +++ PP and mask MM, both of which are are 4 byte long. There must be +++ at least 3 digits in ADDR. +++ +++'T THREAD-ID' +++ Find out if the thread THREAD-ID is alive. *Note thread-id +++ syntax::. +++ +++ Reply: +++ 'OK' +++ thread is still alive +++ 'E NN' +++ thread is dead +++ +++'v' +++ Packets starting with 'v' are identified by a multi-letter name, up +++ to the first ';' or '?' (or the end of the packet). +++ +++'vAttach;PID' +++ Attach to a new process with the specified process ID PID. The +++ process ID is a hexadecimal integer identifying the process. In +++ all-stop mode, all threads in the attached process are stopped; in +++ non-stop mode, it may be attached without being stopped if that is +++ supported by the target. +++ +++ This packet is only available in extended mode (*note extended +++ mode::). +++ +++ Reply: +++ 'E NN' +++ for an error +++ 'Any stop packet' +++ for success in all-stop mode (*note Stop Reply Packets::) +++ 'OK' +++ for success in non-stop mode (*note Remote Non-Stop::) +++ +++'vCont[;ACTION[:THREAD-ID]]...' +++ Resume the inferior, specifying different actions for each thread. +++ +++ For each inferior thread, the leftmost action with a matching +++ THREAD-ID is applied. Threads that don't match any action remain +++ in their current state. Thread IDs are specified using the syntax +++ described in *note thread-id syntax::. If multiprocess extensions +++ (*note multiprocess extensions::) are supported, actions can be +++ specified to match all threads in a process by using the 'pPID.-1' +++ form of the THREAD-ID. An action with no THREAD-ID matches all +++ threads. Specifying no actions is an error. +++ +++ Currently supported actions are: +++ +++ 'c' +++ Continue. +++ 'C SIG' +++ Continue with signal SIG. The signal SIG should be two hex +++ digits. +++ 's' +++ Step. +++ 'S SIG' +++ Step with signal SIG. The signal SIG should be two hex +++ digits. +++ 't' +++ Stop. +++ 'r START,END' +++ Step once, and then keep stepping as long as the thread stops +++ at addresses between START (inclusive) and END (exclusive). +++ The remote stub reports a stop reply when either the thread +++ goes out of the range or is stopped due to an unrelated +++ reason, such as hitting a breakpoint. *Note range stepping::. +++ +++ If the range is empty (START == END), then the action becomes +++ equivalent to the 's' action. In other words, single-step +++ once, and report the stop (even if the stepped instruction +++ jumps to START). +++ +++ (A stop reply may be sent at any point even if the PC is still +++ within the stepping range; for example, it is valid to +++ implement this packet in a degenerate way as a single +++ instruction step operation.) +++ +++ The optional argument ADDR normally associated with the 'c', 'C', +++ 's', and 'S' packets is not supported in 'vCont'. +++ +++ The 't' action is only relevant in non-stop mode (*note Remote +++ Non-Stop::) and may be ignored by the stub otherwise. A stop reply +++ should be generated for any affected thread not already stopped. +++ When a thread is stopped by means of a 't' action, the +++ corresponding stop reply should indicate that the thread has +++ stopped with signal '0', regardless of whether the target uses some +++ other signal as an implementation detail. +++ +++ The server must ignore 'c', 'C', 's', 'S', and 'r' actions for +++ threads that are already running. Conversely, the server must +++ ignore 't' actions for threads that are already stopped. +++ +++ _Note:_ In non-stop mode, a thread is considered running until GDB +++ acknowledges an asynchronous stop notification for it with the +++ 'vStopped' packet (*note Remote Non-Stop::). +++ +++ The stub must support 'vCont' if it reports support for +++ multiprocess extensions (*note multiprocess extensions::). +++ +++ Reply: *Note Stop Reply Packets::, for the reply specifications. +++ +++'vCont?' +++ Request a list of actions supported by the 'vCont' packet. +++ +++ Reply: +++ 'vCont[;ACTION...]' +++ The 'vCont' packet is supported. Each ACTION is a supported +++ command in the 'vCont' packet. +++ '' +++ The 'vCont' packet is not supported. +++ +++'vCtrlC' +++ Interrupt remote target as if a control-C was pressed on the remote +++ terminal. This is the equivalent to reacting to the '^C' ('\003', +++ the control-C character) character in all-stop mode while the +++ target is running, except this works in non-stop mode. *Note +++ interrupting remote targets::, for more info on the all-stop +++ variant. +++ +++ Reply: +++ 'E NN' +++ for an error +++ 'OK' +++ for success +++ +++'vFile:OPERATION:PARAMETER...' +++ Perform a file operation on the target system. For details, see +++ *note Host I/O Packets::. +++ +++'vFlashErase:ADDR,LENGTH' +++ Direct the stub to erase LENGTH bytes of flash starting at ADDR. +++ The region may enclose any number of flash blocks, but its start +++ and end must fall on block boundaries, as indicated by the flash +++ block size appearing in the memory map (*note Memory Map Format::). +++ GDB groups flash memory programming operations together, and sends +++ a 'vFlashDone' request after each group; the stub is allowed to +++ delay erase operation until the 'vFlashDone' packet is received. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'vFlashWrite:ADDR:XX...' +++ Direct the stub to write data to flash address ADDR. The data is +++ passed in binary form using the same encoding as for the 'X' packet +++ (*note Binary Data::). The memory ranges specified by +++ 'vFlashWrite' packets preceding a 'vFlashDone' packet must not +++ overlap, and must appear in order of increasing addresses (although +++ 'vFlashErase' packets for higher addresses may already have been +++ received; the ordering is guaranteed only between 'vFlashWrite' +++ packets). If a packet writes to an address that was neither erased +++ by a preceding 'vFlashErase' packet nor by some other +++ target-specific method, the results are unpredictable. +++ +++ Reply: +++ 'OK' +++ for success +++ 'E.memtype' +++ for vFlashWrite addressing non-flash memory +++ 'E NN' +++ for an error +++ +++'vFlashDone' +++ Indicate to the stub that flash programming operation is finished. +++ The stub is permitted to delay or batch the effects of a group of +++ 'vFlashErase' and 'vFlashWrite' packets until a 'vFlashDone' packet +++ is received. The contents of the affected regions of flash memory +++ are unpredictable until the 'vFlashDone' request is completed. +++ +++'vKill;PID' +++ Kill the process with the specified process ID PID, which is a +++ hexadecimal integer identifying the process. This packet is used +++ in preference to 'k' when multiprocess protocol extensions are +++ supported; see *note multiprocess extensions::. +++ +++ Reply: +++ 'E NN' +++ for an error +++ 'OK' +++ for success +++ +++'vMustReplyEmpty' +++ The correct reply to an unknown 'v' packet is to return the empty +++ string, however, some older versions of 'gdbserver' would +++ incorrectly return 'OK' for unknown 'v' packets. +++ +++ The 'vMustReplyEmpty' is used as a feature test to check how +++ 'gdbserver' handles unknown packets, it is important that this +++ packet be handled in the same way as other unknown 'v' packets. If +++ this packet is handled differently to other unknown 'v' packets +++ then it is possible that GDB may run into problems in other areas, +++ specifically around use of 'vFile:setfs:'. +++ +++'vRun;FILENAME[;ARGUMENT]...' +++ Run the program FILENAME, passing it each ARGUMENT on its command +++ line. The file and arguments are hex-encoded strings. If FILENAME +++ is an empty string, the stub may use a default program (e.g. the +++ last program run). The program is created in the stopped state. +++ +++ This packet is only available in extended mode (*note extended +++ mode::). +++ +++ Reply: +++ 'E NN' +++ for an error +++ 'Any stop packet' +++ for success (*note Stop Reply Packets::) +++ +++'vStopped' +++ *Note Notification Packets::. +++ +++'X ADDR,LENGTH:XX...' +++ Write data to memory, where the data is transmitted in binary. +++ Memory is specified by its address ADDR and number of addressable +++ memory units LENGTH (*note addressable memory unit::); 'XX...' is +++ binary data (*note Binary Data::). +++ +++ Reply: +++ 'OK' +++ for success +++ 'E NN' +++ for an error +++ +++'z TYPE,ADDR,KIND' +++'Z TYPE,ADDR,KIND' +++ Insert ('Z') or remove ('z') a TYPE breakpoint or watchpoint +++ starting at address ADDRESS of kind KIND. +++ +++ Each breakpoint and watchpoint packet TYPE is documented +++ separately. +++ +++ _Implementation notes: A remote target shall return an empty string +++ for an unrecognized breakpoint or watchpoint packet TYPE. A remote +++ target shall support either both or neither of a given 'ZTYPE...' +++ and 'zTYPE...' packet pair. To avoid potential problems with +++ duplicate packets, the operations should be implemented in an +++ idempotent way._ +++ +++'z0,ADDR,KIND' +++'Z0,ADDR,KIND[;COND_LIST...][;cmds:PERSIST,CMD_LIST...]' +++ Insert ('Z0') or remove ('z0') a software breakpoint at address +++ ADDR of type KIND. +++ +++ A software breakpoint is implemented by replacing the instruction +++ at ADDR with a software breakpoint or trap instruction. The KIND +++ is target-specific and typically indicates the size of the +++ breakpoint in bytes that should be inserted. E.g., the ARM and +++ MIPS can insert either a 2 or 4 byte breakpoint. Some +++ architectures have additional meanings for KIND (*note +++ Architecture-Specific Protocol Details::); if no +++ architecture-specific value is being used, it should be '0'. KIND +++ is hex-encoded. COND_LIST is an optional list of conditional +++ expressions in bytecode form that should be evaluated on the +++ target's side. These are the conditions that should be taken into +++ consideration when deciding if the breakpoint trigger should be +++ reported back to GDB. +++ +++ See also the 'swbreak' stop reason (*note swbreak stop reason::) +++ for how to best report a software breakpoint event to GDB. +++ +++ The COND_LIST parameter is comprised of a series of expressions, +++ concatenated without separators. Each expression has the following +++ form: +++ +++ 'X LEN,EXPR' +++ LEN is the length of the bytecode expression and EXPR is the +++ actual conditional expression in bytecode form. +++ +++ The optional CMD_LIST parameter introduces commands that may be run +++ on the target, rather than being reported back to GDB. The +++ parameter starts with a numeric flag PERSIST; if the flag is +++ nonzero, then the breakpoint may remain active and the commands +++ continue to be run even when GDB disconnects from the target. +++ Following this flag is a series of expressions concatenated with no +++ separators. Each expression has the following form: +++ +++ 'X LEN,EXPR' +++ LEN is the length of the bytecode expression and EXPR is the +++ actual commands expression in bytecode form. +++ +++ _Implementation note: It is possible for a target to copy or move +++ code that contains software breakpoints (e.g., when implementing +++ overlays). The behavior of this packet, in the presence of such a +++ target, is not defined._ +++ +++ Reply: +++ 'OK' +++ success +++ '' +++ not supported +++ 'E NN' +++ for an error +++ +++'z1,ADDR,KIND' +++'Z1,ADDR,KIND[;COND_LIST...][;cmds:PERSIST,CMD_LIST...]' +++ Insert ('Z1') or remove ('z1') a hardware breakpoint at address +++ ADDR. +++ +++ A hardware breakpoint is implemented using a mechanism that is not +++ dependent on being able to modify the target's memory. The KIND, +++ COND_LIST, and CMD_LIST arguments have the same meaning as in 'Z0' +++ packets. +++ +++ _Implementation note: A hardware breakpoint is not affected by code +++ movement._ +++ +++ Reply: +++ 'OK' +++ success +++ '' +++ not supported +++ 'E NN' +++ for an error +++ +++'z2,ADDR,KIND' +++'Z2,ADDR,KIND' +++ Insert ('Z2') or remove ('z2') a write watchpoint at ADDR. The +++ number of bytes to watch is specified by KIND. +++ +++ Reply: +++ 'OK' +++ success +++ '' +++ not supported +++ 'E NN' +++ for an error +++ +++'z3,ADDR,KIND' +++'Z3,ADDR,KIND' +++ Insert ('Z3') or remove ('z3') a read watchpoint at ADDR. The +++ number of bytes to watch is specified by KIND. +++ +++ Reply: +++ 'OK' +++ success +++ '' +++ not supported +++ 'E NN' +++ for an error +++ +++'z4,ADDR,KIND' +++'Z4,ADDR,KIND' +++ Insert ('Z4') or remove ('z4') an access watchpoint at ADDR. The +++ number of bytes to watch is specified by KIND. +++ +++ Reply: +++ 'OK' +++ success +++ '' +++ not supported +++ 'E NN' +++ for an error +++ +++ +++File: gdb.info, Node: Stop Reply Packets, Next: General Query Packets, Prev: Packets, Up: Remote Protocol +++ +++E.3 Stop Reply Packets +++====================== +++ +++The 'C', 'c', 'S', 's', 'vCont', 'vAttach', 'vRun', 'vStopped', and '?' +++packets can receive any of the below as a reply. Except for '?' and +++'vStopped', that reply is only returned when the target halts. In the +++below the exact meaning of "signal number" is defined by the header +++'include/gdb/signals.h' in the GDB source code. +++ +++ In non-stop mode, the server will simply reply 'OK' to commands such +++as 'vCont'; any stop will be the subject of a future notification. +++*Note Remote Non-Stop::. +++ +++ As in the description of request packets, we include spaces in the +++reply templates for clarity; these are not part of the reply packet's +++syntax. No GDB stop reply packet uses spaces to separate its +++components. +++ +++'S AA' +++ The program received signal number AA (a two-digit hexadecimal +++ number). This is equivalent to a 'T' response with no N:R pairs. +++ +++'T AA N1:R1;N2:R2;...' +++ The program received signal number AA (a two-digit hexadecimal +++ number). This is equivalent to an 'S' response, except that the +++ 'N:R' pairs can carry values of important registers and other +++ information directly in the stop reply packet, reducing round-trip +++ latency. Single-step and breakpoint traps are reported this way. +++ Each 'N:R' pair is interpreted as follows: +++ +++ * If N is a hexadecimal number, it is a register number, and the +++ corresponding R gives that register's value. The data R is a +++ series of bytes in target byte order, with each byte given by +++ a two-digit hex number. +++ +++ * If N is 'thread', then R is the THREAD-ID of the stopped +++ thread, as specified in *note thread-id syntax::. +++ +++ * If N is 'core', then R is the hexadecimal number of the core +++ on which the stop event was detected. +++ +++ * If N is a recognized "stop reason", it describes a more +++ specific event that stopped the target. The currently defined +++ stop reasons are listed below. The AA should be '05', the +++ trap signal. At most one stop reason should be present. +++ +++ * Otherwise, GDB should ignore this 'N:R' pair and go on to the +++ next; this allows us to extend the protocol in the future. +++ +++ The currently defined stop reasons are: +++ +++ 'watch' +++ 'rwatch' +++ 'awatch' +++ The packet indicates a watchpoint hit, and R is the data +++ address, in hex. +++ +++ 'syscall_entry' +++ 'syscall_return' +++ The packet indicates a syscall entry or return, and R is the +++ syscall number, in hex. +++ +++ 'library' +++ The packet indicates that the loaded libraries have changed. +++ GDB should use 'qXfer:libraries:read' to fetch a new list of +++ loaded libraries. The R part is ignored. +++ +++ 'replaylog' +++ The packet indicates that the target cannot continue replaying +++ logged execution events, because it has reached the end (or +++ the beginning when executing backward) of the log. The value +++ of R will be either 'begin' or 'end'. *Note Reverse +++ Execution::, for more information. +++ +++ 'swbreak' +++ The packet indicates a software breakpoint instruction was +++ executed, irrespective of whether it was GDB that planted the +++ breakpoint or the breakpoint is hardcoded in the program. The +++ R part must be left empty. +++ +++ On some architectures, such as x86, at the architecture level, +++ when a breakpoint instruction executes the program counter +++ points at the breakpoint address plus an offset. On such +++ targets, the stub is responsible for adjusting the PC to point +++ back at the breakpoint address. +++ +++ This packet should not be sent by default; older GDB versions +++ did not support it. GDB requests it, by supplying an +++ appropriate 'qSupported' feature (*note qSupported::). The +++ remote stub must also supply the appropriate 'qSupported' +++ feature indicating support. +++ +++ This packet is required for correct non-stop mode operation. +++ +++ 'hwbreak' +++ The packet indicates the target stopped for a hardware +++ breakpoint. The R part must be left empty. +++ +++ The same remarks about 'qSupported' and non-stop mode above +++ apply. +++ +++ 'fork' +++ The packet indicates that 'fork' was called, and R is the +++ thread ID of the new child process. Refer to *note thread-id +++ syntax:: for the format of the THREAD-ID field. This packet +++ is only applicable to targets that support fork events. +++ +++ This packet should not be sent by default; older GDB versions +++ did not support it. GDB requests it, by supplying an +++ appropriate 'qSupported' feature (*note qSupported::). The +++ remote stub must also supply the appropriate 'qSupported' +++ feature indicating support. +++ +++ 'vfork' +++ The packet indicates that 'vfork' was called, and R is the +++ thread ID of the new child process. Refer to *note thread-id +++ syntax:: for the format of the THREAD-ID field. This packet +++ is only applicable to targets that support vfork events. +++ +++ This packet should not be sent by default; older GDB versions +++ did not support it. GDB requests it, by supplying an +++ appropriate 'qSupported' feature (*note qSupported::). The +++ remote stub must also supply the appropriate 'qSupported' +++ feature indicating support. +++ +++ 'vforkdone' +++ The packet indicates that a child process created by a vfork +++ has either called 'exec' or terminated, so that the address +++ spaces of the parent and child process are no longer shared. +++ The R part is ignored. This packet is only applicable to +++ targets that support vforkdone events. +++ +++ This packet should not be sent by default; older GDB versions +++ did not support it. GDB requests it, by supplying an +++ appropriate 'qSupported' feature (*note qSupported::). The +++ remote stub must also supply the appropriate 'qSupported' +++ feature indicating support. +++ +++ 'exec' +++ The packet indicates that 'execve' was called, and R is the +++ absolute pathname of the file that was executed, in hex. This +++ packet is only applicable to targets that support exec events. +++ +++ This packet should not be sent by default; older GDB versions +++ did not support it. GDB requests it, by supplying an +++ appropriate 'qSupported' feature (*note qSupported::). The +++ remote stub must also supply the appropriate 'qSupported' +++ feature indicating support. +++ +++ 'create' +++ The packet indicates that the thread was just created. The +++ new thread is stopped until GDB sets it running with a +++ resumption packet (*note vCont packet::). This packet should +++ not be sent by default; GDB requests it with the *note +++ QThreadEvents:: packet. See also the 'w' (*note thread exit +++ event::) remote reply below. The R part is ignored. +++ +++'W AA' +++'W AA ; process:PID' +++ The process exited, and AA is the exit status. This is only +++ applicable to certain targets. +++ +++ The second form of the response, including the process ID of the +++ exited process, can be used only when GDB has reported support for +++ multiprocess protocol extensions; see *note multiprocess +++ extensions::. Both AA and PID are formatted as big-endian hex +++ strings. +++ +++'X AA' +++'X AA ; process:PID' +++ The process terminated with signal AA. +++ +++ The second form of the response, including the process ID of the +++ terminated process, can be used only when GDB has reported support +++ for multiprocess protocol extensions; see *note multiprocess +++ extensions::. Both AA and PID are formatted as big-endian hex +++ strings. +++ +++'w AA ; TID' +++ +++ The thread exited, and AA is the exit status. This response should +++ not be sent by default; GDB requests it with the *note +++ QThreadEvents:: packet. See also *note thread create event:: +++ above. AA is formatted as a big-endian hex string. +++ +++'N' +++ There are no resumed threads left in the target. In other words, +++ even though the process is alive, the last resumed thread has +++ exited. For example, say the target process has two threads: +++ thread 1 and thread 2. The client leaves thread 1 stopped, and +++ resumes thread 2, which subsequently exits. At this point, even +++ though the process is still alive, and thus no 'W' stop reply is +++ sent, no thread is actually executing either. The 'N' stop reply +++ thus informs the client that it can stop waiting for stop replies. +++ This packet should not be sent by default; older GDB versions did +++ not support it. GDB requests it, by supplying an appropriate +++ 'qSupported' feature (*note qSupported::). The remote stub must +++ also supply the appropriate 'qSupported' feature indicating +++ support. +++ +++'O XX...' +++ 'XX...' is hex encoding of ASCII data, to be written as the +++ program's console output. This can happen at any time while the +++ program is running and the debugger should continue to wait for +++ 'W', 'T', etc. This reply is not permitted in non-stop mode. +++ +++'F CALL-ID,PARAMETER...' +++ CALL-ID is the identifier which says which host system call should +++ be called. This is just the name of the function. Translation +++ into the correct system call is only applicable as it's defined in +++ GDB. *Note File-I/O Remote Protocol Extension::, for a list of +++ implemented system calls. +++ +++ 'PARAMETER...' is a list of parameters as defined for this very +++ system call. +++ +++ The target replies with this packet when it expects GDB to call a +++ host system call on behalf of the target. GDB replies with an +++ appropriate 'F' packet and keeps up waiting for the next reply +++ packet from the target. The latest 'C', 'c', 'S' or 's' action is +++ expected to be continued. *Note File-I/O Remote Protocol +++ Extension::, for more details. +++ ++diff -Nuar gdb-10.2/gdb/gdb.texinfo gdb-10.2/gdb/gdb.texinfo ++--- gdb-10.2/gdb/gdb.texinfo 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/gdb.texinfo 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,46966 @@ +++\input texinfo @c -*-texinfo-*- +++@c Copyright (C) 1988--2020 Free Software Foundation, Inc. +++@c +++@c %**start of header +++@c makeinfo ignores cmds prev to setfilename, so its arg cannot make use +++@c of @set vars. However, you can override filename with makeinfo -o. +++@setfilename gdb.info +++@c +++@c man begin INCLUDE +++@include gdb-cfg.texi +++@c man end +++@c +++@settitle Debugging with @value{GDBN} +++@setchapternewpage odd +++@c %**end of header +++ +++@iftex +++@c @smallbook +++@c @cropmarks +++@end iftex +++ +++@finalout +++@c To avoid file-name clashes between index.html and Index.html, when +++@c the manual is produced on a Posix host and then moved to a +++@c case-insensitive filesystem (e.g., MS-Windows), we separate the +++@c indices into two: Concept Index and all the rest. +++@syncodeindex ky fn +++@syncodeindex tp fn +++ +++@c readline appendices use @vindex, @findex and @ftable, +++@c annotate.texi and gdbmi use @findex. +++@syncodeindex vr fn +++ +++@c !!set GDB manual's edition---not the same as GDB version! +++@c This is updated by GNU Press. +++@set EDITION Tenth +++ +++@c !!set GDB edit command default editor +++@set EDITOR /bin/ex +++ +++@c THIS MANUAL REQUIRES TEXINFO 4.0 OR LATER. +++ +++@c This is a dir.info fragment to support semi-automated addition of +++@c manuals to an info tree. +++@dircategory Software development +++@direntry +++* Gdb: (gdb). The GNU debugger. +++* gdbserver: (gdb) Server. The GNU debugging server. +++@end direntry +++ +++@copying +++@c man begin COPYRIGHT +++Copyright @copyright{} 1988-2020 Free Software Foundation, Inc. +++ +++Permission is granted to copy, distribute and/or modify this document +++under the terms of the GNU Free Documentation License, Version 1.3 or +++any later version published by the Free Software Foundation; with the +++Invariant Sections being ``Free Software'' and ``Free Software Needs +++Free Documentation'', with the Front-Cover Texts being ``A GNU Manual,'' +++and with the Back-Cover Texts as in (a) below. +++ +++(a) The FSF's Back-Cover Text is: ``You are free to copy and modify +++this GNU Manual. Buying copies from GNU Press supports the FSF in +++developing GNU and promoting software freedom.'' +++@c man end +++@end copying +++ +++@ifnottex +++This file documents the @sc{gnu} debugger @value{GDBN}. +++ +++This is the @value{EDITION} Edition, of @cite{Debugging with +++@value{GDBN}: the @sc{gnu} Source-Level Debugger} for @value{GDBN} +++@ifset VERSION_PACKAGE +++@value{VERSION_PACKAGE} +++@end ifset +++Version @value{GDBVN}. +++ +++@insertcopying +++@end ifnottex +++ +++@titlepage +++@title Debugging with @value{GDBN} +++@subtitle The @sc{gnu} Source-Level Debugger +++@sp 1 +++@subtitle @value{EDITION} Edition, for @value{GDBN} version @value{GDBVN} +++@ifset VERSION_PACKAGE +++@sp 1 +++@subtitle @value{VERSION_PACKAGE} +++@end ifset +++@author Richard Stallman, Roland Pesch, Stan Shebs, et al. +++@page +++@tex +++{\parskip=0pt +++\hfill (Send bugs and comments on @value{GDBN} to @value{BUGURL}.)\par +++\hfill {\it Debugging with @value{GDBN}}\par +++\hfill \TeX{}info \texinfoversion\par +++} +++@end tex +++ +++@vskip 0pt plus 1filll +++Published by the Free Software Foundation @* +++51 Franklin Street, Fifth Floor, +++Boston, MA 02110-1301, USA@* +++ISBN 978-0-9831592-3-0 @* +++ +++@insertcopying +++@end titlepage +++@page +++ +++@ifnottex +++@node Top, Summary +++ +++@top Debugging with @value{GDBN} +++ +++This file describes @value{GDBN}, the @sc{gnu} symbolic debugger. +++ +++This is the @value{EDITION} Edition, for @value{GDBN} +++@ifset VERSION_PACKAGE +++@value{VERSION_PACKAGE} +++@end ifset +++Version @value{GDBVN}. +++ +++Copyright (C) 1988-2020 Free Software Foundation, Inc. +++ +++This edition of the GDB manual is dedicated to the memory of Fred +++Fish. Fred was a long-standing contributor to GDB and to Free +++software in general. We will miss him. +++ +++@menu +++* Summary:: Summary of @value{GDBN} +++* Sample Session:: A sample @value{GDBN} session +++ +++* Invocation:: Getting in and out of @value{GDBN} +++* Commands:: @value{GDBN} commands +++* Running:: Running programs under @value{GDBN} +++* Stopping:: Stopping and continuing +++* Reverse Execution:: Running programs backward +++* Process Record and Replay:: Recording inferior's execution and replaying it +++* Stack:: Examining the stack +++* Source:: Examining source files +++* Data:: Examining data +++* Optimized Code:: Debugging optimized code +++* Macros:: Preprocessor Macros +++* Tracepoints:: Debugging remote targets non-intrusively +++* Overlays:: Debugging programs that use overlays +++ +++* Languages:: Using @value{GDBN} with different languages +++ +++* Symbols:: Examining the symbol table +++* Altering:: Altering execution +++* GDB Files:: @value{GDBN} files +++* Targets:: Specifying a debugging target +++* Remote Debugging:: Debugging remote programs +++* Configurations:: Configuration-specific information +++* Controlling GDB:: Controlling @value{GDBN} +++* Extending GDB:: Extending @value{GDBN} +++* Interpreters:: Command Interpreters +++* TUI:: @value{GDBN} Text User Interface +++* Emacs:: Using @value{GDBN} under @sc{gnu} Emacs +++* GDB/MI:: @value{GDBN}'s Machine Interface. +++* Annotations:: @value{GDBN}'s annotation interface. +++* JIT Interface:: Using the JIT debugging interface. +++* In-Process Agent:: In-Process Agent +++ +++* GDB Bugs:: Reporting bugs in @value{GDBN} +++ +++@ifset SYSTEM_READLINE +++* Command Line Editing: (rluserman). Command Line Editing +++* Using History Interactively: (history). Using History Interactively +++@end ifset +++@ifclear SYSTEM_READLINE +++* Command Line Editing:: Command Line Editing +++* Using History Interactively:: Using History Interactively +++@end ifclear +++* In Memoriam:: In Memoriam +++* Formatting Documentation:: How to format and print @value{GDBN} documentation +++* Installing GDB:: Installing GDB +++* Maintenance Commands:: Maintenance Commands +++* Remote Protocol:: GDB Remote Serial Protocol +++* Agent Expressions:: The GDB Agent Expression Mechanism +++* Target Descriptions:: How targets can describe themselves to +++ @value{GDBN} +++* Operating System Information:: Getting additional information from +++ the operating system +++* Trace File Format:: GDB trace file format +++* Index Section Format:: .gdb_index section format +++* Man Pages:: Manual pages +++* Copying:: GNU General Public License says +++ how you can copy and share GDB +++* GNU Free Documentation License:: The license for this documentation +++* Concept Index:: Index of @value{GDBN} concepts +++* Command and Variable Index:: Index of @value{GDBN} commands, variables, +++ functions, and Python data types +++@end menu +++ +++@end ifnottex +++ +++@contents +++ +++@node Summary +++@unnumbered Summary of @value{GDBN} +++ +++The purpose of a debugger such as @value{GDBN} is to allow you to see what is +++going on ``inside'' another program while it executes---or what another +++program was doing at the moment it crashed. +++ +++@value{GDBN} can do four main kinds of things (plus other things in support of +++these) to help you catch bugs in the act: +++ +++@itemize @bullet +++@item +++Start your program, specifying anything that might affect its behavior. +++ +++@item +++Make your program stop on specified conditions. +++ +++@item +++Examine what has happened, when your program has stopped. +++ +++@item +++Change things in your program, so you can experiment with correcting the +++effects of one bug and go on to learn about another. +++@end itemize +++ +++You can use @value{GDBN} to debug programs written in C and C@t{++}. +++For more information, see @ref{Supported Languages,,Supported Languages}. +++For more information, see @ref{C,,C and C++}. +++ +++Support for D is partial. For information on D, see +++@ref{D,,D}. +++ +++@cindex Modula-2 +++Support for Modula-2 is partial. For information on Modula-2, see +++@ref{Modula-2,,Modula-2}. +++ +++Support for OpenCL C is partial. For information on OpenCL C, see +++@ref{OpenCL C,,OpenCL C}. +++ +++@cindex Pascal +++Debugging Pascal programs which use sets, subranges, file variables, or +++nested functions does not currently work. @value{GDBN} does not support +++entering expressions, printing values, or similar features using Pascal +++syntax. +++ +++@cindex Fortran +++@value{GDBN} can be used to debug programs written in Fortran, although +++it may be necessary to refer to some variables with a trailing +++underscore. +++ +++@value{GDBN} can be used to debug programs written in Objective-C, +++using either the Apple/NeXT or the GNU Objective-C runtime. +++ +++@menu +++* Free Software:: Freely redistributable software +++* Free Documentation:: Free Software Needs Free Documentation +++* Contributors:: Contributors to GDB +++@end menu +++ +++@node Free Software +++@unnumberedsec Free Software +++ +++@value{GDBN} is @dfn{free software}, protected by the @sc{gnu} +++General Public License +++(GPL). The GPL gives you the freedom to copy or adapt a licensed +++program---but every person getting a copy also gets with it the +++freedom to modify that copy (which means that they must get access to +++the source code), and the freedom to distribute further copies. +++Typical software companies use copyrights to limit your freedoms; the +++Free Software Foundation uses the GPL to preserve these freedoms. +++ +++Fundamentally, the General Public License is a license which says that +++you have these freedoms and that you cannot take these freedoms away +++from anyone else. +++ +++@node Free Documentation +++@unnumberedsec Free Software Needs Free Documentation +++ +++The biggest deficiency in the free software community today is not in +++the software---it is the lack of good free documentation that we can +++include with the free software. Many of our most important +++programs do not come with free reference manuals and free introductory +++texts. Documentation is an essential part of any software package; +++when an important free software package does not come with a free +++manual and a free tutorial, that is a major gap. We have many such +++gaps today. +++ +++Consider Perl, for instance. The tutorial manuals that people +++normally use are non-free. How did this come about? Because the +++authors of those manuals published them with restrictive terms---no +++copying, no modification, source files not available---which exclude +++them from the free software world. +++ +++That wasn't the first time this sort of thing happened, and it was far +++from the last. Many times we have heard a GNU user eagerly describe a +++manual that he is writing, his intended contribution to the community, +++only to learn that he had ruined everything by signing a publication +++contract to make it non-free. +++ +++Free documentation, like free software, is a matter of freedom, not +++price. The problem with the non-free manual is not that publishers +++charge a price for printed copies---that in itself is fine. (The Free +++Software Foundation sells printed copies of manuals, too.) The +++problem is the restrictions on the use of the manual. Free manuals +++are available in source code form, and give you permission to copy and +++modify. Non-free manuals do not allow this. +++ +++The criteria of freedom for a free manual are roughly the same as for +++free software. Redistribution (including the normal kinds of +++commercial redistribution) must be permitted, so that the manual can +++accompany every copy of the program, both on-line and on paper. +++ +++Permission for modification of the technical content is crucial too. +++When people modify the software, adding or changing features, if they +++are conscientious they will change the manual too---so they can +++provide accurate and clear documentation for the modified program. A +++manual that leaves you no choice but to write a new manual to document +++a changed version of the program is not really available to our +++community. +++ +++Some kinds of limits on the way modification is handled are +++acceptable. For example, requirements to preserve the original +++author's copyright notice, the distribution terms, or the list of +++authors, are ok. It is also no problem to require modified versions +++to include notice that they were modified. Even entire sections that +++may not be deleted or changed are acceptable, as long as they deal +++with nontechnical topics (like this one). These kinds of restrictions +++are acceptable because they don't obstruct the community's normal use +++of the manual. +++ +++However, it must be possible to modify all the @emph{technical} +++content of the manual, and then distribute the result in all the usual +++media, through all the usual channels. Otherwise, the restrictions +++obstruct the use of the manual, it is not free, and we need another +++manual to replace it. +++ +++Please spread the word about this issue. Our community continues to +++lose manuals to proprietary publishing. If we spread the word that +++free software needs free reference manuals and free tutorials, perhaps +++the next person who wants to contribute by writing documentation will +++realize, before it is too late, that only free manuals contribute to +++the free software community. +++ +++If you are writing documentation, please insist on publishing it under +++the GNU Free Documentation License or another free documentation +++license. Remember that this decision requires your approval---you +++don't have to let the publisher decide. Some commercial publishers +++will use a free license if you insist, but they will not propose the +++option; it is up to you to raise the issue and say firmly that this is +++what you want. If the publisher you are dealing with refuses, please +++try other publishers. If you're not sure whether a proposed license +++is free, write to @email{licensing@@gnu.org}. +++ +++You can encourage commercial publishers to sell more free, copylefted +++manuals and tutorials by buying them, and particularly by buying +++copies from the publishers that paid for their writing or for major +++improvements. Meanwhile, try to avoid buying non-free documentation +++at all. Check the distribution terms of a manual before you buy it, +++and insist that whoever seeks your business must respect your freedom. +++Check the history of the book, and try to reward the publishers that +++have paid or pay the authors to work on it. +++ +++The Free Software Foundation maintains a list of free documentation +++published by other publishers, at +++@url{http://www.fsf.org/doc/other-free-books.html}. +++ +++@node Contributors +++@unnumberedsec Contributors to @value{GDBN} +++ +++Richard Stallman was the original author of @value{GDBN}, and of many +++other @sc{gnu} programs. Many others have contributed to its +++development. This section attempts to credit major contributors. One +++of the virtues of free software is that everyone is free to contribute +++to it; with regret, we cannot actually acknowledge everyone here. The +++file @file{ChangeLog} in the @value{GDBN} distribution approximates a +++blow-by-blow account. +++ +++Changes much prior to version 2.0 are lost in the mists of time. +++ +++@quotation +++@emph{Plea:} Additions to this section are particularly welcome. If you +++or your friends (or enemies, to be evenhanded) have been unfairly +++omitted from this list, we would like to add your names! +++@end quotation +++ +++So that they may not regard their many labors as thankless, we +++particularly thank those who shepherded @value{GDBN} through major +++releases: +++Andrew Cagney (releases 6.3, 6.2, 6.1, 6.0, 5.3, 5.2, 5.1 and 5.0); +++Jim Blandy (release 4.18); +++Jason Molenda (release 4.17); +++Stan Shebs (release 4.14); +++Fred Fish (releases 4.16, 4.15, 4.13, 4.12, 4.11, 4.10, and 4.9); +++Stu Grossman and John Gilmore (releases 4.8, 4.7, 4.6, 4.5, and 4.4); +++John Gilmore (releases 4.3, 4.2, 4.1, 4.0, and 3.9); +++Jim Kingdon (releases 3.5, 3.4, and 3.3); +++and Randy Smith (releases 3.2, 3.1, and 3.0). +++ +++Richard Stallman, assisted at various times by Peter TerMaat, Chris +++Hanson, and Richard Mlynarik, handled releases through 2.8. +++ +++Michael Tiemann is the author of most of the @sc{gnu} C@t{++} support +++in @value{GDBN}, with significant additional contributions from Per +++Bothner and Daniel Berlin. James Clark wrote the @sc{gnu} C@t{++} +++demangler. Early work on C@t{++} was by Peter TerMaat (who also did +++much general update work leading to release 3.0). +++ +++@value{GDBN} uses the BFD subroutine library to examine multiple +++object-file formats; BFD was a joint project of David V. +++Henkel-Wallace, Rich Pixley, Steve Chamberlain, and John Gilmore. +++ +++David Johnson wrote the original COFF support; Pace Willison did +++the original support for encapsulated COFF. +++ +++Brent Benson of Harris Computer Systems contributed DWARF 2 support. +++ +++Adam de Boor and Bradley Davis contributed the ISI Optimum V support. +++Per Bothner, Noboyuki Hikichi, and Alessandro Forin contributed MIPS +++support. +++Jean-Daniel Fekete contributed Sun 386i support. +++Chris Hanson improved the HP9000 support. +++Noboyuki Hikichi and Tomoyuki Hasei contributed Sony/News OS 3 support. +++David Johnson contributed Encore Umax support. +++Jyrki Kuoppala contributed Altos 3068 support. +++Jeff Law contributed HP PA and SOM support. +++Keith Packard contributed NS32K support. +++Doug Rabson contributed Acorn Risc Machine support. +++Bob Rusk contributed Harris Nighthawk CX-UX support. +++Chris Smith contributed Convex support (and Fortran debugging). +++Jonathan Stone contributed Pyramid support. +++Michael Tiemann contributed SPARC support. +++Tim Tucker contributed support for the Gould NP1 and Gould Powernode. +++Pace Willison contributed Intel 386 support. +++Jay Vosburgh contributed Symmetry support. +++Marko Mlinar contributed OpenRISC 1000 support. +++ +++Andreas Schwab contributed M68K @sc{gnu}/Linux support. +++ +++Rich Schaefer and Peter Schauer helped with support of SunOS shared +++libraries. +++ +++Jay Fenlason and Roland McGrath ensured that @value{GDBN} and GAS agree +++about several machine instruction sets. +++ +++Patrick Duval, Ted Goldstein, Vikram Koka and Glenn Engel helped develop +++remote debugging. Intel Corporation, Wind River Systems, AMD, and ARM +++contributed remote debugging modules for the i960, VxWorks, A29K UDI, +++and RDI targets, respectively. +++ +++Brian Fox is the author of the readline libraries providing +++command-line editing and command history. +++ +++Andrew Beers of SUNY Buffalo wrote the language-switching code, the +++Modula-2 support, and contributed the Languages chapter of this manual. +++ +++Fred Fish wrote most of the support for Unix System Vr4. +++He also enhanced the command-completion support to cover C@t{++} overloaded +++symbols. +++ +++Hitachi America (now Renesas America), Ltd. sponsored the support for +++H8/300, H8/500, and Super-H processors. +++ +++NEC sponsored the support for the v850, Vr4xxx, and Vr5xxx processors. +++ +++Mitsubishi (now Renesas) sponsored the support for D10V, D30V, and M32R/D +++processors. +++ +++Toshiba sponsored the support for the TX39 Mips processor. +++ +++Matsushita sponsored the support for the MN10200 and MN10300 processors. +++ +++Fujitsu sponsored the support for SPARClite and FR30 processors. +++ +++Kung Hsu, Jeff Law, and Rick Sladkey added support for hardware +++watchpoints. +++ +++Michael Snyder added support for tracepoints. +++ +++Stu Grossman wrote gdbserver. +++ +++Jim Kingdon, Peter Schauer, Ian Taylor, and Stu Grossman made +++nearly innumerable bug fixes and cleanups throughout @value{GDBN}. +++ +++The following people at the Hewlett-Packard Company contributed +++support for the PA-RISC 2.0 architecture, HP-UX 10.20, 10.30, and 11.0 +++(narrow mode), HP's implementation of kernel threads, HP's aC@t{++} +++compiler, and the Text User Interface (nee Terminal User Interface): +++Ben Krepp, Richard Title, John Bishop, Susan Macchia, Kathy Mann, +++Satish Pai, India Paul, Steve Rehrauer, and Elena Zannoni. Kim Haase +++provided HP-specific information in this manual. +++ +++DJ Delorie ported @value{GDBN} to MS-DOS, for the DJGPP project. +++Robert Hoehne made significant contributions to the DJGPP port. +++ +++Cygnus Solutions has sponsored @value{GDBN} maintenance and much of its +++development since 1991. Cygnus engineers who have worked on @value{GDBN} +++fulltime include Mark Alexander, Jim Blandy, Per Bothner, Kevin +++Buettner, Edith Epstein, Chris Faylor, Fred Fish, Martin Hunt, Jim +++Ingham, John Gilmore, Stu Grossman, Kung Hsu, Jim Kingdon, John Metzler, +++Fernando Nasser, Geoffrey Noer, Dawn Perchik, Rich Pixley, Zdenek +++Radouch, Keith Seitz, Stan Shebs, David Taylor, and Elena Zannoni. In +++addition, Dave Brolley, Ian Carmichael, Steve Chamberlain, Nick Clifton, +++JT Conklin, Stan Cox, DJ Delorie, Ulrich Drepper, Frank Eigler, Doug +++Evans, Sean Fagan, David Henkel-Wallace, Richard Henderson, Jeff +++Holcomb, Jeff Law, Jim Lemke, Tom Lord, Bob Manson, Michael Meissner, +++Jason Merrill, Catherine Moore, Drew Moseley, Ken Raeburn, Gavin +++Romig-Koch, Rob Savoye, Jamie Smith, Mike Stump, Ian Taylor, Angela +++Thomas, Michael Tiemann, Tom Tromey, Ron Unrau, Jim Wilson, and David +++Zuhn have made contributions both large and small. +++ +++Andrew Cagney, Fernando Nasser, and Elena Zannoni, while working for +++Cygnus Solutions, implemented the original @sc{gdb/mi} interface. +++ +++Jim Blandy added support for preprocessor macros, while working for Red +++Hat. +++ +++Andrew Cagney designed @value{GDBN}'s architecture vector. Many +++people including Andrew Cagney, Stephane Carrez, Randolph Chung, Nick +++Duffek, Richard Henderson, Mark Kettenis, Grace Sainsbury, Kei +++Sakamoto, Yoshinori Sato, Michael Snyder, Andreas Schwab, Jason +++Thorpe, Corinna Vinschen, Ulrich Weigand, and Elena Zannoni, helped +++with the migration of old architectures to this new framework. +++ +++Andrew Cagney completely re-designed and re-implemented @value{GDBN}'s +++unwinder framework, this consisting of a fresh new design featuring +++frame IDs, independent frame sniffers, and the sentinel frame. Mark +++Kettenis implemented the @sc{dwarf 2} unwinder, Jeff Johnston the +++libunwind unwinder, and Andrew Cagney the dummy, sentinel, tramp, and +++trad unwinders. The architecture-specific changes, each involving a +++complete rewrite of the architecture's frame code, were carried out by +++Jim Blandy, Joel Brobecker, Kevin Buettner, Andrew Cagney, Stephane +++Carrez, Randolph Chung, Orjan Friberg, Richard Henderson, Daniel +++Jacobowitz, Jeff Johnston, Mark Kettenis, Theodore A. Roth, Kei +++Sakamoto, Yoshinori Sato, Michael Snyder, Corinna Vinschen, and Ulrich +++Weigand. +++ +++Christian Zankel, Ross Morley, Bob Wilson, and Maxim Grigoriev from +++Tensilica, Inc.@: contributed support for Xtensa processors. Others +++who have worked on the Xtensa port of @value{GDBN} in the past include +++Steve Tjiang, John Newlin, and Scott Foehner. +++ +++Michael Eager and staff of Xilinx, Inc., contributed support for the +++Xilinx MicroBlaze architecture. +++ +++Initial support for the FreeBSD/mips target and native configuration +++was developed by SRI International and the University of Cambridge +++Computer Laboratory under DARPA/AFRL contract FA8750-10-C-0237 +++("CTSRD"), as part of the DARPA CRASH research programme. +++ +++Initial support for the FreeBSD/riscv target and native configuration +++was developed by SRI International and the University of Cambridge +++Computer Laboratory (Department of Computer Science and Technology) +++under DARPA contract HR0011-18-C-0016 ("ECATS"), as part of the DARPA +++SSITH research programme. +++ +++The original port to the OpenRISC 1000 is believed to be due to +++Alessandro Forin and Per Bothner. More recent ports have been the work +++of Jeremy Bennett, Franck Jullien, Stefan Wallentowitz and +++Stafford Horne. +++ +++Weimin Pan, David Faust and Jose E. Marchesi contributed support for +++the Linux kernel BPF virtual architecture. This work was sponsored by +++Oracle. +++ +++@node Sample Session +++@chapter A Sample @value{GDBN} Session +++ +++You can use this manual at your leisure to read all about @value{GDBN}. +++However, a handful of commands are enough to get started using the +++debugger. This chapter illustrates those commands. +++ +++@iftex +++In this sample session, we emphasize user input like this: @b{input}, +++to make it easier to pick out from the surrounding output. +++@end iftex +++ +++@c FIXME: this example may not be appropriate for some configs, where +++@c FIXME...primary interest is in remote use. +++ +++One of the preliminary versions of @sc{gnu} @code{m4} (a generic macro +++processor) exhibits the following bug: sometimes, when we change its +++quote strings from the default, the commands used to capture one macro +++definition within another stop working. In the following short @code{m4} +++session, we define a macro @code{foo} which expands to @code{0000}; we +++then use the @code{m4} built-in @code{defn} to define @code{bar} as the +++same thing. However, when we change the open quote string to +++@code{} and the close quote string to @code{}, the same +++procedure fails to define a new synonym @code{baz}: +++ +++@smallexample +++$ @b{cd gnu/m4} +++$ @b{./m4} +++@b{define(foo,0000)} +++ +++@b{foo} +++0000 +++@b{define(bar,defn(`foo'))} +++ +++@b{bar} +++0000 +++@b{changequote(,)} +++ +++@b{define(baz,defn(foo))} +++@b{baz} +++@b{Ctrl-d} +++m4: End of input: 0: fatal error: EOF in string +++@end smallexample +++ +++@noindent +++Let us use @value{GDBN} to try to see what is going on. +++ +++@smallexample +++$ @b{@value{GDBP} m4} +++@c FIXME: this falsifies the exact text played out, to permit smallbook +++@c FIXME... format to come out better. +++@value{GDBN} is free software and you are welcome to distribute copies +++ of it under certain conditions; type "show copying" to see +++ the conditions. +++There is absolutely no warranty for @value{GDBN}; type "show warranty" +++ for details. +++ +++@value{GDBN} @value{GDBVN}, Copyright 1999 Free Software Foundation, Inc... +++(@value{GDBP}) +++@end smallexample +++ +++@noindent +++@value{GDBN} reads only enough symbol data to know where to find the +++rest when needed; as a result, the first prompt comes up very quickly. +++We now tell @value{GDBN} to use a narrower display width than usual, so +++that examples fit in this manual. +++ +++@smallexample +++(@value{GDBP}) @b{set width 70} +++@end smallexample +++ +++@noindent +++We need to see how the @code{m4} built-in @code{changequote} works. +++Having looked at the source, we know the relevant subroutine is +++@code{m4_changequote}, so we set a breakpoint there with the @value{GDBN} +++@code{break} command. +++ +++@smallexample +++(@value{GDBP}) @b{break m4_changequote} +++Breakpoint 1 at 0x62f4: file builtin.c, line 879. +++@end smallexample +++ +++@noindent +++Using the @code{run} command, we start @code{m4} running under @value{GDBN} +++control; as long as control does not reach the @code{m4_changequote} +++subroutine, the program runs as usual: +++ +++@smallexample +++(@value{GDBP}) @b{run} +++Starting program: /work/Editorial/gdb/gnu/m4/m4 +++@b{define(foo,0000)} +++ +++@b{foo} +++0000 +++@end smallexample +++ +++@noindent +++To trigger the breakpoint, we call @code{changequote}. @value{GDBN} +++suspends execution of @code{m4}, displaying information about the +++context where it stops. +++ +++@smallexample +++@b{changequote(,)} +++ +++Breakpoint 1, m4_changequote (argc=3, argv=0x33c70) +++ at builtin.c:879 +++879 if (bad_argc(TOKEN_DATA_TEXT(argv[0]),argc,1,3)) +++@end smallexample +++ +++@noindent +++Now we use the command @code{n} (@code{next}) to advance execution to +++the next line of the current function. +++ +++@smallexample +++(@value{GDBP}) @b{n} +++882 set_quotes((argc >= 2) ? TOKEN_DATA_TEXT(argv[1])\ +++ : nil, +++@end smallexample +++ +++@noindent +++@code{set_quotes} looks like a promising subroutine. We can go into it +++by using the command @code{s} (@code{step}) instead of @code{next}. +++@code{step} goes to the next line to be executed in @emph{any} +++subroutine, so it steps into @code{set_quotes}. +++ +++@smallexample +++(@value{GDBP}) @b{s} +++set_quotes (lq=0x34c78 "", rq=0x34c88 "") +++ at input.c:530 +++530 if (lquote != def_lquote) +++@end smallexample +++ +++@noindent +++The display that shows the subroutine where @code{m4} is now +++suspended (and its arguments) is called a stack frame display. It +++shows a summary of the stack. We can use the @code{backtrace} +++command (which can also be spelled @code{bt}), to see where we are +++in the stack as a whole: the @code{backtrace} command displays a +++stack frame for each active subroutine. +++ +++@smallexample +++(@value{GDBP}) @b{bt} +++#0 set_quotes (lq=0x34c78 "", rq=0x34c88 "") +++ at input.c:530 +++#1 0x6344 in m4_changequote (argc=3, argv=0x33c70) +++ at builtin.c:882 +++#2 0x8174 in expand_macro (sym=0x33320) at macro.c:242 +++#3 0x7a88 in expand_token (obs=0x0, t=209696, td=0xf7fffa30) +++ at macro.c:71 +++#4 0x79dc in expand_input () at macro.c:40 +++#5 0x2930 in main (argc=0, argv=0xf7fffb20) at m4.c:195 +++@end smallexample +++ +++@noindent +++We step through a few more lines to see what happens. The first two +++times, we can use @samp{s}; the next two times we use @code{n} to avoid +++falling into the @code{xstrdup} subroutine. +++ +++@smallexample +++(@value{GDBP}) @b{s} +++0x3b5c 532 if (rquote != def_rquote) +++(@value{GDBP}) @b{s} +++0x3b80 535 lquote = (lq == nil || *lq == '\0') ? \ +++def_lquote : xstrdup(lq); +++(@value{GDBP}) @b{n} +++536 rquote = (rq == nil || *rq == '\0') ? def_rquote\ +++ : xstrdup(rq); +++(@value{GDBP}) @b{n} +++538 len_lquote = strlen(rquote); +++@end smallexample +++ +++@noindent +++The last line displayed looks a little odd; we can examine the variables +++@code{lquote} and @code{rquote} to see if they are in fact the new left +++and right quotes we specified. We use the command @code{p} +++(@code{print}) to see their values. +++ +++@smallexample +++(@value{GDBP}) @b{p lquote} +++$1 = 0x35d40 "" +++(@value{GDBP}) @b{p rquote} +++$2 = 0x35d50 "" +++@end smallexample +++ +++@noindent +++@code{lquote} and @code{rquote} are indeed the new left and right quotes. +++To look at some context, we can display ten lines of source +++surrounding the current line with the @code{l} (@code{list}) command. +++ +++@smallexample +++(@value{GDBP}) @b{l} +++533 xfree(rquote); +++534 +++535 lquote = (lq == nil || *lq == '\0') ? def_lquote\ +++ : xstrdup (lq); +++536 rquote = (rq == nil || *rq == '\0') ? def_rquote\ +++ : xstrdup (rq); +++537 +++538 len_lquote = strlen(rquote); +++539 len_rquote = strlen(lquote); +++540 @} +++541 +++542 void +++@end smallexample +++ +++@noindent +++Let us step past the two lines that set @code{len_lquote} and +++@code{len_rquote}, and then examine the values of those variables. +++ +++@smallexample +++(@value{GDBP}) @b{n} +++539 len_rquote = strlen(lquote); +++(@value{GDBP}) @b{n} +++540 @} +++(@value{GDBP}) @b{p len_lquote} +++$3 = 9 +++(@value{GDBP}) @b{p len_rquote} +++$4 = 7 +++@end smallexample +++ +++@noindent +++That certainly looks wrong, assuming @code{len_lquote} and +++@code{len_rquote} are meant to be the lengths of @code{lquote} and +++@code{rquote} respectively. We can set them to better values using +++the @code{p} command, since it can print the value of +++any expression---and that expression can include subroutine calls and +++assignments. +++ +++@smallexample +++(@value{GDBP}) @b{p len_lquote=strlen(lquote)} +++$5 = 7 +++(@value{GDBP}) @b{p len_rquote=strlen(rquote)} +++$6 = 9 +++@end smallexample +++ +++@noindent +++Is that enough to fix the problem of using the new quotes with the +++@code{m4} built-in @code{defn}? We can allow @code{m4} to continue +++executing with the @code{c} (@code{continue}) command, and then try the +++example that caused trouble initially: +++ +++@smallexample +++(@value{GDBP}) @b{c} +++Continuing. +++ +++@b{define(baz,defn(foo))} +++ +++baz +++0000 +++@end smallexample +++ +++@noindent +++Success! The new quotes now work just as well as the default ones. The +++problem seems to have been just the two typos defining the wrong +++lengths. We allow @code{m4} exit by giving it an EOF as input: +++ +++@smallexample +++@b{Ctrl-d} +++Program exited normally. +++@end smallexample +++ +++@noindent +++The message @samp{Program exited normally.} is from @value{GDBN}; it +++indicates @code{m4} has finished executing. We can end our @value{GDBN} +++session with the @value{GDBN} @code{quit} command. +++ +++@smallexample +++(@value{GDBP}) @b{quit} +++@end smallexample +++ +++@node Invocation +++@chapter Getting In and Out of @value{GDBN} +++ +++This chapter discusses how to start @value{GDBN}, and how to get out of it. +++The essentials are: +++@itemize @bullet +++@item +++type @samp{@value{GDBP}} to start @value{GDBN}. +++@item +++type @kbd{quit} or @kbd{Ctrl-d} to exit. +++@end itemize +++ +++@menu +++* Invoking GDB:: How to start @value{GDBN} +++* Quitting GDB:: How to quit @value{GDBN} +++* Shell Commands:: How to use shell commands inside @value{GDBN} +++* Logging Output:: How to log @value{GDBN}'s output to a file +++@end menu +++ +++@node Invoking GDB +++@section Invoking @value{GDBN} +++ +++Invoke @value{GDBN} by running the program @code{@value{GDBP}}. Once started, +++@value{GDBN} reads commands from the terminal until you tell it to exit. +++ +++You can also run @code{@value{GDBP}} with a variety of arguments and options, +++to specify more of your debugging environment at the outset. +++ +++The command-line options described here are designed +++to cover a variety of situations; in some environments, some of these +++options may effectively be unavailable. +++ +++The most usual way to start @value{GDBN} is with one argument, +++specifying an executable program: +++ +++@smallexample +++@value{GDBP} @var{program} +++@end smallexample +++ +++@noindent +++You can also start with both an executable program and a core file +++specified: +++ +++@smallexample +++@value{GDBP} @var{program} @var{core} +++@end smallexample +++ +++You can, instead, specify a process ID as a second argument or use option +++@code{-p}, if you want to debug a running process: +++ +++@smallexample +++@value{GDBP} @var{program} 1234 +++@value{GDBP} -p 1234 +++@end smallexample +++ +++@noindent +++would attach @value{GDBN} to process @code{1234}. With option @option{-p} you +++can omit the @var{program} filename. +++ +++Taking advantage of the second command-line argument requires a fairly +++complete operating system; when you use @value{GDBN} as a remote +++debugger attached to a bare board, there may not be any notion of +++``process'', and there is often no way to get a core dump. @value{GDBN} +++will warn you if it is unable to attach or to read core dumps. +++ +++You can optionally have @code{@value{GDBP}} pass any arguments after the +++executable file to the inferior using @code{--args}. This option stops +++option processing. +++@smallexample +++@value{GDBP} --args gcc -O2 -c foo.c +++@end smallexample +++This will cause @code{@value{GDBP}} to debug @code{gcc}, and to set +++@code{gcc}'s command-line arguments (@pxref{Arguments}) to @samp{-O2 -c foo.c}. +++ +++You can run @code{@value{GDBP}} without printing the front material, which describes +++@value{GDBN}'s non-warranty, by specifying @code{--silent} +++(or @code{-q}/@code{--quiet}): +++ +++@smallexample +++@value{GDBP} --silent +++@end smallexample +++ +++@noindent +++You can further control how @value{GDBN} starts up by using command-line +++options. @value{GDBN} itself can remind you of the options available. +++ +++@noindent +++Type +++ +++@smallexample +++@value{GDBP} -help +++@end smallexample +++ +++@noindent +++to display all available options and briefly describe their use +++(@samp{@value{GDBP} -h} is a shorter equivalent). +++ +++All options and command line arguments you give are processed +++in sequential order. The order makes a difference when the +++@samp{-x} option is used. +++ +++ +++@menu +++* File Options:: Choosing files +++* Mode Options:: Choosing modes +++* Startup:: What @value{GDBN} does during startup +++@end menu +++ +++@node File Options +++@subsection Choosing Files +++ +++When @value{GDBN} starts, it reads any arguments other than options as +++specifying an executable file and core file (or process ID). This is +++the same as if the arguments were specified by the @samp{-se} and +++@samp{-c} (or @samp{-p}) options respectively. (@value{GDBN} reads the +++first argument that does not have an associated option flag as +++equivalent to the @samp{-se} option followed by that argument; and the +++second argument that does not have an associated option flag, if any, as +++equivalent to the @samp{-c}/@samp{-p} option followed by that argument.) +++If the second argument begins with a decimal digit, @value{GDBN} will +++first attempt to attach to it as a process, and if that fails, attempt +++to open it as a corefile. If you have a corefile whose name begins with +++a digit, you can prevent @value{GDBN} from treating it as a pid by +++prefixing it with @file{./}, e.g.@: @file{./12345}. +++ +++If @value{GDBN} has not been configured to included core file support, +++such as for most embedded targets, then it will complain about a second +++argument and ignore it. +++ +++Many options have both long and short forms; both are shown in the +++following list. @value{GDBN} also recognizes the long forms if you truncate +++them, so long as enough of the option is present to be unambiguous. +++(If you prefer, you can flag option arguments with @samp{--} rather +++than @samp{-}, though we illustrate the more usual convention.) +++ +++@c NOTE: the @cindex entries here use double dashes ON PURPOSE. This +++@c way, both those who look for -foo and --foo in the index, will find +++@c it. +++ +++@table @code +++@item -symbols @var{file} +++@itemx -s @var{file} +++@cindex @code{--symbols} +++@cindex @code{-s} +++Read symbol table from file @var{file}. +++ +++@item -exec @var{file} +++@itemx -e @var{file} +++@cindex @code{--exec} +++@cindex @code{-e} +++Use file @var{file} as the executable file to execute when appropriate, +++and for examining pure data in conjunction with a core dump. +++ +++@item -se @var{file} +++@cindex @code{--se} +++Read symbol table from file @var{file} and use it as the executable +++file. +++ +++@item -core @var{file} +++@itemx -c @var{file} +++@cindex @code{--core} +++@cindex @code{-c} +++Use file @var{file} as a core dump to examine. +++ +++@item -pid @var{number} +++@itemx -p @var{number} +++@cindex @code{--pid} +++@cindex @code{-p} +++Connect to process ID @var{number}, as with the @code{attach} command. +++ +++@item -command @var{file} +++@itemx -x @var{file} +++@cindex @code{--command} +++@cindex @code{-x} +++Execute commands from file @var{file}. The contents of this file is +++evaluated exactly as the @code{source} command would. +++@xref{Command Files,, Command files}. +++ +++@item -eval-command @var{command} +++@itemx -ex @var{command} +++@cindex @code{--eval-command} +++@cindex @code{-ex} +++Execute a single @value{GDBN} command. +++ +++This option may be used multiple times to call multiple commands. It may +++also be interleaved with @samp{-command} as required. +++ +++@smallexample +++@value{GDBP} -ex 'target sim' -ex 'load' \ +++ -x setbreakpoints -ex 'run' a.out +++@end smallexample +++ +++@item -init-command @var{file} +++@itemx -ix @var{file} +++@cindex @code{--init-command} +++@cindex @code{-ix} +++Execute commands from file @var{file} before loading the inferior (but +++after loading gdbinit files). +++@xref{Startup}. +++ +++@item -init-eval-command @var{command} +++@itemx -iex @var{command} +++@cindex @code{--init-eval-command} +++@cindex @code{-iex} +++Execute a single @value{GDBN} command before loading the inferior (but +++after loading gdbinit files). +++@xref{Startup}. +++ +++@item -directory @var{directory} +++@itemx -d @var{directory} +++@cindex @code{--directory} +++@cindex @code{-d} +++Add @var{directory} to the path to search for source and script files. +++ +++@item -r +++@itemx -readnow +++@cindex @code{--readnow} +++@cindex @code{-r} +++Read each symbol file's entire symbol table immediately, rather than +++the default, which is to read it incrementally as it is needed. +++This makes startup slower, but makes future operations faster. +++ +++@item --readnever +++@anchor{--readnever} +++@cindex @code{--readnever}, command-line option +++Do not read each symbol file's symbolic debug information. This makes +++startup faster but at the expense of not being able to perform +++symbolic debugging. DWARF unwind information is also not read, +++meaning backtraces may become incomplete or inaccurate. One use of +++this is when a user simply wants to do the following sequence: attach, +++dump core, detach. Loading the debugging information in this case is +++an unnecessary cause of delay. +++@end table +++ +++@node Mode Options +++@subsection Choosing Modes +++ +++You can run @value{GDBN} in various alternative modes---for example, in +++batch mode or quiet mode. +++ +++@table @code +++@anchor{-nx} +++@item -nx +++@itemx -n +++@cindex @code{--nx} +++@cindex @code{-n} +++Do not execute commands found in any initialization file. +++There are three init files, loaded in the following order: +++ +++@table @code +++@item @file{system.gdbinit} +++This is the system-wide init file. +++Its location is specified with the @code{--with-system-gdbinit} +++configure option (@pxref{System-wide configuration}). +++It is loaded first when @value{GDBN} starts, before command line options +++have been processed. +++@item @file{system.gdbinit.d} +++This is the system-wide init directory. +++Its location is specified with the @code{--with-system-gdbinit-dir} +++configure option (@pxref{System-wide configuration}). +++Files in this directory are loaded in alphabetical order immediately after +++system.gdbinit (if enabled) when @value{GDBN} starts, before command line +++options have been processed. Files need to have a recognized scripting +++language extension (@file{.py}/@file{.scm}) or be named with a @file{.gdb} +++extension to be interpreted as regular @value{GDBN} commands. @value{GDBN} +++will not recurse into any subdirectories of this directory. +++@item @file{~/.gdbinit} +++This is the init file in your home directory. +++It is loaded next, after @file{system.gdbinit}, and before +++command options have been processed. +++@item @file{./.gdbinit} +++This is the init file in the current directory. +++It is loaded last, after command line options other than @code{-x} and +++@code{-ex} have been processed. Command line options @code{-x} and +++@code{-ex} are processed last, after @file{./.gdbinit} has been loaded. +++@end table +++ +++For further documentation on startup processing, @xref{Startup}. +++For documentation on how to write command files, +++@xref{Command Files,,Command Files}. +++ +++@anchor{-nh} +++@item -nh +++@cindex @code{--nh} +++Do not execute commands found in @file{~/.gdbinit}, the init file +++in your home directory. +++@xref{Startup}. +++ +++@item -quiet +++@itemx -silent +++@itemx -q +++@cindex @code{--quiet} +++@cindex @code{--silent} +++@cindex @code{-q} +++``Quiet''. Do not print the introductory and copyright messages. These +++messages are also suppressed in batch mode. +++ +++@item -batch +++@cindex @code{--batch} +++Run in batch mode. Exit with status @code{0} after processing all the +++command files specified with @samp{-x} (and all commands from +++initialization files, if not inhibited with @samp{-n}). Exit with +++nonzero status if an error occurs in executing the @value{GDBN} commands +++in the command files. Batch mode also disables pagination, sets unlimited +++terminal width and height @pxref{Screen Size}, and acts as if @kbd{set confirm +++off} were in effect (@pxref{Messages/Warnings}). +++ +++Batch mode may be useful for running @value{GDBN} as a filter, for +++example to download and run a program on another computer; in order to +++make this more useful, the message +++ +++@smallexample +++Program exited normally. +++@end smallexample +++ +++@noindent +++(which is ordinarily issued whenever a program running under +++@value{GDBN} control terminates) is not issued when running in batch +++mode. +++ +++@item -batch-silent +++@cindex @code{--batch-silent} +++Run in batch mode exactly like @samp{-batch}, but totally silently. All +++@value{GDBN} output to @code{stdout} is prevented (@code{stderr} is +++unaffected). This is much quieter than @samp{-silent} and would be useless +++for an interactive session. +++ +++This is particularly useful when using targets that give @samp{Loading section} +++messages, for example. +++ +++Note that targets that give their output via @value{GDBN}, as opposed to +++writing directly to @code{stdout}, will also be made silent. +++ +++@item -return-child-result +++@cindex @code{--return-child-result} +++The return code from @value{GDBN} will be the return code from the child +++process (the process being debugged), with the following exceptions: +++ +++@itemize @bullet +++@item +++@value{GDBN} exits abnormally. E.g., due to an incorrect argument or an +++internal error. In this case the exit code is the same as it would have been +++without @samp{-return-child-result}. +++@item +++The user quits with an explicit value. E.g., @samp{quit 1}. +++@item +++The child process never runs, or is not allowed to terminate, in which case +++the exit code will be -1. +++@end itemize +++ +++This option is useful in conjunction with @samp{-batch} or @samp{-batch-silent}, +++when @value{GDBN} is being used as a remote program loader or simulator +++interface. +++ +++@item -nowindows +++@itemx -nw +++@cindex @code{--nowindows} +++@cindex @code{-nw} +++``No windows''. If @value{GDBN} comes with a graphical user interface +++(GUI) built in, then this option tells @value{GDBN} to only use the command-line +++interface. If no GUI is available, this option has no effect. +++ +++@item -windows +++@itemx -w +++@cindex @code{--windows} +++@cindex @code{-w} +++If @value{GDBN} includes a GUI, then this option requires it to be +++used if possible. +++ +++@item -cd @var{directory} +++@cindex @code{--cd} +++Run @value{GDBN} using @var{directory} as its working directory, +++instead of the current directory. +++ +++@item -data-directory @var{directory} +++@itemx -D @var{directory} +++@cindex @code{--data-directory} +++@cindex @code{-D} +++Run @value{GDBN} using @var{directory} as its data directory. +++The data directory is where @value{GDBN} searches for its +++auxiliary files. @xref{Data Files}. +++ +++@item -fullname +++@itemx -f +++@cindex @code{--fullname} +++@cindex @code{-f} +++@sc{gnu} Emacs sets this option when it runs @value{GDBN} as a +++subprocess. It tells @value{GDBN} to output the full file name and line +++number in a standard, recognizable fashion each time a stack frame is +++displayed (which includes each time your program stops). This +++recognizable format looks like two @samp{\032} characters, followed by +++the file name, line number and character position separated by colons, +++and a newline. The Emacs-to-@value{GDBN} interface program uses the two +++@samp{\032} characters as a signal to display the source code for the +++frame. +++ +++@item -annotate @var{level} +++@cindex @code{--annotate} +++This option sets the @dfn{annotation level} inside @value{GDBN}. Its +++effect is identical to using @samp{set annotate @var{level}} +++(@pxref{Annotations}). The annotation @var{level} controls how much +++information @value{GDBN} prints together with its prompt, values of +++expressions, source lines, and other types of output. Level 0 is the +++normal, level 1 is for use when @value{GDBN} is run as a subprocess of +++@sc{gnu} Emacs, level 3 is the maximum annotation suitable for programs +++that control @value{GDBN}, and level 2 has been deprecated. +++ +++The annotation mechanism has largely been superseded by @sc{gdb/mi} +++(@pxref{GDB/MI}). +++ +++@item --args +++@cindex @code{--args} +++Change interpretation of command line so that arguments following the +++executable file are passed as command line arguments to the inferior. +++This option stops option processing. +++ +++@item -baud @var{bps} +++@itemx -b @var{bps} +++@cindex @code{--baud} +++@cindex @code{-b} +++Set the line speed (baud rate or bits per second) of any serial +++interface used by @value{GDBN} for remote debugging. +++ +++@item -l @var{timeout} +++@cindex @code{-l} +++Set the timeout (in seconds) of any communication used by @value{GDBN} +++for remote debugging. +++ +++@item -tty @var{device} +++@itemx -t @var{device} +++@cindex @code{--tty} +++@cindex @code{-t} +++Run using @var{device} for your program's standard input and output. +++@c FIXME: kingdon thinks there is more to -tty. Investigate. +++ +++@c resolve the situation of these eventually +++@item -tui +++@cindex @code{--tui} +++Activate the @dfn{Text User Interface} when starting. The Text User +++Interface manages several text windows on the terminal, showing +++source, assembly, registers and @value{GDBN} command outputs +++(@pxref{TUI, ,@value{GDBN} Text User Interface}). Do not use this +++option if you run @value{GDBN} from Emacs (@pxref{Emacs, , +++Using @value{GDBN} under @sc{gnu} Emacs}). +++ +++@item -interpreter @var{interp} +++@cindex @code{--interpreter} +++Use the interpreter @var{interp} for interface with the controlling +++program or device. This option is meant to be set by programs which +++communicate with @value{GDBN} using it as a back end. +++@xref{Interpreters, , Command Interpreters}. +++ +++@samp{--interpreter=mi} (or @samp{--interpreter=mi3}) causes +++@value{GDBN} to use the @dfn{@sc{gdb/mi} interface} version 3 (@pxref{GDB/MI, , +++The @sc{gdb/mi} Interface}) included since @value{GDBN} version 9.1. @sc{gdb/mi} +++version 2 (@code{mi2}), included in @value{GDBN} 6.0 and version 1 (@code{mi1}), +++included in @value{GDBN} 5.3, are also available. Earlier @sc{gdb/mi} +++interfaces are no longer supported. +++ +++@item -write +++@cindex @code{--write} +++Open the executable and core files for both reading and writing. This +++is equivalent to the @samp{set write on} command inside @value{GDBN} +++(@pxref{Patching}). +++ +++@item -statistics +++@cindex @code{--statistics} +++This option causes @value{GDBN} to print statistics about time and +++memory usage after it completes each command and returns to the prompt. +++ +++@item -version +++@cindex @code{--version} +++This option causes @value{GDBN} to print its version number and +++no-warranty blurb, and exit. +++ +++@item -configuration +++@cindex @code{--configuration} +++This option causes @value{GDBN} to print details about its build-time +++configuration parameters, and then exit. These details can be +++important when reporting @value{GDBN} bugs (@pxref{GDB Bugs}). +++ +++@end table +++ +++@node Startup +++@subsection What @value{GDBN} Does During Startup +++@cindex @value{GDBN} startup +++ +++Here's the description of what @value{GDBN} does during session startup: +++ +++@enumerate +++@item +++Sets up the command interpreter as specified by the command line +++(@pxref{Mode Options, interpreter}). +++ +++@item +++@cindex init file +++Reads the system-wide @dfn{init file} (if @option{--with-system-gdbinit} was +++used when building @value{GDBN}; @pxref{System-wide configuration, +++ ,System-wide configuration and settings}) and the files in the system-wide +++gdbinit directory (if @option{--with-system-gdbinit-dir} was used) and executes +++all the commands in those files. The files need to be named with a @file{.gdb} +++extension to be interpreted as @value{GDBN} commands, or they can be written +++in a supported scripting language with an appropriate file extension. +++ +++@anchor{Home Directory Init File} +++@item +++Reads the init file (if any) in your home directory@footnote{On +++DOS/Windows systems, the home directory is the one pointed to by the +++@code{HOME} environment variable.} and executes all the commands in +++that file. +++ +++@anchor{Option -init-eval-command} +++@item +++Executes commands and command files specified by the @samp{-iex} and +++@samp{-ix} options in their specified order. Usually you should use the +++@samp{-ex} and @samp{-x} options instead, but this way you can apply +++settings before @value{GDBN} init files get executed and before inferior +++gets loaded. +++ +++@item +++Processes command line options and operands. +++ +++@anchor{Init File in the Current Directory during Startup} +++@item +++Reads and executes the commands from init file (if any) in the current +++working directory as long as @samp{set auto-load local-gdbinit} is set to +++@samp{on} (@pxref{Init File in the Current Directory}). +++This is only done if the current directory is +++different from your home directory. Thus, you can have more than one +++init file, one generic in your home directory, and another, specific +++to the program you are debugging, in the directory where you invoke +++@value{GDBN}. +++ +++@item +++If the command line specified a program to debug, or a process to +++attach to, or a core file, @value{GDBN} loads any auto-loaded +++scripts provided for the program or for its loaded shared libraries. +++@xref{Auto-loading}. +++ +++If you wish to disable the auto-loading during startup, +++you must do something like the following: +++ +++@smallexample +++$ gdb -iex "set auto-load python-scripts off" myprogram +++@end smallexample +++ +++Option @samp{-ex} does not work because the auto-loading is then turned +++off too late. +++ +++@item +++Executes commands and command files specified by the @samp{-ex} and +++@samp{-x} options in their specified order. @xref{Command Files}, for +++more details about @value{GDBN} command files. +++ +++@item +++Reads the command history recorded in the @dfn{history file}. +++@xref{Command History}, for more details about the command history and the +++files where @value{GDBN} records it. +++@end enumerate +++ +++Init files use the same syntax as @dfn{command files} (@pxref{Command +++Files}) and are processed by @value{GDBN} in the same way. The init +++file in your home directory can set options (such as @samp{set +++complaints}) that affect subsequent processing of command line options +++and operands. Init files are not executed if you use the @samp{-nx} +++option (@pxref{Mode Options, ,Choosing Modes}). +++ +++To display the list of init files loaded by gdb at startup, you +++can use @kbd{gdb --help}. +++ +++@cindex init file name +++@cindex @file{.gdbinit} +++@cindex @file{gdb.ini} +++The @value{GDBN} init files are normally called @file{.gdbinit}. +++The DJGPP port of @value{GDBN} uses the name @file{gdb.ini}, due to +++the limitations of file names imposed by DOS filesystems. The Windows +++port of @value{GDBN} uses the standard name, but if it finds a +++@file{gdb.ini} file in your home directory, it warns you about that +++and suggests to rename the file to the standard name. +++ +++ +++@node Quitting GDB +++@section Quitting @value{GDBN} +++@cindex exiting @value{GDBN} +++@cindex leaving @value{GDBN} +++ +++@table @code +++@kindex quit @r{[}@var{expression}@r{]} +++@kindex q @r{(@code{quit})} +++@item quit @r{[}@var{expression}@r{]} +++@itemx q +++To exit @value{GDBN}, use the @code{quit} command (abbreviated +++@code{q}), or type an end-of-file character (usually @kbd{Ctrl-d}). If you +++do not supply @var{expression}, @value{GDBN} will terminate normally; +++otherwise it will terminate using the result of @var{expression} as the +++error code. +++@end table +++ +++@cindex interrupt +++An interrupt (often @kbd{Ctrl-c}) does not exit from @value{GDBN}, but rather +++terminates the action of any @value{GDBN} command that is in progress and +++returns to @value{GDBN} command level. It is safe to type the interrupt +++character at any time because @value{GDBN} does not allow it to take effect +++until a time when it is safe. +++ +++If you have been using @value{GDBN} to control an attached process or +++device, you can release it with the @code{detach} command +++(@pxref{Attach, ,Debugging an Already-running Process}). +++ +++@node Shell Commands +++@section Shell Commands +++ +++If you need to execute occasional shell commands during your +++debugging session, there is no need to leave or suspend @value{GDBN}; you can +++just use the @code{shell} command. +++ +++@table @code +++@kindex shell +++@kindex ! +++@cindex shell escape +++@item shell @var{command-string} +++@itemx !@var{command-string} +++Invoke a standard shell to execute @var{command-string}. +++Note that no space is needed between @code{!} and @var{command-string}. +++On GNU and Unix systems, the environment variable @code{SHELL}, if it +++exists, determines which shell to run. Otherwise @value{GDBN} uses +++the default shell (@file{/bin/sh} on GNU and Unix systems, +++@file{cmd.exe} on MS-Windows, @file{COMMAND.COM} on MS-DOS, etc.). +++@end table +++ +++The utility @code{make} is often needed in development environments. +++You do not have to use the @code{shell} command for this purpose in +++@value{GDBN}: +++ +++@table @code +++@kindex make +++@cindex calling make +++@item make @var{make-args} +++Execute the @code{make} program with the specified +++arguments. This is equivalent to @samp{shell make @var{make-args}}. +++@end table +++ +++@table @code +++@kindex pipe +++@kindex | +++@cindex send the output of a gdb command to a shell command +++@anchor{pipe} +++@item pipe [@var{command}] | @var{shell_command} +++@itemx | [@var{command}] | @var{shell_command} +++@itemx pipe -d @var{delim} @var{command} @var{delim} @var{shell_command} +++@itemx | -d @var{delim} @var{command} @var{delim} @var{shell_command} +++Executes @var{command} and sends its output to @var{shell_command}. +++Note that no space is needed around @code{|}. +++If no @var{command} is provided, the last command executed is repeated. +++ +++In case the @var{command} contains a @code{|}, the option @code{-d @var{delim}} +++can be used to specify an alternate delimiter string @var{delim} that separates +++the @var{command} from the @var{shell_command}. +++ +++Example: +++@smallexample +++@group +++(gdb) p var +++$1 = @{ +++ black = 144, +++ red = 233, +++ green = 377, +++ blue = 610, +++ white = 987 +++@} +++@end group +++@group +++(gdb) pipe p var|wc +++ 7 19 80 +++(gdb) |p var|wc -l +++7 +++@end group +++@group +++(gdb) p /x var +++$4 = @{ +++ black = 0x90, +++ red = 0xe9, +++ green = 0x179, +++ blue = 0x262, +++ white = 0x3db +++@} +++(gdb) ||grep red +++ red => 0xe9, +++@end group +++@group +++(gdb) | -d ! echo this contains a | char\n ! sed -e 's/|/PIPE/' +++this contains a PIPE char +++(gdb) | -d xxx echo this contains a | char!\n xxx sed -e 's/|/PIPE/' +++this contains a PIPE char! +++(gdb) +++@end group +++@end smallexample +++@end table +++ +++The convenience variables @code{$_shell_exitcode} and @code{$_shell_exitsignal} +++can be used to examine the exit status of the last shell command launched +++by @code{shell}, @code{make}, @code{pipe} and @code{|}. +++@xref{Convenience Vars,, Convenience Variables}. +++ +++@node Logging Output +++@section Logging Output +++@cindex logging @value{GDBN} output +++@cindex save @value{GDBN} output to a file +++ +++You may want to save the output of @value{GDBN} commands to a file. +++There are several commands to control @value{GDBN}'s logging. +++ +++@table @code +++@kindex set logging +++@item set logging on +++Enable logging. +++@item set logging off +++Disable logging. +++@cindex logging file name +++@item set logging file @var{file} +++Change the name of the current logfile. The default logfile is @file{gdb.txt}. +++@item set logging overwrite [on|off] +++By default, @value{GDBN} will append to the logfile. Set @code{overwrite} if +++you want @code{set logging on} to overwrite the logfile instead. +++@item set logging redirect [on|off] +++By default, @value{GDBN} output will go to both the terminal and the logfile. +++Set @code{redirect} if you want output to go only to the log file. +++@item set logging debugredirect [on|off] +++By default, @value{GDBN} debug output will go to both the terminal and the logfile. +++Set @code{debugredirect} if you want debug output to go only to the log file. +++@kindex show logging +++@item show logging +++Show the current values of the logging settings. +++@end table +++ +++You can also redirect the output of a @value{GDBN} command to a +++shell command. @xref{pipe}. +++@node Commands +++@chapter @value{GDBN} Commands +++ +++You can abbreviate a @value{GDBN} command to the first few letters of the command +++name, if that abbreviation is unambiguous; and you can repeat certain +++@value{GDBN} commands by typing just @key{RET}. You can also use the @key{TAB} +++key to get @value{GDBN} to fill out the rest of a word in a command (or to +++show you the alternatives available, if there is more than one possibility). +++ +++@menu +++* Command Syntax:: How to give commands to @value{GDBN} +++* Command Settings:: How to change default behavior of commands +++* Completion:: Command completion +++* Command Options:: Command options +++* Command aliases default args:: Automatically prepend default arguments to user-defined aliases +++* Help:: How to ask @value{GDBN} for help +++@end menu +++ +++@node Command Syntax +++@section Command Syntax +++ +++A @value{GDBN} command is a single line of input. There is no limit on +++how long it can be. It starts with a command name, which is followed by +++arguments whose meaning depends on the command name. For example, the +++command @code{step} accepts an argument which is the number of times to +++step, as in @samp{step 5}. You can also use the @code{step} command +++with no arguments. Some commands do not allow any arguments. +++ +++@cindex abbreviation +++@value{GDBN} command names may always be truncated if that abbreviation is +++unambiguous. Other possible command abbreviations are listed in the +++documentation for individual commands. In some cases, even ambiguous +++abbreviations are allowed; for example, @code{s} is specially defined as +++equivalent to @code{step} even though there are other commands whose +++names start with @code{s}. You can test abbreviations by using them as +++arguments to the @code{help} command. +++ +++@cindex repeating commands +++@kindex RET @r{(repeat last command)} +++A blank line as input to @value{GDBN} (typing just @key{RET}) means to +++repeat the previous command. Certain commands (for example, @code{run}) +++will not repeat this way; these are commands whose unintentional +++repetition might cause trouble and which you are unlikely to want to +++repeat. User-defined commands can disable this feature; see +++@ref{Define, dont-repeat}. +++ +++The @code{list} and @code{x} commands, when you repeat them with +++@key{RET}, construct new arguments rather than repeating +++exactly as typed. This permits easy scanning of source or memory. +++ +++@value{GDBN} can also use @key{RET} in another way: to partition lengthy +++output, in a way similar to the common utility @code{more} +++(@pxref{Screen Size,,Screen Size}). Since it is easy to press one +++@key{RET} too many in this situation, @value{GDBN} disables command +++repetition after any command that generates this sort of display. +++ +++@kindex # @r{(a comment)} +++@cindex comment +++Any text from a @kbd{#} to the end of the line is a comment; it does +++nothing. This is useful mainly in command files (@pxref{Command +++Files,,Command Files}). +++ +++@cindex repeating command sequences +++@kindex Ctrl-o @r{(operate-and-get-next)} +++The @kbd{Ctrl-o} binding is useful for repeating a complex sequence of +++commands. This command accepts the current line, like @key{RET}, and +++then fetches the next line relative to the current line from the history +++for editing. +++ +++ +++@node Command Settings +++@section Command Settings +++@cindex default behavior of commands, changing +++@cindex default settings, changing +++ +++Many commands change their behavior according to command-specific +++variables or settings. These settings can be changed with the +++@code{set} subcommands. For example, the @code{print} command +++(@pxref{Data, ,Examining Data}) prints arrays differently depending on +++settings changeable with the commands @code{set print elements +++NUMBER-OF-ELEMENTS} and @code{set print array-indexes}, among others. +++ +++You can change these settings to your preference in the gdbinit files +++loaded at @value{GDBN} startup. @xref{Startup}. +++ +++The settings can also be changed interactively during the debugging +++session. For example, to change the limit of array elements to print, +++you can do the following: +++@smallexample +++(@value{GDBN}) set print elements 10 +++(@value{GDBN}) print some_array +++$1 = @{0, 10, 20, 30, 40, 50, 60, 70, 80, 90...@} +++@end smallexample +++ +++The above @code{set print elements 10} command changes the number of +++elements to print from the default of 200 to 10. If you only intend +++this limit of 10 to be used for printing @code{some_array}, then you +++must restore the limit back to 200, with @code{set print elements +++200}. +++ +++Some commands allow overriding settings with command options. For +++example, the @code{print} command supports a number of options that +++allow overriding relevant global print settings as set by @code{set +++print} subcommands. @xref{print options}. The example above could be +++rewritten as: +++@smallexample +++(@value{GDBN}) print -elements 10 -- some_array +++$1 = @{0, 10, 20, 30, 40, 50, 60, 70, 80, 90...@} +++@end smallexample +++ +++Alternatively, you can use the @code{with} command to change a setting +++temporarily, for the duration of a command invocation. +++ +++@table @code +++@kindex with command +++@kindex w @r{(@code{with})} +++@cindex settings +++@cindex temporarily change settings +++@item with @var{setting} [@var{value}] [-- @var{command}] +++@itemx w @var{setting} [@var{value}] [-- @var{command}] +++Temporarily set @var{setting} to @var{value} for the duration of +++@var{command}. +++ +++@var{setting} is any setting you can change with the @code{set} +++subcommands. @var{value} is the value to assign to @code{setting} +++while running @code{command}. +++ +++If no @var{command} is provided, the last command executed is +++repeated. +++ +++If a @var{command} is provided, it must be preceded by a double dash +++(@code{--}) separator. This is required because some settings accept +++free-form arguments, such as expressions or filenames. +++ +++For example, the command +++@smallexample +++(@value{GDBN}) with print array on -- print some_array +++@end smallexample +++@noindent +++is equivalent to the following 3 commands: +++@smallexample +++(@value{GDBN}) set print array on +++(@value{GDBN}) print some_array +++(@value{GDBN}) set print array off +++@end smallexample +++ +++The @code{with} command is particularly useful when you want to +++override a setting while running user-defined commands, or commands +++defined in Python or Guile. @xref{Extending GDB,, Extending GDB}. +++ +++@smallexample +++(@value{GDBN}) with print pretty on -- my_complex_command +++@end smallexample +++ +++To change several settings for the same command, you can nest +++@code{with} commands. For example, @code{with language ada -- with +++print elements 10} temporarily changes the language to Ada and sets a +++limit of 10 elements to print for arrays and strings. +++ +++@end table +++ +++@node Completion +++@section Command Completion +++ +++@cindex completion +++@cindex word completion +++@value{GDBN} can fill in the rest of a word in a command for you, if there is +++only one possibility; it can also show you what the valid possibilities +++are for the next word in a command, at any time. This works for @value{GDBN} +++commands, @value{GDBN} subcommands, command options, and the names of symbols +++in your program. +++ +++Press the @key{TAB} key whenever you want @value{GDBN} to fill out the rest +++of a word. If there is only one possibility, @value{GDBN} fills in the +++word, and waits for you to finish the command (or press @key{RET} to +++enter it). For example, if you type +++ +++@c FIXME "@key" does not distinguish its argument sufficiently to permit +++@c complete accuracy in these examples; space introduced for clarity. +++@c If texinfo enhancements make it unnecessary, it would be nice to +++@c replace " @key" by "@key" in the following... +++@smallexample +++(@value{GDBP}) info bre @key{TAB} +++@end smallexample +++ +++@noindent +++@value{GDBN} fills in the rest of the word @samp{breakpoints}, since that is +++the only @code{info} subcommand beginning with @samp{bre}: +++ +++@smallexample +++(@value{GDBP}) info breakpoints +++@end smallexample +++ +++@noindent +++You can either press @key{RET} at this point, to run the @code{info +++breakpoints} command, or backspace and enter something else, if +++@samp{breakpoints} does not look like the command you expected. (If you +++were sure you wanted @code{info breakpoints} in the first place, you +++might as well just type @key{RET} immediately after @samp{info bre}, +++to exploit command abbreviations rather than command completion). +++ +++If there is more than one possibility for the next word when you press +++@key{TAB}, @value{GDBN} sounds a bell. You can either supply more +++characters and try again, or just press @key{TAB} a second time; +++@value{GDBN} displays all the possible completions for that word. For +++example, you might want to set a breakpoint on a subroutine whose name +++begins with @samp{make_}, but when you type @kbd{b make_@key{TAB}} @value{GDBN} +++just sounds the bell. Typing @key{TAB} again displays all the +++function names in your program that begin with those characters, for +++example: +++ +++@smallexample +++(@value{GDBP}) b make_ @key{TAB} +++@exdent @value{GDBN} sounds bell; press @key{TAB} again, to see: +++make_a_section_from_file make_environ +++make_abs_section make_function_type +++make_blockvector make_pointer_type +++make_cleanup make_reference_type +++make_command make_symbol_completion_list +++(@value{GDBP}) b make_ +++@end smallexample +++ +++@noindent +++After displaying the available possibilities, @value{GDBN} copies your +++partial input (@samp{b make_} in the example) so you can finish the +++command. +++ +++If you just want to see the list of alternatives in the first place, you +++can press @kbd{M-?} rather than pressing @key{TAB} twice. @kbd{M-?} +++means @kbd{@key{META} ?}. You can type this either by holding down a +++key designated as the @key{META} shift on your keyboard (if there is +++one) while typing @kbd{?}, or as @key{ESC} followed by @kbd{?}. +++ +++If the number of possible completions is large, @value{GDBN} will +++print as much of the list as it has collected, as well as a message +++indicating that the list may be truncated. +++ +++@smallexample +++(@value{GDBP}) b m@key{TAB}@key{TAB} +++main +++<... the rest of the possible completions ...> +++*** List may be truncated, max-completions reached. *** +++(@value{GDBP}) b m +++@end smallexample +++ +++@noindent +++This behavior can be controlled with the following commands: +++ +++@table @code +++@kindex set max-completions +++@item set max-completions @var{limit} +++@itemx set max-completions unlimited +++Set the maximum number of completion candidates. @value{GDBN} will +++stop looking for more completions once it collects this many candidates. +++This is useful when completing on things like function names as collecting +++all the possible candidates can be time consuming. +++The default value is 200. A value of zero disables tab-completion. +++Note that setting either no limit or a very large limit can make +++completion slow. +++@kindex show max-completions +++@item show max-completions +++Show the maximum number of candidates that @value{GDBN} will collect and show +++during completion. +++@end table +++ +++@cindex quotes in commands +++@cindex completion of quoted strings +++Sometimes the string you need, while logically a ``word'', may contain +++parentheses or other characters that @value{GDBN} normally excludes from +++its notion of a word. To permit word completion to work in this +++situation, you may enclose words in @code{'} (single quote marks) in +++@value{GDBN} commands. +++ +++A likely situation where you might need this is in typing an +++expression that involves a C@t{++} symbol name with template +++parameters. This is because when completing expressions, GDB treats +++the @samp{<} character as word delimiter, assuming that it's the +++less-than comparison operator (@pxref{C Operators, , C and C@t{++} +++Operators}). +++ +++For example, when you want to call a C@t{++} template function +++interactively using the @code{print} or @code{call} commands, you may +++need to distinguish whether you mean the version of @code{name} that +++was specialized for @code{int}, @code{name()}, or the version +++that was specialized for @code{float}, @code{name()}. To use +++the word-completion facilities in this situation, type a single quote +++@code{'} at the beginning of the function name. This alerts +++@value{GDBN} that it may need to consider more information than usual +++when you press @key{TAB} or @kbd{M-?} to request word completion: +++ +++@smallexample +++(@value{GDBP}) p 'func< @kbd{M-?} +++func() func() +++(@value{GDBP}) p 'func< +++@end smallexample +++ +++When setting breakpoints however (@pxref{Specify Location}), you don't +++usually need to type a quote before the function name, because +++@value{GDBN} understands that you want to set a breakpoint on a +++function: +++ +++@smallexample +++(@value{GDBP}) b func< @kbd{M-?} +++func() func() +++(@value{GDBP}) b func< +++@end smallexample +++ +++This is true even in the case of typing the name of C@t{++} overloaded +++functions (multiple definitions of the same function, distinguished by +++argument type). For example, when you want to set a breakpoint you +++don't need to distinguish whether you mean the version of @code{name} +++that takes an @code{int} parameter, @code{name(int)}, or the version +++that takes a @code{float} parameter, @code{name(float)}. +++ +++@smallexample +++(@value{GDBP}) b bubble( @kbd{M-?} +++bubble(int) bubble(double) +++(@value{GDBP}) b bubble(dou @kbd{M-?} +++bubble(double) +++@end smallexample +++ +++See @ref{quoting names} for a description of other scenarios that +++require quoting. +++ +++For more information about overloaded functions, see @ref{C Plus Plus +++Expressions, ,C@t{++} Expressions}. You can use the command @code{set +++overload-resolution off} to disable overload resolution; +++see @ref{Debugging C Plus Plus, ,@value{GDBN} Features for C@t{++}}. +++ +++@cindex completion of structure field names +++@cindex structure field name completion +++@cindex completion of union field names +++@cindex union field name completion +++When completing in an expression which looks up a field in a +++structure, @value{GDBN} also tries@footnote{The completer can be +++confused by certain kinds of invalid expressions. Also, it only +++examines the static type of the expression, not the dynamic type.} to +++limit completions to the field names available in the type of the +++left-hand-side: +++ +++@smallexample +++(@value{GDBP}) p gdb_stdout.@kbd{M-?} +++magic to_fputs to_rewind +++to_data to_isatty to_write +++to_delete to_put to_write_async_safe +++to_flush to_read +++@end smallexample +++ +++@noindent +++This is because the @code{gdb_stdout} is a variable of the type +++@code{struct ui_file} that is defined in @value{GDBN} sources as +++follows: +++ +++@smallexample +++struct ui_file +++@{ +++ int *magic; +++ ui_file_flush_ftype *to_flush; +++ ui_file_write_ftype *to_write; +++ ui_file_write_async_safe_ftype *to_write_async_safe; +++ ui_file_fputs_ftype *to_fputs; +++ ui_file_read_ftype *to_read; +++ ui_file_delete_ftype *to_delete; +++ ui_file_isatty_ftype *to_isatty; +++ ui_file_rewind_ftype *to_rewind; +++ ui_file_put_ftype *to_put; +++ void *to_data; +++@} +++@end smallexample +++ +++@node Command Options +++@section Command options +++ +++@cindex command options +++Some commands accept options starting with a leading dash. For +++example, @code{print -pretty}. Similarly to command names, you can +++abbreviate a @value{GDBN} option to the first few letters of the +++option name, if that abbreviation is unambiguous, and you can also use +++the @key{TAB} key to get @value{GDBN} to fill out the rest of a word +++in an option (or to show you the alternatives available, if there is +++more than one possibility). +++ +++@cindex command options, raw input +++Some commands take raw input as argument. For example, the print +++command processes arbitrary expressions in any of the languages +++supported by @value{GDBN}. With such commands, because raw input may +++start with a leading dash that would be confused with an option or any +++of its abbreviations, e.g.@: @code{print -p} (short for @code{print +++-pretty} or printing negative @code{p}?), if you specify any command +++option, then you must use a double-dash (@code{--}) delimiter to +++indicate the end of options. +++ +++@cindex command options, boolean +++ +++Some options are described as accepting an argument which can be +++either @code{on} or @code{off}. These are known as @dfn{boolean +++options}. Similarly to boolean settings commands---@code{on} and +++@code{off} are the typical values, but any of @code{1}, @code{yes} and +++@code{enable} can also be used as ``true'' value, and any of @code{0}, +++@code{no} and @code{disable} can also be used as ``false'' value. You +++can also omit a ``true'' value, as it is implied by default. +++ +++For example, these are equivalent: +++ +++@smallexample +++(@value{GDBP}) print -object on -pretty off -element unlimited -- *myptr +++(@value{GDBP}) p -o -p 0 -e u -- *myptr +++@end smallexample +++ +++You can discover the set of options some command accepts by completing +++on @code{-} after the command name. For example: +++ +++@smallexample +++(@value{GDBP}) print -@key{TAB}@key{TAB} +++-address -max-depth -raw-values -union +++-array -null-stop -repeats -vtbl +++-array-indexes -object -static-members +++-elements -pretty -symbol +++@end smallexample +++ +++Completion will in some cases guide you with a suggestion of what kind +++of argument an option expects. For example: +++ +++@smallexample +++(@value{GDBP}) print -elements @key{TAB}@key{TAB} +++NUMBER unlimited +++@end smallexample +++ +++Here, the option expects a number (e.g., @code{100}), not literal +++@code{NUMBER}. Such metasyntactical arguments are always presented in +++uppercase. +++ +++(For more on using the @code{print} command, see @ref{Data, ,Examining +++Data}.) +++ +++@node Command aliases default args +++@section Automatically prepend default arguments to user-defined aliases +++ +++You can tell @value{GDBN} to always prepend some default arguments to +++the list of arguments provided explicitly by the user when using a +++user-defined alias. +++ +++If you repeatedly use the same arguments or options for a command, you +++can define an alias for this command and tell @value{GDBN} to +++automatically prepend these arguments or options to the list of +++arguments you type explicitly when using the alias@footnote{@value{GDBN} +++could easily accept default arguments for pre-defined commands and aliases, +++but it was deemed this would be confusing, and so is not allowed.}. +++ +++For example, if you often use the command @code{thread apply all} +++specifying to work on the threads in ascending order and to continue in case it +++encounters an error, you can tell @value{GDBN} to automatically preprend +++the @code{-ascending} and @code{-c} options by using: +++ +++@smallexample +++(@value{GDBP}) alias thread apply asc-all = thread apply all -ascending -c +++@end smallexample +++ +++Once you have defined this alias with its default args, any time you type +++the @code{thread apply asc-all} followed by @code{some arguments}, +++@value{GDBN} will execute @code{thread apply all -ascending -c some arguments}. +++ +++To have even less to type, you can also define a one word alias: +++@smallexample +++(@value{GDBP}) alias t_a_c = thread apply all -ascending -c +++@end smallexample +++ +++As usual, unambiguous abbreviations can be used for @var{alias} +++and @var{default-args}. +++ +++The different aliases of a command do not share their default args. +++For example, you define a new alias @code{bt_ALL} showing all possible +++information and another alias @code{bt_SMALL} showing very limited information +++using: +++@smallexample +++(@value{GDBP}) alias bt_ALL = backtrace -entry-values both -frame-arg all \ +++ -past-main -past-entry -full +++(@value{GDBP}) alias bt_SMALL = backtrace -entry-values no -frame-arg none \ +++ -past-main off -past-entry off +++@end smallexample +++ +++(For more on using the @code{alias} command, see @ref{Aliases}.) +++ +++Default args are not limited to the arguments and options of @var{command}, +++but can specify nested commands if @var{command} accepts such a nested command +++as argument. +++For example, the below defines @code{faalocalsoftype} that lists the +++frames having locals of a certain type, together with the matching +++local vars: +++@smallexample +++(@value{GDBP}) alias faalocalsoftype = frame apply all info locals -q -t +++(@value{GDBP}) faalocalsoftype int +++#1 0x55554f5e in sleeper_or_burner (v=0xdf50) at sleepers.c:86 +++i = 0 +++ret = 21845 +++@end smallexample +++ +++This is also very useful to define an alias for a set of nested @code{with} +++commands to have a particular combination of temporary settings. For example, +++the below defines the alias @code{pp10} that pretty prints an expression +++argument, with a maximum of 10 elements if the expression is a string or +++an array: +++@smallexample +++(@value{GDBP}) alias pp10 = with print pretty -- with print elements 10 -- print +++@end smallexample +++This defines the alias @code{pp10} as being a sequence of 3 commands. +++The first part @code{with print pretty --} temporarily activates the setting +++@code{set print pretty}, then launches the command that follows the separator +++@code{--}. +++The command following the first part is also a @code{with} command that +++temporarily changes the setting @code{set print elements} to 10, then +++launches the command that follows the second separator @code{--}. +++The third part @code{print} is the command the @code{pp10} alias will launch, +++using the temporary values of the settings and the arguments explicitly given +++by the user. +++For more information about the @code{with} command usage, +++see @ref{Command Settings}. +++ +++@node Help +++@section Getting Help +++@cindex online documentation +++@kindex help +++ +++You can always ask @value{GDBN} itself for information on its commands, +++using the command @code{help}. +++ +++@table @code +++@kindex h @r{(@code{help})} +++@item help +++@itemx h +++You can use @code{help} (abbreviated @code{h}) with no arguments to +++display a short list of named classes of commands: +++ +++@smallexample +++(@value{GDBP}) help +++List of classes of commands: +++ +++aliases -- User-defined aliases of other commands +++breakpoints -- Making program stop at certain points +++data -- Examining data +++files -- Specifying and examining files +++internals -- Maintenance commands +++obscure -- Obscure features +++running -- Running the program +++stack -- Examining the stack +++status -- Status inquiries +++support -- Support facilities +++tracepoints -- Tracing of program execution without +++ stopping the program +++user-defined -- User-defined commands +++ +++Type "help" followed by a class name for a list of +++commands in that class. +++Type "help" followed by command name for full +++documentation. +++Command name abbreviations are allowed if unambiguous. +++(@value{GDBP}) +++@end smallexample +++@c the above line break eliminates huge line overfull... +++ +++@item help @var{class} +++Using one of the general help classes as an argument, you can get a +++list of the individual commands in that class. If a command has +++aliases, the aliases are given after the command name, separated by +++commas. If an alias has default arguments, the full definition of +++the alias is given after the first line. +++For example, here is the help display for the class @code{status}: +++ +++@smallexample +++(@value{GDBP}) help status +++Status inquiries. +++ +++List of commands: +++ +++@c Line break in "show" line falsifies real output, but needed +++@c to fit in smallbook page size. +++info, inf, i -- Generic command for showing things +++ about the program being debugged +++info address, iamain -- Describe where symbol SYM is stored. +++ alias iamain = info address main +++info all-registers -- List of all registers and their contents, +++ for selected stack frame. +++... +++show, info set -- Generic command for showing things +++ about the debugger +++ +++Type "help" followed by command name for full +++documentation. +++Command name abbreviations are allowed if unambiguous. +++(@value{GDBP}) +++@end smallexample +++ +++@item help @var{command} +++With a command name as @code{help} argument, @value{GDBN} displays a +++short paragraph on how to use that command. If that command has +++one or more aliases, @value{GDBN} will display a first line with +++the command name and all its aliases separated by commas. +++This first line will be followed by the full definition of all aliases +++having default arguments. +++ +++@kindex apropos +++@item apropos [-v] @var{regexp} +++The @code{apropos} command searches through all of the @value{GDBN} +++commands, and their documentation, for the regular expression specified in +++@var{args}. It prints out all matches found. The optional flag @samp{-v}, +++which stands for @samp{verbose}, indicates to output the full documentation +++of the matching commands and highlight the parts of the documentation +++matching @var{regexp}. For example: +++ +++@smallexample +++apropos alias +++@end smallexample +++ +++@noindent +++results in: +++ +++@smallexample +++@group +++alias -- Define a new command that is an alias of an existing command +++aliases -- User-defined aliases of other commands +++@end group +++@end smallexample +++ +++@noindent +++while +++ +++@smallexample +++apropos -v cut.*thread apply +++@end smallexample +++ +++@noindent +++results in the below output, where @samp{cut for 'thread apply} +++is highlighted if styling is enabled. +++ +++@smallexample +++@group +++taas -- Apply a command to all threads (ignoring errors +++and empty output). +++Usage: taas COMMAND +++shortcut for 'thread apply all -s COMMAND' +++ +++tfaas -- Apply a command to all frames of all threads +++(ignoring errors and empty output). +++Usage: tfaas COMMAND +++shortcut for 'thread apply all -s frame apply all -s COMMAND' +++@end group +++@end smallexample +++ +++@kindex complete +++@item complete @var{args} +++The @code{complete @var{args}} command lists all the possible completions +++for the beginning of a command. Use @var{args} to specify the beginning of the +++command you want completed. For example: +++ +++@smallexample +++complete i +++@end smallexample +++ +++@noindent results in: +++ +++@smallexample +++@group +++if +++ignore +++info +++inspect +++@end group +++@end smallexample +++ +++@noindent This is intended for use by @sc{gnu} Emacs. +++@end table +++ +++In addition to @code{help}, you can use the @value{GDBN} commands @code{info} +++and @code{show} to inquire about the state of your program, or the state +++of @value{GDBN} itself. Each command supports many topics of inquiry; this +++manual introduces each of them in the appropriate context. The listings +++under @code{info} and under @code{show} in the Command, Variable, and +++Function Index point to all the sub-commands. @xref{Command and Variable +++Index}. +++ +++@c @group +++@table @code +++@kindex info +++@kindex i @r{(@code{info})} +++@item info +++This command (abbreviated @code{i}) is for describing the state of your +++program. For example, you can show the arguments passed to a function +++with @code{info args}, list the registers currently in use with @code{info +++registers}, or list the breakpoints you have set with @code{info breakpoints}. +++You can get a complete list of the @code{info} sub-commands with +++@w{@code{help info}}. +++ +++@kindex set +++@item set +++You can assign the result of an expression to an environment variable with +++@code{set}. For example, you can set the @value{GDBN} prompt to a $-sign with +++@code{set prompt $}. +++ +++@kindex show +++@item show +++In contrast to @code{info}, @code{show} is for describing the state of +++@value{GDBN} itself. +++You can change most of the things you can @code{show}, by using the +++related command @code{set}; for example, you can control what number +++system is used for displays with @code{set radix}, or simply inquire +++which is currently in use with @code{show radix}. +++ +++@kindex info set +++To display all the settable parameters and their current +++values, you can use @code{show} with no arguments; you may also use +++@code{info set}. Both commands produce the same display. +++@c FIXME: "info set" violates the rule that "info" is for state of +++@c FIXME...program. Ck w/ GNU: "info set" to be called something else, +++@c FIXME...or change desc of rule---eg "state of prog and debugging session"? +++@end table +++@c @end group +++ +++Here are several miscellaneous @code{show} subcommands, all of which are +++exceptional in lacking corresponding @code{set} commands: +++ +++@table @code +++@kindex show version +++@cindex @value{GDBN} version number +++@item show version +++Show what version of @value{GDBN} is running. You should include this +++information in @value{GDBN} bug-reports. If multiple versions of +++@value{GDBN} are in use at your site, you may need to determine which +++version of @value{GDBN} you are running; as @value{GDBN} evolves, new +++commands are introduced, and old ones may wither away. Also, many +++system vendors ship variant versions of @value{GDBN}, and there are +++variant versions of @value{GDBN} in @sc{gnu}/Linux distributions as well. +++The version number is the same as the one announced when you start +++@value{GDBN}. +++ +++@kindex show copying +++@kindex info copying +++@cindex display @value{GDBN} copyright +++@item show copying +++@itemx info copying +++Display information about permission for copying @value{GDBN}. +++ +++@kindex show warranty +++@kindex info warranty +++@item show warranty +++@itemx info warranty +++Display the @sc{gnu} ``NO WARRANTY'' statement, or a warranty, +++if your version of @value{GDBN} comes with one. +++ +++@kindex show configuration +++@item show configuration +++Display detailed information about the way @value{GDBN} was configured +++when it was built. This displays the optional arguments passed to the +++@file{configure} script and also configuration parameters detected +++automatically by @command{configure}. When reporting a @value{GDBN} +++bug (@pxref{GDB Bugs}), it is important to include this information in +++your report. +++ +++@end table +++ +++@node Running +++@chapter Running Programs Under @value{GDBN} +++ +++When you run a program under @value{GDBN}, you must first generate +++debugging information when you compile it. +++ +++You may start @value{GDBN} with its arguments, if any, in an environment +++of your choice. If you are doing native debugging, you may redirect +++your program's input and output, debug an already running process, or +++kill a child process. +++ +++@menu +++* Compilation:: Compiling for debugging +++* Starting:: Starting your program +++* Arguments:: Your program's arguments +++* Environment:: Your program's environment +++ +++* Working Directory:: Your program's working directory +++* Input/Output:: Your program's input and output +++* Attach:: Debugging an already-running process +++* Kill Process:: Killing the child process +++* Inferiors Connections and Programs:: Debugging multiple inferiors +++ connections and programs +++* Threads:: Debugging programs with multiple threads +++* Forks:: Debugging forks +++* Checkpoint/Restart:: Setting a @emph{bookmark} to return to later +++@end menu +++ +++@node Compilation +++@section Compiling for Debugging +++ +++In order to debug a program effectively, you need to generate +++debugging information when you compile it. This debugging information +++is stored in the object file; it describes the data type of each +++variable or function and the correspondence between source line numbers +++and addresses in the executable code. +++ +++To request debugging information, specify the @samp{-g} option when you run +++the compiler. +++ +++Programs that are to be shipped to your customers are compiled with +++optimizations, using the @samp{-O} compiler option. However, some +++compilers are unable to handle the @samp{-g} and @samp{-O} options +++together. Using those compilers, you cannot generate optimized +++executables containing debugging information. +++ +++@value{NGCC}, the @sc{gnu} C/C@t{++} compiler, supports @samp{-g} with or +++without @samp{-O}, making it possible to debug optimized code. We +++recommend that you @emph{always} use @samp{-g} whenever you compile a +++program. You may think your program is correct, but there is no sense +++in pushing your luck. For more information, see @ref{Optimized Code}. +++ +++Older versions of the @sc{gnu} C compiler permitted a variant option +++@w{@samp{-gg}} for debugging information. @value{GDBN} no longer supports this +++format; if your @sc{gnu} C compiler has this option, do not use it. +++ +++@value{GDBN} knows about preprocessor macros and can show you their +++expansion (@pxref{Macros}). Most compilers do not include information +++about preprocessor macros in the debugging information if you specify +++the @option{-g} flag alone. Version 3.1 and later of @value{NGCC}, +++the @sc{gnu} C compiler, provides macro information if you are using +++the DWARF debugging format, and specify the option @option{-g3}. +++ +++@xref{Debugging Options,,Options for Debugging Your Program or GCC, +++gcc, Using the @sc{gnu} Compiler Collection (GCC)}, for more +++information on @value{NGCC} options affecting debug information. +++ +++You will have the best debugging experience if you use the latest +++version of the DWARF debugging format that your compiler supports. +++DWARF is currently the most expressive and best supported debugging +++format in @value{GDBN}. +++ +++@need 2000 +++@node Starting +++@section Starting your Program +++@cindex starting +++@cindex running +++ +++@table @code +++@kindex run +++@kindex r @r{(@code{run})} +++@item run +++@itemx r +++Use the @code{run} command to start your program under @value{GDBN}. +++You must first specify the program name with an argument to +++@value{GDBN} (@pxref{Invocation, ,Getting In and Out of +++@value{GDBN}}), or by using the @code{file} or @code{exec-file} +++command (@pxref{Files, ,Commands to Specify Files}). +++ +++@end table +++ +++If you are running your program in an execution environment that +++supports processes, @code{run} creates an inferior process and makes +++that process run your program. In some environments without processes, +++@code{run} jumps to the start of your program. Other targets, +++like @samp{remote}, are always running. If you get an error +++message like this one: +++ +++@smallexample +++The "remote" target does not support "run". +++Try "help target" or "continue". +++@end smallexample +++ +++@noindent +++then use @code{continue} to run your program. You may need @code{load} +++first (@pxref{load}). +++ +++The execution of a program is affected by certain information it +++receives from its superior. @value{GDBN} provides ways to specify this +++information, which you must do @emph{before} starting your program. (You +++can change it after starting your program, but such changes only affect +++your program the next time you start it.) This information may be +++divided into four categories: +++ +++@table @asis +++@item The @emph{arguments.} +++Specify the arguments to give your program as the arguments of the +++@code{run} command. If a shell is available on your target, the shell +++is used to pass the arguments, so that you may use normal conventions +++(such as wildcard expansion or variable substitution) in describing +++the arguments. +++In Unix systems, you can control which shell is used with the +++@code{SHELL} environment variable. If you do not define @code{SHELL}, +++@value{GDBN} uses the default shell (@file{/bin/sh}). You can disable +++use of any shell with the @code{set startup-with-shell} command (see +++below for details). +++ +++@item The @emph{environment.} +++Your program normally inherits its environment from @value{GDBN}, but you can +++use the @value{GDBN} commands @code{set environment} and @code{unset +++environment} to change parts of the environment that affect +++your program. @xref{Environment, ,Your Program's Environment}. +++ +++@item The @emph{working directory.} +++You can set your program's working directory with the command +++@kbd{set cwd}. If you do not set any working directory with this +++command, your program will inherit @value{GDBN}'s working directory if +++native debugging, or the remote server's working directory if remote +++debugging. @xref{Working Directory, ,Your Program's Working +++Directory}. +++ +++@item The @emph{standard input and output.} +++Your program normally uses the same device for standard input and +++standard output as @value{GDBN} is using. You can redirect input and output +++in the @code{run} command line, or you can use the @code{tty} command to +++set a different device for your program. +++@xref{Input/Output, ,Your Program's Input and Output}. +++ +++@cindex pipes +++@emph{Warning:} While input and output redirection work, you cannot use +++pipes to pass the output of the program you are debugging to another +++program; if you attempt this, @value{GDBN} is likely to wind up debugging the +++wrong program. +++@end table +++ +++When you issue the @code{run} command, your program begins to execute +++immediately. @xref{Stopping, ,Stopping and Continuing}, for discussion +++of how to arrange for your program to stop. Once your program has +++stopped, you may call functions in your program, using the @code{print} +++or @code{call} commands. @xref{Data, ,Examining Data}. +++ +++If the modification time of your symbol file has changed since the last +++time @value{GDBN} read its symbols, @value{GDBN} discards its symbol +++table, and reads it again. When it does this, @value{GDBN} tries to retain +++your current breakpoints. +++ +++@table @code +++@kindex start +++@item start +++@cindex run to main procedure +++The name of the main procedure can vary from language to language. +++With C or C@t{++}, the main procedure name is always @code{main}, but +++other languages such as Ada do not require a specific name for their +++main procedure. The debugger provides a convenient way to start the +++execution of the program and to stop at the beginning of the main +++procedure, depending on the language used. +++ +++The @samp{start} command does the equivalent of setting a temporary +++breakpoint at the beginning of the main procedure and then invoking +++the @samp{run} command. +++ +++@cindex elaboration phase +++Some programs contain an @dfn{elaboration} phase where some startup code is +++executed before the main procedure is called. This depends on the +++languages used to write your program. In C@t{++}, for instance, +++constructors for static and global objects are executed before +++@code{main} is called. It is therefore possible that the debugger stops +++before reaching the main procedure. However, the temporary breakpoint +++will remain to halt execution. +++ +++Specify the arguments to give to your program as arguments to the +++@samp{start} command. These arguments will be given verbatim to the +++underlying @samp{run} command. Note that the same arguments will be +++reused if no argument is provided during subsequent calls to +++@samp{start} or @samp{run}. +++ +++It is sometimes necessary to debug the program during elaboration. In +++these cases, using the @code{start} command would stop the execution +++of your program too late, as the program would have already completed +++the elaboration phase. Under these circumstances, either insert +++breakpoints in your elaboration code before running your program or +++use the @code{starti} command. +++ +++@kindex starti +++@item starti +++@cindex run to first instruction +++The @samp{starti} command does the equivalent of setting a temporary +++breakpoint at the first instruction of a program's execution and then +++invoking the @samp{run} command. For programs containing an +++elaboration phase, the @code{starti} command will stop execution at +++the start of the elaboration phase. +++ +++@anchor{set exec-wrapper} +++@kindex set exec-wrapper +++@item set exec-wrapper @var{wrapper} +++@itemx show exec-wrapper +++@itemx unset exec-wrapper +++When @samp{exec-wrapper} is set, the specified wrapper is used to +++launch programs for debugging. @value{GDBN} starts your program +++with a shell command of the form @kbd{exec @var{wrapper} +++@var{program}}. Quoting is added to @var{program} and its +++arguments, but not to @var{wrapper}, so you should add quotes if +++appropriate for your shell. The wrapper runs until it executes +++your program, and then @value{GDBN} takes control. +++ +++You can use any program that eventually calls @code{execve} with +++its arguments as a wrapper. Several standard Unix utilities do +++this, e.g.@: @code{env} and @code{nohup}. Any Unix shell script ending +++with @code{exec "$@@"} will also work. +++ +++For example, you can use @code{env} to pass an environment variable to +++the debugged program, without setting the variable in your shell's +++environment: +++ +++@smallexample +++(@value{GDBP}) set exec-wrapper env 'LD_PRELOAD=libtest.so' +++(@value{GDBP}) run +++@end smallexample +++ +++This command is available when debugging locally on most targets, excluding +++@sc{djgpp}, Cygwin, MS Windows, and QNX Neutrino. +++ +++@kindex set startup-with-shell +++@anchor{set startup-with-shell} +++@item set startup-with-shell +++@itemx set startup-with-shell on +++@itemx set startup-with-shell off +++@itemx show startup-with-shell +++On Unix systems, by default, if a shell is available on your target, +++@value{GDBN}) uses it to start your program. Arguments of the +++@code{run} command are passed to the shell, which does variable +++substitution, expands wildcard characters and performs redirection of +++I/O. In some circumstances, it may be useful to disable such use of a +++shell, for example, when debugging the shell itself or diagnosing +++startup failures such as: +++ +++@smallexample +++(@value{GDBP}) run +++Starting program: ./a.out +++During startup program terminated with signal SIGSEGV, Segmentation fault. +++@end smallexample +++ +++@noindent +++which indicates the shell or the wrapper specified with +++@samp{exec-wrapper} crashed, not your program. Most often, this is +++caused by something odd in your shell's non-interactive mode +++initialization file---such as @file{.cshrc} for C-shell, +++$@file{.zshenv} for the Z shell, or the file specified in the +++@samp{BASH_ENV} environment variable for BASH. +++ +++@anchor{set auto-connect-native-target} +++@kindex set auto-connect-native-target +++@item set auto-connect-native-target +++@itemx set auto-connect-native-target on +++@itemx set auto-connect-native-target off +++@itemx show auto-connect-native-target +++ +++By default, if the current inferior is not connected to any target yet +++(e.g., with @code{target remote}), the @code{run} command starts your +++program as a native process under @value{GDBN}, on your local machine. +++If you're sure you don't want to debug programs on your local machine, +++you can tell @value{GDBN} to not connect to the native target +++automatically with the @code{set auto-connect-native-target off} +++command. +++ +++If @code{on}, which is the default, and if the current inferior is not +++connected to a target already, the @code{run} command automaticaly +++connects to the native target, if one is available. +++ +++If @code{off}, and if the current inferior is not connected to a +++target already, the @code{run} command fails with an error: +++ +++@smallexample +++(@value{GDBP}) run +++Don't know how to run. Try "help target". +++@end smallexample +++ +++If the current inferior is already connected to a target, @value{GDBN} +++always uses it with the @code{run} command. +++ +++In any case, you can explicitly connect to the native target with the +++@code{target native} command. For example, +++ +++@smallexample +++(@value{GDBP}) set auto-connect-native-target off +++(@value{GDBP}) run +++Don't know how to run. Try "help target". +++(@value{GDBP}) target native +++(@value{GDBP}) run +++Starting program: ./a.out +++[Inferior 1 (process 10421) exited normally] +++@end smallexample +++ +++In case you connected explicitly to the @code{native} target, +++@value{GDBN} remains connected even if all inferiors exit, ready for +++the next @code{run} command. Use the @code{disconnect} command to +++disconnect. +++ +++Examples of other commands that likewise respect the +++@code{auto-connect-native-target} setting: @code{attach}, @code{info +++proc}, @code{info os}. +++ +++@kindex set disable-randomization +++@item set disable-randomization +++@itemx set disable-randomization on +++This option (enabled by default in @value{GDBN}) will turn off the native +++randomization of the virtual address space of the started program. This option +++is useful for multiple debugging sessions to make the execution better +++reproducible and memory addresses reusable across debugging sessions. +++ +++This feature is implemented only on certain targets, including @sc{gnu}/Linux. +++On @sc{gnu}/Linux you can get the same behavior using +++ +++@smallexample +++(@value{GDBP}) set exec-wrapper setarch `uname -m` -R +++@end smallexample +++ +++@item set disable-randomization off +++Leave the behavior of the started executable unchanged. Some bugs rear their +++ugly heads only when the program is loaded at certain addresses. If your bug +++disappears when you run the program under @value{GDBN}, that might be because +++@value{GDBN} by default disables the address randomization on platforms, such +++as @sc{gnu}/Linux, which do that for stand-alone programs. Use @kbd{set +++disable-randomization off} to try to reproduce such elusive bugs. +++ +++On targets where it is available, virtual address space randomization +++protects the programs against certain kinds of security attacks. In these +++cases the attacker needs to know the exact location of a concrete executable +++code. Randomizing its location makes it impossible to inject jumps misusing +++a code at its expected addresses. +++ +++Prelinking shared libraries provides a startup performance advantage but it +++makes addresses in these libraries predictable for privileged processes by +++having just unprivileged access at the target system. Reading the shared +++library binary gives enough information for assembling the malicious code +++misusing it. Still even a prelinked shared library can get loaded at a new +++random address just requiring the regular relocation process during the +++startup. Shared libraries not already prelinked are always loaded at +++a randomly chosen address. +++ +++Position independent executables (PIE) contain position independent code +++similar to the shared libraries and therefore such executables get loaded at +++a randomly chosen address upon startup. PIE executables always load even +++already prelinked shared libraries at a random address. You can build such +++executable using @command{gcc -fPIE -pie}. +++ +++Heap (malloc storage), stack and custom mmap areas are always placed randomly +++(as long as the randomization is enabled). +++ +++@item show disable-randomization +++Show the current setting of the explicit disable of the native randomization of +++the virtual address space of the started program. +++ +++@end table +++ +++@node Arguments +++@section Your Program's Arguments +++ +++@cindex arguments (to your program) +++The arguments to your program can be specified by the arguments of the +++@code{run} command. +++They are passed to a shell, which expands wildcard characters and +++performs redirection of I/O, and thence to your program. Your +++@code{SHELL} environment variable (if it exists) specifies what shell +++@value{GDBN} uses. If you do not define @code{SHELL}, @value{GDBN} uses +++the default shell (@file{/bin/sh} on Unix). +++ +++On non-Unix systems, the program is usually invoked directly by +++@value{GDBN}, which emulates I/O redirection via the appropriate system +++calls, and the wildcard characters are expanded by the startup code of +++the program, not by the shell. +++ +++@code{run} with no arguments uses the same arguments used by the previous +++@code{run}, or those set by the @code{set args} command. +++ +++@table @code +++@kindex set args +++@item set args +++Specify the arguments to be used the next time your program is run. If +++@code{set args} has no arguments, @code{run} executes your program +++with no arguments. Once you have run your program with arguments, +++using @code{set args} before the next @code{run} is the only way to run +++it again without arguments. +++ +++@kindex show args +++@item show args +++Show the arguments to give your program when it is started. +++@end table +++ +++@node Environment +++@section Your Program's Environment +++ +++@cindex environment (of your program) +++The @dfn{environment} consists of a set of environment variables and +++their values. Environment variables conventionally record such things as +++your user name, your home directory, your terminal type, and your search +++path for programs to run. Usually you set up environment variables with +++the shell and they are inherited by all the other programs you run. When +++debugging, it can be useful to try running your program with a modified +++environment without having to start @value{GDBN} over again. +++ +++@table @code +++@kindex path +++@item path @var{directory} +++Add @var{directory} to the front of the @code{PATH} environment variable +++(the search path for executables) that will be passed to your program. +++The value of @code{PATH} used by @value{GDBN} does not change. +++You may specify several directory names, separated by whitespace or by a +++system-dependent separator character (@samp{:} on Unix, @samp{;} on +++MS-DOS and MS-Windows). If @var{directory} is already in the path, it +++is moved to the front, so it is searched sooner. +++ +++You can use the string @samp{$cwd} to refer to whatever is the current +++working directory at the time @value{GDBN} searches the path. If you +++use @samp{.} instead, it refers to the directory where you executed the +++@code{path} command. @value{GDBN} replaces @samp{.} in the +++@var{directory} argument (with the current path) before adding +++@var{directory} to the search path. +++@c 'path' is explicitly nonrepeatable, but RMS points out it is silly to +++@c document that, since repeating it would be a no-op. +++ +++@kindex show paths +++@item show paths +++Display the list of search paths for executables (the @code{PATH} +++environment variable). +++ +++@kindex show environment +++@item show environment @r{[}@var{varname}@r{]} +++Print the value of environment variable @var{varname} to be given to +++your program when it starts. If you do not supply @var{varname}, +++print the names and values of all environment variables to be given to +++your program. You can abbreviate @code{environment} as @code{env}. +++ +++@kindex set environment +++@anchor{set environment} +++@item set environment @var{varname} @r{[}=@var{value}@r{]} +++Set environment variable @var{varname} to @var{value}. The value +++changes for your program (and the shell @value{GDBN} uses to launch +++it), not for @value{GDBN} itself. The @var{value} may be any string; the +++values of environment variables are just strings, and any +++interpretation is supplied by your program itself. The @var{value} +++parameter is optional; if it is eliminated, the variable is set to a +++null value. +++@c "any string" here does not include leading, trailing +++@c blanks. Gnu asks: does anyone care? +++ +++For example, this command: +++ +++@smallexample +++set env USER = foo +++@end smallexample +++ +++@noindent +++tells the debugged program, when subsequently run, that its user is named +++@samp{foo}. (The spaces around @samp{=} are used for clarity here; they +++are not actually required.) +++ +++Note that on Unix systems, @value{GDBN} runs your program via a shell, +++which also inherits the environment set with @code{set environment}. +++If necessary, you can avoid that by using the @samp{env} program as a +++wrapper instead of using @code{set environment}. @xref{set +++exec-wrapper}, for an example doing just that. +++ +++Environment variables that are set by the user are also transmitted to +++@command{gdbserver} to be used when starting the remote inferior. +++@pxref{QEnvironmentHexEncoded}. +++ +++@kindex unset environment +++@anchor{unset environment} +++@item unset environment @var{varname} +++Remove variable @var{varname} from the environment to be passed to your +++program. This is different from @samp{set env @var{varname} =}; +++@code{unset environment} removes the variable from the environment, +++rather than assigning it an empty value. +++ +++Environment variables that are unset by the user are also unset on +++@command{gdbserver} when starting the remote inferior. +++@pxref{QEnvironmentUnset}. +++@end table +++ +++@emph{Warning:} On Unix systems, @value{GDBN} runs your program using +++the shell indicated by your @code{SHELL} environment variable if it +++exists (or @code{/bin/sh} if not). If your @code{SHELL} variable +++names a shell that runs an initialization file when started +++non-interactively---such as @file{.cshrc} for C-shell, $@file{.zshenv} +++for the Z shell, or the file specified in the @samp{BASH_ENV} +++environment variable for BASH---any variables you set in that file +++affect your program. You may wish to move setting of environment +++variables to files that are only run when you sign on, such as +++@file{.login} or @file{.profile}. +++ +++@node Working Directory +++@section Your Program's Working Directory +++ +++@cindex working directory (of your program) +++Each time you start your program with @code{run}, the inferior will be +++initialized with the current working directory specified by the +++@kbd{set cwd} command. If no directory has been specified by this +++command, then the inferior will inherit @value{GDBN}'s current working +++directory as its working directory if native debugging, or it will +++inherit the remote server's current working directory if remote +++debugging. +++ +++@table @code +++@kindex set cwd +++@cindex change inferior's working directory +++@anchor{set cwd command} +++@item set cwd @r{[}@var{directory}@r{]} +++Set the inferior's working directory to @var{directory}, which will be +++@code{glob}-expanded in order to resolve tildes (@file{~}). If no +++argument has been specified, the command clears the setting and resets +++it to an empty state. This setting has no effect on @value{GDBN}'s +++working directory, and it only takes effect the next time you start +++the inferior. The @file{~} in @var{directory} is a short for the +++@dfn{home directory}, usually pointed to by the @env{HOME} environment +++variable. On MS-Windows, if @env{HOME} is not defined, @value{GDBN} +++uses the concatenation of @env{HOMEDRIVE} and @env{HOMEPATH} as +++fallback. +++ +++You can also change @value{GDBN}'s current working directory by using +++the @code{cd} command. +++@xref{cd command}. +++ +++@kindex show cwd +++@cindex show inferior's working directory +++@item show cwd +++Show the inferior's working directory. If no directory has been +++specified by @kbd{set cwd}, then the default inferior's working +++directory is the same as @value{GDBN}'s working directory. +++ +++@kindex cd +++@cindex change @value{GDBN}'s working directory +++@anchor{cd command} +++@item cd @r{[}@var{directory}@r{]} +++Set the @value{GDBN} working directory to @var{directory}. If not +++given, @var{directory} uses @file{'~'}. +++ +++The @value{GDBN} working directory serves as a default for the +++commands that specify files for @value{GDBN} to operate on. +++@xref{Files, ,Commands to Specify Files}. +++@xref{set cwd command}. +++ +++@kindex pwd +++@item pwd +++Print the @value{GDBN} working directory. +++@end table +++ +++It is generally impossible to find the current working directory of +++the process being debugged (since a program can change its directory +++during its run). If you work on a system where @value{GDBN} supports +++the @code{info proc} command (@pxref{Process Information}), you can +++use the @code{info proc} command to find out the +++current working directory of the debuggee. +++ +++@node Input/Output +++@section Your Program's Input and Output +++ +++@cindex redirection +++@cindex i/o +++@cindex terminal +++By default, the program you run under @value{GDBN} does input and output to +++the same terminal that @value{GDBN} uses. @value{GDBN} switches the terminal +++to its own terminal modes to interact with you, but it records the terminal +++modes your program was using and switches back to them when you continue +++running your program. +++ +++@table @code +++@kindex info terminal +++@item info terminal +++Displays information recorded by @value{GDBN} about the terminal modes your +++program is using. +++@end table +++ +++You can redirect your program's input and/or output using shell +++redirection with the @code{run} command. For example, +++ +++@smallexample +++run > outfile +++@end smallexample +++ +++@noindent +++starts your program, diverting its output to the file @file{outfile}. +++ +++@kindex tty +++@cindex controlling terminal +++Another way to specify where your program should do input and output is +++with the @code{tty} command. This command accepts a file name as +++argument, and causes this file to be the default for future @code{run} +++commands. It also resets the controlling terminal for the child +++process, for future @code{run} commands. For example, +++ +++@smallexample +++tty /dev/ttyb +++@end smallexample +++ +++@noindent +++directs that processes started with subsequent @code{run} commands +++default to do input and output on the terminal @file{/dev/ttyb} and have +++that as their controlling terminal. +++ +++An explicit redirection in @code{run} overrides the @code{tty} command's +++effect on the input/output device, but not its effect on the controlling +++terminal. +++ +++When you use the @code{tty} command or redirect input in the @code{run} +++command, only the input @emph{for your program} is affected. The input +++for @value{GDBN} still comes from your terminal. @code{tty} is an alias +++for @code{set inferior-tty}. +++ +++@cindex inferior tty +++@cindex set inferior controlling terminal +++You can use the @code{show inferior-tty} command to tell @value{GDBN} to +++display the name of the terminal that will be used for future runs of your +++program. +++ +++@table @code +++@item set inferior-tty [ @var{tty} ] +++@kindex set inferior-tty +++Set the tty for the program being debugged to @var{tty}. Omitting @var{tty} +++restores the default behavior, which is to use the same terminal as +++@value{GDBN}. +++ +++@item show inferior-tty +++@kindex show inferior-tty +++Show the current tty for the program being debugged. +++@end table +++ +++@node Attach +++@section Debugging an Already-running Process +++@kindex attach +++@cindex attach +++ +++@table @code +++@item attach @var{process-id} +++This command attaches to a running process---one that was started +++outside @value{GDBN}. (@code{info files} shows your active +++targets.) The command takes as argument a process ID. The usual way to +++find out the @var{process-id} of a Unix process is with the @code{ps} utility, +++or with the @samp{jobs -l} shell command. +++ +++@code{attach} does not repeat if you press @key{RET} a second time after +++executing the command. +++@end table +++ +++To use @code{attach}, your program must be running in an environment +++which supports processes; for example, @code{attach} does not work for +++programs on bare-board targets that lack an operating system. You must +++also have permission to send the process a signal. +++ +++When you use @code{attach}, the debugger finds the program running in +++the process first by looking in the current working directory, then (if +++the program is not found) by using the source file search path +++(@pxref{Source Path, ,Specifying Source Directories}). You can also use +++the @code{file} command to load the program. @xref{Files, ,Commands to +++Specify Files}. +++ +++@anchor{set exec-file-mismatch} +++If the debugger can determine that the executable file running in the +++process it is attaching to does not match the current exec-file loaded +++by @value{GDBN}, the option @code{exec-file-mismatch} specifies how to +++handle the mismatch. @value{GDBN} tries to compare the files by +++comparing their build IDs (@pxref{build ID}), if available. +++ +++@table @code +++@kindex exec-file-mismatch +++@cindex set exec-file-mismatch +++@item set exec-file-mismatch @samp{ask|warn|off} +++ +++Whether to detect mismatch between the current executable file loaded +++by @value{GDBN} and the executable file used to start the process. If +++@samp{ask}, the default, display a warning and ask the user whether to +++load the process executable file; if @samp{warn}, just display a +++warning; if @samp{off}, don't attempt to detect a mismatch. +++If the user confirms loading the process executable file, then its symbols +++will be loaded as well. +++ +++@cindex show exec-file-mismatch +++@item show exec-file-mismatch +++Show the current value of @code{exec-file-mismatch}. +++ +++@end table +++ +++The first thing @value{GDBN} does after arranging to debug the specified +++process is to stop it. You can examine and modify an attached process +++with all the @value{GDBN} commands that are ordinarily available when +++you start processes with @code{run}. You can insert breakpoints; you +++can step and continue; you can modify storage. If you would rather the +++process continue running, you may use the @code{continue} command after +++attaching @value{GDBN} to the process. +++ +++@table @code +++@kindex detach +++@item detach +++When you have finished debugging the attached process, you can use the +++@code{detach} command to release it from @value{GDBN} control. Detaching +++the process continues its execution. After the @code{detach} command, +++that process and @value{GDBN} become completely independent once more, and you +++are ready to @code{attach} another process or start one with @code{run}. +++@code{detach} does not repeat if you press @key{RET} again after +++executing the command. +++@end table +++ +++If you exit @value{GDBN} while you have an attached process, you detach +++that process. If you use the @code{run} command, you kill that process. +++By default, @value{GDBN} asks for confirmation if you try to do either of these +++things; you can control whether or not you need to confirm by using the +++@code{set confirm} command (@pxref{Messages/Warnings, ,Optional Warnings and +++Messages}). +++ +++@node Kill Process +++@section Killing the Child Process +++ +++@table @code +++@kindex kill +++@item kill +++Kill the child process in which your program is running under @value{GDBN}. +++@end table +++ +++This command is useful if you wish to debug a core dump instead of a +++running process. @value{GDBN} ignores any core dump file while your program +++is running. +++ +++On some operating systems, a program cannot be executed outside @value{GDBN} +++while you have breakpoints set on it inside @value{GDBN}. You can use the +++@code{kill} command in this situation to permit running your program +++outside the debugger. +++ +++The @code{kill} command is also useful if you wish to recompile and +++relink your program, since on many systems it is impossible to modify an +++executable file while it is running in a process. In this case, when you +++next type @code{run}, @value{GDBN} notices that the file has changed, and +++reads the symbol table again (while trying to preserve your current +++breakpoint settings). +++ +++@node Inferiors Connections and Programs +++@section Debugging Multiple Inferiors Connections and Programs +++ +++@value{GDBN} lets you run and debug multiple programs in a single +++session. In addition, @value{GDBN} on some systems may let you run +++several programs simultaneously (otherwise you have to exit from one +++before starting another). On some systems @value{GDBN} may even let +++you debug several programs simultaneously on different remote systems. +++In the most general case, you can have multiple threads of execution +++in each of multiple processes, launched from multiple executables, +++running on different machines. +++ +++@cindex inferior +++@value{GDBN} represents the state of each program execution with an +++object called an @dfn{inferior}. An inferior typically corresponds to +++a process, but is more general and applies also to targets that do not +++have processes. Inferiors may be created before a process runs, and +++may be retained after a process exits. Inferiors have unique +++identifiers that are different from process ids. Usually each +++inferior will also have its own distinct address space, although some +++embedded targets may have several inferiors running in different parts +++of a single address space. Each inferior may in turn have multiple +++threads running in it. +++ +++To find out what inferiors exist at any moment, use @w{@code{info +++inferiors}}: +++ +++@table @code +++@kindex info inferiors [ @var{id}@dots{} ] +++@item info inferiors +++Print a list of all inferiors currently being managed by @value{GDBN}. +++By default all inferiors are printed, but the argument @var{id}@dots{} +++-- a space separated list of inferior numbers -- can be used to limit +++the display to just the requested inferiors. +++ +++@value{GDBN} displays for each inferior (in this order): +++ +++@enumerate +++@item +++the inferior number assigned by @value{GDBN} +++ +++@item +++the target system's inferior identifier +++ +++@item +++the target connection the inferior is bound to, including the unique +++connection number assigned by @value{GDBN}, and the protocol used by +++the connection. +++ +++@item +++the name of the executable the inferior is running. +++ +++@end enumerate +++ +++@noindent +++An asterisk @samp{*} preceding the @value{GDBN} inferior number +++indicates the current inferior. +++ +++For example, +++@end table +++@c end table here to get a little more width for example +++ +++@smallexample +++(@value{GDBP}) info inferiors +++ Num Description Connection Executable +++* 1 process 3401 1 (native) goodbye +++ 2 process 2307 2 (extended-remote host:10000) hello +++@end smallexample +++ +++To find out what open target connections exist at any moment, use +++@w{@code{info connections}}: +++ +++@table @code +++@kindex info connections [ @var{id}@dots{} ] +++@item info connections +++Print a list of all open target connections currently being managed by +++@value{GDBN}. By default all connections are printed, but the +++argument @var{id}@dots{} -- a space separated list of connections +++numbers -- can be used to limit the display to just the requested +++connections. +++ +++@value{GDBN} displays for each connection (in this order): +++ +++@enumerate +++@item +++the connection number assigned by @value{GDBN}. +++ +++@item +++the protocol used by the connection. +++ +++@item +++a textual description of the protocol used by the connection. +++ +++@end enumerate +++ +++@noindent +++An asterisk @samp{*} preceding the connection number indicates the +++connection of the current inferior. +++ +++For example, +++@end table +++@c end table here to get a little more width for example +++ +++@smallexample +++(@value{GDBP}) info connections +++ Num What Description +++* 1 extended-remote host:10000 Extended remote serial target in gdb-specific protocol +++ 2 native Native process +++ 3 core Local core dump file +++@end smallexample +++ +++To switch focus between inferiors, use the @code{inferior} command: +++ +++@table @code +++@kindex inferior @var{infno} +++@item inferior @var{infno} +++Make inferior number @var{infno} the current inferior. The argument +++@var{infno} is the inferior number assigned by @value{GDBN}, as shown +++in the first field of the @samp{info inferiors} display. +++@end table +++ +++@vindex $_inferior@r{, convenience variable} +++The debugger convenience variable @samp{$_inferior} contains the +++number of the current inferior. You may find this useful in writing +++breakpoint conditional expressions, command scripts, and so forth. +++@xref{Convenience Vars,, Convenience Variables}, for general +++information on convenience variables. +++ +++You can get multiple executables into a debugging session via the +++@code{add-inferior} and @w{@code{clone-inferior}} commands. On some +++systems @value{GDBN} can add inferiors to the debug session +++automatically by following calls to @code{fork} and @code{exec}. To +++remove inferiors from the debugging session use the +++@w{@code{remove-inferiors}} command. +++ +++@table @code +++@kindex add-inferior +++@item add-inferior [ -copies @var{n} ] [ -exec @var{executable} ] [-no-connection ] +++Adds @var{n} inferiors to be run using @var{executable} as the +++executable; @var{n} defaults to 1. If no executable is specified, +++the inferiors begins empty, with no program. You can still assign or +++change the program assigned to the inferior at any time by using the +++@code{file} command with the executable name as its argument. +++ +++By default, the new inferior begins connected to the same target +++connection as the current inferior. For example, if the current +++inferior was connected to @code{gdbserver} with @code{target remote}, +++then the new inferior will be connected to the same @code{gdbserver} +++instance. The @samp{-no-connection} option starts the new inferior +++with no connection yet. You can then for example use the @code{target +++remote} command to connect to some other @code{gdbserver} instance, +++use @code{run} to spawn a local program, etc. +++ +++@kindex clone-inferior +++@item clone-inferior [ -copies @var{n} ] [ @var{infno} ] +++Adds @var{n} inferiors ready to execute the same program as inferior +++@var{infno}; @var{n} defaults to 1, and @var{infno} defaults to the +++number of the current inferior. This is a convenient command when you +++want to run another instance of the inferior you are debugging. +++ +++@smallexample +++(@value{GDBP}) info inferiors +++ Num Description Connection Executable +++* 1 process 29964 1 (native) helloworld +++(@value{GDBP}) clone-inferior +++Added inferior 2. +++1 inferiors added. +++(@value{GDBP}) info inferiors +++ Num Description Connection Executable +++* 1 process 29964 1 (native) helloworld +++ 2 1 (native) helloworld +++@end smallexample +++ +++You can now simply switch focus to inferior 2 and run it. +++ +++@kindex remove-inferiors +++@item remove-inferiors @var{infno}@dots{} +++Removes the inferior or inferiors @var{infno}@dots{}. It is not +++possible to remove an inferior that is running with this command. For +++those, use the @code{kill} or @code{detach} command first. +++ +++@end table +++ +++To quit debugging one of the running inferiors that is not the current +++inferior, you can either detach from it by using the @w{@code{detach +++inferior}} command (allowing it to run independently), or kill it +++using the @w{@code{kill inferiors}} command: +++ +++@table @code +++@kindex detach inferiors @var{infno}@dots{} +++@item detach inferior @var{infno}@dots{} +++Detach from the inferior or inferiors identified by @value{GDBN} +++inferior number(s) @var{infno}@dots{}. Note that the inferior's entry +++still stays on the list of inferiors shown by @code{info inferiors}, +++but its Description will show @samp{}. +++ +++@kindex kill inferiors @var{infno}@dots{} +++@item kill inferiors @var{infno}@dots{} +++Kill the inferior or inferiors identified by @value{GDBN} inferior +++number(s) @var{infno}@dots{}. Note that the inferior's entry still +++stays on the list of inferiors shown by @code{info inferiors}, but its +++Description will show @samp{}. +++@end table +++ +++After the successful completion of a command such as @code{detach}, +++@code{detach inferiors}, @code{kill} or @code{kill inferiors}, or after +++a normal process exit, the inferior is still valid and listed with +++@code{info inferiors}, ready to be restarted. +++ +++ +++To be notified when inferiors are started or exit under @value{GDBN}'s +++control use @w{@code{set print inferior-events}}: +++ +++@table @code +++@kindex set print inferior-events +++@cindex print messages on inferior start and exit +++@item set print inferior-events +++@itemx set print inferior-events on +++@itemx set print inferior-events off +++The @code{set print inferior-events} command allows you to enable or +++disable printing of messages when @value{GDBN} notices that new +++inferiors have started or that inferiors have exited or have been +++detached. By default, these messages will not be printed. +++ +++@kindex show print inferior-events +++@item show print inferior-events +++Show whether messages will be printed when @value{GDBN} detects that +++inferiors have started, exited or have been detached. +++@end table +++ +++Many commands will work the same with multiple programs as with a +++single program: e.g., @code{print myglobal} will simply display the +++value of @code{myglobal} in the current inferior. +++ +++ +++Occasionally, when debugging @value{GDBN} itself, it may be useful to +++get more info about the relationship of inferiors, programs, address +++spaces in a debug session. You can do that with the @w{@code{maint +++info program-spaces}} command. +++ +++@table @code +++@kindex maint info program-spaces +++@item maint info program-spaces +++Print a list of all program spaces currently being managed by +++@value{GDBN}. +++ +++@value{GDBN} displays for each program space (in this order): +++ +++@enumerate +++@item +++the program space number assigned by @value{GDBN} +++ +++@item +++the name of the executable loaded into the program space, with e.g., +++the @code{file} command. +++ +++@end enumerate +++ +++@noindent +++An asterisk @samp{*} preceding the @value{GDBN} program space number +++indicates the current program space. +++ +++In addition, below each program space line, @value{GDBN} prints extra +++information that isn't suitable to display in tabular form. For +++example, the list of inferiors bound to the program space. +++ +++@smallexample +++(@value{GDBP}) maint info program-spaces +++ Id Executable +++* 1 hello +++ 2 goodbye +++ Bound inferiors: ID 1 (process 21561) +++@end smallexample +++ +++Here we can see that no inferior is running the program @code{hello}, +++while @code{process 21561} is running the program @code{goodbye}. On +++some targets, it is possible that multiple inferiors are bound to the +++same program space. The most common example is that of debugging both +++the parent and child processes of a @code{vfork} call. For example, +++ +++@smallexample +++(@value{GDBP}) maint info program-spaces +++ Id Executable +++* 1 vfork-test +++ Bound inferiors: ID 2 (process 18050), ID 1 (process 18045) +++@end smallexample +++ +++Here, both inferior 2 and inferior 1 are running in the same program +++space as a result of inferior 1 having executed a @code{vfork} call. +++@end table +++ +++@node Threads +++@section Debugging Programs with Multiple Threads +++ +++@cindex threads of execution +++@cindex multiple threads +++@cindex switching threads +++In some operating systems, such as GNU/Linux and Solaris, a single program +++may have more than one @dfn{thread} of execution. The precise semantics +++of threads differ from one operating system to another, but in general +++the threads of a single program are akin to multiple processes---except +++that they share one address space (that is, they can all examine and +++modify the same variables). On the other hand, each thread has its own +++registers and execution stack, and perhaps private memory. +++ +++@value{GDBN} provides these facilities for debugging multi-thread +++programs: +++ +++@itemize @bullet +++@item automatic notification of new threads +++@item @samp{thread @var{thread-id}}, a command to switch among threads +++@item @samp{info threads}, a command to inquire about existing threads +++@item @samp{thread apply [@var{thread-id-list} | all] @var{args}}, +++a command to apply a command to a list of threads +++@item thread-specific breakpoints +++@item @samp{set print thread-events}, which controls printing of +++messages on thread start and exit. +++@item @samp{set libthread-db-search-path @var{path}}, which lets +++the user specify which @code{libthread_db} to use if the default choice +++isn't compatible with the program. +++@end itemize +++ +++@cindex focus of debugging +++@cindex current thread +++The @value{GDBN} thread debugging facility allows you to observe all +++threads while your program runs---but whenever @value{GDBN} takes +++control, one thread in particular is always the focus of debugging. +++This thread is called the @dfn{current thread}. Debugging commands show +++program information from the perspective of the current thread. +++ +++@cindex @code{New} @var{systag} message +++@cindex thread identifier (system) +++@c FIXME-implementors!! It would be more helpful if the [New...] message +++@c included GDB's numeric thread handle, so you could just go to that +++@c thread without first checking `info threads'. +++Whenever @value{GDBN} detects a new thread in your program, it displays +++the target system's identification for the thread with a message in the +++form @samp{[New @var{systag}]}, where @var{systag} is a thread identifier +++whose form varies depending on the particular system. For example, on +++@sc{gnu}/Linux, you might see +++ +++@smallexample +++[New Thread 0x41e02940 (LWP 25582)] +++@end smallexample +++ +++@noindent +++when @value{GDBN} notices a new thread. In contrast, on other systems, +++the @var{systag} is simply something like @samp{process 368}, with no +++further qualifier. +++ +++@c FIXME!! (1) Does the [New...] message appear even for the very first +++@c thread of a program, or does it only appear for the +++@c second---i.e.@: when it becomes obvious we have a multithread +++@c program? +++@c (2) *Is* there necessarily a first thread always? Or do some +++@c multithread systems permit starting a program with multiple +++@c threads ab initio? +++ +++@anchor{thread numbers} +++@cindex thread number, per inferior +++@cindex thread identifier (GDB) +++For debugging purposes, @value{GDBN} associates its own thread number +++---always a single integer---with each thread of an inferior. This +++number is unique between all threads of an inferior, but not unique +++between threads of different inferiors. +++ +++@cindex qualified thread ID +++You can refer to a given thread in an inferior using the qualified +++@var{inferior-num}.@var{thread-num} syntax, also known as +++@dfn{qualified thread ID}, with @var{inferior-num} being the inferior +++number and @var{thread-num} being the thread number of the given +++inferior. For example, thread @code{2.3} refers to thread number 3 of +++inferior 2. If you omit @var{inferior-num} (e.g., @code{thread 3}), +++then @value{GDBN} infers you're referring to a thread of the current +++inferior. +++ +++Until you create a second inferior, @value{GDBN} does not show the +++@var{inferior-num} part of thread IDs, even though you can always use +++the full @var{inferior-num}.@var{thread-num} form to refer to threads +++of inferior 1, the initial inferior. +++ +++@anchor{thread ID lists} +++@cindex thread ID lists +++Some commands accept a space-separated @dfn{thread ID list} as +++argument. A list element can be: +++ +++@enumerate +++@item +++A thread ID as shown in the first field of the @samp{info threads} +++display, with or without an inferior qualifier. E.g., @samp{2.1} or +++@samp{1}. +++ +++@item +++A range of thread numbers, again with or without an inferior +++qualifier, as in @var{inf}.@var{thr1}-@var{thr2} or +++@var{thr1}-@var{thr2}. E.g., @samp{1.2-4} or @samp{2-4}. +++ +++@item +++All threads of an inferior, specified with a star wildcard, with or +++without an inferior qualifier, as in @var{inf}.@code{*} (e.g., +++@samp{1.*}) or @code{*}. The former refers to all threads of the +++given inferior, and the latter form without an inferior qualifier +++refers to all threads of the current inferior. +++ +++@end enumerate +++ +++For example, if the current inferior is 1, and inferior 7 has one +++thread with ID 7.1, the thread list @samp{1 2-3 4.5 6.7-9 7.*} +++includes threads 1 to 3 of inferior 1, thread 5 of inferior 4, threads +++7 to 9 of inferior 6 and all threads of inferior 7. That is, in +++expanded qualified form, the same as @samp{1.1 1.2 1.3 4.5 6.7 6.8 6.9 +++7.1}. +++ +++ +++@anchor{global thread numbers} +++@cindex global thread number +++@cindex global thread identifier (GDB) +++In addition to a @emph{per-inferior} number, each thread is also +++assigned a unique @emph{global} number, also known as @dfn{global +++thread ID}, a single integer. Unlike the thread number component of +++the thread ID, no two threads have the same global ID, even when +++you're debugging multiple inferiors. +++ +++From @value{GDBN}'s perspective, a process always has at least one +++thread. In other words, @value{GDBN} assigns a thread number to the +++program's ``main thread'' even if the program is not multi-threaded. +++ +++@vindex $_thread@r{, convenience variable} +++@vindex $_gthread@r{, convenience variable} +++The debugger convenience variables @samp{$_thread} and +++@samp{$_gthread} contain, respectively, the per-inferior thread number +++and the global thread number of the current thread. You may find this +++useful in writing breakpoint conditional expressions, command scripts, +++and so forth. @xref{Convenience Vars,, Convenience Variables}, for +++general information on convenience variables. +++ +++If @value{GDBN} detects the program is multi-threaded, it augments the +++usual message about stopping at a breakpoint with the ID and name of +++the thread that hit the breakpoint. +++ +++@smallexample +++Thread 2 "client" hit Breakpoint 1, send_message () at client.c:68 +++@end smallexample +++ +++Likewise when the program receives a signal: +++ +++@smallexample +++Thread 1 "main" received signal SIGINT, Interrupt. +++@end smallexample +++ +++@table @code +++@kindex info threads +++@item info threads @r{[}@var{thread-id-list}@r{]} +++ +++Display information about one or more threads. With no arguments +++displays information about all threads. You can specify the list of +++threads that you want to display using the thread ID list syntax +++(@pxref{thread ID lists}). +++ +++@value{GDBN} displays for each thread (in this order): +++ +++@enumerate +++@item +++the per-inferior thread number assigned by @value{GDBN} +++ +++@item +++the global thread number assigned by @value{GDBN}, if the @samp{-gid} +++option was specified +++ +++@item +++the target system's thread identifier (@var{systag}) +++ +++@item +++the thread's name, if one is known. A thread can either be named by +++the user (see @code{thread name}, below), or, in some cases, by the +++program itself. +++ +++@item +++the current stack frame summary for that thread +++@end enumerate +++ +++@noindent +++An asterisk @samp{*} to the left of the @value{GDBN} thread number +++indicates the current thread. +++ +++For example, +++@end table +++@c end table here to get a little more width for example +++ +++@smallexample +++(@value{GDBP}) info threads +++ Id Target Id Frame +++* 1 process 35 thread 13 main (argc=1, argv=0x7ffffff8) +++ 2 process 35 thread 23 0x34e5 in sigpause () +++ 3 process 35 thread 27 0x34e5 in sigpause () +++ at threadtest.c:68 +++@end smallexample +++ +++If you're debugging multiple inferiors, @value{GDBN} displays thread +++IDs using the qualified @var{inferior-num}.@var{thread-num} format. +++Otherwise, only @var{thread-num} is shown. +++ +++If you specify the @samp{-gid} option, @value{GDBN} displays a column +++indicating each thread's global thread ID: +++ +++@smallexample +++(@value{GDBP}) info threads +++ Id GId Target Id Frame +++ 1.1 1 process 35 thread 13 main (argc=1, argv=0x7ffffff8) +++ 1.2 3 process 35 thread 23 0x34e5 in sigpause () +++ 1.3 4 process 35 thread 27 0x34e5 in sigpause () +++* 2.1 2 process 65 thread 1 main (argc=1, argv=0x7ffffff8) +++@end smallexample +++ +++On Solaris, you can display more information about user threads with a +++Solaris-specific command: +++ +++@table @code +++@item maint info sol-threads +++@kindex maint info sol-threads +++@cindex thread info (Solaris) +++Display info on Solaris user threads. +++@end table +++ +++@table @code +++@kindex thread @var{thread-id} +++@item thread @var{thread-id} +++Make thread ID @var{thread-id} the current thread. The command +++argument @var{thread-id} is the @value{GDBN} thread ID, as shown in +++the first field of the @samp{info threads} display, with or without an +++inferior qualifier (e.g., @samp{2.1} or @samp{1}). +++ +++@value{GDBN} responds by displaying the system identifier of the +++thread you selected, and its current stack frame summary: +++ +++@smallexample +++(@value{GDBP}) thread 2 +++[Switching to thread 2 (Thread 0xb7fdab70 (LWP 12747))] +++#0 some_function (ignore=0x0) at example.c:8 +++8 printf ("hello\n"); +++@end smallexample +++ +++@noindent +++As with the @samp{[New @dots{}]} message, the form of the text after +++@samp{Switching to} depends on your system's conventions for identifying +++threads. +++ +++@anchor{thread apply all} +++@kindex thread apply +++@cindex apply command to several threads +++@item thread apply [@var{thread-id-list} | all [-ascending]] [@var{flag}]@dots{} @var{command} +++The @code{thread apply} command allows you to apply the named +++@var{command} to one or more threads. Specify the threads that you +++want affected using the thread ID list syntax (@pxref{thread ID +++lists}), or specify @code{all} to apply to all threads. To apply a +++command to all threads in descending order, type @kbd{thread apply all +++@var{command}}. To apply a command to all threads in ascending order, +++type @kbd{thread apply all -ascending @var{command}}. +++ +++The @var{flag} arguments control what output to produce and how to handle +++errors raised when applying @var{command} to a thread. @var{flag} +++must start with a @code{-} directly followed by one letter in +++@code{qcs}. If several flags are provided, they must be given +++individually, such as @code{-c -q}. +++ +++By default, @value{GDBN} displays some thread information before the +++output produced by @var{command}, and an error raised during the +++execution of a @var{command} will abort @code{thread apply}. The +++following flags can be used to fine-tune this behavior: +++ +++@table @code +++@item -c +++The flag @code{-c}, which stands for @samp{continue}, causes any +++errors in @var{command} to be displayed, and the execution of +++@code{thread apply} then continues. +++@item -s +++The flag @code{-s}, which stands for @samp{silent}, causes any errors +++or empty output produced by a @var{command} to be silently ignored. +++That is, the execution continues, but the thread information and errors +++are not printed. +++@item -q +++The flag @code{-q} (@samp{quiet}) disables printing the thread +++information. +++@end table +++ +++Flags @code{-c} and @code{-s} cannot be used together. +++ +++@kindex taas +++@cindex apply command to all threads (ignoring errors and empty output) +++@item taas [@var{option}]@dots{} @var{command} +++Shortcut for @code{thread apply all -s [@var{option}]@dots{} @var{command}}. +++Applies @var{command} on all threads, ignoring errors and empty output. +++ +++The @code{taas} command accepts the same options as the @code{thread +++apply all} command. @xref{thread apply all}. +++ +++@kindex tfaas +++@cindex apply a command to all frames of all threads (ignoring errors and empty output) +++@item tfaas [@var{option}]@dots{} @var{command} +++Shortcut for @code{thread apply all -s -- frame apply all -s [@var{option}]@dots{} @var{command}}. +++Applies @var{command} on all frames of all threads, ignoring errors +++and empty output. Note that the flag @code{-s} is specified twice: +++The first @code{-s} ensures that @code{thread apply} only shows the thread +++information of the threads for which @code{frame apply} produces +++some output. The second @code{-s} is needed to ensure that @code{frame +++apply} shows the frame information of a frame only if the +++@var{command} successfully produced some output. +++ +++It can for example be used to print a local variable or a function +++argument without knowing the thread or frame where this variable or argument +++is, using: +++@smallexample +++(@value{GDBP}) tfaas p some_local_var_i_do_not_remember_where_it_is +++@end smallexample +++ +++The @code{tfaas} command accepts the same options as the @code{frame +++apply} command. @xref{Frame Apply,,frame apply}. +++ +++@kindex thread name +++@cindex name a thread +++@item thread name [@var{name}] +++This command assigns a name to the current thread. If no argument is +++given, any existing user-specified name is removed. The thread name +++appears in the @samp{info threads} display. +++ +++On some systems, such as @sc{gnu}/Linux, @value{GDBN} is able to +++determine the name of the thread as given by the OS. On these +++systems, a name specified with @samp{thread name} will override the +++system-give name, and removing the user-specified name will cause +++@value{GDBN} to once again display the system-specified name. +++ +++@kindex thread find +++@cindex search for a thread +++@item thread find [@var{regexp}] +++Search for and display thread ids whose name or @var{systag} +++matches the supplied regular expression. +++ +++As well as being the complement to the @samp{thread name} command, +++this command also allows you to identify a thread by its target +++@var{systag}. For instance, on @sc{gnu}/Linux, the target @var{systag} +++is the LWP id. +++ +++@smallexample +++(@value{GDBN}) thread find 26688 +++Thread 4 has target id 'Thread 0x41e02940 (LWP 26688)' +++(@value{GDBN}) info thread 4 +++ Id Target Id Frame +++ 4 Thread 0x41e02940 (LWP 26688) 0x00000031ca6cd372 in select () +++@end smallexample +++ +++@kindex set print thread-events +++@cindex print messages on thread start and exit +++@item set print thread-events +++@itemx set print thread-events on +++@itemx set print thread-events off +++The @code{set print thread-events} command allows you to enable or +++disable printing of messages when @value{GDBN} notices that new threads have +++started or that threads have exited. By default, these messages will +++be printed if detection of these events is supported by the target. +++Note that these messages cannot be disabled on all targets. +++ +++@kindex show print thread-events +++@item show print thread-events +++Show whether messages will be printed when @value{GDBN} detects that threads +++have started and exited. +++@end table +++ +++@xref{Thread Stops,,Stopping and Starting Multi-thread Programs}, for +++more information about how @value{GDBN} behaves when you stop and start +++programs with multiple threads. +++ +++@xref{Set Watchpoints,,Setting Watchpoints}, for information about +++watchpoints in programs with multiple threads. +++ +++@anchor{set libthread-db-search-path} +++@table @code +++@kindex set libthread-db-search-path +++@cindex search path for @code{libthread_db} +++@item set libthread-db-search-path @r{[}@var{path}@r{]} +++If this variable is set, @var{path} is a colon-separated list of +++directories @value{GDBN} will use to search for @code{libthread_db}. +++If you omit @var{path}, @samp{libthread-db-search-path} will be reset to +++its default value (@code{$sdir:$pdir} on @sc{gnu}/Linux and Solaris systems). +++Internally, the default value comes from the @code{LIBTHREAD_DB_SEARCH_PATH} +++macro. +++ +++On @sc{gnu}/Linux and Solaris systems, @value{GDBN} uses a ``helper'' +++@code{libthread_db} library to obtain information about threads in the +++inferior process. @value{GDBN} will use @samp{libthread-db-search-path} +++to find @code{libthread_db}. @value{GDBN} also consults first if inferior +++specific thread debugging library loading is enabled +++by @samp{set auto-load libthread-db} (@pxref{libthread_db.so.1 file}). +++ +++A special entry @samp{$sdir} for @samp{libthread-db-search-path} +++refers to the default system directories that are +++normally searched for loading shared libraries. The @samp{$sdir} entry +++is the only kind not needing to be enabled by @samp{set auto-load libthread-db} +++(@pxref{libthread_db.so.1 file}). +++ +++A special entry @samp{$pdir} for @samp{libthread-db-search-path} +++refers to the directory from which @code{libpthread} +++was loaded in the inferior process. +++ +++For any @code{libthread_db} library @value{GDBN} finds in above directories, +++@value{GDBN} attempts to initialize it with the current inferior process. +++If this initialization fails (which could happen because of a version +++mismatch between @code{libthread_db} and @code{libpthread}), @value{GDBN} +++will unload @code{libthread_db}, and continue with the next directory. +++If none of @code{libthread_db} libraries initialize successfully, +++@value{GDBN} will issue a warning and thread debugging will be disabled. +++ +++Setting @code{libthread-db-search-path} is currently implemented +++only on some platforms. +++ +++@kindex show libthread-db-search-path +++@item show libthread-db-search-path +++Display current libthread_db search path. +++ +++@kindex set debug libthread-db +++@kindex show debug libthread-db +++@cindex debugging @code{libthread_db} +++@item set debug libthread-db +++@itemx show debug libthread-db +++Turns on or off display of @code{libthread_db}-related events. +++Use @code{1} to enable, @code{0} to disable. +++@end table +++ +++@node Forks +++@section Debugging Forks +++ +++@cindex fork, debugging programs which call +++@cindex multiple processes +++@cindex processes, multiple +++On most systems, @value{GDBN} has no special support for debugging +++programs which create additional processes using the @code{fork} +++function. When a program forks, @value{GDBN} will continue to debug the +++parent process and the child process will run unimpeded. If you have +++set a breakpoint in any code which the child then executes, the child +++will get a @code{SIGTRAP} signal which (unless it catches the signal) +++will cause it to terminate. +++ +++However, if you want to debug the child process there is a workaround +++which isn't too painful. Put a call to @code{sleep} in the code which +++the child process executes after the fork. It may be useful to sleep +++only if a certain environment variable is set, or a certain file exists, +++so that the delay need not occur when you don't want to run @value{GDBN} +++on the child. While the child is sleeping, use the @code{ps} program to +++get its process ID. Then tell @value{GDBN} (a new invocation of +++@value{GDBN} if you are also debugging the parent process) to attach to +++the child process (@pxref{Attach}). From that point on you can debug +++the child process just like any other process which you attached to. +++ +++On some systems, @value{GDBN} provides support for debugging programs +++that create additional processes using the @code{fork} or @code{vfork} +++functions. On @sc{gnu}/Linux platforms, this feature is supported +++with kernel version 2.5.46 and later. +++ +++The fork debugging commands are supported in native mode and when +++connected to @code{gdbserver} in either @code{target remote} mode or +++@code{target extended-remote} mode. +++ +++By default, when a program forks, @value{GDBN} will continue to debug +++the parent process and the child process will run unimpeded. +++ +++If you want to follow the child process instead of the parent process, +++use the command @w{@code{set follow-fork-mode}}. +++ +++@table @code +++@kindex set follow-fork-mode +++@item set follow-fork-mode @var{mode} +++Set the debugger response to a program call of @code{fork} or +++@code{vfork}. A call to @code{fork} or @code{vfork} creates a new +++process. The @var{mode} argument can be: +++ +++@table @code +++@item parent +++The original process is debugged after a fork. The child process runs +++unimpeded. This is the default. +++ +++@item child +++The new process is debugged after a fork. The parent process runs +++unimpeded. +++ +++@end table +++ +++@kindex show follow-fork-mode +++@item show follow-fork-mode +++Display the current debugger response to a @code{fork} or @code{vfork} call. +++@end table +++ +++@cindex debugging multiple processes +++On Linux, if you want to debug both the parent and child processes, use the +++command @w{@code{set detach-on-fork}}. +++ +++@table @code +++@kindex set detach-on-fork +++@item set detach-on-fork @var{mode} +++Tells gdb whether to detach one of the processes after a fork, or +++retain debugger control over them both. +++ +++@table @code +++@item on +++The child process (or parent process, depending on the value of +++@code{follow-fork-mode}) will be detached and allowed to run +++independently. This is the default. +++ +++@item off +++Both processes will be held under the control of @value{GDBN}. +++One process (child or parent, depending on the value of +++@code{follow-fork-mode}) is debugged as usual, while the other +++is held suspended. +++ +++@end table +++ +++@kindex show detach-on-fork +++@item show detach-on-fork +++Show whether detach-on-fork mode is on/off. +++@end table +++ +++If you choose to set @samp{detach-on-fork} mode off, then @value{GDBN} +++will retain control of all forked processes (including nested forks). +++You can list the forked processes under the control of @value{GDBN} by +++using the @w{@code{info inferiors}} command, and switch from one fork +++to another by using the @code{inferior} command (@pxref{Inferiors Connections and +++Programs, ,Debugging Multiple Inferiors Connections and Programs}). +++ +++To quit debugging one of the forked processes, you can either detach +++from it by using the @w{@code{detach inferiors}} command (allowing it +++to run independently), or kill it using the @w{@code{kill inferiors}} +++command. @xref{Inferiors Connections and Programs, ,Debugging +++Multiple Inferiors Connections and Programs}. +++ +++If you ask to debug a child process and a @code{vfork} is followed by an +++@code{exec}, @value{GDBN} executes the new target up to the first +++breakpoint in the new target. If you have a breakpoint set on +++@code{main} in your original program, the breakpoint will also be set on +++the child process's @code{main}. +++ +++On some systems, when a child process is spawned by @code{vfork}, you +++cannot debug the child or parent until an @code{exec} call completes. +++ +++If you issue a @code{run} command to @value{GDBN} after an @code{exec} +++call executes, the new target restarts. To restart the parent +++process, use the @code{file} command with the parent executable name +++as its argument. By default, after an @code{exec} call executes, +++@value{GDBN} discards the symbols of the previous executable image. +++You can change this behaviour with the @w{@code{set follow-exec-mode}} +++command. +++ +++@table @code +++@kindex set follow-exec-mode +++@item set follow-exec-mode @var{mode} +++ +++Set debugger response to a program call of @code{exec}. An +++@code{exec} call replaces the program image of a process. +++ +++@code{follow-exec-mode} can be: +++ +++@table @code +++@item new +++@value{GDBN} creates a new inferior and rebinds the process to this +++new inferior. The program the process was running before the +++@code{exec} call can be restarted afterwards by restarting the +++original inferior. +++ +++For example: +++ +++@smallexample +++(@value{GDBP}) info inferiors +++(gdb) info inferior +++ Id Description Executable +++* 1 prog1 +++(@value{GDBP}) run +++process 12020 is executing new program: prog2 +++Program exited normally. +++(@value{GDBP}) info inferiors +++ Id Description Executable +++ 1 prog1 +++* 2 prog2 +++@end smallexample +++ +++@item same +++@value{GDBN} keeps the process bound to the same inferior. The new +++executable image replaces the previous executable loaded in the +++inferior. Restarting the inferior after the @code{exec} call, with +++e.g., the @code{run} command, restarts the executable the process was +++running after the @code{exec} call. This is the default mode. +++ +++For example: +++ +++@smallexample +++(@value{GDBP}) info inferiors +++ Id Description Executable +++* 1 prog1 +++(@value{GDBP}) run +++process 12020 is executing new program: prog2 +++Program exited normally. +++(@value{GDBP}) info inferiors +++ Id Description Executable +++* 1 prog2 +++@end smallexample +++ +++@end table +++@end table +++ +++@code{follow-exec-mode} is supported in native mode and +++@code{target extended-remote} mode. +++ +++You can use the @code{catch} command to make @value{GDBN} stop whenever +++a @code{fork}, @code{vfork}, or @code{exec} call is made. @xref{Set +++Catchpoints, ,Setting Catchpoints}. +++ +++@node Checkpoint/Restart +++@section Setting a @emph{Bookmark} to Return to Later +++ +++@cindex checkpoint +++@cindex restart +++@cindex bookmark +++@cindex snapshot of a process +++@cindex rewind program state +++ +++On certain operating systems@footnote{Currently, only +++@sc{gnu}/Linux.}, @value{GDBN} is able to save a @dfn{snapshot} of a +++program's state, called a @dfn{checkpoint}, and come back to it +++later. +++ +++Returning to a checkpoint effectively undoes everything that has +++happened in the program since the @code{checkpoint} was saved. This +++includes changes in memory, registers, and even (within some limits) +++system state. Effectively, it is like going back in time to the +++moment when the checkpoint was saved. +++ +++Thus, if you're stepping thru a program and you think you're +++getting close to the point where things go wrong, you can save +++a checkpoint. Then, if you accidentally go too far and miss +++the critical statement, instead of having to restart your program +++from the beginning, you can just go back to the checkpoint and +++start again from there. +++ +++This can be especially useful if it takes a lot of time or +++steps to reach the point where you think the bug occurs. +++ +++To use the @code{checkpoint}/@code{restart} method of debugging: +++ +++@table @code +++@kindex checkpoint +++@item checkpoint +++Save a snapshot of the debugged program's current execution state. +++The @code{checkpoint} command takes no arguments, but each checkpoint +++is assigned a small integer id, similar to a breakpoint id. +++ +++@kindex info checkpoints +++@item info checkpoints +++List the checkpoints that have been saved in the current debugging +++session. For each checkpoint, the following information will be +++listed: +++ +++@table @code +++@item Checkpoint ID +++@item Process ID +++@item Code Address +++@item Source line, or label +++@end table +++ +++@kindex restart @var{checkpoint-id} +++@item restart @var{checkpoint-id} +++Restore the program state that was saved as checkpoint number +++@var{checkpoint-id}. All program variables, registers, stack frames +++etc.@: will be returned to the values that they had when the checkpoint +++was saved. In essence, gdb will ``wind back the clock'' to the point +++in time when the checkpoint was saved. +++ +++Note that breakpoints, @value{GDBN} variables, command history etc. +++are not affected by restoring a checkpoint. In general, a checkpoint +++only restores things that reside in the program being debugged, not in +++the debugger. +++ +++@kindex delete checkpoint @var{checkpoint-id} +++@item delete checkpoint @var{checkpoint-id} +++Delete the previously-saved checkpoint identified by @var{checkpoint-id}. +++ +++@end table +++ +++Returning to a previously saved checkpoint will restore the user state +++of the program being debugged, plus a significant subset of the system +++(OS) state, including file pointers. It won't ``un-write'' data from +++a file, but it will rewind the file pointer to the previous location, +++so that the previously written data can be overwritten. For files +++opened in read mode, the pointer will also be restored so that the +++previously read data can be read again. +++ +++Of course, characters that have been sent to a printer (or other +++external device) cannot be ``snatched back'', and characters received +++from eg.@: a serial device can be removed from internal program buffers, +++but they cannot be ``pushed back'' into the serial pipeline, ready to +++be received again. Similarly, the actual contents of files that have +++been changed cannot be restored (at this time). +++ +++However, within those constraints, you actually can ``rewind'' your +++program to a previously saved point in time, and begin debugging it +++again --- and you can change the course of events so as to debug a +++different execution path this time. +++ +++@cindex checkpoints and process id +++Finally, there is one bit of internal program state that will be +++different when you return to a checkpoint --- the program's process +++id. Each checkpoint will have a unique process id (or @var{pid}), +++and each will be different from the program's original @var{pid}. +++If your program has saved a local copy of its process id, this could +++potentially pose a problem. +++ +++@subsection A Non-obvious Benefit of Using Checkpoints +++ +++On some systems such as @sc{gnu}/Linux, address space randomization +++is performed on new processes for security reasons. This makes it +++difficult or impossible to set a breakpoint, or watchpoint, on an +++absolute address if you have to restart the program, since the +++absolute location of a symbol will change from one execution to the +++next. +++ +++A checkpoint, however, is an @emph{identical} copy of a process. +++Therefore if you create a checkpoint at (eg.@:) the start of main, +++and simply return to that checkpoint instead of restarting the +++process, you can avoid the effects of address randomization and +++your symbols will all stay in the same place. +++ +++@node Stopping +++@chapter Stopping and Continuing +++ +++The principal purposes of using a debugger are so that you can stop your +++program before it terminates; or so that, if your program runs into +++trouble, you can investigate and find out why. +++ +++Inside @value{GDBN}, your program may stop for any of several reasons, +++such as a signal, a breakpoint, or reaching a new line after a +++@value{GDBN} command such as @code{step}. You may then examine and +++change variables, set new breakpoints or remove old ones, and then +++continue execution. Usually, the messages shown by @value{GDBN} provide +++ample explanation of the status of your program---but you can also +++explicitly request this information at any time. +++ +++@table @code +++@kindex info program +++@item info program +++Display information about the status of your program: whether it is +++running or not, what process it is, and why it stopped. +++@end table +++ +++@menu +++* Breakpoints:: Breakpoints, watchpoints, and catchpoints +++* Continuing and Stepping:: Resuming execution +++* Skipping Over Functions and Files:: +++ Skipping over functions and files +++* Signals:: Signals +++* Thread Stops:: Stopping and starting multi-thread programs +++@end menu +++ +++@node Breakpoints +++@section Breakpoints, Watchpoints, and Catchpoints +++ +++@cindex breakpoints +++A @dfn{breakpoint} makes your program stop whenever a certain point in +++the program is reached. For each breakpoint, you can add conditions to +++control in finer detail whether your program stops. You can set +++breakpoints with the @code{break} command and its variants (@pxref{Set +++Breaks, ,Setting Breakpoints}), to specify the place where your program +++should stop by line number, function name or exact address in the +++program. +++ +++On some systems, you can set breakpoints in shared libraries before +++the executable is run. +++ +++@cindex watchpoints +++@cindex data breakpoints +++@cindex memory tracing +++@cindex breakpoint on memory address +++@cindex breakpoint on variable modification +++A @dfn{watchpoint} is a special breakpoint that stops your program +++when the value of an expression changes. The expression may be a value +++of a variable, or it could involve values of one or more variables +++combined by operators, such as @samp{a + b}. This is sometimes called +++@dfn{data breakpoints}. You must use a different command to set +++watchpoints (@pxref{Set Watchpoints, ,Setting Watchpoints}), but aside +++from that, you can manage a watchpoint like any other breakpoint: you +++enable, disable, and delete both breakpoints and watchpoints using the +++same commands. +++ +++You can arrange to have values from your program displayed automatically +++whenever @value{GDBN} stops at a breakpoint. @xref{Auto Display,, +++Automatic Display}. +++ +++@cindex catchpoints +++@cindex breakpoint on events +++A @dfn{catchpoint} is another special breakpoint that stops your program +++when a certain kind of event occurs, such as the throwing of a C@t{++} +++exception or the loading of a library. As with watchpoints, you use a +++different command to set a catchpoint (@pxref{Set Catchpoints, ,Setting +++Catchpoints}), but aside from that, you can manage a catchpoint like any +++other breakpoint. (To stop when your program receives a signal, use the +++@code{handle} command; see @ref{Signals, ,Signals}.) +++ +++@cindex breakpoint numbers +++@cindex numbers for breakpoints +++@value{GDBN} assigns a number to each breakpoint, watchpoint, or +++catchpoint when you create it; these numbers are successive integers +++starting with one. In many of the commands for controlling various +++features of breakpoints you use the breakpoint number to say which +++breakpoint you want to change. Each breakpoint may be @dfn{enabled} or +++@dfn{disabled}; if disabled, it has no effect on your program until you +++enable it again. +++ +++@cindex breakpoint ranges +++@cindex breakpoint lists +++@cindex ranges of breakpoints +++@cindex lists of breakpoints +++Some @value{GDBN} commands accept a space-separated list of breakpoints +++on which to operate. A list element can be either a single breakpoint number, +++like @samp{5}, or a range of such numbers, like @samp{5-7}. +++When a breakpoint list is given to a command, all breakpoints in that list +++are operated on. +++ +++@menu +++* Set Breaks:: Setting breakpoints +++* Set Watchpoints:: Setting watchpoints +++* Set Catchpoints:: Setting catchpoints +++* Delete Breaks:: Deleting breakpoints +++* Disabling:: Disabling breakpoints +++* Conditions:: Break conditions +++* Break Commands:: Breakpoint command lists +++* Dynamic Printf:: Dynamic printf +++* Save Breakpoints:: How to save breakpoints in a file +++* Static Probe Points:: Listing static probe points +++* Error in Breakpoints:: ``Cannot insert breakpoints'' +++* Breakpoint-related Warnings:: ``Breakpoint address adjusted...'' +++@end menu +++ +++@node Set Breaks +++@subsection Setting Breakpoints +++ +++@c FIXME LMB what does GDB do if no code on line of breakpt? +++@c consider in particular declaration with/without initialization. +++@c +++@c FIXME 2 is there stuff on this already? break at fun start, already init? +++ +++@kindex break +++@kindex b @r{(@code{break})} +++@vindex $bpnum@r{, convenience variable} +++@cindex latest breakpoint +++Breakpoints are set with the @code{break} command (abbreviated +++@code{b}). The debugger convenience variable @samp{$bpnum} records the +++number of the breakpoint you've set most recently; see @ref{Convenience +++Vars,, Convenience Variables}, for a discussion of what you can do with +++convenience variables. +++ +++@table @code +++@item break @var{location} +++Set a breakpoint at the given @var{location}, which can specify a +++function name, a line number, or an address of an instruction. +++(@xref{Specify Location}, for a list of all the possible ways to +++specify a @var{location}.) The breakpoint will stop your program just +++before it executes any of the code in the specified @var{location}. +++ +++When using source languages that permit overloading of symbols, such as +++C@t{++}, a function name may refer to more than one possible place to break. +++@xref{Ambiguous Expressions,,Ambiguous Expressions}, for a discussion of +++that situation. +++ +++It is also possible to insert a breakpoint that will stop the program +++only if a specific thread (@pxref{Thread-Specific Breakpoints}) +++or a specific task (@pxref{Ada Tasks}) hits that breakpoint. +++ +++@item break +++When called without any arguments, @code{break} sets a breakpoint at +++the next instruction to be executed in the selected stack frame +++(@pxref{Stack, ,Examining the Stack}). In any selected frame but the +++innermost, this makes your program stop as soon as control +++returns to that frame. This is similar to the effect of a +++@code{finish} command in the frame inside the selected frame---except +++that @code{finish} does not leave an active breakpoint. If you use +++@code{break} without an argument in the innermost frame, @value{GDBN} stops +++the next time it reaches the current location; this may be useful +++inside loops. +++ +++@value{GDBN} normally ignores breakpoints when it resumes execution, until at +++least one instruction has been executed. If it did not do this, you +++would be unable to proceed past a breakpoint without first disabling the +++breakpoint. This rule applies whether or not the breakpoint already +++existed when your program stopped. +++ +++@item break @dots{} if @var{cond} +++Set a breakpoint with condition @var{cond}; evaluate the expression +++@var{cond} each time the breakpoint is reached, and stop only if the +++value is nonzero---that is, if @var{cond} evaluates as true. +++@samp{@dots{}} stands for one of the possible arguments described +++above (or no argument) specifying where to break. @xref{Conditions, +++,Break Conditions}, for more information on breakpoint conditions. +++ +++@kindex tbreak +++@item tbreak @var{args} +++Set a breakpoint enabled only for one stop. The @var{args} are the +++same as for the @code{break} command, and the breakpoint is set in the same +++way, but the breakpoint is automatically deleted after the first time your +++program stops there. @xref{Disabling, ,Disabling Breakpoints}. +++ +++@kindex hbreak +++@cindex hardware breakpoints +++@item hbreak @var{args} +++Set a hardware-assisted breakpoint. The @var{args} are the same as for the +++@code{break} command and the breakpoint is set in the same way, but the +++breakpoint requires hardware support and some target hardware may not +++have this support. The main purpose of this is EPROM/ROM code +++debugging, so you can set a breakpoint at an instruction without +++changing the instruction. This can be used with the new trap-generation +++provided by SPARClite DSU and most x86-based targets. These targets +++will generate traps when a program accesses some data or instruction +++address that is assigned to the debug registers. However the hardware +++breakpoint registers can take a limited number of breakpoints. For +++example, on the DSU, only two data breakpoints can be set at a time, and +++@value{GDBN} will reject this command if more than two are used. Delete +++or disable unused hardware breakpoints before setting new ones +++(@pxref{Disabling, ,Disabling Breakpoints}). +++@xref{Conditions, ,Break Conditions}. +++For remote targets, you can restrict the number of hardware +++breakpoints @value{GDBN} will use, see @ref{set remote +++hardware-breakpoint-limit}. +++ +++@kindex thbreak +++@item thbreak @var{args} +++Set a hardware-assisted breakpoint enabled only for one stop. The @var{args} +++are the same as for the @code{hbreak} command and the breakpoint is set in +++the same way. However, like the @code{tbreak} command, +++the breakpoint is automatically deleted after the +++first time your program stops there. Also, like the @code{hbreak} +++command, the breakpoint requires hardware support and some target hardware +++may not have this support. @xref{Disabling, ,Disabling Breakpoints}. +++See also @ref{Conditions, ,Break Conditions}. +++ +++@kindex rbreak +++@cindex regular expression +++@cindex breakpoints at functions matching a regexp +++@cindex set breakpoints in many functions +++@item rbreak @var{regex} +++Set breakpoints on all functions matching the regular expression +++@var{regex}. This command sets an unconditional breakpoint on all +++matches, printing a list of all breakpoints it set. Once these +++breakpoints are set, they are treated just like the breakpoints set with +++the @code{break} command. You can delete them, disable them, or make +++them conditional the same way as any other breakpoint. +++ +++In programs using different languages, @value{GDBN} chooses the syntax +++to print the list of all breakpoints it sets according to the +++@samp{set language} value: using @samp{set language auto} +++(see @ref{Automatically, ,Set Language Automatically}) means to use the +++language of the breakpoint's function, other values mean to use +++the manually specified language (see @ref{Manually, ,Set Language Manually}). +++ +++The syntax of the regular expression is the standard one used with tools +++like @file{grep}. Note that this is different from the syntax used by +++shells, so for instance @code{foo*} matches all functions that include +++an @code{fo} followed by zero or more @code{o}s. There is an implicit +++@code{.*} leading and trailing the regular expression you supply, so to +++match only functions that begin with @code{foo}, use @code{^foo}. +++ +++@cindex non-member C@t{++} functions, set breakpoint in +++When debugging C@t{++} programs, @code{rbreak} is useful for setting +++breakpoints on overloaded functions that are not members of any special +++classes. +++ +++@cindex set breakpoints on all functions +++The @code{rbreak} command can be used to set breakpoints in +++@strong{all} the functions in a program, like this: +++ +++@smallexample +++(@value{GDBP}) rbreak . +++@end smallexample +++ +++@item rbreak @var{file}:@var{regex} +++If @code{rbreak} is called with a filename qualification, it limits +++the search for functions matching the given regular expression to the +++specified @var{file}. This can be used, for example, to set breakpoints on +++every function in a given file: +++ +++@smallexample +++(@value{GDBP}) rbreak file.c:. +++@end smallexample +++ +++The colon separating the filename qualifier from the regex may +++optionally be surrounded by spaces. +++ +++@kindex info breakpoints +++@cindex @code{$_} and @code{info breakpoints} +++@item info breakpoints @r{[}@var{list}@dots{}@r{]} +++@itemx info break @r{[}@var{list}@dots{}@r{]} +++Print a table of all breakpoints, watchpoints, and catchpoints set and +++not deleted. Optional argument @var{n} means print information only +++about the specified breakpoint(s) (or watchpoint(s) or catchpoint(s)). +++For each breakpoint, following columns are printed: +++ +++@table @emph +++@item Breakpoint Numbers +++@item Type +++Breakpoint, watchpoint, or catchpoint. +++@item Disposition +++Whether the breakpoint is marked to be disabled or deleted when hit. +++@item Enabled or Disabled +++Enabled breakpoints are marked with @samp{y}. @samp{n} marks breakpoints +++that are not enabled. +++@item Address +++Where the breakpoint is in your program, as a memory address. For a +++pending breakpoint whose address is not yet known, this field will +++contain @samp{}. Such breakpoint won't fire until a shared +++library that has the symbol or line referred by breakpoint is loaded. +++See below for details. A breakpoint with several locations will +++have @samp{} in this field---see below for details. +++@item What +++Where the breakpoint is in the source for your program, as a file and +++line number. For a pending breakpoint, the original string passed to +++the breakpoint command will be listed as it cannot be resolved until +++the appropriate shared library is loaded in the future. +++@end table +++ +++@noindent +++If a breakpoint is conditional, there are two evaluation modes: ``host'' and +++``target''. If mode is ``host'', breakpoint condition evaluation is done by +++@value{GDBN} on the host's side. If it is ``target'', then the condition +++is evaluated by the target. The @code{info break} command shows +++the condition on the line following the affected breakpoint, together with +++its condition evaluation mode in between parentheses. +++ +++Breakpoint commands, if any, are listed after that. A pending breakpoint is +++allowed to have a condition specified for it. The condition is not parsed for +++validity until a shared library is loaded that allows the pending +++breakpoint to resolve to a valid location. +++ +++@noindent +++@code{info break} with a breakpoint +++number @var{n} as argument lists only that breakpoint. The +++convenience variable @code{$_} and the default examining-address for +++the @code{x} command are set to the address of the last breakpoint +++listed (@pxref{Memory, ,Examining Memory}). +++ +++@noindent +++@code{info break} displays a count of the number of times the breakpoint +++has been hit. This is especially useful in conjunction with the +++@code{ignore} command. You can ignore a large number of breakpoint +++hits, look at the breakpoint info to see how many times the breakpoint +++was hit, and then run again, ignoring one less than that number. This +++will get you quickly to the last hit of that breakpoint. +++ +++@noindent +++For a breakpoints with an enable count (xref) greater than 1, +++@code{info break} also displays that count. +++ +++@end table +++ +++@value{GDBN} allows you to set any number of breakpoints at the same place in +++your program. There is nothing silly or meaningless about this. When +++the breakpoints are conditional, this is even useful +++(@pxref{Conditions, ,Break Conditions}). +++ +++@cindex multiple locations, breakpoints +++@cindex breakpoints, multiple locations +++It is possible that a breakpoint corresponds to several locations +++in your program. Examples of this situation are: +++ +++@itemize @bullet +++@item +++Multiple functions in the program may have the same name. +++ +++@item +++For a C@t{++} constructor, the @value{NGCC} compiler generates several +++instances of the function body, used in different cases. +++ +++@item +++For a C@t{++} template function, a given line in the function can +++correspond to any number of instantiations. +++ +++@item +++For an inlined function, a given source line can correspond to +++several places where that function is inlined. +++@end itemize +++ +++In all those cases, @value{GDBN} will insert a breakpoint at all +++the relevant locations. +++ +++A breakpoint with multiple locations is displayed in the breakpoint +++table using several rows---one header row, followed by one row for +++each breakpoint location. The header row has @samp{} in the +++address column. The rows for individual locations contain the actual +++addresses for locations, and show the functions to which those +++locations belong. The number column for a location is of the form +++@var{breakpoint-number}.@var{location-number}. +++ +++For example: +++ +++@smallexample +++Num Type Disp Enb Address What +++1 breakpoint keep y +++ stop only if i==1 +++ breakpoint already hit 1 time +++1.1 y 0x080486a2 in void foo() at t.cc:8 +++1.2 y 0x080486ca in void foo() at t.cc:8 +++@end smallexample +++ +++You cannot delete the individual locations from a breakpoint. However, +++each location can be individually enabled or disabled by passing +++@var{breakpoint-number}.@var{location-number} as argument to the +++@code{enable} and @code{disable} commands. It's also possible to +++@code{enable} and @code{disable} a range of @var{location-number} +++locations using a @var{breakpoint-number} and two @var{location-number}s, +++in increasing order, separated by a hyphen, like +++@kbd{@var{breakpoint-number}.@var{location-number1}-@var{location-number2}}, +++in which case @value{GDBN} acts on all the locations in the range (inclusive). +++Disabling or enabling the parent breakpoint (@pxref{Disabling}) affects +++all of the locations that belong to that breakpoint. +++ +++@cindex pending breakpoints +++It's quite common to have a breakpoint inside a shared library. +++Shared libraries can be loaded and unloaded explicitly, +++and possibly repeatedly, as the program is executed. To support +++this use case, @value{GDBN} updates breakpoint locations whenever +++any shared library is loaded or unloaded. Typically, you would +++set a breakpoint in a shared library at the beginning of your +++debugging session, when the library is not loaded, and when the +++symbols from the library are not available. When you try to set +++breakpoint, @value{GDBN} will ask you if you want to set +++a so called @dfn{pending breakpoint}---breakpoint whose address +++is not yet resolved. +++ +++After the program is run, whenever a new shared library is loaded, +++@value{GDBN} reevaluates all the breakpoints. When a newly loaded +++shared library contains the symbol or line referred to by some +++pending breakpoint, that breakpoint is resolved and becomes an +++ordinary breakpoint. When a library is unloaded, all breakpoints +++that refer to its symbols or source lines become pending again. +++ +++This logic works for breakpoints with multiple locations, too. For +++example, if you have a breakpoint in a C@t{++} template function, and +++a newly loaded shared library has an instantiation of that template, +++a new location is added to the list of locations for the breakpoint. +++ +++Except for having unresolved address, pending breakpoints do not +++differ from regular breakpoints. You can set conditions or commands, +++enable and disable them and perform other breakpoint operations. +++ +++@value{GDBN} provides some additional commands for controlling what +++happens when the @samp{break} command cannot resolve breakpoint +++address specification to an address: +++ +++@kindex set breakpoint pending +++@kindex show breakpoint pending +++@table @code +++@item set breakpoint pending auto +++This is the default behavior. When @value{GDBN} cannot find the breakpoint +++location, it queries you whether a pending breakpoint should be created. +++ +++@item set breakpoint pending on +++This indicates that an unrecognized breakpoint location should automatically +++result in a pending breakpoint being created. +++ +++@item set breakpoint pending off +++This indicates that pending breakpoints are not to be created. Any +++unrecognized breakpoint location results in an error. This setting does +++not affect any pending breakpoints previously created. +++ +++@item show breakpoint pending +++Show the current behavior setting for creating pending breakpoints. +++@end table +++ +++The settings above only affect the @code{break} command and its +++variants. Once breakpoint is set, it will be automatically updated +++as shared libraries are loaded and unloaded. +++ +++@cindex automatic hardware breakpoints +++For some targets, @value{GDBN} can automatically decide if hardware or +++software breakpoints should be used, depending on whether the +++breakpoint address is read-only or read-write. This applies to +++breakpoints set with the @code{break} command as well as to internal +++breakpoints set by commands like @code{next} and @code{finish}. For +++breakpoints set with @code{hbreak}, @value{GDBN} will always use hardware +++breakpoints. +++ +++You can control this automatic behaviour with the following commands: +++ +++@kindex set breakpoint auto-hw +++@kindex show breakpoint auto-hw +++@table @code +++@item set breakpoint auto-hw on +++This is the default behavior. When @value{GDBN} sets a breakpoint, it +++will try to use the target memory map to decide if software or hardware +++breakpoint must be used. +++ +++@item set breakpoint auto-hw off +++This indicates @value{GDBN} should not automatically select breakpoint +++type. If the target provides a memory map, @value{GDBN} will warn when +++trying to set software breakpoint at a read-only address. +++@end table +++ +++@value{GDBN} normally implements breakpoints by replacing the program code +++at the breakpoint address with a special instruction, which, when +++executed, given control to the debugger. By default, the program +++code is so modified only when the program is resumed. As soon as +++the program stops, @value{GDBN} restores the original instructions. This +++behaviour guards against leaving breakpoints inserted in the +++target should gdb abrubptly disconnect. However, with slow remote +++targets, inserting and removing breakpoint can reduce the performance. +++This behavior can be controlled with the following commands:: +++ +++@kindex set breakpoint always-inserted +++@kindex show breakpoint always-inserted +++@table @code +++@item set breakpoint always-inserted off +++All breakpoints, including newly added by the user, are inserted in +++the target only when the target is resumed. All breakpoints are +++removed from the target when it stops. This is the default mode. +++ +++@item set breakpoint always-inserted on +++Causes all breakpoints to be inserted in the target at all times. If +++the user adds a new breakpoint, or changes an existing breakpoint, the +++breakpoints in the target are updated immediately. A breakpoint is +++removed from the target only when breakpoint itself is deleted. +++@end table +++ +++@value{GDBN} handles conditional breakpoints by evaluating these conditions +++when a breakpoint breaks. If the condition is true, then the process being +++debugged stops, otherwise the process is resumed. +++ +++If the target supports evaluating conditions on its end, @value{GDBN} may +++download the breakpoint, together with its conditions, to it. +++ +++This feature can be controlled via the following commands: +++ +++@kindex set breakpoint condition-evaluation +++@kindex show breakpoint condition-evaluation +++@table @code +++@item set breakpoint condition-evaluation host +++This option commands @value{GDBN} to evaluate the breakpoint +++conditions on the host's side. Unconditional breakpoints are sent to +++the target which in turn receives the triggers and reports them back to GDB +++for condition evaluation. This is the standard evaluation mode. +++ +++@item set breakpoint condition-evaluation target +++This option commands @value{GDBN} to download breakpoint conditions +++to the target at the moment of their insertion. The target +++is responsible for evaluating the conditional expression and reporting +++breakpoint stop events back to @value{GDBN} whenever the condition +++is true. Due to limitations of target-side evaluation, some conditions +++cannot be evaluated there, e.g., conditions that depend on local data +++that is only known to the host. Examples include +++conditional expressions involving convenience variables, complex types +++that cannot be handled by the agent expression parser and expressions +++that are too long to be sent over to the target, specially when the +++target is a remote system. In these cases, the conditions will be +++evaluated by @value{GDBN}. +++ +++@item set breakpoint condition-evaluation auto +++This is the default mode. If the target supports evaluating breakpoint +++conditions on its end, @value{GDBN} will download breakpoint conditions to +++the target (limitations mentioned previously apply). If the target does +++not support breakpoint condition evaluation, then @value{GDBN} will fallback +++to evaluating all these conditions on the host's side. +++@end table +++ +++ +++@cindex negative breakpoint numbers +++@cindex internal @value{GDBN} breakpoints +++@value{GDBN} itself sometimes sets breakpoints in your program for +++special purposes, such as proper handling of @code{longjmp} (in C +++programs). These internal breakpoints are assigned negative numbers, +++starting with @code{-1}; @samp{info breakpoints} does not display them. +++You can see these breakpoints with the @value{GDBN} maintenance command +++@samp{maint info breakpoints} (@pxref{maint info breakpoints}). +++ +++ +++@node Set Watchpoints +++@subsection Setting Watchpoints +++ +++@cindex setting watchpoints +++You can use a watchpoint to stop execution whenever the value of an +++expression changes, without having to predict a particular place where +++this may happen. (This is sometimes called a @dfn{data breakpoint}.) +++The expression may be as simple as the value of a single variable, or +++as complex as many variables combined by operators. Examples include: +++ +++@itemize @bullet +++@item +++A reference to the value of a single variable. +++ +++@item +++An address cast to an appropriate data type. For example, +++@samp{*(int *)0x12345678} will watch a 4-byte region at the specified +++address (assuming an @code{int} occupies 4 bytes). +++ +++@item +++An arbitrarily complex expression, such as @samp{a*b + c/d}. The +++expression can use any operators valid in the program's native +++language (@pxref{Languages}). +++@end itemize +++ +++You can set a watchpoint on an expression even if the expression can +++not be evaluated yet. For instance, you can set a watchpoint on +++@samp{*global_ptr} before @samp{global_ptr} is initialized. +++@value{GDBN} will stop when your program sets @samp{global_ptr} and +++the expression produces a valid value. If the expression becomes +++valid in some other way than changing a variable (e.g.@: if the memory +++pointed to by @samp{*global_ptr} becomes readable as the result of a +++@code{malloc} call), @value{GDBN} may not stop until the next time +++the expression changes. +++ +++@cindex software watchpoints +++@cindex hardware watchpoints +++Depending on your system, watchpoints may be implemented in software or +++hardware. @value{GDBN} does software watchpointing by single-stepping your +++program and testing the variable's value each time, which is hundreds of +++times slower than normal execution. (But this may still be worth it, to +++catch errors where you have no clue what part of your program is the +++culprit.) +++ +++On some systems, such as most PowerPC or x86-based targets, +++@value{GDBN} includes support for hardware watchpoints, which do not +++slow down the running of your program. +++ +++@table @code +++@kindex watch +++@item watch @r{[}-l@r{|}-location@r{]} @var{expr} @r{[}thread @var{thread-id}@r{]} @r{[}mask @var{maskvalue}@r{]} +++Set a watchpoint for an expression. @value{GDBN} will break when the +++expression @var{expr} is written into by the program and its value +++changes. The simplest (and the most popular) use of this command is +++to watch the value of a single variable: +++ +++@smallexample +++(@value{GDBP}) watch foo +++@end smallexample +++ +++If the command includes a @code{@r{[}thread @var{thread-id}@r{]}} +++argument, @value{GDBN} breaks only when the thread identified by +++@var{thread-id} changes the value of @var{expr}. If any other threads +++change the value of @var{expr}, @value{GDBN} will not break. Note +++that watchpoints restricted to a single thread in this way only work +++with Hardware Watchpoints. +++ +++Ordinarily a watchpoint respects the scope of variables in @var{expr} +++(see below). The @code{-location} argument tells @value{GDBN} to +++instead watch the memory referred to by @var{expr}. In this case, +++@value{GDBN} will evaluate @var{expr}, take the address of the result, +++and watch the memory at that address. The type of the result is used +++to determine the size of the watched memory. If the expression's +++result does not have an address, then @value{GDBN} will print an +++error. +++ +++The @code{@r{[}mask @var{maskvalue}@r{]}} argument allows creation +++of masked watchpoints, if the current architecture supports this +++feature (e.g., PowerPC Embedded architecture, see @ref{PowerPC +++Embedded}.) A @dfn{masked watchpoint} specifies a mask in addition +++to an address to watch. The mask specifies that some bits of an address +++(the bits which are reset in the mask) should be ignored when matching +++the address accessed by the inferior against the watchpoint address. +++Thus, a masked watchpoint watches many addresses simultaneously---those +++addresses whose unmasked bits are identical to the unmasked bits in the +++watchpoint address. The @code{mask} argument implies @code{-location}. +++Examples: +++ +++@smallexample +++(@value{GDBP}) watch foo mask 0xffff00ff +++(@value{GDBP}) watch *0xdeadbeef mask 0xffffff00 +++@end smallexample +++ +++@kindex rwatch +++@item rwatch @r{[}-l@r{|}-location@r{]} @var{expr} @r{[}thread @var{thread-id}@r{]} @r{[}mask @var{maskvalue}@r{]} +++Set a watchpoint that will break when the value of @var{expr} is read +++by the program. +++ +++@kindex awatch +++@item awatch @r{[}-l@r{|}-location@r{]} @var{expr} @r{[}thread @var{thread-id}@r{]} @r{[}mask @var{maskvalue}@r{]} +++Set a watchpoint that will break when @var{expr} is either read from +++or written into by the program. +++ +++@kindex info watchpoints @r{[}@var{list}@dots{}@r{]} +++@item info watchpoints @r{[}@var{list}@dots{}@r{]} +++This command prints a list of watchpoints, using the same format as +++@code{info break} (@pxref{Set Breaks}). +++@end table +++ +++If you watch for a change in a numerically entered address you need to +++dereference it, as the address itself is just a constant number which will +++never change. @value{GDBN} refuses to create a watchpoint that watches +++a never-changing value: +++ +++@smallexample +++(@value{GDBP}) watch 0x600850 +++Cannot watch constant value 0x600850. +++(@value{GDBP}) watch *(int *) 0x600850 +++Watchpoint 1: *(int *) 6293584 +++@end smallexample +++ +++@value{GDBN} sets a @dfn{hardware watchpoint} if possible. Hardware +++watchpoints execute very quickly, and the debugger reports a change in +++value at the exact instruction where the change occurs. If @value{GDBN} +++cannot set a hardware watchpoint, it sets a software watchpoint, which +++executes more slowly and reports the change in value at the next +++@emph{statement}, not the instruction, after the change occurs. +++ +++@cindex use only software watchpoints +++You can force @value{GDBN} to use only software watchpoints with the +++@kbd{set can-use-hw-watchpoints 0} command. With this variable set to +++zero, @value{GDBN} will never try to use hardware watchpoints, even if +++the underlying system supports them. (Note that hardware-assisted +++watchpoints that were set @emph{before} setting +++@code{can-use-hw-watchpoints} to zero will still use the hardware +++mechanism of watching expression values.) +++ +++@table @code +++@item set can-use-hw-watchpoints +++@kindex set can-use-hw-watchpoints +++Set whether or not to use hardware watchpoints. +++ +++@item show can-use-hw-watchpoints +++@kindex show can-use-hw-watchpoints +++Show the current mode of using hardware watchpoints. +++@end table +++ +++For remote targets, you can restrict the number of hardware +++watchpoints @value{GDBN} will use, see @ref{set remote +++hardware-breakpoint-limit}. +++ +++When you issue the @code{watch} command, @value{GDBN} reports +++ +++@smallexample +++Hardware watchpoint @var{num}: @var{expr} +++@end smallexample +++ +++@noindent +++if it was able to set a hardware watchpoint. +++ +++Currently, the @code{awatch} and @code{rwatch} commands can only set +++hardware watchpoints, because accesses to data that don't change the +++value of the watched expression cannot be detected without examining +++every instruction as it is being executed, and @value{GDBN} does not do +++that currently. If @value{GDBN} finds that it is unable to set a +++hardware breakpoint with the @code{awatch} or @code{rwatch} command, it +++will print a message like this: +++ +++@smallexample +++Expression cannot be implemented with read/access watchpoint. +++@end smallexample +++ +++Sometimes, @value{GDBN} cannot set a hardware watchpoint because the +++data type of the watched expression is wider than what a hardware +++watchpoint on the target machine can handle. For example, some systems +++can only watch regions that are up to 4 bytes wide; on such systems you +++cannot set hardware watchpoints for an expression that yields a +++double-precision floating-point number (which is typically 8 bytes +++wide). As a work-around, it might be possible to break the large region +++into a series of smaller ones and watch them with separate watchpoints. +++ +++If you set too many hardware watchpoints, @value{GDBN} might be unable +++to insert all of them when you resume the execution of your program. +++Since the precise number of active watchpoints is unknown until such +++time as the program is about to be resumed, @value{GDBN} might not be +++able to warn you about this when you set the watchpoints, and the +++warning will be printed only when the program is resumed: +++ +++@smallexample +++Hardware watchpoint @var{num}: Could not insert watchpoint +++@end smallexample +++ +++@noindent +++If this happens, delete or disable some of the watchpoints. +++ +++Watching complex expressions that reference many variables can also +++exhaust the resources available for hardware-assisted watchpoints. +++That's because @value{GDBN} needs to watch every variable in the +++expression with separately allocated resources. +++ +++If you call a function interactively using @code{print} or @code{call}, +++any watchpoints you have set will be inactive until @value{GDBN} reaches another +++kind of breakpoint or the call completes. +++ +++@value{GDBN} automatically deletes watchpoints that watch local +++(automatic) variables, or expressions that involve such variables, when +++they go out of scope, that is, when the execution leaves the block in +++which these variables were defined. In particular, when the program +++being debugged terminates, @emph{all} local variables go out of scope, +++and so only watchpoints that watch global variables remain set. If you +++rerun the program, you will need to set all such watchpoints again. One +++way of doing that would be to set a code breakpoint at the entry to the +++@code{main} function and when it breaks, set all the watchpoints. +++ +++@cindex watchpoints and threads +++@cindex threads and watchpoints +++In multi-threaded programs, watchpoints will detect changes to the +++watched expression from every thread. +++ +++@quotation +++@emph{Warning:} In multi-threaded programs, software watchpoints +++have only limited usefulness. If @value{GDBN} creates a software +++watchpoint, it can only watch the value of an expression @emph{in a +++single thread}. If you are confident that the expression can only +++change due to the current thread's activity (and if you are also +++confident that no other thread can become current), then you can use +++software watchpoints as usual. However, @value{GDBN} may not notice +++when a non-current thread's activity changes the expression. (Hardware +++watchpoints, in contrast, watch an expression in all threads.) +++@end quotation +++ +++@xref{set remote hardware-watchpoint-limit}. +++ +++@node Set Catchpoints +++@subsection Setting Catchpoints +++@cindex catchpoints, setting +++@cindex exception handlers +++@cindex event handling +++ +++You can use @dfn{catchpoints} to cause the debugger to stop for certain +++kinds of program events, such as C@t{++} exceptions or the loading of a +++shared library. Use the @code{catch} command to set a catchpoint. +++ +++@table @code +++@kindex catch +++@item catch @var{event} +++Stop when @var{event} occurs. The @var{event} can be any of the following: +++ +++@table @code +++@item throw @r{[}@var{regexp}@r{]} +++@itemx rethrow @r{[}@var{regexp}@r{]} +++@itemx catch @r{[}@var{regexp}@r{]} +++@kindex catch throw +++@kindex catch rethrow +++@kindex catch catch +++@cindex stop on C@t{++} exceptions +++The throwing, re-throwing, or catching of a C@t{++} exception. +++ +++If @var{regexp} is given, then only exceptions whose type matches the +++regular expression will be caught. +++ +++@vindex $_exception@r{, convenience variable} +++The convenience variable @code{$_exception} is available at an +++exception-related catchpoint, on some systems. This holds the +++exception being thrown. +++ +++There are currently some limitations to C@t{++} exception handling in +++@value{GDBN}: +++ +++@itemize @bullet +++@item +++The support for these commands is system-dependent. Currently, only +++systems using the @samp{gnu-v3} C@t{++} ABI (@pxref{ABI}) are +++supported. +++ +++@item +++The regular expression feature and the @code{$_exception} convenience +++variable rely on the presence of some SDT probes in @code{libstdc++}. +++If these probes are not present, then these features cannot be used. +++These probes were first available in the GCC 4.8 release, but whether +++or not they are available in your GCC also depends on how it was +++built. +++ +++@item +++The @code{$_exception} convenience variable is only valid at the +++instruction at which an exception-related catchpoint is set. +++ +++@item +++When an exception-related catchpoint is hit, @value{GDBN} stops at a +++location in the system library which implements runtime exception +++support for C@t{++}, usually @code{libstdc++}. You can use @code{up} +++(@pxref{Selection}) to get to your code. +++ +++@item +++If you call a function interactively, @value{GDBN} normally returns +++control to you when the function has finished executing. If the call +++raises an exception, however, the call may bypass the mechanism that +++returns control to you and cause your program either to abort or to +++simply continue running until it hits a breakpoint, catches a signal +++that @value{GDBN} is listening for, or exits. This is the case even if +++you set a catchpoint for the exception; catchpoints on exceptions are +++disabled within interactive calls. @xref{Calling}, for information on +++controlling this with @code{set unwind-on-terminating-exception}. +++ +++@item +++You cannot raise an exception interactively. +++ +++@item +++You cannot install an exception handler interactively. +++@end itemize +++ +++@item exception @r{[}@var{name}@r{]} +++@kindex catch exception +++@cindex Ada exception catching +++@cindex catch Ada exceptions +++An Ada exception being raised. If an exception name is specified +++at the end of the command (eg @code{catch exception Program_Error}), +++the debugger will stop only when this specific exception is raised. +++Otherwise, the debugger stops execution when any Ada exception is raised. +++ +++When inserting an exception catchpoint on a user-defined exception whose +++name is identical to one of the exceptions defined by the language, the +++fully qualified name must be used as the exception name. Otherwise, +++@value{GDBN} will assume that it should stop on the pre-defined exception +++rather than the user-defined one. For instance, assuming an exception +++called @code{Constraint_Error} is defined in package @code{Pck}, then +++the command to use to catch such exceptions is @kbd{catch exception +++Pck.Constraint_Error}. +++ +++@vindex $_ada_exception@r{, convenience variable} +++The convenience variable @code{$_ada_exception} holds the address of +++the exception being thrown. This can be useful when setting a +++condition for such a catchpoint. +++ +++@item exception unhandled +++@kindex catch exception unhandled +++An exception that was raised but is not handled by the program. The +++convenience variable @code{$_ada_exception} is set as for @code{catch +++exception}. +++ +++@item handlers @r{[}@var{name}@r{]} +++@kindex catch handlers +++@cindex Ada exception handlers catching +++@cindex catch Ada exceptions when handled +++An Ada exception being handled. If an exception name is +++specified at the end of the command +++ (eg @kbd{catch handlers Program_Error}), the debugger will stop +++only when this specific exception is handled. +++Otherwise, the debugger stops execution when any Ada exception is handled. +++ +++When inserting a handlers catchpoint on a user-defined +++exception whose name is identical to one of the exceptions +++defined by the language, the fully qualified name must be used +++as the exception name. Otherwise, @value{GDBN} will assume that it +++should stop on the pre-defined exception rather than the +++user-defined one. For instance, assuming an exception called +++ @code{Constraint_Error} is defined in package @code{Pck}, then the +++command to use to catch such exceptions handling is +++@kbd{catch handlers Pck.Constraint_Error}. +++ +++The convenience variable @code{$_ada_exception} is set as for +++@code{catch exception}. +++ +++@item assert +++@kindex catch assert +++A failed Ada assertion. Note that the convenience variable +++@code{$_ada_exception} is @emph{not} set by this catchpoint. +++ +++@item exec +++@kindex catch exec +++@cindex break on fork/exec +++A call to @code{exec}. +++ +++@anchor{catch syscall} +++@item syscall +++@itemx syscall @r{[}@var{name} @r{|} @var{number} @r{|} @r{group:}@var{groupname} @r{|} @r{g:}@var{groupname}@r{]} @dots{} +++@kindex catch syscall +++@cindex break on a system call. +++A call to or return from a system call, a.k.a.@: @dfn{syscall}. A +++syscall is a mechanism for application programs to request a service +++from the operating system (OS) or one of the OS system services. +++@value{GDBN} can catch some or all of the syscalls issued by the +++debuggee, and show the related information for each syscall. If no +++argument is specified, calls to and returns from all system calls +++will be caught. +++ +++@var{name} can be any system call name that is valid for the +++underlying OS. Just what syscalls are valid depends on the OS. On +++GNU and Unix systems, you can find the full list of valid syscall +++names on @file{/usr/include/asm/unistd.h}. +++ +++@c For MS-Windows, the syscall names and the corresponding numbers +++@c can be found, e.g., on this URL: +++@c http://www.metasploit.com/users/opcode/syscalls.html +++@c but we don't support Windows syscalls yet. +++ +++Normally, @value{GDBN} knows in advance which syscalls are valid for +++each OS, so you can use the @value{GDBN} command-line completion +++facilities (@pxref{Completion,, command completion}) to list the +++available choices. +++ +++You may also specify the system call numerically. A syscall's +++number is the value passed to the OS's syscall dispatcher to +++identify the requested service. When you specify the syscall by its +++name, @value{GDBN} uses its database of syscalls to convert the name +++into the corresponding numeric code, but using the number directly +++may be useful if @value{GDBN}'s database does not have the complete +++list of syscalls on your system (e.g., because @value{GDBN} lags +++behind the OS upgrades). +++ +++You may specify a group of related syscalls to be caught at once using +++the @code{group:} syntax (@code{g:} is a shorter equivalent). For +++instance, on some platforms @value{GDBN} allows you to catch all +++network related syscalls, by passing the argument @code{group:network} +++to @code{catch syscall}. Note that not all syscall groups are +++available in every system. You can use the command completion +++facilities (@pxref{Completion,, command completion}) to list the +++syscall groups available on your environment. +++ +++The example below illustrates how this command works if you don't provide +++arguments to it: +++ +++@smallexample +++(@value{GDBP}) catch syscall +++Catchpoint 1 (syscall) +++(@value{GDBP}) r +++Starting program: /tmp/catch-syscall +++ +++Catchpoint 1 (call to syscall 'close'), \ +++ 0xffffe424 in __kernel_vsyscall () +++(@value{GDBP}) c +++Continuing. +++ +++Catchpoint 1 (returned from syscall 'close'), \ +++ 0xffffe424 in __kernel_vsyscall () +++(@value{GDBP}) +++@end smallexample +++ +++Here is an example of catching a system call by name: +++ +++@smallexample +++(@value{GDBP}) catch syscall chroot +++Catchpoint 1 (syscall 'chroot' [61]) +++(@value{GDBP}) r +++Starting program: /tmp/catch-syscall +++ +++Catchpoint 1 (call to syscall 'chroot'), \ +++ 0xffffe424 in __kernel_vsyscall () +++(@value{GDBP}) c +++Continuing. +++ +++Catchpoint 1 (returned from syscall 'chroot'), \ +++ 0xffffe424 in __kernel_vsyscall () +++(@value{GDBP}) +++@end smallexample +++ +++An example of specifying a system call numerically. In the case +++below, the syscall number has a corresponding entry in the XML +++file, so @value{GDBN} finds its name and prints it: +++ +++@smallexample +++(@value{GDBP}) catch syscall 252 +++Catchpoint 1 (syscall(s) 'exit_group') +++(@value{GDBP}) r +++Starting program: /tmp/catch-syscall +++ +++Catchpoint 1 (call to syscall 'exit_group'), \ +++ 0xffffe424 in __kernel_vsyscall () +++(@value{GDBP}) c +++Continuing. +++ +++Program exited normally. +++(@value{GDBP}) +++@end smallexample +++ +++Here is an example of catching a syscall group: +++ +++@smallexample +++(@value{GDBP}) catch syscall group:process +++Catchpoint 1 (syscalls 'exit' [1] 'fork' [2] 'waitpid' [7] +++'execve' [11] 'wait4' [114] 'clone' [120] 'vfork' [190] +++'exit_group' [252] 'waitid' [284] 'unshare' [310]) +++(@value{GDBP}) r +++Starting program: /tmp/catch-syscall +++ +++Catchpoint 1 (call to syscall fork), 0x00007ffff7df4e27 in open64 () +++ from /lib64/ld-linux-x86-64.so.2 +++ +++(@value{GDBP}) c +++Continuing. +++@end smallexample +++ +++However, there can be situations when there is no corresponding name +++in XML file for that syscall number. In this case, @value{GDBN} prints +++a warning message saying that it was not able to find the syscall name, +++but the catchpoint will be set anyway. See the example below: +++ +++@smallexample +++(@value{GDBP}) catch syscall 764 +++warning: The number '764' does not represent a known syscall. +++Catchpoint 2 (syscall 764) +++(@value{GDBP}) +++@end smallexample +++ +++If you configure @value{GDBN} using the @samp{--without-expat} option, +++it will not be able to display syscall names. Also, if your +++architecture does not have an XML file describing its system calls, +++you will not be able to see the syscall names. It is important to +++notice that these two features are used for accessing the syscall +++name database. In either case, you will see a warning like this: +++ +++@smallexample +++(@value{GDBP}) catch syscall +++warning: Could not open "syscalls/i386-linux.xml" +++warning: Could not load the syscall XML file 'syscalls/i386-linux.xml'. +++GDB will not be able to display syscall names. +++Catchpoint 1 (syscall) +++(@value{GDBP}) +++@end smallexample +++ +++Of course, the file name will change depending on your architecture and system. +++ +++Still using the example above, you can also try to catch a syscall by its +++number. In this case, you would see something like: +++ +++@smallexample +++(@value{GDBP}) catch syscall 252 +++Catchpoint 1 (syscall(s) 252) +++@end smallexample +++ +++Again, in this case @value{GDBN} would not be able to display syscall's names. +++ +++@item fork +++@kindex catch fork +++A call to @code{fork}. +++ +++@item vfork +++@kindex catch vfork +++A call to @code{vfork}. +++ +++@item load @r{[}@var{regexp}@r{]} +++@itemx unload @r{[}@var{regexp}@r{]} +++@kindex catch load +++@kindex catch unload +++The loading or unloading of a shared library. If @var{regexp} is +++given, then the catchpoint will stop only if the regular expression +++matches one of the affected libraries. +++ +++@item signal @r{[}@var{signal}@dots{} @r{|} @samp{all}@r{]} +++@kindex catch signal +++The delivery of a signal. +++ +++With no arguments, this catchpoint will catch any signal that is not +++used internally by @value{GDBN}, specifically, all signals except +++@samp{SIGTRAP} and @samp{SIGINT}. +++ +++With the argument @samp{all}, all signals, including those used by +++@value{GDBN}, will be caught. This argument cannot be used with other +++signal names. +++ +++Otherwise, the arguments are a list of signal names as given to +++@code{handle} (@pxref{Signals}). Only signals specified in this list +++will be caught. +++ +++One reason that @code{catch signal} can be more useful than +++@code{handle} is that you can attach commands and conditions to the +++catchpoint. +++ +++When a signal is caught by a catchpoint, the signal's @code{stop} and +++@code{print} settings, as specified by @code{handle}, are ignored. +++However, whether the signal is still delivered to the inferior depends +++on the @code{pass} setting; this can be changed in the catchpoint's +++commands. +++ +++@end table +++ +++@item tcatch @var{event} +++@kindex tcatch +++Set a catchpoint that is enabled only for one stop. The catchpoint is +++automatically deleted after the first time the event is caught. +++ +++@end table +++ +++Use the @code{info break} command to list the current catchpoints. +++ +++ +++@node Delete Breaks +++@subsection Deleting Breakpoints +++ +++@cindex clearing breakpoints, watchpoints, catchpoints +++@cindex deleting breakpoints, watchpoints, catchpoints +++It is often necessary to eliminate a breakpoint, watchpoint, or +++catchpoint once it has done its job and you no longer want your program +++to stop there. This is called @dfn{deleting} the breakpoint. A +++breakpoint that has been deleted no longer exists; it is forgotten. +++ +++With the @code{clear} command you can delete breakpoints according to +++where they are in your program. With the @code{delete} command you can +++delete individual breakpoints, watchpoints, or catchpoints by specifying +++their breakpoint numbers. +++ +++It is not necessary to delete a breakpoint to proceed past it. @value{GDBN} +++automatically ignores breakpoints on the first instruction to be executed +++when you continue execution without changing the execution address. +++ +++@table @code +++@kindex clear +++@item clear +++Delete any breakpoints at the next instruction to be executed in the +++selected stack frame (@pxref{Selection, ,Selecting a Frame}). When +++the innermost frame is selected, this is a good way to delete a +++breakpoint where your program just stopped. +++ +++@item clear @var{location} +++Delete any breakpoints set at the specified @var{location}. +++@xref{Specify Location}, for the various forms of @var{location}; the +++most useful ones are listed below: +++ +++@table @code +++@item clear @var{function} +++@itemx clear @var{filename}:@var{function} +++Delete any breakpoints set at entry to the named @var{function}. +++ +++@item clear @var{linenum} +++@itemx clear @var{filename}:@var{linenum} +++Delete any breakpoints set at or within the code of the specified +++@var{linenum} of the specified @var{filename}. +++@end table +++ +++@cindex delete breakpoints +++@kindex delete +++@kindex d @r{(@code{delete})} +++@item delete @r{[}breakpoints@r{]} @r{[}@var{list}@dots{}@r{]} +++Delete the breakpoints, watchpoints, or catchpoints of the breakpoint +++list specified as argument. If no argument is specified, delete all +++breakpoints (@value{GDBN} asks confirmation, unless you have @code{set +++confirm off}). You can abbreviate this command as @code{d}. +++@end table +++ +++@node Disabling +++@subsection Disabling Breakpoints +++ +++@cindex enable/disable a breakpoint +++Rather than deleting a breakpoint, watchpoint, or catchpoint, you might +++prefer to @dfn{disable} it. This makes the breakpoint inoperative as if +++it had been deleted, but remembers the information on the breakpoint so +++that you can @dfn{enable} it again later. +++ +++You disable and enable breakpoints, watchpoints, and catchpoints with +++the @code{enable} and @code{disable} commands, optionally specifying +++one or more breakpoint numbers as arguments. Use @code{info break} to +++print a list of all breakpoints, watchpoints, and catchpoints if you +++do not know which numbers to use. +++ +++Disabling and enabling a breakpoint that has multiple locations +++affects all of its locations. +++ +++A breakpoint, watchpoint, or catchpoint can have any of several +++different states of enablement: +++ +++@itemize @bullet +++@item +++Enabled. The breakpoint stops your program. A breakpoint set +++with the @code{break} command starts out in this state. +++@item +++Disabled. The breakpoint has no effect on your program. +++@item +++Enabled once. The breakpoint stops your program, but then becomes +++disabled. +++@item +++Enabled for a count. The breakpoint stops your program for the next +++N times, then becomes disabled. +++@item +++Enabled for deletion. The breakpoint stops your program, but +++immediately after it does so it is deleted permanently. A breakpoint +++set with the @code{tbreak} command starts out in this state. +++@end itemize +++ +++You can use the following commands to enable or disable breakpoints, +++watchpoints, and catchpoints: +++ +++@table @code +++@kindex disable +++@kindex dis @r{(@code{disable})} +++@item disable @r{[}breakpoints@r{]} @r{[}@var{list}@dots{}@r{]} +++Disable the specified breakpoints---or all breakpoints, if none are +++listed. A disabled breakpoint has no effect but is not forgotten. All +++options such as ignore-counts, conditions and commands are remembered in +++case the breakpoint is enabled again later. You may abbreviate +++@code{disable} as @code{dis}. +++ +++@kindex enable +++@item enable @r{[}breakpoints@r{]} @r{[}@var{list}@dots{}@r{]} +++Enable the specified breakpoints (or all defined breakpoints). They +++become effective once again in stopping your program. +++ +++@item enable @r{[}breakpoints@r{]} once @var{list}@dots{} +++Enable the specified breakpoints temporarily. @value{GDBN} disables any +++of these breakpoints immediately after stopping your program. +++ +++@item enable @r{[}breakpoints@r{]} count @var{count} @var{list}@dots{} +++Enable the specified breakpoints temporarily. @value{GDBN} records +++@var{count} with each of the specified breakpoints, and decrements a +++breakpoint's count when it is hit. When any count reaches 0, +++@value{GDBN} disables that breakpoint. If a breakpoint has an ignore +++count (@pxref{Conditions, ,Break Conditions}), that will be +++decremented to 0 before @var{count} is affected. +++ +++@item enable @r{[}breakpoints@r{]} delete @var{list}@dots{} +++Enable the specified breakpoints to work once, then die. @value{GDBN} +++deletes any of these breakpoints as soon as your program stops there. +++Breakpoints set by the @code{tbreak} command start out in this state. +++@end table +++ +++@c FIXME: I think the following ``Except for [...] @code{tbreak}'' is +++@c confusing: tbreak is also initially enabled. +++Except for a breakpoint set with @code{tbreak} (@pxref{Set Breaks, +++,Setting Breakpoints}), breakpoints that you set are initially enabled; +++subsequently, they become disabled or enabled only when you use one of +++the commands above. (The command @code{until} can set and delete a +++breakpoint of its own, but it does not change the state of your other +++breakpoints; see @ref{Continuing and Stepping, ,Continuing and +++Stepping}.) +++ +++@node Conditions +++@subsection Break Conditions +++@cindex conditional breakpoints +++@cindex breakpoint conditions +++ +++@c FIXME what is scope of break condition expr? Context where wanted? +++@c in particular for a watchpoint? +++The simplest sort of breakpoint breaks every time your program reaches a +++specified place. You can also specify a @dfn{condition} for a +++breakpoint. A condition is just a Boolean expression in your +++programming language (@pxref{Expressions, ,Expressions}). A breakpoint with +++a condition evaluates the expression each time your program reaches it, +++and your program stops only if the condition is @emph{true}. +++ +++This is the converse of using assertions for program validation; in that +++situation, you want to stop when the assertion is violated---that is, +++when the condition is false. In C, if you want to test an assertion expressed +++by the condition @var{assert}, you should set the condition +++@samp{! @var{assert}} on the appropriate breakpoint. +++ +++Conditions are also accepted for watchpoints; you may not need them, +++since a watchpoint is inspecting the value of an expression anyhow---but +++it might be simpler, say, to just set a watchpoint on a variable name, +++and specify a condition that tests whether the new value is an interesting +++one. +++ +++Break conditions can have side effects, and may even call functions in +++your program. This can be useful, for example, to activate functions +++that log program progress, or to use your own print functions to +++format special data structures. The effects are completely predictable +++unless there is another enabled breakpoint at the same address. (In +++that case, @value{GDBN} might see the other breakpoint first and stop your +++program without checking the condition of this one.) Note that +++breakpoint commands are usually more convenient and flexible than break +++conditions for the +++purpose of performing side effects when a breakpoint is reached +++(@pxref{Break Commands, ,Breakpoint Command Lists}). +++ +++Breakpoint conditions can also be evaluated on the target's side if +++the target supports it. Instead of evaluating the conditions locally, +++@value{GDBN} encodes the expression into an agent expression +++(@pxref{Agent Expressions}) suitable for execution on the target, +++independently of @value{GDBN}. Global variables become raw memory +++locations, locals become stack accesses, and so forth. +++ +++In this case, @value{GDBN} will only be notified of a breakpoint trigger +++when its condition evaluates to true. This mechanism may provide faster +++response times depending on the performance characteristics of the target +++since it does not need to keep @value{GDBN} informed about +++every breakpoint trigger, even those with false conditions. +++ +++Break conditions can be specified when a breakpoint is set, by using +++@samp{if} in the arguments to the @code{break} command. @xref{Set +++Breaks, ,Setting Breakpoints}. They can also be changed at any time +++with the @code{condition} command. +++ +++You can also use the @code{if} keyword with the @code{watch} command. +++The @code{catch} command does not recognize the @code{if} keyword; +++@code{condition} is the only way to impose a further condition on a +++catchpoint. +++ +++@table @code +++@kindex condition +++@item condition @var{bnum} @var{expression} +++Specify @var{expression} as the break condition for breakpoint, +++watchpoint, or catchpoint number @var{bnum}. After you set a condition, +++breakpoint @var{bnum} stops your program only if the value of +++@var{expression} is true (nonzero, in C). When you use +++@code{condition}, @value{GDBN} checks @var{expression} immediately for +++syntactic correctness, and to determine whether symbols in it have +++referents in the context of your breakpoint. If @var{expression} uses +++symbols not referenced in the context of the breakpoint, @value{GDBN} +++prints an error message: +++ +++@smallexample +++No symbol "foo" in current context. +++@end smallexample +++ +++@noindent +++@value{GDBN} does +++not actually evaluate @var{expression} at the time the @code{condition} +++command (or a command that sets a breakpoint with a condition, like +++@code{break if @dots{}}) is given, however. @xref{Expressions, ,Expressions}. +++ +++@item condition @var{bnum} +++Remove the condition from breakpoint number @var{bnum}. It becomes +++an ordinary unconditional breakpoint. +++@end table +++ +++@cindex ignore count (of breakpoint) +++A special case of a breakpoint condition is to stop only when the +++breakpoint has been reached a certain number of times. This is so +++useful that there is a special way to do it, using the @dfn{ignore +++count} of the breakpoint. Every breakpoint has an ignore count, which +++is an integer. Most of the time, the ignore count is zero, and +++therefore has no effect. But if your program reaches a breakpoint whose +++ignore count is positive, then instead of stopping, it just decrements +++the ignore count by one and continues. As a result, if the ignore count +++value is @var{n}, the breakpoint does not stop the next @var{n} times +++your program reaches it. +++ +++@table @code +++@kindex ignore +++@item ignore @var{bnum} @var{count} +++Set the ignore count of breakpoint number @var{bnum} to @var{count}. +++The next @var{count} times the breakpoint is reached, your program's +++execution does not stop; other than to decrement the ignore count, @value{GDBN} +++takes no action. +++ +++To make the breakpoint stop the next time it is reached, specify +++a count of zero. +++ +++When you use @code{continue} to resume execution of your program from a +++breakpoint, you can specify an ignore count directly as an argument to +++@code{continue}, rather than using @code{ignore}. @xref{Continuing and +++Stepping,,Continuing and Stepping}. +++ +++If a breakpoint has a positive ignore count and a condition, the +++condition is not checked. Once the ignore count reaches zero, +++@value{GDBN} resumes checking the condition. +++ +++You could achieve the effect of the ignore count with a condition such +++as @w{@samp{$foo-- <= 0}} using a debugger convenience variable that +++is decremented each time. @xref{Convenience Vars, ,Convenience +++Variables}. +++@end table +++ +++Ignore counts apply to breakpoints, watchpoints, and catchpoints. +++ +++ +++@node Break Commands +++@subsection Breakpoint Command Lists +++ +++@cindex breakpoint commands +++You can give any breakpoint (or watchpoint or catchpoint) a series of +++commands to execute when your program stops due to that breakpoint. For +++example, you might want to print the values of certain expressions, or +++enable other breakpoints. +++ +++@table @code +++@kindex commands +++@kindex end@r{ (breakpoint commands)} +++@item commands @r{[}@var{list}@dots{}@r{]} +++@itemx @dots{} @var{command-list} @dots{} +++@itemx end +++Specify a list of commands for the given breakpoints. The commands +++themselves appear on the following lines. Type a line containing just +++@code{end} to terminate the commands. +++ +++To remove all commands from a breakpoint, type @code{commands} and +++follow it immediately with @code{end}; that is, give no commands. +++ +++With no argument, @code{commands} refers to the last breakpoint, +++watchpoint, or catchpoint set (not to the breakpoint most recently +++encountered). If the most recent breakpoints were set with a single +++command, then the @code{commands} will apply to all the breakpoints +++set by that command. This applies to breakpoints set by +++@code{rbreak}, and also applies when a single @code{break} command +++creates multiple breakpoints (@pxref{Ambiguous Expressions,,Ambiguous +++Expressions}). +++@end table +++ +++Pressing @key{RET} as a means of repeating the last @value{GDBN} command is +++disabled within a @var{command-list}. +++ +++You can use breakpoint commands to start your program up again. Simply +++use the @code{continue} command, or @code{step}, or any other command +++that resumes execution. +++ +++Any other commands in the command list, after a command that resumes +++execution, are ignored. This is because any time you resume execution +++(even with a simple @code{next} or @code{step}), you may encounter +++another breakpoint---which could have its own command list, leading to +++ambiguities about which list to execute. +++ +++@kindex silent +++If the first command you specify in a command list is @code{silent}, the +++usual message about stopping at a breakpoint is not printed. This may +++be desirable for breakpoints that are to print a specific message and +++then continue. If none of the remaining commands print anything, you +++see no sign that the breakpoint was reached. @code{silent} is +++meaningful only at the beginning of a breakpoint command list. +++ +++The commands @code{echo}, @code{output}, and @code{printf} allow you to +++print precisely controlled output, and are often useful in silent +++breakpoints. @xref{Output, ,Commands for Controlled Output}. +++ +++For example, here is how you could use breakpoint commands to print the +++value of @code{x} at entry to @code{foo} whenever @code{x} is positive. +++ +++@smallexample +++break foo if x>0 +++commands +++silent +++printf "x is %d\n",x +++cont +++end +++@end smallexample +++ +++One application for breakpoint commands is to compensate for one bug so +++you can test for another. Put a breakpoint just after the erroneous line +++of code, give it a condition to detect the case in which something +++erroneous has been done, and give it commands to assign correct values +++to any variables that need them. End with the @code{continue} command +++so that your program does not stop, and start with the @code{silent} +++command so that no output is produced. Here is an example: +++ +++@smallexample +++break 403 +++commands +++silent +++set x = y + 4 +++cont +++end +++@end smallexample +++ +++@node Dynamic Printf +++@subsection Dynamic Printf +++ +++@cindex dynamic printf +++@cindex dprintf +++The dynamic printf command @code{dprintf} combines a breakpoint with +++formatted printing of your program's data to give you the effect of +++inserting @code{printf} calls into your program on-the-fly, without +++having to recompile it. +++ +++In its most basic form, the output goes to the GDB console. However, +++you can set the variable @code{dprintf-style} for alternate handling. +++For instance, you can ask to format the output by calling your +++program's @code{printf} function. This has the advantage that the +++characters go to the program's output device, so they can recorded in +++redirects to files and so forth. +++ +++If you are doing remote debugging with a stub or agent, you can also +++ask to have the printf handled by the remote agent. In addition to +++ensuring that the output goes to the remote program's device along +++with any other output the program might produce, you can also ask that +++the dprintf remain active even after disconnecting from the remote +++target. Using the stub/agent is also more efficient, as it can do +++everything without needing to communicate with @value{GDBN}. +++ +++@table @code +++@kindex dprintf +++@item dprintf @var{location},@var{template},@var{expression}[,@var{expression}@dots{}] +++Whenever execution reaches @var{location}, print the values of one or +++more @var{expressions} under the control of the string @var{template}. +++To print several values, separate them with commas. +++ +++@item set dprintf-style @var{style} +++Set the dprintf output to be handled in one of several different +++styles enumerated below. A change of style affects all existing +++dynamic printfs immediately. (If you need individual control over the +++print commands, simply define normal breakpoints with +++explicitly-supplied command lists.) +++ +++@table @code +++@item gdb +++@kindex dprintf-style gdb +++Handle the output using the @value{GDBN} @code{printf} command. +++ +++@item call +++@kindex dprintf-style call +++Handle the output by calling a function in your program (normally +++@code{printf}). +++ +++@item agent +++@kindex dprintf-style agent +++Have the remote debugging agent (such as @code{gdbserver}) handle +++the output itself. This style is only available for agents that +++support running commands on the target. +++@end table +++ +++@item set dprintf-function @var{function} +++Set the function to call if the dprintf style is @code{call}. By +++default its value is @code{printf}. You may set it to any expression. +++that @value{GDBN} can evaluate to a function, as per the @code{call} +++command. +++ +++@item set dprintf-channel @var{channel} +++Set a ``channel'' for dprintf. If set to a non-empty value, +++@value{GDBN} will evaluate it as an expression and pass the result as +++a first argument to the @code{dprintf-function}, in the manner of +++@code{fprintf} and similar functions. Otherwise, the dprintf format +++string will be the first argument, in the manner of @code{printf}. +++ +++As an example, if you wanted @code{dprintf} output to go to a logfile +++that is a standard I/O stream assigned to the variable @code{mylog}, +++you could do the following: +++ +++@example +++(gdb) set dprintf-style call +++(gdb) set dprintf-function fprintf +++(gdb) set dprintf-channel mylog +++(gdb) dprintf 25,"at line 25, glob=%d\n",glob +++Dprintf 1 at 0x123456: file main.c, line 25. +++(gdb) info break +++1 dprintf keep y 0x00123456 in main at main.c:25 +++ call (void) fprintf (mylog,"at line 25, glob=%d\n",glob) +++ continue +++(gdb) +++@end example +++ +++Note that the @code{info break} displays the dynamic printf commands +++as normal breakpoint commands; you can thus easily see the effect of +++the variable settings. +++ +++@item set disconnected-dprintf on +++@itemx set disconnected-dprintf off +++@kindex set disconnected-dprintf +++Choose whether @code{dprintf} commands should continue to run if +++@value{GDBN} has disconnected from the target. This only applies +++if the @code{dprintf-style} is @code{agent}. +++ +++@item show disconnected-dprintf off +++@kindex show disconnected-dprintf +++Show the current choice for disconnected @code{dprintf}. +++ +++@end table +++ +++@value{GDBN} does not check the validity of function and channel, +++relying on you to supply values that are meaningful for the contexts +++in which they are being used. For instance, the function and channel +++may be the values of local variables, but if that is the case, then +++all enabled dynamic prints must be at locations within the scope of +++those locals. If evaluation fails, @value{GDBN} will report an error. +++ +++@node Save Breakpoints +++@subsection How to save breakpoints to a file +++ +++To save breakpoint definitions to a file use the @w{@code{save +++breakpoints}} command. +++ +++@table @code +++@kindex save breakpoints +++@cindex save breakpoints to a file for future sessions +++@item save breakpoints [@var{filename}] +++This command saves all current breakpoint definitions together with +++their commands and ignore counts, into a file @file{@var{filename}} +++suitable for use in a later debugging session. This includes all +++types of breakpoints (breakpoints, watchpoints, catchpoints, +++tracepoints). To read the saved breakpoint definitions, use the +++@code{source} command (@pxref{Command Files}). Note that watchpoints +++with expressions involving local variables may fail to be recreated +++because it may not be possible to access the context where the +++watchpoint is valid anymore. Because the saved breakpoint definitions +++are simply a sequence of @value{GDBN} commands that recreate the +++breakpoints, you can edit the file in your favorite editing program, +++and remove the breakpoint definitions you're not interested in, or +++that can no longer be recreated. +++@end table +++ +++@node Static Probe Points +++@subsection Static Probe Points +++ +++@cindex static probe point, SystemTap +++@cindex static probe point, DTrace +++@value{GDBN} supports @dfn{SDT} probes in the code. @acronym{SDT} stands +++for Statically Defined Tracing, and the probes are designed to have a tiny +++runtime code and data footprint, and no dynamic relocations. +++ +++Currently, the following types of probes are supported on +++ELF-compatible systems: +++ +++@itemize @bullet +++ +++@item @code{SystemTap} (@uref{http://sourceware.org/systemtap/}) +++@acronym{SDT} probes@footnote{See +++@uref{http://sourceware.org/systemtap/wiki/AddingUserSpaceProbingToApps} +++for more information on how to add @code{SystemTap} @acronym{SDT} +++probes in your applications.}. @code{SystemTap} probes are usable +++from assembly, C and C@t{++} languages@footnote{See +++@uref{http://sourceware.org/systemtap/wiki/UserSpaceProbeImplementation} +++for a good reference on how the @acronym{SDT} probes are implemented.}. +++ +++@item @code{DTrace} (@uref{http://oss.oracle.com/projects/DTrace}) +++@acronym{USDT} probes. @code{DTrace} probes are usable from C and +++C@t{++} languages. +++@end itemize +++ +++@cindex semaphores on static probe points +++Some @code{SystemTap} probes have an associated semaphore variable; +++for instance, this happens automatically if you defined your probe +++using a DTrace-style @file{.d} file. If your probe has a semaphore, +++@value{GDBN} will automatically enable it when you specify a +++breakpoint using the @samp{-probe-stap} notation. But, if you put a +++breakpoint at a probe's location by some other method (e.g., +++@code{break file:line}), then @value{GDBN} will not automatically set +++the semaphore. @code{DTrace} probes do not support semaphores. +++ +++You can examine the available static static probes using @code{info +++probes}, with optional arguments: +++ +++@table @code +++@kindex info probes +++@item info probes @r{[}@var{type}@r{]} @r{[}@var{provider} @r{[}@var{name} @r{[}@var{objfile}@r{]}@r{]}@r{]} +++If given, @var{type} is either @code{stap} for listing +++@code{SystemTap} probes or @code{dtrace} for listing @code{DTrace} +++probes. If omitted all probes are listed regardless of their types. +++ +++If given, @var{provider} is a regular expression used to match against provider +++names when selecting which probes to list. If omitted, probes by all +++probes from all providers are listed. +++ +++If given, @var{name} is a regular expression to match against probe names +++when selecting which probes to list. If omitted, probe names are not +++considered when deciding whether to display them. +++ +++If given, @var{objfile} is a regular expression used to select which +++object files (executable or shared libraries) to examine. If not +++given, all object files are considered. +++ +++@item info probes all +++List the available static probes, from all types. +++@end table +++ +++@cindex enabling and disabling probes +++Some probe points can be enabled and/or disabled. The effect of +++enabling or disabling a probe depends on the type of probe being +++handled. Some @code{DTrace} probes can be enabled or +++disabled, but @code{SystemTap} probes cannot be disabled. +++ +++You can enable (or disable) one or more probes using the following +++commands, with optional arguments: +++ +++@table @code +++@kindex enable probes +++@item enable probes @r{[}@var{provider} @r{[}@var{name} @r{[}@var{objfile}@r{]}@r{]}@r{]} +++If given, @var{provider} is a regular expression used to match against +++provider names when selecting which probes to enable. If omitted, +++all probes from all providers are enabled. +++ +++If given, @var{name} is a regular expression to match against probe +++names when selecting which probes to enable. If omitted, probe names +++are not considered when deciding whether to enable them. +++ +++If given, @var{objfile} is a regular expression used to select which +++object files (executable or shared libraries) to examine. If not +++given, all object files are considered. +++ +++@kindex disable probes +++@item disable probes @r{[}@var{provider} @r{[}@var{name} @r{[}@var{objfile}@r{]}@r{]}@r{]} +++See the @code{enable probes} command above for a description of the +++optional arguments accepted by this command. +++@end table +++ +++@vindex $_probe_arg@r{, convenience variable} +++A probe may specify up to twelve arguments. These are available at the +++point at which the probe is defined---that is, when the current PC is +++at the probe's location. The arguments are available using the +++convenience variables (@pxref{Convenience Vars}) +++@code{$_probe_arg0}@dots{}@code{$_probe_arg11}. In @code{SystemTap} +++probes each probe argument is an integer of the appropriate size; +++types are not preserved. In @code{DTrace} probes types are preserved +++provided that they are recognized as such by @value{GDBN}; otherwise +++the value of the probe argument will be a long integer. The +++convenience variable @code{$_probe_argc} holds the number of arguments +++at the current probe point. +++ +++These variables are always available, but attempts to access them at +++any location other than a probe point will cause @value{GDBN} to give +++an error message. +++ +++ +++@c @ifclear BARETARGET +++@node Error in Breakpoints +++@subsection ``Cannot insert breakpoints'' +++ +++If you request too many active hardware-assisted breakpoints and +++watchpoints, you will see this error message: +++ +++@c FIXME: the precise wording of this message may change; the relevant +++@c source change is not committed yet (Sep 3, 1999). +++@smallexample +++Stopped; cannot insert breakpoints. +++You may have requested too many hardware breakpoints and watchpoints. +++@end smallexample +++ +++@noindent +++This message is printed when you attempt to resume the program, since +++only then @value{GDBN} knows exactly how many hardware breakpoints and +++watchpoints it needs to insert. +++ +++When this message is printed, you need to disable or remove some of the +++hardware-assisted breakpoints and watchpoints, and then continue. +++ +++@node Breakpoint-related Warnings +++@subsection ``Breakpoint address adjusted...'' +++@cindex breakpoint address adjusted +++ +++Some processor architectures place constraints on the addresses at +++which breakpoints may be placed. For architectures thus constrained, +++@value{GDBN} will attempt to adjust the breakpoint's address to comply +++with the constraints dictated by the architecture. +++ +++One example of such an architecture is the Fujitsu FR-V. The FR-V is +++a VLIW architecture in which a number of RISC-like instructions may be +++bundled together for parallel execution. The FR-V architecture +++constrains the location of a breakpoint instruction within such a +++bundle to the instruction with the lowest address. @value{GDBN} +++honors this constraint by adjusting a breakpoint's address to the +++first in the bundle. +++ +++It is not uncommon for optimized code to have bundles which contain +++instructions from different source statements, thus it may happen that +++a breakpoint's address will be adjusted from one source statement to +++another. Since this adjustment may significantly alter @value{GDBN}'s +++breakpoint related behavior from what the user expects, a warning is +++printed when the breakpoint is first set and also when the breakpoint +++is hit. +++ +++A warning like the one below is printed when setting a breakpoint +++that's been subject to address adjustment: +++ +++@smallexample +++warning: Breakpoint address adjusted from 0x00010414 to 0x00010410. +++@end smallexample +++ +++Such warnings are printed both for user settable and @value{GDBN}'s +++internal breakpoints. If you see one of these warnings, you should +++verify that a breakpoint set at the adjusted address will have the +++desired affect. If not, the breakpoint in question may be removed and +++other breakpoints may be set which will have the desired behavior. +++E.g., it may be sufficient to place the breakpoint at a later +++instruction. A conditional breakpoint may also be useful in some +++cases to prevent the breakpoint from triggering too often. +++ +++@value{GDBN} will also issue a warning when stopping at one of these +++adjusted breakpoints: +++ +++@smallexample +++warning: Breakpoint 1 address previously adjusted from 0x00010414 +++to 0x00010410. +++@end smallexample +++ +++When this warning is encountered, it may be too late to take remedial +++action except in cases where the breakpoint is hit earlier or more +++frequently than expected. +++ +++@node Continuing and Stepping +++@section Continuing and Stepping +++ +++@cindex stepping +++@cindex continuing +++@cindex resuming execution +++@dfn{Continuing} means resuming program execution until your program +++completes normally. In contrast, @dfn{stepping} means executing just +++one more ``step'' of your program, where ``step'' may mean either one +++line of source code, or one machine instruction (depending on what +++particular command you use). Either when continuing or when stepping, +++your program may stop even sooner, due to a breakpoint or a signal. (If +++it stops due to a signal, you may want to use @code{handle}, or use +++@samp{signal 0} to resume execution (@pxref{Signals, ,Signals}), +++or you may step into the signal's handler (@pxref{stepping and signal +++handlers}).) +++ +++@table @code +++@kindex continue +++@kindex c @r{(@code{continue})} +++@kindex fg @r{(resume foreground execution)} +++@item continue @r{[}@var{ignore-count}@r{]} +++@itemx c @r{[}@var{ignore-count}@r{]} +++@itemx fg @r{[}@var{ignore-count}@r{]} +++Resume program execution, at the address where your program last stopped; +++any breakpoints set at that address are bypassed. The optional argument +++@var{ignore-count} allows you to specify a further number of times to +++ignore a breakpoint at this location; its effect is like that of +++@code{ignore} (@pxref{Conditions, ,Break Conditions}). +++ +++The argument @var{ignore-count} is meaningful only when your program +++stopped due to a breakpoint. At other times, the argument to +++@code{continue} is ignored. +++ +++The synonyms @code{c} and @code{fg} (for @dfn{foreground}, as the +++debugged program is deemed to be the foreground program) are provided +++purely for convenience, and have exactly the same behavior as +++@code{continue}. +++@end table +++ +++To resume execution at a different place, you can use @code{return} +++(@pxref{Returning, ,Returning from a Function}) to go back to the +++calling function; or @code{jump} (@pxref{Jumping, ,Continuing at a +++Different Address}) to go to an arbitrary location in your program. +++ +++A typical technique for using stepping is to set a breakpoint +++(@pxref{Breakpoints, ,Breakpoints; Watchpoints; and Catchpoints}) at the +++beginning of the function or the section of your program where a problem +++is believed to lie, run your program until it stops at that breakpoint, +++and then step through the suspect area, examining the variables that are +++interesting, until you see the problem happen. +++ +++@table @code +++@kindex step +++@kindex s @r{(@code{step})} +++@item step +++Continue running your program until control reaches a different source +++line, then stop it and return control to @value{GDBN}. This command is +++abbreviated @code{s}. +++ +++@quotation +++@c "without debugging information" is imprecise; actually "without line +++@c numbers in the debugging information". (gcc -g1 has debugging info but +++@c not line numbers). But it seems complex to try to make that +++@c distinction here. +++@emph{Warning:} If you use the @code{step} command while control is +++within a function that was compiled without debugging information, +++execution proceeds until control reaches a function that does have +++debugging information. Likewise, it will not step into a function which +++is compiled without debugging information. To step through functions +++without debugging information, use the @code{stepi} command, described +++below. +++@end quotation +++ +++The @code{step} command only stops at the first instruction of a source +++line. This prevents the multiple stops that could otherwise occur in +++@code{switch} statements, @code{for} loops, etc. @code{step} continues +++to stop if a function that has debugging information is called within +++the line. In other words, @code{step} @emph{steps inside} any functions +++called within the line. +++ +++Also, the @code{step} command only enters a function if there is line +++number information for the function. Otherwise it acts like the +++@code{next} command. This avoids problems when using @code{cc -gl} +++on @acronym{MIPS} machines. Previously, @code{step} entered subroutines if there +++was any debugging information about the routine. +++ +++@item step @var{count} +++Continue running as in @code{step}, but do so @var{count} times. If a +++breakpoint is reached, or a signal not related to stepping occurs before +++@var{count} steps, stepping stops right away. +++ +++@kindex next +++@kindex n @r{(@code{next})} +++@item next @r{[}@var{count}@r{]} +++Continue to the next source line in the current (innermost) stack frame. +++This is similar to @code{step}, but function calls that appear within +++the line of code are executed without stopping. Execution stops when +++control reaches a different line of code at the original stack level +++that was executing when you gave the @code{next} command. This command +++is abbreviated @code{n}. +++ +++An argument @var{count} is a repeat count, as for @code{step}. +++ +++ +++@c FIX ME!! Do we delete this, or is there a way it fits in with +++@c the following paragraph? --- Vctoria +++@c +++@c @code{next} within a function that lacks debugging information acts like +++@c @code{step}, but any function calls appearing within the code of the +++@c function are executed without stopping. +++ +++The @code{next} command only stops at the first instruction of a +++source line. This prevents multiple stops that could otherwise occur in +++@code{switch} statements, @code{for} loops, etc. +++ +++@kindex set step-mode +++@item set step-mode +++@cindex functions without line info, and stepping +++@cindex stepping into functions with no line info +++@itemx set step-mode on +++The @code{set step-mode on} command causes the @code{step} command to +++stop at the first instruction of a function which contains no debug line +++information rather than stepping over it. +++ +++This is useful in cases where you may be interested in inspecting the +++machine instructions of a function which has no symbolic info and do not +++want @value{GDBN} to automatically skip over this function. +++ +++@item set step-mode off +++Causes the @code{step} command to step over any functions which contains no +++debug information. This is the default. +++ +++@item show step-mode +++Show whether @value{GDBN} will stop in or step over functions without +++source line debug information. +++ +++@kindex finish +++@kindex fin @r{(@code{finish})} +++@item finish +++Continue running until just after function in the selected stack frame +++returns. Print the returned value (if any). This command can be +++abbreviated as @code{fin}. +++ +++Contrast this with the @code{return} command (@pxref{Returning, +++,Returning from a Function}). +++ +++@kindex set print finish +++@kindex show print finish +++@item set print finish @r{[}on|off@r{]} +++@itemx show print finish +++By default the @code{finish} command will show the value that is +++returned by the function. This can be disabled using @code{set print +++finish off}. When disabled, the value is still entered into the value +++history (@pxref{Value History}), but not displayed. +++ +++@kindex until +++@kindex u @r{(@code{until})} +++@cindex run until specified location +++@item until +++@itemx u +++Continue running until a source line past the current line, in the +++current stack frame, is reached. This command is used to avoid single +++stepping through a loop more than once. It is like the @code{next} +++command, except that when @code{until} encounters a jump, it +++automatically continues execution until the program counter is greater +++than the address of the jump. +++ +++This means that when you reach the end of a loop after single stepping +++though it, @code{until} makes your program continue execution until it +++exits the loop. In contrast, a @code{next} command at the end of a loop +++simply steps back to the beginning of the loop, which forces you to step +++through the next iteration. +++ +++@code{until} always stops your program if it attempts to exit the current +++stack frame. +++ +++@code{until} may produce somewhat counterintuitive results if the order +++of machine code does not match the order of the source lines. For +++example, in the following excerpt from a debugging session, the @code{f} +++(@code{frame}) command shows that execution is stopped at line +++@code{206}; yet when we use @code{until}, we get to line @code{195}: +++ +++@smallexample +++(@value{GDBP}) f +++#0 main (argc=4, argv=0xf7fffae8) at m4.c:206 +++206 expand_input(); +++(@value{GDBP}) until +++195 for ( ; argc > 0; NEXTARG) @{ +++@end smallexample +++ +++This happened because, for execution efficiency, the compiler had +++generated code for the loop closure test at the end, rather than the +++start, of the loop---even though the test in a C @code{for}-loop is +++written before the body of the loop. The @code{until} command appeared +++to step back to the beginning of the loop when it advanced to this +++expression; however, it has not really gone to an earlier +++statement---not in terms of the actual machine code. +++ +++@code{until} with no argument works by means of single +++instruction stepping, and hence is slower than @code{until} with an +++argument. +++ +++@item until @var{location} +++@itemx u @var{location} +++Continue running your program until either the specified @var{location} is +++reached, or the current stack frame returns. The location is any of +++the forms described in @ref{Specify Location}. +++This form of the command uses temporary breakpoints, and +++hence is quicker than @code{until} without an argument. The specified +++location is actually reached only if it is in the current frame. This +++implies that @code{until} can be used to skip over recursive function +++invocations. For instance in the code below, if the current location is +++line @code{96}, issuing @code{until 99} will execute the program up to +++line @code{99} in the same invocation of factorial, i.e., after the inner +++invocations have returned. +++ +++@smallexample +++94 int factorial (int value) +++95 @{ +++96 if (value > 1) @{ +++97 value *= factorial (value - 1); +++98 @} +++99 return (value); +++100 @} +++@end smallexample +++ +++ +++@kindex advance @var{location} +++@item advance @var{location} +++Continue running the program up to the given @var{location}. An argument is +++required, which should be of one of the forms described in +++@ref{Specify Location}. +++Execution will also stop upon exit from the current stack +++frame. This command is similar to @code{until}, but @code{advance} will +++not skip over recursive function calls, and the target location doesn't +++have to be in the same frame as the current one. +++ +++ +++@kindex stepi +++@kindex si @r{(@code{stepi})} +++@item stepi +++@itemx stepi @var{arg} +++@itemx si +++Execute one machine instruction, then stop and return to the debugger. +++ +++It is often useful to do @samp{display/i $pc} when stepping by machine +++instructions. This makes @value{GDBN} automatically display the next +++instruction to be executed, each time your program stops. @xref{Auto +++Display,, Automatic Display}. +++ +++An argument is a repeat count, as in @code{step}. +++ +++@need 750 +++@kindex nexti +++@kindex ni @r{(@code{nexti})} +++@item nexti +++@itemx nexti @var{arg} +++@itemx ni +++Execute one machine instruction, but if it is a function call, +++proceed until the function returns. +++ +++An argument is a repeat count, as in @code{next}. +++ +++@end table +++ +++@anchor{range stepping} +++@cindex range stepping +++@cindex target-assisted range stepping +++By default, and if available, @value{GDBN} makes use of +++target-assisted @dfn{range stepping}. In other words, whenever you +++use a stepping command (e.g., @code{step}, @code{next}), @value{GDBN} +++tells the target to step the corresponding range of instruction +++addresses instead of issuing multiple single-steps. This speeds up +++line stepping, particularly for remote targets. Ideally, there should +++be no reason you would want to turn range stepping off. However, it's +++possible that a bug in the debug info, a bug in the remote stub (for +++remote targets), or even a bug in @value{GDBN} could make line +++stepping behave incorrectly when target-assisted range stepping is +++enabled. You can use the following command to turn off range stepping +++if necessary: +++ +++@table @code +++@kindex set range-stepping +++@kindex show range-stepping +++@item set range-stepping +++@itemx show range-stepping +++Control whether range stepping is enabled. +++ +++If @code{on}, and the target supports it, @value{GDBN} tells the +++target to step a range of addresses itself, instead of issuing +++multiple single-steps. If @code{off}, @value{GDBN} always issues +++single-steps, even if range stepping is supported by the target. The +++default is @code{on}. +++ +++@end table +++ +++@node Skipping Over Functions and Files +++@section Skipping Over Functions and Files +++@cindex skipping over functions and files +++ +++The program you are debugging may contain some functions which are +++uninteresting to debug. The @code{skip} command lets you tell @value{GDBN} to +++skip a function, all functions in a file or a particular function in +++a particular file when stepping. +++ +++For example, consider the following C function: +++ +++@smallexample +++101 int func() +++102 @{ +++103 foo(boring()); +++104 bar(boring()); +++105 @} +++@end smallexample +++ +++@noindent +++Suppose you wish to step into the functions @code{foo} and @code{bar}, but you +++are not interested in stepping through @code{boring}. If you run @code{step} +++at line 103, you'll enter @code{boring()}, but if you run @code{next}, you'll +++step over both @code{foo} and @code{boring}! +++ +++One solution is to @code{step} into @code{boring} and use the @code{finish} +++command to immediately exit it. But this can become tedious if @code{boring} +++is called from many places. +++ +++A more flexible solution is to execute @kbd{skip boring}. This instructs +++@value{GDBN} never to step into @code{boring}. Now when you execute +++@code{step} at line 103, you'll step over @code{boring} and directly into +++@code{foo}. +++ +++Functions may be skipped by providing either a function name, linespec +++(@pxref{Specify Location}), regular expression that matches the function's +++name, file name or a @code{glob}-style pattern that matches the file name. +++ +++On Posix systems the form of the regular expression is +++``Extended Regular Expressions''. See for example @samp{man 7 regex} +++on @sc{gnu}/Linux systems. On non-Posix systems the form of the regular +++expression is whatever is provided by the @code{regcomp} function of +++the underlying system. +++See for example @samp{man 7 glob} on @sc{gnu}/Linux systems for a +++description of @code{glob}-style patterns. +++ +++@table @code +++@kindex skip +++@item skip @r{[}@var{options}@r{]} +++The basic form of the @code{skip} command takes zero or more options +++that specify what to skip. +++The @var{options} argument is any useful combination of the following: +++ +++@table @code +++@item -file @var{file} +++@itemx -fi @var{file} +++Functions in @var{file} will be skipped over when stepping. +++ +++@item -gfile @var{file-glob-pattern} +++@itemx -gfi @var{file-glob-pattern} +++@cindex skipping over files via glob-style patterns +++Functions in files matching @var{file-glob-pattern} will be skipped +++over when stepping. +++ +++@smallexample +++(gdb) skip -gfi utils/*.c +++@end smallexample +++ +++@item -function @var{linespec} +++@itemx -fu @var{linespec} +++Functions named by @var{linespec} or the function containing the line +++named by @var{linespec} will be skipped over when stepping. +++@xref{Specify Location}. +++ +++@item -rfunction @var{regexp} +++@itemx -rfu @var{regexp} +++@cindex skipping over functions via regular expressions +++Functions whose name matches @var{regexp} will be skipped over when stepping. +++ +++This form is useful for complex function names. +++For example, there is generally no need to step into C@t{++} @code{std::string} +++constructors or destructors. Plus with C@t{++} templates it can be hard to +++write out the full name of the function, and often it doesn't matter what +++the template arguments are. Specifying the function to be skipped as a +++regular expression makes this easier. +++ +++@smallexample +++(gdb) skip -rfu ^std::(allocator|basic_string)<.*>::~?\1 *\( +++@end smallexample +++ +++If you want to skip every templated C@t{++} constructor and destructor +++in the @code{std} namespace you can do: +++ +++@smallexample +++(gdb) skip -rfu ^std::([a-zA-z0-9_]+)<.*>::~?\1 *\( +++@end smallexample +++@end table +++ +++If no options are specified, the function you're currently debugging +++will be skipped. +++ +++@kindex skip function +++@item skip function @r{[}@var{linespec}@r{]} +++After running this command, the function named by @var{linespec} or the +++function containing the line named by @var{linespec} will be skipped over when +++stepping. @xref{Specify Location}. +++ +++If you do not specify @var{linespec}, the function you're currently debugging +++will be skipped. +++ +++(If you have a function called @code{file} that you want to skip, use +++@kbd{skip function file}.) +++ +++@kindex skip file +++@item skip file @r{[}@var{filename}@r{]} +++After running this command, any function whose source lives in @var{filename} +++will be skipped over when stepping. +++ +++@smallexample +++(gdb) skip file boring.c +++File boring.c will be skipped when stepping. +++@end smallexample +++ +++If you do not specify @var{filename}, functions whose source lives in the file +++you're currently debugging will be skipped. +++@end table +++ +++Skips can be listed, deleted, disabled, and enabled, much like breakpoints. +++These are the commands for managing your list of skips: +++ +++@table @code +++@kindex info skip +++@item info skip @r{[}@var{range}@r{]} +++Print details about the specified skip(s). If @var{range} is not specified, +++print a table with details about all functions and files marked for skipping. +++@code{info skip} prints the following information about each skip: +++ +++@table @emph +++@item Identifier +++A number identifying this skip. +++@item Enabled or Disabled +++Enabled skips are marked with @samp{y}. +++Disabled skips are marked with @samp{n}. +++@item Glob +++If the file name is a @samp{glob} pattern this is @samp{y}. +++Otherwise it is @samp{n}. +++@item File +++The name or @samp{glob} pattern of the file to be skipped. +++If no file is specified this is @samp{}. +++@item RE +++If the function name is a @samp{regular expression} this is @samp{y}. +++Otherwise it is @samp{n}. +++@item Function +++The name or regular expression of the function to skip. +++If no function is specified this is @samp{}. +++@end table +++ +++@kindex skip delete +++@item skip delete @r{[}@var{range}@r{]} +++Delete the specified skip(s). If @var{range} is not specified, delete all +++skips. +++ +++@kindex skip enable +++@item skip enable @r{[}@var{range}@r{]} +++Enable the specified skip(s). If @var{range} is not specified, enable all +++skips. +++ +++@kindex skip disable +++@item skip disable @r{[}@var{range}@r{]} +++Disable the specified skip(s). If @var{range} is not specified, disable all +++skips. +++ +++@kindex set debug skip +++@item set debug skip @r{[}on|off@r{]} +++Set whether to print the debug output about skipping files and functions. +++ +++@kindex show debug skip +++@item show debug skip +++Show whether the debug output about skipping files and functions is printed. +++ +++@end table +++ +++@node Signals +++@section Signals +++@cindex signals +++ +++A signal is an asynchronous event that can happen in a program. The +++operating system defines the possible kinds of signals, and gives each +++kind a name and a number. For example, in Unix @code{SIGINT} is the +++signal a program gets when you type an interrupt character (often @kbd{Ctrl-c}); +++@code{SIGSEGV} is the signal a program gets from referencing a place in +++memory far away from all the areas in use; @code{SIGALRM} occurs when +++the alarm clock timer goes off (which happens only if your program has +++requested an alarm). +++ +++@cindex fatal signals +++Some signals, including @code{SIGALRM}, are a normal part of the +++functioning of your program. Others, such as @code{SIGSEGV}, indicate +++errors; these signals are @dfn{fatal} (they kill your program immediately) if the +++program has not specified in advance some other way to handle the signal. +++@code{SIGINT} does not indicate an error in your program, but it is normally +++fatal so it can carry out the purpose of the interrupt: to kill the program. +++ +++@value{GDBN} has the ability to detect any occurrence of a signal in your +++program. You can tell @value{GDBN} in advance what to do for each kind of +++signal. +++ +++@cindex handling signals +++Normally, @value{GDBN} is set up to let the non-erroneous signals like +++@code{SIGALRM} be silently passed to your program +++(so as not to interfere with their role in the program's functioning) +++but to stop your program immediately whenever an error signal happens. +++You can change these settings with the @code{handle} command. +++ +++@table @code +++@kindex info signals +++@kindex info handle +++@item info signals +++@itemx info handle +++Print a table of all the kinds of signals and how @value{GDBN} has been told to +++handle each one. You can use this to see the signal numbers of all +++the defined types of signals. +++ +++@item info signals @var{sig} +++Similar, but print information only about the specified signal number. +++ +++@code{info handle} is an alias for @code{info signals}. +++ +++@item catch signal @r{[}@var{signal}@dots{} @r{|} @samp{all}@r{]} +++Set a catchpoint for the indicated signals. @xref{Set Catchpoints}, +++for details about this command. +++ +++@kindex handle +++@item handle @var{signal} @r{[}@var{keywords}@dots{}@r{]} +++Change the way @value{GDBN} handles signal @var{signal}. The @var{signal} +++can be the number of a signal or its name (with or without the +++@samp{SIG} at the beginning); a list of signal numbers of the form +++@samp{@var{low}-@var{high}}; or the word @samp{all}, meaning all the +++known signals. Optional arguments @var{keywords}, described below, +++say what change to make. +++@end table +++ +++@c @group +++The keywords allowed by the @code{handle} command can be abbreviated. +++Their full names are: +++ +++@table @code +++@item nostop +++@value{GDBN} should not stop your program when this signal happens. It may +++still print a message telling you that the signal has come in. +++ +++@item stop +++@value{GDBN} should stop your program when this signal happens. This implies +++the @code{print} keyword as well. +++ +++@item print +++@value{GDBN} should print a message when this signal happens. +++ +++@item noprint +++@value{GDBN} should not mention the occurrence of the signal at all. This +++implies the @code{nostop} keyword as well. +++ +++@item pass +++@itemx noignore +++@value{GDBN} should allow your program to see this signal; your program +++can handle the signal, or else it may terminate if the signal is fatal +++and not handled. @code{pass} and @code{noignore} are synonyms. +++ +++@item nopass +++@itemx ignore +++@value{GDBN} should not allow your program to see this signal. +++@code{nopass} and @code{ignore} are synonyms. +++@end table +++@c @end group +++ +++When a signal stops your program, the signal is not visible to the +++program until you +++continue. Your program sees the signal then, if @code{pass} is in +++effect for the signal in question @emph{at that time}. In other words, +++after @value{GDBN} reports a signal, you can use the @code{handle} +++command with @code{pass} or @code{nopass} to control whether your +++program sees that signal when you continue. +++ +++The default is set to @code{nostop}, @code{noprint}, @code{pass} for +++non-erroneous signals such as @code{SIGALRM}, @code{SIGWINCH} and +++@code{SIGCHLD}, and to @code{stop}, @code{print}, @code{pass} for the +++erroneous signals. +++ +++You can also use the @code{signal} command to prevent your program from +++seeing a signal, or cause it to see a signal it normally would not see, +++or to give it any signal at any time. For example, if your program stopped +++due to some sort of memory reference error, you might store correct +++values into the erroneous variables and continue, hoping to see more +++execution; but your program would probably terminate immediately as +++a result of the fatal signal once it saw the signal. To prevent this, +++you can continue with @samp{signal 0}. @xref{Signaling, ,Giving your +++Program a Signal}. +++ +++@cindex stepping and signal handlers +++@anchor{stepping and signal handlers} +++ +++@value{GDBN} optimizes for stepping the mainline code. If a signal +++that has @code{handle nostop} and @code{handle pass} set arrives while +++a stepping command (e.g., @code{stepi}, @code{step}, @code{next}) is +++in progress, @value{GDBN} lets the signal handler run and then resumes +++stepping the mainline code once the signal handler returns. In other +++words, @value{GDBN} steps over the signal handler. This prevents +++signals that you've specified as not interesting (with @code{handle +++nostop}) from changing the focus of debugging unexpectedly. Note that +++the signal handler itself may still hit a breakpoint, stop for another +++signal that has @code{handle stop} in effect, or for any other event +++that normally results in stopping the stepping command sooner. Also +++note that @value{GDBN} still informs you that the program received a +++signal if @code{handle print} is set. +++ +++@anchor{stepping into signal handlers} +++ +++If you set @code{handle pass} for a signal, and your program sets up a +++handler for it, then issuing a stepping command, such as @code{step} +++or @code{stepi}, when your program is stopped due to the signal will +++step @emph{into} the signal handler (if the target supports that). +++ +++Likewise, if you use the @code{queue-signal} command to queue a signal +++to be delivered to the current thread when execution of the thread +++resumes (@pxref{Signaling, ,Giving your Program a Signal}), then a +++stepping command will step into the signal handler. +++ +++Here's an example, using @code{stepi} to step to the first instruction +++of @code{SIGUSR1}'s handler: +++ +++@smallexample +++(@value{GDBP}) handle SIGUSR1 +++Signal Stop Print Pass to program Description +++SIGUSR1 Yes Yes Yes User defined signal 1 +++(@value{GDBP}) c +++Continuing. +++ +++Program received signal SIGUSR1, User defined signal 1. +++main () sigusr1.c:28 +++28 p = 0; +++(@value{GDBP}) si +++sigusr1_handler () at sigusr1.c:9 +++9 @{ +++@end smallexample +++ +++The same, but using @code{queue-signal} instead of waiting for the +++program to receive the signal first: +++ +++@smallexample +++(@value{GDBP}) n +++28 p = 0; +++(@value{GDBP}) queue-signal SIGUSR1 +++(@value{GDBP}) si +++sigusr1_handler () at sigusr1.c:9 +++9 @{ +++(@value{GDBP}) +++@end smallexample +++ +++@cindex extra signal information +++@anchor{extra signal information} +++ +++On some targets, @value{GDBN} can inspect extra signal information +++associated with the intercepted signal, before it is actually +++delivered to the program being debugged. This information is exported +++by the convenience variable @code{$_siginfo}, and consists of data +++that is passed by the kernel to the signal handler at the time of the +++receipt of a signal. The data type of the information itself is +++target dependent. You can see the data type using the @code{ptype +++$_siginfo} command. On Unix systems, it typically corresponds to the +++standard @code{siginfo_t} type, as defined in the @file{signal.h} +++system header. +++ +++Here's an example, on a @sc{gnu}/Linux system, printing the stray +++referenced address that raised a segmentation fault. +++ +++@smallexample +++@group +++(@value{GDBP}) continue +++Program received signal SIGSEGV, Segmentation fault. +++0x0000000000400766 in main () +++69 *(int *)p = 0; +++(@value{GDBP}) ptype $_siginfo +++type = struct @{ +++ int si_signo; +++ int si_errno; +++ int si_code; +++ union @{ +++ int _pad[28]; +++ struct @{...@} _kill; +++ struct @{...@} _timer; +++ struct @{...@} _rt; +++ struct @{...@} _sigchld; +++ struct @{...@} _sigfault; +++ struct @{...@} _sigpoll; +++ @} _sifields; +++@} +++(@value{GDBP}) ptype $_siginfo._sifields._sigfault +++type = struct @{ +++ void *si_addr; +++@} +++(@value{GDBP}) p $_siginfo._sifields._sigfault.si_addr +++$1 = (void *) 0x7ffff7ff7000 +++@end group +++@end smallexample +++ +++Depending on target support, @code{$_siginfo} may also be writable. +++ +++@cindex Intel MPX boundary violations +++@cindex boundary violations, Intel MPX +++On some targets, a @code{SIGSEGV} can be caused by a boundary +++violation, i.e., accessing an address outside of the allowed range. +++In those cases @value{GDBN} may displays additional information, +++depending on how @value{GDBN} has been told to handle the signal. +++With @code{handle stop SIGSEGV}, @value{GDBN} displays the violation +++kind: "Upper" or "Lower", the memory address accessed and the +++bounds, while with @code{handle nostop SIGSEGV} no additional +++information is displayed. +++ +++The usual output of a segfault is: +++@smallexample +++Program received signal SIGSEGV, Segmentation fault +++0x0000000000400d7c in upper () at i386-mpx-sigsegv.c:68 +++68 value = *(p + len); +++@end smallexample +++ +++While a bound violation is presented as: +++@smallexample +++Program received signal SIGSEGV, Segmentation fault +++Upper bound violation while accessing address 0x7fffffffc3b3 +++Bounds: [lower = 0x7fffffffc390, upper = 0x7fffffffc3a3] +++0x0000000000400d7c in upper () at i386-mpx-sigsegv.c:68 +++68 value = *(p + len); +++@end smallexample +++ +++@node Thread Stops +++@section Stopping and Starting Multi-thread Programs +++ +++@cindex stopped threads +++@cindex threads, stopped +++ +++@cindex continuing threads +++@cindex threads, continuing +++ +++@value{GDBN} supports debugging programs with multiple threads +++(@pxref{Threads,, Debugging Programs with Multiple Threads}). There +++are two modes of controlling execution of your program within the +++debugger. In the default mode, referred to as @dfn{all-stop mode}, +++when any thread in your program stops (for example, at a breakpoint +++or while being stepped), all other threads in the program are also stopped by +++@value{GDBN}. On some targets, @value{GDBN} also supports +++@dfn{non-stop mode}, in which other threads can continue to run freely while +++you examine the stopped thread in the debugger. +++ +++@menu +++* All-Stop Mode:: All threads stop when GDB takes control +++* Non-Stop Mode:: Other threads continue to execute +++* Background Execution:: Running your program asynchronously +++* Thread-Specific Breakpoints:: Controlling breakpoints +++* Interrupted System Calls:: GDB may interfere with system calls +++* Observer Mode:: GDB does not alter program behavior +++@end menu +++ +++@node All-Stop Mode +++@subsection All-Stop Mode +++ +++@cindex all-stop mode +++ +++In all-stop mode, whenever your program stops under @value{GDBN} for any reason, +++@emph{all} threads of execution stop, not just the current thread. This +++allows you to examine the overall state of the program, including +++switching between threads, without worrying that things may change +++underfoot. +++ +++Conversely, whenever you restart the program, @emph{all} threads start +++executing. @emph{This is true even when single-stepping} with commands +++like @code{step} or @code{next}. +++ +++In particular, @value{GDBN} cannot single-step all threads in lockstep. +++Since thread scheduling is up to your debugging target's operating +++system (not controlled by @value{GDBN}), other threads may +++execute more than one statement while the current thread completes a +++single step. Moreover, in general other threads stop in the middle of a +++statement, rather than at a clean statement boundary, when the program +++stops. +++ +++You might even find your program stopped in another thread after +++continuing or even single-stepping. This happens whenever some other +++thread runs into a breakpoint, a signal, or an exception before the +++first thread completes whatever you requested. +++ +++@cindex automatic thread selection +++@cindex switching threads automatically +++@cindex threads, automatic switching +++Whenever @value{GDBN} stops your program, due to a breakpoint or a +++signal, it automatically selects the thread where that breakpoint or +++signal happened. @value{GDBN} alerts you to the context switch with a +++message such as @samp{[Switching to Thread @var{n}]} to identify the +++thread. +++ +++On some OSes, you can modify @value{GDBN}'s default behavior by +++locking the OS scheduler to allow only a single thread to run. +++ +++@table @code +++@item set scheduler-locking @var{mode} +++@cindex scheduler locking mode +++@cindex lock scheduler +++Set the scheduler locking mode. It applies to normal execution, +++record mode, and replay mode. If it is @code{off}, then there is no +++locking and any thread may run at any time. If @code{on}, then only +++the current thread may run when the inferior is resumed. The +++@code{step} mode optimizes for single-stepping; it prevents other +++threads from preempting the current thread while you are stepping, so +++that the focus of debugging does not change unexpectedly. Other +++threads never get a chance to run when you step, and they are +++completely free to run when you use commands like @samp{continue}, +++@samp{until}, or @samp{finish}. However, unless another thread hits a +++breakpoint during its timeslice, @value{GDBN} does not change the +++current thread away from the thread that you are debugging. The +++@code{replay} mode behaves like @code{off} in record mode and like +++@code{on} in replay mode. +++ +++@item show scheduler-locking +++Display the current scheduler locking mode. +++@end table +++ +++@cindex resume threads of multiple processes simultaneously +++By default, when you issue one of the execution commands such as +++@code{continue}, @code{next} or @code{step}, @value{GDBN} allows only +++threads of the current inferior to run. For example, if @value{GDBN} +++is attached to two inferiors, each with two threads, the +++@code{continue} command resumes only the two threads of the current +++inferior. This is useful, for example, when you debug a program that +++forks and you want to hold the parent stopped (so that, for instance, +++it doesn't run to exit), while you debug the child. In other +++situations, you may not be interested in inspecting the current state +++of any of the processes @value{GDBN} is attached to, and you may want +++to resume them all until some breakpoint is hit. In the latter case, +++you can instruct @value{GDBN} to allow all threads of all the +++inferiors to run with the @w{@code{set schedule-multiple}} command. +++ +++@table @code +++@kindex set schedule-multiple +++@item set schedule-multiple +++Set the mode for allowing threads of multiple processes to be resumed +++when an execution command is issued. When @code{on}, all threads of +++all processes are allowed to run. When @code{off}, only the threads +++of the current process are resumed. The default is @code{off}. The +++@code{scheduler-locking} mode takes precedence when set to @code{on}, +++or while you are stepping and set to @code{step}. +++ +++@item show schedule-multiple +++Display the current mode for resuming the execution of threads of +++multiple processes. +++@end table +++ +++@node Non-Stop Mode +++@subsection Non-Stop Mode +++ +++@cindex non-stop mode +++ +++@c This section is really only a place-holder, and needs to be expanded +++@c with more details. +++ +++For some multi-threaded targets, @value{GDBN} supports an optional +++mode of operation in which you can examine stopped program threads in +++the debugger while other threads continue to execute freely. This +++minimizes intrusion when debugging live systems, such as programs +++where some threads have real-time constraints or must continue to +++respond to external events. This is referred to as @dfn{non-stop} mode. +++ +++In non-stop mode, when a thread stops to report a debugging event, +++@emph{only} that thread is stopped; @value{GDBN} does not stop other +++threads as well, in contrast to the all-stop mode behavior. Additionally, +++execution commands such as @code{continue} and @code{step} apply by default +++only to the current thread in non-stop mode, rather than all threads as +++in all-stop mode. This allows you to control threads explicitly in +++ways that are not possible in all-stop mode --- for example, stepping +++one thread while allowing others to run freely, stepping +++one thread while holding all others stopped, or stepping several threads +++independently and simultaneously. +++ +++To enter non-stop mode, use this sequence of commands before you run +++or attach to your program: +++ +++@smallexample +++# If using the CLI, pagination breaks non-stop. +++set pagination off +++ +++# Finally, turn it on! +++set non-stop on +++@end smallexample +++ +++You can use these commands to manipulate the non-stop mode setting: +++ +++@table @code +++@kindex set non-stop +++@item set non-stop on +++Enable selection of non-stop mode. +++@item set non-stop off +++Disable selection of non-stop mode. +++@kindex show non-stop +++@item show non-stop +++Show the current non-stop enablement setting. +++@end table +++ +++Note these commands only reflect whether non-stop mode is enabled, +++not whether the currently-executing program is being run in non-stop mode. +++In particular, the @code{set non-stop} preference is only consulted when +++@value{GDBN} starts or connects to the target program, and it is generally +++not possible to switch modes once debugging has started. Furthermore, +++since not all targets support non-stop mode, even when you have enabled +++non-stop mode, @value{GDBN} may still fall back to all-stop operation by +++default. +++ +++In non-stop mode, all execution commands apply only to the current thread +++by default. That is, @code{continue} only continues one thread. +++To continue all threads, issue @code{continue -a} or @code{c -a}. +++ +++You can use @value{GDBN}'s background execution commands +++(@pxref{Background Execution}) to run some threads in the background +++while you continue to examine or step others from @value{GDBN}. +++The MI execution commands (@pxref{GDB/MI Program Execution}) are +++always executed asynchronously in non-stop mode. +++ +++Suspending execution is done with the @code{interrupt} command when +++running in the background, or @kbd{Ctrl-c} during foreground execution. +++In all-stop mode, this stops the whole process; +++but in non-stop mode the interrupt applies only to the current thread. +++To stop the whole program, use @code{interrupt -a}. +++ +++Other execution commands do not currently support the @code{-a} option. +++ +++In non-stop mode, when a thread stops, @value{GDBN} doesn't automatically make +++that thread current, as it does in all-stop mode. This is because the +++thread stop notifications are asynchronous with respect to @value{GDBN}'s +++command interpreter, and it would be confusing if @value{GDBN} unexpectedly +++changed to a different thread just as you entered a command to operate on the +++previously current thread. +++ +++@node Background Execution +++@subsection Background Execution +++ +++@cindex foreground execution +++@cindex background execution +++@cindex asynchronous execution +++@cindex execution, foreground, background and asynchronous +++ +++@value{GDBN}'s execution commands have two variants: the normal +++foreground (synchronous) behavior, and a background +++(asynchronous) behavior. In foreground execution, @value{GDBN} waits for +++the program to report that some thread has stopped before prompting for +++another command. In background execution, @value{GDBN} immediately gives +++a command prompt so that you can issue other commands while your program runs. +++ +++If the target doesn't support async mode, @value{GDBN} issues an error +++message if you attempt to use the background execution commands. +++ +++@cindex @code{&}, background execution of commands +++To specify background execution, add a @code{&} to the command. For example, +++the background form of the @code{continue} command is @code{continue&}, or +++just @code{c&}. The execution commands that accept background execution +++are: +++ +++@table @code +++@kindex run& +++@item run +++@xref{Starting, , Starting your Program}. +++ +++@item attach +++@kindex attach& +++@xref{Attach, , Debugging an Already-running Process}. +++ +++@item step +++@kindex step& +++@xref{Continuing and Stepping, step}. +++ +++@item stepi +++@kindex stepi& +++@xref{Continuing and Stepping, stepi}. +++ +++@item next +++@kindex next& +++@xref{Continuing and Stepping, next}. +++ +++@item nexti +++@kindex nexti& +++@xref{Continuing and Stepping, nexti}. +++ +++@item continue +++@kindex continue& +++@xref{Continuing and Stepping, continue}. +++ +++@item finish +++@kindex finish& +++@xref{Continuing and Stepping, finish}. +++ +++@item until +++@kindex until& +++@xref{Continuing and Stepping, until}. +++ +++@end table +++ +++Background execution is especially useful in conjunction with non-stop +++mode for debugging programs with multiple threads; see @ref{Non-Stop Mode}. +++However, you can also use these commands in the normal all-stop mode with +++the restriction that you cannot issue another execution command until the +++previous one finishes. Examples of commands that are valid in all-stop +++mode while the program is running include @code{help} and @code{info break}. +++ +++You can interrupt your program while it is running in the background by +++using the @code{interrupt} command. +++ +++@table @code +++@kindex interrupt +++@item interrupt +++@itemx interrupt -a +++ +++Suspend execution of the running program. In all-stop mode, +++@code{interrupt} stops the whole process, but in non-stop mode, it stops +++only the current thread. To stop the whole program in non-stop mode, +++use @code{interrupt -a}. +++@end table +++ +++@node Thread-Specific Breakpoints +++@subsection Thread-Specific Breakpoints +++ +++When your program has multiple threads (@pxref{Threads,, Debugging +++Programs with Multiple Threads}), you can choose whether to set +++breakpoints on all threads, or on a particular thread. +++ +++@table @code +++@cindex breakpoints and threads +++@cindex thread breakpoints +++@kindex break @dots{} thread @var{thread-id} +++@item break @var{location} thread @var{thread-id} +++@itemx break @var{location} thread @var{thread-id} if @dots{} +++@var{location} specifies source lines; there are several ways of +++writing them (@pxref{Specify Location}), but the effect is always to +++specify some source line. +++ +++Use the qualifier @samp{thread @var{thread-id}} with a breakpoint command +++to specify that you only want @value{GDBN} to stop the program when a +++particular thread reaches this breakpoint. The @var{thread-id} specifier +++is one of the thread identifiers assigned by @value{GDBN}, shown +++in the first column of the @samp{info threads} display. +++ +++If you do not specify @samp{thread @var{thread-id}} when you set a +++breakpoint, the breakpoint applies to @emph{all} threads of your +++program. +++ +++You can use the @code{thread} qualifier on conditional breakpoints as +++well; in this case, place @samp{thread @var{thread-id}} before or +++after the breakpoint condition, like this: +++ +++@smallexample +++(@value{GDBP}) break frik.c:13 thread 28 if bartab > lim +++@end smallexample +++ +++@end table +++ +++Thread-specific breakpoints are automatically deleted when +++@value{GDBN} detects the corresponding thread is no longer in the +++thread list. For example: +++ +++@smallexample +++(@value{GDBP}) c +++Thread-specific breakpoint 3 deleted - thread 28 no longer in the thread list. +++@end smallexample +++ +++There are several ways for a thread to disappear, such as a regular +++thread exit, but also when you detach from the process with the +++@code{detach} command (@pxref{Attach, ,Debugging an Already-running +++Process}), or if @value{GDBN} loses the remote connection +++(@pxref{Remote Debugging}), etc. Note that with some targets, +++@value{GDBN} is only able to detect a thread has exited when the user +++explictly asks for the thread list with the @code{info threads} +++command. +++ +++@node Interrupted System Calls +++@subsection Interrupted System Calls +++ +++@cindex thread breakpoints and system calls +++@cindex system calls and thread breakpoints +++@cindex premature return from system calls +++There is an unfortunate side effect when using @value{GDBN} to debug +++multi-threaded programs. If one thread stops for a +++breakpoint, or for some other reason, and another thread is blocked in a +++system call, then the system call may return prematurely. This is a +++consequence of the interaction between multiple threads and the signals +++that @value{GDBN} uses to implement breakpoints and other events that +++stop execution. +++ +++To handle this problem, your program should check the return value of +++each system call and react appropriately. This is good programming +++style anyways. +++ +++For example, do not write code like this: +++ +++@smallexample +++ sleep (10); +++@end smallexample +++ +++The call to @code{sleep} will return early if a different thread stops +++at a breakpoint or for some other reason. +++ +++Instead, write this: +++ +++@smallexample +++ int unslept = 10; +++ while (unslept > 0) +++ unslept = sleep (unslept); +++@end smallexample +++ +++A system call is allowed to return early, so the system is still +++conforming to its specification. But @value{GDBN} does cause your +++multi-threaded program to behave differently than it would without +++@value{GDBN}. +++ +++Also, @value{GDBN} uses internal breakpoints in the thread library to +++monitor certain events such as thread creation and thread destruction. +++When such an event happens, a system call in another thread may return +++prematurely, even though your program does not appear to stop. +++ +++@node Observer Mode +++@subsection Observer Mode +++ +++If you want to build on non-stop mode and observe program behavior +++without any chance of disruption by @value{GDBN}, you can set +++variables to disable all of the debugger's attempts to modify state, +++whether by writing memory, inserting breakpoints, etc. These operate +++at a low level, intercepting operations from all commands. +++ +++When all of these are set to @code{off}, then @value{GDBN} is said to +++be @dfn{observer mode}. As a convenience, the variable +++@code{observer} can be set to disable these, plus enable non-stop +++mode. +++ +++Note that @value{GDBN} will not prevent you from making nonsensical +++combinations of these settings. For instance, if you have enabled +++@code{may-insert-breakpoints} but disabled @code{may-write-memory}, +++then breakpoints that work by writing trap instructions into the code +++stream will still not be able to be placed. +++ +++@table @code +++ +++@kindex observer +++@item set observer on +++@itemx set observer off +++When set to @code{on}, this disables all the permission variables +++below (except for @code{insert-fast-tracepoints}), plus enables +++non-stop debugging. Setting this to @code{off} switches back to +++normal debugging, though remaining in non-stop mode. +++ +++@item show observer +++Show whether observer mode is on or off. +++ +++@kindex may-write-registers +++@item set may-write-registers on +++@itemx set may-write-registers off +++This controls whether @value{GDBN} will attempt to alter the values of +++registers, such as with assignment expressions in @code{print}, or the +++@code{jump} command. It defaults to @code{on}. +++ +++@item show may-write-registers +++Show the current permission to write registers. +++ +++@kindex may-write-memory +++@item set may-write-memory on +++@itemx set may-write-memory off +++This controls whether @value{GDBN} will attempt to alter the contents +++of memory, such as with assignment expressions in @code{print}. It +++defaults to @code{on}. +++ +++@item show may-write-memory +++Show the current permission to write memory. +++ +++@kindex may-insert-breakpoints +++@item set may-insert-breakpoints on +++@itemx set may-insert-breakpoints off +++This controls whether @value{GDBN} will attempt to insert breakpoints. +++This affects all breakpoints, including internal breakpoints defined +++by @value{GDBN}. It defaults to @code{on}. +++ +++@item show may-insert-breakpoints +++Show the current permission to insert breakpoints. +++ +++@kindex may-insert-tracepoints +++@item set may-insert-tracepoints on +++@itemx set may-insert-tracepoints off +++This controls whether @value{GDBN} will attempt to insert (regular) +++tracepoints at the beginning of a tracing experiment. It affects only +++non-fast tracepoints, fast tracepoints being under the control of +++@code{may-insert-fast-tracepoints}. It defaults to @code{on}. +++ +++@item show may-insert-tracepoints +++Show the current permission to insert tracepoints. +++ +++@kindex may-insert-fast-tracepoints +++@item set may-insert-fast-tracepoints on +++@itemx set may-insert-fast-tracepoints off +++This controls whether @value{GDBN} will attempt to insert fast +++tracepoints at the beginning of a tracing experiment. It affects only +++fast tracepoints, regular (non-fast) tracepoints being under the +++control of @code{may-insert-tracepoints}. It defaults to @code{on}. +++ +++@item show may-insert-fast-tracepoints +++Show the current permission to insert fast tracepoints. +++ +++@kindex may-interrupt +++@item set may-interrupt on +++@itemx set may-interrupt off +++This controls whether @value{GDBN} will attempt to interrupt or stop +++program execution. When this variable is @code{off}, the +++@code{interrupt} command will have no effect, nor will +++@kbd{Ctrl-c}. It defaults to @code{on}. +++ +++@item show may-interrupt +++Show the current permission to interrupt or stop the program. +++ +++@end table +++ +++@node Reverse Execution +++@chapter Running programs backward +++@cindex reverse execution +++@cindex running programs backward +++ +++When you are debugging a program, it is not unusual to realize that +++you have gone too far, and some event of interest has already happened. +++If the target environment supports it, @value{GDBN} can allow you to +++``rewind'' the program by running it backward. +++ +++A target environment that supports reverse execution should be able +++to ``undo'' the changes in machine state that have taken place as the +++program was executing normally. Variables, registers etc.@: should +++revert to their previous values. Obviously this requires a great +++deal of sophistication on the part of the target environment; not +++all target environments can support reverse execution. +++ +++When a program is executed in reverse, the instructions that +++have most recently been executed are ``un-executed'', in reverse +++order. The program counter runs backward, following the previous +++thread of execution in reverse. As each instruction is ``un-executed'', +++the values of memory and/or registers that were changed by that +++instruction are reverted to their previous states. After executing +++a piece of source code in reverse, all side effects of that code +++should be ``undone'', and all variables should be returned to their +++prior values@footnote{ +++Note that some side effects are easier to undo than others. For instance, +++memory and registers are relatively easy, but device I/O is hard. Some +++targets may be able undo things like device I/O, and some may not. +++ +++The contract between @value{GDBN} and the reverse executing target +++requires only that the target do something reasonable when +++@value{GDBN} tells it to execute backwards, and then report the +++results back to @value{GDBN}. Whatever the target reports back to +++@value{GDBN}, @value{GDBN} will report back to the user. @value{GDBN} +++assumes that the memory and registers that the target reports are in a +++consistent state, but @value{GDBN} accepts whatever it is given. +++}. +++ +++On some platforms, @value{GDBN} has built-in support for reverse +++execution, activated with the @code{record} or @code{record btrace} +++commands. @xref{Process Record and Replay}. Some remote targets, +++typically full system emulators, support reverse execution directly +++without requiring any special command. +++ +++If you are debugging in a target environment that supports +++reverse execution, @value{GDBN} provides the following commands. +++ +++@table @code +++@kindex reverse-continue +++@kindex rc @r{(@code{reverse-continue})} +++@item reverse-continue @r{[}@var{ignore-count}@r{]} +++@itemx rc @r{[}@var{ignore-count}@r{]} +++Beginning at the point where your program last stopped, start executing +++in reverse. Reverse execution will stop for breakpoints and synchronous +++exceptions (signals), just like normal execution. Behavior of +++asynchronous signals depends on the target environment. +++ +++@kindex reverse-step +++@kindex rs @r{(@code{step})} +++@item reverse-step @r{[}@var{count}@r{]} +++Run the program backward until control reaches the start of a +++different source line; then stop it, and return control to @value{GDBN}. +++ +++Like the @code{step} command, @code{reverse-step} will only stop +++at the beginning of a source line. It ``un-executes'' the previously +++executed source line. If the previous source line included calls to +++debuggable functions, @code{reverse-step} will step (backward) into +++the called function, stopping at the beginning of the @emph{last} +++statement in the called function (typically a return statement). +++ +++Also, as with the @code{step} command, if non-debuggable functions are +++called, @code{reverse-step} will run thru them backward without stopping. +++ +++@kindex reverse-stepi +++@kindex rsi @r{(@code{reverse-stepi})} +++@item reverse-stepi @r{[}@var{count}@r{]} +++Reverse-execute one machine instruction. Note that the instruction +++to be reverse-executed is @emph{not} the one pointed to by the program +++counter, but the instruction executed prior to that one. For instance, +++if the last instruction was a jump, @code{reverse-stepi} will take you +++back from the destination of the jump to the jump instruction itself. +++ +++@kindex reverse-next +++@kindex rn @r{(@code{reverse-next})} +++@item reverse-next @r{[}@var{count}@r{]} +++Run backward to the beginning of the previous line executed in +++the current (innermost) stack frame. If the line contains function +++calls, they will be ``un-executed'' without stopping. Starting from +++the first line of a function, @code{reverse-next} will take you back +++to the caller of that function, @emph{before} the function was called, +++just as the normal @code{next} command would take you from the last +++line of a function back to its return to its caller +++@footnote{Unless the code is too heavily optimized.}. +++ +++@kindex reverse-nexti +++@kindex rni @r{(@code{reverse-nexti})} +++@item reverse-nexti @r{[}@var{count}@r{]} +++Like @code{nexti}, @code{reverse-nexti} executes a single instruction +++in reverse, except that called functions are ``un-executed'' atomically. +++That is, if the previously executed instruction was a return from +++another function, @code{reverse-nexti} will continue to execute +++in reverse until the call to that function (from the current stack +++frame) is reached. +++ +++@kindex reverse-finish +++@item reverse-finish +++Just as the @code{finish} command takes you to the point where the +++current function returns, @code{reverse-finish} takes you to the point +++where it was called. Instead of ending up at the end of the current +++function invocation, you end up at the beginning. +++ +++@kindex set exec-direction +++@item set exec-direction +++Set the direction of target execution. +++@item set exec-direction reverse +++@cindex execute forward or backward in time +++@value{GDBN} will perform all execution commands in reverse, until the +++exec-direction mode is changed to ``forward''. Affected commands include +++@code{step, stepi, next, nexti, continue, and finish}. The @code{return} +++command cannot be used in reverse mode. +++@item set exec-direction forward +++@value{GDBN} will perform all execution commands in the normal fashion. +++This is the default. +++@end table +++ +++ +++@node Process Record and Replay +++@chapter Recording Inferior's Execution and Replaying It +++@cindex process record and replay +++@cindex recording inferior's execution and replaying it +++ +++On some platforms, @value{GDBN} provides a special @dfn{process record +++and replay} target that can record a log of the process execution, and +++replay it later with both forward and reverse execution commands. +++ +++@cindex replay mode +++When this target is in use, if the execution log includes the record +++for the next instruction, @value{GDBN} will debug in @dfn{replay +++mode}. In the replay mode, the inferior does not really execute code +++instructions. Instead, all the events that normally happen during +++code execution are taken from the execution log. While code is not +++really executed in replay mode, the values of registers (including the +++program counter register) and the memory of the inferior are still +++changed as they normally would. Their contents are taken from the +++execution log. +++ +++@cindex record mode +++If the record for the next instruction is not in the execution log, +++@value{GDBN} will debug in @dfn{record mode}. In this mode, the +++inferior executes normally, and @value{GDBN} records the execution log +++for future replay. +++ +++The process record and replay target supports reverse execution +++(@pxref{Reverse Execution}), even if the platform on which the +++inferior runs does not. However, the reverse execution is limited in +++this case by the range of the instructions recorded in the execution +++log. In other words, reverse execution on platforms that don't +++support it directly can only be done in the replay mode. +++ +++When debugging in the reverse direction, @value{GDBN} will work in +++replay mode as long as the execution log includes the record for the +++previous instruction; otherwise, it will work in record mode, if the +++platform supports reverse execution, or stop if not. +++ +++Currently, process record and replay is supported on ARM, Aarch64, +++Moxie, PowerPC, PowerPC64, S/390, and x86 (i386/amd64) running +++GNU/Linux. Process record and replay can be used both when native +++debugging, and when remote debugging via @code{gdbserver}. +++ +++For architecture environments that support process record and replay, +++@value{GDBN} provides the following commands: +++ +++@table @code +++@kindex target record +++@kindex target record-full +++@kindex target record-btrace +++@kindex record +++@kindex record full +++@kindex record btrace +++@kindex record btrace bts +++@kindex record btrace pt +++@kindex record bts +++@kindex record pt +++@kindex rec +++@kindex rec full +++@kindex rec btrace +++@kindex rec btrace bts +++@kindex rec btrace pt +++@kindex rec bts +++@kindex rec pt +++@item record @var{method} +++This command starts the process record and replay target. The +++recording method can be specified as parameter. Without a parameter +++the command uses the @code{full} recording method. The following +++recording methods are available: +++ +++@table @code +++@item full +++Full record/replay recording using @value{GDBN}'s software record and +++replay implementation. This method allows replaying and reverse +++execution. +++ +++@item btrace @var{format} +++Hardware-supported instruction recording, supported on Intel +++processors. This method does not record data. Further, the data is +++collected in a ring buffer so old data will be overwritten when the +++buffer is full. It allows limited reverse execution. Variables and +++registers are not available during reverse execution. In remote +++debugging, recording continues on disconnect. Recorded data can be +++inspected after reconnecting. The recording may be stopped using +++@code{record stop}. +++ +++The recording format can be specified as parameter. Without a parameter +++the command chooses the recording format. The following recording +++formats are available: +++ +++@table @code +++@item bts +++@cindex branch trace store +++Use the @dfn{Branch Trace Store} (@acronym{BTS}) recording format. In +++this format, the processor stores a from/to record for each executed +++branch in the btrace ring buffer. +++ +++@item pt +++@cindex Intel Processor Trace +++Use the @dfn{Intel Processor Trace} recording format. In this +++format, the processor stores the execution trace in a compressed form +++that is afterwards decoded by @value{GDBN}. +++ +++The trace can be recorded with very low overhead. The compressed +++trace format also allows small trace buffers to already contain a big +++number of instructions compared to @acronym{BTS}. +++ +++Decoding the recorded execution trace, on the other hand, is more +++expensive than decoding @acronym{BTS} trace. This is mostly due to the +++increased number of instructions to process. You should increase the +++buffer-size with care. +++@end table +++ +++Not all recording formats may be available on all processors. +++@end table +++ +++The process record and replay target can only debug a process that is +++already running. Therefore, you need first to start the process with +++the @kbd{run} or @kbd{start} commands, and then start the recording +++with the @kbd{record @var{method}} command. +++ +++@cindex displaced stepping, and process record and replay +++Displaced stepping (@pxref{Maintenance Commands,, displaced stepping}) +++will be automatically disabled when process record and replay target +++is started. That's because the process record and replay target +++doesn't support displaced stepping. +++ +++@cindex non-stop mode, and process record and replay +++@cindex asynchronous execution, and process record and replay +++If the inferior is in the non-stop mode (@pxref{Non-Stop Mode}) or in +++the asynchronous execution mode (@pxref{Background Execution}), not +++all recording methods are available. The @code{full} recording method +++does not support these two modes. +++ +++@kindex record stop +++@kindex rec s +++@item record stop +++Stop the process record and replay target. When process record and +++replay target stops, the entire execution log will be deleted and the +++inferior will either be terminated, or will remain in its final state. +++ +++When you stop the process record and replay target in record mode (at +++the end of the execution log), the inferior will be stopped at the +++next instruction that would have been recorded. In other words, if +++you record for a while and then stop recording, the inferior process +++will be left in the same state as if the recording never happened. +++ +++On the other hand, if the process record and replay target is stopped +++while in replay mode (that is, not at the end of the execution log, +++but at some earlier point), the inferior process will become ``live'' +++at that earlier state, and it will then be possible to continue the +++usual ``live'' debugging of the process from that state. +++ +++When the inferior process exits, or @value{GDBN} detaches from it, +++process record and replay target will automatically stop itself. +++ +++@kindex record goto +++@item record goto +++Go to a specific location in the execution log. There are several +++ways to specify the location to go to: +++ +++@table @code +++@item record goto begin +++@itemx record goto start +++Go to the beginning of the execution log. +++ +++@item record goto end +++Go to the end of the execution log. +++ +++@item record goto @var{n} +++Go to instruction number @var{n} in the execution log. +++@end table +++ +++@kindex record save +++@item record save @var{filename} +++Save the execution log to a file @file{@var{filename}}. +++Default filename is @file{gdb_record.@var{process_id}}, where +++@var{process_id} is the process ID of the inferior. +++ +++This command may not be available for all recording methods. +++ +++@kindex record restore +++@item record restore @var{filename} +++Restore the execution log from a file @file{@var{filename}}. +++File must have been created with @code{record save}. +++ +++@kindex set record full +++@item set record full insn-number-max @var{limit} +++@itemx set record full insn-number-max unlimited +++Set the limit of instructions to be recorded for the @code{full} +++recording method. Default value is 200000. +++ +++If @var{limit} is a positive number, then @value{GDBN} will start +++deleting instructions from the log once the number of the record +++instructions becomes greater than @var{limit}. For every new recorded +++instruction, @value{GDBN} will delete the earliest recorded +++instruction to keep the number of recorded instructions at the limit. +++(Since deleting recorded instructions loses information, @value{GDBN} +++lets you control what happens when the limit is reached, by means of +++the @code{stop-at-limit} option, described below.) +++ +++If @var{limit} is @code{unlimited} or zero, @value{GDBN} will never +++delete recorded instructions from the execution log. The number of +++recorded instructions is limited only by the available memory. +++ +++@kindex show record full +++@item show record full insn-number-max +++Show the limit of instructions to be recorded with the @code{full} +++recording method. +++ +++@item set record full stop-at-limit +++Control the behavior of the @code{full} recording method when the +++number of recorded instructions reaches the limit. If ON (the +++default), @value{GDBN} will stop when the limit is reached for the +++first time and ask you whether you want to stop the inferior or +++continue running it and recording the execution log. If you decide +++to continue recording, each new recorded instruction will cause the +++oldest one to be deleted. +++ +++If this option is OFF, @value{GDBN} will automatically delete the +++oldest record to make room for each new one, without asking. +++ +++@item show record full stop-at-limit +++Show the current setting of @code{stop-at-limit}. +++ +++@item set record full memory-query +++Control the behavior when @value{GDBN} is unable to record memory +++changes caused by an instruction for the @code{full} recording method. +++If ON, @value{GDBN} will query whether to stop the inferior in that +++case. +++ +++If this option is OFF (the default), @value{GDBN} will automatically +++ignore the effect of such instructions on memory. Later, when +++@value{GDBN} replays this execution log, it will mark the log of this +++instruction as not accessible, and it will not affect the replay +++results. +++ +++@item show record full memory-query +++Show the current setting of @code{memory-query}. +++ +++@kindex set record btrace +++The @code{btrace} record target does not trace data. As a +++convenience, when replaying, @value{GDBN} reads read-only memory off +++the live program directly, assuming that the addresses of the +++read-only areas don't change. This for example makes it possible to +++disassemble code while replaying, but not to print variables. +++In some cases, being able to inspect variables might be useful. +++You can use the following command for that: +++ +++@item set record btrace replay-memory-access +++Control the behavior of the @code{btrace} recording method when +++accessing memory during replay. If @code{read-only} (the default), +++@value{GDBN} will only allow accesses to read-only memory. +++If @code{read-write}, @value{GDBN} will allow accesses to read-only +++and to read-write memory. Beware that the accessed memory corresponds +++to the live target and not necessarily to the current replay +++position. +++ +++@item set record btrace cpu @var{identifier} +++Set the processor to be used for enabling workarounds for processor +++errata when decoding the trace. +++ +++Processor errata are defects in processor operation, caused by its +++design or manufacture. They can cause a trace not to match the +++specification. This, in turn, may cause trace decode to fail. +++@value{GDBN} can detect erroneous trace packets and correct them, thus +++avoiding the decoding failures. These corrections are known as +++@dfn{errata workarounds}, and are enabled based on the processor on +++which the trace was recorded. +++ +++By default, @value{GDBN} attempts to detect the processor +++automatically, and apply the necessary workarounds for it. However, +++you may need to specify the processor if @value{GDBN} does not yet +++support it. This command allows you to do that, and also allows to +++disable the workarounds. +++ +++The argument @var{identifier} identifies the @sc{cpu} and is of the +++form: @code{@var{vendor}:@var{processor identifier}}. In addition, +++there are two special identifiers, @code{none} and @code{auto} +++(default). +++ +++The following vendor identifiers and corresponding processor +++identifiers are currently supported: +++ +++@multitable @columnfractions .1 .9 +++ +++@item @code{intel} +++@tab @var{family}/@var{model}[/@var{stepping}] +++ +++@end multitable +++ +++On GNU/Linux systems, the processor @var{family}, @var{model}, and +++@var{stepping} can be obtained from @code{/proc/cpuinfo}. +++ +++If @var{identifier} is @code{auto}, enable errata workarounds for the +++processor on which the trace was recorded. If @var{identifier} is +++@code{none}, errata workarounds are disabled. +++ +++For example, when using an old @value{GDBN} on a new system, decode +++may fail because @value{GDBN} does not support the new processor. It +++often suffices to specify an older processor that @value{GDBN} +++supports. +++ +++@smallexample +++(gdb) info record +++Active record target: record-btrace +++Recording format: Intel Processor Trace. +++Buffer size: 16kB. +++Failed to configure the Intel Processor Trace decoder: unknown cpu. +++(gdb) set record btrace cpu intel:6/158 +++(gdb) info record +++Active record target: record-btrace +++Recording format: Intel Processor Trace. +++Buffer size: 16kB. +++Recorded 84872 instructions in 3189 functions (0 gaps) for thread 1 (...). +++@end smallexample +++ +++@kindex show record btrace +++@item show record btrace replay-memory-access +++Show the current setting of @code{replay-memory-access}. +++ +++@item show record btrace cpu +++Show the processor to be used for enabling trace decode errata +++workarounds. +++ +++@kindex set record btrace bts +++@item set record btrace bts buffer-size @var{size} +++@itemx set record btrace bts buffer-size unlimited +++Set the requested ring buffer size for branch tracing in @acronym{BTS} +++format. Default is 64KB. +++ +++If @var{size} is a positive number, then @value{GDBN} will try to +++allocate a buffer of at least @var{size} bytes for each new thread +++that uses the btrace recording method and the @acronym{BTS} format. +++The actually obtained buffer size may differ from the requested +++@var{size}. Use the @code{info record} command to see the actual +++buffer size for each thread that uses the btrace recording method and +++the @acronym{BTS} format. +++ +++If @var{limit} is @code{unlimited} or zero, @value{GDBN} will try to +++allocate a buffer of 4MB. +++ +++Bigger buffers mean longer traces. On the other hand, @value{GDBN} will +++also need longer to process the branch trace data before it can be used. +++ +++@item show record btrace bts buffer-size @var{size} +++Show the current setting of the requested ring buffer size for branch +++tracing in @acronym{BTS} format. +++ +++@kindex set record btrace pt +++@item set record btrace pt buffer-size @var{size} +++@itemx set record btrace pt buffer-size unlimited +++Set the requested ring buffer size for branch tracing in Intel +++Processor Trace format. Default is 16KB. +++ +++If @var{size} is a positive number, then @value{GDBN} will try to +++allocate a buffer of at least @var{size} bytes for each new thread +++that uses the btrace recording method and the Intel Processor Trace +++format. The actually obtained buffer size may differ from the +++requested @var{size}. Use the @code{info record} command to see the +++actual buffer size for each thread. +++ +++If @var{limit} is @code{unlimited} or zero, @value{GDBN} will try to +++allocate a buffer of 4MB. +++ +++Bigger buffers mean longer traces. On the other hand, @value{GDBN} will +++also need longer to process the branch trace data before it can be used. +++ +++@item show record btrace pt buffer-size @var{size} +++Show the current setting of the requested ring buffer size for branch +++tracing in Intel Processor Trace format. +++ +++@kindex info record +++@item info record +++Show various statistics about the recording depending on the recording +++method: +++ +++@table @code +++@item full +++For the @code{full} recording method, it shows the state of process +++record and its in-memory execution log buffer, including: +++ +++@itemize @bullet +++@item +++Whether in record mode or replay mode. +++@item +++Lowest recorded instruction number (counting from when the current execution log started recording instructions). +++@item +++Highest recorded instruction number. +++@item +++Current instruction about to be replayed (if in replay mode). +++@item +++Number of instructions contained in the execution log. +++@item +++Maximum number of instructions that may be contained in the execution log. +++@end itemize +++ +++@item btrace +++For the @code{btrace} recording method, it shows: +++ +++@itemize @bullet +++@item +++Recording format. +++@item +++Number of instructions that have been recorded. +++@item +++Number of blocks of sequential control-flow formed by the recorded +++instructions. +++@item +++Whether in record mode or replay mode. +++@end itemize +++ +++For the @code{bts} recording format, it also shows: +++@itemize @bullet +++@item +++Size of the perf ring buffer. +++@end itemize +++ +++For the @code{pt} recording format, it also shows: +++@itemize @bullet +++@item +++Size of the perf ring buffer. +++@end itemize +++@end table +++ +++@kindex record delete +++@kindex rec del +++@item record delete +++When record target runs in replay mode (``in the past''), delete the +++subsequent execution log and begin to record a new execution log starting +++from the current address. This means you will abandon the previously +++recorded ``future'' and begin recording a new ``future''. +++ +++@kindex record instruction-history +++@kindex rec instruction-history +++@item record instruction-history +++Disassembles instructions from the recorded execution log. By +++default, ten instructions are disassembled. This can be changed using +++the @code{set record instruction-history-size} command. Instructions +++are printed in execution order. +++ +++It can also print mixed source+disassembly if you specify the the +++@code{/m} or @code{/s} modifier, and print the raw instructions in hex +++as well as in symbolic form by specifying the @code{/r} modifier. +++ +++The current position marker is printed for the instruction at the +++current program counter value. This instruction can appear multiple +++times in the trace and the current position marker will be printed +++every time. To omit the current position marker, specify the +++@code{/p} modifier. +++ +++To better align the printed instructions when the trace contains +++instructions from more than one function, the function name may be +++omitted by specifying the @code{/f} modifier. +++ +++Speculatively executed instructions are prefixed with @samp{?}. This +++feature is not available for all recording formats. +++ +++There are several ways to specify what part of the execution log to +++disassemble: +++ +++@table @code +++@item record instruction-history @var{insn} +++Disassembles ten instructions starting from instruction number +++@var{insn}. +++ +++@item record instruction-history @var{insn}, +/-@var{n} +++Disassembles @var{n} instructions around instruction number +++@var{insn}. If @var{n} is preceded with @code{+}, disassembles +++@var{n} instructions after instruction number @var{insn}. If +++@var{n} is preceded with @code{-}, disassembles @var{n} +++instructions before instruction number @var{insn}. +++ +++@item record instruction-history +++Disassembles ten more instructions after the last disassembly. +++ +++@item record instruction-history - +++Disassembles ten more instructions before the last disassembly. +++ +++@item record instruction-history @var{begin}, @var{end} +++Disassembles instructions beginning with instruction number +++@var{begin} until instruction number @var{end}. The instruction +++number @var{end} is included. +++@end table +++ +++This command may not be available for all recording methods. +++ +++@kindex set record +++@item set record instruction-history-size @var{size} +++@itemx set record instruction-history-size unlimited +++Define how many instructions to disassemble in the @code{record +++instruction-history} command. The default value is 10. +++A @var{size} of @code{unlimited} means unlimited instructions. +++ +++@kindex show record +++@item show record instruction-history-size +++Show how many instructions to disassemble in the @code{record +++instruction-history} command. +++ +++@kindex record function-call-history +++@kindex rec function-call-history +++@item record function-call-history +++Prints the execution history at function granularity. It prints one +++line for each sequence of instructions that belong to the same +++function giving the name of that function, the source lines +++for this instruction sequence (if the @code{/l} modifier is +++specified), and the instructions numbers that form the sequence (if +++the @code{/i} modifier is specified). The function names are indented +++to reflect the call stack depth if the @code{/c} modifier is +++specified. The @code{/l}, @code{/i}, and @code{/c} modifiers can be +++given together. +++ +++@smallexample +++(@value{GDBP}) @b{list 1, 10} +++1 void foo (void) +++2 @{ +++3 @} +++4 +++5 void bar (void) +++6 @{ +++7 ... +++8 foo (); +++9 ... +++10 @} +++(@value{GDBP}) @b{record function-call-history /ilc} +++1 bar inst 1,4 at foo.c:6,8 +++2 foo inst 5,10 at foo.c:2,3 +++3 bar inst 11,13 at foo.c:9,10 +++@end smallexample +++ +++By default, ten lines are printed. This can be changed using the +++@code{set record function-call-history-size} command. Functions are +++printed in execution order. There are several ways to specify what +++to print: +++ +++@table @code +++@item record function-call-history @var{func} +++Prints ten functions starting from function number @var{func}. +++ +++@item record function-call-history @var{func}, +/-@var{n} +++Prints @var{n} functions around function number @var{func}. If +++@var{n} is preceded with @code{+}, prints @var{n} functions after +++function number @var{func}. If @var{n} is preceded with @code{-}, +++prints @var{n} functions before function number @var{func}. +++ +++@item record function-call-history +++Prints ten more functions after the last ten-line print. +++ +++@item record function-call-history - +++Prints ten more functions before the last ten-line print. +++ +++@item record function-call-history @var{begin}, @var{end} +++Prints functions beginning with function number @var{begin} until +++function number @var{end}. The function number @var{end} is included. +++@end table +++ +++This command may not be available for all recording methods. +++ +++@item set record function-call-history-size @var{size} +++@itemx set record function-call-history-size unlimited +++Define how many lines to print in the +++@code{record function-call-history} command. The default value is 10. +++A size of @code{unlimited} means unlimited lines. +++ +++@item show record function-call-history-size +++Show how many lines to print in the +++@code{record function-call-history} command. +++@end table +++ +++ +++@node Stack +++@chapter Examining the Stack +++ +++When your program has stopped, the first thing you need to know is where it +++stopped and how it got there. +++ +++@cindex call stack +++Each time your program performs a function call, information about the call +++is generated. +++That information includes the location of the call in your program, +++the arguments of the call, +++and the local variables of the function being called. +++The information is saved in a block of data called a @dfn{stack frame}. +++The stack frames are allocated in a region of memory called the @dfn{call +++stack}. +++ +++When your program stops, the @value{GDBN} commands for examining the +++stack allow you to see all of this information. +++ +++@cindex selected frame +++One of the stack frames is @dfn{selected} by @value{GDBN} and many +++@value{GDBN} commands refer implicitly to the selected frame. In +++particular, whenever you ask @value{GDBN} for the value of a variable in +++your program, the value is found in the selected frame. There are +++special @value{GDBN} commands to select whichever frame you are +++interested in. @xref{Selection, ,Selecting a Frame}. +++ +++When your program stops, @value{GDBN} automatically selects the +++currently executing frame and describes it briefly, similar to the +++@code{frame} command (@pxref{Frame Info, ,Information about a Frame}). +++ +++@menu +++* Frames:: Stack frames +++* Backtrace:: Backtraces +++* Selection:: Selecting a frame +++* Frame Info:: Information on a frame +++* Frame Apply:: Applying a command to several frames +++* Frame Filter Management:: Managing frame filters +++ +++@end menu +++ +++@node Frames +++@section Stack Frames +++ +++@cindex frame, definition +++@cindex stack frame +++The call stack is divided up into contiguous pieces called @dfn{stack +++frames}, or @dfn{frames} for short; each frame is the data associated +++with one call to one function. The frame contains the arguments given +++to the function, the function's local variables, and the address at +++which the function is executing. +++ +++@cindex initial frame +++@cindex outermost frame +++@cindex innermost frame +++When your program is started, the stack has only one frame, that of the +++function @code{main}. This is called the @dfn{initial} frame or the +++@dfn{outermost} frame. Each time a function is called, a new frame is +++made. Each time a function returns, the frame for that function invocation +++is eliminated. If a function is recursive, there can be many frames for +++the same function. The frame for the function in which execution is +++actually occurring is called the @dfn{innermost} frame. This is the most +++recently created of all the stack frames that still exist. +++ +++@cindex frame pointer +++Inside your program, stack frames are identified by their addresses. A +++stack frame consists of many bytes, each of which has its own address; each +++kind of computer has a convention for choosing one byte whose +++address serves as the address of the frame. Usually this address is kept +++in a register called the @dfn{frame pointer register} +++(@pxref{Registers, $fp}) while execution is going on in that frame. +++ +++@cindex frame level +++@cindex frame number +++@value{GDBN} labels each existing stack frame with a @dfn{level}, a +++number that is zero for the innermost frame, one for the frame that +++called it, and so on upward. These level numbers give you a way of +++designating stack frames in @value{GDBN} commands. The terms +++@dfn{frame number} and @dfn{frame level} can be used interchangeably to +++describe this number. +++ +++@c The -fomit-frame-pointer below perennially causes hbox overflow +++@c underflow problems. +++@cindex frameless execution +++Some compilers provide a way to compile functions so that they operate +++without stack frames. (For example, the @value{NGCC} option +++@smallexample +++@samp{-fomit-frame-pointer} +++@end smallexample +++generates functions without a frame.) +++This is occasionally done with heavily used library functions to save +++the frame setup time. @value{GDBN} has limited facilities for dealing +++with these function invocations. If the innermost function invocation +++has no stack frame, @value{GDBN} nevertheless regards it as though +++it had a separate frame, which is numbered zero as usual, allowing +++correct tracing of the function call chain. However, @value{GDBN} has +++no provision for frameless functions elsewhere in the stack. +++ +++@node Backtrace +++@section Backtraces +++ +++@cindex traceback +++@cindex call stack traces +++A backtrace is a summary of how your program got where it is. It shows one +++line per frame, for many frames, starting with the currently executing +++frame (frame zero), followed by its caller (frame one), and on up the +++stack. +++ +++@anchor{backtrace-command} +++@kindex backtrace +++@kindex bt @r{(@code{backtrace})} +++To print a backtrace of the entire stack, use the @code{backtrace} +++command, or its alias @code{bt}. This command will print one line per +++frame for frames in the stack. By default, all stack frames are +++printed. You can stop the backtrace at any time by typing the system +++interrupt character, normally @kbd{Ctrl-c}. +++ +++@table @code +++@item backtrace [@var{option}]@dots{} [@var{qualifier}]@dots{} [@var{count}] +++@itemx bt [@var{option}]@dots{} [@var{qualifier}]@dots{} [@var{count}] +++Print the backtrace of the entire stack. +++ +++The optional @var{count} can be one of the following: +++ +++@table @code +++@item @var{n} +++@itemx @var{n} +++Print only the innermost @var{n} frames, where @var{n} is a positive +++number. +++ +++@item -@var{n} +++@itemx -@var{n} +++Print only the outermost @var{n} frames, where @var{n} is a positive +++number. +++@end table +++ +++Options: +++ +++@table @code +++@item -full +++Print the values of the local variables also. This can be combined +++with the optional @var{count} to limit the number of frames shown. +++ +++@item -no-filters +++Do not run Python frame filters on this backtrace. @xref{Frame +++Filter API}, for more information. Additionally use @ref{disable +++frame-filter all} to turn off all frame filters. This is only +++relevant when @value{GDBN} has been configured with @code{Python} +++support. +++ +++@item -hide +++A Python frame filter might decide to ``elide'' some frames. Normally +++such elided frames are still printed, but they are indented relative +++to the filtered frames that cause them to be elided. The @code{-hide} +++option causes elided frames to not be printed at all. +++@end table +++ +++The @code{backtrace} command also supports a number of options that +++allow overriding relevant global print settings as set by @code{set +++backtrace} and @code{set print} subcommands: +++ +++@table @code +++@item -past-main [@code{on}|@code{off}] +++Set whether backtraces should continue past @code{main}. Related setting: +++@ref{set backtrace past-main}. +++ +++@item -past-entry [@code{on}|@code{off}] +++Set whether backtraces should continue past the entry point of a program. +++Related setting: @ref{set backtrace past-entry}. +++ +++@item -entry-values @code{no}|@code{only}|@code{preferred}|@code{if-needed}|@code{both}|@code{compact}|@code{default} +++Set printing of function arguments at function entry. +++Related setting: @ref{set print entry-values}. +++ +++@item -frame-arguments @code{all}|@code{scalars}|@code{none} +++Set printing of non-scalar frame arguments. +++Related setting: @ref{set print frame-arguments}. +++ +++@item -raw-frame-arguments [@code{on}|@code{off}] +++Set whether to print frame arguments in raw form. +++Related setting: @ref{set print raw-frame-arguments}. +++ +++@item -frame-info @code{auto}|@code{source-line}|@code{location}|@code{source-and-location}|@code{location-and-address}|@code{short-location} +++Set printing of frame information. +++Related setting: @ref{set print frame-info}. +++@end table +++ +++The optional @var{qualifier} is maintained for backward compatibility. +++It can be one of the following: +++ +++@table @code +++@item full +++Equivalent to the @code{-full} option. +++ +++@item no-filters +++Equivalent to the @code{-no-filters} option. +++ +++@item hide +++Equivalent to the @code{-hide} option. +++@end table +++ +++@end table +++ +++@kindex where +++@kindex info stack +++The names @code{where} and @code{info stack} (abbreviated @code{info s}) +++are additional aliases for @code{backtrace}. +++ +++@cindex multiple threads, backtrace +++In a multi-threaded program, @value{GDBN} by default shows the +++backtrace only for the current thread. To display the backtrace for +++several or all of the threads, use the command @code{thread apply} +++(@pxref{Threads, thread apply}). For example, if you type @kbd{thread +++apply all backtrace}, @value{GDBN} will display the backtrace for all +++the threads; this is handy when you debug a core dump of a +++multi-threaded program. +++ +++Each line in the backtrace shows the frame number and the function name. +++The program counter value is also shown---unless you use @code{set +++print address off}. The backtrace also shows the source file name and +++line number, as well as the arguments to the function. The program +++counter value is omitted if it is at the beginning of the code for that +++line number. +++ +++Here is an example of a backtrace. It was made with the command +++@samp{bt 3}, so it shows the innermost three frames. +++ +++@smallexample +++@group +++#0 m4_traceon (obs=0x24eb0, argc=1, argv=0x2b8c8) +++ at builtin.c:993 +++#1 0x6e38 in expand_macro (sym=0x2b600, data=...) at macro.c:242 +++#2 0x6840 in expand_token (obs=0x0, t=177664, td=0xf7fffb08) +++ at macro.c:71 +++(More stack frames follow...) +++@end group +++@end smallexample +++ +++@noindent +++The display for frame zero does not begin with a program counter +++value, indicating that your program has stopped at the beginning of the +++code for line @code{993} of @code{builtin.c}. +++ +++@noindent +++The value of parameter @code{data} in frame 1 has been replaced by +++@code{@dots{}}. By default, @value{GDBN} prints the value of a parameter +++only if it is a scalar (integer, pointer, enumeration, etc). See command +++@kbd{set print frame-arguments} in @ref{Print Settings} for more details +++on how to configure the way function parameter values are printed. +++The command @kbd{set print frame-info} (@pxref{Print Settings}) controls +++what frame information is printed. +++ +++@cindex optimized out, in backtrace +++@cindex function call arguments, optimized out +++If your program was compiled with optimizations, some compilers will +++optimize away arguments passed to functions if those arguments are +++never used after the call. Such optimizations generate code that +++passes arguments through registers, but doesn't store those arguments +++in the stack frame. @value{GDBN} has no way of displaying such +++arguments in stack frames other than the innermost one. Here's what +++such a backtrace might look like: +++ +++@smallexample +++@group +++#0 m4_traceon (obs=0x24eb0, argc=1, argv=0x2b8c8) +++ at builtin.c:993 +++#1 0x6e38 in expand_macro (sym=) at macro.c:242 +++#2 0x6840 in expand_token (obs=0x0, t=, td=0xf7fffb08) +++ at macro.c:71 +++(More stack frames follow...) +++@end group +++@end smallexample +++ +++@noindent +++The values of arguments that were not saved in their stack frames are +++shown as @samp{}. +++ +++If you need to display the values of such optimized-out arguments, +++either deduce that from other variables whose values depend on the one +++you are interested in, or recompile without optimizations. +++ +++@cindex backtrace beyond @code{main} function +++@cindex program entry point +++@cindex startup code, and backtrace +++Most programs have a standard user entry point---a place where system +++libraries and startup code transition into user code. For C this is +++@code{main}@footnote{ +++Note that embedded programs (the so-called ``free-standing'' +++environment) are not required to have a @code{main} function as the +++entry point. They could even have multiple entry points.}. +++When @value{GDBN} finds the entry function in a backtrace +++it will terminate the backtrace, to avoid tracing into highly +++system-specific (and generally uninteresting) code. +++ +++If you need to examine the startup code, or limit the number of levels +++in a backtrace, you can change this behavior: +++ +++@table @code +++@item set backtrace past-main +++@itemx set backtrace past-main on +++@anchor{set backtrace past-main} +++@kindex set backtrace +++Backtraces will continue past the user entry point. +++ +++@item set backtrace past-main off +++Backtraces will stop when they encounter the user entry point. This is the +++default. +++ +++@item show backtrace past-main +++@kindex show backtrace +++Display the current user entry point backtrace policy. +++ +++@item set backtrace past-entry +++@itemx set backtrace past-entry on +++@anchor{set backtrace past-entry} +++Backtraces will continue past the internal entry point of an application. +++This entry point is encoded by the linker when the application is built, +++and is likely before the user entry point @code{main} (or equivalent) is called. +++ +++@item set backtrace past-entry off +++Backtraces will stop when they encounter the internal entry point of an +++application. This is the default. +++ +++@item show backtrace past-entry +++Display the current internal entry point backtrace policy. +++ +++@item set backtrace limit @var{n} +++@itemx set backtrace limit 0 +++@itemx set backtrace limit unlimited +++@anchor{set backtrace limit} +++@cindex backtrace limit +++Limit the backtrace to @var{n} levels. A value of @code{unlimited} +++or zero means unlimited levels. +++ +++@item show backtrace limit +++Display the current limit on backtrace levels. +++@end table +++ +++You can control how file names are displayed. +++ +++@table @code +++@item set filename-display +++@itemx set filename-display relative +++@cindex filename-display +++Display file names relative to the compilation directory. This is the default. +++ +++@item set filename-display basename +++Display only basename of a filename. +++ +++@item set filename-display absolute +++Display an absolute filename. +++ +++@item show filename-display +++Show the current way to display filenames. +++@end table +++ +++@node Selection +++@section Selecting a Frame +++ +++Most commands for examining the stack and other data in your program work on +++whichever stack frame is selected at the moment. Here are the commands for +++selecting a stack frame; all of them finish by printing a brief description +++of the stack frame just selected. +++ +++@table @code +++@kindex frame@r{, selecting} +++@kindex f @r{(@code{frame})} +++@item frame @r{[} @var{frame-selection-spec} @r{]} +++@item f @r{[} @var{frame-selection-spec} @r{]} +++The @command{frame} command allows different stack frames to be +++selected. The @var{frame-selection-spec} can be any of the following: +++ +++@table @code +++@kindex frame level +++@item @var{num} +++@item level @var{num} +++Select frame level @var{num}. Recall that frame zero is the innermost +++(currently executing) frame, frame one is the frame that called the +++innermost one, and so on. The highest level frame is usually the one +++for @code{main}. +++ +++As this is the most common method of navigating the frame stack, the +++string @command{level} can be omitted. For example, the following two +++commands are equivalent: +++ +++@smallexample +++(@value{GDBP}) frame 3 +++(@value{GDBP}) frame level 3 +++@end smallexample +++ +++@kindex frame address +++@item address @var{stack-address} +++Select the frame with stack address @var{stack-address}. The +++@var{stack-address} for a frame can be seen in the output of +++@command{info frame}, for example: +++ +++@smallexample +++(gdb) info frame +++Stack level 1, frame at 0x7fffffffda30: +++ rip = 0x40066d in b (amd64-entry-value.cc:59); saved rip 0x4004c5 +++ tail call frame, caller of frame at 0x7fffffffda30 +++ source language c++. +++ Arglist at unknown address. +++ Locals at unknown address, Previous frame's sp is 0x7fffffffda30 +++@end smallexample +++ +++The @var{stack-address} for this frame is @code{0x7fffffffda30} as +++indicated by the line: +++ +++@smallexample +++Stack level 1, frame at 0x7fffffffda30: +++@end smallexample +++ +++@kindex frame function +++@item function @var{function-name} +++Select the stack frame for function @var{function-name}. If there are +++multiple stack frames for function @var{function-name} then the inner +++most stack frame is selected. +++ +++@kindex frame view +++@item view @var{stack-address} @r{[} @var{pc-addr} @r{]} +++View a frame that is not part of @value{GDBN}'s backtrace. The frame +++viewed has stack address @var{stack-addr}, and optionally, a program +++counter address of @var{pc-addr}. +++ +++This is useful mainly if the chaining of stack frames has been +++damaged by a bug, making it impossible for @value{GDBN} to assign +++numbers properly to all frames. In addition, this can be useful +++when your program has multiple stacks and switches between them. +++ +++When viewing a frame outside the current backtrace using +++@command{frame view} then you can always return to the original +++stack using one of the previous stack frame selection instructions, +++for example @command{frame level 0}. +++ +++@end table +++ +++@kindex up +++@item up @var{n} +++Move @var{n} frames up the stack; @var{n} defaults to 1. For positive +++numbers @var{n}, this advances toward the outermost frame, to higher +++frame numbers, to frames that have existed longer. +++ +++@kindex down +++@kindex do @r{(@code{down})} +++@item down @var{n} +++Move @var{n} frames down the stack; @var{n} defaults to 1. For +++positive numbers @var{n}, this advances toward the innermost frame, to +++lower frame numbers, to frames that were created more recently. +++You may abbreviate @code{down} as @code{do}. +++@end table +++ +++All of these commands end by printing two lines of output describing the +++frame. The first line shows the frame number, the function name, the +++arguments, and the source file and line number of execution in that +++frame. The second line shows the text of that source line. +++ +++@need 1000 +++For example: +++ +++@smallexample +++@group +++(@value{GDBP}) up +++#1 0x22f0 in main (argc=1, argv=0xf7fffbf4, env=0xf7fffbfc) +++ at env.c:10 +++10 read_input_file (argv[i]); +++@end group +++@end smallexample +++ +++After such a printout, the @code{list} command with no arguments +++prints ten lines centered on the point of execution in the frame. +++You can also edit the program at the point of execution with your favorite +++editing program by typing @code{edit}. +++@xref{List, ,Printing Source Lines}, +++for details. +++ +++@table @code +++@kindex select-frame +++@item select-frame @r{[} @var{frame-selection-spec} @r{]} +++The @code{select-frame} command is a variant of @code{frame} that does +++not display the new frame after selecting it. This command is +++intended primarily for use in @value{GDBN} command scripts, where the +++output might be unnecessary and distracting. The +++@var{frame-selection-spec} is as for the @command{frame} command +++described in @ref{Selection, ,Selecting a Frame}. +++ +++@kindex down-silently +++@kindex up-silently +++@item up-silently @var{n} +++@itemx down-silently @var{n} +++These two commands are variants of @code{up} and @code{down}, +++respectively; they differ in that they do their work silently, without +++causing display of the new frame. They are intended primarily for use +++in @value{GDBN} command scripts, where the output might be unnecessary and +++distracting. +++@end table +++ +++@node Frame Info +++@section Information About a Frame +++ +++There are several other commands to print information about the selected +++stack frame. +++ +++@table @code +++@item frame +++@itemx f +++When used without any argument, this command does not change which +++frame is selected, but prints a brief description of the currently +++selected stack frame. It can be abbreviated @code{f}. With an +++argument, this command is used to select a stack frame. +++@xref{Selection, ,Selecting a Frame}. +++ +++@kindex info frame +++@kindex info f @r{(@code{info frame})} +++@item info frame +++@itemx info f +++This command prints a verbose description of the selected stack frame, +++including: +++ +++@itemize @bullet +++@item +++the address of the frame +++@item +++the address of the next frame down (called by this frame) +++@item +++the address of the next frame up (caller of this frame) +++@item +++the language in which the source code corresponding to this frame is written +++@item +++the address of the frame's arguments +++@item +++the address of the frame's local variables +++@item +++the program counter saved in it (the address of execution in the caller frame) +++@item +++which registers were saved in the frame +++@end itemize +++ +++@noindent The verbose description is useful when +++something has gone wrong that has made the stack format fail to fit +++the usual conventions. +++ +++@item info frame @r{[} @var{frame-selection-spec} @r{]} +++@itemx info f @r{[} @var{frame-selection-spec} @r{]} +++Print a verbose description of the frame selected by +++@var{frame-selection-spec}. The @var{frame-selection-spec} is the +++same as for the @command{frame} command (@pxref{Selection, ,Selecting +++a Frame}). The selected frame remains unchanged by this command. +++ +++@kindex info args +++@item info args [-q] +++Print the arguments of the selected frame, each on a separate line. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no argument +++have been printed. +++ +++@item info args [-q] [-t @var{type_regexp}] [@var{regexp}] +++Like @kbd{info args}, but only print the arguments selected +++with the provided regexp(s). +++ +++If @var{regexp} is provided, print only the arguments whose names +++match the regular expression @var{regexp}. +++ +++If @var{type_regexp} is provided, print only the arguments whose +++types, as printed by the @code{whatis} command, match +++the regular expression @var{type_regexp}. +++If @var{type_regexp} contains space(s), it should be enclosed in +++quote characters. If needed, use backslash to escape the meaning +++of special characters or quotes. +++ +++If both @var{regexp} and @var{type_regexp} are provided, an argument +++is printed only if its name matches @var{regexp} and its type matches +++@var{type_regexp}. +++ +++@item info locals [-q] +++@kindex info locals +++Print the local variables of the selected frame, each on a separate +++line. These are all variables (declared either static or automatic) +++accessible at the point of execution of the selected frame. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no local variables +++have been printed. +++ +++@item info locals [-q] [-t @var{type_regexp}] [@var{regexp}] +++Like @kbd{info locals}, but only print the local variables selected +++with the provided regexp(s). +++ +++If @var{regexp} is provided, print only the local variables whose names +++match the regular expression @var{regexp}. +++ +++If @var{type_regexp} is provided, print only the local variables whose +++types, as printed by the @code{whatis} command, match +++the regular expression @var{type_regexp}. +++If @var{type_regexp} contains space(s), it should be enclosed in +++quote characters. If needed, use backslash to escape the meaning +++of special characters or quotes. +++ +++If both @var{regexp} and @var{type_regexp} are provided, a local variable +++is printed only if its name matches @var{regexp} and its type matches +++@var{type_regexp}. +++ +++The command @kbd{info locals -q -t @var{type_regexp}} can usefully be +++combined with the commands @kbd{frame apply} and @kbd{thread apply}. +++For example, your program might use Resource Acquisition Is +++Initialization types (RAII) such as @code{lock_something_t}: each +++local variable of type @code{lock_something_t} automatically places a +++lock that is destroyed when the variable goes out of scope. You can +++then list all acquired locks in your program by doing +++@smallexample +++thread apply all -s frame apply all -s info locals -q -t lock_something_t +++@end smallexample +++@noindent +++or the equivalent shorter form +++@smallexample +++tfaas i lo -q -t lock_something_t +++@end smallexample +++ +++@end table +++ +++@node Frame Apply +++@section Applying a Command to Several Frames. +++@kindex frame apply +++@cindex apply command to several frames +++@table @code +++@item frame apply [all | @var{count} | @var{-count} | level @var{level}@dots{}] [@var{option}]@dots{} @var{command} +++The @code{frame apply} command allows you to apply the named +++@var{command} to one or more frames. +++ +++@table @code +++@item @code{all} +++Specify @code{all} to apply @var{command} to all frames. +++ +++@item @var{count} +++Use @var{count} to apply @var{command} to the innermost @var{count} +++frames, where @var{count} is a positive number. +++ +++@item @var{-count} +++Use @var{-count} to apply @var{command} to the outermost @var{count} +++frames, where @var{count} is a positive number. +++ +++@item @code{level} +++Use @code{level} to apply @var{command} to the set of frames identified +++by the @var{level} list. @var{level} is a frame level or a range of frame +++levels as @var{level1}-@var{level2}. The frame level is the number shown +++in the first field of the @samp{backtrace} command output. +++E.g., @samp{2-4 6-8 3} indicates to apply @var{command} for the frames +++at levels 2, 3, 4, 6, 7, 8, and then again on frame at level 3. +++ +++@end table +++ +++Note that the frames on which @code{frame apply} applies a command are +++also influenced by the @code{set backtrace} settings such as @code{set +++backtrace past-main} and @code{set backtrace limit N}. +++@xref{Backtrace,,Backtraces}. +++ +++The @code{frame apply} command also supports a number of options that +++allow overriding relevant @code{set backtrace} settings: +++ +++@table @code +++@item -past-main [@code{on}|@code{off}] +++Whether backtraces should continue past @code{main}. +++Related setting: @ref{set backtrace past-main}. +++ +++@item -past-entry [@code{on}|@code{off}] +++Whether backtraces should continue past the entry point of a program. +++Related setting: @ref{set backtrace past-entry}. +++@end table +++ +++By default, @value{GDBN} displays some frame information before the +++output produced by @var{command}, and an error raised during the +++execution of a @var{command} will abort @code{frame apply}. The +++following options can be used to fine-tune these behaviors: +++ +++@table @code +++@item -c +++The flag @code{-c}, which stands for @samp{continue}, causes any +++errors in @var{command} to be displayed, and the execution of +++@code{frame apply} then continues. +++@item -s +++The flag @code{-s}, which stands for @samp{silent}, causes any errors +++or empty output produced by a @var{command} to be silently ignored. +++That is, the execution continues, but the frame information and errors +++are not printed. +++@item -q +++The flag @code{-q} (@samp{quiet}) disables printing the frame +++information. +++@end table +++ +++The following example shows how the flags @code{-c} and @code{-s} are +++working when applying the command @code{p j} to all frames, where +++variable @code{j} can only be successfully printed in the outermost +++@code{#1 main} frame. +++ +++@smallexample +++@group +++(gdb) frame apply all p j +++#0 some_function (i=5) at fun.c:4 +++No symbol "j" in current context. +++(gdb) frame apply all -c p j +++#0 some_function (i=5) at fun.c:4 +++No symbol "j" in current context. +++#1 0x565555fb in main (argc=1, argv=0xffffd2c4) at fun.c:11 +++$1 = 5 +++(gdb) frame apply all -s p j +++#1 0x565555fb in main (argc=1, argv=0xffffd2c4) at fun.c:11 +++$2 = 5 +++(gdb) +++@end group +++@end smallexample +++ +++By default, @samp{frame apply}, prints the frame location +++information before the command output: +++ +++@smallexample +++@group +++(gdb) frame apply all p $sp +++#0 some_function (i=5) at fun.c:4 +++$4 = (void *) 0xffffd1e0 +++#1 0x565555fb in main (argc=1, argv=0xffffd2c4) at fun.c:11 +++$5 = (void *) 0xffffd1f0 +++(gdb) +++@end group +++@end smallexample +++ +++If the flag @code{-q} is given, no frame information is printed: +++@smallexample +++@group +++(gdb) frame apply all -q p $sp +++$12 = (void *) 0xffffd1e0 +++$13 = (void *) 0xffffd1f0 +++(gdb) +++@end group +++@end smallexample +++ +++@end table +++ +++@table @code +++ +++@kindex faas +++@cindex apply a command to all frames (ignoring errors and empty output) +++@item faas @var{command} +++Shortcut for @code{frame apply all -s @var{command}}. +++Applies @var{command} on all frames, ignoring errors and empty output. +++ +++It can for example be used to print a local variable or a function +++argument without knowing the frame where this variable or argument +++is, using: +++@smallexample +++(@value{GDBP}) faas p some_local_var_i_do_not_remember_where_it_is +++@end smallexample +++ +++The @code{faas} command accepts the same options as the @code{frame +++apply} command. @xref{Frame Apply,,frame apply}. +++ +++Note that the command @code{tfaas @var{command}} applies @var{command} +++on all frames of all threads. See @xref{Threads,,Threads}. +++@end table +++ +++ +++@node Frame Filter Management +++@section Management of Frame Filters. +++@cindex managing frame filters +++ +++Frame filters are Python based utilities to manage and decorate the +++output of frames. @xref{Frame Filter API}, for further information. +++ +++Managing frame filters is performed by several commands available +++within @value{GDBN}, detailed here. +++ +++@table @code +++@kindex info frame-filter +++@item info frame-filter +++Print a list of installed frame filters from all dictionaries, showing +++their name, priority and enabled status. +++ +++@kindex disable frame-filter +++@anchor{disable frame-filter all} +++@item disable frame-filter @var{filter-dictionary} @var{filter-name} +++Disable a frame filter in the dictionary matching +++@var{filter-dictionary} and @var{filter-name}. The +++@var{filter-dictionary} may be @code{all}, @code{global}, +++@code{progspace}, or the name of the object file where the frame filter +++dictionary resides. When @code{all} is specified, all frame filters +++across all dictionaries are disabled. The @var{filter-name} is the name +++of the frame filter and is used when @code{all} is not the option for +++@var{filter-dictionary}. A disabled frame-filter is not deleted, it +++may be enabled again later. +++ +++@kindex enable frame-filter +++@item enable frame-filter @var{filter-dictionary} @var{filter-name} +++Enable a frame filter in the dictionary matching +++@var{filter-dictionary} and @var{filter-name}. The +++@var{filter-dictionary} may be @code{all}, @code{global}, +++@code{progspace} or the name of the object file where the frame filter +++dictionary resides. When @code{all} is specified, all frame filters across +++all dictionaries are enabled. The @var{filter-name} is the name of the frame +++filter and is used when @code{all} is not the option for +++@var{filter-dictionary}. +++ +++Example: +++ +++@smallexample +++(gdb) info frame-filter +++ +++global frame-filters: +++ Priority Enabled Name +++ 1000 No PrimaryFunctionFilter +++ 100 Yes Reverse +++ +++progspace /build/test frame-filters: +++ Priority Enabled Name +++ 100 Yes ProgspaceFilter +++ +++objfile /build/test frame-filters: +++ Priority Enabled Name +++ 999 Yes BuildProgramFilter +++ +++(gdb) disable frame-filter /build/test BuildProgramFilter +++(gdb) info frame-filter +++ +++global frame-filters: +++ Priority Enabled Name +++ 1000 No PrimaryFunctionFilter +++ 100 Yes Reverse +++ +++progspace /build/test frame-filters: +++ Priority Enabled Name +++ 100 Yes ProgspaceFilter +++ +++objfile /build/test frame-filters: +++ Priority Enabled Name +++ 999 No BuildProgramFilter +++ +++(gdb) enable frame-filter global PrimaryFunctionFilter +++(gdb) info frame-filter +++ +++global frame-filters: +++ Priority Enabled Name +++ 1000 Yes PrimaryFunctionFilter +++ 100 Yes Reverse +++ +++progspace /build/test frame-filters: +++ Priority Enabled Name +++ 100 Yes ProgspaceFilter +++ +++objfile /build/test frame-filters: +++ Priority Enabled Name +++ 999 No BuildProgramFilter +++@end smallexample +++ +++@kindex set frame-filter priority +++@item set frame-filter priority @var{filter-dictionary} @var{filter-name} @var{priority} +++Set the @var{priority} of a frame filter in the dictionary matching +++@var{filter-dictionary}, and the frame filter name matching +++@var{filter-name}. The @var{filter-dictionary} may be @code{global}, +++@code{progspace} or the name of the object file where the frame filter +++dictionary resides. The @var{priority} is an integer. +++ +++@kindex show frame-filter priority +++@item show frame-filter priority @var{filter-dictionary} @var{filter-name} +++Show the @var{priority} of a frame filter in the dictionary matching +++@var{filter-dictionary}, and the frame filter name matching +++@var{filter-name}. The @var{filter-dictionary} may be @code{global}, +++@code{progspace} or the name of the object file where the frame filter +++dictionary resides. +++ +++Example: +++ +++@smallexample +++(gdb) info frame-filter +++ +++global frame-filters: +++ Priority Enabled Name +++ 1000 Yes PrimaryFunctionFilter +++ 100 Yes Reverse +++ +++progspace /build/test frame-filters: +++ Priority Enabled Name +++ 100 Yes ProgspaceFilter +++ +++objfile /build/test frame-filters: +++ Priority Enabled Name +++ 999 No BuildProgramFilter +++ +++(gdb) set frame-filter priority global Reverse 50 +++(gdb) info frame-filter +++ +++global frame-filters: +++ Priority Enabled Name +++ 1000 Yes PrimaryFunctionFilter +++ 50 Yes Reverse +++ +++progspace /build/test frame-filters: +++ Priority Enabled Name +++ 100 Yes ProgspaceFilter +++ +++objfile /build/test frame-filters: +++ Priority Enabled Name +++ 999 No BuildProgramFilter +++@end smallexample +++@end table +++ +++@node Source +++@chapter Examining Source Files +++ +++@value{GDBN} can print parts of your program's source, since the debugging +++information recorded in the program tells @value{GDBN} what source files were +++used to build it. When your program stops, @value{GDBN} spontaneously prints +++the line where it stopped. Likewise, when you select a stack frame +++(@pxref{Selection, ,Selecting a Frame}), @value{GDBN} prints the line where +++execution in that frame has stopped. You can print other portions of +++source files by explicit command. +++ +++If you use @value{GDBN} through its @sc{gnu} Emacs interface, you may +++prefer to use Emacs facilities to view source; see @ref{Emacs, ,Using +++@value{GDBN} under @sc{gnu} Emacs}. +++ +++@menu +++* List:: Printing source lines +++* Specify Location:: How to specify code locations +++* Edit:: Editing source files +++* Search:: Searching source files +++* Source Path:: Specifying source directories +++* Machine Code:: Source and machine code +++@end menu +++ +++@node List +++@section Printing Source Lines +++ +++@kindex list +++@kindex l @r{(@code{list})} +++To print lines from a source file, use the @code{list} command +++(abbreviated @code{l}). By default, ten lines are printed. +++There are several ways to specify what part of the file you want to +++print; see @ref{Specify Location}, for the full list. +++ +++Here are the forms of the @code{list} command most commonly used: +++ +++@table @code +++@item list @var{linenum} +++Print lines centered around line number @var{linenum} in the +++current source file. +++ +++@item list @var{function} +++Print lines centered around the beginning of function +++@var{function}. +++ +++@item list +++Print more lines. If the last lines printed were printed with a +++@code{list} command, this prints lines following the last lines +++printed; however, if the last line printed was a solitary line printed +++as part of displaying a stack frame (@pxref{Stack, ,Examining the +++Stack}), this prints lines centered around that line. +++ +++@item list - +++Print lines just before the lines last printed. +++@end table +++ +++@cindex @code{list}, how many lines to display +++By default, @value{GDBN} prints ten source lines with any of these forms of +++the @code{list} command. You can change this using @code{set listsize}: +++ +++@table @code +++@kindex set listsize +++@item set listsize @var{count} +++@itemx set listsize unlimited +++Make the @code{list} command display @var{count} source lines (unless +++the @code{list} argument explicitly specifies some other number). +++Setting @var{count} to @code{unlimited} or 0 means there's no limit. +++ +++@kindex show listsize +++@item show listsize +++Display the number of lines that @code{list} prints. +++@end table +++ +++Repeating a @code{list} command with @key{RET} discards the argument, +++so it is equivalent to typing just @code{list}. This is more useful +++than listing the same lines again. An exception is made for an +++argument of @samp{-}; that argument is preserved in repetition so that +++each repetition moves up in the source file. +++ +++In general, the @code{list} command expects you to supply zero, one or two +++@dfn{locations}. Locations specify source lines; there are several ways +++of writing them (@pxref{Specify Location}), but the effect is always +++to specify some source line. +++ +++Here is a complete description of the possible arguments for @code{list}: +++ +++@table @code +++@item list @var{location} +++Print lines centered around the line specified by @var{location}. +++ +++@item list @var{first},@var{last} +++Print lines from @var{first} to @var{last}. Both arguments are +++locations. When a @code{list} command has two locations, and the +++source file of the second location is omitted, this refers to +++the same source file as the first location. +++ +++@item list ,@var{last} +++Print lines ending with @var{last}. +++ +++@item list @var{first}, +++Print lines starting with @var{first}. +++ +++@item list + +++Print lines just after the lines last printed. +++ +++@item list - +++Print lines just before the lines last printed. +++ +++@item list +++As described in the preceding table. +++@end table +++ +++@node Specify Location +++@section Specifying a Location +++@cindex specifying location +++@cindex location +++@cindex source location +++ +++@menu +++* Linespec Locations:: Linespec locations +++* Explicit Locations:: Explicit locations +++* Address Locations:: Address locations +++@end menu +++ +++Several @value{GDBN} commands accept arguments that specify a location +++of your program's code. Since @value{GDBN} is a source-level +++debugger, a location usually specifies some line in the source code. +++Locations may be specified using three different formats: +++linespec locations, explicit locations, or address locations. +++ +++@node Linespec Locations +++@subsection Linespec Locations +++@cindex linespec locations +++ +++A @dfn{linespec} is a colon-separated list of source location parameters such +++as file name, function name, etc. Here are all the different ways of +++specifying a linespec: +++ +++@table @code +++@item @var{linenum} +++Specifies the line number @var{linenum} of the current source file. +++ +++@item -@var{offset} +++@itemx +@var{offset} +++Specifies the line @var{offset} lines before or after the @dfn{current +++line}. For the @code{list} command, the current line is the last one +++printed; for the breakpoint commands, this is the line at which +++execution stopped in the currently selected @dfn{stack frame} +++(@pxref{Frames, ,Frames}, for a description of stack frames.) When +++used as the second of the two linespecs in a @code{list} command, +++this specifies the line @var{offset} lines up or down from the first +++linespec. +++ +++@item @var{filename}:@var{linenum} +++Specifies the line @var{linenum} in the source file @var{filename}. +++If @var{filename} is a relative file name, then it will match any +++source file name with the same trailing components. For example, if +++@var{filename} is @samp{gcc/expr.c}, then it will match source file +++name of @file{/build/trunk/gcc/expr.c}, but not +++@file{/build/trunk/libcpp/expr.c} or @file{/build/trunk/gcc/x-expr.c}. +++ +++@item @var{function} +++Specifies the line that begins the body of the function @var{function}. +++For example, in C, this is the line with the open brace. +++ +++By default, in C@t{++} and Ada, @var{function} is interpreted as +++specifying all functions named @var{function} in all scopes. For +++C@t{++}, this means in all namespaces and classes. For Ada, this +++means in all packages. +++ +++For example, assuming a program with C@t{++} symbols named +++@code{A::B::func} and @code{B::func}, both commands @w{@kbd{break +++func}} and @w{@kbd{break B::func}} set a breakpoint on both symbols. +++ +++Commands that accept a linespec let you override this with the +++@code{-qualified} option. For example, @w{@kbd{break -qualified +++func}} sets a breakpoint on a free-function named @code{func} ignoring +++any C@t{++} class methods and namespace functions called @code{func}. +++ +++@xref{Explicit Locations}. +++ +++@item @var{function}:@var{label} +++Specifies the line where @var{label} appears in @var{function}. +++ +++@item @var{filename}:@var{function} +++Specifies the line that begins the body of the function @var{function} +++in the file @var{filename}. You only need the file name with a +++function name to avoid ambiguity when there are identically named +++functions in different source files. +++ +++@item @var{label} +++Specifies the line at which the label named @var{label} appears +++in the function corresponding to the currently selected stack frame. +++If there is no current selected stack frame (for instance, if the inferior +++is not running), then @value{GDBN} will not search for a label. +++ +++@cindex breakpoint at static probe point +++@item -pstap|-probe-stap @r{[}@var{objfile}:@r{[}@var{provider}:@r{]}@r{]}@var{name} +++The @sc{gnu}/Linux tool @code{SystemTap} provides a way for +++applications to embed static probes. @xref{Static Probe Points}, for more +++information on finding and using static probes. This form of linespec +++specifies the location of such a static probe. +++ +++If @var{objfile} is given, only probes coming from that shared library +++or executable matching @var{objfile} as a regular expression are considered. +++If @var{provider} is given, then only probes from that provider are considered. +++If several probes match the spec, @value{GDBN} will insert a breakpoint at +++each one of those probes. +++@end table +++ +++@node Explicit Locations +++@subsection Explicit Locations +++@cindex explicit locations +++ +++@dfn{Explicit locations} allow the user to directly specify the source +++location's parameters using option-value pairs. +++ +++Explicit locations are useful when several functions, labels, or +++file names have the same name (base name for files) in the program's +++sources. In these cases, explicit locations point to the source +++line you meant more accurately and unambiguously. Also, using +++explicit locations might be faster in large programs. +++ +++For example, the linespec @samp{foo:bar} may refer to a function @code{bar} +++defined in the file named @file{foo} or the label @code{bar} in a function +++named @code{foo}. @value{GDBN} must search either the file system or +++the symbol table to know. +++ +++The list of valid explicit location options is summarized in the +++following table: +++ +++@table @code +++@item -source @var{filename} +++The value specifies the source file name. To differentiate between +++files with the same base name, prepend as many directories as is necessary +++to uniquely identify the desired file, e.g., @file{foo/bar/baz.c}. Otherwise +++@value{GDBN} will use the first file it finds with the given base +++name. This option requires the use of either @code{-function} or @code{-line}. +++ +++@item -function @var{function} +++The value specifies the name of a function. Operations +++on function locations unmodified by other options (such as @code{-label} +++or @code{-line}) refer to the line that begins the body of the function. +++In C, for example, this is the line with the open brace. +++ +++By default, in C@t{++} and Ada, @var{function} is interpreted as +++specifying all functions named @var{function} in all scopes. For +++C@t{++}, this means in all namespaces and classes. For Ada, this +++means in all packages. +++ +++For example, assuming a program with C@t{++} symbols named +++@code{A::B::func} and @code{B::func}, both commands @w{@kbd{break +++-function func}} and @w{@kbd{break -function B::func}} set a +++breakpoint on both symbols. +++ +++You can use the @kbd{-qualified} flag to override this (see below). +++ +++@item -qualified +++ +++This flag makes @value{GDBN} interpret a function name specified with +++@kbd{-function} as a complete fully-qualified name. +++ +++For example, assuming a C@t{++} program with symbols named +++@code{A::B::func} and @code{B::func}, the @w{@kbd{break -qualified +++-function B::func}} command sets a breakpoint on @code{B::func}, only. +++ +++(Note: the @kbd{-qualified} option can precede a linespec as well +++(@pxref{Linespec Locations}), so the particular example above could be +++simplified as @w{@kbd{break -qualified B::func}}.) +++ +++@item -label @var{label} +++The value specifies the name of a label. When the function +++name is not specified, the label is searched in the function of the currently +++selected stack frame. +++ +++@item -line @var{number} +++The value specifies a line offset for the location. The offset may either +++be absolute (@code{-line 3}) or relative (@code{-line +3}), depending on +++the command. When specified without any other options, the line offset is +++relative to the current line. +++@end table +++ +++Explicit location options may be abbreviated by omitting any non-unique +++trailing characters from the option name, e.g., @w{@kbd{break -s main.c -li 3}}. +++ +++@node Address Locations +++@subsection Address Locations +++@cindex address locations +++ +++@dfn{Address locations} indicate a specific program address. They have +++the generalized form *@var{address}. +++ +++For line-oriented commands, such as @code{list} and @code{edit}, this +++specifies a source line that contains @var{address}. For @code{break} and +++other breakpoint-oriented commands, this can be used to set breakpoints in +++parts of your program which do not have debugging information or +++source files. +++ +++Here @var{address} may be any expression valid in the current working +++language (@pxref{Languages, working language}) that specifies a code +++address. In addition, as a convenience, @value{GDBN} extends the +++semantics of expressions used in locations to cover several situations +++that frequently occur during debugging. Here are the various forms +++of @var{address}: +++ +++@table @code +++@item @var{expression} +++Any expression valid in the current working language. +++ +++@item @var{funcaddr} +++An address of a function or procedure derived from its name. In C, +++C@t{++}, Objective-C, Fortran, minimal, and assembly, this is +++simply the function's name @var{function} (and actually a special case +++of a valid expression). In Pascal and Modula-2, this is +++@code{&@var{function}}. In Ada, this is @code{@var{function}'Address} +++(although the Pascal form also works). +++ +++This form specifies the address of the function's first instruction, +++before the stack frame and arguments have been set up. +++ +++@item '@var{filename}':@var{funcaddr} +++Like @var{funcaddr} above, but also specifies the name of the source +++file explicitly. This is useful if the name of the function does not +++specify the function unambiguously, e.g., if there are several +++functions with identical names in different source files. +++@end table +++ +++@node Edit +++@section Editing Source Files +++@cindex editing source files +++ +++@kindex edit +++@kindex e @r{(@code{edit})} +++To edit the lines in a source file, use the @code{edit} command. +++The editing program of your choice +++is invoked with the current line set to +++the active line in the program. +++Alternatively, there are several ways to specify what part of the file you +++want to print if you want to see other parts of the program: +++ +++@table @code +++@item edit @var{location} +++Edit the source file specified by @code{location}. Editing starts at +++that @var{location}, e.g., at the specified source line of the +++specified file. @xref{Specify Location}, for all the possible forms +++of the @var{location} argument; here are the forms of the @code{edit} +++command most commonly used: +++ +++@table @code +++@item edit @var{number} +++Edit the current source file with @var{number} as the active line number. +++ +++@item edit @var{function} +++Edit the file containing @var{function} at the beginning of its definition. +++@end table +++ +++@end table +++ +++@subsection Choosing your Editor +++You can customize @value{GDBN} to use any editor you want +++@footnote{ +++The only restriction is that your editor (say @code{ex}), recognizes the +++following command-line syntax: +++@smallexample +++ex +@var{number} file +++@end smallexample +++The optional numeric value +@var{number} specifies the number of the line in +++the file where to start editing.}. +++By default, it is @file{@value{EDITOR}}, but you can change this +++by setting the environment variable @code{EDITOR} before using +++@value{GDBN}. For example, to configure @value{GDBN} to use the +++@code{vi} editor, you could use these commands with the @code{sh} shell: +++@smallexample +++EDITOR=/usr/bin/vi +++export EDITOR +++gdb @dots{} +++@end smallexample +++or in the @code{csh} shell, +++@smallexample +++setenv EDITOR /usr/bin/vi +++gdb @dots{} +++@end smallexample +++ +++@node Search +++@section Searching Source Files +++@cindex searching source files +++ +++There are two commands for searching through the current source file for a +++regular expression. +++ +++@table @code +++@kindex search +++@kindex forward-search +++@kindex fo @r{(@code{forward-search})} +++@item forward-search @var{regexp} +++@itemx search @var{regexp} +++The command @samp{forward-search @var{regexp}} checks each line, +++starting with the one following the last line listed, for a match for +++@var{regexp}. It lists the line that is found. You can use the +++synonym @samp{search @var{regexp}} or abbreviate the command name as +++@code{fo}. +++ +++@kindex reverse-search +++@item reverse-search @var{regexp} +++The command @samp{reverse-search @var{regexp}} checks each line, starting +++with the one before the last line listed and going backward, for a match +++for @var{regexp}. It lists the line that is found. You can abbreviate +++this command as @code{rev}. +++@end table +++ +++@node Source Path +++@section Specifying Source Directories +++ +++@cindex source path +++@cindex directories for source files +++Executable programs sometimes do not record the directories of the source +++files from which they were compiled, just the names. Even when they do, +++the directories could be moved between the compilation and your debugging +++session. @value{GDBN} has a list of directories to search for source files; +++this is called the @dfn{source path}. Each time @value{GDBN} wants a source file, +++it tries all the directories in the list, in the order they are present +++in the list, until it finds a file with the desired name. +++ +++For example, suppose an executable references the file +++@file{/usr/src/foo-1.0/lib/foo.c}, does not record a compilation +++directory, and the @dfn{source path} is @file{/mnt/cross}. +++@value{GDBN} would look for the source file in the following +++locations: +++ +++@enumerate +++ +++@item @file{/usr/src/foo-1.0/lib/foo.c} +++@item @file{/mnt/cross/usr/src/foo-1.0/lib/foo.c} +++@item @file{/mnt/cross/foo.c} +++ +++@end enumerate +++ +++If the source file is not present at any of the above locations then +++an error is printed. @value{GDBN} does not look up the parts of the +++source file name, such as @file{/mnt/cross/src/foo-1.0/lib/foo.c}. +++Likewise, the subdirectories of the source path are not searched: if +++the source path is @file{/mnt/cross}, and the binary refers to +++@file{foo.c}, @value{GDBN} would not find it under +++@file{/mnt/cross/usr/src/foo-1.0/lib}. +++ +++Plain file names, relative file names with leading directories, file +++names containing dots, etc.@: are all treated as described above, +++except that non-absolute file names are not looked up literally. If +++the @dfn{source path} is @file{/mnt/cross}, the source file is +++recorded as @file{../lib/foo.c}, and no compilation directory is +++recorded, then @value{GDBN} will search in the following locations: +++ +++@enumerate +++ +++@item @file{/mnt/cross/../lib/foo.c} +++@item @file{/mnt/cross/foo.c} +++ +++@end enumerate +++ +++@kindex cdir +++@kindex cwd +++@vindex $cdir@r{, convenience variable} +++@vindex $cwd@r{, convenience variable} +++@cindex compilation directory +++@cindex current directory +++@cindex working directory +++@cindex directory, current +++@cindex directory, compilation +++The @dfn{source path} will always include two special entries +++@samp{$cdir} and @samp{$cwd}, these refer to the compilation directory +++(if one is recorded) and the current working directory respectively. +++ +++@samp{$cdir} causes @value{GDBN} to search within the compilation +++directory, if one is recorded in the debug information. If no +++compilation directory is recorded in the debug information then +++@samp{$cdir} is ignored. +++ +++@samp{$cwd} is not the same as @samp{.}---the former tracks the +++current working directory as it changes during your @value{GDBN} +++session, while the latter is immediately expanded to the current +++directory at the time you add an entry to the source path. +++ +++If a compilation directory is recorded in the debug information, and +++@value{GDBN} has not found the source file after the first search +++using @dfn{source path}, then @value{GDBN} will combine the +++compilation directory and the filename, and then search for the source +++file again using the @dfn{source path}. +++ +++For example, if the executable records the source file as +++@file{/usr/src/foo-1.0/lib/foo.c}, the compilation directory is +++recorded as @file{/project/build}, and the @dfn{source path} is +++@file{/mnt/cross:$cdir:$cwd} while the current working directory of +++the @value{GDBN} session is @file{/home/user}, then @value{GDBN} will +++search for the source file in the following locations: +++ +++@enumerate +++ +++@item @file{/usr/src/foo-1.0/lib/foo.c} +++@item @file{/mnt/cross/usr/src/foo-1.0/lib/foo.c} +++@item @file{/project/build/usr/src/foo-1.0/lib/foo.c} +++@item @file{/home/user/usr/src/foo-1.0/lib/foo.c} +++@item @file{/mnt/cross/project/build/usr/src/foo-1.0/lib/foo.c} +++@item @file{/project/build/project/build/usr/src/foo-1.0/lib/foo.c} +++@item @file{/home/user/project/build/usr/src/foo-1.0/lib/foo.c} +++@item @file{/mnt/cross/foo.c} +++@item @file{/project/build/foo.c} +++@item @file{/home/user/foo.c} +++ +++@end enumerate +++ +++If the file name in the previous example had been recorded in the +++executable as a relative path rather than an absolute path, then the +++first look up would not have occurred, but all of the remaining steps +++would be similar. +++ +++When searching for source files on MS-DOS and MS-Windows, where +++absolute paths start with a drive letter (e.g. +++@file{C:/project/foo.c}), @value{GDBN} will remove the drive letter +++from the file name before appending it to a search directory from +++@dfn{source path}; for instance if the executable references the +++source file @file{C:/project/foo.c} and @dfn{source path} is set to +++@file{D:/mnt/cross}, then @value{GDBN} will search in the following +++locations for the source file: +++ +++@enumerate +++ +++@item @file{C:/project/foo.c} +++@item @file{D:/mnt/cross/project/foo.c} +++@item @file{D:/mnt/cross/foo.c} +++ +++@end enumerate +++ +++Note that the executable search path is @emph{not} used to locate the +++source files. +++ +++Whenever you reset or rearrange the source path, @value{GDBN} clears out +++any information it has cached about where source files are found and where +++each line is in the file. +++ +++@kindex directory +++@kindex dir +++When you start @value{GDBN}, its source path includes only @samp{$cdir} +++and @samp{$cwd}, in that order. +++To add other directories, use the @code{directory} command. +++ +++The search path is used to find both program source files and @value{GDBN} +++script files (read using the @samp{-command} option and @samp{source} command). +++ +++In addition to the source path, @value{GDBN} provides a set of commands +++that manage a list of source path substitution rules. A @dfn{substitution +++rule} specifies how to rewrite source directories stored in the program's +++debug information in case the sources were moved to a different +++directory between compilation and debugging. A rule is made of +++two strings, the first specifying what needs to be rewritten in +++the path, and the second specifying how it should be rewritten. +++In @ref{set substitute-path}, we name these two parts @var{from} and +++@var{to} respectively. @value{GDBN} does a simple string replacement +++of @var{from} with @var{to} at the start of the directory part of the +++source file name, and uses that result instead of the original file +++name to look up the sources. +++ +++Using the previous example, suppose the @file{foo-1.0} tree has been +++moved from @file{/usr/src} to @file{/mnt/cross}, then you can tell +++@value{GDBN} to replace @file{/usr/src} in all source path names with +++@file{/mnt/cross}. The first lookup will then be +++@file{/mnt/cross/foo-1.0/lib/foo.c} in place of the original location +++of @file{/usr/src/foo-1.0/lib/foo.c}. To define a source path +++substitution rule, use the @code{set substitute-path} command +++(@pxref{set substitute-path}). +++ +++To avoid unexpected substitution results, a rule is applied only if the +++@var{from} part of the directory name ends at a directory separator. +++For instance, a rule substituting @file{/usr/source} into +++@file{/mnt/cross} will be applied to @file{/usr/source/foo-1.0} but +++not to @file{/usr/sourceware/foo-2.0}. And because the substitution +++is applied only at the beginning of the directory name, this rule will +++not be applied to @file{/root/usr/source/baz.c} either. +++ +++In many cases, you can achieve the same result using the @code{directory} +++command. However, @code{set substitute-path} can be more efficient in +++the case where the sources are organized in a complex tree with multiple +++subdirectories. With the @code{directory} command, you need to add each +++subdirectory of your project. If you moved the entire tree while +++preserving its internal organization, then @code{set substitute-path} +++allows you to direct the debugger to all the sources with one single +++command. +++ +++@code{set substitute-path} is also more than just a shortcut command. +++The source path is only used if the file at the original location no +++longer exists. On the other hand, @code{set substitute-path} modifies +++the debugger behavior to look at the rewritten location instead. So, if +++for any reason a source file that is not relevant to your executable is +++located at the original location, a substitution rule is the only +++method available to point @value{GDBN} at the new location. +++ +++@cindex @samp{--with-relocated-sources} +++@cindex default source path substitution +++You can configure a default source path substitution rule by +++configuring @value{GDBN} with the +++@samp{--with-relocated-sources=@var{dir}} option. The @var{dir} +++should be the name of a directory under @value{GDBN}'s configured +++prefix (set with @samp{--prefix} or @samp{--exec-prefix}), and +++directory names in debug information under @var{dir} will be adjusted +++automatically if the installed @value{GDBN} is moved to a new +++location. This is useful if @value{GDBN}, libraries or executables +++with debug information and corresponding source code are being moved +++together. +++ +++@table @code +++@item directory @var{dirname} @dots{} +++@item dir @var{dirname} @dots{} +++Add directory @var{dirname} to the front of the source path. Several +++directory names may be given to this command, separated by @samp{:} +++(@samp{;} on MS-DOS and MS-Windows, where @samp{:} usually appears as +++part of absolute file names) or +++whitespace. You may specify a directory that is already in the source +++path; this moves it forward, so @value{GDBN} searches it sooner. +++ +++The special strings @samp{$cdir} (to refer to the compilation +++directory, if one is recorded), and @samp{$cwd} (to refer to the +++current working directory) can also be included in the list of +++directories @var{dirname}. Though these will already be in the source +++path they will be moved forward in the list so @value{GDBN} searches +++them sooner. +++ +++@item directory +++Reset the source path to its default value (@samp{$cdir:$cwd} on Unix systems). This requires confirmation. +++ +++@c RET-repeat for @code{directory} is explicitly disabled, but since +++@c repeating it would be a no-op we do not say that. (thanks to RMS) +++ +++@item set directories @var{path-list} +++@kindex set directories +++Set the source path to @var{path-list}. +++@samp{$cdir:$cwd} are added if missing. +++ +++@item show directories +++@kindex show directories +++Print the source path: show which directories it contains. +++ +++@anchor{set substitute-path} +++@item set substitute-path @var{from} @var{to} +++@kindex set substitute-path +++Define a source path substitution rule, and add it at the end of the +++current list of existing substitution rules. If a rule with the same +++@var{from} was already defined, then the old rule is also deleted. +++ +++For example, if the file @file{/foo/bar/baz.c} was moved to +++@file{/mnt/cross/baz.c}, then the command +++ +++@smallexample +++(@value{GDBP}) set substitute-path /foo/bar /mnt/cross +++@end smallexample +++ +++@noindent +++will tell @value{GDBN} to replace @samp{/foo/bar} with +++@samp{/mnt/cross}, which will allow @value{GDBN} to find the file +++@file{baz.c} even though it was moved. +++ +++In the case when more than one substitution rule have been defined, +++the rules are evaluated one by one in the order where they have been +++defined. The first one matching, if any, is selected to perform +++the substitution. +++ +++For instance, if we had entered the following commands: +++ +++@smallexample +++(@value{GDBP}) set substitute-path /usr/src/include /mnt/include +++(@value{GDBP}) set substitute-path /usr/src /mnt/src +++@end smallexample +++ +++@noindent +++@value{GDBN} would then rewrite @file{/usr/src/include/defs.h} into +++@file{/mnt/include/defs.h} by using the first rule. However, it would +++use the second rule to rewrite @file{/usr/src/lib/foo.c} into +++@file{/mnt/src/lib/foo.c}. +++ +++ +++@item unset substitute-path [path] +++@kindex unset substitute-path +++If a path is specified, search the current list of substitution rules +++for a rule that would rewrite that path. Delete that rule if found. +++A warning is emitted by the debugger if no rule could be found. +++ +++If no path is specified, then all substitution rules are deleted. +++ +++@item show substitute-path [path] +++@kindex show substitute-path +++If a path is specified, then print the source path substitution rule +++which would rewrite that path, if any. +++ +++If no path is specified, then print all existing source path substitution +++rules. +++ +++@end table +++ +++If your source path is cluttered with directories that are no longer of +++interest, @value{GDBN} may sometimes cause confusion by finding the wrong +++versions of source. You can correct the situation as follows: +++ +++@enumerate +++@item +++Use @code{directory} with no argument to reset the source path to its default value. +++ +++@item +++Use @code{directory} with suitable arguments to reinstall the +++directories you want in the source path. You can add all the +++directories in one command. +++@end enumerate +++ +++@node Machine Code +++@section Source and Machine Code +++@cindex source line and its code address +++ +++You can use the command @code{info line} to map source lines to program +++addresses (and vice versa), and the command @code{disassemble} to display +++a range of addresses as machine instructions. You can use the command +++@code{set disassemble-next-line} to set whether to disassemble next +++source line when execution stops. When run under @sc{gnu} Emacs +++mode, the @code{info line} command causes the arrow to point to the +++line specified. Also, @code{info line} prints addresses in symbolic form as +++well as hex. +++ +++@table @code +++@kindex info line +++@item info line +++@itemx info line @var{location} +++Print the starting and ending addresses of the compiled code for +++source line @var{location}. You can specify source lines in any of +++the ways documented in @ref{Specify Location}. With no @var{location} +++information about the current source line is printed. +++@end table +++ +++For example, we can use @code{info line} to discover the location of +++the object code for the first line of function +++@code{m4_changequote}: +++ +++@smallexample +++(@value{GDBP}) info line m4_changequote +++Line 895 of "builtin.c" starts at pc 0x634c and \ +++ ends at 0x6350 . +++@end smallexample +++ +++@noindent +++@cindex code address and its source line +++We can also inquire (using @code{*@var{addr}} as the form for +++@var{location}) what source line covers a particular address: +++@smallexample +++(@value{GDBP}) info line *0x63ff +++Line 926 of "builtin.c" starts at pc 0x63e4 and \ +++ ends at 0x6404 . +++@end smallexample +++ +++@cindex @code{$_} and @code{info line} +++@cindex @code{x} command, default address +++@kindex x@r{(examine), and} info line +++After @code{info line}, the default address for the @code{x} command +++is changed to the starting address of the line, so that @samp{x/i} is +++sufficient to begin examining the machine code (@pxref{Memory, +++,Examining Memory}). Also, this address is saved as the value of the +++convenience variable @code{$_} (@pxref{Convenience Vars, ,Convenience +++Variables}). +++ +++@cindex info line, repeated calls +++After @code{info line}, using @code{info line} again without +++specifying a location will display information about the next source +++line. +++ +++@table @code +++@kindex disassemble +++@cindex assembly instructions +++@cindex instructions, assembly +++@cindex machine instructions +++@cindex listing machine instructions +++@item disassemble +++@itemx disassemble /m +++@itemx disassemble /s +++@itemx disassemble /r +++This specialized command dumps a range of memory as machine +++instructions. It can also print mixed source+disassembly by specifying +++the @code{/m} or @code{/s} modifier and print the raw instructions in hex +++as well as in symbolic form by specifying the @code{/r} modifier. +++The default memory range is the function surrounding the +++program counter of the selected frame. A single argument to this +++command is a program counter value; @value{GDBN} dumps the function +++surrounding this value. When two arguments are given, they should +++be separated by a comma, possibly surrounded by whitespace. The +++arguments specify a range of addresses to dump, in one of two forms: +++ +++@table @code +++@item @var{start},@var{end} +++the addresses from @var{start} (inclusive) to @var{end} (exclusive) +++@item @var{start},+@var{length} +++the addresses from @var{start} (inclusive) to +++@code{@var{start}+@var{length}} (exclusive). +++@end table +++ +++@noindent +++When 2 arguments are specified, the name of the function is also +++printed (since there could be several functions in the given range). +++ +++The argument(s) can be any expression yielding a numeric value, such as +++@samp{0x32c4}, @samp{&main+10} or @samp{$pc - 8}. +++ +++If the range of memory being disassembled contains current program counter, +++the instruction at that location is shown with a @code{=>} marker. +++@end table +++ +++The following example shows the disassembly of a range of addresses of +++HP PA-RISC 2.0 code: +++ +++@smallexample +++(@value{GDBP}) disas 0x32c4, 0x32e4 +++Dump of assembler code from 0x32c4 to 0x32e4: +++ 0x32c4 : addil 0,dp +++ 0x32c8 : ldw 0x22c(sr0,r1),r26 +++ 0x32cc : ldil 0x3000,r31 +++ 0x32d0 : ble 0x3f8(sr4,r31) +++ 0x32d4 : ldo 0(r31),rp +++ 0x32d8 : addil -0x800,dp +++ 0x32dc : ldo 0x588(r1),r26 +++ 0x32e0 : ldil 0x3000,r31 +++End of assembler dump. +++@end smallexample +++ +++Here is an example showing mixed source+assembly for Intel x86 +++with @code{/m} or @code{/s}, when the program is stopped just after +++function prologue in a non-optimized function with no inline code. +++ +++@smallexample +++(@value{GDBP}) disas /m main +++Dump of assembler code for function main: +++5 @{ +++ 0x08048330 <+0>: push %ebp +++ 0x08048331 <+1>: mov %esp,%ebp +++ 0x08048333 <+3>: sub $0x8,%esp +++ 0x08048336 <+6>: and $0xfffffff0,%esp +++ 0x08048339 <+9>: sub $0x10,%esp +++ +++6 printf ("Hello.\n"); +++=> 0x0804833c <+12>: movl $0x8048440,(%esp) +++ 0x08048343 <+19>: call 0x8048284 +++ +++7 return 0; +++8 @} +++ 0x08048348 <+24>: mov $0x0,%eax +++ 0x0804834d <+29>: leave +++ 0x0804834e <+30>: ret +++ +++End of assembler dump. +++@end smallexample +++ +++The @code{/m} option is deprecated as its output is not useful when +++there is either inlined code or re-ordered code. +++The @code{/s} option is the preferred choice. +++Here is an example for AMD x86-64 showing the difference between +++@code{/m} output and @code{/s} output. +++This example has one inline function defined in a header file, +++and the code is compiled with @samp{-O2} optimization. +++Note how the @code{/m} output is missing the disassembly of +++several instructions that are present in the @code{/s} output. +++ +++@file{foo.h}: +++ +++@smallexample +++int +++foo (int a) +++@{ +++ if (a < 0) +++ return a * 2; +++ if (a == 0) +++ return 1; +++ return a + 10; +++@} +++@end smallexample +++ +++@file{foo.c}: +++ +++@smallexample +++#include "foo.h" +++volatile int x, y; +++int +++main () +++@{ +++ x = foo (y); +++ return 0; +++@} +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) disas /m main +++Dump of assembler code for function main: +++5 @{ +++ +++6 x = foo (y); +++ 0x0000000000400400 <+0>: mov 0x200c2e(%rip),%eax # 0x601034 +++ 0x0000000000400417 <+23>: mov %eax,0x200c13(%rip) # 0x601030 +++ +++7 return 0; +++8 @} +++ 0x000000000040041d <+29>: xor %eax,%eax +++ 0x000000000040041f <+31>: retq +++ 0x0000000000400420 <+32>: add %eax,%eax +++ 0x0000000000400422 <+34>: jmp 0x400417 +++ +++End of assembler dump. +++(@value{GDBP}) disas /s main +++Dump of assembler code for function main: +++foo.c: +++5 @{ +++6 x = foo (y); +++ 0x0000000000400400 <+0>: mov 0x200c2e(%rip),%eax # 0x601034 +++ +++foo.h: +++4 if (a < 0) +++ 0x0000000000400406 <+6>: test %eax,%eax +++ 0x0000000000400408 <+8>: js 0x400420 +++ +++6 if (a == 0) +++7 return 1; +++8 return a + 10; +++ 0x000000000040040a <+10>: lea 0xa(%rax),%edx +++ 0x000000000040040d <+13>: test %eax,%eax +++ 0x000000000040040f <+15>: mov $0x1,%eax +++ 0x0000000000400414 <+20>: cmovne %edx,%eax +++ +++foo.c: +++6 x = foo (y); +++ 0x0000000000400417 <+23>: mov %eax,0x200c13(%rip) # 0x601030 +++ +++7 return 0; +++8 @} +++ 0x000000000040041d <+29>: xor %eax,%eax +++ 0x000000000040041f <+31>: retq +++ +++foo.h: +++5 return a * 2; +++ 0x0000000000400420 <+32>: add %eax,%eax +++ 0x0000000000400422 <+34>: jmp 0x400417 +++End of assembler dump. +++@end smallexample +++ +++Here is another example showing raw instructions in hex for AMD x86-64, +++ +++@smallexample +++(gdb) disas /r 0x400281,+10 +++Dump of assembler code from 0x400281 to 0x40028b: +++ 0x0000000000400281: 38 36 cmp %dh,(%rsi) +++ 0x0000000000400283: 2d 36 34 2e 73 sub $0x732e3436,%eax +++ 0x0000000000400288: 6f outsl %ds:(%rsi),(%dx) +++ 0x0000000000400289: 2e 32 00 xor %cs:(%rax),%al +++End of assembler dump. +++@end smallexample +++ +++Addresses cannot be specified as a location (@pxref{Specify Location}). +++So, for example, if you want to disassemble function @code{bar} +++in file @file{foo.c}, you must type @samp{disassemble 'foo.c'::bar} +++and not @samp{disassemble foo.c:bar}. +++ +++Some architectures have more than one commonly-used set of instruction +++mnemonics or other syntax. +++ +++For programs that were dynamically linked and use shared libraries, +++instructions that call functions or branch to locations in the shared +++libraries might show a seemingly bogus location---it's actually a +++location of the relocation table. On some architectures, @value{GDBN} +++might be able to resolve these to actual function names. +++ +++@table @code +++@kindex set disassembler-options +++@cindex disassembler options +++@item set disassembler-options @var{option1}[,@var{option2}@dots{}] +++This command controls the passing of target specific information to +++the disassembler. For a list of valid options, please refer to the +++@code{-M}/@code{--disassembler-options} section of the @samp{objdump} +++manual and/or the output of @kbd{objdump --help} +++(@pxref{objdump,,objdump,binutils,The GNU Binary Utilities}). +++The default value is the empty string. +++ +++If it is necessary to specify more than one disassembler option, then +++multiple options can be placed together into a comma separated list. +++Currently this command is only supported on targets ARM, MIPS, PowerPC +++and S/390. +++ +++@kindex show disassembler-options +++@item show disassembler-options +++Show the current setting of the disassembler options. +++@end table +++ +++@table @code +++@kindex set disassembly-flavor +++@cindex Intel disassembly flavor +++@cindex AT&T disassembly flavor +++@item set disassembly-flavor @var{instruction-set} +++Select the instruction set to use when disassembling the +++program via the @code{disassemble} or @code{x/i} commands. +++ +++Currently this command is only defined for the Intel x86 family. You +++can set @var{instruction-set} to either @code{intel} or @code{att}. +++The default is @code{att}, the AT&T flavor used by default by Unix +++assemblers for x86-based targets. +++ +++@kindex show disassembly-flavor +++@item show disassembly-flavor +++Show the current setting of the disassembly flavor. +++@end table +++ +++@table @code +++@kindex set disassemble-next-line +++@kindex show disassemble-next-line +++@item set disassemble-next-line +++@itemx show disassemble-next-line +++Control whether or not @value{GDBN} will disassemble the next source +++line or instruction when execution stops. If ON, @value{GDBN} will +++display disassembly of the next source line when execution of the +++program being debugged stops. This is @emph{in addition} to +++displaying the source line itself, which @value{GDBN} always does if +++possible. If the next source line cannot be displayed for some reason +++(e.g., if @value{GDBN} cannot find the source file, or there's no line +++info in the debug info), @value{GDBN} will display disassembly of the +++next @emph{instruction} instead of showing the next source line. If +++AUTO, @value{GDBN} will display disassembly of next instruction only +++if the source line cannot be displayed. This setting causes +++@value{GDBN} to display some feedback when you step through a function +++with no line info or whose source file is unavailable. The default is +++OFF, which means never display the disassembly of the next line or +++instruction. +++@end table +++ +++ +++@node Data +++@chapter Examining Data +++ +++@cindex printing data +++@cindex examining data +++@kindex print +++@kindex inspect +++The usual way to examine data in your program is with the @code{print} +++command (abbreviated @code{p}), or its synonym @code{inspect}. It +++evaluates and prints the value of an expression of the language your +++program is written in (@pxref{Languages, ,Using @value{GDBN} with +++Different Languages}). It may also print the expression using a +++Python-based pretty-printer (@pxref{Pretty Printing}). +++ +++@table @code +++@item print [[@var{options}] --] @var{expr} +++@itemx print [[@var{options}] --] /@var{f} @var{expr} +++@var{expr} is an expression (in the source language). By default the +++value of @var{expr} is printed in a format appropriate to its data type; +++you can choose a different format by specifying @samp{/@var{f}}, where +++@var{f} is a letter specifying the format; see @ref{Output Formats,,Output +++Formats}. +++ +++@anchor{print options} +++The @code{print} command supports a number of options that allow +++overriding relevant global print settings as set by @code{set print} +++subcommands: +++ +++@table @code +++@item -address [@code{on}|@code{off}] +++Set printing of addresses. +++Related setting: @ref{set print address}. +++ +++@item -array [@code{on}|@code{off}] +++Pretty formatting of arrays. +++Related setting: @ref{set print array}. +++ +++@item -array-indexes [@code{on}|@code{off}] +++Set printing of array indexes. +++Related setting: @ref{set print array-indexes}. +++ +++@item -elements @var{number-of-elements}|@code{unlimited} +++Set limit on string chars or array elements to print. The value +++@code{unlimited} causes there to be no limit. Related setting: +++@ref{set print elements}. +++ +++@item -max-depth @var{depth}|@code{unlimited} +++Set the threshold after which nested structures are replaced with +++ellipsis. Related setting: @ref{set print max-depth}. +++ +++@item -null-stop [@code{on}|@code{off}] +++Set printing of char arrays to stop at first null char. Related +++setting: @ref{set print null-stop}. +++ +++@item -object [@code{on}|@code{off}] +++Set printing C@t{++} virtual function tables. Related setting: +++@ref{set print object}. +++ +++@item -pretty [@code{on}|@code{off}] +++Set pretty formatting of structures. Related setting: @ref{set print +++pretty}. +++ +++@item -raw-values [@code{on}|@code{off}] +++Set whether to print values in raw form, bypassing any +++pretty-printers for that value. Related setting: @ref{set print +++raw-values}. +++ +++@item -repeats @var{number-of-repeats}|@code{unlimited} +++Set threshold for repeated print elements. @code{unlimited} causes +++all elements to be individually printed. Related setting: @ref{set +++print repeats}. +++ +++@item -static-members [@code{on}|@code{off}] +++Set printing C@t{++} static members. Related setting: @ref{set print +++static-members}. +++ +++@item -symbol [@code{on}|@code{off}] +++Set printing of symbol names when printing pointers. Related setting: +++@ref{set print symbol}. +++ +++@item -union [@code{on}|@code{off}] +++Set printing of unions interior to structures. Related setting: +++@ref{set print union}. +++ +++@item -vtbl [@code{on}|@code{off}] +++Set printing of C++ virtual function tables. Related setting: +++@ref{set print vtbl}. +++@end table +++ +++Because the @code{print} command accepts arbitrary expressions which +++may look like options (including abbreviations), if you specify any +++command option, then you must use a double dash (@code{--}) to mark +++the end of option processing. +++ +++For example, this prints the value of the @code{-p} expression: +++ +++@smallexample +++(@value{GDBP}) print -p +++@end smallexample +++ +++While this repeats the last value in the value history (see below) +++with the @code{-pretty} option in effect: +++ +++@smallexample +++(@value{GDBP}) print -p -- +++@end smallexample +++ +++Here is an example including both on option and an expression: +++ +++@smallexample +++@group +++(@value{GDBP}) print -pretty -- *myptr +++$1 = @{ +++ next = 0x0, +++ flags = @{ +++ sweet = 1, +++ sour = 1 +++ @}, +++ meat = 0x54 "Pork" +++@} +++@end group +++@end smallexample +++ +++@item print [@var{options}] +++@itemx print [@var{options}] /@var{f} +++@cindex reprint the last value +++If you omit @var{expr}, @value{GDBN} displays the last value again (from the +++@dfn{value history}; @pxref{Value History, ,Value History}). This allows you to +++conveniently inspect the same value in an alternative format. +++@end table +++ +++A more low-level way of examining data is with the @code{x} command. +++It examines data in memory at a specified address and prints it in a +++specified format. @xref{Memory, ,Examining Memory}. +++ +++If you are interested in information about types, or about how the +++fields of a struct or a class are declared, use the @code{ptype @var{exp}} +++command rather than @code{print}. @xref{Symbols, ,Examining the Symbol +++Table}. +++ +++@cindex exploring hierarchical data structures +++@kindex explore +++Another way of examining values of expressions and type information is +++through the Python extension command @code{explore} (available only if +++the @value{GDBN} build is configured with @code{--with-python}). It +++offers an interactive way to start at the highest level (or, the most +++abstract level) of the data type of an expression (or, the data type +++itself) and explore all the way down to leaf scalar values/fields +++embedded in the higher level data types. +++ +++@table @code +++@item explore @var{arg} +++@var{arg} is either an expression (in the source language), or a type +++visible in the current context of the program being debugged. +++@end table +++ +++The working of the @code{explore} command can be illustrated with an +++example. If a data type @code{struct ComplexStruct} is defined in your +++C program as +++ +++@smallexample +++struct SimpleStruct +++@{ +++ int i; +++ double d; +++@}; +++ +++struct ComplexStruct +++@{ +++ struct SimpleStruct *ss_p; +++ int arr[10]; +++@}; +++@end smallexample +++ +++@noindent +++followed by variable declarations as +++ +++@smallexample +++struct SimpleStruct ss = @{ 10, 1.11 @}; +++struct ComplexStruct cs = @{ &ss, @{ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 @} @}; +++@end smallexample +++ +++@noindent +++then, the value of the variable @code{cs} can be explored using the +++@code{explore} command as follows. +++ +++@smallexample +++(gdb) explore cs +++The value of `cs' is a struct/class of type `struct ComplexStruct' with +++the following fields: +++ +++ ss_p = +++ arr = +++ +++Enter the field number of choice: +++@end smallexample +++ +++@noindent +++Since the fields of @code{cs} are not scalar values, you are being +++prompted to chose the field you want to explore. Let's say you choose +++the field @code{ss_p} by entering @code{0}. Then, since this field is a +++pointer, you will be asked if it is pointing to a single value. From +++the declaration of @code{cs} above, it is indeed pointing to a single +++value, hence you enter @code{y}. If you enter @code{n}, then you will +++be asked if it were pointing to an array of values, in which case this +++field will be explored as if it were an array. +++ +++@smallexample +++`cs.ss_p' is a pointer to a value of type `struct SimpleStruct' +++Continue exploring it as a pointer to a single value [y/n]: y +++The value of `*(cs.ss_p)' is a struct/class of type `struct +++SimpleStruct' with the following fields: +++ +++ i = 10 .. (Value of type `int') +++ d = 1.1100000000000001 .. (Value of type `double') +++ +++Press enter to return to parent value: +++@end smallexample +++ +++@noindent +++If the field @code{arr} of @code{cs} was chosen for exploration by +++entering @code{1} earlier, then since it is as array, you will be +++prompted to enter the index of the element in the array that you want +++to explore. +++ +++@smallexample +++`cs.arr' is an array of `int'. +++Enter the index of the element you want to explore in `cs.arr': 5 +++ +++`(cs.arr)[5]' is a scalar value of type `int'. +++ +++(cs.arr)[5] = 4 +++ +++Press enter to return to parent value: +++@end smallexample +++ +++In general, at any stage of exploration, you can go deeper towards the +++leaf values by responding to the prompts appropriately, or hit the +++return key to return to the enclosing data structure (the @i{higher} +++level data structure). +++ +++Similar to exploring values, you can use the @code{explore} command to +++explore types. Instead of specifying a value (which is typically a +++variable name or an expression valid in the current context of the +++program being debugged), you specify a type name. If you consider the +++same example as above, your can explore the type +++@code{struct ComplexStruct} by passing the argument +++@code{struct ComplexStruct} to the @code{explore} command. +++ +++@smallexample +++(gdb) explore struct ComplexStruct +++@end smallexample +++ +++@noindent +++By responding to the prompts appropriately in the subsequent interactive +++session, you can explore the type @code{struct ComplexStruct} in a +++manner similar to how the value @code{cs} was explored in the above +++example. +++ +++The @code{explore} command also has two sub-commands, +++@code{explore value} and @code{explore type}. The former sub-command is +++a way to explicitly specify that value exploration of the argument is +++being invoked, while the latter is a way to explicitly specify that type +++exploration of the argument is being invoked. +++ +++@table @code +++@item explore value @var{expr} +++@cindex explore value +++This sub-command of @code{explore} explores the value of the +++expression @var{expr} (if @var{expr} is an expression valid in the +++current context of the program being debugged). The behavior of this +++command is identical to that of the behavior of the @code{explore} +++command being passed the argument @var{expr}. +++ +++@item explore type @var{arg} +++@cindex explore type +++This sub-command of @code{explore} explores the type of @var{arg} (if +++@var{arg} is a type visible in the current context of program being +++debugged), or the type of the value/expression @var{arg} (if @var{arg} +++is an expression valid in the current context of the program being +++debugged). If @var{arg} is a type, then the behavior of this command is +++identical to that of the @code{explore} command being passed the +++argument @var{arg}. If @var{arg} is an expression, then the behavior of +++this command will be identical to that of the @code{explore} command +++being passed the type of @var{arg} as the argument. +++@end table +++ +++@menu +++* Expressions:: Expressions +++* Ambiguous Expressions:: Ambiguous Expressions +++* Variables:: Program variables +++* Arrays:: Artificial arrays +++* Output Formats:: Output formats +++* Memory:: Examining memory +++* Auto Display:: Automatic display +++* Print Settings:: Print settings +++* Pretty Printing:: Python pretty printing +++* Value History:: Value history +++* Convenience Vars:: Convenience variables +++* Convenience Funs:: Convenience functions +++* Registers:: Registers +++* Floating Point Hardware:: Floating point hardware +++* Vector Unit:: Vector Unit +++* OS Information:: Auxiliary data provided by operating system +++* Memory Region Attributes:: Memory region attributes +++* Dump/Restore Files:: Copy between memory and a file +++* Core File Generation:: Cause a program dump its core +++* Character Sets:: Debugging programs that use a different +++ character set than GDB does +++* Caching Target Data:: Data caching for targets +++* Searching Memory:: Searching memory for a sequence of bytes +++* Value Sizes:: Managing memory allocated for values +++@end menu +++ +++@node Expressions +++@section Expressions +++ +++@cindex expressions +++@code{print} and many other @value{GDBN} commands accept an expression and +++compute its value. Any kind of constant, variable or operator defined +++by the programming language you are using is valid in an expression in +++@value{GDBN}. This includes conditional expressions, function calls, +++casts, and string constants. It also includes preprocessor macros, if +++you compiled your program to include this information; see +++@ref{Compilation}. +++ +++@cindex arrays in expressions +++@value{GDBN} supports array constants in expressions input by +++the user. The syntax is @{@var{element}, @var{element}@dots{}@}. For example, +++you can use the command @code{print @{1, 2, 3@}} to create an array +++of three integers. If you pass an array to a function or assign it +++to a program variable, @value{GDBN} copies the array to memory that +++is @code{malloc}ed in the target program. +++ +++Because C is so widespread, most of the expressions shown in examples in +++this manual are in C. @xref{Languages, , Using @value{GDBN} with Different +++Languages}, for information on how to use expressions in other +++languages. +++ +++In this section, we discuss operators that you can use in @value{GDBN} +++expressions regardless of your programming language. +++ +++@cindex casts, in expressions +++Casts are supported in all languages, not just in C, because it is so +++useful to cast a number into a pointer in order to examine a structure +++at that address in memory. +++@c FIXME: casts supported---Mod2 true? +++ +++@value{GDBN} supports these operators, in addition to those common +++to programming languages: +++ +++@table @code +++@item @@ +++@samp{@@} is a binary operator for treating parts of memory as arrays. +++@xref{Arrays, ,Artificial Arrays}, for more information. +++ +++@item :: +++@samp{::} allows you to specify a variable in terms of the file or +++function where it is defined. @xref{Variables, ,Program Variables}. +++ +++@cindex @{@var{type}@} +++@cindex type casting memory +++@cindex memory, viewing as typed object +++@cindex casts, to view memory +++@item @{@var{type}@} @var{addr} +++Refers to an object of type @var{type} stored at address @var{addr} in +++memory. The address @var{addr} may be any expression whose value is +++an integer or pointer (but parentheses are required around binary +++operators, just as in a cast). This construct is allowed regardless +++of what kind of data is normally supposed to reside at @var{addr}. +++@end table +++ +++@node Ambiguous Expressions +++@section Ambiguous Expressions +++@cindex ambiguous expressions +++ +++Expressions can sometimes contain some ambiguous elements. For instance, +++some programming languages (notably Ada, C@t{++} and Objective-C) permit +++a single function name to be defined several times, for application in +++different contexts. This is called @dfn{overloading}. Another example +++involving Ada is generics. A @dfn{generic package} is similar to C@t{++} +++templates and is typically instantiated several times, resulting in +++the same function name being defined in different contexts. +++ +++In some cases and depending on the language, it is possible to adjust +++the expression to remove the ambiguity. For instance in C@t{++}, you +++can specify the signature of the function you want to break on, as in +++@kbd{break @var{function}(@var{types})}. In Ada, using the fully +++qualified name of your function often makes the expression unambiguous +++as well. +++ +++When an ambiguity that needs to be resolved is detected, the debugger +++has the capability to display a menu of numbered choices for each +++possibility, and then waits for the selection with the prompt @samp{>}. +++The first option is always @samp{[0] cancel}, and typing @kbd{0 @key{RET}} +++aborts the current command. If the command in which the expression was +++used allows more than one choice to be selected, the next option in the +++menu is @samp{[1] all}, and typing @kbd{1 @key{RET}} selects all possible +++choices. +++ +++For example, the following session excerpt shows an attempt to set a +++breakpoint at the overloaded symbol @code{String::after}. +++We choose three particular definitions of that function name: +++ +++@c FIXME! This is likely to change to show arg type lists, at least +++@smallexample +++@group +++(@value{GDBP}) b String::after +++[0] cancel +++[1] all +++[2] file:String.cc; line number:867 +++[3] file:String.cc; line number:860 +++[4] file:String.cc; line number:875 +++[5] file:String.cc; line number:853 +++[6] file:String.cc; line number:846 +++[7] file:String.cc; line number:735 +++> 2 4 6 +++Breakpoint 1 at 0xb26c: file String.cc, line 867. +++Breakpoint 2 at 0xb344: file String.cc, line 875. +++Breakpoint 3 at 0xafcc: file String.cc, line 846. +++Multiple breakpoints were set. +++Use the "delete" command to delete unwanted +++ breakpoints. +++(@value{GDBP}) +++@end group +++@end smallexample +++ +++@table @code +++@kindex set multiple-symbols +++@item set multiple-symbols @var{mode} +++@cindex multiple-symbols menu +++ +++This option allows you to adjust the debugger behavior when an expression +++is ambiguous. +++ +++By default, @var{mode} is set to @code{all}. If the command with which +++the expression is used allows more than one choice, then @value{GDBN} +++automatically selects all possible choices. For instance, inserting +++a breakpoint on a function using an ambiguous name results in a breakpoint +++inserted on each possible match. However, if a unique choice must be made, +++then @value{GDBN} uses the menu to help you disambiguate the expression. +++For instance, printing the address of an overloaded function will result +++in the use of the menu. +++ +++When @var{mode} is set to @code{ask}, the debugger always uses the menu +++when an ambiguity is detected. +++ +++Finally, when @var{mode} is set to @code{cancel}, the debugger reports +++an error due to the ambiguity and the command is aborted. +++ +++@kindex show multiple-symbols +++@item show multiple-symbols +++Show the current value of the @code{multiple-symbols} setting. +++@end table +++ +++@node Variables +++@section Program Variables +++ +++The most common kind of expression to use is the name of a variable +++in your program. +++ +++Variables in expressions are understood in the selected stack frame +++(@pxref{Selection, ,Selecting a Frame}); they must be either: +++ +++@itemize @bullet +++@item +++global (or file-static) +++@end itemize +++ +++@noindent or +++ +++@itemize @bullet +++@item +++visible according to the scope rules of the +++programming language from the point of execution in that frame +++@end itemize +++ +++@noindent This means that in the function +++ +++@smallexample +++foo (a) +++ int a; +++@{ +++ bar (a); +++ @{ +++ int b = test (); +++ bar (b); +++ @} +++@} +++@end smallexample +++ +++@noindent +++you can examine and use the variable @code{a} whenever your program is +++executing within the function @code{foo}, but you can only use or +++examine the variable @code{b} while your program is executing inside +++the block where @code{b} is declared. +++ +++@cindex variable name conflict +++There is an exception: you can refer to a variable or function whose +++scope is a single source file even if the current execution point is not +++in this file. But it is possible to have more than one such variable or +++function with the same name (in different source files). If that +++happens, referring to that name has unpredictable effects. If you wish, +++you can specify a static variable in a particular function or file by +++using the colon-colon (@code{::}) notation: +++ +++@cindex colon-colon, context for variables/functions +++@ifnotinfo +++@c info cannot cope with a :: index entry, but why deprive hard copy readers? +++@cindex @code{::}, context for variables/functions +++@end ifnotinfo +++@smallexample +++@var{file}::@var{variable} +++@var{function}::@var{variable} +++@end smallexample +++ +++@noindent +++Here @var{file} or @var{function} is the name of the context for the +++static @var{variable}. In the case of file names, you can use quotes to +++make sure @value{GDBN} parses the file name as a single word---for example, +++to print a global value of @code{x} defined in @file{f2.c}: +++ +++@smallexample +++(@value{GDBP}) p 'f2.c'::x +++@end smallexample +++ +++The @code{::} notation is normally used for referring to +++static variables, since you typically disambiguate uses of local variables +++in functions by selecting the appropriate frame and using the +++simple name of the variable. However, you may also use this notation +++to refer to local variables in frames enclosing the selected frame: +++ +++@smallexample +++void +++foo (int a) +++@{ +++ if (a < 10) +++ bar (a); +++ else +++ process (a); /* Stop here */ +++@} +++ +++int +++bar (int a) +++@{ +++ foo (a + 5); +++@} +++@end smallexample +++ +++@noindent +++For example, if there is a breakpoint at the commented line, +++here is what you might see +++when the program stops after executing the call @code{bar(0)}: +++ +++@smallexample +++(@value{GDBP}) p a +++$1 = 10 +++(@value{GDBP}) p bar::a +++$2 = 5 +++(@value{GDBP}) up 2 +++#2 0x080483d0 in foo (a=5) at foobar.c:12 +++(@value{GDBP}) p a +++$3 = 5 +++(@value{GDBP}) p bar::a +++$4 = 0 +++@end smallexample +++ +++@cindex C@t{++} scope resolution +++These uses of @samp{::} are very rarely in conflict with the very +++similar use of the same notation in C@t{++}. When they are in +++conflict, the C@t{++} meaning takes precedence; however, this can be +++overridden by quoting the file or function name with single quotes. +++ +++For example, suppose the program is stopped in a method of a class +++that has a field named @code{includefile}, and there is also an +++include file named @file{includefile} that defines a variable, +++@code{some_global}. +++ +++@smallexample +++(@value{GDBP}) p includefile +++$1 = 23 +++(@value{GDBP}) p includefile::some_global +++A syntax error in expression, near `'. +++(@value{GDBP}) p 'includefile'::some_global +++$2 = 27 +++@end smallexample +++ +++@cindex wrong values +++@cindex variable values, wrong +++@cindex function entry/exit, wrong values of variables +++@cindex optimized code, wrong values of variables +++@quotation +++@emph{Warning:} Occasionally, a local variable may appear to have the +++wrong value at certain points in a function---just after entry to a new +++scope, and just before exit. +++@end quotation +++You may see this problem when you are stepping by machine instructions. +++This is because, on most machines, it takes more than one instruction to +++set up a stack frame (including local variable definitions); if you are +++stepping by machine instructions, variables may appear to have the wrong +++values until the stack frame is completely built. On exit, it usually +++also takes more than one machine instruction to destroy a stack frame; +++after you begin stepping through that group of instructions, local +++variable definitions may be gone. +++ +++This may also happen when the compiler does significant optimizations. +++To be sure of always seeing accurate values, turn off all optimization +++when compiling. +++ +++@cindex ``No symbol "foo" in current context'' +++Another possible effect of compiler optimizations is to optimize +++unused variables out of existence, or assign variables to registers (as +++opposed to memory addresses). Depending on the support for such cases +++offered by the debug info format used by the compiler, @value{GDBN} +++might not be able to display values for such local variables. If that +++happens, @value{GDBN} will print a message like this: +++ +++@smallexample +++No symbol "foo" in current context. +++@end smallexample +++ +++To solve such problems, either recompile without optimizations, or use a +++different debug info format, if the compiler supports several such +++formats. @xref{Compilation}, for more information on choosing compiler +++options. @xref{C, ,C and C@t{++}}, for more information about debug +++info formats that are best suited to C@t{++} programs. +++ +++If you ask to print an object whose contents are unknown to +++@value{GDBN}, e.g., because its data type is not completely specified +++by the debug information, @value{GDBN} will say @samp{}. @xref{Symbols, incomplete type}, for more about this. +++ +++@cindex no debug info variables +++If you try to examine or use the value of a (global) variable for +++which @value{GDBN} has no type information, e.g., because the program +++includes no debug information, @value{GDBN} displays an error message. +++@xref{Symbols, unknown type}, for more about unknown types. If you +++cast the variable to its declared type, @value{GDBN} gets the +++variable's value using the cast-to type as the variable's type. For +++example, in a C program: +++ +++@smallexample +++ (@value{GDBP}) p var +++ 'var' has unknown type; cast it to its declared type +++ (@value{GDBP}) p (float) var +++ $1 = 3.14 +++@end smallexample +++ +++If you append @kbd{@@entry} string to a function parameter name you get its +++value at the time the function got called. If the value is not available an +++error message is printed. Entry values are available only with some compilers. +++Entry values are normally also printed at the function parameter list according +++to @ref{set print entry-values}. +++ +++@smallexample +++Breakpoint 1, d (i=30) at gdb.base/entry-value.c:29 +++29 i++; +++(gdb) next +++30 e (i); +++(gdb) print i +++$1 = 31 +++(gdb) print i@@entry +++$2 = 30 +++@end smallexample +++ +++Strings are identified as arrays of @code{char} values without specified +++signedness. Arrays of either @code{signed char} or @code{unsigned char} get +++printed as arrays of 1 byte sized integers. @code{-fsigned-char} or +++@code{-funsigned-char} @value{NGCC} options have no effect as @value{GDBN} +++defines literal string type @code{"char"} as @code{char} without a sign. +++For program code +++ +++@smallexample +++char var0[] = "A"; +++signed char var1[] = "A"; +++@end smallexample +++ +++You get during debugging +++@smallexample +++(gdb) print var0 +++$1 = "A" +++(gdb) print var1 +++$2 = @{65 'A', 0 '\0'@} +++@end smallexample +++ +++@node Arrays +++@section Artificial Arrays +++ +++@cindex artificial array +++@cindex arrays +++@kindex @@@r{, referencing memory as an array} +++It is often useful to print out several successive objects of the +++same type in memory; a section of an array, or an array of +++dynamically determined size for which only a pointer exists in the +++program. +++ +++You can do this by referring to a contiguous span of memory as an +++@dfn{artificial array}, using the binary operator @samp{@@}. The left +++operand of @samp{@@} should be the first element of the desired array +++and be an individual object. The right operand should be the desired length +++of the array. The result is an array value whose elements are all of +++the type of the left argument. The first element is actually the left +++argument; the second element comes from bytes of memory immediately +++following those that hold the first element, and so on. Here is an +++example. If a program says +++ +++@smallexample +++int *array = (int *) malloc (len * sizeof (int)); +++@end smallexample +++ +++@noindent +++you can print the contents of @code{array} with +++ +++@smallexample +++p *array@@len +++@end smallexample +++ +++The left operand of @samp{@@} must reside in memory. Array values made +++with @samp{@@} in this way behave just like other arrays in terms of +++subscripting, and are coerced to pointers when used in expressions. +++Artificial arrays most often appear in expressions via the value history +++(@pxref{Value History, ,Value History}), after printing one out. +++ +++Another way to create an artificial array is to use a cast. +++This re-interprets a value as if it were an array. +++The value need not be in memory: +++@smallexample +++(@value{GDBP}) p/x (short[2])0x12345678 +++$1 = @{0x1234, 0x5678@} +++@end smallexample +++ +++As a convenience, if you leave the array length out (as in +++@samp{(@var{type}[])@var{value}}) @value{GDBN} calculates the size to fill +++the value (as @samp{sizeof(@var{value})/sizeof(@var{type})}: +++@smallexample +++(@value{GDBP}) p/x (short[])0x12345678 +++$2 = @{0x1234, 0x5678@} +++@end smallexample +++ +++Sometimes the artificial array mechanism is not quite enough; in +++moderately complex data structures, the elements of interest may not +++actually be adjacent---for example, if you are interested in the values +++of pointers in an array. One useful work-around in this situation is +++to use a convenience variable (@pxref{Convenience Vars, ,Convenience +++Variables}) as a counter in an expression that prints the first +++interesting value, and then repeat that expression via @key{RET}. For +++instance, suppose you have an array @code{dtab} of pointers to +++structures, and you are interested in the values of a field @code{fv} +++in each structure. Here is an example of what you might type: +++ +++@smallexample +++set $i = 0 +++p dtab[$i++]->fv +++@key{RET} +++@key{RET} +++@dots{} +++@end smallexample +++ +++@node Output Formats +++@section Output Formats +++ +++@cindex formatted output +++@cindex output formats +++By default, @value{GDBN} prints a value according to its data type. Sometimes +++this is not what you want. For example, you might want to print a number +++in hex, or a pointer in decimal. Or you might want to view data in memory +++at a certain address as a character string or as an instruction. To do +++these things, specify an @dfn{output format} when you print a value. +++ +++The simplest use of output formats is to say how to print a value +++already computed. This is done by starting the arguments of the +++@code{print} command with a slash and a format letter. The format +++letters supported are: +++ +++@table @code +++@item x +++Regard the bits of the value as an integer, and print the integer in +++hexadecimal. +++ +++@item d +++Print as integer in signed decimal. +++ +++@item u +++Print as integer in unsigned decimal. +++ +++@item o +++Print as integer in octal. +++ +++@item t +++Print as integer in binary. The letter @samp{t} stands for ``two''. +++@footnote{@samp{b} cannot be used because these format letters are also +++used with the @code{x} command, where @samp{b} stands for ``byte''; +++see @ref{Memory,,Examining Memory}.} +++ +++@item a +++@cindex unknown address, locating +++@cindex locate address +++Print as an address, both absolute in hexadecimal and as an offset from +++the nearest preceding symbol. You can use this format used to discover +++where (in what function) an unknown address is located: +++ +++@smallexample +++(@value{GDBP}) p/a 0x54320 +++$3 = 0x54320 <_initialize_vx+396> +++@end smallexample +++ +++@noindent +++The command @code{info symbol 0x54320} yields similar results. +++@xref{Symbols, info symbol}. +++ +++@item c +++Regard as an integer and print it as a character constant. This +++prints both the numerical value and its character representation. The +++character representation is replaced with the octal escape @samp{\nnn} +++for characters outside the 7-bit @sc{ascii} range. +++ +++Without this format, @value{GDBN} displays @code{char}, +++@w{@code{unsigned char}}, and @w{@code{signed char}} data as character +++constants. Single-byte members of vectors are displayed as integer +++data. +++ +++@item f +++Regard the bits of the value as a floating point number and print +++using typical floating point syntax. +++ +++@item s +++@cindex printing strings +++@cindex printing byte arrays +++Regard as a string, if possible. With this format, pointers to single-byte +++data are displayed as null-terminated strings and arrays of single-byte data +++are displayed as fixed-length strings. Other values are displayed in their +++natural types. +++ +++Without this format, @value{GDBN} displays pointers to and arrays of +++@code{char}, @w{@code{unsigned char}}, and @w{@code{signed char}} as +++strings. Single-byte members of a vector are displayed as an integer +++array. +++ +++@item z +++Like @samp{x} formatting, the value is treated as an integer and +++printed as hexadecimal, but leading zeros are printed to pad the value +++to the size of the integer type. +++ +++@item r +++@cindex raw printing +++Print using the @samp{raw} formatting. By default, @value{GDBN} will +++use a Python-based pretty-printer, if one is available (@pxref{Pretty +++Printing}). This typically results in a higher-level display of the +++value's contents. The @samp{r} format bypasses any Python +++pretty-printer which might exist. +++@end table +++ +++For example, to print the program counter in hex (@pxref{Registers}), type +++ +++@smallexample +++p/x $pc +++@end smallexample +++ +++@noindent +++Note that no space is required before the slash; this is because command +++names in @value{GDBN} cannot contain a slash. +++ +++To reprint the last value in the value history with a different format, +++you can use the @code{print} command with just a format and no +++expression. For example, @samp{p/x} reprints the last value in hex. +++ +++@node Memory +++@section Examining Memory +++ +++You can use the command @code{x} (for ``examine'') to examine memory in +++any of several formats, independently of your program's data types. +++ +++@cindex examining memory +++@table @code +++@kindex x @r{(examine memory)} +++@item x/@var{nfu} @var{addr} +++@itemx x @var{addr} +++@itemx x +++Use the @code{x} command to examine memory. +++@end table +++ +++@var{n}, @var{f}, and @var{u} are all optional parameters that specify how +++much memory to display and how to format it; @var{addr} is an +++expression giving the address where you want to start displaying memory. +++If you use defaults for @var{nfu}, you need not type the slash @samp{/}. +++Several commands set convenient defaults for @var{addr}. +++ +++@table @r +++@item @var{n}, the repeat count +++The repeat count is a decimal integer; the default is 1. It specifies +++how much memory (counting by units @var{u}) to display. If a negative +++number is specified, memory is examined backward from @var{addr}. +++@c This really is **decimal**; unaffected by 'set radix' as of GDB +++@c 4.1.2. +++ +++@item @var{f}, the display format +++The display format is one of the formats used by @code{print} +++(@samp{x}, @samp{d}, @samp{u}, @samp{o}, @samp{t}, @samp{a}, @samp{c}, +++@samp{f}, @samp{s}), and in addition @samp{i} (for machine instructions). +++The default is @samp{x} (hexadecimal) initially. The default changes +++each time you use either @code{x} or @code{print}. +++ +++@item @var{u}, the unit size +++The unit size is any of +++ +++@table @code +++@item b +++Bytes. +++@item h +++Halfwords (two bytes). +++@item w +++Words (four bytes). This is the initial default. +++@item g +++Giant words (eight bytes). +++@end table +++ +++Each time you specify a unit size with @code{x}, that size becomes the +++default unit the next time you use @code{x}. For the @samp{i} format, +++the unit size is ignored and is normally not written. For the @samp{s} format, +++the unit size defaults to @samp{b}, unless it is explicitly given. +++Use @kbd{x /hs} to display 16-bit char strings and @kbd{x /ws} to display +++32-bit strings. The next use of @kbd{x /s} will again display 8-bit strings. +++Note that the results depend on the programming language of the +++current compilation unit. If the language is C, the @samp{s} +++modifier will use the UTF-16 encoding while @samp{w} will use +++UTF-32. The encoding is set by the programming language and cannot +++be altered. +++ +++@item @var{addr}, starting display address +++@var{addr} is the address where you want @value{GDBN} to begin displaying +++memory. The expression need not have a pointer value (though it may); +++it is always interpreted as an integer address of a byte of memory. +++@xref{Expressions, ,Expressions}, for more information on expressions. The default for +++@var{addr} is usually just after the last address examined---but several +++other commands also set the default address: @code{info breakpoints} (to +++the address of the last breakpoint listed), @code{info line} (to the +++starting address of a line), and @code{print} (if you use it to display +++a value from memory). +++@end table +++ +++For example, @samp{x/3uh 0x54320} is a request to display three halfwords +++(@code{h}) of memory, formatted as unsigned decimal integers (@samp{u}), +++starting at address @code{0x54320}. @samp{x/4xw $sp} prints the four +++words (@samp{w}) of memory above the stack pointer (here, @samp{$sp}; +++@pxref{Registers, ,Registers}) in hexadecimal (@samp{x}). +++ +++You can also specify a negative repeat count to examine memory backward +++from the given address. For example, @samp{x/-3uh 0x54320} prints three +++halfwords (@code{h}) at @code{0x54314}, @code{0x54328}, and @code{0x5431c}. +++ +++Since the letters indicating unit sizes are all distinct from the +++letters specifying output formats, you do not have to remember whether +++unit size or format comes first; either order works. The output +++specifications @samp{4xw} and @samp{4wx} mean exactly the same thing. +++(However, the count @var{n} must come first; @samp{wx4} does not work.) +++ +++Even though the unit size @var{u} is ignored for the formats @samp{s} +++and @samp{i}, you might still want to use a count @var{n}; for example, +++@samp{3i} specifies that you want to see three machine instructions, +++including any operands. For convenience, especially when used with +++the @code{display} command, the @samp{i} format also prints branch delay +++slot instructions, if any, beyond the count specified, which immediately +++follow the last instruction that is within the count. The command +++@code{disassemble} gives an alternative way of inspecting machine +++instructions; see @ref{Machine Code,,Source and Machine Code}. +++ +++If a negative repeat count is specified for the formats @samp{s} or @samp{i}, +++the command displays null-terminated strings or instructions before the given +++address as many as the absolute value of the given number. For the @samp{i} +++format, we use line number information in the debug info to accurately locate +++instruction boundaries while disassembling backward. If line info is not +++available, the command stops examining memory with an error message. +++ +++All the defaults for the arguments to @code{x} are designed to make it +++easy to continue scanning memory with minimal specifications each time +++you use @code{x}. For example, after you have inspected three machine +++instructions with @samp{x/3i @var{addr}}, you can inspect the next seven +++with just @samp{x/7}. If you use @key{RET} to repeat the @code{x} command, +++the repeat count @var{n} is used again; the other arguments default as +++for successive uses of @code{x}. +++ +++When examining machine instructions, the instruction at current program +++counter is shown with a @code{=>} marker. For example: +++ +++@smallexample +++(@value{GDBP}) x/5i $pc-6 +++ 0x804837f : mov %esp,%ebp +++ 0x8048381 : push %ecx +++ 0x8048382 : sub $0x4,%esp +++=> 0x8048385 : movl $0x8048460,(%esp) +++ 0x804838c : call 0x80482d4 +++@end smallexample +++ +++@cindex @code{$_}, @code{$__}, and value history +++The addresses and contents printed by the @code{x} command are not saved +++in the value history because there is often too much of them and they +++would get in the way. Instead, @value{GDBN} makes these values available for +++subsequent use in expressions as values of the convenience variables +++@code{$_} and @code{$__}. After an @code{x} command, the last address +++examined is available for use in expressions in the convenience variable +++@code{$_}. The contents of that address, as examined, are available in +++the convenience variable @code{$__}. +++ +++If the @code{x} command has a repeat count, the address and contents saved +++are from the last memory unit printed; this is not the same as the last +++address printed if several units were printed on the last line of output. +++ +++@anchor{addressable memory unit} +++@cindex addressable memory unit +++Most targets have an addressable memory unit size of 8 bits. This means +++that to each memory address are associated 8 bits of data. Some +++targets, however, have other addressable memory unit sizes. +++Within @value{GDBN} and this document, the term +++@dfn{addressable memory unit} (or @dfn{memory unit} for short) is used +++when explicitly referring to a chunk of data of that size. The word +++@dfn{byte} is used to refer to a chunk of data of 8 bits, regardless of +++the addressable memory unit size of the target. For most systems, +++addressable memory unit is a synonym of byte. +++ +++@cindex remote memory comparison +++@cindex target memory comparison +++@cindex verify remote memory image +++@cindex verify target memory image +++When you are debugging a program running on a remote target machine +++(@pxref{Remote Debugging}), you may wish to verify the program's image +++in the remote machine's memory against the executable file you +++downloaded to the target. Or, on any target, you may want to check +++whether the program has corrupted its own read-only sections. The +++@code{compare-sections} command is provided for such situations. +++ +++@table @code +++@kindex compare-sections +++@item compare-sections @r{[}@var{section-name}@r{|}@code{-r}@r{]} +++Compare the data of a loadable section @var{section-name} in the +++executable file of the program being debugged with the same section in +++the target machine's memory, and report any mismatches. With no +++arguments, compares all loadable sections. With an argument of +++@code{-r}, compares all loadable read-only sections. +++ +++Note: for remote targets, this command can be accelerated if the +++target supports computing the CRC checksum of a block of memory +++(@pxref{qCRC packet}). +++@end table +++ +++@node Auto Display +++@section Automatic Display +++@cindex automatic display +++@cindex display of expressions +++ +++If you find that you want to print the value of an expression frequently +++(to see how it changes), you might want to add it to the @dfn{automatic +++display list} so that @value{GDBN} prints its value each time your program stops. +++Each expression added to the list is given a number to identify it; +++to remove an expression from the list, you specify that number. +++The automatic display looks like this: +++ +++@smallexample +++2: foo = 38 +++3: bar[5] = (struct hack *) 0x3804 +++@end smallexample +++ +++@noindent +++This display shows item numbers, expressions and their current values. As with +++displays you request manually using @code{x} or @code{print}, you can +++specify the output format you prefer; in fact, @code{display} decides +++whether to use @code{print} or @code{x} depending your format +++specification---it uses @code{x} if you specify either the @samp{i} +++or @samp{s} format, or a unit size; otherwise it uses @code{print}. +++ +++@table @code +++@kindex display +++@item display @var{expr} +++Add the expression @var{expr} to the list of expressions to display +++each time your program stops. @xref{Expressions, ,Expressions}. +++ +++@code{display} does not repeat if you press @key{RET} again after using it. +++ +++@item display/@var{fmt} @var{expr} +++For @var{fmt} specifying only a display format and not a size or +++count, add the expression @var{expr} to the auto-display list but +++arrange to display it each time in the specified format @var{fmt}. +++@xref{Output Formats,,Output Formats}. +++ +++@item display/@var{fmt} @var{addr} +++For @var{fmt} @samp{i} or @samp{s}, or including a unit-size or a +++number of units, add the expression @var{addr} as a memory address to +++be examined each time your program stops. Examining means in effect +++doing @samp{x/@var{fmt} @var{addr}}. @xref{Memory, ,Examining Memory}. +++@end table +++ +++For example, @samp{display/i $pc} can be helpful, to see the machine +++instruction about to be executed each time execution stops (@samp{$pc} +++is a common name for the program counter; @pxref{Registers, ,Registers}). +++ +++@table @code +++@kindex delete display +++@kindex undisplay +++@item undisplay @var{dnums}@dots{} +++@itemx delete display @var{dnums}@dots{} +++Remove items from the list of expressions to display. Specify the +++numbers of the displays that you want affected with the command +++argument @var{dnums}. It can be a single display number, one of the +++numbers shown in the first field of the @samp{info display} display; +++or it could be a range of display numbers, as in @code{2-4}. +++ +++@code{undisplay} does not repeat if you press @key{RET} after using it. +++(Otherwise you would just get the error @samp{No display number @dots{}}.) +++ +++@kindex disable display +++@item disable display @var{dnums}@dots{} +++Disable the display of item numbers @var{dnums}. A disabled display +++item is not printed automatically, but is not forgotten. It may be +++enabled again later. Specify the numbers of the displays that you +++want affected with the command argument @var{dnums}. It can be a +++single display number, one of the numbers shown in the first field of +++the @samp{info display} display; or it could be a range of display +++numbers, as in @code{2-4}. +++ +++@kindex enable display +++@item enable display @var{dnums}@dots{} +++Enable display of item numbers @var{dnums}. It becomes effective once +++again in auto display of its expression, until you specify otherwise. +++Specify the numbers of the displays that you want affected with the +++command argument @var{dnums}. It can be a single display number, one +++of the numbers shown in the first field of the @samp{info display} +++display; or it could be a range of display numbers, as in @code{2-4}. +++ +++@item display +++Display the current values of the expressions on the list, just as is +++done when your program stops. +++ +++@kindex info display +++@item info display +++Print the list of expressions previously set up to display +++automatically, each one with its item number, but without showing the +++values. This includes disabled expressions, which are marked as such. +++It also includes expressions which would not be displayed right now +++because they refer to automatic variables not currently available. +++@end table +++ +++@cindex display disabled out of scope +++If a display expression refers to local variables, then it does not make +++sense outside the lexical context for which it was set up. Such an +++expression is disabled when execution enters a context where one of its +++variables is not defined. For example, if you give the command +++@code{display last_char} while inside a function with an argument +++@code{last_char}, @value{GDBN} displays this argument while your program +++continues to stop inside that function. When it stops elsewhere---where +++there is no variable @code{last_char}---the display is disabled +++automatically. The next time your program stops where @code{last_char} +++is meaningful, you can enable the display expression once again. +++ +++@node Print Settings +++@section Print Settings +++ +++@cindex format options +++@cindex print settings +++@value{GDBN} provides the following ways to control how arrays, structures, +++and symbols are printed. +++ +++@noindent +++These settings are useful for debugging programs in any language: +++ +++@table @code +++@kindex set print +++@anchor{set print address} +++@item set print address +++@itemx set print address on +++@cindex print/don't print memory addresses +++@value{GDBN} prints memory addresses showing the location of stack +++traces, structure values, pointer values, breakpoints, and so forth, +++even when it also displays the contents of those addresses. The default +++is @code{on}. For example, this is what a stack frame display looks like with +++@code{set print address on}: +++ +++@smallexample +++@group +++(@value{GDBP}) f +++#0 set_quotes (lq=0x34c78 "<<", rq=0x34c88 ">>") +++ at input.c:530 +++530 if (lquote != def_lquote) +++@end group +++@end smallexample +++ +++@item set print address off +++Do not print addresses when displaying their contents. For example, +++this is the same stack frame displayed with @code{set print address off}: +++ +++@smallexample +++@group +++(@value{GDBP}) set print addr off +++(@value{GDBP}) f +++#0 set_quotes (lq="<<", rq=">>") at input.c:530 +++530 if (lquote != def_lquote) +++@end group +++@end smallexample +++ +++You can use @samp{set print address off} to eliminate all machine +++dependent displays from the @value{GDBN} interface. For example, with +++@code{print address off}, you should get the same text for backtraces on +++all machines---whether or not they involve pointer arguments. +++ +++@kindex show print +++@item show print address +++Show whether or not addresses are to be printed. +++@end table +++ +++When @value{GDBN} prints a symbolic address, it normally prints the +++closest earlier symbol plus an offset. If that symbol does not uniquely +++identify the address (for example, it is a name whose scope is a single +++source file), you may need to clarify. One way to do this is with +++@code{info line}, for example @samp{info line *0x4537}. Alternately, +++you can set @value{GDBN} to print the source file and line number when +++it prints a symbolic address: +++ +++@table @code +++@item set print symbol-filename on +++@cindex source file and line of a symbol +++@cindex symbol, source file and line +++Tell @value{GDBN} to print the source file name and line number of a +++symbol in the symbolic form of an address. +++ +++@item set print symbol-filename off +++Do not print source file name and line number of a symbol. This is the +++default. +++ +++@item show print symbol-filename +++Show whether or not @value{GDBN} will print the source file name and +++line number of a symbol in the symbolic form of an address. +++@end table +++ +++Another situation where it is helpful to show symbol filenames and line +++numbers is when disassembling code; @value{GDBN} shows you the line +++number and source file that corresponds to each instruction. +++ +++Also, you may wish to see the symbolic form only if the address being +++printed is reasonably close to the closest earlier symbol: +++ +++@table @code +++@item set print max-symbolic-offset @var{max-offset} +++@itemx set print max-symbolic-offset unlimited +++@cindex maximum value for offset of closest symbol +++Tell @value{GDBN} to only display the symbolic form of an address if the +++offset between the closest earlier symbol and the address is less than +++@var{max-offset}. The default is @code{unlimited}, which tells @value{GDBN} +++to always print the symbolic form of an address if any symbol precedes +++it. Zero is equivalent to @code{unlimited}. +++ +++@item show print max-symbolic-offset +++Ask how large the maximum offset is that @value{GDBN} prints in a +++symbolic address. +++@end table +++ +++@cindex wild pointer, interpreting +++@cindex pointer, finding referent +++If you have a pointer and you are not sure where it points, try +++@samp{set print symbol-filename on}. Then you can determine the name +++and source file location of the variable where it points, using +++@samp{p/a @var{pointer}}. This interprets the address in symbolic form. +++For example, here @value{GDBN} shows that a variable @code{ptt} points +++at another variable @code{t}, defined in @file{hi2.c}: +++ +++@smallexample +++(@value{GDBP}) set print symbol-filename on +++(@value{GDBP}) p/a ptt +++$4 = 0xe008 +++@end smallexample +++ +++@quotation +++@emph{Warning:} For pointers that point to a local variable, @samp{p/a} +++does not show the symbol name and filename of the referent, even with +++the appropriate @code{set print} options turned on. +++@end quotation +++ +++You can also enable @samp{/a}-like formatting all the time using +++@samp{set print symbol on}: +++ +++@anchor{set print symbol} +++@table @code +++@item set print symbol on +++Tell @value{GDBN} to print the symbol corresponding to an address, if +++one exists. +++ +++@item set print symbol off +++Tell @value{GDBN} not to print the symbol corresponding to an +++address. In this mode, @value{GDBN} will still print the symbol +++corresponding to pointers to functions. This is the default. +++ +++@item show print symbol +++Show whether @value{GDBN} will display the symbol corresponding to an +++address. +++@end table +++ +++Other settings control how different kinds of objects are printed: +++ +++@table @code +++@anchor{set print array} +++@item set print array +++@itemx set print array on +++@cindex pretty print arrays +++Pretty print arrays. This format is more convenient to read, +++but uses more space. The default is off. +++ +++@item set print array off +++Return to compressed format for arrays. +++ +++@item show print array +++Show whether compressed or pretty format is selected for displaying +++arrays. +++ +++@cindex print array indexes +++@anchor{set print array-indexes} +++@item set print array-indexes +++@itemx set print array-indexes on +++Print the index of each element when displaying arrays. May be more +++convenient to locate a given element in the array or quickly find the +++index of a given element in that printed array. The default is off. +++ +++@item set print array-indexes off +++Stop printing element indexes when displaying arrays. +++ +++@item show print array-indexes +++Show whether the index of each element is printed when displaying +++arrays. +++ +++@anchor{set print elements} +++@item set print elements @var{number-of-elements} +++@itemx set print elements unlimited +++@cindex number of array elements to print +++@cindex limit on number of printed array elements +++Set a limit on how many elements of an array @value{GDBN} will print. +++If @value{GDBN} is printing a large array, it stops printing after it has +++printed the number of elements set by the @code{set print elements} command. +++This limit also applies to the display of strings. +++When @value{GDBN} starts, this limit is set to 200. +++Setting @var{number-of-elements} to @code{unlimited} or zero means +++that the number of elements to print is unlimited. +++ +++@item show print elements +++Display the number of elements of a large array that @value{GDBN} will print. +++If the number is 0, then the printing is unlimited. +++ +++@anchor{set print frame-arguments} +++@item set print frame-arguments @var{value} +++@kindex set print frame-arguments +++@cindex printing frame argument values +++@cindex print all frame argument values +++@cindex print frame argument values for scalars only +++@cindex do not print frame arguments +++This command allows to control how the values of arguments are printed +++when the debugger prints a frame (@pxref{Frames}). The possible +++values are: +++ +++@table @code +++@item all +++The values of all arguments are printed. +++ +++@item scalars +++Print the value of an argument only if it is a scalar. The value of more +++complex arguments such as arrays, structures, unions, etc, is replaced +++by @code{@dots{}}. This is the default. Here is an example where +++only scalar arguments are shown: +++ +++@smallexample +++#1 0x08048361 in call_me (i=3, s=@dots{}, ss=0xbf8d508c, u=@dots{}, e=green) +++ at frame-args.c:23 +++@end smallexample +++ +++@item none +++None of the argument values are printed. Instead, the value of each argument +++is replaced by @code{@dots{}}. In this case, the example above now becomes: +++ +++@smallexample +++#1 0x08048361 in call_me (i=@dots{}, s=@dots{}, ss=@dots{}, u=@dots{}, e=@dots{}) +++ at frame-args.c:23 +++@end smallexample +++ +++@item presence +++Only the presence of arguments is indicated by @code{@dots{}}. +++The @code{@dots{}} are not printed for function without any arguments. +++None of the argument names and values are printed. +++In this case, the example above now becomes: +++ +++@smallexample +++#1 0x08048361 in call_me (@dots{}) at frame-args.c:23 +++@end smallexample +++ +++@end table +++ +++By default, only scalar arguments are printed. This command can be used +++to configure the debugger to print the value of all arguments, regardless +++of their type. However, it is often advantageous to not print the value +++of more complex parameters. For instance, it reduces the amount of +++information printed in each frame, making the backtrace more readable. +++Also, it improves performance when displaying Ada frames, because +++the computation of large arguments can sometimes be CPU-intensive, +++especially in large applications. Setting @code{print frame-arguments} +++to @code{scalars} (the default), @code{none} or @code{presence} avoids +++this computation, thus speeding up the display of each Ada frame. +++ +++@item show print frame-arguments +++Show how the value of arguments should be displayed when printing a frame. +++ +++@anchor{set print raw-frame-arguments} +++@item set print raw-frame-arguments on +++Print frame arguments in raw, non pretty-printed, form. +++ +++@item set print raw-frame-arguments off +++Print frame arguments in pretty-printed form, if there is a pretty-printer +++for the value (@pxref{Pretty Printing}), +++otherwise print the value in raw form. +++This is the default. +++ +++@item show print raw-frame-arguments +++Show whether to print frame arguments in raw form. +++ +++@anchor{set print entry-values} +++@item set print entry-values @var{value} +++@kindex set print entry-values +++Set printing of frame argument values at function entry. In some cases +++@value{GDBN} can determine the value of function argument which was passed by +++the function caller, even if the value was modified inside the called function +++and therefore is different. With optimized code, the current value could be +++unavailable, but the entry value may still be known. +++ +++The default value is @code{default} (see below for its description). Older +++@value{GDBN} behaved as with the setting @code{no}. Compilers not supporting +++this feature will behave in the @code{default} setting the same way as with the +++@code{no} setting. +++ +++This functionality is currently supported only by DWARF 2 debugging format and +++the compiler has to produce @samp{DW_TAG_call_site} tags. With +++@value{NGCC}, you need to specify @option{-O -g} during compilation, to get +++this information. +++ +++The @var{value} parameter can be one of the following: +++ +++@table @code +++@item no +++Print only actual parameter values, never print values from function entry +++point. +++@smallexample +++#0 equal (val=5) +++#0 different (val=6) +++#0 lost (val=) +++#0 born (val=10) +++#0 invalid (val=) +++@end smallexample +++ +++@item only +++Print only parameter values from function entry point. The actual parameter +++values are never printed. +++@smallexample +++#0 equal (val@@entry=5) +++#0 different (val@@entry=5) +++#0 lost (val@@entry=5) +++#0 born (val@@entry=) +++#0 invalid (val@@entry=) +++@end smallexample +++ +++@item preferred +++Print only parameter values from function entry point. If value from function +++entry point is not known while the actual value is known, print the actual +++value for such parameter. +++@smallexample +++#0 equal (val@@entry=5) +++#0 different (val@@entry=5) +++#0 lost (val@@entry=5) +++#0 born (val=10) +++#0 invalid (val@@entry=) +++@end smallexample +++ +++@item if-needed +++Print actual parameter values. If actual parameter value is not known while +++value from function entry point is known, print the entry point value for such +++parameter. +++@smallexample +++#0 equal (val=5) +++#0 different (val=6) +++#0 lost (val@@entry=5) +++#0 born (val=10) +++#0 invalid (val=) +++@end smallexample +++ +++@item both +++Always print both the actual parameter value and its value from function entry +++point, even if values of one or both are not available due to compiler +++optimizations. +++@smallexample +++#0 equal (val=5, val@@entry=5) +++#0 different (val=6, val@@entry=5) +++#0 lost (val=, val@@entry=5) +++#0 born (val=10, val@@entry=) +++#0 invalid (val=, val@@entry=) +++@end smallexample +++ +++@item compact +++Print the actual parameter value if it is known and also its value from +++function entry point if it is known. If neither is known, print for the actual +++value @code{}. If not in MI mode (@pxref{GDB/MI}) and if both +++values are known and identical, print the shortened +++@code{param=param@@entry=VALUE} notation. +++@smallexample +++#0 equal (val=val@@entry=5) +++#0 different (val=6, val@@entry=5) +++#0 lost (val@@entry=5) +++#0 born (val=10) +++#0 invalid (val=) +++@end smallexample +++ +++@item default +++Always print the actual parameter value. Print also its value from function +++entry point, but only if it is known. If not in MI mode (@pxref{GDB/MI}) and +++if both values are known and identical, print the shortened +++@code{param=param@@entry=VALUE} notation. +++@smallexample +++#0 equal (val=val@@entry=5) +++#0 different (val=6, val@@entry=5) +++#0 lost (val=, val@@entry=5) +++#0 born (val=10) +++#0 invalid (val=) +++@end smallexample +++@end table +++ +++For analysis messages on possible failures of frame argument values at function +++entry resolution see @ref{set debug entry-values}. +++ +++@item show print entry-values +++Show the method being used for printing of frame argument values at function +++entry. +++ +++@anchor{set print frame-info} +++@item set print frame-info @var{value} +++@kindex set print frame-info +++@cindex printing frame information +++@cindex frame information, printing +++This command allows to control the information printed when +++the debugger prints a frame. See @ref{Frames}, @ref{Backtrace}, +++for a general explanation about frames and frame information. +++Note that some other settings (such as @code{set print frame-arguments} +++and @code{set print address}) are also influencing if and how some frame +++information is displayed. In particular, the frame program counter is never +++printed if @code{set print address} is off. +++ +++The possible values for @code{set print frame-info} are: +++@table @code +++@item short-location +++Print the frame level, the program counter (if not at the +++beginning of the location source line), the function, the function +++arguments. +++@item location +++Same as @code{short-location} but also print the source file and source line +++number. +++@item location-and-address +++Same as @code{location} but print the program counter even if located at the +++beginning of the location source line. +++@item source-line +++Print the program counter (if not at the beginning of the location +++source line), the line number and the source line. +++@item source-and-location +++Print what @code{location} and @code{source-line} are printing. +++@item auto +++The information printed for a frame is decided automatically +++by the @value{GDBN} command that prints a frame. +++For example, @code{frame} prints the information printed by +++@code{source-and-location} while @code{stepi} will switch between +++@code{source-line} and @code{source-and-location} depending on the program +++counter. +++The default value is @code{auto}. +++@end table +++ +++@anchor{set print repeats} +++@item set print repeats @var{number-of-repeats} +++@itemx set print repeats unlimited +++@cindex repeated array elements +++Set the threshold for suppressing display of repeated array +++elements. When the number of consecutive identical elements of an +++array exceeds the threshold, @value{GDBN} prints the string +++@code{""}, where @var{n} is the number of +++identical repetitions, instead of displaying the identical elements +++themselves. Setting the threshold to @code{unlimited} or zero will +++cause all elements to be individually printed. The default threshold +++is 10. +++ +++@item show print repeats +++Display the current threshold for printing repeated identical +++elements. +++ +++@anchor{set print max-depth} +++@item set print max-depth @var{depth} +++@item set print max-depth unlimited +++@cindex printing nested structures +++Set the threshold after which nested structures are replaced with +++ellipsis, this can make visualising deeply nested structures easier. +++ +++For example, given this C code +++ +++@smallexample +++typedef struct s1 @{ int a; @} s1; +++typedef struct s2 @{ s1 b; @} s2; +++typedef struct s3 @{ s2 c; @} s3; +++typedef struct s4 @{ s3 d; @} s4; +++ +++s4 var = @{ @{ @{ @{ 3 @} @} @} @}; +++@end smallexample +++ +++The following table shows how different values of @var{depth} will +++effect how @code{var} is printed by @value{GDBN}: +++ +++@multitable @columnfractions .3 .7 +++@headitem @var{depth} setting @tab Result of @samp{p var} +++@item unlimited +++@tab @code{$1 = @{d = @{c = @{b = @{a = 3@}@}@}@}} +++@item @code{0} +++@tab @code{$1 = @{...@}} +++@item @code{1} +++@tab @code{$1 = @{d = @{...@}@}} +++@item @code{2} +++@tab @code{$1 = @{d = @{c = @{...@}@}@}} +++@item @code{3} +++@tab @code{$1 = @{d = @{c = @{b = @{...@}@}@}@}} +++@item @code{4} +++@tab @code{$1 = @{d = @{c = @{b = @{a = 3@}@}@}@}} +++@end multitable +++ +++To see the contents of structures that have been hidden the user can +++either increase the print max-depth, or they can print the elements of +++the structure that are visible, for example +++ +++@smallexample +++(gdb) set print max-depth 2 +++(gdb) p var +++$1 = @{d = @{c = @{...@}@}@} +++(gdb) p var.d +++$2 = @{c = @{b = @{...@}@}@} +++(gdb) p var.d.c +++$3 = @{b = @{a = 3@}@} +++@end smallexample +++ +++The pattern used to replace nested structures varies based on +++language, for most languages @code{@{...@}} is used, but Fortran uses +++@code{(...)}. +++ +++@item show print max-depth +++Display the current threshold after which nested structures are +++replaces with ellipsis. +++ +++@anchor{set print null-stop} +++@item set print null-stop +++@cindex @sc{null} elements in arrays +++Cause @value{GDBN} to stop printing the characters of an array when the first +++@sc{null} is encountered. This is useful when large arrays actually +++contain only short strings. +++The default is off. +++ +++@item show print null-stop +++Show whether @value{GDBN} stops printing an array on the first +++@sc{null} character. +++ +++@anchor{set print pretty} +++@item set print pretty on +++@cindex print structures in indented form +++@cindex indentation in structure display +++Cause @value{GDBN} to print structures in an indented format with one member +++per line, like this: +++ +++@smallexample +++@group +++$1 = @{ +++ next = 0x0, +++ flags = @{ +++ sweet = 1, +++ sour = 1 +++ @}, +++ meat = 0x54 "Pork" +++@} +++@end group +++@end smallexample +++ +++@item set print pretty off +++Cause @value{GDBN} to print structures in a compact format, like this: +++ +++@smallexample +++@group +++$1 = @{next = 0x0, flags = @{sweet = 1, sour = 1@}, \ +++meat = 0x54 "Pork"@} +++@end group +++@end smallexample +++ +++@noindent +++This is the default format. +++ +++@item show print pretty +++Show which format @value{GDBN} is using to print structures. +++ +++@anchor{set print raw-values} +++@item set print raw-values on +++Print values in raw form, without applying the pretty +++printers for the value. +++ +++@item set print raw-values off +++Print values in pretty-printed form, if there is a pretty-printer +++for the value (@pxref{Pretty Printing}), +++otherwise print the value in raw form. +++ +++The default setting is ``off''. +++ +++@item show print raw-values +++Show whether to print values in raw form. +++ +++@item set print sevenbit-strings on +++@cindex eight-bit characters in strings +++@cindex octal escapes in strings +++Print using only seven-bit characters; if this option is set, +++@value{GDBN} displays any eight-bit characters (in strings or +++character values) using the notation @code{\}@var{nnn}. This setting is +++best if you are working in English (@sc{ascii}) and you use the +++high-order bit of characters as a marker or ``meta'' bit. +++ +++@item set print sevenbit-strings off +++Print full eight-bit characters. This allows the use of more +++international character sets, and is the default. +++ +++@item show print sevenbit-strings +++Show whether or not @value{GDBN} is printing only seven-bit characters. +++ +++@anchor{set print union} +++@item set print union on +++@cindex unions in structures, printing +++Tell @value{GDBN} to print unions which are contained in structures +++and other unions. This is the default setting. +++ +++@item set print union off +++Tell @value{GDBN} not to print unions which are contained in +++structures and other unions. @value{GDBN} will print @code{"@{...@}"} +++instead. +++ +++@item show print union +++Ask @value{GDBN} whether or not it will print unions which are contained in +++structures and other unions. +++ +++For example, given the declarations +++ +++@smallexample +++typedef enum @{Tree, Bug@} Species; +++typedef enum @{Big_tree, Acorn, Seedling@} Tree_forms; +++typedef enum @{Caterpillar, Cocoon, Butterfly@} +++ Bug_forms; +++ +++struct thing @{ +++ Species it; +++ union @{ +++ Tree_forms tree; +++ Bug_forms bug; +++ @} form; +++@}; +++ +++struct thing foo = @{Tree, @{Acorn@}@}; +++@end smallexample +++ +++@noindent +++with @code{set print union on} in effect @samp{p foo} would print +++ +++@smallexample +++$1 = @{it = Tree, form = @{tree = Acorn, bug = Cocoon@}@} +++@end smallexample +++ +++@noindent +++and with @code{set print union off} in effect it would print +++ +++@smallexample +++$1 = @{it = Tree, form = @{...@}@} +++@end smallexample +++ +++@noindent +++@code{set print union} affects programs written in C-like languages +++and in Pascal. +++@end table +++ +++@need 1000 +++@noindent +++These settings are of interest when debugging C@t{++} programs: +++ +++@table @code +++@cindex demangling C@t{++} names +++@item set print demangle +++@itemx set print demangle on +++Print C@t{++} names in their source form rather than in the encoded +++(``mangled'') form passed to the assembler and linker for type-safe +++linkage. The default is on. +++ +++@item show print demangle +++Show whether C@t{++} names are printed in mangled or demangled form. +++ +++@item set print asm-demangle +++@itemx set print asm-demangle on +++Print C@t{++} names in their source form rather than their mangled form, even +++in assembler code printouts such as instruction disassemblies. +++The default is off. +++ +++@item show print asm-demangle +++Show whether C@t{++} names in assembly listings are printed in mangled +++or demangled form. +++ +++@cindex C@t{++} symbol decoding style +++@cindex symbol decoding style, C@t{++} +++@kindex set demangle-style +++@item set demangle-style @var{style} +++Choose among several encoding schemes used by different compilers to represent +++C@t{++} names. If you omit @var{style}, you will see a list of possible +++formats. The default value is @var{auto}, which lets @value{GDBN} choose a +++decoding style by inspecting your program. +++ +++@item show demangle-style +++Display the encoding style currently in use for decoding C@t{++} symbols. +++ +++@anchor{set print object} +++@item set print object +++@itemx set print object on +++@cindex derived type of an object, printing +++@cindex display derived types +++When displaying a pointer to an object, identify the @emph{actual} +++(derived) type of the object rather than the @emph{declared} type, using +++the virtual function table. Note that the virtual function table is +++required---this feature can only work for objects that have run-time +++type identification; a single virtual method in the object's declared +++type is sufficient. Note that this setting is also taken into account when +++working with variable objects via MI (@pxref{GDB/MI}). +++ +++@item set print object off +++Display only the declared type of objects, without reference to the +++virtual function table. This is the default setting. +++ +++@item show print object +++Show whether actual, or declared, object types are displayed. +++ +++@anchor{set print static-members} +++@item set print static-members +++@itemx set print static-members on +++@cindex static members of C@t{++} objects +++Print static members when displaying a C@t{++} object. The default is on. +++ +++@item set print static-members off +++Do not print static members when displaying a C@t{++} object. +++ +++@item show print static-members +++Show whether C@t{++} static members are printed or not. +++ +++@item set print pascal_static-members +++@itemx set print pascal_static-members on +++@cindex static members of Pascal objects +++@cindex Pascal objects, static members display +++Print static members when displaying a Pascal object. The default is on. +++ +++@item set print pascal_static-members off +++Do not print static members when displaying a Pascal object. +++ +++@item show print pascal_static-members +++Show whether Pascal static members are printed or not. +++ +++@c These don't work with HP ANSI C++ yet. +++@anchor{set print vtbl} +++@item set print vtbl +++@itemx set print vtbl on +++@cindex pretty print C@t{++} virtual function tables +++@cindex virtual functions (C@t{++}) display +++@cindex VTBL display +++Pretty print C@t{++} virtual function tables. The default is off. +++(The @code{vtbl} commands do not work on programs compiled with the HP +++ANSI C@t{++} compiler (@code{aCC}).) +++ +++@item set print vtbl off +++Do not pretty print C@t{++} virtual function tables. +++ +++@item show print vtbl +++Show whether C@t{++} virtual function tables are pretty printed, or not. +++@end table +++ +++@node Pretty Printing +++@section Pretty Printing +++ +++@value{GDBN} provides a mechanism to allow pretty-printing of values using +++Python code. It greatly simplifies the display of complex objects. This +++mechanism works for both MI and the CLI. +++ +++@menu +++* Pretty-Printer Introduction:: Introduction to pretty-printers +++* Pretty-Printer Example:: An example pretty-printer +++* Pretty-Printer Commands:: Pretty-printer commands +++@end menu +++ +++@node Pretty-Printer Introduction +++@subsection Pretty-Printer Introduction +++ +++When @value{GDBN} prints a value, it first sees if there is a pretty-printer +++registered for the value. If there is then @value{GDBN} invokes the +++pretty-printer to print the value. Otherwise the value is printed normally. +++ +++Pretty-printers are normally named. This makes them easy to manage. +++The @samp{info pretty-printer} command will list all the installed +++pretty-printers with their names. +++If a pretty-printer can handle multiple data types, then its +++@dfn{subprinters} are the printers for the individual data types. +++Each such subprinter has its own name. +++The format of the name is @var{printer-name};@var{subprinter-name}. +++ +++Pretty-printers are installed by @dfn{registering} them with @value{GDBN}. +++Typically they are automatically loaded and registered when the corresponding +++debug information is loaded, thus making them available without having to +++do anything special. +++ +++There are three places where a pretty-printer can be registered. +++ +++@itemize @bullet +++@item +++Pretty-printers registered globally are available when debugging +++all inferiors. +++ +++@item +++Pretty-printers registered with a program space are available only +++when debugging that program. +++@xref{Progspaces In Python}, for more details on program spaces in Python. +++ +++@item +++Pretty-printers registered with an objfile are loaded and unloaded +++with the corresponding objfile (e.g., shared library). +++@xref{Objfiles In Python}, for more details on objfiles in Python. +++@end itemize +++ +++@xref{Selecting Pretty-Printers}, for further information on how +++pretty-printers are selected, +++ +++@xref{Writing a Pretty-Printer}, for implementing pretty printers +++for new types. +++ +++@node Pretty-Printer Example +++@subsection Pretty-Printer Example +++ +++Here is how a C@t{++} @code{std::string} looks without a pretty-printer: +++ +++@smallexample +++(@value{GDBP}) print s +++$1 = @{ +++ static npos = 4294967295, +++ _M_dataplus = @{ +++ > = @{ +++ <__gnu_cxx::new_allocator> = @{ +++ @}, +++ @}, +++ members of std::basic_string, +++ std::allocator >::_Alloc_hider: +++ _M_p = 0x804a014 "abcd" +++ @} +++@} +++@end smallexample +++ +++With a pretty-printer for @code{std::string} only the contents are printed: +++ +++@smallexample +++(@value{GDBP}) print s +++$2 = "abcd" +++@end smallexample +++ +++@node Pretty-Printer Commands +++@subsection Pretty-Printer Commands +++@cindex pretty-printer commands +++ +++@table @code +++@kindex info pretty-printer +++@item info pretty-printer [@var{object-regexp} [@var{name-regexp}]] +++Print the list of installed pretty-printers. +++This includes disabled pretty-printers, which are marked as such. +++ +++@var{object-regexp} is a regular expression matching the objects +++whose pretty-printers to list. +++Objects can be @code{global}, the program space's file +++(@pxref{Progspaces In Python}), +++and the object files within that program space (@pxref{Objfiles In Python}). +++@xref{Selecting Pretty-Printers}, for details on how @value{GDBN} +++looks up a printer from these three objects. +++ +++@var{name-regexp} is a regular expression matching the name of the printers +++to list. +++ +++@kindex disable pretty-printer +++@item disable pretty-printer [@var{object-regexp} [@var{name-regexp}]] +++Disable pretty-printers matching @var{object-regexp} and @var{name-regexp}. +++A disabled pretty-printer is not forgotten, it may be enabled again later. +++ +++@kindex enable pretty-printer +++@item enable pretty-printer [@var{object-regexp} [@var{name-regexp}]] +++Enable pretty-printers matching @var{object-regexp} and @var{name-regexp}. +++@end table +++ +++Example: +++ +++Suppose we have three pretty-printers installed: one from library1.so +++named @code{foo} that prints objects of type @code{foo}, and +++another from library2.so named @code{bar} that prints two types of objects, +++@code{bar1} and @code{bar2}. +++ +++@smallexample +++(gdb) info pretty-printer +++library1.so: +++ foo +++library2.so: +++ bar +++ bar1 +++ bar2 +++(gdb) info pretty-printer library2 +++library2.so: +++ bar +++ bar1 +++ bar2 +++(gdb) disable pretty-printer library1 +++1 printer disabled +++2 of 3 printers enabled +++(gdb) info pretty-printer +++library1.so: +++ foo [disabled] +++library2.so: +++ bar +++ bar1 +++ bar2 +++(gdb) disable pretty-printer library2 bar;bar1 +++1 printer disabled +++1 of 3 printers enabled +++(gdb) info pretty-printer library2 +++library1.so: +++ foo [disabled] +++library2.so: +++ bar +++ bar1 [disabled] +++ bar2 +++(gdb) disable pretty-printer library2 bar +++1 printer disabled +++0 of 3 printers enabled +++(gdb) info pretty-printer library2 +++library1.so: +++ foo [disabled] +++library2.so: +++ bar [disabled] +++ bar1 [disabled] +++ bar2 +++@end smallexample +++ +++Note that for @code{bar} the entire printer can be disabled, +++as can each individual subprinter. +++ +++Printing values and frame arguments is done by default using +++the enabled pretty printers. +++ +++The print option @code{-raw-values} and @value{GDBN} setting +++@code{set print raw-values} (@pxref{set print raw-values}) can be +++used to print values without applying the enabled pretty printers. +++ +++Similarly, the backtrace option @code{-raw-frame-arguments} and +++@value{GDBN} setting @code{set print raw-frame-arguments} +++(@pxref{set print raw-frame-arguments}) can be used to ignore the +++enabled pretty printers when printing frame argument values. +++ +++@node Value History +++@section Value History +++ +++@cindex value history +++@cindex history of values printed by @value{GDBN} +++Values printed by the @code{print} command are saved in the @value{GDBN} +++@dfn{value history}. This allows you to refer to them in other expressions. +++Values are kept until the symbol table is re-read or discarded +++(for example with the @code{file} or @code{symbol-file} commands). +++When the symbol table changes, the value history is discarded, +++since the values may contain pointers back to the types defined in the +++symbol table. +++ +++@cindex @code{$} +++@cindex @code{$$} +++@cindex history number +++The values printed are given @dfn{history numbers} by which you can +++refer to them. These are successive integers starting with one. +++@code{print} shows you the history number assigned to a value by +++printing @samp{$@var{num} = } before the value; here @var{num} is the +++history number. +++ +++To refer to any previous value, use @samp{$} followed by the value's +++history number. The way @code{print} labels its output is designed to +++remind you of this. Just @code{$} refers to the most recent value in +++the history, and @code{$$} refers to the value before that. +++@code{$$@var{n}} refers to the @var{n}th value from the end; @code{$$2} +++is the value just prior to @code{$$}, @code{$$1} is equivalent to +++@code{$$}, and @code{$$0} is equivalent to @code{$}. +++ +++For example, suppose you have just printed a pointer to a structure and +++want to see the contents of the structure. It suffices to type +++ +++@smallexample +++p *$ +++@end smallexample +++ +++If you have a chain of structures where the component @code{next} points +++to the next one, you can print the contents of the next one with this: +++ +++@smallexample +++p *$.next +++@end smallexample +++ +++@noindent +++You can print successive links in the chain by repeating this +++command---which you can do by just typing @key{RET}. +++ +++Note that the history records values, not expressions. If the value of +++@code{x} is 4 and you type these commands: +++ +++@smallexample +++print x +++set x=5 +++@end smallexample +++ +++@noindent +++then the value recorded in the value history by the @code{print} command +++remains 4 even though the value of @code{x} has changed. +++ +++@table @code +++@kindex show values +++@item show values +++Print the last ten values in the value history, with their item numbers. +++This is like @samp{p@ $$9} repeated ten times, except that @code{show +++values} does not change the history. +++ +++@item show values @var{n} +++Print ten history values centered on history item number @var{n}. +++ +++@item show values + +++Print ten history values just after the values last printed. If no more +++values are available, @code{show values +} produces no display. +++@end table +++ +++Pressing @key{RET} to repeat @code{show values @var{n}} has exactly the +++same effect as @samp{show values +}. +++ +++@node Convenience Vars +++@section Convenience Variables +++ +++@cindex convenience variables +++@cindex user-defined variables +++@value{GDBN} provides @dfn{convenience variables} that you can use within +++@value{GDBN} to hold on to a value and refer to it later. These variables +++exist entirely within @value{GDBN}; they are not part of your program, and +++setting a convenience variable has no direct effect on further execution +++of your program. That is why you can use them freely. +++ +++Convenience variables are prefixed with @samp{$}. Any name preceded by +++@samp{$} can be used for a convenience variable, unless it is one of +++the predefined machine-specific register names (@pxref{Registers, ,Registers}). +++(Value history references, in contrast, are @emph{numbers} preceded +++by @samp{$}. @xref{Value History, ,Value History}.) +++ +++You can save a value in a convenience variable with an assignment +++expression, just as you would set a variable in your program. +++For example: +++ +++@smallexample +++set $foo = *object_ptr +++@end smallexample +++ +++@noindent +++would save in @code{$foo} the value contained in the object pointed to by +++@code{object_ptr}. +++ +++Using a convenience variable for the first time creates it, but its +++value is @code{void} until you assign a new value. You can alter the +++value with another assignment at any time. +++ +++Convenience variables have no fixed types. You can assign a convenience +++variable any type of value, including structures and arrays, even if +++that variable already has a value of a different type. The convenience +++variable, when used as an expression, has the type of its current value. +++ +++@table @code +++@kindex show convenience +++@cindex show all user variables and functions +++@item show convenience +++Print a list of convenience variables used so far, and their values, +++as well as a list of the convenience functions. +++Abbreviated @code{show conv}. +++ +++@kindex init-if-undefined +++@cindex convenience variables, initializing +++@item init-if-undefined $@var{variable} = @var{expression} +++Set a convenience variable if it has not already been set. This is useful +++for user-defined commands that keep some state. It is similar, in concept, +++to using local static variables with initializers in C (except that +++convenience variables are global). It can also be used to allow users to +++override default values used in a command script. +++ +++If the variable is already defined then the expression is not evaluated so +++any side-effects do not occur. +++@end table +++ +++One of the ways to use a convenience variable is as a counter to be +++incremented or a pointer to be advanced. For example, to print +++a field from successive elements of an array of structures: +++ +++@smallexample +++set $i = 0 +++print bar[$i++]->contents +++@end smallexample +++ +++@noindent +++Repeat that command by typing @key{RET}. +++ +++Some convenience variables are created automatically by @value{GDBN} and given +++values likely to be useful. +++ +++@table @code +++@vindex $_@r{, convenience variable} +++@item $_ +++The variable @code{$_} is automatically set by the @code{x} command to +++the last address examined (@pxref{Memory, ,Examining Memory}). Other +++commands which provide a default address for @code{x} to examine also +++set @code{$_} to that address; these commands include @code{info line} +++and @code{info breakpoint}. The type of @code{$_} is @code{void *} +++except when set by the @code{x} command, in which case it is a pointer +++to the type of @code{$__}. +++ +++@vindex $__@r{, convenience variable} +++@item $__ +++The variable @code{$__} is automatically set by the @code{x} command +++to the value found in the last address examined. Its type is chosen +++to match the format in which the data was printed. +++ +++@item $_exitcode +++@vindex $_exitcode@r{, convenience variable} +++When the program being debugged terminates normally, @value{GDBN} +++automatically sets this variable to the exit code of the program, and +++resets @code{$_exitsignal} to @code{void}. +++ +++@item $_exitsignal +++@vindex $_exitsignal@r{, convenience variable} +++When the program being debugged dies due to an uncaught signal, +++@value{GDBN} automatically sets this variable to that signal's number, +++and resets @code{$_exitcode} to @code{void}. +++ +++To distinguish between whether the program being debugged has exited +++(i.e., @code{$_exitcode} is not @code{void}) or signalled (i.e., +++@code{$_exitsignal} is not @code{void}), the convenience function +++@code{$_isvoid} can be used (@pxref{Convenience Funs,, Convenience +++Functions}). For example, considering the following source code: +++ +++@smallexample +++#include +++ +++int +++main (int argc, char *argv[]) +++@{ +++ raise (SIGALRM); +++ return 0; +++@} +++@end smallexample +++ +++A valid way of telling whether the program being debugged has exited +++or signalled would be: +++ +++@smallexample +++(@value{GDBP}) define has_exited_or_signalled +++Type commands for definition of ``has_exited_or_signalled''. +++End with a line saying just ``end''. +++>if $_isvoid ($_exitsignal) +++ >echo The program has exited\n +++ >else +++ >echo The program has signalled\n +++ >end +++>end +++(@value{GDBP}) run +++Starting program: +++ +++Program terminated with signal SIGALRM, Alarm clock. +++The program no longer exists. +++(@value{GDBP}) has_exited_or_signalled +++The program has signalled +++@end smallexample +++ +++As can be seen, @value{GDBN} correctly informs that the program being +++debugged has signalled, since it calls @code{raise} and raises a +++@code{SIGALRM} signal. If the program being debugged had not called +++@code{raise}, then @value{GDBN} would report a normal exit: +++ +++@smallexample +++(@value{GDBP}) has_exited_or_signalled +++The program has exited +++@end smallexample +++ +++@item $_exception +++The variable @code{$_exception} is set to the exception object being +++thrown at an exception-related catchpoint. @xref{Set Catchpoints}. +++ +++@item $_ada_exception +++The variable @code{$_ada_exception} is set to the address of the +++exception being caught or thrown at an Ada exception-related +++catchpoint. @xref{Set Catchpoints}. +++ +++@item $_probe_argc +++@itemx $_probe_arg0@dots{}$_probe_arg11 +++Arguments to a static probe. @xref{Static Probe Points}. +++ +++@item $_sdata +++@vindex $_sdata@r{, inspect, convenience variable} +++The variable @code{$_sdata} contains extra collected static tracepoint +++data. @xref{Tracepoint Actions,,Tracepoint Action Lists}. Note that +++@code{$_sdata} could be empty, if not inspecting a trace buffer, or +++if extra static tracepoint data has not been collected. +++ +++@item $_siginfo +++@vindex $_siginfo@r{, convenience variable} +++The variable @code{$_siginfo} contains extra signal information +++(@pxref{extra signal information}). Note that @code{$_siginfo} +++could be empty, if the application has not yet received any signals. +++For example, it will be empty before you execute the @code{run} command. +++ +++@item $_tlb +++@vindex $_tlb@r{, convenience variable} +++The variable @code{$_tlb} is automatically set when debugging +++applications running on MS-Windows in native mode or connected to +++gdbserver that supports the @code{qGetTIBAddr} request. +++@xref{General Query Packets}. +++This variable contains the address of the thread information block. +++ +++@item $_inferior +++The number of the current inferior. @xref{Inferiors Connections and +++Programs, ,Debugging Multiple Inferiors Connections and Programs}. +++ +++@item $_thread +++The thread number of the current thread. @xref{thread numbers}. +++ +++@item $_gthread +++The global number of the current thread. @xref{global thread numbers}. +++ +++@item $_gdb_major +++@itemx $_gdb_minor +++@vindex $_gdb_major@r{, convenience variable} +++@vindex $_gdb_minor@r{, convenience variable} +++The major and minor version numbers of the running @value{GDBN}. +++Development snapshots and pretest versions have their minor version +++incremented by one; thus, @value{GDBN} pretest 9.11.90 will produce +++the value 12 for @code{$_gdb_minor}. These variables allow you to +++write scripts that work with different versions of @value{GDBN} +++without errors caused by features unavailable in some of those +++versions. +++ +++@item $_shell_exitcode +++@itemx $_shell_exitsignal +++@vindex $_shell_exitcode@r{, convenience variable} +++@vindex $_shell_exitsignal@r{, convenience variable} +++@cindex shell command, exit code +++@cindex shell command, exit signal +++@cindex exit status of shell commands +++@value{GDBN} commands such as @code{shell} and @code{|} are launching +++shell commands. When a launched command terminates, @value{GDBN} +++automatically maintains the variables @code{$_shell_exitcode} +++and @code{$_shell_exitsignal} according to the exit status of the last +++launched command. These variables are set and used similarly to +++the variables @code{$_exitcode} and @code{$_exitsignal}. +++ +++@end table +++ +++@node Convenience Funs +++@section Convenience Functions +++ +++@cindex convenience functions +++@value{GDBN} also supplies some @dfn{convenience functions}. These +++have a syntax similar to convenience variables. A convenience +++function can be used in an expression just like an ordinary function; +++however, a convenience function is implemented internally to +++@value{GDBN}. +++ +++These functions do not require @value{GDBN} to be configured with +++@code{Python} support, which means that they are always available. +++ +++@table @code +++ +++@item $_isvoid (@var{expr}) +++@findex $_isvoid@r{, convenience function} +++Return one if the expression @var{expr} is @code{void}. Otherwise it +++returns zero. +++ +++A @code{void} expression is an expression where the type of the result +++is @code{void}. For example, you can examine a convenience variable +++(see @ref{Convenience Vars,, Convenience Variables}) to check whether +++it is @code{void}: +++ +++@smallexample +++(@value{GDBP}) print $_exitcode +++$1 = void +++(@value{GDBP}) print $_isvoid ($_exitcode) +++$2 = 1 +++(@value{GDBP}) run +++Starting program: ./a.out +++[Inferior 1 (process 29572) exited normally] +++(@value{GDBP}) print $_exitcode +++$3 = 0 +++(@value{GDBP}) print $_isvoid ($_exitcode) +++$4 = 0 +++@end smallexample +++ +++In the example above, we used @code{$_isvoid} to check whether +++@code{$_exitcode} is @code{void} before and after the execution of the +++program being debugged. Before the execution there is no exit code to +++be examined, therefore @code{$_exitcode} is @code{void}. After the +++execution the program being debugged returned zero, therefore +++@code{$_exitcode} is zero, which means that it is not @code{void} +++anymore. +++ +++The @code{void} expression can also be a call of a function from the +++program being debugged. For example, given the following function: +++ +++@smallexample +++void +++foo (void) +++@{ +++@} +++@end smallexample +++ +++The result of calling it inside @value{GDBN} is @code{void}: +++ +++@smallexample +++(@value{GDBP}) print foo () +++$1 = void +++(@value{GDBP}) print $_isvoid (foo ()) +++$2 = 1 +++(@value{GDBP}) set $v = foo () +++(@value{GDBP}) print $v +++$3 = void +++(@value{GDBP}) print $_isvoid ($v) +++$4 = 1 +++@end smallexample +++ +++@item $_gdb_setting_str (@var{setting}) +++@findex $_gdb_setting_str@r{, convenience function} +++Return the value of the @value{GDBN} @var{setting} as a string. +++@var{setting} is any setting that can be used in a @code{set} or +++@code{show} command (@pxref{Controlling GDB}). +++ +++@smallexample +++(@value{GDBP}) show print frame-arguments +++Printing of non-scalar frame arguments is "scalars". +++(@value{GDBP}) p $_gdb_setting_str("print frame-arguments") +++$1 = "scalars" +++(@value{GDBP}) p $_gdb_setting_str("height") +++$2 = "30" +++(@value{GDBP}) +++@end smallexample +++ +++@item $_gdb_setting (@var{setting}) +++@findex $_gdb_setting@r{, convenience function} +++Return the value of the @value{GDBN} @var{setting}. +++The type of the returned value depends on the setting. +++ +++The value type for boolean and auto boolean settings is @code{int}. +++The boolean values @code{off} and @code{on} are converted to +++the integer values @code{0} and @code{1}. The value @code{auto} is +++converted to the value @code{-1}. +++ +++The value type for integer settings is either @code{unsigned int} +++or @code{int}, depending on the setting. +++ +++Some integer settings accept an @code{unlimited} value. +++Depending on the setting, the @code{set} command also accepts +++the value @code{0} or the value @code{@minus{}1} as a synonym for +++@code{unlimited}. +++For example, @code{set height unlimited} is equivalent to +++@code{set height 0}. +++ +++Some other settings that accept the @code{unlimited} value +++use the value @code{0} to literally mean zero. +++For example, @code{set history size 0} indicates to not +++record any @value{GDBN} commands in the command history. +++For such settings, @code{@minus{}1} is the synonym +++for @code{unlimited}. +++ +++See the documentation of the corresponding @code{set} command for +++the numerical value equivalent to @code{unlimited}. +++ +++The @code{$_gdb_setting} function converts the unlimited value +++to a @code{0} or a @code{@minus{}1} value according to what the +++@code{set} command uses. +++ +++@smallexample +++@group +++(@value{GDBP}) p $_gdb_setting_str("height") +++$1 = "30" +++(@value{GDBP}) p $_gdb_setting("height") +++$2 = 30 +++(@value{GDBP}) set height unlimited +++(@value{GDBP}) p $_gdb_setting_str("height") +++$3 = "unlimited" +++(@value{GDBP}) p $_gdb_setting("height") +++$4 = 0 +++@end group +++@group +++(@value{GDBP}) p $_gdb_setting_str("history size") +++$5 = "unlimited" +++(@value{GDBP}) p $_gdb_setting("history size") +++$6 = -1 +++(@value{GDBP}) p $_gdb_setting_str("disassemble-next-line") +++$7 = "auto" +++(@value{GDBP}) p $_gdb_setting("disassemble-next-line") +++$8 = -1 +++(@value{GDBP}) +++@end group +++@end smallexample +++ +++Other setting types (enum, filename, optional filename, string, string noescape) +++are returned as string values. +++ +++ +++@item $_gdb_maint_setting_str (@var{setting}) +++@findex $_gdb_maint_setting_str@r{, convenience function} +++Like the @code{$_gdb_setting_str} function, but works with +++@code{maintenance set} variables. +++ +++@item $_gdb_maint_setting (@var{setting}) +++@findex $_gdb_maint_setting@r{, convenience function} +++Like the @code{$_gdb_setting} function, but works with +++@code{maintenance set} variables. +++ +++@end table +++ +++The following functions require @value{GDBN} to be configured with +++@code{Python} support. +++ +++@table @code +++ +++@item $_memeq(@var{buf1}, @var{buf2}, @var{length}) +++@findex $_memeq@r{, convenience function} +++Returns one if the @var{length} bytes at the addresses given by +++@var{buf1} and @var{buf2} are equal. +++Otherwise it returns zero. +++ +++@item $_regex(@var{str}, @var{regex}) +++@findex $_regex@r{, convenience function} +++Returns one if the string @var{str} matches the regular expression +++@var{regex}. Otherwise it returns zero. +++The syntax of the regular expression is that specified by @code{Python}'s +++regular expression support. +++ +++@item $_streq(@var{str1}, @var{str2}) +++@findex $_streq@r{, convenience function} +++Returns one if the strings @var{str1} and @var{str2} are equal. +++Otherwise it returns zero. +++ +++@item $_strlen(@var{str}) +++@findex $_strlen@r{, convenience function} +++Returns the length of string @var{str}. +++ +++@item $_caller_is(@var{name}@r{[}, @var{number_of_frames}@r{]}) +++@findex $_caller_is@r{, convenience function} +++Returns one if the calling function's name is equal to @var{name}. +++Otherwise it returns zero. +++ +++If the optional argument @var{number_of_frames} is provided, +++it is the number of frames up in the stack to look. +++The default is 1. +++ +++Example: +++ +++@smallexample +++(gdb) backtrace +++#0 bottom_func () +++ at testsuite/gdb.python/py-caller-is.c:21 +++#1 0x00000000004005a0 in middle_func () +++ at testsuite/gdb.python/py-caller-is.c:27 +++#2 0x00000000004005ab in top_func () +++ at testsuite/gdb.python/py-caller-is.c:33 +++#3 0x00000000004005b6 in main () +++ at testsuite/gdb.python/py-caller-is.c:39 +++(gdb) print $_caller_is ("middle_func") +++$1 = 1 +++(gdb) print $_caller_is ("top_func", 2) +++$1 = 1 +++@end smallexample +++ +++@item $_caller_matches(@var{regexp}@r{[}, @var{number_of_frames}@r{]}) +++@findex $_caller_matches@r{, convenience function} +++Returns one if the calling function's name matches the regular expression +++@var{regexp}. Otherwise it returns zero. +++ +++If the optional argument @var{number_of_frames} is provided, +++it is the number of frames up in the stack to look. +++The default is 1. +++ +++@item $_any_caller_is(@var{name}@r{[}, @var{number_of_frames}@r{]}) +++@findex $_any_caller_is@r{, convenience function} +++Returns one if any calling function's name is equal to @var{name}. +++Otherwise it returns zero. +++ +++If the optional argument @var{number_of_frames} is provided, +++it is the number of frames up in the stack to look. +++The default is 1. +++ +++This function differs from @code{$_caller_is} in that this function +++checks all stack frames from the immediate caller to the frame specified +++by @var{number_of_frames}, whereas @code{$_caller_is} only checks the +++frame specified by @var{number_of_frames}. +++ +++@item $_any_caller_matches(@var{regexp}@r{[}, @var{number_of_frames}@r{]}) +++@findex $_any_caller_matches@r{, convenience function} +++Returns one if any calling function's name matches the regular expression +++@var{regexp}. Otherwise it returns zero. +++ +++If the optional argument @var{number_of_frames} is provided, +++it is the number of frames up in the stack to look. +++The default is 1. +++ +++This function differs from @code{$_caller_matches} in that this function +++checks all stack frames from the immediate caller to the frame specified +++by @var{number_of_frames}, whereas @code{$_caller_matches} only checks the +++frame specified by @var{number_of_frames}. +++ +++@item $_as_string(@var{value}) +++@findex $_as_string@r{, convenience function} +++Return the string representation of @var{value}. +++ +++This function is useful to obtain the textual label (enumerator) of an +++enumeration value. For example, assuming the variable @var{node} is of +++an enumerated type: +++ +++@smallexample +++(gdb) printf "Visiting node of type %s\n", $_as_string(node) +++Visiting node of type NODE_INTEGER +++@end smallexample +++ +++@item $_cimag(@var{value}) +++@itemx $_creal(@var{value}) +++@findex $_cimag@r{, convenience function} +++@findex $_creal@r{, convenience function} +++Return the imaginary (@code{$_cimag}) or real (@code{$_creal}) part of +++the complex number @var{value}. +++ +++The type of the imaginary or real part depends on the type of the +++complex number, e.g., using @code{$_cimag} on a @code{float complex} +++will return an imaginary part of type @code{float}. +++ +++@end table +++ +++@value{GDBN} provides the ability to list and get help on +++convenience functions. +++ +++@table @code +++@item help function +++@kindex help function +++@cindex show all convenience functions +++Print a list of all convenience functions. +++@end table +++ +++@node Registers +++@section Registers +++ +++@cindex registers +++You can refer to machine register contents, in expressions, as variables +++with names starting with @samp{$}. The names of registers are different +++for each machine; use @code{info registers} to see the names used on +++your machine. +++ +++@table @code +++@kindex info registers +++@item info registers +++Print the names and values of all registers except floating-point +++and vector registers (in the selected stack frame). +++ +++@kindex info all-registers +++@cindex floating point registers +++@item info all-registers +++Print the names and values of all registers, including floating-point +++and vector registers (in the selected stack frame). +++ +++@anchor{info_registers_reggroup} +++@item info registers @var{reggroup} @dots{} +++Print the name and value of the registers in each of the specified +++@var{reggroup}s. The @var{reggroup} can be any of those returned by +++@code{maint print reggroups} (@pxref{Maintenance Commands}). +++ +++@item info registers @var{regname} @dots{} +++Print the @dfn{relativized} value of each specified register @var{regname}. +++As discussed in detail below, register values are normally relative to +++the selected stack frame. The @var{regname} may be any register name valid on +++the machine you are using, with or without the initial @samp{$}. +++@end table +++ +++@anchor{standard registers} +++@cindex stack pointer register +++@cindex program counter register +++@cindex process status register +++@cindex frame pointer register +++@cindex standard registers +++@value{GDBN} has four ``standard'' register names that are available (in +++expressions) on most machines---whenever they do not conflict with an +++architecture's canonical mnemonics for registers. The register names +++@code{$pc} and @code{$sp} are used for the program counter register and +++the stack pointer. @code{$fp} is used for a register that contains a +++pointer to the current stack frame, and @code{$ps} is used for a +++register that contains the processor status. For example, +++you could print the program counter in hex with +++ +++@smallexample +++p/x $pc +++@end smallexample +++ +++@noindent +++or print the instruction to be executed next with +++ +++@smallexample +++x/i $pc +++@end smallexample +++ +++@noindent +++or add four to the stack pointer@footnote{This is a way of removing +++one word from the stack, on machines where stacks grow downward in +++memory (most machines, nowadays). This assumes that the innermost +++stack frame is selected; setting @code{$sp} is not allowed when other +++stack frames are selected. To pop entire frames off the stack, +++regardless of machine architecture, use @code{return}; +++see @ref{Returning, ,Returning from a Function}.} with +++ +++@smallexample +++set $sp += 4 +++@end smallexample +++ +++Whenever possible, these four standard register names are available on +++your machine even though the machine has different canonical mnemonics, +++so long as there is no conflict. The @code{info registers} command +++shows the canonical names. For example, on the SPARC, @code{info +++registers} displays the processor status register as @code{$psr} but you +++can also refer to it as @code{$ps}; and on x86-based machines @code{$ps} +++is an alias for the @sc{eflags} register. +++ +++@value{GDBN} always considers the contents of an ordinary register as an +++integer when the register is examined in this way. Some machines have +++special registers which can hold nothing but floating point; these +++registers are considered to have floating point values. There is no way +++to refer to the contents of an ordinary register as floating point value +++(although you can @emph{print} it as a floating point value with +++@samp{print/f $@var{regname}}). +++ +++Some registers have distinct ``raw'' and ``virtual'' data formats. This +++means that the data format in which the register contents are saved by +++the operating system is not the same one that your program normally +++sees. For example, the registers of the 68881 floating point +++coprocessor are always saved in ``extended'' (raw) format, but all C +++programs expect to work with ``double'' (virtual) format. In such +++cases, @value{GDBN} normally works with the virtual format only (the format +++that makes sense for your program), but the @code{info registers} command +++prints the data in both formats. +++ +++@cindex SSE registers (x86) +++@cindex MMX registers (x86) +++Some machines have special registers whose contents can be interpreted +++in several different ways. For example, modern x86-based machines +++have SSE and MMX registers that can hold several values packed +++together in several different formats. @value{GDBN} refers to such +++registers in @code{struct} notation: +++ +++@smallexample +++(@value{GDBP}) print $xmm1 +++$1 = @{ +++ v4_float = @{0, 3.43859137e-038, 1.54142831e-044, 1.821688e-044@}, +++ v2_double = @{9.92129282474342e-303, 2.7585945287983262e-313@}, +++ v16_int8 = "\000\000\000\000\3706;\001\v\000\000\000\r\000\000", +++ v8_int16 = @{0, 0, 14072, 315, 11, 0, 13, 0@}, +++ v4_int32 = @{0, 20657912, 11, 13@}, +++ v2_int64 = @{88725056443645952, 55834574859@}, +++ uint128 = 0x0000000d0000000b013b36f800000000 +++@} +++@end smallexample +++ +++@noindent +++To set values of such registers, you need to tell @value{GDBN} which +++view of the register you wish to change, as if you were assigning +++value to a @code{struct} member: +++ +++@smallexample +++ (@value{GDBP}) set $xmm1.uint128 = 0x000000000000000000000000FFFFFFFF +++@end smallexample +++ +++Normally, register values are relative to the selected stack frame +++(@pxref{Selection, ,Selecting a Frame}). This means that you get the +++value that the register would contain if all stack frames farther in +++were exited and their saved registers restored. In order to see the +++true contents of hardware registers, you must select the innermost +++frame (with @samp{frame 0}). +++ +++@cindex caller-saved registers +++@cindex call-clobbered registers +++@cindex volatile registers +++@cindex values +++Usually ABIs reserve some registers as not needed to be saved by the +++callee (a.k.a.: ``caller-saved'', ``call-clobbered'' or ``volatile'' +++registers). It may therefore not be possible for @value{GDBN} to know +++the value a register had before the call (in other words, in the outer +++frame), if the register value has since been changed by the callee. +++@value{GDBN} tries to deduce where the inner frame saved +++(``callee-saved'') registers, from the debug info, unwind info, or the +++machine code generated by your compiler. If some register is not +++saved, and @value{GDBN} knows the register is ``caller-saved'' (via +++its own knowledge of the ABI, or because the debug/unwind info +++explicitly says the register's value is undefined), @value{GDBN} +++displays @w{@samp{}} as the register's value. With targets +++that @value{GDBN} has no knowledge of the register saving convention, +++if a register was not saved by the callee, then its value and location +++in the outer frame are assumed to be the same of the inner frame. +++This is usually harmless, because if the register is call-clobbered, +++the caller either does not care what is in the register after the +++call, or has code to restore the value that it does care about. Note, +++however, that if you change such a register in the outer frame, you +++may also be affecting the inner frame. Also, the more ``outer'' the +++frame is you're looking at, the more likely a call-clobbered +++register's value is to be wrong, in the sense that it doesn't actually +++represent the value the register had just before the call. +++ +++@node Floating Point Hardware +++@section Floating Point Hardware +++@cindex floating point +++ +++Depending on the configuration, @value{GDBN} may be able to give +++you more information about the status of the floating point hardware. +++ +++@table @code +++@kindex info float +++@item info float +++Display hardware-dependent information about the floating +++point unit. The exact contents and layout vary depending on the +++floating point chip. Currently, @samp{info float} is supported on +++the ARM and x86 machines. +++@end table +++ +++@node Vector Unit +++@section Vector Unit +++@cindex vector unit +++ +++Depending on the configuration, @value{GDBN} may be able to give you +++more information about the status of the vector unit. +++ +++@table @code +++@kindex info vector +++@item info vector +++Display information about the vector unit. The exact contents and +++layout vary depending on the hardware. +++@end table +++ +++@node OS Information +++@section Operating System Auxiliary Information +++@cindex OS information +++ +++@value{GDBN} provides interfaces to useful OS facilities that can help +++you debug your program. +++ +++@cindex auxiliary vector +++@cindex vector, auxiliary +++Some operating systems supply an @dfn{auxiliary vector} to programs at +++startup. This is akin to the arguments and environment that you +++specify for a program, but contains a system-dependent variety of +++binary values that tell system libraries important details about the +++hardware, operating system, and process. Each value's purpose is +++identified by an integer tag; the meanings are well-known but system-specific. +++Depending on the configuration and operating system facilities, +++@value{GDBN} may be able to show you this information. For remote +++targets, this functionality may further depend on the remote stub's +++support of the @samp{qXfer:auxv:read} packet, see +++@ref{qXfer auxiliary vector read}. +++ +++@table @code +++@kindex info auxv +++@item info auxv +++Display the auxiliary vector of the inferior, which can be either a +++live process or a core dump file. @value{GDBN} prints each tag value +++numerically, and also shows names and text descriptions for recognized +++tags. Some values in the vector are numbers, some bit masks, and some +++pointers to strings or other data. @value{GDBN} displays each value in the +++most appropriate form for a recognized tag, and in hexadecimal for +++an unrecognized tag. +++@end table +++ +++On some targets, @value{GDBN} can access operating system-specific +++information and show it to you. The types of information available +++will differ depending on the type of operating system running on the +++target. The mechanism used to fetch the data is described in +++@ref{Operating System Information}. For remote targets, this +++functionality depends on the remote stub's support of the +++@samp{qXfer:osdata:read} packet, see @ref{qXfer osdata read}. +++ +++@table @code +++@kindex info os +++@item info os @var{infotype} +++ +++Display OS information of the requested type. +++ +++On @sc{gnu}/Linux, the following values of @var{infotype} are valid: +++ +++@anchor{linux info os infotypes} +++@table @code +++@kindex info os cpus +++@item cpus +++Display the list of all CPUs/cores. For each CPU/core, @value{GDBN} prints +++the available fields from /proc/cpuinfo. For each supported architecture +++different fields are available. Two common entries are processor which gives +++CPU number and bogomips; a system constant that is calculated during +++kernel initialization. +++ +++@kindex info os files +++@item files +++Display the list of open file descriptors on the target. For each +++file descriptor, @value{GDBN} prints the identifier of the process +++owning the descriptor, the command of the owning process, the value +++of the descriptor, and the target of the descriptor. +++ +++@kindex info os modules +++@item modules +++Display the list of all loaded kernel modules on the target. For each +++module, @value{GDBN} prints the module name, the size of the module in +++bytes, the number of times the module is used, the dependencies of the +++module, the status of the module, and the address of the loaded module +++in memory. +++ +++@kindex info os msg +++@item msg +++Display the list of all System V message queues on the target. For each +++message queue, @value{GDBN} prints the message queue key, the message +++queue identifier, the access permissions, the current number of bytes +++on the queue, the current number of messages on the queue, the processes +++that last sent and received a message on the queue, the user and group +++of the owner and creator of the message queue, the times at which a +++message was last sent and received on the queue, and the time at which +++the message queue was last changed. +++ +++@kindex info os processes +++@item processes +++Display the list of processes on the target. For each process, +++@value{GDBN} prints the process identifier, the name of the user, the +++command corresponding to the process, and the list of processor cores +++that the process is currently running on. (To understand what these +++properties mean, for this and the following info types, please consult +++the general @sc{gnu}/Linux documentation.) +++ +++@kindex info os procgroups +++@item procgroups +++Display the list of process groups on the target. For each process, +++@value{GDBN} prints the identifier of the process group that it belongs +++to, the command corresponding to the process group leader, the process +++identifier, and the command line of the process. The list is sorted +++first by the process group identifier, then by the process identifier, +++so that processes belonging to the same process group are grouped together +++and the process group leader is listed first. +++ +++@kindex info os semaphores +++@item semaphores +++Display the list of all System V semaphore sets on the target. For each +++semaphore set, @value{GDBN} prints the semaphore set key, the semaphore +++set identifier, the access permissions, the number of semaphores in the +++set, the user and group of the owner and creator of the semaphore set, +++and the times at which the semaphore set was operated upon and changed. +++ +++@kindex info os shm +++@item shm +++Display the list of all System V shared-memory regions on the target. +++For each shared-memory region, @value{GDBN} prints the region key, +++the shared-memory identifier, the access permissions, the size of the +++region, the process that created the region, the process that last +++attached to or detached from the region, the current number of live +++attaches to the region, and the times at which the region was last +++attached to, detach from, and changed. +++ +++@kindex info os sockets +++@item sockets +++Display the list of Internet-domain sockets on the target. For each +++socket, @value{GDBN} prints the address and port of the local and +++remote endpoints, the current state of the connection, the creator of +++the socket, the IP address family of the socket, and the type of the +++connection. +++ +++@kindex info os threads +++@item threads +++Display the list of threads running on the target. For each thread, +++@value{GDBN} prints the identifier of the process that the thread +++belongs to, the command of the process, the thread identifier, and the +++processor core that it is currently running on. The main thread of a +++process is not listed. +++@end table +++ +++@item info os +++If @var{infotype} is omitted, then list the possible values for +++@var{infotype} and the kind of OS information available for each +++@var{infotype}. If the target does not return a list of possible +++types, this command will report an error. +++@end table +++ +++@node Memory Region Attributes +++@section Memory Region Attributes +++@cindex memory region attributes +++ +++@dfn{Memory region attributes} allow you to describe special handling +++required by regions of your target's memory. @value{GDBN} uses +++attributes to determine whether to allow certain types of memory +++accesses; whether to use specific width accesses; and whether to cache +++target memory. By default the description of memory regions is +++fetched from the target (if the current target supports this), but the +++user can override the fetched regions. +++ +++Defined memory regions can be individually enabled and disabled. When a +++memory region is disabled, @value{GDBN} uses the default attributes when +++accessing memory in that region. Similarly, if no memory regions have +++been defined, @value{GDBN} uses the default attributes when accessing +++all memory. +++ +++When a memory region is defined, it is given a number to identify it; +++to enable, disable, or remove a memory region, you specify that number. +++ +++@table @code +++@kindex mem +++@item mem @var{lower} @var{upper} @var{attributes}@dots{} +++Define a memory region bounded by @var{lower} and @var{upper} with +++attributes @var{attributes}@dots{}, and add it to the list of regions +++monitored by @value{GDBN}. Note that @var{upper} == 0 is a special +++case: it is treated as the target's maximum memory address. +++(0xffff on 16 bit targets, 0xffffffff on 32 bit targets, etc.) +++ +++@item mem auto +++Discard any user changes to the memory regions and use target-supplied +++regions, if available, or no regions if the target does not support. +++ +++@kindex delete mem +++@item delete mem @var{nums}@dots{} +++Remove memory regions @var{nums}@dots{} from the list of regions +++monitored by @value{GDBN}. +++ +++@kindex disable mem +++@item disable mem @var{nums}@dots{} +++Disable monitoring of memory regions @var{nums}@dots{}. +++A disabled memory region is not forgotten. +++It may be enabled again later. +++ +++@kindex enable mem +++@item enable mem @var{nums}@dots{} +++Enable monitoring of memory regions @var{nums}@dots{}. +++ +++@kindex info mem +++@item info mem +++Print a table of all defined memory regions, with the following columns +++for each region: +++ +++@table @emph +++@item Memory Region Number +++@item Enabled or Disabled. +++Enabled memory regions are marked with @samp{y}. +++Disabled memory regions are marked with @samp{n}. +++ +++@item Lo Address +++The address defining the inclusive lower bound of the memory region. +++ +++@item Hi Address +++The address defining the exclusive upper bound of the memory region. +++ +++@item Attributes +++The list of attributes set for this memory region. +++@end table +++@end table +++ +++ +++@subsection Attributes +++ +++@subsubsection Memory Access Mode +++The access mode attributes set whether @value{GDBN} may make read or +++write accesses to a memory region. +++ +++While these attributes prevent @value{GDBN} from performing invalid +++memory accesses, they do nothing to prevent the target system, I/O DMA, +++etc.@: from accessing memory. +++ +++@table @code +++@item ro +++Memory is read only. +++@item wo +++Memory is write only. +++@item rw +++Memory is read/write. This is the default. +++@end table +++ +++@subsubsection Memory Access Size +++The access size attribute tells @value{GDBN} to use specific sized +++accesses in the memory region. Often memory mapped device registers +++require specific sized accesses. If no access size attribute is +++specified, @value{GDBN} may use accesses of any size. +++ +++@table @code +++@item 8 +++Use 8 bit memory accesses. +++@item 16 +++Use 16 bit memory accesses. +++@item 32 +++Use 32 bit memory accesses. +++@item 64 +++Use 64 bit memory accesses. +++@end table +++ +++@c @subsubsection Hardware/Software Breakpoints +++@c The hardware/software breakpoint attributes set whether @value{GDBN} +++@c will use hardware or software breakpoints for the internal breakpoints +++@c used by the step, next, finish, until, etc. commands. +++@c +++@c @table @code +++@c @item hwbreak +++@c Always use hardware breakpoints +++@c @item swbreak (default) +++@c @end table +++ +++@subsubsection Data Cache +++The data cache attributes set whether @value{GDBN} will cache target +++memory. While this generally improves performance by reducing debug +++protocol overhead, it can lead to incorrect results because @value{GDBN} +++does not know about volatile variables or memory mapped device +++registers. +++ +++@table @code +++@item cache +++Enable @value{GDBN} to cache target memory. +++@item nocache +++Disable @value{GDBN} from caching target memory. This is the default. +++@end table +++ +++@subsection Memory Access Checking +++@value{GDBN} can be instructed to refuse accesses to memory that is +++not explicitly described. This can be useful if accessing such +++regions has undesired effects for a specific target, or to provide +++better error checking. The following commands control this behaviour. +++ +++@table @code +++@kindex set mem inaccessible-by-default +++@item set mem inaccessible-by-default [on|off] +++If @code{on} is specified, make @value{GDBN} treat memory not +++explicitly described by the memory ranges as non-existent and refuse accesses +++to such memory. The checks are only performed if there's at least one +++memory range defined. If @code{off} is specified, make @value{GDBN} +++treat the memory not explicitly described by the memory ranges as RAM. +++The default value is @code{on}. +++@kindex show mem inaccessible-by-default +++@item show mem inaccessible-by-default +++Show the current handling of accesses to unknown memory. +++@end table +++ +++ +++@c @subsubsection Memory Write Verification +++@c The memory write verification attributes set whether @value{GDBN} +++@c will re-reads data after each write to verify the write was successful. +++@c +++@c @table @code +++@c @item verify +++@c @item noverify (default) +++@c @end table +++ +++@node Dump/Restore Files +++@section Copy Between Memory and a File +++@cindex dump/restore files +++@cindex append data to a file +++@cindex dump data to a file +++@cindex restore data from a file +++ +++You can use the commands @code{dump}, @code{append}, and +++@code{restore} to copy data between target memory and a file. The +++@code{dump} and @code{append} commands write data to a file, and the +++@code{restore} command reads data from a file back into the inferior's +++memory. Files may be in binary, Motorola S-record, Intel hex, +++Tektronix Hex, or Verilog Hex format; however, @value{GDBN} can only +++append to binary files, and cannot read from Verilog Hex files. +++ +++@table @code +++ +++@kindex dump +++@item dump @r{[}@var{format}@r{]} memory @var{filename} @var{start_addr} @var{end_addr} +++@itemx dump @r{[}@var{format}@r{]} value @var{filename} @var{expr} +++Dump the contents of memory from @var{start_addr} to @var{end_addr}, +++or the value of @var{expr}, to @var{filename} in the given format. +++ +++The @var{format} parameter may be any one of: +++@table @code +++@item binary +++Raw binary form. +++@item ihex +++Intel hex format. +++@item srec +++Motorola S-record format. +++@item tekhex +++Tektronix Hex format. +++@item verilog +++Verilog Hex format. +++@end table +++ +++@value{GDBN} uses the same definitions of these formats as the +++@sc{gnu} binary utilities, like @samp{objdump} and @samp{objcopy}. If +++@var{format} is omitted, @value{GDBN} dumps the data in raw binary +++form. +++ +++@kindex append +++@item append @r{[}binary@r{]} memory @var{filename} @var{start_addr} @var{end_addr} +++@itemx append @r{[}binary@r{]} value @var{filename} @var{expr} +++Append the contents of memory from @var{start_addr} to @var{end_addr}, +++or the value of @var{expr}, to the file @var{filename}, in raw binary form. +++(@value{GDBN} can only append data to files in raw binary form.) +++ +++@kindex restore +++@item restore @var{filename} @r{[}binary@r{]} @var{bias} @var{start} @var{end} +++Restore the contents of file @var{filename} into memory. The +++@code{restore} command can automatically recognize any known @sc{bfd} +++file format, except for raw binary. To restore a raw binary file you +++must specify the optional keyword @code{binary} after the filename. +++ +++If @var{bias} is non-zero, its value will be added to the addresses +++contained in the file. Binary files always start at address zero, so +++they will be restored at address @var{bias}. Other bfd files have +++a built-in location; they will be restored at offset @var{bias} +++from that location. +++ +++If @var{start} and/or @var{end} are non-zero, then only data between +++file offset @var{start} and file offset @var{end} will be restored. +++These offsets are relative to the addresses in the file, before +++the @var{bias} argument is applied. +++ +++@end table +++ +++@node Core File Generation +++@section How to Produce a Core File from Your Program +++@cindex dump core from inferior +++ +++A @dfn{core file} or @dfn{core dump} is a file that records the memory +++image of a running process and its process status (register values +++etc.). Its primary use is post-mortem debugging of a program that +++crashed while it ran outside a debugger. A program that crashes +++automatically produces a core file, unless this feature is disabled by +++the user. @xref{Files}, for information on invoking @value{GDBN} in +++the post-mortem debugging mode. +++ +++Occasionally, you may wish to produce a core file of the program you +++are debugging in order to preserve a snapshot of its state. +++@value{GDBN} has a special command for that. +++ +++@table @code +++@kindex gcore +++@kindex generate-core-file +++@item generate-core-file [@var{file}] +++@itemx gcore [@var{file}] +++Produce a core dump of the inferior process. The optional argument +++@var{file} specifies the file name where to put the core dump. If not +++specified, the file name defaults to @file{core.@var{pid}}, where +++@var{pid} is the inferior process ID. +++ +++Note that this command is implemented only for some systems (as of +++this writing, @sc{gnu}/Linux, FreeBSD, Solaris, and S390). +++ +++On @sc{gnu}/Linux, this command can take into account the value of the +++file @file{/proc/@var{pid}/coredump_filter} when generating the core +++dump (@pxref{set use-coredump-filter}), and by default honors the +++@code{VM_DONTDUMP} flag for mappings where it is present in the file +++@file{/proc/@var{pid}/smaps} (@pxref{set dump-excluded-mappings}). +++ +++@kindex set use-coredump-filter +++@anchor{set use-coredump-filter} +++@item set use-coredump-filter on +++@itemx set use-coredump-filter off +++Enable or disable the use of the file +++@file{/proc/@var{pid}/coredump_filter} when generating core dump +++files. This file is used by the Linux kernel to decide what types of +++memory mappings will be dumped or ignored when generating a core dump +++file. @var{pid} is the process ID of a currently running process. +++ +++To make use of this feature, you have to write in the +++@file{/proc/@var{pid}/coredump_filter} file a value, in hexadecimal, +++which is a bit mask representing the memory mapping types. If a bit +++is set in the bit mask, then the memory mappings of the corresponding +++types will be dumped; otherwise, they will be ignored. This +++configuration is inherited by child processes. For more information +++about the bits that can be set in the +++@file{/proc/@var{pid}/coredump_filter} file, please refer to the +++manpage of @code{core(5)}. +++ +++By default, this option is @code{on}. If this option is turned +++@code{off}, @value{GDBN} does not read the @file{coredump_filter} file +++and instead uses the same default value as the Linux kernel in order +++to decide which pages will be dumped in the core dump file. This +++value is currently @code{0x33}, which means that bits @code{0} +++(anonymous private mappings), @code{1} (anonymous shared mappings), +++@code{4} (ELF headers) and @code{5} (private huge pages) are active. +++This will cause these memory mappings to be dumped automatically. +++ +++@kindex set dump-excluded-mappings +++@anchor{set dump-excluded-mappings} +++@item set dump-excluded-mappings on +++@itemx set dump-excluded-mappings off +++If @code{on} is specified, @value{GDBN} will dump memory mappings +++marked with the @code{VM_DONTDUMP} flag. This flag is represented in +++the file @file{/proc/@var{pid}/smaps} with the acronym @code{dd}. +++ +++The default value is @code{off}. +++@end table +++ +++@node Character Sets +++@section Character Sets +++@cindex character sets +++@cindex charset +++@cindex translating between character sets +++@cindex host character set +++@cindex target character set +++ +++If the program you are debugging uses a different character set to +++represent characters and strings than the one @value{GDBN} uses itself, +++@value{GDBN} can automatically translate between the character sets for +++you. The character set @value{GDBN} uses we call the @dfn{host +++character set}; the one the inferior program uses we call the +++@dfn{target character set}. +++ +++For example, if you are running @value{GDBN} on a @sc{gnu}/Linux system, which +++uses the ISO Latin 1 character set, but you are using @value{GDBN}'s +++remote protocol (@pxref{Remote Debugging}) to debug a program +++running on an IBM mainframe, which uses the @sc{ebcdic} character set, +++then the host character set is Latin-1, and the target character set is +++@sc{ebcdic}. If you give @value{GDBN} the command @code{set +++target-charset EBCDIC-US}, then @value{GDBN} translates between +++@sc{ebcdic} and Latin 1 as you print character or string values, or use +++character and string literals in expressions. +++ +++@value{GDBN} has no way to automatically recognize which character set +++the inferior program uses; you must tell it, using the @code{set +++target-charset} command, described below. +++ +++Here are the commands for controlling @value{GDBN}'s character set +++support: +++ +++@table @code +++@item set target-charset @var{charset} +++@kindex set target-charset +++Set the current target character set to @var{charset}. To display the +++list of supported target character sets, type +++@kbd{@w{set target-charset @key{TAB}@key{TAB}}}. +++ +++@item set host-charset @var{charset} +++@kindex set host-charset +++Set the current host character set to @var{charset}. +++ +++By default, @value{GDBN} uses a host character set appropriate to the +++system it is running on; you can override that default using the +++@code{set host-charset} command. On some systems, @value{GDBN} cannot +++automatically determine the appropriate host character set. In this +++case, @value{GDBN} uses @samp{UTF-8}. +++ +++@value{GDBN} can only use certain character sets as its host character +++set. If you type @kbd{@w{set host-charset @key{TAB}@key{TAB}}}, +++@value{GDBN} will list the host character sets it supports. +++ +++@item set charset @var{charset} +++@kindex set charset +++Set the current host and target character sets to @var{charset}. As +++above, if you type @kbd{@w{set charset @key{TAB}@key{TAB}}}, +++@value{GDBN} will list the names of the character sets that can be used +++for both host and target. +++ +++@item show charset +++@kindex show charset +++Show the names of the current host and target character sets. +++ +++@item show host-charset +++@kindex show host-charset +++Show the name of the current host character set. +++ +++@item show target-charset +++@kindex show target-charset +++Show the name of the current target character set. +++ +++@item set target-wide-charset @var{charset} +++@kindex set target-wide-charset +++Set the current target's wide character set to @var{charset}. This is +++the character set used by the target's @code{wchar_t} type. To +++display the list of supported wide character sets, type +++@kbd{@w{set target-wide-charset @key{TAB}@key{TAB}}}. +++ +++@item show target-wide-charset +++@kindex show target-wide-charset +++Show the name of the current target's wide character set. +++@end table +++ +++Here is an example of @value{GDBN}'s character set support in action. +++Assume that the following source code has been placed in the file +++@file{charset-test.c}: +++ +++@smallexample +++#include +++ +++char ascii_hello[] +++ = @{72, 101, 108, 108, 111, 44, 32, 119, +++ 111, 114, 108, 100, 33, 10, 0@}; +++char ibm1047_hello[] +++ = @{200, 133, 147, 147, 150, 107, 64, 166, +++ 150, 153, 147, 132, 90, 37, 0@}; +++ +++main () +++@{ +++ printf ("Hello, world!\n"); +++@} +++@end smallexample +++ +++In this program, @code{ascii_hello} and @code{ibm1047_hello} are arrays +++containing the string @samp{Hello, world!} followed by a newline, +++encoded in the @sc{ascii} and @sc{ibm1047} character sets. +++ +++We compile the program, and invoke the debugger on it: +++ +++@smallexample +++$ gcc -g charset-test.c -o charset-test +++$ gdb -nw charset-test +++GNU gdb 2001-12-19-cvs +++Copyright 2001 Free Software Foundation, Inc. +++@dots{} +++(@value{GDBP}) +++@end smallexample +++ +++We can use the @code{show charset} command to see what character sets +++@value{GDBN} is currently using to interpret and display characters and +++strings: +++ +++@smallexample +++(@value{GDBP}) show charset +++The current host and target character set is `ISO-8859-1'. +++(@value{GDBP}) +++@end smallexample +++ +++For the sake of printing this manual, let's use @sc{ascii} as our +++initial character set: +++@smallexample +++(@value{GDBP}) set charset ASCII +++(@value{GDBP}) show charset +++The current host and target character set is `ASCII'. +++(@value{GDBP}) +++@end smallexample +++ +++Let's assume that @sc{ascii} is indeed the correct character set for our +++host system --- in other words, let's assume that if @value{GDBN} prints +++characters using the @sc{ascii} character set, our terminal will display +++them properly. Since our current target character set is also +++@sc{ascii}, the contents of @code{ascii_hello} print legibly: +++ +++@smallexample +++(@value{GDBP}) print ascii_hello +++$1 = 0x401698 "Hello, world!\n" +++(@value{GDBP}) print ascii_hello[0] +++$2 = 72 'H' +++(@value{GDBP}) +++@end smallexample +++ +++@value{GDBN} uses the target character set for character and string +++literals you use in expressions: +++ +++@smallexample +++(@value{GDBP}) print '+' +++$3 = 43 '+' +++(@value{GDBP}) +++@end smallexample +++ +++The @sc{ascii} character set uses the number 43 to encode the @samp{+} +++character. +++ +++@value{GDBN} relies on the user to tell it which character set the +++target program uses. If we print @code{ibm1047_hello} while our target +++character set is still @sc{ascii}, we get jibberish: +++ +++@smallexample +++(@value{GDBP}) print ibm1047_hello +++$4 = 0x4016a8 "\310\205\223\223\226k@@\246\226\231\223\204Z%" +++(@value{GDBP}) print ibm1047_hello[0] +++$5 = 200 '\310' +++(@value{GDBP}) +++@end smallexample +++ +++If we invoke the @code{set target-charset} followed by @key{TAB}@key{TAB}, +++@value{GDBN} tells us the character sets it supports: +++ +++@smallexample +++(@value{GDBP}) set target-charset +++ASCII EBCDIC-US IBM1047 ISO-8859-1 +++(@value{GDBP}) set target-charset +++@end smallexample +++ +++We can select @sc{ibm1047} as our target character set, and examine the +++program's strings again. Now the @sc{ascii} string is wrong, but +++@value{GDBN} translates the contents of @code{ibm1047_hello} from the +++target character set, @sc{ibm1047}, to the host character set, +++@sc{ascii}, and they display correctly: +++ +++@smallexample +++(@value{GDBP}) set target-charset IBM1047 +++(@value{GDBP}) show charset +++The current host character set is `ASCII'. +++The current target character set is `IBM1047'. +++(@value{GDBP}) print ascii_hello +++$6 = 0x401698 "\110\145%%?\054\040\167?\162%\144\041\012" +++(@value{GDBP}) print ascii_hello[0] +++$7 = 72 '\110' +++(@value{GDBP}) print ibm1047_hello +++$8 = 0x4016a8 "Hello, world!\n" +++(@value{GDBP}) print ibm1047_hello[0] +++$9 = 200 'H' +++(@value{GDBP}) +++@end smallexample +++ +++As above, @value{GDBN} uses the target character set for character and +++string literals you use in expressions: +++ +++@smallexample +++(@value{GDBP}) print '+' +++$10 = 78 '+' +++(@value{GDBP}) +++@end smallexample +++ +++The @sc{ibm1047} character set uses the number 78 to encode the @samp{+} +++character. +++ +++@node Caching Target Data +++@section Caching Data of Targets +++@cindex caching data of targets +++ +++@value{GDBN} caches data exchanged between the debugger and a target. +++Each cache is associated with the address space of the inferior. +++@xref{Inferiors Connections and Programs}, about inferior and address space. +++Such caching generally improves performance in remote debugging +++(@pxref{Remote Debugging}), because it reduces the overhead of the +++remote protocol by bundling memory reads and writes into large chunks. +++Unfortunately, simply caching everything would lead to incorrect results, +++since @value{GDBN} does not necessarily know anything about volatile +++values, memory-mapped I/O addresses, etc. Furthermore, in non-stop mode +++(@pxref{Non-Stop Mode}) memory can be changed @emph{while} a gdb command +++is executing. +++Therefore, by default, @value{GDBN} only caches data +++known to be on the stack@footnote{In non-stop mode, it is moderately +++rare for a running thread to modify the stack of a stopped thread +++in a way that would interfere with a backtrace, and caching of +++stack reads provides a significant speed up of remote backtraces.} or +++in the code segment. +++Other regions of memory can be explicitly marked as +++cacheable; @pxref{Memory Region Attributes}. +++ +++@table @code +++@kindex set remotecache +++@item set remotecache on +++@itemx set remotecache off +++This option no longer does anything; it exists for compatibility +++with old scripts. +++ +++@kindex show remotecache +++@item show remotecache +++Show the current state of the obsolete remotecache flag. +++ +++@kindex set stack-cache +++@item set stack-cache on +++@itemx set stack-cache off +++Enable or disable caching of stack accesses. When @code{on}, use +++caching. By default, this option is @code{on}. +++ +++@kindex show stack-cache +++@item show stack-cache +++Show the current state of data caching for memory accesses. +++ +++@kindex set code-cache +++@item set code-cache on +++@itemx set code-cache off +++Enable or disable caching of code segment accesses. When @code{on}, +++use caching. By default, this option is @code{on}. This improves +++performance of disassembly in remote debugging. +++ +++@kindex show code-cache +++@item show code-cache +++Show the current state of target memory cache for code segment +++accesses. +++ +++@kindex info dcache +++@item info dcache @r{[}line@r{]} +++Print the information about the performance of data cache of the +++current inferior's address space. The information displayed +++includes the dcache width and depth, and for each cache line, its +++number, address, and how many times it was referenced. This +++command is useful for debugging the data cache operation. +++ +++If a line number is specified, the contents of that line will be +++printed in hex. +++ +++@item set dcache size @var{size} +++@cindex dcache size +++@kindex set dcache size +++Set maximum number of entries in dcache (dcache depth above). +++ +++@item set dcache line-size @var{line-size} +++@cindex dcache line-size +++@kindex set dcache line-size +++Set number of bytes each dcache entry caches (dcache width above). +++Must be a power of 2. +++ +++@item show dcache size +++@kindex show dcache size +++Show maximum number of dcache entries. @xref{Caching Target Data, info dcache}. +++ +++@item show dcache line-size +++@kindex show dcache line-size +++Show default size of dcache lines. +++ +++@end table +++ +++@node Searching Memory +++@section Search Memory +++@cindex searching memory +++ +++Memory can be searched for a particular sequence of bytes with the +++@code{find} command. +++ +++@table @code +++@kindex find +++@item find @r{[}/@var{sn}@r{]} @var{start_addr}, +@var{len}, @var{val1} @r{[}, @var{val2}, @dots{}@r{]} +++@itemx find @r{[}/@var{sn}@r{]} @var{start_addr}, @var{end_addr}, @var{val1} @r{[}, @var{val2}, @dots{}@r{]} +++Search memory for the sequence of bytes specified by @var{val1}, @var{val2}, +++etc. The search begins at address @var{start_addr} and continues for either +++@var{len} bytes or through to @var{end_addr} inclusive. +++@end table +++ +++@var{s} and @var{n} are optional parameters. +++They may be specified in either order, apart or together. +++ +++@table @r +++@item @var{s}, search query size +++The size of each search query value. +++ +++@table @code +++@item b +++bytes +++@item h +++halfwords (two bytes) +++@item w +++words (four bytes) +++@item g +++giant words (eight bytes) +++@end table +++ +++All values are interpreted in the current language. +++This means, for example, that if the current source language is C/C@t{++} +++then searching for the string ``hello'' includes the trailing '\0'. +++The null terminator can be removed from searching by using casts, +++e.g.: @samp{@{char[5]@}"hello"}. +++ +++If the value size is not specified, it is taken from the +++value's type in the current language. +++This is useful when one wants to specify the search +++pattern as a mixture of types. +++Note that this means, for example, that in the case of C-like languages +++a search for an untyped 0x42 will search for @samp{(int) 0x42} +++which is typically four bytes. +++ +++@item @var{n}, maximum number of finds +++The maximum number of matches to print. The default is to print all finds. +++@end table +++ +++You can use strings as search values. Quote them with double-quotes +++ (@code{"}). +++The string value is copied into the search pattern byte by byte, +++regardless of the endianness of the target and the size specification. +++ +++The address of each match found is printed as well as a count of the +++number of matches found. +++ +++The address of the last value found is stored in convenience variable +++@samp{$_}. +++A count of the number of matches is stored in @samp{$numfound}. +++ +++For example, if stopped at the @code{printf} in this function: +++ +++@smallexample +++void +++hello () +++@{ +++ static char hello[] = "hello-hello"; +++ static struct @{ char c; short s; int i; @} +++ __attribute__ ((packed)) mixed +++ = @{ 'c', 0x1234, 0x87654321 @}; +++ printf ("%s\n", hello); +++@} +++@end smallexample +++ +++@noindent +++you get during debugging: +++ +++@smallexample +++(gdb) find &hello[0], +sizeof(hello), "hello" +++0x804956d +++1 pattern found +++(gdb) find &hello[0], +sizeof(hello), 'h', 'e', 'l', 'l', 'o' +++0x8049567 +++0x804956d +++2 patterns found. +++(gdb) find &hello[0], +sizeof(hello), @{char[5]@}"hello" +++0x8049567 +++0x804956d +++2 patterns found. +++(gdb) find /b1 &hello[0], +sizeof(hello), 'h', 0x65, 'l' +++0x8049567 +++1 pattern found +++(gdb) find &mixed, +sizeof(mixed), (char) 'c', (short) 0x1234, (int) 0x87654321 +++0x8049560 +++1 pattern found +++(gdb) print $numfound +++$1 = 1 +++(gdb) print $_ +++$2 = (void *) 0x8049560 +++@end smallexample +++ +++@node Value Sizes +++@section Value Sizes +++ +++Whenever @value{GDBN} prints a value memory will be allocated within +++@value{GDBN} to hold the contents of the value. It is possible in +++some languages with dynamic typing systems, that an invalid program +++may indicate a value that is incorrectly large, this in turn may cause +++@value{GDBN} to try and allocate an overly large amount of memory. +++ +++@table @code +++@kindex set max-value-size +++@item set max-value-size @var{bytes} +++@itemx set max-value-size unlimited +++Set the maximum size of memory that @value{GDBN} will allocate for the +++contents of a value to @var{bytes}, trying to display a value that +++requires more memory than that will result in an error. +++ +++Setting this variable does not effect values that have already been +++allocated within @value{GDBN}, only future allocations. +++ +++There's a minimum size that @code{max-value-size} can be set to in +++order that @value{GDBN} can still operate correctly, this minimum is +++currently 16 bytes. +++ +++The limit applies to the results of some subexpressions as well as to +++complete expressions. For example, an expression denoting a simple +++integer component, such as @code{x.y.z}, may fail if the size of +++@var{x.y} is dynamic and exceeds @var{bytes}. On the other hand, +++@value{GDBN} is sometimes clever; the expression @code{A[i]}, where +++@var{A} is an array variable with non-constant size, will generally +++succeed regardless of the bounds on @var{A}, as long as the component +++size is less than @var{bytes}. +++ +++The default value of @code{max-value-size} is currently 64k. +++ +++@kindex show max-value-size +++@item show max-value-size +++Show the maximum size of memory, in bytes, that @value{GDBN} will +++allocate for the contents of a value. +++@end table +++ +++@node Optimized Code +++@chapter Debugging Optimized Code +++@cindex optimized code, debugging +++@cindex debugging optimized code +++ +++Almost all compilers support optimization. With optimization +++disabled, the compiler generates assembly code that corresponds +++directly to your source code, in a simplistic way. As the compiler +++applies more powerful optimizations, the generated assembly code +++diverges from your original source code. With help from debugging +++information generated by the compiler, @value{GDBN} can map from +++the running program back to constructs from your original source. +++ +++@value{GDBN} is more accurate with optimization disabled. If you +++can recompile without optimization, it is easier to follow the +++progress of your program during debugging. But, there are many cases +++where you may need to debug an optimized version. +++ +++When you debug a program compiled with @samp{-g -O}, remember that the +++optimizer has rearranged your code; the debugger shows you what is +++really there. Do not be too surprised when the execution path does not +++exactly match your source file! An extreme example: if you define a +++variable, but never use it, @value{GDBN} never sees that +++variable---because the compiler optimizes it out of existence. +++ +++Some things do not work as well with @samp{-g -O} as with just +++@samp{-g}, particularly on machines with instruction scheduling. If in +++doubt, recompile with @samp{-g} alone, and if this fixes the problem, +++please report it to us as a bug (including a test case!). +++@xref{Variables}, for more information about debugging optimized code. +++ +++@menu +++* Inline Functions:: How @value{GDBN} presents inlining +++* Tail Call Frames:: @value{GDBN} analysis of jumps to functions +++@end menu +++ +++@node Inline Functions +++@section Inline Functions +++@cindex inline functions, debugging +++ +++@dfn{Inlining} is an optimization that inserts a copy of the function +++body directly at each call site, instead of jumping to a shared +++routine. @value{GDBN} displays inlined functions just like +++non-inlined functions. They appear in backtraces. You can view their +++arguments and local variables, step into them with @code{step}, skip +++them with @code{next}, and escape from them with @code{finish}. +++You can check whether a function was inlined by using the +++@code{info frame} command. +++ +++For @value{GDBN} to support inlined functions, the compiler must +++record information about inlining in the debug information --- +++@value{NGCC} using the @sc{dwarf 2} format does this, and several +++other compilers do also. @value{GDBN} only supports inlined functions +++when using @sc{dwarf 2}. Versions of @value{NGCC} before 4.1 +++do not emit two required attributes (@samp{DW_AT_call_file} and +++@samp{DW_AT_call_line}); @value{GDBN} does not display inlined +++function calls with earlier versions of @value{NGCC}. It instead +++displays the arguments and local variables of inlined functions as +++local variables in the caller. +++ +++The body of an inlined function is directly included at its call site; +++unlike a non-inlined function, there are no instructions devoted to +++the call. @value{GDBN} still pretends that the call site and the +++start of the inlined function are different instructions. Stepping to +++the call site shows the call site, and then stepping again shows +++the first line of the inlined function, even though no additional +++instructions are executed. +++ +++This makes source-level debugging much clearer; you can see both the +++context of the call and then the effect of the call. Only stepping by +++a single instruction using @code{stepi} or @code{nexti} does not do +++this; single instruction steps always show the inlined body. +++ +++There are some ways that @value{GDBN} does not pretend that inlined +++function calls are the same as normal calls: +++ +++@itemize @bullet +++@item +++Setting breakpoints at the call site of an inlined function may not +++work, because the call site does not contain any code. @value{GDBN} +++may incorrectly move the breakpoint to the next line of the enclosing +++function, after the call. This limitation will be removed in a future +++version of @value{GDBN}; until then, set a breakpoint on an earlier line +++or inside the inlined function instead. +++ +++@item +++@value{GDBN} cannot locate the return value of inlined calls after +++using the @code{finish} command. This is a limitation of compiler-generated +++debugging information; after @code{finish}, you can step to the next line +++and print a variable where your program stored the return value. +++ +++@end itemize +++ +++@node Tail Call Frames +++@section Tail Call Frames +++@cindex tail call frames, debugging +++ +++Function @code{B} can call function @code{C} in its very last statement. In +++unoptimized compilation the call of @code{C} is immediately followed by return +++instruction at the end of @code{B} code. Optimizing compiler may replace the +++call and return in function @code{B} into one jump to function @code{C} +++instead. Such use of a jump instruction is called @dfn{tail call}. +++ +++During execution of function @code{C}, there will be no indication in the +++function call stack frames that it was tail-called from @code{B}. If function +++@code{A} regularly calls function @code{B} which tail-calls function @code{C}, +++then @value{GDBN} will see @code{A} as the caller of @code{C}. However, in +++some cases @value{GDBN} can determine that @code{C} was tail-called from +++@code{B}, and it will then create fictitious call frame for that, with the +++return address set up as if @code{B} called @code{C} normally. +++ +++This functionality is currently supported only by DWARF 2 debugging format and +++the compiler has to produce @samp{DW_TAG_call_site} tags. With +++@value{NGCC}, you need to specify @option{-O -g} during compilation, to get +++this information. +++ +++@kbd{info frame} command (@pxref{Frame Info}) will indicate the tail call frame +++kind by text @code{tail call frame} such as in this sample @value{GDBN} output: +++ +++@smallexample +++(gdb) x/i $pc - 2 +++ 0x40066b : jmp 0x400640 +++(gdb) info frame +++Stack level 1, frame at 0x7fffffffda30: +++ rip = 0x40066d in b (amd64-entry-value.cc:59); saved rip 0x4004c5 +++ tail call frame, caller of frame at 0x7fffffffda30 +++ source language c++. +++ Arglist at unknown address. +++ Locals at unknown address, Previous frame's sp is 0x7fffffffda30 +++@end smallexample +++ +++The detection of all the possible code path executions can find them ambiguous. +++There is no execution history stored (possible @ref{Reverse Execution} is never +++used for this purpose) and the last known caller could have reached the known +++callee by multiple different jump sequences. In such case @value{GDBN} still +++tries to show at least all the unambiguous top tail callers and all the +++unambiguous bottom tail calees, if any. +++ +++@table @code +++@anchor{set debug entry-values} +++@item set debug entry-values +++@kindex set debug entry-values +++When set to on, enables printing of analysis messages for both frame argument +++values at function entry and tail calls. It will show all the possible valid +++tail calls code paths it has considered. It will also print the intersection +++of them with the final unambiguous (possibly partial or even empty) code path +++result. +++ +++@item show debug entry-values +++@kindex show debug entry-values +++Show the current state of analysis messages printing for both frame argument +++values at function entry and tail calls. +++@end table +++ +++The analysis messages for tail calls can for example show why the virtual tail +++call frame for function @code{c} has not been recognized (due to the indirect +++reference by variable @code{x}): +++ +++@smallexample +++static void __attribute__((noinline, noclone)) c (void); +++void (*x) (void) = c; +++static void __attribute__((noinline, noclone)) a (void) @{ x++; @} +++static void __attribute__((noinline, noclone)) c (void) @{ a (); @} +++int main (void) @{ x (); return 0; @} +++ +++Breakpoint 1, DW_OP_entry_value resolving cannot find +++DW_TAG_call_site 0x40039a in main +++a () at t.c:3 +++3 static void __attribute__((noinline, noclone)) a (void) @{ x++; @} +++(gdb) bt +++#0 a () at t.c:3 +++#1 0x000000000040039a in main () at t.c:5 +++@end smallexample +++ +++Another possibility is an ambiguous virtual tail call frames resolution: +++ +++@smallexample +++int i; +++static void __attribute__((noinline, noclone)) f (void) @{ i++; @} +++static void __attribute__((noinline, noclone)) e (void) @{ f (); @} +++static void __attribute__((noinline, noclone)) d (void) @{ f (); @} +++static void __attribute__((noinline, noclone)) c (void) @{ d (); @} +++static void __attribute__((noinline, noclone)) b (void) +++@{ if (i) c (); else e (); @} +++static void __attribute__((noinline, noclone)) a (void) @{ b (); @} +++int main (void) @{ a (); return 0; @} +++ +++tailcall: initial: 0x4004d2(a) 0x4004ce(b) 0x4004b2(c) 0x4004a2(d) +++tailcall: compare: 0x4004d2(a) 0x4004cc(b) 0x400492(e) +++tailcall: reduced: 0x4004d2(a) | +++(gdb) bt +++#0 f () at t.c:2 +++#1 0x00000000004004d2 in a () at t.c:8 +++#2 0x0000000000400395 in main () at t.c:9 +++@end smallexample +++ +++@set CALLSEQ1A @code{main@value{ARROW}a@value{ARROW}b@value{ARROW}c@value{ARROW}d@value{ARROW}f} +++@set CALLSEQ2A @code{main@value{ARROW}a@value{ARROW}b@value{ARROW}e@value{ARROW}f} +++ +++@c Convert CALLSEQ#A to CALLSEQ#B depending on HAVE_MAKEINFO_CLICK. +++@ifset HAVE_MAKEINFO_CLICK +++@set ARROW @click{} +++@set CALLSEQ1B @clicksequence{@value{CALLSEQ1A}} +++@set CALLSEQ2B @clicksequence{@value{CALLSEQ2A}} +++@end ifset +++@ifclear HAVE_MAKEINFO_CLICK +++@set ARROW -> +++@set CALLSEQ1B @value{CALLSEQ1A} +++@set CALLSEQ2B @value{CALLSEQ2A} +++@end ifclear +++ +++Frames #0 and #2 are real, #1 is a virtual tail call frame. +++The code can have possible execution paths @value{CALLSEQ1B} or +++@value{CALLSEQ2B}, @value{GDBN} cannot find which one from the inferior state. +++ +++@code{initial:} state shows some random possible calling sequence @value{GDBN} +++has found. It then finds another possible calling sequence - that one is +++prefixed by @code{compare:}. The non-ambiguous intersection of these two is +++printed as the @code{reduced:} calling sequence. That one could have many +++further @code{compare:} and @code{reduced:} statements as long as there remain +++any non-ambiguous sequence entries. +++ +++For the frame of function @code{b} in both cases there are different possible +++@code{$pc} values (@code{0x4004cc} or @code{0x4004ce}), therefore this frame is +++also ambiguous. The only non-ambiguous frame is the one for function @code{a}, +++therefore this one is displayed to the user while the ambiguous frames are +++omitted. +++ +++There can be also reasons why printing of frame argument values at function +++entry may fail: +++ +++@smallexample +++int v; +++static void __attribute__((noinline, noclone)) c (int i) @{ v++; @} +++static void __attribute__((noinline, noclone)) a (int i); +++static void __attribute__((noinline, noclone)) b (int i) @{ a (i); @} +++static void __attribute__((noinline, noclone)) a (int i) +++@{ if (i) b (i - 1); else c (0); @} +++int main (void) @{ a (5); return 0; @} +++ +++(gdb) bt +++#0 c (i=i@@entry=0) at t.c:2 +++#1 0x0000000000400428 in a (DW_OP_entry_value resolving has found +++function "a" at 0x400420 can call itself via tail calls +++i=) at t.c:6 +++#2 0x000000000040036e in main () at t.c:7 +++@end smallexample +++ +++@value{GDBN} cannot find out from the inferior state if and how many times did +++function @code{a} call itself (via function @code{b}) as these calls would be +++tail calls. Such tail calls would modify the @code{i} variable, therefore +++@value{GDBN} cannot be sure the value it knows would be right - @value{GDBN} +++prints @code{} instead. +++ +++@node Macros +++@chapter C Preprocessor Macros +++ +++Some languages, such as C and C@t{++}, provide a way to define and invoke +++``preprocessor macros'' which expand into strings of tokens. +++@value{GDBN} can evaluate expressions containing macro invocations, show +++the result of macro expansion, and show a macro's definition, including +++where it was defined. +++ +++You may need to compile your program specially to provide @value{GDBN} +++with information about preprocessor macros. Most compilers do not +++include macros in their debugging information, even when you compile +++with the @option{-g} flag. @xref{Compilation}. +++ +++A program may define a macro at one point, remove that definition later, +++and then provide a different definition after that. Thus, at different +++points in the program, a macro may have different definitions, or have +++no definition at all. If there is a current stack frame, @value{GDBN} +++uses the macros in scope at that frame's source code line. Otherwise, +++@value{GDBN} uses the macros in scope at the current listing location; +++see @ref{List}. +++ +++Whenever @value{GDBN} evaluates an expression, it always expands any +++macro invocations present in the expression. @value{GDBN} also provides +++the following commands for working with macros explicitly. +++ +++@table @code +++ +++@kindex macro expand +++@cindex macro expansion, showing the results of preprocessor +++@cindex preprocessor macro expansion, showing the results of +++@cindex expanding preprocessor macros +++@item macro expand @var{expression} +++@itemx macro exp @var{expression} +++Show the results of expanding all preprocessor macro invocations in +++@var{expression}. Since @value{GDBN} simply expands macros, but does +++not parse the result, @var{expression} need not be a valid expression; +++it can be any string of tokens. +++ +++@kindex macro exp1 +++@item macro expand-once @var{expression} +++@itemx macro exp1 @var{expression} +++@cindex expand macro once +++@i{(This command is not yet implemented.)} Show the results of +++expanding those preprocessor macro invocations that appear explicitly in +++@var{expression}. Macro invocations appearing in that expansion are +++left unchanged. This command allows you to see the effect of a +++particular macro more clearly, without being confused by further +++expansions. Since @value{GDBN} simply expands macros, but does not +++parse the result, @var{expression} need not be a valid expression; it +++can be any string of tokens. +++ +++@kindex info macro +++@cindex macro definition, showing +++@cindex definition of a macro, showing +++@cindex macros, from debug info +++@item info macro [-a|-all] [--] @var{macro} +++Show the current definition or all definitions of the named @var{macro}, +++and describe the source location or compiler command-line where that +++definition was established. The optional double dash is to signify the end of +++argument processing and the beginning of @var{macro} for non C-like macros where +++the macro may begin with a hyphen. +++ +++@kindex info macros +++@item info macros @var{location} +++Show all macro definitions that are in effect at the location specified +++by @var{location}, and describe the source location or compiler +++command-line where those definitions were established. +++ +++@kindex macro define +++@cindex user-defined macros +++@cindex defining macros interactively +++@cindex macros, user-defined +++@item macro define @var{macro} @var{replacement-list} +++@itemx macro define @var{macro}(@var{arglist}) @var{replacement-list} +++Introduce a definition for a preprocessor macro named @var{macro}, +++invocations of which are replaced by the tokens given in +++@var{replacement-list}. The first form of this command defines an +++``object-like'' macro, which takes no arguments; the second form +++defines a ``function-like'' macro, which takes the arguments given in +++@var{arglist}. +++ +++A definition introduced by this command is in scope in every +++expression evaluated in @value{GDBN}, until it is removed with the +++@code{macro undef} command, described below. The definition overrides +++all definitions for @var{macro} present in the program being debugged, +++as well as any previous user-supplied definition. +++ +++@kindex macro undef +++@item macro undef @var{macro} +++Remove any user-supplied definition for the macro named @var{macro}. +++This command only affects definitions provided with the @code{macro +++define} command, described above; it cannot remove definitions present +++in the program being debugged. +++ +++@kindex macro list +++@item macro list +++List all the macros defined using the @code{macro define} command. +++@end table +++ +++@cindex macros, example of debugging with +++Here is a transcript showing the above commands in action. First, we +++show our source files: +++ +++@smallexample +++$ cat sample.c +++#include +++#include "sample.h" +++ +++#define M 42 +++#define ADD(x) (M + x) +++ +++main () +++@{ +++#define N 28 +++ printf ("Hello, world!\n"); +++#undef N +++ printf ("We're so creative.\n"); +++#define N 1729 +++ printf ("Goodbye, world!\n"); +++@} +++$ cat sample.h +++#define Q < +++$ +++@end smallexample +++ +++Now, we compile the program using the @sc{gnu} C compiler, +++@value{NGCC}. We pass the @option{-gdwarf-2}@footnote{This is the +++minimum. Recent versions of @value{NGCC} support @option{-gdwarf-3} +++and @option{-gdwarf-4}; we recommend always choosing the most recent +++version of DWARF.} @emph{and} @option{-g3} flags to ensure the compiler +++includes information about preprocessor macros in the debugging +++information. +++ +++@smallexample +++$ gcc -gdwarf-2 -g3 sample.c -o sample +++$ +++@end smallexample +++ +++Now, we start @value{GDBN} on our sample program: +++ +++@smallexample +++$ gdb -nw sample +++GNU gdb 2002-05-06-cvs +++Copyright 2002 Free Software Foundation, Inc. +++GDB is free software, @dots{} +++(@value{GDBP}) +++@end smallexample +++ +++We can expand macros and examine their definitions, even when the +++program is not running. @value{GDBN} uses the current listing position +++to decide which macro definitions are in scope: +++ +++@smallexample +++(@value{GDBP}) list main +++3 +++4 #define M 42 +++5 #define ADD(x) (M + x) +++6 +++7 main () +++8 @{ +++9 #define N 28 +++10 printf ("Hello, world!\n"); +++11 #undef N +++12 printf ("We're so creative.\n"); +++(@value{GDBP}) info macro ADD +++Defined at /home/jimb/gdb/macros/play/sample.c:5 +++#define ADD(x) (M + x) +++(@value{GDBP}) info macro Q +++Defined at /home/jimb/gdb/macros/play/sample.h:1 +++ included at /home/jimb/gdb/macros/play/sample.c:2 +++#define Q < +++(@value{GDBP}) macro expand ADD(1) +++expands to: (42 + 1) +++(@value{GDBP}) macro expand-once ADD(1) +++expands to: once (M + 1) +++(@value{GDBP}) +++@end smallexample +++ +++In the example above, note that @code{macro expand-once} expands only +++the macro invocation explicit in the original text --- the invocation of +++@code{ADD} --- but does not expand the invocation of the macro @code{M}, +++which was introduced by @code{ADD}. +++ +++Once the program is running, @value{GDBN} uses the macro definitions in +++force at the source line of the current stack frame: +++ +++@smallexample +++(@value{GDBP}) break main +++Breakpoint 1 at 0x8048370: file sample.c, line 10. +++(@value{GDBP}) run +++Starting program: /home/jimb/gdb/macros/play/sample +++ +++Breakpoint 1, main () at sample.c:10 +++10 printf ("Hello, world!\n"); +++(@value{GDBP}) +++@end smallexample +++ +++At line 10, the definition of the macro @code{N} at line 9 is in force: +++ +++@smallexample +++(@value{GDBP}) info macro N +++Defined at /home/jimb/gdb/macros/play/sample.c:9 +++#define N 28 +++(@value{GDBP}) macro expand N Q M +++expands to: 28 < 42 +++(@value{GDBP}) print N Q M +++$1 = 1 +++(@value{GDBP}) +++@end smallexample +++ +++As we step over directives that remove @code{N}'s definition, and then +++give it a new definition, @value{GDBN} finds the definition (or lack +++thereof) in force at each point: +++ +++@smallexample +++(@value{GDBP}) next +++Hello, world! +++12 printf ("We're so creative.\n"); +++(@value{GDBP}) info macro N +++The symbol `N' has no definition as a C/C++ preprocessor macro +++at /home/jimb/gdb/macros/play/sample.c:12 +++(@value{GDBP}) next +++We're so creative. +++14 printf ("Goodbye, world!\n"); +++(@value{GDBP}) info macro N +++Defined at /home/jimb/gdb/macros/play/sample.c:13 +++#define N 1729 +++(@value{GDBP}) macro expand N Q M +++expands to: 1729 < 42 +++(@value{GDBP}) print N Q M +++$2 = 0 +++(@value{GDBP}) +++@end smallexample +++ +++In addition to source files, macros can be defined on the compilation command +++line using the @option{-D@var{name}=@var{value}} syntax. For macros defined in +++such a way, @value{GDBN} displays the location of their definition as line zero +++of the source file submitted to the compiler. +++ +++@smallexample +++(@value{GDBP}) info macro __STDC__ +++Defined at /home/jimb/gdb/macros/play/sample.c:0 +++-D__STDC__=1 +++(@value{GDBP}) +++@end smallexample +++ +++ +++@node Tracepoints +++@chapter Tracepoints +++@c This chapter is based on the documentation written by Michael +++@c Snyder, David Taylor, Jim Blandy, and Elena Zannoni. +++ +++@cindex tracepoints +++In some applications, it is not feasible for the debugger to interrupt +++the program's execution long enough for the developer to learn +++anything helpful about its behavior. If the program's correctness +++depends on its real-time behavior, delays introduced by a debugger +++might cause the program to change its behavior drastically, or perhaps +++fail, even when the code itself is correct. It is useful to be able +++to observe the program's behavior without interrupting it. +++ +++Using @value{GDBN}'s @code{trace} and @code{collect} commands, you can +++specify locations in the program, called @dfn{tracepoints}, and +++arbitrary expressions to evaluate when those tracepoints are reached. +++Later, using the @code{tfind} command, you can examine the values +++those expressions had when the program hit the tracepoints. The +++expressions may also denote objects in memory---structures or arrays, +++for example---whose values @value{GDBN} should record; while visiting +++a particular tracepoint, you may inspect those objects as if they were +++in memory at that moment. However, because @value{GDBN} records these +++values without interacting with you, it can do so quickly and +++unobtrusively, hopefully not disturbing the program's behavior. +++ +++The tracepoint facility is currently available only for remote +++targets. @xref{Targets}. In addition, your remote target must know +++how to collect trace data. This functionality is implemented in the +++remote stub; however, none of the stubs distributed with @value{GDBN} +++support tracepoints as of this writing. The format of the remote +++packets used to implement tracepoints are described in @ref{Tracepoint +++Packets}. +++ +++It is also possible to get trace data from a file, in a manner reminiscent +++of corefiles; you specify the filename, and use @code{tfind} to search +++through the file. @xref{Trace Files}, for more details. +++ +++This chapter describes the tracepoint commands and features. +++ +++@menu +++* Set Tracepoints:: +++* Analyze Collected Data:: +++* Tracepoint Variables:: +++* Trace Files:: +++@end menu +++ +++@node Set Tracepoints +++@section Commands to Set Tracepoints +++ +++Before running such a @dfn{trace experiment}, an arbitrary number of +++tracepoints can be set. A tracepoint is actually a special type of +++breakpoint (@pxref{Set Breaks}), so you can manipulate it using +++standard breakpoint commands. For instance, as with breakpoints, +++tracepoint numbers are successive integers starting from one, and many +++of the commands associated with tracepoints take the tracepoint number +++as their argument, to identify which tracepoint to work on. +++ +++For each tracepoint, you can specify, in advance, some arbitrary set +++of data that you want the target to collect in the trace buffer when +++it hits that tracepoint. The collected data can include registers, +++local variables, or global data. Later, you can use @value{GDBN} +++commands to examine the values these data had at the time the +++tracepoint was hit. +++ +++Tracepoints do not support every breakpoint feature. Ignore counts on +++tracepoints have no effect, and tracepoints cannot run @value{GDBN} +++commands when they are hit. Tracepoints may not be thread-specific +++either. +++ +++@cindex fast tracepoints +++Some targets may support @dfn{fast tracepoints}, which are inserted in +++a different way (such as with a jump instead of a trap), that is +++faster but possibly restricted in where they may be installed. +++ +++@cindex static tracepoints +++@cindex markers, static tracepoints +++@cindex probing markers, static tracepoints +++Regular and fast tracepoints are dynamic tracing facilities, meaning +++that they can be used to insert tracepoints at (almost) any location +++in the target. Some targets may also support controlling @dfn{static +++tracepoints} from @value{GDBN}. With static tracing, a set of +++instrumentation points, also known as @dfn{markers}, are embedded in +++the target program, and can be activated or deactivated by name or +++address. These are usually placed at locations which facilitate +++investigating what the target is actually doing. @value{GDBN}'s +++support for static tracing includes being able to list instrumentation +++points, and attach them with @value{GDBN} defined high level +++tracepoints that expose the whole range of convenience of +++@value{GDBN}'s tracepoints support. Namely, support for collecting +++registers values and values of global or local (to the instrumentation +++point) variables; tracepoint conditions and trace state variables. +++The act of installing a @value{GDBN} static tracepoint on an +++instrumentation point, or marker, is referred to as @dfn{probing} a +++static tracepoint marker. +++ +++@code{gdbserver} supports tracepoints on some target systems. +++@xref{Server,,Tracepoints support in @code{gdbserver}}. +++ +++This section describes commands to set tracepoints and associated +++conditions and actions. +++ +++@menu +++* Create and Delete Tracepoints:: +++* Enable and Disable Tracepoints:: +++* Tracepoint Passcounts:: +++* Tracepoint Conditions:: +++* Trace State Variables:: +++* Tracepoint Actions:: +++* Listing Tracepoints:: +++* Listing Static Tracepoint Markers:: +++* Starting and Stopping Trace Experiments:: +++* Tracepoint Restrictions:: +++@end menu +++ +++@node Create and Delete Tracepoints +++@subsection Create and Delete Tracepoints +++ +++@table @code +++@cindex set tracepoint +++@kindex trace +++@item trace @var{location} +++The @code{trace} command is very similar to the @code{break} command. +++Its argument @var{location} can be any valid location. +++@xref{Specify Location}. The @code{trace} command defines a tracepoint, +++which is a point in the target program where the debugger will briefly stop, +++collect some data, and then allow the program to continue. Setting a tracepoint +++or changing its actions takes effect immediately if the remote stub +++supports the @samp{InstallInTrace} feature (@pxref{install tracepoint +++in tracing}). +++If remote stub doesn't support the @samp{InstallInTrace} feature, all +++these changes don't take effect until the next @code{tstart} +++command, and once a trace experiment is running, further changes will +++not have any effect until the next trace experiment starts. In addition, +++@value{GDBN} supports @dfn{pending tracepoints}---tracepoints whose +++address is not yet resolved. (This is similar to pending breakpoints.) +++Pending tracepoints are not downloaded to the target and not installed +++until they are resolved. The resolution of pending tracepoints requires +++@value{GDBN} support---when debugging with the remote target, and +++@value{GDBN} disconnects from the remote stub (@pxref{disconnected +++tracing}), pending tracepoints can not be resolved (and downloaded to +++the remote stub) while @value{GDBN} is disconnected. +++ +++Here are some examples of using the @code{trace} command: +++ +++@smallexample +++(@value{GDBP}) @b{trace foo.c:121} // a source file and line number +++ +++(@value{GDBP}) @b{trace +2} // 2 lines forward +++ +++(@value{GDBP}) @b{trace my_function} // first source line of function +++ +++(@value{GDBP}) @b{trace *my_function} // EXACT start address of function +++ +++(@value{GDBP}) @b{trace *0x2117c4} // an address +++@end smallexample +++ +++@noindent +++You can abbreviate @code{trace} as @code{tr}. +++ +++@item trace @var{location} if @var{cond} +++Set a tracepoint with condition @var{cond}; evaluate the expression +++@var{cond} each time the tracepoint is reached, and collect data only +++if the value is nonzero---that is, if @var{cond} evaluates as true. +++@xref{Tracepoint Conditions, ,Tracepoint Conditions}, for more +++information on tracepoint conditions. +++ +++@item ftrace @var{location} [ if @var{cond} ] +++@cindex set fast tracepoint +++@cindex fast tracepoints, setting +++@kindex ftrace +++The @code{ftrace} command sets a fast tracepoint. For targets that +++support them, fast tracepoints will use a more efficient but possibly +++less general technique to trigger data collection, such as a jump +++instruction instead of a trap, or some sort of hardware support. It +++may not be possible to create a fast tracepoint at the desired +++location, in which case the command will exit with an explanatory +++message. +++ +++@value{GDBN} handles arguments to @code{ftrace} exactly as for +++@code{trace}. +++ +++On 32-bit x86-architecture systems, fast tracepoints normally need to +++be placed at an instruction that is 5 bytes or longer, but can be +++placed at 4-byte instructions if the low 64K of memory of the target +++program is available to install trampolines. Some Unix-type systems, +++such as @sc{gnu}/Linux, exclude low addresses from the program's +++address space; but for instance with the Linux kernel it is possible +++to let @value{GDBN} use this area by doing a @command{sysctl} command +++to set the @code{mmap_min_addr} kernel parameter, as in +++ +++@example +++sudo sysctl -w vm.mmap_min_addr=32768 +++@end example +++ +++@noindent +++which sets the low address to 32K, which leaves plenty of room for +++trampolines. The minimum address should be set to a page boundary. +++ +++@item strace @var{location} [ if @var{cond} ] +++@cindex set static tracepoint +++@cindex static tracepoints, setting +++@cindex probe static tracepoint marker +++@kindex strace +++The @code{strace} command sets a static tracepoint. For targets that +++support it, setting a static tracepoint probes a static +++instrumentation point, or marker, found at @var{location}. It may not +++be possible to set a static tracepoint at the desired location, in +++which case the command will exit with an explanatory message. +++ +++@value{GDBN} handles arguments to @code{strace} exactly as for +++@code{trace}, with the addition that the user can also specify +++@code{-m @var{marker}} as @var{location}. This probes the marker +++identified by the @var{marker} string identifier. This identifier +++depends on the static tracepoint backend library your program is +++using. You can find all the marker identifiers in the @samp{ID} field +++of the @code{info static-tracepoint-markers} command output. +++@xref{Listing Static Tracepoint Markers,,Listing Static Tracepoint +++Markers}. For example, in the following small program using the UST +++tracing engine: +++ +++@smallexample +++main () +++@{ +++ trace_mark(ust, bar33, "str %s", "FOOBAZ"); +++@} +++@end smallexample +++ +++@noindent +++the marker id is composed of joining the first two arguments to the +++@code{trace_mark} call with a slash, which translates to: +++ +++@smallexample +++(@value{GDBP}) info static-tracepoint-markers +++Cnt Enb ID Address What +++1 n ust/bar33 0x0000000000400ddc in main at stexample.c:22 +++ Data: "str %s" +++[etc...] +++@end smallexample +++ +++@noindent +++so you may probe the marker above with: +++ +++@smallexample +++(@value{GDBP}) strace -m ust/bar33 +++@end smallexample +++ +++Static tracepoints accept an extra collect action --- @code{collect +++$_sdata}. This collects arbitrary user data passed in the probe point +++call to the tracing library. In the UST example above, you'll see +++that the third argument to @code{trace_mark} is a printf-like format +++string. The user data is then the result of running that formatting +++string against the following arguments. Note that @code{info +++static-tracepoint-markers} command output lists that format string in +++the @samp{Data:} field. +++ +++You can inspect this data when analyzing the trace buffer, by printing +++the $_sdata variable like any other variable available to +++@value{GDBN}. @xref{Tracepoint Actions,,Tracepoint Action Lists}. +++ +++@vindex $tpnum +++@cindex last tracepoint number +++@cindex recent tracepoint number +++@cindex tracepoint number +++The convenience variable @code{$tpnum} records the tracepoint number +++of the most recently set tracepoint. +++ +++@kindex delete tracepoint +++@cindex tracepoint deletion +++@item delete tracepoint @r{[}@var{num}@r{]} +++Permanently delete one or more tracepoints. With no argument, the +++default is to delete all tracepoints. Note that the regular +++@code{delete} command can remove tracepoints also. +++ +++Examples: +++ +++@smallexample +++(@value{GDBP}) @b{delete trace 1 2 3} // remove three tracepoints +++ +++(@value{GDBP}) @b{delete trace} // remove all tracepoints +++@end smallexample +++ +++@noindent +++You can abbreviate this command as @code{del tr}. +++@end table +++ +++@node Enable and Disable Tracepoints +++@subsection Enable and Disable Tracepoints +++ +++These commands are deprecated; they are equivalent to plain @code{disable} and @code{enable}. +++ +++@table @code +++@kindex disable tracepoint +++@item disable tracepoint @r{[}@var{num}@r{]} +++Disable tracepoint @var{num}, or all tracepoints if no argument +++@var{num} is given. A disabled tracepoint will have no effect during +++a trace experiment, but it is not forgotten. You can re-enable +++a disabled tracepoint using the @code{enable tracepoint} command. +++If the command is issued during a trace experiment and the debug target +++has support for disabling tracepoints during a trace experiment, then the +++change will be effective immediately. Otherwise, it will be applied to the +++next trace experiment. +++ +++@kindex enable tracepoint +++@item enable tracepoint @r{[}@var{num}@r{]} +++Enable tracepoint @var{num}, or all tracepoints. If this command is +++issued during a trace experiment and the debug target supports enabling +++tracepoints during a trace experiment, then the enabled tracepoints will +++become effective immediately. Otherwise, they will become effective the +++next time a trace experiment is run. +++@end table +++ +++@node Tracepoint Passcounts +++@subsection Tracepoint Passcounts +++ +++@table @code +++@kindex passcount +++@cindex tracepoint pass count +++@item passcount @r{[}@var{n} @r{[}@var{num}@r{]]} +++Set the @dfn{passcount} of a tracepoint. The passcount is a way to +++automatically stop a trace experiment. If a tracepoint's passcount is +++@var{n}, then the trace experiment will be automatically stopped on +++the @var{n}'th time that tracepoint is hit. If the tracepoint number +++@var{num} is not specified, the @code{passcount} command sets the +++passcount of the most recently defined tracepoint. If no passcount is +++given, the trace experiment will run until stopped explicitly by the +++user. +++ +++Examples: +++ +++@smallexample +++(@value{GDBP}) @b{passcount 5 2} // Stop on the 5th execution of +++@exdent @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @code{// tracepoint 2} +++ +++(@value{GDBP}) @b{passcount 12} // Stop on the 12th execution of the +++@exdent @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @code{// most recently defined tracepoint.} +++(@value{GDBP}) @b{trace foo} +++(@value{GDBP}) @b{pass 3} +++(@value{GDBP}) @b{trace bar} +++(@value{GDBP}) @b{pass 2} +++(@value{GDBP}) @b{trace baz} +++(@value{GDBP}) @b{pass 1} // Stop tracing when foo has been +++@exdent @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @code{// executed 3 times OR when bar has} +++@exdent @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @code{// been executed 2 times} +++@exdent @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @code{// OR when baz has been executed 1 time.} +++@end smallexample +++@end table +++ +++@node Tracepoint Conditions +++@subsection Tracepoint Conditions +++@cindex conditional tracepoints +++@cindex tracepoint conditions +++ +++The simplest sort of tracepoint collects data every time your program +++reaches a specified place. You can also specify a @dfn{condition} for +++a tracepoint. A condition is just a Boolean expression in your +++programming language (@pxref{Expressions, ,Expressions}). A +++tracepoint with a condition evaluates the expression each time your +++program reaches it, and data collection happens only if the condition +++is true. +++ +++Tracepoint conditions can be specified when a tracepoint is set, by +++using @samp{if} in the arguments to the @code{trace} command. +++@xref{Create and Delete Tracepoints, ,Setting Tracepoints}. They can +++also be set or changed at any time with the @code{condition} command, +++just as with breakpoints. +++ +++Unlike breakpoint conditions, @value{GDBN} does not actually evaluate +++the conditional expression itself. Instead, @value{GDBN} encodes the +++expression into an agent expression (@pxref{Agent Expressions}) +++suitable for execution on the target, independently of @value{GDBN}. +++Global variables become raw memory locations, locals become stack +++accesses, and so forth. +++ +++For instance, suppose you have a function that is usually called +++frequently, but should not be called after an error has occurred. You +++could use the following tracepoint command to collect data about calls +++of that function that happen while the error code is propagating +++through the program; an unconditional tracepoint could end up +++collecting thousands of useless trace frames that you would have to +++search through. +++ +++@smallexample +++(@value{GDBP}) @kbd{trace normal_operation if errcode > 0} +++@end smallexample +++ +++@node Trace State Variables +++@subsection Trace State Variables +++@cindex trace state variables +++ +++A @dfn{trace state variable} is a special type of variable that is +++created and managed by target-side code. The syntax is the same as +++that for GDB's convenience variables (a string prefixed with ``$''), +++but they are stored on the target. They must be created explicitly, +++using a @code{tvariable} command. They are always 64-bit signed +++integers. +++ +++Trace state variables are remembered by @value{GDBN}, and downloaded +++to the target along with tracepoint information when the trace +++experiment starts. There are no intrinsic limits on the number of +++trace state variables, beyond memory limitations of the target. +++ +++@cindex convenience variables, and trace state variables +++Although trace state variables are managed by the target, you can use +++them in print commands and expressions as if they were convenience +++variables; @value{GDBN} will get the current value from the target +++while the trace experiment is running. Trace state variables share +++the same namespace as other ``$'' variables, which means that you +++cannot have trace state variables with names like @code{$23} or +++@code{$pc}, nor can you have a trace state variable and a convenience +++variable with the same name. +++ +++@table @code +++ +++@item tvariable $@var{name} [ = @var{expression} ] +++@kindex tvariable +++The @code{tvariable} command creates a new trace state variable named +++@code{$@var{name}}, and optionally gives it an initial value of +++@var{expression}. The @var{expression} is evaluated when this command is +++entered; the result will be converted to an integer if possible, +++otherwise @value{GDBN} will report an error. A subsequent +++@code{tvariable} command specifying the same name does not create a +++variable, but instead assigns the supplied initial value to the +++existing variable of that name, overwriting any previous initial +++value. The default initial value is 0. +++ +++@item info tvariables +++@kindex info tvariables +++List all the trace state variables along with their initial values. +++Their current values may also be displayed, if the trace experiment is +++currently running. +++ +++@item delete tvariable @r{[} $@var{name} @dots{} @r{]} +++@kindex delete tvariable +++Delete the given trace state variables, or all of them if no arguments +++are specified. +++ +++@end table +++ +++@node Tracepoint Actions +++@subsection Tracepoint Action Lists +++ +++@table @code +++@kindex actions +++@cindex tracepoint actions +++@item actions @r{[}@var{num}@r{]} +++This command will prompt for a list of actions to be taken when the +++tracepoint is hit. If the tracepoint number @var{num} is not +++specified, this command sets the actions for the one that was most +++recently defined (so that you can define a tracepoint and then say +++@code{actions} without bothering about its number). You specify the +++actions themselves on the following lines, one action at a time, and +++terminate the actions list with a line containing just @code{end}. So +++far, the only defined actions are @code{collect}, @code{teval}, and +++@code{while-stepping}. +++ +++@code{actions} is actually equivalent to @code{commands} (@pxref{Break +++Commands, ,Breakpoint Command Lists}), except that only the defined +++actions are allowed; any other @value{GDBN} command is rejected. +++ +++@cindex remove actions from a tracepoint +++To remove all actions from a tracepoint, type @samp{actions @var{num}} +++and follow it immediately with @samp{end}. +++ +++@smallexample +++(@value{GDBP}) @b{collect @var{data}} // collect some data +++ +++(@value{GDBP}) @b{while-stepping 5} // single-step 5 times, collect data +++ +++(@value{GDBP}) @b{end} // signals the end of actions. +++@end smallexample +++ +++In the following example, the action list begins with @code{collect} +++commands indicating the things to be collected when the tracepoint is +++hit. Then, in order to single-step and collect additional data +++following the tracepoint, a @code{while-stepping} command is used, +++followed by the list of things to be collected after each step in a +++sequence of single steps. The @code{while-stepping} command is +++terminated by its own separate @code{end} command. Lastly, the action +++list is terminated by an @code{end} command. +++ +++@smallexample +++(@value{GDBP}) @b{trace foo} +++(@value{GDBP}) @b{actions} +++Enter actions for tracepoint 1, one per line: +++> collect bar,baz +++> collect $regs +++> while-stepping 12 +++ > collect $pc, arr[i] +++ > end +++end +++@end smallexample +++ +++@kindex collect @r{(tracepoints)} +++@item collect@r{[}/@var{mods}@r{]} @var{expr1}, @var{expr2}, @dots{} +++Collect values of the given expressions when the tracepoint is hit. +++This command accepts a comma-separated list of any valid expressions. +++In addition to global, static, or local variables, the following +++special arguments are supported: +++ +++@table @code +++@item $regs +++Collect all registers. +++ +++@item $args +++Collect all function arguments. +++ +++@item $locals +++Collect all local variables. +++ +++@item $_ret +++Collect the return address. This is helpful if you want to see more +++of a backtrace. +++ +++@emph{Note:} The return address location can not always be reliably +++determined up front, and the wrong address / registers may end up +++collected instead. On some architectures the reliability is higher +++for tracepoints at function entry, while on others it's the opposite. +++When this happens, backtracing will stop because the return address is +++found unavailable (unless another collect rule happened to match it). +++ +++@item $_probe_argc +++Collects the number of arguments from the static probe at which the +++tracepoint is located. +++@xref{Static Probe Points}. +++ +++@item $_probe_arg@var{n} +++@var{n} is an integer between 0 and 11. Collects the @var{n}th argument +++from the static probe at which the tracepoint is located. +++@xref{Static Probe Points}. +++ +++@item $_sdata +++@vindex $_sdata@r{, collect} +++Collect static tracepoint marker specific data. Only available for +++static tracepoints. @xref{Tracepoint Actions,,Tracepoint Action +++Lists}. On the UST static tracepoints library backend, an +++instrumentation point resembles a @code{printf} function call. The +++tracing library is able to collect user specified data formatted to a +++character string using the format provided by the programmer that +++instrumented the program. Other backends have similar mechanisms. +++Here's an example of a UST marker call: +++ +++@smallexample +++ const char master_name[] = "$your_name"; +++ trace_mark(channel1, marker1, "hello %s", master_name) +++@end smallexample +++ +++In this case, collecting @code{$_sdata} collects the string +++@samp{hello $yourname}. When analyzing the trace buffer, you can +++inspect @samp{$_sdata} like any other variable available to +++@value{GDBN}. +++@end table +++ +++You can give several consecutive @code{collect} commands, each one +++with a single argument, or one @code{collect} command with several +++arguments separated by commas; the effect is the same. +++ +++The optional @var{mods} changes the usual handling of the arguments. +++@code{s} requests that pointers to chars be handled as strings, in +++particular collecting the contents of the memory being pointed at, up +++to the first zero. The upper bound is by default the value of the +++@code{print elements} variable; if @code{s} is followed by a decimal +++number, that is the upper bound instead. So for instance +++@samp{collect/s25 mystr} collects as many as 25 characters at +++@samp{mystr}. +++ +++The command @code{info scope} (@pxref{Symbols, info scope}) is +++particularly useful for figuring out what data to collect. +++ +++@kindex teval @r{(tracepoints)} +++@item teval @var{expr1}, @var{expr2}, @dots{} +++Evaluate the given expressions when the tracepoint is hit. This +++command accepts a comma-separated list of expressions. The results +++are discarded, so this is mainly useful for assigning values to trace +++state variables (@pxref{Trace State Variables}) without adding those +++values to the trace buffer, as would be the case if the @code{collect} +++action were used. +++ +++@kindex while-stepping @r{(tracepoints)} +++@item while-stepping @var{n} +++Perform @var{n} single-step instruction traces after the tracepoint, +++collecting new data after each step. The @code{while-stepping} +++command is followed by the list of what to collect while stepping +++(followed by its own @code{end} command): +++ +++@smallexample +++> while-stepping 12 +++ > collect $regs, myglobal +++ > end +++> +++@end smallexample +++ +++@noindent +++Note that @code{$pc} is not automatically collected by +++@code{while-stepping}; you need to explicitly collect that register if +++you need it. You may abbreviate @code{while-stepping} as @code{ws} or +++@code{stepping}. +++ +++@item set default-collect @var{expr1}, @var{expr2}, @dots{} +++@kindex set default-collect +++@cindex default collection action +++This variable is a list of expressions to collect at each tracepoint +++hit. It is effectively an additional @code{collect} action prepended +++to every tracepoint action list. The expressions are parsed +++individually for each tracepoint, so for instance a variable named +++@code{xyz} may be interpreted as a global for one tracepoint, and a +++local for another, as appropriate to the tracepoint's location. +++ +++@item show default-collect +++@kindex show default-collect +++Show the list of expressions that are collected by default at each +++tracepoint hit. +++ +++@end table +++ +++@node Listing Tracepoints +++@subsection Listing Tracepoints +++ +++@table @code +++@kindex info tracepoints @r{[}@var{n}@dots{}@r{]} +++@kindex info tp @r{[}@var{n}@dots{}@r{]} +++@cindex information about tracepoints +++@item info tracepoints @r{[}@var{num}@dots{}@r{]} +++Display information about the tracepoint @var{num}. If you don't +++specify a tracepoint number, displays information about all the +++tracepoints defined so far. The format is similar to that used for +++@code{info breakpoints}; in fact, @code{info tracepoints} is the same +++command, simply restricting itself to tracepoints. +++ +++A tracepoint's listing may include additional information specific to +++tracing: +++ +++@itemize @bullet +++@item +++its passcount as given by the @code{passcount @var{n}} command +++ +++@item +++the state about installed on target of each location +++@end itemize +++ +++@smallexample +++(@value{GDBP}) @b{info trace} +++Num Type Disp Enb Address What +++1 tracepoint keep y 0x0804ab57 in foo() at main.cxx:7 +++ while-stepping 20 +++ collect globfoo, $regs +++ end +++ collect globfoo2 +++ end +++ pass count 1200 +++2 tracepoint keep y +++ collect $eip +++2.1 y 0x0804859c in func4 at change-loc.h:35 +++ installed on target +++2.2 y 0xb7ffc480 in func4 at change-loc.h:35 +++ installed on target +++2.3 y set_tracepoint +++3 tracepoint keep y 0x080485b1 in foo at change-loc.c:29 +++ not installed on target +++(@value{GDBP}) +++@end smallexample +++ +++@noindent +++This command can be abbreviated @code{info tp}. +++@end table +++ +++@node Listing Static Tracepoint Markers +++@subsection Listing Static Tracepoint Markers +++ +++@table @code +++@kindex info static-tracepoint-markers +++@cindex information about static tracepoint markers +++@item info static-tracepoint-markers +++Display information about all static tracepoint markers defined in the +++program. +++ +++For each marker, the following columns are printed: +++ +++@table @emph +++@item Count +++An incrementing counter, output to help readability. This is not a +++stable identifier. +++@item ID +++The marker ID, as reported by the target. +++@item Enabled or Disabled +++Probed markers are tagged with @samp{y}. @samp{n} identifies marks +++that are not enabled. +++@item Address +++Where the marker is in your program, as a memory address. +++@item What +++Where the marker is in the source for your program, as a file and line +++number. If the debug information included in the program does not +++allow @value{GDBN} to locate the source of the marker, this column +++will be left blank. +++@end table +++ +++@noindent +++In addition, the following information may be printed for each marker: +++ +++@table @emph +++@item Data +++User data passed to the tracing library by the marker call. In the +++UST backend, this is the format string passed as argument to the +++marker call. +++@item Static tracepoints probing the marker +++The list of static tracepoints attached to the marker. +++@end table +++ +++@smallexample +++(@value{GDBP}) info static-tracepoint-markers +++Cnt ID Enb Address What +++1 ust/bar2 y 0x0000000000400e1a in main at stexample.c:25 +++ Data: number1 %d number2 %d +++ Probed by static tracepoints: #2 +++2 ust/bar33 n 0x0000000000400c87 in main at stexample.c:24 +++ Data: str %s +++(@value{GDBP}) +++@end smallexample +++@end table +++ +++@node Starting and Stopping Trace Experiments +++@subsection Starting and Stopping Trace Experiments +++ +++@table @code +++@kindex tstart [ @var{notes} ] +++@cindex start a new trace experiment +++@cindex collected data discarded +++@item tstart +++This command starts the trace experiment, and begins collecting data. +++It has the side effect of discarding all the data collected in the +++trace buffer during the previous trace experiment. If any arguments +++are supplied, they are taken as a note and stored with the trace +++experiment's state. The notes may be arbitrary text, and are +++especially useful with disconnected tracing in a multi-user context; +++the notes can explain what the trace is doing, supply user contact +++information, and so forth. +++ +++@kindex tstop [ @var{notes} ] +++@cindex stop a running trace experiment +++@item tstop +++This command stops the trace experiment. If any arguments are +++supplied, they are recorded with the experiment as a note. This is +++useful if you are stopping a trace started by someone else, for +++instance if the trace is interfering with the system's behavior and +++needs to be stopped quickly. +++ +++@strong{Note}: a trace experiment and data collection may stop +++automatically if any tracepoint's passcount is reached +++(@pxref{Tracepoint Passcounts}), or if the trace buffer becomes full. +++ +++@kindex tstatus +++@cindex status of trace data collection +++@cindex trace experiment, status of +++@item tstatus +++This command displays the status of the current trace data +++collection. +++@end table +++ +++Here is an example of the commands we described so far: +++ +++@smallexample +++(@value{GDBP}) @b{trace gdb_c_test} +++(@value{GDBP}) @b{actions} +++Enter actions for tracepoint #1, one per line. +++> collect $regs,$locals,$args +++> while-stepping 11 +++ > collect $regs +++ > end +++> end +++(@value{GDBP}) @b{tstart} +++ [time passes @dots{}] +++(@value{GDBP}) @b{tstop} +++@end smallexample +++ +++@anchor{disconnected tracing} +++@cindex disconnected tracing +++You can choose to continue running the trace experiment even if +++@value{GDBN} disconnects from the target, voluntarily or +++involuntarily. For commands such as @code{detach}, the debugger will +++ask what you want to do with the trace. But for unexpected +++terminations (@value{GDBN} crash, network outage), it would be +++unfortunate to lose hard-won trace data, so the variable +++@code{disconnected-tracing} lets you decide whether the trace should +++continue running without @value{GDBN}. +++ +++@table @code +++@item set disconnected-tracing on +++@itemx set disconnected-tracing off +++@kindex set disconnected-tracing +++Choose whether a tracing run should continue to run if @value{GDBN} +++has disconnected from the target. Note that @code{detach} or +++@code{quit} will ask you directly what to do about a running trace no +++matter what this variable's setting, so the variable is mainly useful +++for handling unexpected situations, such as loss of the network. +++ +++@item show disconnected-tracing +++@kindex show disconnected-tracing +++Show the current choice for disconnected tracing. +++ +++@end table +++ +++When you reconnect to the target, the trace experiment may or may not +++still be running; it might have filled the trace buffer in the +++meantime, or stopped for one of the other reasons. If it is running, +++it will continue after reconnection. +++ +++Upon reconnection, the target will upload information about the +++tracepoints in effect. @value{GDBN} will then compare that +++information to the set of tracepoints currently defined, and attempt +++to match them up, allowing for the possibility that the numbers may +++have changed due to creation and deletion in the meantime. If one of +++the target's tracepoints does not match any in @value{GDBN}, the +++debugger will create a new tracepoint, so that you have a number with +++which to specify that tracepoint. This matching-up process is +++necessarily heuristic, and it may result in useless tracepoints being +++created; you may simply delete them if they are of no use. +++ +++@cindex circular trace buffer +++If your target agent supports a @dfn{circular trace buffer}, then you +++can run a trace experiment indefinitely without filling the trace +++buffer; when space runs out, the agent deletes already-collected trace +++frames, oldest first, until there is enough room to continue +++collecting. This is especially useful if your tracepoints are being +++hit too often, and your trace gets terminated prematurely because the +++buffer is full. To ask for a circular trace buffer, simply set +++@samp{circular-trace-buffer} to on. You can set this at any time, +++including during tracing; if the agent can do it, it will change +++buffer handling on the fly, otherwise it will not take effect until +++the next run. +++ +++@table @code +++@item set circular-trace-buffer on +++@itemx set circular-trace-buffer off +++@kindex set circular-trace-buffer +++Choose whether a tracing run should use a linear or circular buffer +++for trace data. A linear buffer will not lose any trace data, but may +++fill up prematurely, while a circular buffer will discard old trace +++data, but it will have always room for the latest tracepoint hits. +++ +++@item show circular-trace-buffer +++@kindex show circular-trace-buffer +++Show the current choice for the trace buffer. Note that this may not +++match the agent's current buffer handling, nor is it guaranteed to +++match the setting that might have been in effect during a past run, +++for instance if you are looking at frames from a trace file. +++ +++@end table +++ +++@table @code +++@item set trace-buffer-size @var{n} +++@itemx set trace-buffer-size unlimited +++@kindex set trace-buffer-size +++Request that the target use a trace buffer of @var{n} bytes. Not all +++targets will honor the request; they may have a compiled-in size for +++the trace buffer, or some other limitation. Set to a value of +++@code{unlimited} or @code{-1} to let the target use whatever size it +++likes. This is also the default. +++ +++@item show trace-buffer-size +++@kindex show trace-buffer-size +++Show the current requested size for the trace buffer. Note that this +++will only match the actual size if the target supports size-setting, +++and was able to handle the requested size. For instance, if the +++target can only change buffer size between runs, this variable will +++not reflect the change until the next run starts. Use @code{tstatus} +++to get a report of the actual buffer size. +++@end table +++ +++@table @code +++@item set trace-user @var{text} +++@kindex set trace-user +++ +++@item show trace-user +++@kindex show trace-user +++ +++@item set trace-notes @var{text} +++@kindex set trace-notes +++Set the trace run's notes. +++ +++@item show trace-notes +++@kindex show trace-notes +++Show the trace run's notes. +++ +++@item set trace-stop-notes @var{text} +++@kindex set trace-stop-notes +++Set the trace run's stop notes. The handling of the note is as for +++@code{tstop} arguments; the set command is convenient way to fix a +++stop note that is mistaken or incomplete. +++ +++@item show trace-stop-notes +++@kindex show trace-stop-notes +++Show the trace run's stop notes. +++ +++@end table +++ +++@node Tracepoint Restrictions +++@subsection Tracepoint Restrictions +++ +++@cindex tracepoint restrictions +++There are a number of restrictions on the use of tracepoints. As +++described above, tracepoint data gathering occurs on the target +++without interaction from @value{GDBN}. Thus the full capabilities of +++the debugger are not available during data gathering, and then at data +++examination time, you will be limited by only having what was +++collected. The following items describe some common problems, but it +++is not exhaustive, and you may run into additional difficulties not +++mentioned here. +++ +++@itemize @bullet +++ +++@item +++Tracepoint expressions are intended to gather objects (lvalues). Thus +++the full flexibility of GDB's expression evaluator is not available. +++You cannot call functions, cast objects to aggregate types, access +++convenience variables or modify values (except by assignment to trace +++state variables). Some language features may implicitly call +++functions (for instance Objective-C fields with accessors), and therefore +++cannot be collected either. +++ +++@item +++Collection of local variables, either individually or in bulk with +++@code{$locals} or @code{$args}, during @code{while-stepping} may +++behave erratically. The stepping action may enter a new scope (for +++instance by stepping into a function), or the location of the variable +++may change (for instance it is loaded into a register). The +++tracepoint data recorded uses the location information for the +++variables that is correct for the tracepoint location. When the +++tracepoint is created, it is not possible, in general, to determine +++where the steps of a @code{while-stepping} sequence will advance the +++program---particularly if a conditional branch is stepped. +++ +++@item +++Collection of an incompletely-initialized or partially-destroyed object +++may result in something that @value{GDBN} cannot display, or displays +++in a misleading way. +++ +++@item +++When @value{GDBN} displays a pointer to character it automatically +++dereferences the pointer to also display characters of the string +++being pointed to. However, collecting the pointer during tracing does +++not automatically collect the string. You need to explicitly +++dereference the pointer and provide size information if you want to +++collect not only the pointer, but the memory pointed to. For example, +++@code{*ptr@@50} can be used to collect the 50 element array pointed to +++by @code{ptr}. +++ +++@item +++It is not possible to collect a complete stack backtrace at a +++tracepoint. Instead, you may collect the registers and a few hundred +++bytes from the stack pointer with something like @code{*(unsigned char *)$esp@@300} +++(adjust to use the name of the actual stack pointer register on your +++target architecture, and the amount of stack you wish to capture). +++Then the @code{backtrace} command will show a partial backtrace when +++using a trace frame. The number of stack frames that can be examined +++depends on the sizes of the frames in the collected stack. Note that +++if you ask for a block so large that it goes past the bottom of the +++stack, the target agent may report an error trying to read from an +++invalid address. +++ +++@item +++If you do not collect registers at a tracepoint, @value{GDBN} can +++infer that the value of @code{$pc} must be the same as the address of +++the tracepoint and use that when you are looking at a trace frame +++for that tracepoint. However, this cannot work if the tracepoint has +++multiple locations (for instance if it was set in a function that was +++inlined), or if it has a @code{while-stepping} loop. In those cases +++@value{GDBN} will warn you that it can't infer @code{$pc}, and default +++it to zero. +++ +++@end itemize +++ +++@node Analyze Collected Data +++@section Using the Collected Data +++ +++After the tracepoint experiment ends, you use @value{GDBN} commands +++for examining the trace data. The basic idea is that each tracepoint +++collects a trace @dfn{snapshot} every time it is hit and another +++snapshot every time it single-steps. All these snapshots are +++consecutively numbered from zero and go into a buffer, and you can +++examine them later. The way you examine them is to @dfn{focus} on a +++specific trace snapshot. When the remote stub is focused on a trace +++snapshot, it will respond to all @value{GDBN} requests for memory and +++registers by reading from the buffer which belongs to that snapshot, +++rather than from @emph{real} memory or registers of the program being +++debugged. This means that @strong{all} @value{GDBN} commands +++(@code{print}, @code{info registers}, @code{backtrace}, etc.) will +++behave as if we were currently debugging the program state as it was +++when the tracepoint occurred. Any requests for data that are not in +++the buffer will fail. +++ +++@menu +++* tfind:: How to select a trace snapshot +++* tdump:: How to display all data for a snapshot +++* save tracepoints:: How to save tracepoints for a future run +++@end menu +++ +++@node tfind +++@subsection @code{tfind @var{n}} +++ +++@kindex tfind +++@cindex select trace snapshot +++@cindex find trace snapshot +++The basic command for selecting a trace snapshot from the buffer is +++@code{tfind @var{n}}, which finds trace snapshot number @var{n}, +++counting from zero. If no argument @var{n} is given, the next +++snapshot is selected. +++ +++Here are the various forms of using the @code{tfind} command. +++ +++@table @code +++@item tfind start +++Find the first snapshot in the buffer. This is a synonym for +++@code{tfind 0} (since 0 is the number of the first snapshot). +++ +++@item tfind none +++Stop debugging trace snapshots, resume @emph{live} debugging. +++ +++@item tfind end +++Same as @samp{tfind none}. +++ +++@item tfind +++No argument means find the next trace snapshot or find the first +++one if no trace snapshot is selected. +++ +++@item tfind - +++Find the previous trace snapshot before the current one. This permits +++retracing earlier steps. +++ +++@item tfind tracepoint @var{num} +++Find the next snapshot associated with tracepoint @var{num}. Search +++proceeds forward from the last examined trace snapshot. If no +++argument @var{num} is given, it means find the next snapshot collected +++for the same tracepoint as the current snapshot. +++ +++@item tfind pc @var{addr} +++Find the next snapshot associated with the value @var{addr} of the +++program counter. Search proceeds forward from the last examined trace +++snapshot. If no argument @var{addr} is given, it means find the next +++snapshot with the same value of PC as the current snapshot. +++ +++@item tfind outside @var{addr1}, @var{addr2} +++Find the next snapshot whose PC is outside the given range of +++addresses (exclusive). +++ +++@item tfind range @var{addr1}, @var{addr2} +++Find the next snapshot whose PC is between @var{addr1} and +++@var{addr2} (inclusive). +++ +++@item tfind line @r{[}@var{file}:@r{]}@var{n} +++Find the next snapshot associated with the source line @var{n}. If +++the optional argument @var{file} is given, refer to line @var{n} in +++that source file. Search proceeds forward from the last examined +++trace snapshot. If no argument @var{n} is given, it means find the +++next line other than the one currently being examined; thus saying +++@code{tfind line} repeatedly can appear to have the same effect as +++stepping from line to line in a @emph{live} debugging session. +++@end table +++ +++The default arguments for the @code{tfind} commands are specifically +++designed to make it easy to scan through the trace buffer. For +++instance, @code{tfind} with no argument selects the next trace +++snapshot, and @code{tfind -} with no argument selects the previous +++trace snapshot. So, by giving one @code{tfind} command, and then +++simply hitting @key{RET} repeatedly you can examine all the trace +++snapshots in order. Or, by saying @code{tfind -} and then hitting +++@key{RET} repeatedly you can examine the snapshots in reverse order. +++The @code{tfind line} command with no argument selects the snapshot +++for the next source line executed. The @code{tfind pc} command with +++no argument selects the next snapshot with the same program counter +++(PC) as the current frame. The @code{tfind tracepoint} command with +++no argument selects the next trace snapshot collected by the same +++tracepoint as the current one. +++ +++In addition to letting you scan through the trace buffer manually, +++these commands make it easy to construct @value{GDBN} scripts that +++scan through the trace buffer and print out whatever collected data +++you are interested in. Thus, if we want to examine the PC, FP, and SP +++registers from each trace frame in the buffer, we can say this: +++ +++@smallexample +++(@value{GDBP}) @b{tfind start} +++(@value{GDBP}) @b{while ($trace_frame != -1)} +++> printf "Frame %d, PC = %08X, SP = %08X, FP = %08X\n", \ +++ $trace_frame, $pc, $sp, $fp +++> tfind +++> end +++ +++Frame 0, PC = 0020DC64, SP = 0030BF3C, FP = 0030BF44 +++Frame 1, PC = 0020DC6C, SP = 0030BF38, FP = 0030BF44 +++Frame 2, PC = 0020DC70, SP = 0030BF34, FP = 0030BF44 +++Frame 3, PC = 0020DC74, SP = 0030BF30, FP = 0030BF44 +++Frame 4, PC = 0020DC78, SP = 0030BF2C, FP = 0030BF44 +++Frame 5, PC = 0020DC7C, SP = 0030BF28, FP = 0030BF44 +++Frame 6, PC = 0020DC80, SP = 0030BF24, FP = 0030BF44 +++Frame 7, PC = 0020DC84, SP = 0030BF20, FP = 0030BF44 +++Frame 8, PC = 0020DC88, SP = 0030BF1C, FP = 0030BF44 +++Frame 9, PC = 0020DC8E, SP = 0030BF18, FP = 0030BF44 +++Frame 10, PC = 00203F6C, SP = 0030BE3C, FP = 0030BF14 +++@end smallexample +++ +++Or, if we want to examine the variable @code{X} at each source line in +++the buffer: +++ +++@smallexample +++(@value{GDBP}) @b{tfind start} +++(@value{GDBP}) @b{while ($trace_frame != -1)} +++> printf "Frame %d, X == %d\n", $trace_frame, X +++> tfind line +++> end +++ +++Frame 0, X = 1 +++Frame 7, X = 2 +++Frame 13, X = 255 +++@end smallexample +++ +++@node tdump +++@subsection @code{tdump} +++@kindex tdump +++@cindex dump all data collected at tracepoint +++@cindex tracepoint data, display +++ +++This command takes no arguments. It prints all the data collected at +++the current trace snapshot. +++ +++@smallexample +++(@value{GDBP}) @b{trace 444} +++(@value{GDBP}) @b{actions} +++Enter actions for tracepoint #2, one per line: +++> collect $regs, $locals, $args, gdb_long_test +++> end +++ +++(@value{GDBP}) @b{tstart} +++ +++(@value{GDBP}) @b{tfind line 444} +++#0 gdb_test (p1=0x11, p2=0x22, p3=0x33, p4=0x44, p5=0x55, p6=0x66) +++at gdb_test.c:444 +++444 printp( "%s: arguments = 0x%X 0x%X 0x%X 0x%X 0x%X 0x%X\n", ) +++ +++(@value{GDBP}) @b{tdump} +++Data collected at tracepoint 2, trace frame 1: +++d0 0xc4aa0085 -995491707 +++d1 0x18 24 +++d2 0x80 128 +++d3 0x33 51 +++d4 0x71aea3d 119204413 +++d5 0x22 34 +++d6 0xe0 224 +++d7 0x380035 3670069 +++a0 0x19e24a 1696330 +++a1 0x3000668 50333288 +++a2 0x100 256 +++a3 0x322000 3284992 +++a4 0x3000698 50333336 +++a5 0x1ad3cc 1758156 +++fp 0x30bf3c 0x30bf3c +++sp 0x30bf34 0x30bf34 +++ps 0x0 0 +++pc 0x20b2c8 0x20b2c8 +++fpcontrol 0x0 0 +++fpstatus 0x0 0 +++fpiaddr 0x0 0 +++p = 0x20e5b4 "gdb-test" +++p1 = (void *) 0x11 +++p2 = (void *) 0x22 +++p3 = (void *) 0x33 +++p4 = (void *) 0x44 +++p5 = (void *) 0x55 +++p6 = (void *) 0x66 +++gdb_long_test = 17 '\021' +++ +++(@value{GDBP}) +++@end smallexample +++ +++@code{tdump} works by scanning the tracepoint's current collection +++actions and printing the value of each expression listed. So +++@code{tdump} can fail, if after a run, you change the tracepoint's +++actions to mention variables that were not collected during the run. +++ +++Also, for tracepoints with @code{while-stepping} loops, @code{tdump} +++uses the collected value of @code{$pc} to distinguish between trace +++frames that were collected at the tracepoint hit, and frames that were +++collected while stepping. This allows it to correctly choose whether +++to display the basic list of collections, or the collections from the +++body of the while-stepping loop. However, if @code{$pc} was not collected, +++then @code{tdump} will always attempt to dump using the basic collection +++list, and may fail if a while-stepping frame does not include all the +++same data that is collected at the tracepoint hit. +++@c This is getting pretty arcane, example would be good. +++ +++@node save tracepoints +++@subsection @code{save tracepoints @var{filename}} +++@kindex save tracepoints +++@kindex save-tracepoints +++@cindex save tracepoints for future sessions +++ +++This command saves all current tracepoint definitions together with +++their actions and passcounts, into a file @file{@var{filename}} +++suitable for use in a later debugging session. To read the saved +++tracepoint definitions, use the @code{source} command (@pxref{Command +++Files}). The @w{@code{save-tracepoints}} command is a deprecated +++alias for @w{@code{save tracepoints}} +++ +++@node Tracepoint Variables +++@section Convenience Variables for Tracepoints +++@cindex tracepoint variables +++@cindex convenience variables for tracepoints +++ +++@table @code +++@vindex $trace_frame +++@item (int) $trace_frame +++The current trace snapshot (a.k.a.@: @dfn{frame}) number, or -1 if no +++snapshot is selected. +++ +++@vindex $tracepoint +++@item (int) $tracepoint +++The tracepoint for the current trace snapshot. +++ +++@vindex $trace_line +++@item (int) $trace_line +++The line number for the current trace snapshot. +++ +++@vindex $trace_file +++@item (char []) $trace_file +++The source file for the current trace snapshot. +++ +++@vindex $trace_func +++@item (char []) $trace_func +++The name of the function containing @code{$tracepoint}. +++@end table +++ +++Note: @code{$trace_file} is not suitable for use in @code{printf}, +++use @code{output} instead. +++ +++Here's a simple example of using these convenience variables for +++stepping through all the trace snapshots and printing some of their +++data. Note that these are not the same as trace state variables, +++which are managed by the target. +++ +++@smallexample +++(@value{GDBP}) @b{tfind start} +++ +++(@value{GDBP}) @b{while $trace_frame != -1} +++> output $trace_file +++> printf ", line %d (tracepoint #%d)\n", $trace_line, $tracepoint +++> tfind +++> end +++@end smallexample +++ +++@node Trace Files +++@section Using Trace Files +++@cindex trace files +++ +++In some situations, the target running a trace experiment may no +++longer be available; perhaps it crashed, or the hardware was needed +++for a different activity. To handle these cases, you can arrange to +++dump the trace data into a file, and later use that file as a source +++of trace data, via the @code{target tfile} command. +++ +++@table @code +++ +++@kindex tsave +++@item tsave [ -r ] @var{filename} +++@itemx tsave [-ctf] @var{dirname} +++Save the trace data to @var{filename}. By default, this command +++assumes that @var{filename} refers to the host filesystem, so if +++necessary @value{GDBN} will copy raw trace data up from the target and +++then save it. If the target supports it, you can also supply the +++optional argument @code{-r} (``remote'') to direct the target to save +++the data directly into @var{filename} in its own filesystem, which may be +++more efficient if the trace buffer is very large. (Note, however, that +++@code{target tfile} can only read from files accessible to the host.) +++By default, this command will save trace frame in tfile format. +++You can supply the optional argument @code{-ctf} to save data in CTF +++format. The @dfn{Common Trace Format} (CTF) is proposed as a trace format +++that can be shared by multiple debugging and tracing tools. Please go to +++@indicateurl{http://www.efficios.com/ctf} to get more information. +++ +++@kindex target tfile +++@kindex tfile +++@kindex target ctf +++@kindex ctf +++@item target tfile @var{filename} +++@itemx target ctf @var{dirname} +++Use the file named @var{filename} or directory named @var{dirname} as +++a source of trace data. Commands that examine data work as they do with +++a live target, but it is not possible to run any new trace experiments. +++@code{tstatus} will report the state of the trace run at the moment +++the data was saved, as well as the current trace frame you are examining. +++Both @var{filename} and @var{dirname} must be on a filesystem accessible to +++the host. +++ +++@smallexample +++(@value{GDBP}) target ctf ctf.ctf +++(@value{GDBP}) tfind +++Found trace frame 0, tracepoint 2 +++39 ++a; /* set tracepoint 1 here */ +++(@value{GDBP}) tdump +++Data collected at tracepoint 2, trace frame 0: +++i = 0 +++a = 0 +++b = 1 '\001' +++c = @{"123", "456", "789", "123", "456", "789"@} +++d = @{@{@{a = 1, b = 2@}, @{a = 3, b = 4@}@}, @{@{a = 5, b = 6@}, @{a = 7, b = 8@}@}@} +++(@value{GDBP}) p b +++$1 = 1 +++@end smallexample +++ +++@end table +++ +++@node Overlays +++@chapter Debugging Programs That Use Overlays +++@cindex overlays +++ +++If your program is too large to fit completely in your target system's +++memory, you can sometimes use @dfn{overlays} to work around this +++problem. @value{GDBN} provides some support for debugging programs that +++use overlays. +++ +++@menu +++* How Overlays Work:: A general explanation of overlays. +++* Overlay Commands:: Managing overlays in @value{GDBN}. +++* Automatic Overlay Debugging:: @value{GDBN} can find out which overlays are +++ mapped by asking the inferior. +++* Overlay Sample Program:: A sample program using overlays. +++@end menu +++ +++@node How Overlays Work +++@section How Overlays Work +++@cindex mapped overlays +++@cindex unmapped overlays +++@cindex load address, overlay's +++@cindex mapped address +++@cindex overlay area +++ +++Suppose you have a computer whose instruction address space is only 64 +++kilobytes long, but which has much more memory which can be accessed by +++other means: special instructions, segment registers, or memory +++management hardware, for example. Suppose further that you want to +++adapt a program which is larger than 64 kilobytes to run on this system. +++ +++One solution is to identify modules of your program which are relatively +++independent, and need not call each other directly; call these modules +++@dfn{overlays}. Separate the overlays from the main program, and place +++their machine code in the larger memory. Place your main program in +++instruction memory, but leave at least enough space there to hold the +++largest overlay as well. +++ +++Now, to call a function located in an overlay, you must first copy that +++overlay's machine code from the large memory into the space set aside +++for it in the instruction memory, and then jump to its entry point +++there. +++ +++@c NB: In the below the mapped area's size is greater or equal to the +++@c size of all overlays. This is intentional to remind the developer +++@c that overlays don't necessarily need to be the same size. +++ +++@smallexample +++@group +++ Data Instruction Larger +++Address Space Address Space Address Space ++++-----------+ +-----------+ +-----------+ +++| | | | | | ++++-----------+ +-----------+ +-----------+<-- overlay 1 +++| program | | main | .----| overlay 1 | load address +++| variables | | program | | +-----------+ +++| and heap | | | | | | ++++-----------+ | | | +-----------+<-- overlay 2 +++| | +-----------+ | | | load address ++++-----------+ | | | .-| overlay 2 | +++ | | | | | | +++ mapped --->+-----------+ | | +-----------+ +++ address | | | | | | +++ | overlay | <-' | | | +++ | area | <---' +-----------+<-- overlay 3 +++ | | <---. | | load address +++ +-----------+ `--| overlay 3 | +++ | | | | +++ +-----------+ | | +++ +-----------+ +++ | | +++ +-----------+ +++ +++ @anchor{A code overlay}A code overlay +++@end group +++@end smallexample +++ +++The diagram (@pxref{A code overlay}) shows a system with separate data +++and instruction address spaces. To map an overlay, the program copies +++its code from the larger address space to the instruction address space. +++Since the overlays shown here all use the same mapped address, only one +++may be mapped at a time. For a system with a single address space for +++data and instructions, the diagram would be similar, except that the +++program variables and heap would share an address space with the main +++program and the overlay area. +++ +++An overlay loaded into instruction memory and ready for use is called a +++@dfn{mapped} overlay; its @dfn{mapped address} is its address in the +++instruction memory. An overlay not present (or only partially present) +++in instruction memory is called @dfn{unmapped}; its @dfn{load address} +++is its address in the larger memory. The mapped address is also called +++the @dfn{virtual memory address}, or @dfn{VMA}; the load address is also +++called the @dfn{load memory address}, or @dfn{LMA}. +++ +++Unfortunately, overlays are not a completely transparent way to adapt a +++program to limited instruction memory. They introduce a new set of +++global constraints you must keep in mind as you design your program: +++ +++@itemize @bullet +++ +++@item +++Before calling or returning to a function in an overlay, your program +++must make sure that overlay is actually mapped. Otherwise, the call or +++return will transfer control to the right address, but in the wrong +++overlay, and your program will probably crash. +++ +++@item +++If the process of mapping an overlay is expensive on your system, you +++will need to choose your overlays carefully to minimize their effect on +++your program's performance. +++ +++@item +++The executable file you load onto your system must contain each +++overlay's instructions, appearing at the overlay's load address, not its +++mapped address. However, each overlay's instructions must be relocated +++and its symbols defined as if the overlay were at its mapped address. +++You can use GNU linker scripts to specify different load and relocation +++addresses for pieces of your program; see @ref{Overlay Description,,, +++ld.info, Using ld: the GNU linker}. +++ +++@item +++The procedure for loading executable files onto your system must be able +++to load their contents into the larger address space as well as the +++instruction and data spaces. +++ +++@end itemize +++ +++The overlay system described above is rather simple, and could be +++improved in many ways: +++ +++@itemize @bullet +++ +++@item +++If your system has suitable bank switch registers or memory management +++hardware, you could use those facilities to make an overlay's load area +++contents simply appear at their mapped address in instruction space. +++This would probably be faster than copying the overlay to its mapped +++area in the usual way. +++ +++@item +++If your overlays are small enough, you could set aside more than one +++overlay area, and have more than one overlay mapped at a time. +++ +++@item +++You can use overlays to manage data, as well as instructions. In +++general, data overlays are even less transparent to your design than +++code overlays: whereas code overlays only require care when you call or +++return to functions, data overlays require care every time you access +++the data. Also, if you change the contents of a data overlay, you +++must copy its contents back out to its load address before you can copy a +++different data overlay into the same mapped area. +++ +++@end itemize +++ +++ +++@node Overlay Commands +++@section Overlay Commands +++ +++To use @value{GDBN}'s overlay support, each overlay in your program must +++correspond to a separate section of the executable file. The section's +++virtual memory address and load memory address must be the overlay's +++mapped and load addresses. Identifying overlays with sections allows +++@value{GDBN} to determine the appropriate address of a function or +++variable, depending on whether the overlay is mapped or not. +++ +++@value{GDBN}'s overlay commands all start with the word @code{overlay}; +++you can abbreviate this as @code{ov} or @code{ovly}. The commands are: +++ +++@table @code +++@item overlay off +++@kindex overlay +++Disable @value{GDBN}'s overlay support. When overlay support is +++disabled, @value{GDBN} assumes that all functions and variables are +++always present at their mapped addresses. By default, @value{GDBN}'s +++overlay support is disabled. +++ +++@item overlay manual +++@cindex manual overlay debugging +++Enable @dfn{manual} overlay debugging. In this mode, @value{GDBN} +++relies on you to tell it which overlays are mapped, and which are not, +++using the @code{overlay map-overlay} and @code{overlay unmap-overlay} +++commands described below. +++ +++@item overlay map-overlay @var{overlay} +++@itemx overlay map @var{overlay} +++@cindex map an overlay +++Tell @value{GDBN} that @var{overlay} is now mapped; @var{overlay} must +++be the name of the object file section containing the overlay. When an +++overlay is mapped, @value{GDBN} assumes it can find the overlay's +++functions and variables at their mapped addresses. @value{GDBN} assumes +++that any other overlays whose mapped ranges overlap that of +++@var{overlay} are now unmapped. +++ +++@item overlay unmap-overlay @var{overlay} +++@itemx overlay unmap @var{overlay} +++@cindex unmap an overlay +++Tell @value{GDBN} that @var{overlay} is no longer mapped; @var{overlay} +++must be the name of the object file section containing the overlay. +++When an overlay is unmapped, @value{GDBN} assumes it can find the +++overlay's functions and variables at their load addresses. +++ +++@item overlay auto +++Enable @dfn{automatic} overlay debugging. In this mode, @value{GDBN} +++consults a data structure the overlay manager maintains in the inferior +++to see which overlays are mapped. For details, see @ref{Automatic +++Overlay Debugging}. +++ +++@item overlay load-target +++@itemx overlay load +++@cindex reloading the overlay table +++Re-read the overlay table from the inferior. Normally, @value{GDBN} +++re-reads the table @value{GDBN} automatically each time the inferior +++stops, so this command should only be necessary if you have changed the +++overlay mapping yourself using @value{GDBN}. This command is only +++useful when using automatic overlay debugging. +++ +++@item overlay list-overlays +++@itemx overlay list +++@cindex listing mapped overlays +++Display a list of the overlays currently mapped, along with their mapped +++addresses, load addresses, and sizes. +++ +++@end table +++ +++Normally, when @value{GDBN} prints a code address, it includes the name +++of the function the address falls in: +++ +++@smallexample +++(@value{GDBP}) print main +++$3 = @{int ()@} 0x11a0
+++@end smallexample +++@noindent +++When overlay debugging is enabled, @value{GDBN} recognizes code in +++unmapped overlays, and prints the names of unmapped functions with +++asterisks around them. For example, if @code{foo} is a function in an +++unmapped overlay, @value{GDBN} prints it this way: +++ +++@smallexample +++(@value{GDBP}) overlay list +++No sections are mapped. +++(@value{GDBP}) print foo +++$5 = @{int (int)@} 0x100000 <*foo*> +++@end smallexample +++@noindent +++When @code{foo}'s overlay is mapped, @value{GDBN} prints the function's +++name normally: +++ +++@smallexample +++(@value{GDBP}) overlay list +++Section .ov.foo.text, loaded at 0x100000 - 0x100034, +++ mapped at 0x1016 - 0x104a +++(@value{GDBP}) print foo +++$6 = @{int (int)@} 0x1016 +++@end smallexample +++ +++When overlay debugging is enabled, @value{GDBN} can find the correct +++address for functions and variables in an overlay, whether or not the +++overlay is mapped. This allows most @value{GDBN} commands, like +++@code{break} and @code{disassemble}, to work normally, even on unmapped +++code. However, @value{GDBN}'s breakpoint support has some limitations: +++ +++@itemize @bullet +++@item +++@cindex breakpoints in overlays +++@cindex overlays, setting breakpoints in +++You can set breakpoints in functions in unmapped overlays, as long as +++@value{GDBN} can write to the overlay at its load address. +++@item +++@value{GDBN} can not set hardware or simulator-based breakpoints in +++unmapped overlays. However, if you set a breakpoint at the end of your +++overlay manager (and tell @value{GDBN} which overlays are now mapped, if +++you are using manual overlay management), @value{GDBN} will re-set its +++breakpoints properly. +++@end itemize +++ +++ +++@node Automatic Overlay Debugging +++@section Automatic Overlay Debugging +++@cindex automatic overlay debugging +++ +++@value{GDBN} can automatically track which overlays are mapped and which +++are not, given some simple co-operation from the overlay manager in the +++inferior. If you enable automatic overlay debugging with the +++@code{overlay auto} command (@pxref{Overlay Commands}), @value{GDBN} +++looks in the inferior's memory for certain variables describing the +++current state of the overlays. +++ +++Here are the variables your overlay manager must define to support +++@value{GDBN}'s automatic overlay debugging: +++ +++@table @asis +++ +++@item @code{_ovly_table}: +++This variable must be an array of the following structures: +++ +++@smallexample +++struct +++@{ +++ /* The overlay's mapped address. */ +++ unsigned long vma; +++ +++ /* The size of the overlay, in bytes. */ +++ unsigned long size; +++ +++ /* The overlay's load address. */ +++ unsigned long lma; +++ +++ /* Non-zero if the overlay is currently mapped; +++ zero otherwise. */ +++ unsigned long mapped; +++@} +++@end smallexample +++ +++@item @code{_novlys}: +++This variable must be a four-byte signed integer, holding the total +++number of elements in @code{_ovly_table}. +++ +++@end table +++ +++To decide whether a particular overlay is mapped or not, @value{GDBN} +++looks for an entry in @w{@code{_ovly_table}} whose @code{vma} and +++@code{lma} members equal the VMA and LMA of the overlay's section in the +++executable file. When @value{GDBN} finds a matching entry, it consults +++the entry's @code{mapped} member to determine whether the overlay is +++currently mapped. +++ +++In addition, your overlay manager may define a function called +++@code{_ovly_debug_event}. If this function is defined, @value{GDBN} +++will silently set a breakpoint there. If the overlay manager then +++calls this function whenever it has changed the overlay table, this +++will enable @value{GDBN} to accurately keep track of which overlays +++are in program memory, and update any breakpoints that may be set +++in overlays. This will allow breakpoints to work even if the +++overlays are kept in ROM or other non-writable memory while they +++are not being executed. +++ +++@node Overlay Sample Program +++@section Overlay Sample Program +++@cindex overlay example program +++ +++When linking a program which uses overlays, you must place the overlays +++at their load addresses, while relocating them to run at their mapped +++addresses. To do this, you must write a linker script (@pxref{Overlay +++Description,,, ld.info, Using ld: the GNU linker}). Unfortunately, +++since linker scripts are specific to a particular host system, target +++architecture, and target memory layout, this manual cannot provide +++portable sample code demonstrating @value{GDBN}'s overlay support. +++ +++However, the @value{GDBN} source distribution does contain an overlaid +++program, with linker scripts for a few systems, as part of its test +++suite. The program consists of the following files from +++@file{gdb/testsuite/gdb.base}: +++ +++@table @file +++@item overlays.c +++The main program file. +++@item ovlymgr.c +++A simple overlay manager, used by @file{overlays.c}. +++@item foo.c +++@itemx bar.c +++@itemx baz.c +++@itemx grbx.c +++Overlay modules, loaded and used by @file{overlays.c}. +++@item d10v.ld +++@itemx m32r.ld +++Linker scripts for linking the test program on the @code{d10v-elf} +++and @code{m32r-elf} targets. +++@end table +++ +++You can build the test program using the @code{d10v-elf} GCC +++cross-compiler like this: +++ +++@smallexample +++$ d10v-elf-gcc -g -c overlays.c +++$ d10v-elf-gcc -g -c ovlymgr.c +++$ d10v-elf-gcc -g -c foo.c +++$ d10v-elf-gcc -g -c bar.c +++$ d10v-elf-gcc -g -c baz.c +++$ d10v-elf-gcc -g -c grbx.c +++$ d10v-elf-gcc -g overlays.o ovlymgr.o foo.o bar.o \ +++ baz.o grbx.o -Wl,-Td10v.ld -o overlays +++@end smallexample +++ +++The build process is identical for any other architecture, except that +++you must substitute the appropriate compiler and linker script for the +++target system for @code{d10v-elf-gcc} and @code{d10v.ld}. +++ +++ +++@node Languages +++@chapter Using @value{GDBN} with Different Languages +++@cindex languages +++ +++Although programming languages generally have common aspects, they are +++rarely expressed in the same manner. For instance, in ANSI C, +++dereferencing a pointer @code{p} is accomplished by @code{*p}, but in +++Modula-2, it is accomplished by @code{p^}. Values can also be +++represented (and displayed) differently. Hex numbers in C appear as +++@samp{0x1ae}, while in Modula-2 they appear as @samp{1AEH}. +++ +++@cindex working language +++Language-specific information is built into @value{GDBN} for some languages, +++allowing you to express operations like the above in your program's +++native language, and allowing @value{GDBN} to output values in a manner +++consistent with the syntax of your program's native language. The +++language you use to build expressions is called the @dfn{working +++language}. +++ +++@menu +++* Setting:: Switching between source languages +++* Show:: Displaying the language +++* Checks:: Type and range checks +++* Supported Languages:: Supported languages +++* Unsupported Languages:: Unsupported languages +++@end menu +++ +++@node Setting +++@section Switching Between Source Languages +++ +++There are two ways to control the working language---either have @value{GDBN} +++set it automatically, or select it manually yourself. You can use the +++@code{set language} command for either purpose. On startup, @value{GDBN} +++defaults to setting the language automatically. The working language is +++used to determine how expressions you type are interpreted, how values +++are printed, etc. +++ +++In addition to the working language, every source file that +++@value{GDBN} knows about has its own working language. For some object +++file formats, the compiler might indicate which language a particular +++source file is in. However, most of the time @value{GDBN} infers the +++language from the name of the file. The language of a source file +++controls whether C@t{++} names are demangled---this way @code{backtrace} can +++show each frame appropriately for its own language. There is no way to +++set the language of a source file from within @value{GDBN}, but you can +++set the language associated with a filename extension. @xref{Show, , +++Displaying the Language}. +++ +++This is most commonly a problem when you use a program, such +++as @code{cfront} or @code{f2c}, that generates C but is written in +++another language. In that case, make the +++program use @code{#line} directives in its C output; that way +++@value{GDBN} will know the correct language of the source code of the original +++program, and will display that source code, not the generated C code. +++ +++@menu +++* Filenames:: Filename extensions and languages. +++* Manually:: Setting the working language manually +++* Automatically:: Having @value{GDBN} infer the source language +++@end menu +++ +++@node Filenames +++@subsection List of Filename Extensions and Languages +++ +++If a source file name ends in one of the following extensions, then +++@value{GDBN} infers that its language is the one indicated. +++ +++@table @file +++@item .ada +++@itemx .ads +++@itemx .adb +++@itemx .a +++Ada source file. +++ +++@item .c +++C source file +++ +++@item .C +++@itemx .cc +++@itemx .cp +++@itemx .cpp +++@itemx .cxx +++@itemx .c++ +++C@t{++} source file +++ +++@item .d +++D source file +++ +++@item .m +++Objective-C source file +++ +++@item .f +++@itemx .F +++Fortran source file +++ +++@item .mod +++Modula-2 source file +++ +++@item .s +++@itemx .S +++Assembler source file. This actually behaves almost like C, but +++@value{GDBN} does not skip over function prologues when stepping. +++@end table +++ +++In addition, you may set the language associated with a filename +++extension. @xref{Show, , Displaying the Language}. +++ +++@node Manually +++@subsection Setting the Working Language +++ +++If you allow @value{GDBN} to set the language automatically, +++expressions are interpreted the same way in your debugging session and +++your program. +++ +++@kindex set language +++If you wish, you may set the language manually. To do this, issue the +++command @samp{set language @var{lang}}, where @var{lang} is the name of +++a language, such as +++@code{c} or @code{modula-2}. +++For a list of the supported languages, type @samp{set language}. +++ +++Setting the language manually prevents @value{GDBN} from updating the working +++language automatically. This can lead to confusion if you try +++to debug a program when the working language is not the same as the +++source language, when an expression is acceptable to both +++languages---but means different things. For instance, if the current +++source file were written in C, and @value{GDBN} was parsing Modula-2, a +++command such as: +++ +++@smallexample +++print a = b + c +++@end smallexample +++ +++@noindent +++might not have the effect you intended. In C, this means to add +++@code{b} and @code{c} and place the result in @code{a}. The result +++printed would be the value of @code{a}. In Modula-2, this means to compare +++@code{a} to the result of @code{b+c}, yielding a @code{BOOLEAN} value. +++ +++@node Automatically +++@subsection Having @value{GDBN} Infer the Source Language +++ +++To have @value{GDBN} set the working language automatically, use +++@samp{set language local} or @samp{set language auto}. @value{GDBN} +++then infers the working language. That is, when your program stops in a +++frame (usually by encountering a breakpoint), @value{GDBN} sets the +++working language to the language recorded for the function in that +++frame. If the language for a frame is unknown (that is, if the function +++or block corresponding to the frame was defined in a source file that +++does not have a recognized extension), the current working language is +++not changed, and @value{GDBN} issues a warning. +++ +++This may not seem necessary for most programs, which are written +++entirely in one source language. However, program modules and libraries +++written in one source language can be used by a main program written in +++a different source language. Using @samp{set language auto} in this +++case frees you from having to set the working language manually. +++ +++@node Show +++@section Displaying the Language +++ +++The following commands help you find out which language is the +++working language, and also what language source files were written in. +++ +++@table @code +++@item show language +++@anchor{show language} +++@kindex show language +++Display the current working language. This is the +++language you can use with commands such as @code{print} to +++build and compute expressions that may involve variables in your program. +++ +++@item info frame +++@kindex info frame@r{, show the source language} +++Display the source language for this frame. This language becomes the +++working language if you use an identifier from this frame. +++@xref{Frame Info, ,Information about a Frame}, to identify the other +++information listed here. +++ +++@item info source +++@kindex info source@r{, show the source language} +++Display the source language of this source file. +++@xref{Symbols, ,Examining the Symbol Table}, to identify the other +++information listed here. +++@end table +++ +++In unusual circumstances, you may have source files with extensions +++not in the standard list. You can then set the extension associated +++with a language explicitly: +++ +++@table @code +++@item set extension-language @var{ext} @var{language} +++@kindex set extension-language +++Tell @value{GDBN} that source files with extension @var{ext} are to be +++assumed as written in the source language @var{language}. +++ +++@item info extensions +++@kindex info extensions +++List all the filename extensions and the associated languages. +++@end table +++ +++@node Checks +++@section Type and Range Checking +++ +++Some languages are designed to guard you against making seemingly common +++errors through a series of compile- and run-time checks. These include +++checking the type of arguments to functions and operators and making +++sure mathematical overflows are caught at run time. Checks such as +++these help to ensure a program's correctness once it has been compiled +++by eliminating type mismatches and providing active checks for range +++errors when your program is running. +++ +++By default @value{GDBN} checks for these errors according to the +++rules of the current source language. Although @value{GDBN} does not check +++the statements in your program, it can check expressions entered directly +++into @value{GDBN} for evaluation via the @code{print} command, for example. +++ +++@menu +++* Type Checking:: An overview of type checking +++* Range Checking:: An overview of range checking +++@end menu +++ +++@cindex type checking +++@cindex checks, type +++@node Type Checking +++@subsection An Overview of Type Checking +++ +++Some languages, such as C and C@t{++}, are strongly typed, meaning that the +++arguments to operators and functions have to be of the correct type, +++otherwise an error occurs. These checks prevent type mismatch +++errors from ever causing any run-time problems. For example, +++ +++@smallexample +++int klass::my_method(char *b) @{ return b ? 1 : 2; @} +++ +++(@value{GDBP}) print obj.my_method (0) +++$1 = 2 +++@exdent but +++(@value{GDBP}) print obj.my_method (0x1234) +++Cannot resolve method klass::my_method to any overloaded instance +++@end smallexample +++ +++The second example fails because in C@t{++} the integer constant +++@samp{0x1234} is not type-compatible with the pointer parameter type. +++ +++For the expressions you use in @value{GDBN} commands, you can tell +++@value{GDBN} to not enforce strict type checking or +++to treat any mismatches as errors and abandon the expression; +++When type checking is disabled, @value{GDBN} successfully evaluates +++expressions like the second example above. +++ +++Even if type checking is off, there may be other reasons +++related to type that prevent @value{GDBN} from evaluating an expression. +++For instance, @value{GDBN} does not know how to add an @code{int} and +++a @code{struct foo}. These particular type errors have nothing to do +++with the language in use and usually arise from expressions which make +++little sense to evaluate anyway. +++ +++@value{GDBN} provides some additional commands for controlling type checking: +++ +++@kindex set check type +++@kindex show check type +++@table @code +++@item set check type on +++@itemx set check type off +++Set strict type checking on or off. If any type mismatches occur in +++evaluating an expression while type checking is on, @value{GDBN} prints a +++message and aborts evaluation of the expression. +++ +++@item show check type +++Show the current setting of type checking and whether @value{GDBN} +++is enforcing strict type checking rules. +++@end table +++ +++@cindex range checking +++@cindex checks, range +++@node Range Checking +++@subsection An Overview of Range Checking +++ +++In some languages (such as Modula-2), it is an error to exceed the +++bounds of a type; this is enforced with run-time checks. Such range +++checking is meant to ensure program correctness by making sure +++computations do not overflow, or indices on an array element access do +++not exceed the bounds of the array. +++ +++For expressions you use in @value{GDBN} commands, you can tell +++@value{GDBN} to treat range errors in one of three ways: ignore them, +++always treat them as errors and abandon the expression, or issue +++warnings but evaluate the expression anyway. +++ +++A range error can result from numerical overflow, from exceeding an +++array index bound, or when you type a constant that is not a member +++of any type. Some languages, however, do not treat overflows as an +++error. In many implementations of C, mathematical overflow causes the +++result to ``wrap around'' to lower values---for example, if @var{m} is +++the largest integer value, and @var{s} is the smallest, then +++ +++@smallexample +++@var{m} + 1 @result{} @var{s} +++@end smallexample +++ +++This, too, is specific to individual languages, and in some cases +++specific to individual compilers or machines. @xref{Supported Languages, , +++Supported Languages}, for further details on specific languages. +++ +++@value{GDBN} provides some additional commands for controlling the range checker: +++ +++@kindex set check range +++@kindex show check range +++@table @code +++@item set check range auto +++Set range checking on or off based on the current working language. +++@xref{Supported Languages, ,Supported Languages}, for the default settings for +++each language. +++ +++@item set check range on +++@itemx set check range off +++Set range checking on or off, overriding the default setting for the +++current working language. A warning is issued if the setting does not +++match the language default. If a range error occurs and range checking is on, +++then a message is printed and evaluation of the expression is aborted. +++ +++@item set check range warn +++Output messages when the @value{GDBN} range checker detects a range error, +++but attempt to evaluate the expression anyway. Evaluating the +++expression may still be impossible for other reasons, such as accessing +++memory that the process does not own (a typical example from many Unix +++systems). +++ +++@item show range +++Show the current setting of the range checker, and whether or not it is +++being set automatically by @value{GDBN}. +++@end table +++ +++@node Supported Languages +++@section Supported Languages +++ +++@value{GDBN} supports C, C@t{++}, D, Go, Objective-C, Fortran, +++OpenCL C, Pascal, Rust, assembly, Modula-2, and Ada. +++@c This is false ... +++Some @value{GDBN} features may be used in expressions regardless of the +++language you use: the @value{GDBN} @code{@@} and @code{::} operators, +++and the @samp{@{type@}addr} construct (@pxref{Expressions, +++,Expressions}) can be used with the constructs of any supported +++language. +++ +++The following sections detail to what degree each source language is +++supported by @value{GDBN}. These sections are not meant to be language +++tutorials or references, but serve only as a reference guide to what the +++@value{GDBN} expression parser accepts, and what input and output +++formats should look like for different languages. There are many good +++books written on each of these languages; please look to these for a +++language reference or tutorial. +++ +++@menu +++* C:: C and C@t{++} +++* D:: D +++* Go:: Go +++* Objective-C:: Objective-C +++* OpenCL C:: OpenCL C +++* Fortran:: Fortran +++* Pascal:: Pascal +++* Rust:: Rust +++* Modula-2:: Modula-2 +++* Ada:: Ada +++@end menu +++ +++@node C +++@subsection C and C@t{++} +++ +++@cindex C and C@t{++} +++@cindex expressions in C or C@t{++} +++ +++Since C and C@t{++} are so closely related, many features of @value{GDBN} apply +++to both languages. Whenever this is the case, we discuss those languages +++together. +++ +++@cindex C@t{++} +++@cindex @code{g++}, @sc{gnu} C@t{++} compiler +++@cindex @sc{gnu} C@t{++} +++The C@t{++} debugging facilities are jointly implemented by the C@t{++} +++compiler and @value{GDBN}. Therefore, to debug your C@t{++} code +++effectively, you must compile your C@t{++} programs with a supported +++C@t{++} compiler, such as @sc{gnu} @code{g++}, or the HP ANSI C@t{++} +++compiler (@code{aCC}). +++ +++@menu +++* C Operators:: C and C@t{++} operators +++* C Constants:: C and C@t{++} constants +++* C Plus Plus Expressions:: C@t{++} expressions +++* C Defaults:: Default settings for C and C@t{++} +++* C Checks:: C and C@t{++} type and range checks +++* Debugging C:: @value{GDBN} and C +++* Debugging C Plus Plus:: @value{GDBN} features for C@t{++} +++* Decimal Floating Point:: Numbers in Decimal Floating Point format +++@end menu +++ +++@node C Operators +++@subsubsection C and C@t{++} Operators +++ +++@cindex C and C@t{++} operators +++ +++Operators must be defined on values of specific types. For instance, +++@code{+} is defined on numbers, but not on structures. Operators are +++often defined on groups of types. +++ +++For the purposes of C and C@t{++}, the following definitions hold: +++ +++@itemize @bullet +++ +++@item +++@emph{Integral types} include @code{int} with any of its storage-class +++specifiers; @code{char}; @code{enum}; and, for C@t{++}, @code{bool}. +++ +++@item +++@emph{Floating-point types} include @code{float}, @code{double}, and +++@code{long double} (if supported by the target platform). +++ +++@item +++@emph{Pointer types} include all types defined as @code{(@var{type} *)}. +++ +++@item +++@emph{Scalar types} include all of the above. +++ +++@end itemize +++ +++@noindent +++The following operators are supported. They are listed here +++in order of increasing precedence: +++ +++@table @code +++@item , +++The comma or sequencing operator. Expressions in a comma-separated list +++are evaluated from left to right, with the result of the entire +++expression being the last expression evaluated. +++ +++@item = +++Assignment. The value of an assignment expression is the value +++assigned. Defined on scalar types. +++ +++@item @var{op}= +++Used in an expression of the form @w{@code{@var{a} @var{op}= @var{b}}}, +++and translated to @w{@code{@var{a} = @var{a op b}}}. +++@w{@code{@var{op}=}} and @code{=} have the same precedence. The operator +++@var{op} is any one of the operators @code{|}, @code{^}, @code{&}, +++@code{<<}, @code{>>}, @code{+}, @code{-}, @code{*}, @code{/}, @code{%}. +++ +++@item ?: +++The ternary operator. @code{@var{a} ? @var{b} : @var{c}} can be thought +++of as: if @var{a} then @var{b} else @var{c}. The argument @var{a} +++should be of an integral type. +++ +++@item || +++Logical @sc{or}. Defined on integral types. +++ +++@item && +++Logical @sc{and}. Defined on integral types. +++ +++@item | +++Bitwise @sc{or}. Defined on integral types. +++ +++@item ^ +++Bitwise exclusive-@sc{or}. Defined on integral types. +++ +++@item & +++Bitwise @sc{and}. Defined on integral types. +++ +++@item ==@r{, }!= +++Equality and inequality. Defined on scalar types. The value of these +++expressions is 0 for false and non-zero for true. +++ +++@item <@r{, }>@r{, }<=@r{, }>= +++Less than, greater than, less than or equal, greater than or equal. +++Defined on scalar types. The value of these expressions is 0 for false +++and non-zero for true. +++ +++@item <<@r{, }>> +++left shift, and right shift. Defined on integral types. +++ +++@item @@ +++The @value{GDBN} ``artificial array'' operator (@pxref{Expressions, ,Expressions}). +++ +++@item +@r{, }- +++Addition and subtraction. Defined on integral types, floating-point types and +++pointer types. +++ +++@item *@r{, }/@r{, }% +++Multiplication, division, and modulus. Multiplication and division are +++defined on integral and floating-point types. Modulus is defined on +++integral types. +++ +++@item ++@r{, }-- +++Increment and decrement. When appearing before a variable, the +++operation is performed before the variable is used in an expression; +++when appearing after it, the variable's value is used before the +++operation takes place. +++ +++@item * +++Pointer dereferencing. Defined on pointer types. Same precedence as +++@code{++}. +++ +++@item & +++Address operator. Defined on variables. Same precedence as @code{++}. +++ +++For debugging C@t{++}, @value{GDBN} implements a use of @samp{&} beyond what is +++allowed in the C@t{++} language itself: you can use @samp{&(&@var{ref})} +++to examine the address +++where a C@t{++} reference variable (declared with @samp{&@var{ref}}) is +++stored. +++ +++@item - +++Negative. Defined on integral and floating-point types. Same +++precedence as @code{++}. +++ +++@item ! +++Logical negation. Defined on integral types. Same precedence as +++@code{++}. +++ +++@item ~ +++Bitwise complement operator. Defined on integral types. Same precedence as +++@code{++}. +++ +++ +++@item .@r{, }-> +++Structure member, and pointer-to-structure member. For convenience, +++@value{GDBN} regards the two as equivalent, choosing whether to dereference a +++pointer based on the stored type information. +++Defined on @code{struct} and @code{union} data. +++ +++@item .*@r{, }->* +++Dereferences of pointers to members. +++ +++@item [] +++Array indexing. @code{@var{a}[@var{i}]} is defined as +++@code{*(@var{a}+@var{i})}. Same precedence as @code{->}. +++ +++@item () +++Function parameter list. Same precedence as @code{->}. +++ +++@item :: +++C@t{++} scope resolution operator. Defined on @code{struct}, @code{union}, +++and @code{class} types. +++ +++@item :: +++Doubled colons also represent the @value{GDBN} scope operator +++(@pxref{Expressions, ,Expressions}). Same precedence as @code{::}, +++above. +++@end table +++ +++If an operator is redefined in the user code, @value{GDBN} usually +++attempts to invoke the redefined version instead of using the operator's +++predefined meaning. +++ +++@node C Constants +++@subsubsection C and C@t{++} Constants +++ +++@cindex C and C@t{++} constants +++ +++@value{GDBN} allows you to express the constants of C and C@t{++} in the +++following ways: +++ +++@itemize @bullet +++@item +++Integer constants are a sequence of digits. Octal constants are +++specified by a leading @samp{0} (i.e.@: zero), and hexadecimal constants +++by a leading @samp{0x} or @samp{0X}. Constants may also end with a letter +++@samp{l}, specifying that the constant should be treated as a +++@code{long} value. +++ +++@item +++Floating point constants are a sequence of digits, followed by a decimal +++point, followed by a sequence of digits, and optionally followed by an +++exponent. An exponent is of the form: +++@samp{@w{e@r{[[}+@r{]|}-@r{]}@var{nnn}}}, where @var{nnn} is another +++sequence of digits. The @samp{+} is optional for positive exponents. +++A floating-point constant may also end with a letter @samp{f} or +++@samp{F}, specifying that the constant should be treated as being of +++the @code{float} (as opposed to the default @code{double}) type; or with +++a letter @samp{l} or @samp{L}, which specifies a @code{long double} +++constant. +++ +++@item +++Enumerated constants consist of enumerated identifiers, or their +++integral equivalents. +++ +++@item +++Character constants are a single character surrounded by single quotes +++(@code{'}), or a number---the ordinal value of the corresponding character +++(usually its @sc{ascii} value). Within quotes, the single character may +++be represented by a letter or by @dfn{escape sequences}, which are of +++the form @samp{\@var{nnn}}, where @var{nnn} is the octal representation +++of the character's ordinal value; or of the form @samp{\@var{x}}, where +++@samp{@var{x}} is a predefined special character---for example, +++@samp{\n} for newline. +++ +++Wide character constants can be written by prefixing a character +++constant with @samp{L}, as in C. For example, @samp{L'x'} is the wide +++form of @samp{x}. The target wide character set is used when +++computing the value of this constant (@pxref{Character Sets}). +++ +++@item +++String constants are a sequence of character constants surrounded by +++double quotes (@code{"}). Any valid character constant (as described +++above) may appear. Double quotes within the string must be preceded by +++a backslash, so for instance @samp{"a\"b'c"} is a string of five +++characters. +++ +++Wide string constants can be written by prefixing a string constant +++with @samp{L}, as in C. The target wide character set is used when +++computing the value of this constant (@pxref{Character Sets}). +++ +++@item +++Pointer constants are an integral value. You can also write pointers +++to constants using the C operator @samp{&}. +++ +++@item +++Array constants are comma-separated lists surrounded by braces @samp{@{} +++and @samp{@}}; for example, @samp{@{1,2,3@}} is a three-element array of +++integers, @samp{@{@{1,2@}, @{3,4@}, @{5,6@}@}} is a three-by-two array, +++and @samp{@{&"hi", &"there", &"fred"@}} is a three-element array of pointers. +++@end itemize +++ +++@node C Plus Plus Expressions +++@subsubsection C@t{++} Expressions +++ +++@cindex expressions in C@t{++} +++@value{GDBN} expression handling can interpret most C@t{++} expressions. +++ +++@cindex debugging C@t{++} programs +++@cindex C@t{++} compilers +++@cindex debug formats and C@t{++} +++@cindex @value{NGCC} and C@t{++} +++@quotation +++@emph{Warning:} @value{GDBN} can only debug C@t{++} code if you use +++the proper compiler and the proper debug format. Currently, +++@value{GDBN} works best when debugging C@t{++} code that is compiled +++with the most recent version of @value{NGCC} possible. The DWARF +++debugging format is preferred; @value{NGCC} defaults to this on most +++popular platforms. Other compilers and/or debug formats are likely to +++work badly or not at all when using @value{GDBN} to debug C@t{++} +++code. @xref{Compilation}. +++@end quotation +++ +++@enumerate +++ +++@cindex member functions +++@item +++Member function calls are allowed; you can use expressions like +++ +++@smallexample +++count = aml->GetOriginal(x, y) +++@end smallexample +++ +++@vindex this@r{, inside C@t{++} member functions} +++@cindex namespace in C@t{++} +++@item +++While a member function is active (in the selected stack frame), your +++expressions have the same namespace available as the member function; +++that is, @value{GDBN} allows implicit references to the class instance +++pointer @code{this} following the same rules as C@t{++}. @code{using} +++declarations in the current scope are also respected by @value{GDBN}. +++ +++@cindex call overloaded functions +++@cindex overloaded functions, calling +++@cindex type conversions in C@t{++} +++@item +++You can call overloaded functions; @value{GDBN} resolves the function +++call to the right definition, with some restrictions. @value{GDBN} does not +++perform overload resolution involving user-defined type conversions, +++calls to constructors, or instantiations of templates that do not exist +++in the program. It also cannot handle ellipsis argument lists or +++default arguments. +++ +++It does perform integral conversions and promotions, floating-point +++promotions, arithmetic conversions, pointer conversions, conversions of +++class objects to base classes, and standard conversions such as those of +++functions or arrays to pointers; it requires an exact match on the +++number of function arguments. +++ +++Overload resolution is always performed, unless you have specified +++@code{set overload-resolution off}. @xref{Debugging C Plus Plus, +++,@value{GDBN} Features for C@t{++}}. +++ +++You must specify @code{set overload-resolution off} in order to use an +++explicit function signature to call an overloaded function, as in +++@smallexample +++p 'foo(char,int)'('x', 13) +++@end smallexample +++ +++The @value{GDBN} command-completion facility can simplify this; +++see @ref{Completion, ,Command Completion}. +++ +++@cindex reference declarations +++@item +++@value{GDBN} understands variables declared as C@t{++} lvalue or rvalue +++references; you can use them in expressions just as you do in C@t{++} +++source---they are automatically dereferenced. +++ +++In the parameter list shown when @value{GDBN} displays a frame, the values of +++reference variables are not displayed (unlike other variables); this +++avoids clutter, since references are often used for large structures. +++The @emph{address} of a reference variable is always shown, unless +++you have specified @samp{set print address off}. +++ +++@item +++@value{GDBN} supports the C@t{++} name resolution operator @code{::}---your +++expressions can use it just as expressions in your program do. Since +++one scope may be defined in another, you can use @code{::} repeatedly if +++necessary, for example in an expression like +++@samp{@var{scope1}::@var{scope2}::@var{name}}. @value{GDBN} also allows +++resolving name scope by reference to source files, in both C and C@t{++} +++debugging (@pxref{Variables, ,Program Variables}). +++ +++@item +++@value{GDBN} performs argument-dependent lookup, following the C@t{++} +++specification. +++@end enumerate +++ +++@node C Defaults +++@subsubsection C and C@t{++} Defaults +++ +++@cindex C and C@t{++} defaults +++ +++If you allow @value{GDBN} to set range checking automatically, it +++defaults to @code{off} whenever the working language changes to +++C or C@t{++}. This happens regardless of whether you or @value{GDBN} +++selects the working language. +++ +++If you allow @value{GDBN} to set the language automatically, it +++recognizes source files whose names end with @file{.c}, @file{.C}, or +++@file{.cc}, etc, and when @value{GDBN} enters code compiled from one of +++these files, it sets the working language to C or C@t{++}. +++@xref{Automatically, ,Having @value{GDBN} Infer the Source Language}, +++for further details. +++ +++@node C Checks +++@subsubsection C and C@t{++} Type and Range Checks +++ +++@cindex C and C@t{++} checks +++ +++By default, when @value{GDBN} parses C or C@t{++} expressions, strict type +++checking is used. However, if you turn type checking off, @value{GDBN} +++will allow certain non-standard conversions, such as promoting integer +++constants to pointers. +++ +++Range checking, if turned on, is done on mathematical operations. Array +++indices are not checked, since they are often used to index a pointer +++that is not itself an array. +++ +++@node Debugging C +++@subsubsection @value{GDBN} and C +++ +++The @code{set print union} and @code{show print union} commands apply to +++the @code{union} type. When set to @samp{on}, any @code{union} that is +++inside a @code{struct} or @code{class} is also printed. Otherwise, it +++appears as @samp{@{...@}}. +++ +++The @code{@@} operator aids in the debugging of dynamic arrays, formed +++with pointers and a memory allocation function. @xref{Expressions, +++,Expressions}. +++ +++@node Debugging C Plus Plus +++@subsubsection @value{GDBN} Features for C@t{++} +++ +++@cindex commands for C@t{++} +++ +++Some @value{GDBN} commands are particularly useful with C@t{++}, and some are +++designed specifically for use with C@t{++}. Here is a summary: +++ +++@table @code +++@cindex break in overloaded functions +++@item @r{breakpoint menus} +++When you want a breakpoint in a function whose name is overloaded, +++@value{GDBN} has the capability to display a menu of possible breakpoint +++locations to help you specify which function definition you want. +++@xref{Ambiguous Expressions,,Ambiguous Expressions}. +++ +++@cindex overloading in C@t{++} +++@item rbreak @var{regex} +++Setting breakpoints using regular expressions is helpful for setting +++breakpoints on overloaded functions that are not members of any special +++classes. +++@xref{Set Breaks, ,Setting Breakpoints}. +++ +++@cindex C@t{++} exception handling +++@item catch throw +++@itemx catch rethrow +++@itemx catch catch +++Debug C@t{++} exception handling using these commands. @xref{Set +++Catchpoints, , Setting Catchpoints}. +++ +++@cindex inheritance +++@item ptype @var{typename} +++Print inheritance relationships as well as other information for type +++@var{typename}. +++@xref{Symbols, ,Examining the Symbol Table}. +++ +++@item info vtbl @var{expression}. +++The @code{info vtbl} command can be used to display the virtual +++method tables of the object computed by @var{expression}. This shows +++one entry per virtual table; there may be multiple virtual tables when +++multiple inheritance is in use. +++ +++@cindex C@t{++} demangling +++@item demangle @var{name} +++Demangle @var{name}. +++@xref{Symbols}, for a more complete description of the @code{demangle} command. +++ +++@cindex C@t{++} symbol display +++@item set print demangle +++@itemx show print demangle +++@itemx set print asm-demangle +++@itemx show print asm-demangle +++Control whether C@t{++} symbols display in their source form, both when +++displaying code as C@t{++} source and when displaying disassemblies. +++@xref{Print Settings, ,Print Settings}. +++ +++@item set print object +++@itemx show print object +++Choose whether to print derived (actual) or declared types of objects. +++@xref{Print Settings, ,Print Settings}. +++ +++@item set print vtbl +++@itemx show print vtbl +++Control the format for printing virtual function tables. +++@xref{Print Settings, ,Print Settings}. +++(The @code{vtbl} commands do not work on programs compiled with the HP +++ANSI C@t{++} compiler (@code{aCC}).) +++ +++@kindex set overload-resolution +++@cindex overloaded functions, overload resolution +++@item set overload-resolution on +++Enable overload resolution for C@t{++} expression evaluation. The default +++is on. For overloaded functions, @value{GDBN} evaluates the arguments +++and searches for a function whose signature matches the argument types, +++using the standard C@t{++} conversion rules (see @ref{C Plus Plus +++Expressions, ,C@t{++} Expressions}, for details). +++If it cannot find a match, it emits a message. +++ +++@item set overload-resolution off +++Disable overload resolution for C@t{++} expression evaluation. For +++overloaded functions that are not class member functions, @value{GDBN} +++chooses the first function of the specified name that it finds in the +++symbol table, whether or not its arguments are of the correct type. For +++overloaded functions that are class member functions, @value{GDBN} +++searches for a function whose signature @emph{exactly} matches the +++argument types. +++ +++@kindex show overload-resolution +++@item show overload-resolution +++Show the current setting of overload resolution. +++ +++@item @r{Overloaded symbol names} +++You can specify a particular definition of an overloaded symbol, using +++the same notation that is used to declare such symbols in C@t{++}: type +++@code{@var{symbol}(@var{types})} rather than just @var{symbol}. You can +++also use the @value{GDBN} command-line word completion facilities to list the +++available choices, or to finish the type list for you. +++@xref{Completion,, Command Completion}, for details on how to do this. +++ +++@item @r{Breakpoints in functions with ABI tags} +++ +++The GNU C@t{++} compiler introduced the notion of ABI ``tags'', which +++correspond to changes in the ABI of a type, function, or variable that +++would not otherwise be reflected in a mangled name. See +++@url{https://developers.redhat.com/blog/2015/02/05/gcc5-and-the-c11-abi/} +++for more detail. +++ +++The ABI tags are visible in C@t{++} demangled names. For example, a +++function that returns a std::string: +++ +++@smallexample +++std::string function(int); +++@end smallexample +++ +++@noindent +++when compiled for the C++11 ABI is marked with the @code{cxx11} ABI +++tag, and @value{GDBN} displays the symbol like this: +++ +++@smallexample +++function[abi:cxx11](int) +++@end smallexample +++ +++You can set a breakpoint on such functions simply as if they had no +++tag. For example: +++ +++@smallexample +++(gdb) b function(int) +++Breakpoint 2 at 0x40060d: file main.cc, line 10. +++(gdb) info breakpoints +++Num Type Disp Enb Address What +++1 breakpoint keep y 0x0040060d in function[abi:cxx11](int) +++ at main.cc:10 +++@end smallexample +++ +++On the rare occasion you need to disambiguate between different ABI +++tags, you can do so by simply including the ABI tag in the function +++name, like: +++ +++@smallexample +++(@value{GDBP}) b ambiguous[abi:other_tag](int) +++@end smallexample +++@end table +++ +++@node Decimal Floating Point +++@subsubsection Decimal Floating Point format +++@cindex decimal floating point format +++ +++@value{GDBN} can examine, set and perform computations with numbers in +++decimal floating point format, which in the C language correspond to the +++@code{_Decimal32}, @code{_Decimal64} and @code{_Decimal128} types as +++specified by the extension to support decimal floating-point arithmetic. +++ +++There are two encodings in use, depending on the architecture: BID (Binary +++Integer Decimal) for x86 and x86-64, and DPD (Densely Packed Decimal) for +++PowerPC and S/390. @value{GDBN} will use the appropriate encoding for the +++configured target. +++ +++Because of a limitation in @file{libdecnumber}, the library used by @value{GDBN} +++to manipulate decimal floating point numbers, it is not possible to convert +++(using a cast, for example) integers wider than 32-bit to decimal float. +++ +++In addition, in order to imitate @value{GDBN}'s behaviour with binary floating +++point computations, error checking in decimal float operations ignores +++underflow, overflow and divide by zero exceptions. +++ +++In the PowerPC architecture, @value{GDBN} provides a set of pseudo-registers +++to inspect @code{_Decimal128} values stored in floating point registers. +++See @ref{PowerPC,,PowerPC} for more details. +++ +++@node D +++@subsection D +++ +++@cindex D +++@value{GDBN} can be used to debug programs written in D and compiled with +++GDC, LDC or DMD compilers. Currently @value{GDBN} supports only one D +++specific feature --- dynamic arrays. +++ +++@node Go +++@subsection Go +++ +++@cindex Go (programming language) +++@value{GDBN} can be used to debug programs written in Go and compiled with +++@file{gccgo} or @file{6g} compilers. +++ +++Here is a summary of the Go-specific features and restrictions: +++ +++@table @code +++@cindex current Go package +++@item The current Go package +++The name of the current package does not need to be specified when +++specifying global variables and functions. +++ +++For example, given the program: +++ +++@example +++package main +++var myglob = "Shall we?" +++func main () @{ +++ // ... +++@} +++@end example +++ +++When stopped inside @code{main} either of these work: +++ +++@example +++(gdb) p myglob +++(gdb) p main.myglob +++@end example +++ +++@cindex builtin Go types +++@item Builtin Go types +++The @code{string} type is recognized by @value{GDBN} and is printed +++as a string. +++ +++@cindex builtin Go functions +++@item Builtin Go functions +++The @value{GDBN} expression parser recognizes the @code{unsafe.Sizeof} +++function and handles it internally. +++ +++@cindex restrictions on Go expressions +++@item Restrictions on Go expressions +++All Go operators are supported except @code{&^}. +++The Go @code{_} ``blank identifier'' is not supported. +++Automatic dereferencing of pointers is not supported. +++@end table +++ +++@node Objective-C +++@subsection Objective-C +++ +++@cindex Objective-C +++This section provides information about some commands and command +++options that are useful for debugging Objective-C code. See also +++@ref{Symbols, info classes}, and @ref{Symbols, info selectors}, for a +++few more commands specific to Objective-C support. +++ +++@menu +++* Method Names in Commands:: +++* The Print Command with Objective-C:: +++@end menu +++ +++@node Method Names in Commands +++@subsubsection Method Names in Commands +++ +++The following commands have been extended to accept Objective-C method +++names as line specifications: +++ +++@kindex clear@r{, and Objective-C} +++@kindex break@r{, and Objective-C} +++@kindex info line@r{, and Objective-C} +++@kindex jump@r{, and Objective-C} +++@kindex list@r{, and Objective-C} +++@itemize +++@item @code{clear} +++@item @code{break} +++@item @code{info line} +++@item @code{jump} +++@item @code{list} +++@end itemize +++ +++A fully qualified Objective-C method name is specified as +++ +++@smallexample +++-[@var{Class} @var{methodName}] +++@end smallexample +++ +++where the minus sign is used to indicate an instance method and a +++plus sign (not shown) is used to indicate a class method. The class +++name @var{Class} and method name @var{methodName} are enclosed in +++brackets, similar to the way messages are specified in Objective-C +++source code. For example, to set a breakpoint at the @code{create} +++instance method of class @code{Fruit} in the program currently being +++debugged, enter: +++ +++@smallexample +++break -[Fruit create] +++@end smallexample +++ +++To list ten program lines around the @code{initialize} class method, +++enter: +++ +++@smallexample +++list +[NSText initialize] +++@end smallexample +++ +++In the current version of @value{GDBN}, the plus or minus sign is +++required. In future versions of @value{GDBN}, the plus or minus +++sign will be optional, but you can use it to narrow the search. It +++is also possible to specify just a method name: +++ +++@smallexample +++break create +++@end smallexample +++ +++You must specify the complete method name, including any colons. If +++your program's source files contain more than one @code{create} method, +++you'll be presented with a numbered list of classes that implement that +++method. Indicate your choice by number, or type @samp{0} to exit if +++none apply. +++ +++As another example, to clear a breakpoint established at the +++@code{makeKeyAndOrderFront:} method of the @code{NSWindow} class, enter: +++ +++@smallexample +++clear -[NSWindow makeKeyAndOrderFront:] +++@end smallexample +++ +++@node The Print Command with Objective-C +++@subsubsection The Print Command With Objective-C +++@cindex Objective-C, print objects +++@kindex print-object +++@kindex po @r{(@code{print-object})} +++ +++The print command has also been extended to accept methods. For example: +++ +++@smallexample +++print -[@var{object} hash] +++@end smallexample +++ +++@cindex print an Objective-C object description +++@cindex @code{_NSPrintForDebugger}, and printing Objective-C objects +++@noindent +++will tell @value{GDBN} to send the @code{hash} message to @var{object} +++and print the result. Also, an additional command has been added, +++@code{print-object} or @code{po} for short, which is meant to print +++the description of an object. However, this command may only work +++with certain Objective-C libraries that have a particular hook +++function, @code{_NSPrintForDebugger}, defined. +++ +++@node OpenCL C +++@subsection OpenCL C +++ +++@cindex OpenCL C +++This section provides information about @value{GDBN}s OpenCL C support. +++ +++@menu +++* OpenCL C Datatypes:: +++* OpenCL C Expressions:: +++* OpenCL C Operators:: +++@end menu +++ +++@node OpenCL C Datatypes +++@subsubsection OpenCL C Datatypes +++ +++@cindex OpenCL C Datatypes +++@value{GDBN} supports the builtin scalar and vector datatypes specified +++by OpenCL 1.1. In addition the half- and double-precision floating point +++data types of the @code{cl_khr_fp16} and @code{cl_khr_fp64} OpenCL +++extensions are also known to @value{GDBN}. +++ +++@node OpenCL C Expressions +++@subsubsection OpenCL C Expressions +++ +++@cindex OpenCL C Expressions +++@value{GDBN} supports accesses to vector components including the access as +++lvalue where possible. Since OpenCL C is based on C99 most C expressions +++supported by @value{GDBN} can be used as well. +++ +++@node OpenCL C Operators +++@subsubsection OpenCL C Operators +++ +++@cindex OpenCL C Operators +++@value{GDBN} supports the operators specified by OpenCL 1.1 for scalar and +++vector data types. +++ +++@node Fortran +++@subsection Fortran +++@cindex Fortran-specific support in @value{GDBN} +++ +++@value{GDBN} can be used to debug programs written in Fortran, but it +++currently supports only the features of Fortran 77 language. +++ +++@cindex trailing underscore, in Fortran symbols +++Some Fortran compilers (@sc{gnu} Fortran 77 and Fortran 95 compilers +++among them) append an underscore to the names of variables and +++functions. When you debug programs compiled by those compilers, you +++will need to refer to variables and functions with a trailing +++underscore. +++ +++@menu +++* Fortran Operators:: Fortran operators and expressions +++* Fortran Defaults:: Default settings for Fortran +++* Special Fortran Commands:: Special @value{GDBN} commands for Fortran +++@end menu +++ +++@node Fortran Operators +++@subsubsection Fortran Operators and Expressions +++ +++@cindex Fortran operators and expressions +++ +++Operators must be defined on values of specific types. For instance, +++@code{+} is defined on numbers, but not on characters or other non- +++arithmetic types. Operators are often defined on groups of types. +++ +++@table @code +++@item ** +++The exponentiation operator. It raises the first operand to the power +++of the second one. +++ +++@item : +++The range operator. Normally used in the form of array(low:high) to +++represent a section of array. +++ +++@item % +++The access component operator. Normally used to access elements in derived +++types. Also suitable for unions. As unions aren't part of regular Fortran, +++this can only happen when accessing a register that uses a gdbarch-defined +++union type. +++@item :: +++The scope operator. Normally used to access variables in modules or +++to set breakpoints on subroutines nested in modules or in other +++subroutines (internal subroutines). +++@end table +++ +++@node Fortran Defaults +++@subsubsection Fortran Defaults +++ +++@cindex Fortran Defaults +++ +++Fortran symbols are usually case-insensitive, so @value{GDBN} by +++default uses case-insensitive matches for Fortran symbols. You can +++change that with the @samp{set case-insensitive} command, see +++@ref{Symbols}, for the details. +++ +++@node Special Fortran Commands +++@subsubsection Special Fortran Commands +++ +++@cindex Special Fortran commands +++ +++@value{GDBN} has some commands to support Fortran-specific features, +++such as displaying common blocks. +++ +++@table @code +++@cindex @code{COMMON} blocks, Fortran +++@kindex info common +++@item info common @r{[}@var{common-name}@r{]} +++This command prints the values contained in the Fortran @code{COMMON} +++block whose name is @var{common-name}. With no argument, the names of +++all @code{COMMON} blocks visible at the current program location are +++printed. +++@end table +++ +++@node Pascal +++@subsection Pascal +++ +++@cindex Pascal support in @value{GDBN}, limitations +++Debugging Pascal programs which use sets, subranges, file variables, or +++nested functions does not currently work. @value{GDBN} does not support +++entering expressions, printing values, or similar features using Pascal +++syntax. +++ +++The Pascal-specific command @code{set print pascal_static-members} +++controls whether static members of Pascal objects are displayed. +++@xref{Print Settings, pascal_static-members}. +++ +++@node Rust +++@subsection Rust +++ +++@value{GDBN} supports the @url{https://www.rust-lang.org/, Rust +++Programming Language}. Type- and value-printing, and expression +++parsing, are reasonably complete. However, there are a few +++peculiarities and holes to be aware of. +++ +++@itemize @bullet +++@item +++Linespecs (@pxref{Specify Location}) are never relative to the current +++crate. Instead, they act as if there were a global namespace of +++crates, somewhat similar to the way @code{extern crate} behaves. +++ +++That is, if @value{GDBN} is stopped at a breakpoint in a function in +++crate @samp{A}, module @samp{B}, then @code{break B::f} will attempt +++to set a breakpoint in a function named @samp{f} in a crate named +++@samp{B}. +++ +++As a consequence of this approach, linespecs also cannot refer to +++items using @samp{self::} or @samp{super::}. +++ +++@item +++Because @value{GDBN} implements Rust name-lookup semantics in +++expressions, it will sometimes prepend the current crate to a name. +++For example, if @value{GDBN} is stopped at a breakpoint in the crate +++@samp{K}, then @code{print ::x::y} will try to find the symbol +++@samp{K::x::y}. +++ +++However, since it is useful to be able to refer to other crates when +++debugging, @value{GDBN} provides the @code{extern} extension to +++circumvent this. To use the extension, just put @code{extern} before +++a path expression to refer to the otherwise unavailable ``global'' +++scope. +++ +++In the above example, if you wanted to refer to the symbol @samp{y} in +++the crate @samp{x}, you would use @code{print extern x::y}. +++ +++@item +++The Rust expression evaluator does not support ``statement-like'' +++expressions such as @code{if} or @code{match}, or lambda expressions. +++ +++@item +++Tuple expressions are not implemented. +++ +++@item +++The Rust expression evaluator does not currently implement the +++@code{Drop} trait. Objects that may be created by the evaluator will +++never be destroyed. +++ +++@item +++@value{GDBN} does not implement type inference for generics. In order +++to call generic functions or otherwise refer to generic items, you +++will have to specify the type parameters manually. +++ +++@item +++@value{GDBN} currently uses the C@t{++} demangler for Rust. In most +++cases this does not cause any problems. However, in an expression +++context, completing a generic function name will give syntactically +++invalid results. This happens because Rust requires the @samp{::} +++operator between the function name and its generic arguments. For +++example, @value{GDBN} might provide a completion like +++@code{crate::f}, where the parser would require +++@code{crate::f::}. +++ +++@item +++As of this writing, the Rust compiler (version 1.8) has a few holes in +++the debugging information it generates. These holes prevent certain +++features from being implemented by @value{GDBN}: +++@itemize @bullet +++ +++@item +++Method calls cannot be made via traits. +++ +++@item +++Operator overloading is not implemented. +++ +++@item +++When debugging in a monomorphized function, you cannot use the generic +++type names. +++ +++@item +++The type @code{Self} is not available. +++ +++@item +++@code{use} statements are not available, so some names may not be +++available in the crate. +++@end itemize +++@end itemize +++ +++@node Modula-2 +++@subsection Modula-2 +++ +++@cindex Modula-2, @value{GDBN} support +++ +++The extensions made to @value{GDBN} to support Modula-2 only support +++output from the @sc{gnu} Modula-2 compiler (which is currently being +++developed). Other Modula-2 compilers are not currently supported, and +++attempting to debug executables produced by them is most likely +++to give an error as @value{GDBN} reads in the executable's symbol +++table. +++ +++@cindex expressions in Modula-2 +++@menu +++* M2 Operators:: Built-in operators +++* Built-In Func/Proc:: Built-in functions and procedures +++* M2 Constants:: Modula-2 constants +++* M2 Types:: Modula-2 types +++* M2 Defaults:: Default settings for Modula-2 +++* Deviations:: Deviations from standard Modula-2 +++* M2 Checks:: Modula-2 type and range checks +++* M2 Scope:: The scope operators @code{::} and @code{.} +++* GDB/M2:: @value{GDBN} and Modula-2 +++@end menu +++ +++@node M2 Operators +++@subsubsection Operators +++@cindex Modula-2 operators +++ +++Operators must be defined on values of specific types. For instance, +++@code{+} is defined on numbers, but not on structures. Operators are +++often defined on groups of types. For the purposes of Modula-2, the +++following definitions hold: +++ +++@itemize @bullet +++ +++@item +++@emph{Integral types} consist of @code{INTEGER}, @code{CARDINAL}, and +++their subranges. +++ +++@item +++@emph{Character types} consist of @code{CHAR} and its subranges. +++ +++@item +++@emph{Floating-point types} consist of @code{REAL}. +++ +++@item +++@emph{Pointer types} consist of anything declared as @code{POINTER TO +++@var{type}}. +++ +++@item +++@emph{Scalar types} consist of all of the above. +++ +++@item +++@emph{Set types} consist of @code{SET} and @code{BITSET} types. +++ +++@item +++@emph{Boolean types} consist of @code{BOOLEAN}. +++@end itemize +++ +++@noindent +++The following operators are supported, and appear in order of +++increasing precedence: +++ +++@table @code +++@item , +++Function argument or array index separator. +++ +++@item := +++Assignment. The value of @var{var} @code{:=} @var{value} is +++@var{value}. +++ +++@item <@r{, }> +++Less than, greater than on integral, floating-point, or enumerated +++types. +++ +++@item <=@r{, }>= +++Less than or equal to, greater than or equal to +++on integral, floating-point and enumerated types, or set inclusion on +++set types. Same precedence as @code{<}. +++ +++@item =@r{, }<>@r{, }# +++Equality and two ways of expressing inequality, valid on scalar types. +++Same precedence as @code{<}. In @value{GDBN} scripts, only @code{<>} is +++available for inequality, since @code{#} conflicts with the script +++comment character. +++ +++@item IN +++Set membership. Defined on set types and the types of their members. +++Same precedence as @code{<}. +++ +++@item OR +++Boolean disjunction. Defined on boolean types. +++ +++@item AND@r{, }& +++Boolean conjunction. Defined on boolean types. +++ +++@item @@ +++The @value{GDBN} ``artificial array'' operator (@pxref{Expressions, ,Expressions}). +++ +++@item +@r{, }- +++Addition and subtraction on integral and floating-point types, or union +++and difference on set types. +++ +++@item * +++Multiplication on integral and floating-point types, or set intersection +++on set types. +++ +++@item / +++Division on floating-point types, or symmetric set difference on set +++types. Same precedence as @code{*}. +++ +++@item DIV@r{, }MOD +++Integer division and remainder. Defined on integral types. Same +++precedence as @code{*}. +++ +++@item - +++Negative. Defined on @code{INTEGER} and @code{REAL} data. +++ +++@item ^ +++Pointer dereferencing. Defined on pointer types. +++ +++@item NOT +++Boolean negation. Defined on boolean types. Same precedence as +++@code{^}. +++ +++@item . +++@code{RECORD} field selector. Defined on @code{RECORD} data. Same +++precedence as @code{^}. +++ +++@item [] +++Array indexing. Defined on @code{ARRAY} data. Same precedence as @code{^}. +++ +++@item () +++Procedure argument list. Defined on @code{PROCEDURE} objects. Same precedence +++as @code{^}. +++ +++@item ::@r{, }. +++@value{GDBN} and Modula-2 scope operators. +++@end table +++ +++@quotation +++@emph{Warning:} Set expressions and their operations are not yet supported, so @value{GDBN} +++treats the use of the operator @code{IN}, or the use of operators +++@code{+}, @code{-}, @code{*}, @code{/}, @code{=}, , @code{<>}, @code{#}, +++@code{<=}, and @code{>=} on sets as an error. +++@end quotation +++ +++ +++@node Built-In Func/Proc +++@subsubsection Built-in Functions and Procedures +++@cindex Modula-2 built-ins +++ +++Modula-2 also makes available several built-in procedures and functions. +++In describing these, the following metavariables are used: +++ +++@table @var +++ +++@item a +++represents an @code{ARRAY} variable. +++ +++@item c +++represents a @code{CHAR} constant or variable. +++ +++@item i +++represents a variable or constant of integral type. +++ +++@item m +++represents an identifier that belongs to a set. Generally used in the +++same function with the metavariable @var{s}. The type of @var{s} should +++be @code{SET OF @var{mtype}} (where @var{mtype} is the type of @var{m}). +++ +++@item n +++represents a variable or constant of integral or floating-point type. +++ +++@item r +++represents a variable or constant of floating-point type. +++ +++@item t +++represents a type. +++ +++@item v +++represents a variable. +++ +++@item x +++represents a variable or constant of one of many types. See the +++explanation of the function for details. +++@end table +++ +++All Modula-2 built-in procedures also return a result, described below. +++ +++@table @code +++@item ABS(@var{n}) +++Returns the absolute value of @var{n}. +++ +++@item CAP(@var{c}) +++If @var{c} is a lower case letter, it returns its upper case +++equivalent, otherwise it returns its argument. +++ +++@item CHR(@var{i}) +++Returns the character whose ordinal value is @var{i}. +++ +++@item DEC(@var{v}) +++Decrements the value in the variable @var{v} by one. Returns the new value. +++ +++@item DEC(@var{v},@var{i}) +++Decrements the value in the variable @var{v} by @var{i}. Returns the +++new value. +++ +++@item EXCL(@var{m},@var{s}) +++Removes the element @var{m} from the set @var{s}. Returns the new +++set. +++ +++@item FLOAT(@var{i}) +++Returns the floating point equivalent of the integer @var{i}. +++ +++@item HIGH(@var{a}) +++Returns the index of the last member of @var{a}. +++ +++@item INC(@var{v}) +++Increments the value in the variable @var{v} by one. Returns the new value. +++ +++@item INC(@var{v},@var{i}) +++Increments the value in the variable @var{v} by @var{i}. Returns the +++new value. +++ +++@item INCL(@var{m},@var{s}) +++Adds the element @var{m} to the set @var{s} if it is not already +++there. Returns the new set. +++ +++@item MAX(@var{t}) +++Returns the maximum value of the type @var{t}. +++ +++@item MIN(@var{t}) +++Returns the minimum value of the type @var{t}. +++ +++@item ODD(@var{i}) +++Returns boolean TRUE if @var{i} is an odd number. +++ +++@item ORD(@var{x}) +++Returns the ordinal value of its argument. For example, the ordinal +++value of a character is its @sc{ascii} value (on machines supporting +++the @sc{ascii} character set). The argument @var{x} must be of an +++ordered type, which include integral, character and enumerated types. +++ +++@item SIZE(@var{x}) +++Returns the size of its argument. The argument @var{x} can be a +++variable or a type. +++ +++@item TRUNC(@var{r}) +++Returns the integral part of @var{r}. +++ +++@item TSIZE(@var{x}) +++Returns the size of its argument. The argument @var{x} can be a +++variable or a type. +++ +++@item VAL(@var{t},@var{i}) +++Returns the member of the type @var{t} whose ordinal value is @var{i}. +++@end table +++ +++@quotation +++@emph{Warning:} Sets and their operations are not yet supported, so +++@value{GDBN} treats the use of procedures @code{INCL} and @code{EXCL} as +++an error. +++@end quotation +++ +++@cindex Modula-2 constants +++@node M2 Constants +++@subsubsection Constants +++ +++@value{GDBN} allows you to express the constants of Modula-2 in the following +++ways: +++ +++@itemize @bullet +++ +++@item +++Integer constants are simply a sequence of digits. When used in an +++expression, a constant is interpreted to be type-compatible with the +++rest of the expression. Hexadecimal integers are specified by a +++trailing @samp{H}, and octal integers by a trailing @samp{B}. +++ +++@item +++Floating point constants appear as a sequence of digits, followed by a +++decimal point and another sequence of digits. An optional exponent can +++then be specified, in the form @samp{E@r{[}+@r{|}-@r{]}@var{nnn}}, where +++@samp{@r{[}+@r{|}-@r{]}@var{nnn}} is the desired exponent. All of the +++digits of the floating point constant must be valid decimal (base 10) +++digits. +++ +++@item +++Character constants consist of a single character enclosed by a pair of +++like quotes, either single (@code{'}) or double (@code{"}). They may +++also be expressed by their ordinal value (their @sc{ascii} value, usually) +++followed by a @samp{C}. +++ +++@item +++String constants consist of a sequence of characters enclosed by a +++pair of like quotes, either single (@code{'}) or double (@code{"}). +++Escape sequences in the style of C are also allowed. @xref{C +++Constants, ,C and C@t{++} Constants}, for a brief explanation of escape +++sequences. +++ +++@item +++Enumerated constants consist of an enumerated identifier. +++ +++@item +++Boolean constants consist of the identifiers @code{TRUE} and +++@code{FALSE}. +++ +++@item +++Pointer constants consist of integral values only. +++ +++@item +++Set constants are not yet supported. +++@end itemize +++ +++@node M2 Types +++@subsubsection Modula-2 Types +++@cindex Modula-2 types +++ +++Currently @value{GDBN} can print the following data types in Modula-2 +++syntax: array types, record types, set types, pointer types, procedure +++types, enumerated types, subrange types and base types. You can also +++print the contents of variables declared using these type. +++This section gives a number of simple source code examples together with +++sample @value{GDBN} sessions. +++ +++The first example contains the following section of code: +++ +++@smallexample +++VAR +++ s: SET OF CHAR ; +++ r: [20..40] ; +++@end smallexample +++ +++@noindent +++and you can request @value{GDBN} to interrogate the type and value of +++@code{r} and @code{s}. +++ +++@smallexample +++(@value{GDBP}) print s +++@{'A'..'C', 'Z'@} +++(@value{GDBP}) ptype s +++SET OF CHAR +++(@value{GDBP}) print r +++21 +++(@value{GDBP}) ptype r +++[20..40] +++@end smallexample +++ +++@noindent +++Likewise if your source code declares @code{s} as: +++ +++@smallexample +++VAR +++ s: SET ['A'..'Z'] ; +++@end smallexample +++ +++@noindent +++then you may query the type of @code{s} by: +++ +++@smallexample +++(@value{GDBP}) ptype s +++type = SET ['A'..'Z'] +++@end smallexample +++ +++@noindent +++Note that at present you cannot interactively manipulate set +++expressions using the debugger. +++ +++The following example shows how you might declare an array in Modula-2 +++and how you can interact with @value{GDBN} to print its type and contents: +++ +++@smallexample +++VAR +++ s: ARRAY [-10..10] OF CHAR ; +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) ptype s +++ARRAY [-10..10] OF CHAR +++@end smallexample +++ +++Note that the array handling is not yet complete and although the type +++is printed correctly, expression handling still assumes that all +++arrays have a lower bound of zero and not @code{-10} as in the example +++above. +++ +++Here are some more type related Modula-2 examples: +++ +++@smallexample +++TYPE +++ colour = (blue, red, yellow, green) ; +++ t = [blue..yellow] ; +++VAR +++ s: t ; +++BEGIN +++ s := blue ; +++@end smallexample +++ +++@noindent +++The @value{GDBN} interaction shows how you can query the data type +++and value of a variable. +++ +++@smallexample +++(@value{GDBP}) print s +++$1 = blue +++(@value{GDBP}) ptype t +++type = [blue..yellow] +++@end smallexample +++ +++@noindent +++In this example a Modula-2 array is declared and its contents +++displayed. Observe that the contents are written in the same way as +++their @code{C} counterparts. +++ +++@smallexample +++VAR +++ s: ARRAY [1..5] OF CARDINAL ; +++BEGIN +++ s[1] := 1 ; +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) print s +++$1 = @{1, 0, 0, 0, 0@} +++(@value{GDBP}) ptype s +++type = ARRAY [1..5] OF CARDINAL +++@end smallexample +++ +++The Modula-2 language interface to @value{GDBN} also understands +++pointer types as shown in this example: +++ +++@smallexample +++VAR +++ s: POINTER TO ARRAY [1..5] OF CARDINAL ; +++BEGIN +++ NEW(s) ; +++ s^[1] := 1 ; +++@end smallexample +++ +++@noindent +++and you can request that @value{GDBN} describes the type of @code{s}. +++ +++@smallexample +++(@value{GDBP}) ptype s +++type = POINTER TO ARRAY [1..5] OF CARDINAL +++@end smallexample +++ +++@value{GDBN} handles compound types as we can see in this example. +++Here we combine array types, record types, pointer types and subrange +++types: +++ +++@smallexample +++TYPE +++ foo = RECORD +++ f1: CARDINAL ; +++ f2: CHAR ; +++ f3: myarray ; +++ END ; +++ +++ myarray = ARRAY myrange OF CARDINAL ; +++ myrange = [-2..2] ; +++VAR +++ s: POINTER TO ARRAY myrange OF foo ; +++@end smallexample +++ +++@noindent +++and you can ask @value{GDBN} to describe the type of @code{s} as shown +++below. +++ +++@smallexample +++(@value{GDBP}) ptype s +++type = POINTER TO ARRAY [-2..2] OF foo = RECORD +++ f1 : CARDINAL; +++ f2 : CHAR; +++ f3 : ARRAY [-2..2] OF CARDINAL; +++END +++@end smallexample +++ +++@node M2 Defaults +++@subsubsection Modula-2 Defaults +++@cindex Modula-2 defaults +++ +++If type and range checking are set automatically by @value{GDBN}, they +++both default to @code{on} whenever the working language changes to +++Modula-2. This happens regardless of whether you or @value{GDBN} +++selected the working language. +++ +++If you allow @value{GDBN} to set the language automatically, then entering +++code compiled from a file whose name ends with @file{.mod} sets the +++working language to Modula-2. @xref{Automatically, ,Having @value{GDBN} +++Infer the Source Language}, for further details. +++ +++@node Deviations +++@subsubsection Deviations from Standard Modula-2 +++@cindex Modula-2, deviations from +++ +++A few changes have been made to make Modula-2 programs easier to debug. +++This is done primarily via loosening its type strictness: +++ +++@itemize @bullet +++@item +++Unlike in standard Modula-2, pointer constants can be formed by +++integers. This allows you to modify pointer variables during +++debugging. (In standard Modula-2, the actual address contained in a +++pointer variable is hidden from you; it can only be modified +++through direct assignment to another pointer variable or expression that +++returned a pointer.) +++ +++@item +++C escape sequences can be used in strings and characters to represent +++non-printable characters. @value{GDBN} prints out strings with these +++escape sequences embedded. Single non-printable characters are +++printed using the @samp{CHR(@var{nnn})} format. +++ +++@item +++The assignment operator (@code{:=}) returns the value of its right-hand +++argument. +++ +++@item +++All built-in procedures both modify @emph{and} return their argument. +++@end itemize +++ +++@node M2 Checks +++@subsubsection Modula-2 Type and Range Checks +++@cindex Modula-2 checks +++ +++@quotation +++@emph{Warning:} in this release, @value{GDBN} does not yet perform type or +++range checking. +++@end quotation +++@c FIXME remove warning when type/range checks added +++ +++@value{GDBN} considers two Modula-2 variables type equivalent if: +++ +++@itemize @bullet +++@item +++They are of types that have been declared equivalent via a @code{TYPE +++@var{t1} = @var{t2}} statement +++ +++@item +++They have been declared on the same line. (Note: This is true of the +++@sc{gnu} Modula-2 compiler, but it may not be true of other compilers.) +++@end itemize +++ +++As long as type checking is enabled, any attempt to combine variables +++whose types are not equivalent is an error. +++ +++Range checking is done on all mathematical operations, assignment, array +++index bounds, and all built-in functions and procedures. +++ +++@node M2 Scope +++@subsubsection The Scope Operators @code{::} and @code{.} +++@cindex scope +++@cindex @code{.}, Modula-2 scope operator +++@cindex colon, doubled as scope operator +++@ifinfo +++@vindex colon-colon@r{, in Modula-2} +++@c Info cannot handle :: but TeX can. +++@end ifinfo +++@ifnotinfo +++@vindex ::@r{, in Modula-2} +++@end ifnotinfo +++ +++There are a few subtle differences between the Modula-2 scope operator +++(@code{.}) and the @value{GDBN} scope operator (@code{::}). The two have +++similar syntax: +++ +++@smallexample +++ +++@var{module} . @var{id} +++@var{scope} :: @var{id} +++@end smallexample +++ +++@noindent +++where @var{scope} is the name of a module or a procedure, +++@var{module} the name of a module, and @var{id} is any declared +++identifier within your program, except another module. +++ +++Using the @code{::} operator makes @value{GDBN} search the scope +++specified by @var{scope} for the identifier @var{id}. If it is not +++found in the specified scope, then @value{GDBN} searches all scopes +++enclosing the one specified by @var{scope}. +++ +++Using the @code{.} operator makes @value{GDBN} search the current scope for +++the identifier specified by @var{id} that was imported from the +++definition module specified by @var{module}. With this operator, it is +++an error if the identifier @var{id} was not imported from definition +++module @var{module}, or if @var{id} is not an identifier in +++@var{module}. +++ +++@node GDB/M2 +++@subsubsection @value{GDBN} and Modula-2 +++ +++Some @value{GDBN} commands have little use when debugging Modula-2 programs. +++Five subcommands of @code{set print} and @code{show print} apply +++specifically to C and C@t{++}: @samp{vtbl}, @samp{demangle}, +++@samp{asm-demangle}, @samp{object}, and @samp{union}. The first four +++apply to C@t{++}, and the last to the C @code{union} type, which has no direct +++analogue in Modula-2. +++ +++The @code{@@} operator (@pxref{Expressions, ,Expressions}), while available +++with any language, is not useful with Modula-2. Its +++intent is to aid the debugging of @dfn{dynamic arrays}, which cannot be +++created in Modula-2 as they can in C or C@t{++}. However, because an +++address can be specified by an integral constant, the construct +++@samp{@{@var{type}@}@var{adrexp}} is still useful. +++ +++@cindex @code{#} in Modula-2 +++In @value{GDBN} scripts, the Modula-2 inequality operator @code{#} is +++interpreted as the beginning of a comment. Use @code{<>} instead. +++ +++@node Ada +++@subsection Ada +++@cindex Ada +++ +++The extensions made to @value{GDBN} for Ada only support +++output from the @sc{gnu} Ada (GNAT) compiler. +++Other Ada compilers are not currently supported, and +++attempting to debug executables produced by them is most likely +++to be difficult. +++ +++ +++@cindex expressions in Ada +++@menu +++* Ada Mode Intro:: General remarks on the Ada syntax +++ and semantics supported by Ada mode +++ in @value{GDBN}. +++* Omissions from Ada:: Restrictions on the Ada expression syntax. +++* Additions to Ada:: Extensions of the Ada expression syntax. +++* Overloading support for Ada:: Support for expressions involving overloaded +++ subprograms. +++* Stopping Before Main Program:: Debugging the program during elaboration. +++* Ada Exceptions:: Ada Exceptions +++* Ada Tasks:: Listing and setting breakpoints in tasks. +++* Ada Tasks and Core Files:: Tasking Support when Debugging Core Files +++* Ravenscar Profile:: Tasking Support when using the Ravenscar +++ Profile +++* Ada Settings:: New settable GDB parameters for Ada. +++* Ada Glitches:: Known peculiarities of Ada mode. +++@end menu +++ +++@node Ada Mode Intro +++@subsubsection Introduction +++@cindex Ada mode, general +++ +++The Ada mode of @value{GDBN} supports a fairly large subset of Ada expression +++syntax, with some extensions. +++The philosophy behind the design of this subset is +++ +++@itemize @bullet +++@item +++That @value{GDBN} should provide basic literals and access to operations for +++arithmetic, dereferencing, field selection, indexing, and subprogram calls, +++leaving more sophisticated computations to subprograms written into the +++program (which therefore may be called from @value{GDBN}). +++ +++@item +++That type safety and strict adherence to Ada language restrictions +++are not particularly important to the @value{GDBN} user. +++ +++@item +++That brevity is important to the @value{GDBN} user. +++@end itemize +++ +++Thus, for brevity, the debugger acts as if all names declared in +++user-written packages are directly visible, even if they are not visible +++according to Ada rules, thus making it unnecessary to fully qualify most +++names with their packages, regardless of context. Where this causes +++ambiguity, @value{GDBN} asks the user's intent. +++ +++The debugger will start in Ada mode if it detects an Ada main program. +++As for other languages, it will enter Ada mode when stopped in a program that +++was translated from an Ada source file. +++ +++While in Ada mode, you may use `@t{--}' for comments. This is useful +++mostly for documenting command files. The standard @value{GDBN} comment +++(@samp{#}) still works at the beginning of a line in Ada mode, but not in the +++middle (to allow based literals). +++ +++@node Omissions from Ada +++@subsubsection Omissions from Ada +++@cindex Ada, omissions from +++ +++Here are the notable omissions from the subset: +++ +++@itemize @bullet +++@item +++Only a subset of the attributes are supported: +++ +++@itemize @minus +++@item +++@t{'First}, @t{'Last}, and @t{'Length} +++ on array objects (not on types and subtypes). +++ +++@item +++@t{'Min} and @t{'Max}. +++ +++@item +++@t{'Pos} and @t{'Val}. +++ +++@item +++@t{'Tag}. +++ +++@item +++@t{'Range} on array objects (not subtypes), but only as the right +++operand of the membership (@code{in}) operator. +++ +++@item +++@t{'Access}, @t{'Unchecked_Access}, and +++@t{'Unrestricted_Access} (a GNAT extension). +++ +++@item +++@t{'Address}. +++@end itemize +++ +++@item +++The names in +++@code{Characters.Latin_1} are not available and +++concatenation is not implemented. Thus, escape characters in strings are +++not currently available. +++ +++@item +++Equality tests (@samp{=} and @samp{/=}) on arrays test for bitwise +++equality of representations. They will generally work correctly +++for strings and arrays whose elements have integer or enumeration types. +++They may not work correctly for arrays whose element +++types have user-defined equality, for arrays of real values +++(in particular, IEEE-conformant floating point, because of negative +++zeroes and NaNs), and for arrays whose elements contain unused bits with +++indeterminate values. +++ +++@item +++The other component-by-component array operations (@code{and}, @code{or}, +++@code{xor}, @code{not}, and relational tests other than equality) +++are not implemented. +++ +++@item +++@cindex array aggregates (Ada) +++@cindex record aggregates (Ada) +++@cindex aggregates (Ada) +++There is limited support for array and record aggregates. They are +++permitted only on the right sides of assignments, as in these examples: +++ +++@smallexample +++(@value{GDBP}) set An_Array := (1, 2, 3, 4, 5, 6) +++(@value{GDBP}) set An_Array := (1, others => 0) +++(@value{GDBP}) set An_Array := (0|4 => 1, 1..3 => 2, 5 => 6) +++(@value{GDBP}) set A_2D_Array := ((1, 2, 3), (4, 5, 6), (7, 8, 9)) +++(@value{GDBP}) set A_Record := (1, "Peter", True); +++(@value{GDBP}) set A_Record := (Name => "Peter", Id => 1, Alive => True) +++@end smallexample +++ +++Changing a +++discriminant's value by assigning an aggregate has an +++undefined effect if that discriminant is used within the record. +++However, you can first modify discriminants by directly assigning to +++them (which normally would not be allowed in Ada), and then performing an +++aggregate assignment. For example, given a variable @code{A_Rec} +++declared to have a type such as: +++ +++@smallexample +++type Rec (Len : Small_Integer := 0) is record +++ Id : Integer; +++ Vals : IntArray (1 .. Len); +++end record; +++@end smallexample +++ +++you can assign a value with a different size of @code{Vals} with two +++assignments: +++ +++@smallexample +++(@value{GDBP}) set A_Rec.Len := 4 +++(@value{GDBP}) set A_Rec := (Id => 42, Vals => (1, 2, 3, 4)) +++@end smallexample +++ +++As this example also illustrates, @value{GDBN} is very loose about the usual +++rules concerning aggregates. You may leave out some of the +++components of an array or record aggregate (such as the @code{Len} +++component in the assignment to @code{A_Rec} above); they will retain their +++original values upon assignment. You may freely use dynamic values as +++indices in component associations. You may even use overlapping or +++redundant component associations, although which component values are +++assigned in such cases is not defined. +++ +++@item +++Calls to dispatching subprograms are not implemented. +++ +++@item +++The overloading algorithm is much more limited (i.e., less selective) +++than that of real Ada. It makes only limited use of the context in +++which a subexpression appears to resolve its meaning, and it is much +++looser in its rules for allowing type matches. As a result, some +++function calls will be ambiguous, and the user will be asked to choose +++the proper resolution. +++ +++@item +++The @code{new} operator is not implemented. +++ +++@item +++Entry calls are not implemented. +++ +++@item +++Aside from printing, arithmetic operations on the native VAX floating-point +++formats are not supported. +++ +++@item +++It is not possible to slice a packed array. +++ +++@item +++The names @code{True} and @code{False}, when not part of a qualified name, +++are interpreted as if implicitly prefixed by @code{Standard}, regardless of +++context. +++Should your program +++redefine these names in a package or procedure (at best a dubious practice), +++you will have to use fully qualified names to access their new definitions. +++@end itemize +++ +++@node Additions to Ada +++@subsubsection Additions to Ada +++@cindex Ada, deviations from +++ +++As it does for other languages, @value{GDBN} makes certain generic +++extensions to Ada (@pxref{Expressions}): +++ +++@itemize @bullet +++@item +++If the expression @var{E} is a variable residing in memory (typically +++a local variable or array element) and @var{N} is a positive integer, +++then @code{@var{E}@@@var{N}} displays the values of @var{E} and the +++@var{N}-1 adjacent variables following it in memory as an array. In +++Ada, this operator is generally not necessary, since its prime use is +++in displaying parts of an array, and slicing will usually do this in +++Ada. However, there are occasional uses when debugging programs in +++which certain debugging information has been optimized away. +++ +++@item +++@code{@var{B}::@var{var}} means ``the variable named @var{var} that +++appears in function or file @var{B}.'' When @var{B} is a file name, +++you must typically surround it in single quotes. +++ +++@item +++The expression @code{@{@var{type}@} @var{addr}} means ``the variable of type +++@var{type} that appears at address @var{addr}.'' +++ +++@item +++A name starting with @samp{$} is a convenience variable +++(@pxref{Convenience Vars}) or a machine register (@pxref{Registers}). +++@end itemize +++ +++In addition, @value{GDBN} provides a few other shortcuts and outright +++additions specific to Ada: +++ +++@itemize @bullet +++@item +++The assignment statement is allowed as an expression, returning +++its right-hand operand as its value. Thus, you may enter +++ +++@smallexample +++(@value{GDBP}) set x := y + 3 +++(@value{GDBP}) print A(tmp := y + 1) +++@end smallexample +++ +++@item +++The semicolon is allowed as an ``operator,'' returning as its value +++the value of its right-hand operand. +++This allows, for example, +++complex conditional breaks: +++ +++@smallexample +++(@value{GDBP}) break f +++(@value{GDBP}) condition 1 (report(i); k += 1; A(k) > 100) +++@end smallexample +++ +++@item +++Rather than use catenation and symbolic character names to introduce special +++characters into strings, one may instead use a special bracket notation, +++which is also used to print strings. A sequence of characters of the form +++@samp{["@var{XX}"]} within a string or character literal denotes the +++(single) character whose numeric encoding is @var{XX} in hexadecimal. The +++sequence of characters @samp{["""]} also denotes a single quotation mark +++in strings. For example, +++@smallexample +++ "One line.["0a"]Next line.["0a"]" +++@end smallexample +++@noindent +++contains an ASCII newline character (@code{Ada.Characters.Latin_1.LF}) +++after each period. +++ +++@item +++The subtype used as a prefix for the attributes @t{'Pos}, @t{'Min}, and +++@t{'Max} is optional (and is ignored in any case). For example, it is valid +++to write +++ +++@smallexample +++(@value{GDBP}) print 'max(x, y) +++@end smallexample +++ +++@item +++When printing arrays, @value{GDBN} uses positional notation when the +++array has a lower bound of 1, and uses a modified named notation otherwise. +++For example, a one-dimensional array of three integers with a lower bound +++of 3 might print as +++ +++@smallexample +++(3 => 10, 17, 1) +++@end smallexample +++ +++@noindent +++That is, in contrast to valid Ada, only the first component has a @code{=>} +++clause. +++ +++@item +++You may abbreviate attributes in expressions with any unique, +++multi-character subsequence of +++their names (an exact match gets preference). +++For example, you may use @t{a'len}, @t{a'gth}, or @t{a'lh} +++in place of @t{a'length}. +++ +++@item +++@cindex quoting Ada internal identifiers +++Since Ada is case-insensitive, the debugger normally maps identifiers you type +++to lower case. The GNAT compiler uses upper-case characters for +++some of its internal identifiers, which are normally of no interest to users. +++For the rare occasions when you actually have to look at them, +++enclose them in angle brackets to avoid the lower-case mapping. +++For example, +++@smallexample +++(@value{GDBP}) print [0] +++@end smallexample +++ +++@item +++Printing an object of class-wide type or dereferencing an +++access-to-class-wide value will display all the components of the object's +++specific type (as indicated by its run-time tag). Likewise, component +++selection on such a value will operate on the specific type of the +++object. +++ +++@end itemize +++ +++@node Overloading support for Ada +++@subsubsection Overloading support for Ada +++@cindex overloading, Ada +++ +++The debugger supports limited overloading. Given a subprogram call in which +++the function symbol has multiple definitions, it will use the number of +++actual parameters and some information about their types to attempt to narrow +++the set of definitions. It also makes very limited use of context, preferring +++procedures to functions in the context of the @code{call} command, and +++functions to procedures elsewhere. +++ +++If, after narrowing, the set of matching definitions still contains more than +++one definition, @value{GDBN} will display a menu to query which one it should +++use, for instance: +++ +++@smallexample +++(@value{GDBP}) print f(1) +++Multiple matches for f +++[0] cancel +++[1] foo.f (integer) return boolean at foo.adb:23 +++[2] foo.f (foo.new_integer) return boolean at foo.adb:28 +++> +++@end smallexample +++ +++In this case, just select one menu entry either to cancel expression evaluation +++(type @kbd{0} and press @key{RET}) or to continue evaluation with a specific +++instance (type the corresponding number and press @key{RET}). +++ +++Here are a couple of commands to customize @value{GDBN}'s behavior in this +++case: +++ +++@table @code +++ +++@kindex set ada print-signatures +++@item set ada print-signatures +++Control whether parameter types and return types are displayed in overloads +++selection menus. It is @code{on} by default. +++@xref{Overloading support for Ada}. +++ +++@kindex show ada print-signatures +++@item show ada print-signatures +++Show the current setting for displaying parameter types and return types in +++overloads selection menu. +++@xref{Overloading support for Ada}. +++ +++@end table +++ +++@node Stopping Before Main Program +++@subsubsection Stopping at the Very Beginning +++ +++@cindex breakpointing Ada elaboration code +++It is sometimes necessary to debug the program during elaboration, and +++before reaching the main procedure. +++As defined in the Ada Reference +++Manual, the elaboration code is invoked from a procedure called +++@code{adainit}. To run your program up to the beginning of +++elaboration, simply use the following two commands: +++@code{tbreak adainit} and @code{run}. +++ +++@node Ada Exceptions +++@subsubsection Ada Exceptions +++ +++A command is provided to list all Ada exceptions: +++ +++@table @code +++@kindex info exceptions +++@item info exceptions +++@itemx info exceptions @var{regexp} +++The @code{info exceptions} command allows you to list all Ada exceptions +++defined within the program being debugged, as well as their addresses. +++With a regular expression, @var{regexp}, as argument, only those exceptions +++whose names match @var{regexp} are listed. +++@end table +++ +++Below is a small example, showing how the command can be used, first +++without argument, and next with a regular expression passed as an +++argument. +++ +++@smallexample +++(@value{GDBP}) info exceptions +++All defined Ada exceptions: +++constraint_error: 0x613da0 +++program_error: 0x613d20 +++storage_error: 0x613ce0 +++tasking_error: 0x613ca0 +++const.aint_global_e: 0x613b00 +++(@value{GDBP}) info exceptions const.aint +++All Ada exceptions matching regular expression "const.aint": +++constraint_error: 0x613da0 +++const.aint_global_e: 0x613b00 +++@end smallexample +++ +++It is also possible to ask @value{GDBN} to stop your program's execution +++when an exception is raised. For more details, see @ref{Set Catchpoints}. +++ +++@node Ada Tasks +++@subsubsection Extensions for Ada Tasks +++@cindex Ada, tasking +++ +++Support for Ada tasks is analogous to that for threads (@pxref{Threads}). +++@value{GDBN} provides the following task-related commands: +++ +++@table @code +++@kindex info tasks +++@item info tasks +++This command shows a list of current Ada tasks, as in the following example: +++ +++ +++@smallexample +++@iftex +++@leftskip=0.5cm +++@end iftex +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 8088000 0 15 Child Activation Wait main_task +++ 2 80a4000 1 15 Accept Statement b +++ 3 809a800 1 15 Child Activation Wait a +++* 4 80ae800 3 15 Runnable c +++ +++@end smallexample +++ +++@noindent +++In this listing, the asterisk before the last task indicates it to be the +++task currently being inspected. +++ +++@table @asis +++@item ID +++Represents @value{GDBN}'s internal task number. +++ +++@item TID +++The Ada task ID. +++ +++@item P-ID +++The parent's task ID (@value{GDBN}'s internal task number). +++ +++@item Pri +++The base priority of the task. +++ +++@item State +++Current state of the task. +++ +++@table @code +++@item Unactivated +++The task has been created but has not been activated. It cannot be +++executing. +++ +++@item Runnable +++The task is not blocked for any reason known to Ada. (It may be waiting +++for a mutex, though.) It is conceptually "executing" in normal mode. +++ +++@item Terminated +++The task is terminated, in the sense of ARM 9.3 (5). Any dependents +++that were waiting on terminate alternatives have been awakened and have +++terminated themselves. +++ +++@item Child Activation Wait +++The task is waiting for created tasks to complete activation. +++ +++@item Accept Statement +++The task is waiting on an accept or selective wait statement. +++ +++@item Waiting on entry call +++The task is waiting on an entry call. +++ +++@item Async Select Wait +++The task is waiting to start the abortable part of an asynchronous +++select statement. +++ +++@item Delay Sleep +++The task is waiting on a select statement with only a delay +++alternative open. +++ +++@item Child Termination Wait +++The task is sleeping having completed a master within itself, and is +++waiting for the tasks dependent on that master to become terminated or +++waiting on a terminate Phase. +++ +++@item Wait Child in Term Alt +++The task is sleeping waiting for tasks on terminate alternatives to +++finish terminating. +++ +++@item Accepting RV with @var{taskno} +++The task is accepting a rendez-vous with the task @var{taskno}. +++@end table +++ +++@item Name +++Name of the task in the program. +++ +++@end table +++ +++@kindex info task @var{taskno} +++@item info task @var{taskno} +++This command shows detailed informations on the specified task, as in +++the following example: +++@smallexample +++@iftex +++@leftskip=0.5cm +++@end iftex +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 8077880 0 15 Child Activation Wait main_task +++* 2 807c468 1 15 Runnable task_1 +++(@value{GDBP}) info task 2 +++Ada Task: 0x807c468 +++Name: "task_1" +++Thread: 0 +++LWP: 0x1fac +++Parent: 1 ("main_task") +++Base Priority: 15 +++State: Runnable +++@end smallexample +++ +++@item task +++@kindex task@r{ (Ada)} +++@cindex current Ada task ID +++This command prints the ID and name of the current task. +++ +++@smallexample +++@iftex +++@leftskip=0.5cm +++@end iftex +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 8077870 0 15 Child Activation Wait main_task +++* 2 807c458 1 15 Runnable some_task +++(@value{GDBP}) task +++[Current task is 2 "some_task"] +++@end smallexample +++ +++@item task @var{taskno} +++@cindex Ada task switching +++This command is like the @code{thread @var{thread-id}} +++command (@pxref{Threads}). It switches the context of debugging +++from the current task to the given task. +++ +++@smallexample +++@iftex +++@leftskip=0.5cm +++@end iftex +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 8077870 0 15 Child Activation Wait main_task +++* 2 807c458 1 15 Runnable some_task +++(@value{GDBP}) task 1 +++[Switching to task 1 "main_task"] +++#0 0x8067726 in pthread_cond_wait () +++(@value{GDBP}) bt +++#0 0x8067726 in pthread_cond_wait () +++#1 0x8056714 in system.os_interface.pthread_cond_wait () +++#2 0x805cb63 in system.task_primitives.operations.sleep () +++#3 0x806153e in system.tasking.stages.activate_tasks () +++#4 0x804aacc in un () at un.adb:5 +++@end smallexample +++ +++@item break @var{location} task @var{taskno} +++@itemx break @var{location} task @var{taskno} if @dots{} +++@cindex breakpoints and tasks, in Ada +++@cindex task breakpoints, in Ada +++@kindex break @dots{} task @var{taskno}@r{ (Ada)} +++These commands are like the @code{break @dots{} thread @dots{}} +++command (@pxref{Thread Stops}). The +++@var{location} argument specifies source lines, as described +++in @ref{Specify Location}. +++ +++Use the qualifier @samp{task @var{taskno}} with a breakpoint command +++to specify that you only want @value{GDBN} to stop the program when a +++particular Ada task reaches this breakpoint. The @var{taskno} is one of the +++numeric task identifiers assigned by @value{GDBN}, shown in the first +++column of the @samp{info tasks} display. +++ +++If you do not specify @samp{task @var{taskno}} when you set a +++breakpoint, the breakpoint applies to @emph{all} tasks of your +++program. +++ +++You can use the @code{task} qualifier on conditional breakpoints as +++well; in this case, place @samp{task @var{taskno}} before the +++breakpoint condition (before the @code{if}). +++ +++For example, +++ +++@smallexample +++@iftex +++@leftskip=0.5cm +++@end iftex +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 140022020 0 15 Child Activation Wait main_task +++ 2 140045060 1 15 Accept/Select Wait t2 +++ 3 140044840 1 15 Runnable t1 +++* 4 140056040 1 15 Runnable t3 +++(@value{GDBP}) b 15 task 2 +++Breakpoint 5 at 0x120044cb0: file test_task_debug.adb, line 15. +++(@value{GDBP}) cont +++Continuing. +++task # 1 running +++task # 2 running +++ +++Breakpoint 5, test_task_debug () at test_task_debug.adb:15 +++15 flush; +++(@value{GDBP}) info tasks +++ ID TID P-ID Pri State Name +++ 1 140022020 0 15 Child Activation Wait main_task +++* 2 140045060 1 15 Runnable t2 +++ 3 140044840 1 15 Runnable t1 +++ 4 140056040 1 15 Delay Sleep t3 +++@end smallexample +++@end table +++ +++@node Ada Tasks and Core Files +++@subsubsection Tasking Support when Debugging Core Files +++@cindex Ada tasking and core file debugging +++ +++When inspecting a core file, as opposed to debugging a live program, +++tasking support may be limited or even unavailable, depending on +++the platform being used. +++For instance, on x86-linux, the list of tasks is available, but task +++switching is not supported. +++ +++On certain platforms, the debugger needs to perform some +++memory writes in order to provide Ada tasking support. When inspecting +++a core file, this means that the core file must be opened with read-write +++privileges, using the command @samp{"set write on"} (@pxref{Patching}). +++Under these circumstances, you should make a backup copy of the core +++file before inspecting it with @value{GDBN}. +++ +++@node Ravenscar Profile +++@subsubsection Tasking Support when using the Ravenscar Profile +++@cindex Ravenscar Profile +++ +++The @dfn{Ravenscar Profile} is a subset of the Ada tasking features, +++specifically designed for systems with safety-critical real-time +++requirements. +++ +++@table @code +++@kindex set ravenscar task-switching on +++@cindex task switching with program using Ravenscar Profile +++@item set ravenscar task-switching on +++Allows task switching when debugging a program that uses the Ravenscar +++Profile. This is the default. +++ +++@kindex set ravenscar task-switching off +++@item set ravenscar task-switching off +++Turn off task switching when debugging a program that uses the Ravenscar +++Profile. This is mostly intended to disable the code that adds support +++for the Ravenscar Profile, in case a bug in either @value{GDBN} or in +++the Ravenscar runtime is preventing @value{GDBN} from working properly. +++To be effective, this command should be run before the program is started. +++ +++@kindex show ravenscar task-switching +++@item show ravenscar task-switching +++Show whether it is possible to switch from task to task in a program +++using the Ravenscar Profile. +++ +++@end table +++ +++@cindex Ravenscar thread +++When Ravenscar task-switching is enabled, Ravenscar tasks are +++announced by @value{GDBN} as if they were threads: +++ +++@smallexample +++(gdb) continue +++[New Ravenscar Thread 0x2b8f0] +++@end smallexample +++ +++Both Ravenscar tasks and the underlying CPU threads will show up in +++the output of @code{info threads}: +++ +++@smallexample +++(gdb) info threads +++ Id Target Id Frame +++ 1 Thread 1 (CPU#0 [running]) simple () at simple.adb:10 +++ 2 Thread 2 (CPU#1 [running]) 0x0000000000003d34 in __gnat_initialize_cpu_devices () +++ 3 Thread 3 (CPU#2 [running]) 0x0000000000003d28 in __gnat_initialize_cpu_devices () +++ 4 Thread 4 (CPU#3 [halted ]) 0x000000000000c6ec in system.task_primitives.operations.idle () +++* 5 Ravenscar Thread 0x2b8f0 simple () at simple.adb:10 +++ 6 Ravenscar Thread 0x2f150 0x000000000000c6ec in system.task_primitives.operations.idle () +++@end smallexample +++ +++One known limitation of the Ravenscar support in @value{GDBN} is that +++it isn't currently possible to single-step through the runtime +++initialization sequence. If you need to debug this code, you should +++use @code{set ravenscar task-switching off}. +++ +++@node Ada Settings +++@subsubsection Ada Settings +++@cindex Ada settings +++ +++@table @code +++@kindex set varsize-limit +++@item set varsize-limit @var{size} +++Prevent @value{GDBN} from attempting to evaluate objects whose size +++is above the given limit (@var{size}) when those sizes are computed +++from run-time quantities. This is typically the case when the object +++has a variable size, such as an array whose bounds are not known at +++compile time for example. Setting @var{size} to @code{unlimited} +++removes the size limitation. By default, the limit is about 65KB. +++ +++The purpose of having such a limit is to prevent @value{GDBN} from +++trying to grab enormous chunks of virtual memory when asked to evaluate +++a quantity whose bounds have been corrupted or have not yet been fully +++initialized. The limit applies to the results of some subexpressions +++as well as to complete expressions. For example, an expression denoting +++a simple integer component, such as @code{x.y.z}, may fail if the size of +++@code{x.y} is variable and exceeds @code{size}. On the other hand, +++@value{GDBN} is sometimes clever; the expression @code{A(i)}, where +++@code{A} is an array variable with non-constant size, will generally +++succeed regardless of the bounds on @code{A}, as long as the component +++size is less than @var{size}. +++ +++@kindex show varsize-limit +++@item show varsize-limit +++Show the limit on types whose size is determined by run-time quantities. +++@end table +++ +++@node Ada Glitches +++@subsubsection Known Peculiarities of Ada Mode +++@cindex Ada, problems +++ +++Besides the omissions listed previously (@pxref{Omissions from Ada}), +++we know of several problems with and limitations of Ada mode in +++@value{GDBN}, +++some of which will be fixed with planned future releases of the debugger +++and the GNU Ada compiler. +++ +++@itemize @bullet +++@item +++Static constants that the compiler chooses not to materialize as objects in +++storage are invisible to the debugger. +++ +++@item +++Named parameter associations in function argument lists are ignored (the +++argument lists are treated as positional). +++ +++@item +++Many useful library packages are currently invisible to the debugger. +++ +++@item +++Fixed-point arithmetic, conversions, input, and output is carried out using +++floating-point arithmetic, and may give results that only approximate those on +++the host machine. +++ +++@item +++The GNAT compiler never generates the prefix @code{Standard} for any of +++the standard symbols defined by the Ada language. @value{GDBN} knows about +++this: it will strip the prefix from names when you use it, and will never +++look for a name you have so qualified among local symbols, nor match against +++symbols in other packages or subprograms. If you have +++defined entities anywhere in your program other than parameters and +++local variables whose simple names match names in @code{Standard}, +++GNAT's lack of qualification here can cause confusion. When this happens, +++you can usually resolve the confusion +++by qualifying the problematic names with package +++@code{Standard} explicitly. +++@end itemize +++ +++Older versions of the compiler sometimes generate erroneous debugging +++information, resulting in the debugger incorrectly printing the value +++of affected entities. In some cases, the debugger is able to work +++around an issue automatically. In other cases, the debugger is able +++to work around the issue, but the work-around has to be specifically +++enabled. +++ +++@kindex set ada trust-PAD-over-XVS +++@kindex show ada trust-PAD-over-XVS +++@table @code +++ +++@item set ada trust-PAD-over-XVS on +++Configure GDB to strictly follow the GNAT encoding when computing the +++value of Ada entities, particularly when @code{PAD} and @code{PAD___XVS} +++types are involved (see @code{ada/exp_dbug.ads} in the GCC sources for +++a complete description of the encoding used by the GNAT compiler). +++This is the default. +++ +++@item set ada trust-PAD-over-XVS off +++This is related to the encoding using by the GNAT compiler. If @value{GDBN} +++sometimes prints the wrong value for certain entities, changing @code{ada +++trust-PAD-over-XVS} to @code{off} activates a work-around which may fix +++the issue. It is always safe to set @code{ada trust-PAD-over-XVS} to +++@code{off}, but this incurs a slight performance penalty, so it is +++recommended to leave this setting to @code{on} unless necessary. +++ +++@end table +++ +++@cindex GNAT descriptive types +++@cindex GNAT encoding +++Internally, the debugger also relies on the compiler following a number +++of conventions known as the @samp{GNAT Encoding}, all documented in +++@file{gcc/ada/exp_dbug.ads} in the GCC sources. This encoding describes +++how the debugging information should be generated for certain types. +++In particular, this convention makes use of @dfn{descriptive types}, +++which are artificial types generated purely to help the debugger. +++ +++These encodings were defined at a time when the debugging information +++format used was not powerful enough to describe some of the more complex +++types available in Ada. Since DWARF allows us to express nearly all +++Ada features, the long-term goal is to slowly replace these descriptive +++types by their pure DWARF equivalent. To facilitate that transition, +++a new maintenance option is available to force the debugger to ignore +++those descriptive types. It allows the user to quickly evaluate how +++well @value{GDBN} works without them. +++ +++@table @code +++ +++@kindex maint ada set ignore-descriptive-types +++@item maintenance ada set ignore-descriptive-types [on|off] +++Control whether the debugger should ignore descriptive types. +++The default is not to ignore descriptives types (@code{off}). +++ +++@kindex maint ada show ignore-descriptive-types +++@item maintenance ada show ignore-descriptive-types +++Show if descriptive types are ignored by @value{GDBN}. +++ +++@end table +++ +++@node Unsupported Languages +++@section Unsupported Languages +++ +++@cindex unsupported languages +++@cindex minimal language +++In addition to the other fully-supported programming languages, +++@value{GDBN} also provides a pseudo-language, called @code{minimal}. +++It does not represent a real programming language, but provides a set +++of capabilities close to what the C or assembly languages provide. +++This should allow most simple operations to be performed while debugging +++an application that uses a language currently not supported by @value{GDBN}. +++ +++If the language is set to @code{auto}, @value{GDBN} will automatically +++select this language if the current frame corresponds to an unsupported +++language. +++ +++@node Symbols +++@chapter Examining the Symbol Table +++ +++The commands described in this chapter allow you to inquire about the +++symbols (names of variables, functions and types) defined in your +++program. This information is inherent in the text of your program and +++does not change as your program executes. @value{GDBN} finds it in your +++program's symbol table, in the file indicated when you started @value{GDBN} +++(@pxref{File Options, ,Choosing Files}), or by one of the +++file-management commands (@pxref{Files, ,Commands to Specify Files}). +++ +++@cindex symbol names +++@cindex names of symbols +++@cindex quoting names +++@anchor{quoting names} +++Occasionally, you may need to refer to symbols that contain unusual +++characters, which @value{GDBN} ordinarily treats as word delimiters. The +++most frequent case is in referring to static variables in other +++source files (@pxref{Variables,,Program Variables}). File names +++are recorded in object files as debugging symbols, but @value{GDBN} would +++ordinarily parse a typical file name, like @file{foo.c}, as the three words +++@samp{foo} @samp{.} @samp{c}. To allow @value{GDBN} to recognize +++@samp{foo.c} as a single symbol, enclose it in single quotes; for example, +++ +++@smallexample +++p 'foo.c'::x +++@end smallexample +++ +++@noindent +++looks up the value of @code{x} in the scope of the file @file{foo.c}. +++ +++@table @code +++@cindex case-insensitive symbol names +++@cindex case sensitivity in symbol names +++@kindex set case-sensitive +++@item set case-sensitive on +++@itemx set case-sensitive off +++@itemx set case-sensitive auto +++Normally, when @value{GDBN} looks up symbols, it matches their names +++with case sensitivity determined by the current source language. +++Occasionally, you may wish to control that. The command @code{set +++case-sensitive} lets you do that by specifying @code{on} for +++case-sensitive matches or @code{off} for case-insensitive ones. If +++you specify @code{auto}, case sensitivity is reset to the default +++suitable for the source language. The default is case-sensitive +++matches for all languages except for Fortran, for which the default is +++case-insensitive matches. +++ +++@kindex show case-sensitive +++@item show case-sensitive +++This command shows the current setting of case sensitivity for symbols +++lookups. +++ +++@kindex set print type methods +++@item set print type methods +++@itemx set print type methods on +++@itemx set print type methods off +++Normally, when @value{GDBN} prints a class, it displays any methods +++declared in that class. You can control this behavior either by +++passing the appropriate flag to @code{ptype}, or using @command{set +++print type methods}. Specifying @code{on} will cause @value{GDBN} to +++display the methods; this is the default. Specifying @code{off} will +++cause @value{GDBN} to omit the methods. +++ +++@kindex show print type methods +++@item show print type methods +++This command shows the current setting of method display when printing +++classes. +++ +++@kindex set print type nested-type-limit +++@item set print type nested-type-limit @var{limit} +++@itemx set print type nested-type-limit unlimited +++Set the limit of displayed nested types that the type printer will +++show. A @var{limit} of @code{unlimited} or @code{-1} will show all +++nested definitions. By default, the type printer will not show any nested +++types defined in classes. +++ +++@kindex show print type nested-type-limit +++@item show print type nested-type-limit +++This command shows the current display limit of nested types when +++printing classes. +++ +++@kindex set print type typedefs +++@item set print type typedefs +++@itemx set print type typedefs on +++@itemx set print type typedefs off +++ +++Normally, when @value{GDBN} prints a class, it displays any typedefs +++defined in that class. You can control this behavior either by +++passing the appropriate flag to @code{ptype}, or using @command{set +++print type typedefs}. Specifying @code{on} will cause @value{GDBN} to +++display the typedef definitions; this is the default. Specifying +++@code{off} will cause @value{GDBN} to omit the typedef definitions. +++Note that this controls whether the typedef definition itself is +++printed, not whether typedef names are substituted when printing other +++types. +++ +++@kindex show print type typedefs +++@item show print type typedefs +++This command shows the current setting of typedef display when +++printing classes. +++ +++@kindex info address +++@cindex address of a symbol +++@item info address @var{symbol} +++Describe where the data for @var{symbol} is stored. For a register +++variable, this says which register it is kept in. For a non-register +++local variable, this prints the stack-frame offset at which the variable +++is always stored. +++ +++Note the contrast with @samp{print &@var{symbol}}, which does not work +++at all for a register variable, and for a stack local variable prints +++the exact address of the current instantiation of the variable. +++ +++@kindex info symbol +++@cindex symbol from address +++@cindex closest symbol and offset for an address +++@item info symbol @var{addr} +++Print the name of a symbol which is stored at the address @var{addr}. +++If no symbol is stored exactly at @var{addr}, @value{GDBN} prints the +++nearest symbol and an offset from it: +++ +++@smallexample +++(@value{GDBP}) info symbol 0x54320 +++_initialize_vx + 396 in section .text +++@end smallexample +++ +++@noindent +++This is the opposite of the @code{info address} command. You can use +++it to find out the name of a variable or a function given its address. +++ +++For dynamically linked executables, the name of executable or shared +++library containing the symbol is also printed: +++ +++@smallexample +++(@value{GDBP}) info symbol 0x400225 +++_start + 5 in section .text of /tmp/a.out +++(@value{GDBP}) info symbol 0x2aaaac2811cf +++__read_nocancel + 6 in section .text of /usr/lib64/libc.so.6 +++@end smallexample +++ +++@kindex demangle +++@cindex demangle +++@item demangle @r{[}-l @var{language}@r{]} @r{[}@var{--}@r{]} @var{name} +++Demangle @var{name}. +++If @var{language} is provided it is the name of the language to demangle +++@var{name} in. Otherwise @var{name} is demangled in the current language. +++ +++The @samp{--} option specifies the end of options, +++and is useful when @var{name} begins with a dash. +++ +++The parameter @code{demangle-style} specifies how to interpret the kind +++of mangling used. @xref{Print Settings}. +++ +++@kindex whatis +++@item whatis[/@var{flags}] [@var{arg}] +++Print the data type of @var{arg}, which can be either an expression +++or a name of a data type. With no argument, print the data type of +++@code{$}, the last value in the value history. +++ +++If @var{arg} is an expression (@pxref{Expressions, ,Expressions}), it +++is not actually evaluated, and any side-effecting operations (such as +++assignments or function calls) inside it do not take place. +++ +++If @var{arg} is a variable or an expression, @code{whatis} prints its +++literal type as it is used in the source code. If the type was +++defined using a @code{typedef}, @code{whatis} will @emph{not} print +++the data type underlying the @code{typedef}. If the type of the +++variable or the expression is a compound data type, such as +++@code{struct} or @code{class}, @code{whatis} never prints their +++fields or methods. It just prints the @code{struct}/@code{class} +++name (a.k.a.@: its @dfn{tag}). If you want to see the members of +++such a compound data type, use @code{ptype}. +++ +++If @var{arg} is a type name that was defined using @code{typedef}, +++@code{whatis} @dfn{unrolls} only one level of that @code{typedef}. +++Unrolling means that @code{whatis} will show the underlying type used +++in the @code{typedef} declaration of @var{arg}. However, if that +++underlying type is also a @code{typedef}, @code{whatis} will not +++unroll it. +++ +++For C code, the type names may also have the form @samp{class +++@var{class-name}}, @samp{struct @var{struct-tag}}, @samp{union +++@var{union-tag}} or @samp{enum @var{enum-tag}}. +++ +++@var{flags} can be used to modify how the type is displayed. +++Available flags are: +++ +++@table @code +++@item r +++Display in ``raw'' form. Normally, @value{GDBN} substitutes template +++parameters and typedefs defined in a class when printing the class' +++members. The @code{/r} flag disables this. +++ +++@item m +++Do not print methods defined in the class. +++ +++@item M +++Print methods defined in the class. This is the default, but the flag +++exists in case you change the default with @command{set print type methods}. +++ +++@item t +++Do not print typedefs defined in the class. Note that this controls +++whether the typedef definition itself is printed, not whether typedef +++names are substituted when printing other types. +++ +++@item T +++Print typedefs defined in the class. This is the default, but the flag +++exists in case you change the default with @command{set print type typedefs}. +++ +++@item o +++Print the offsets and sizes of fields in a struct, similar to what the +++@command{pahole} tool does. This option implies the @code{/tm} flags. +++ +++For example, given the following declarations: +++ +++@smallexample +++struct tuv +++@{ +++ int a1; +++ char *a2; +++ int a3; +++@}; +++ +++struct xyz +++@{ +++ int f1; +++ char f2; +++ void *f3; +++ struct tuv f4; +++@}; +++ +++union qwe +++@{ +++ struct tuv fff1; +++ struct xyz fff2; +++@}; +++ +++struct tyu +++@{ +++ int a1 : 1; +++ int a2 : 3; +++ int a3 : 23; +++ char a4 : 2; +++ int64_t a5; +++ int a6 : 5; +++ int64_t a7 : 3; +++@}; +++@end smallexample +++ +++Issuing a @kbd{ptype /o struct tuv} command would print: +++ +++@smallexample +++(@value{GDBP}) ptype /o struct tuv +++/* offset | size */ type = struct tuv @{ +++/* 0 | 4 */ int a1; +++/* XXX 4-byte hole */ +++/* 8 | 8 */ char *a2; +++/* 16 | 4 */ int a3; +++ +++ /* total size (bytes): 24 */ +++ @} +++@end smallexample +++ +++Notice the format of the first column of comments. There, you can +++find two parts separated by the @samp{|} character: the @emph{offset}, +++which indicates where the field is located inside the struct, in +++bytes, and the @emph{size} of the field. Another interesting line is +++the marker of a @emph{hole} in the struct, indicating that it may be +++possible to pack the struct and make it use less space by reorganizing +++its fields. +++ +++It is also possible to print offsets inside an union: +++ +++@smallexample +++(@value{GDBP}) ptype /o union qwe +++/* offset | size */ type = union qwe @{ +++/* 24 */ struct tuv @{ +++/* 0 | 4 */ int a1; +++/* XXX 4-byte hole */ +++/* 8 | 8 */ char *a2; +++/* 16 | 4 */ int a3; +++ +++ /* total size (bytes): 24 */ +++ @} fff1; +++/* 40 */ struct xyz @{ +++/* 0 | 4 */ int f1; +++/* 4 | 1 */ char f2; +++/* XXX 3-byte hole */ +++/* 8 | 8 */ void *f3; +++/* 16 | 24 */ struct tuv @{ +++/* 16 | 4 */ int a1; +++/* XXX 4-byte hole */ +++/* 24 | 8 */ char *a2; +++/* 32 | 4 */ int a3; +++ +++ /* total size (bytes): 24 */ +++ @} f4; +++ +++ /* total size (bytes): 40 */ +++ @} fff2; +++ +++ /* total size (bytes): 40 */ +++ @} +++@end smallexample +++ +++In this case, since @code{struct tuv} and @code{struct xyz} occupy the +++same space (because we are dealing with an union), the offset is not +++printed for them. However, you can still examine the offset of each +++of these structures' fields. +++ +++Another useful scenario is printing the offsets of a struct containing +++bitfields: +++ +++@smallexample +++(@value{GDBP}) ptype /o struct tyu +++/* offset | size */ type = struct tyu @{ +++/* 0:31 | 4 */ int a1 : 1; +++/* 0:28 | 4 */ int a2 : 3; +++/* 0: 5 | 4 */ int a3 : 23; +++/* 3: 3 | 1 */ signed char a4 : 2; +++/* XXX 3-bit hole */ +++/* XXX 4-byte hole */ +++/* 8 | 8 */ int64_t a5; +++/* 16: 0 | 4 */ int a6 : 5; +++/* 16: 5 | 8 */ int64_t a7 : 3; +++"/* XXX 7-byte padding */ +++ +++ /* total size (bytes): 24 */ +++ @} +++@end smallexample +++ +++Note how the offset information is now extended to also include the +++first bit of the bitfield. +++@end table +++ +++@kindex ptype +++@item ptype[/@var{flags}] [@var{arg}] +++@code{ptype} accepts the same arguments as @code{whatis}, but prints a +++detailed description of the type, instead of just the name of the type. +++@xref{Expressions, ,Expressions}. +++ +++Contrary to @code{whatis}, @code{ptype} always unrolls any +++@code{typedef}s in its argument declaration, whether the argument is +++a variable, expression, or a data type. This means that @code{ptype} +++of a variable or an expression will not print literally its type as +++present in the source code---use @code{whatis} for that. @code{typedef}s at +++the pointer or reference targets are also unrolled. Only @code{typedef}s of +++fields, methods and inner @code{class typedef}s of @code{struct}s, +++@code{class}es and @code{union}s are not unrolled even with @code{ptype}. +++ +++For example, for this variable declaration: +++ +++@smallexample +++typedef double real_t; +++struct complex @{ real_t real; double imag; @}; +++typedef struct complex complex_t; +++complex_t var; +++real_t *real_pointer_var; +++@end smallexample +++ +++@noindent +++the two commands give this output: +++ +++@smallexample +++@group +++(@value{GDBP}) whatis var +++type = complex_t +++(@value{GDBP}) ptype var +++type = struct complex @{ +++ real_t real; +++ double imag; +++@} +++(@value{GDBP}) whatis complex_t +++type = struct complex +++(@value{GDBP}) whatis struct complex +++type = struct complex +++(@value{GDBP}) ptype struct complex +++type = struct complex @{ +++ real_t real; +++ double imag; +++@} +++(@value{GDBP}) whatis real_pointer_var +++type = real_t * +++(@value{GDBP}) ptype real_pointer_var +++type = double * +++@end group +++@end smallexample +++ +++@noindent +++As with @code{whatis}, using @code{ptype} without an argument refers to +++the type of @code{$}, the last value in the value history. +++ +++@cindex incomplete type +++Sometimes, programs use opaque data types or incomplete specifications +++of complex data structure. If the debug information included in the +++program does not allow @value{GDBN} to display a full declaration of +++the data type, it will say @samp{}. For example, +++given these declarations: +++ +++@smallexample +++ struct foo; +++ struct foo *fooptr; +++@end smallexample +++ +++@noindent +++but no definition for @code{struct foo} itself, @value{GDBN} will say: +++ +++@smallexample +++ (@value{GDBP}) ptype foo +++ $1 = +++@end smallexample +++ +++@noindent +++``Incomplete type'' is C terminology for data types that are not +++completely specified. +++ +++@cindex unknown type +++Othertimes, information about a variable's type is completely absent +++from the debug information included in the program. This most often +++happens when the program or library where the variable is defined +++includes no debug information at all. @value{GDBN} knows the variable +++exists from inspecting the linker/loader symbol table (e.g., the ELF +++dynamic symbol table), but such symbols do not contain type +++information. Inspecting the type of a (global) variable for which +++@value{GDBN} has no type information shows: +++ +++@smallexample +++ (@value{GDBP}) ptype var +++ type = +++@end smallexample +++ +++@xref{Variables, no debug info variables}, for how to print the values +++of such variables. +++ +++@kindex info types +++@item info types [-q] [@var{regexp}] +++Print a brief description of all types whose names match the regular +++expression @var{regexp} (or all types in your program, if you supply +++no argument). Each complete typename is matched as though it were a +++complete line; thus, @samp{i type value} gives information on all +++types in your program whose names include the string @code{value}, but +++@samp{i type ^value$} gives information only on types whose complete +++name is @code{value}. +++ +++In programs using different languages, @value{GDBN} chooses the syntax +++to print the type description according to the +++@samp{set language} value: using @samp{set language auto} +++(see @ref{Automatically, ,Set Language Automatically}) means to use the +++language of the type, other values mean to use +++the manually specified language (see @ref{Manually, ,Set Language Manually}). +++ +++This command differs from @code{ptype} in two ways: first, like +++@code{whatis}, it does not print a detailed description; second, it +++lists all source files and line numbers where a type is defined. +++ +++The output from @samp{into types} is proceeded with a header line +++describing what types are being listed. The optional flag @samp{-q}, +++which stands for @samp{quiet}, disables printing this header +++information. +++ +++@kindex info type-printers +++@item info type-printers +++Versions of @value{GDBN} that ship with Python scripting enabled may +++have ``type printers'' available. When using @command{ptype} or +++@command{whatis}, these printers are consulted when the name of a type +++is needed. @xref{Type Printing API}, for more information on writing +++type printers. +++ +++@code{info type-printers} displays all the available type printers. +++ +++@kindex enable type-printer +++@kindex disable type-printer +++@item enable type-printer @var{name}@dots{} +++@item disable type-printer @var{name}@dots{} +++These commands can be used to enable or disable type printers. +++ +++@kindex info scope +++@cindex local variables +++@item info scope @var{location} +++List all the variables local to a particular scope. This command +++accepts a @var{location} argument---a function name, a source line, or +++an address preceded by a @samp{*}, and prints all the variables local +++to the scope defined by that location. (@xref{Specify Location}, for +++details about supported forms of @var{location}.) For example: +++ +++@smallexample +++(@value{GDBP}) @b{info scope command_line_handler} +++Scope for command_line_handler: +++Symbol rl is an argument at stack/frame offset 8, length 4. +++Symbol linebuffer is in static storage at address 0x150a18, length 4. +++Symbol linelength is in static storage at address 0x150a1c, length 4. +++Symbol p is a local variable in register $esi, length 4. +++Symbol p1 is a local variable in register $ebx, length 4. +++Symbol nline is a local variable in register $edx, length 4. +++Symbol repeat is a local variable at frame offset -8, length 4. +++@end smallexample +++ +++@noindent +++This command is especially useful for determining what data to collect +++during a @dfn{trace experiment}, see @ref{Tracepoint Actions, +++collect}. +++ +++@kindex info source +++@item info source +++Show information about the current source file---that is, the source file for +++the function containing the current point of execution: +++@itemize @bullet +++@item +++the name of the source file, and the directory containing it, +++@item +++the directory it was compiled in, +++@item +++its length, in lines, +++@item +++which programming language it is written in, +++@item +++if the debug information provides it, the program that compiled the file +++(which may include, e.g., the compiler version and command line arguments), +++@item +++whether the executable includes debugging information for that file, and +++if so, what format the information is in (e.g., STABS, Dwarf 2, etc.), and +++@item +++whether the debugging information includes information about +++preprocessor macros. +++@end itemize +++ +++ +++@kindex info sources +++@item info sources +++Print the names of all source files in your program for which there is +++debugging information, organized into two lists: files whose symbols +++have already been read, and files whose symbols will be read when needed. +++ +++@item info sources [-dirname | -basename] [--] [@var{regexp}] +++Like @samp{info sources}, but only print the names of the files +++matching the provided @var{regexp}. +++By default, the @var{regexp} is used to match anywhere in the filename. +++If @code{-dirname}, only files having a dirname matching @var{regexp} are shown. +++If @code{-basename}, only files having a basename matching @var{regexp} +++are shown. +++The matching is case-sensitive, except on operating systems that +++have case-insensitive filesystem (e.g., MS-Windows). +++ +++@kindex info functions +++@item info functions [-q] [-n] +++Print the names and data types of all defined functions. +++Similarly to @samp{info types}, this command groups its output by source +++files and annotates each function definition with its source line +++number. +++ +++In programs using different languages, @value{GDBN} chooses the syntax +++to print the function name and type according to the +++@samp{set language} value: using @samp{set language auto} +++(see @ref{Automatically, ,Set Language Automatically}) means to use the +++language of the function, other values mean to use +++the manually specified language (see @ref{Manually, ,Set Language Manually}). +++ +++The @samp{-n} flag excludes @dfn{non-debugging symbols} from the +++results. A non-debugging symbol is a symbol that comes from the +++executable's symbol table, not from the debug information (for +++example, DWARF) associated with the executable. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no functions +++have been printed. +++ +++@item info functions [-q] [-n] [-t @var{type_regexp}] [@var{regexp}] +++Like @samp{info functions}, but only print the names and data types +++of the functions selected with the provided regexp(s). +++ +++If @var{regexp} is provided, print only the functions whose names +++match the regular expression @var{regexp}. +++Thus, @samp{info fun step} finds all functions whose +++names include @code{step}; @samp{info fun ^step} finds those whose names +++start with @code{step}. If a function name contains characters that +++conflict with the regular expression language (e.g.@: +++@samp{operator*()}), they may be quoted with a backslash. +++ +++If @var{type_regexp} is provided, print only the functions whose +++types, as printed by the @code{whatis} command, match +++the regular expression @var{type_regexp}. +++If @var{type_regexp} contains space(s), it should be enclosed in +++quote characters. If needed, use backslash to escape the meaning +++of special characters or quotes. +++Thus, @samp{info fun -t '^int ('} finds the functions that return +++an integer; @samp{info fun -t '(.*int.*'} finds the functions that +++have an argument type containing int; @samp{info fun -t '^int (' ^step} +++finds the functions whose names start with @code{step} and that return +++int. +++ +++If both @var{regexp} and @var{type_regexp} are provided, a function +++is printed only if its name matches @var{regexp} and its type matches +++@var{type_regexp}. +++ +++ +++@kindex info variables +++@item info variables [-q] [-n] +++Print the names and data types of all variables that are defined +++outside of functions (i.e.@: excluding local variables). +++The printed variables are grouped by source files and annotated with +++their respective source line numbers. +++ +++In programs using different languages, @value{GDBN} chooses the syntax +++to print the variable name and type according to the +++@samp{set language} value: using @samp{set language auto} +++(see @ref{Automatically, ,Set Language Automatically}) means to use the +++language of the variable, other values mean to use +++the manually specified language (see @ref{Manually, ,Set Language Manually}). +++ +++The @samp{-n} flag excludes non-debugging symbols from the results. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no variables +++have been printed. +++ +++@item info variables [-q] [-n] [-t @var{type_regexp}] [@var{regexp}] +++Like @kbd{info variables}, but only print the variables selected +++with the provided regexp(s). +++ +++If @var{regexp} is provided, print only the variables whose names +++match the regular expression @var{regexp}. +++ +++If @var{type_regexp} is provided, print only the variables whose +++types, as printed by the @code{whatis} command, match +++the regular expression @var{type_regexp}. +++If @var{type_regexp} contains space(s), it should be enclosed in +++quote characters. If needed, use backslash to escape the meaning +++of special characters or quotes. +++ +++If both @var{regexp} and @var{type_regexp} are provided, an argument +++is printed only if its name matches @var{regexp} and its type matches +++@var{type_regexp}. +++ +++@kindex info modules +++@cindex modules +++@item info modules @r{[}-q@r{]} @r{[}@var{regexp}@r{]} +++List all Fortran modules in the program, or all modules matching the +++optional regular expression @var{regexp}. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no modules +++have been printed. +++ +++@kindex info module +++@cindex Fortran modules, information about +++@cindex functions and variables by Fortran module +++@cindex module functions and variables +++@item info module functions @r{[}-q@r{]} @r{[}-m @var{module-regexp}@r{]} @r{[}-t @var{type-regexp}@r{]} @r{[}@var{regexp}@r{]} +++@itemx info module variables @r{[}-q@r{]} @r{[}-m @var{module-regexp}@r{]} @r{[}-t @var{type-regexp}@r{]} @r{[}@var{regexp}@r{]} +++List all functions or variables within all Fortran modules. The set +++of functions or variables listed can be limited by providing some or +++all of the optional regular expressions. If @var{module-regexp} is +++provided, then only Fortran modules matching @var{module-regexp} will +++be searched. Only functions or variables whose type matches the +++optional regular expression @var{type-regexp} will be listed. And +++only functions or variables whose name matches the optional regular +++expression @var{regexp} will be listed. +++ +++The optional flag @samp{-q}, which stands for @samp{quiet}, disables +++printing header information and messages explaining why no functions +++or variables have been printed. +++ +++@kindex info classes +++@cindex Objective-C, classes and selectors +++@item info classes +++@itemx info classes @var{regexp} +++Display all Objective-C classes in your program, or +++(with the @var{regexp} argument) all those matching a particular regular +++expression. +++ +++@kindex info selectors +++@item info selectors +++@itemx info selectors @var{regexp} +++Display all Objective-C selectors in your program, or +++(with the @var{regexp} argument) all those matching a particular regular +++expression. +++ +++@ignore +++This was never implemented. +++@kindex info methods +++@item info methods +++@itemx info methods @var{regexp} +++The @code{info methods} command permits the user to examine all defined +++methods within C@t{++} program, or (with the @var{regexp} argument) a +++specific set of methods found in the various C@t{++} classes. Many +++C@t{++} classes provide a large number of methods. Thus, the output +++from the @code{ptype} command can be overwhelming and hard to use. The +++@code{info-methods} command filters the methods, printing only those +++which match the regular-expression @var{regexp}. +++@end ignore +++ +++@cindex opaque data types +++@kindex set opaque-type-resolution +++@item set opaque-type-resolution on +++Tell @value{GDBN} to resolve opaque types. An opaque type is a type +++declared as a pointer to a @code{struct}, @code{class}, or +++@code{union}---for example, @code{struct MyType *}---that is used in one +++source file although the full declaration of @code{struct MyType} is in +++another source file. The default is on. +++ +++A change in the setting of this subcommand will not take effect until +++the next time symbols for a file are loaded. +++ +++@item set opaque-type-resolution off +++Tell @value{GDBN} not to resolve opaque types. In this case, the type +++is printed as follows: +++@smallexample +++@{@} +++@end smallexample +++ +++@kindex show opaque-type-resolution +++@item show opaque-type-resolution +++Show whether opaque types are resolved or not. +++ +++@kindex set print symbol-loading +++@cindex print messages when symbols are loaded +++@item set print symbol-loading +++@itemx set print symbol-loading full +++@itemx set print symbol-loading brief +++@itemx set print symbol-loading off +++The @code{set print symbol-loading} command allows you to control the +++printing of messages when @value{GDBN} loads symbol information. +++By default a message is printed for the executable and one for each +++shared library, and normally this is what you want. However, when +++debugging apps with large numbers of shared libraries these messages +++can be annoying. +++When set to @code{brief} a message is printed for each executable, +++and when @value{GDBN} loads a collection of shared libraries at once +++it will only print one message regardless of the number of shared +++libraries. When set to @code{off} no messages are printed. +++ +++@kindex show print symbol-loading +++@item show print symbol-loading +++Show whether messages will be printed when a @value{GDBN} command +++entered from the keyboard causes symbol information to be loaded. +++ +++@kindex maint print symbols +++@cindex symbol dump +++@kindex maint print psymbols +++@cindex partial symbol dump +++@kindex maint print msymbols +++@cindex minimal symbol dump +++@item maint print symbols @r{[}-pc @var{address}@r{]} @r{[}@var{filename}@r{]} +++@itemx maint print symbols @r{[}-objfile @var{objfile}@r{]} @r{[}-source @var{source}@r{]} @r{[}--@r{]} @r{[}@var{filename}@r{]} +++@itemx maint print psymbols @r{[}-objfile @var{objfile}@r{]} @r{[}-pc @var{address}@r{]} @r{[}--@r{]} @r{[}@var{filename}@r{]} +++@itemx maint print psymbols @r{[}-objfile @var{objfile}@r{]} @r{[}-source @var{source}@r{]} @r{[}--@r{]} @r{[}@var{filename}@r{]} +++@itemx maint print msymbols @r{[}-objfile @var{objfile}@r{]} @r{[}--@r{]} @r{[}@var{filename}@r{]} +++Write a dump of debugging symbol data into the file @var{filename} or +++the terminal if @var{filename} is unspecified. +++If @code{-objfile @var{objfile}} is specified, only dump symbols for +++that objfile. +++If @code{-pc @var{address}} is specified, only dump symbols for the file +++with code at that address. Note that @var{address} may be a symbol like +++@code{main}. +++If @code{-source @var{source}} is specified, only dump symbols for that +++source file. +++ +++These commands are used to debug the @value{GDBN} symbol-reading code. +++These commands do not modify internal @value{GDBN} state, therefore +++@samp{maint print symbols} will only print symbols for already expanded symbol +++tables. +++You can use the command @code{info sources} to find out which files these are. +++If you use @samp{maint print psymbols} instead, the dump shows information +++about symbols that @value{GDBN} only knows partially---that is, symbols +++defined in files that @value{GDBN} has skimmed, but not yet read completely. +++Finally, @samp{maint print msymbols} just dumps ``minimal symbols'', e.g., +++``ELF symbols''. +++ +++@xref{Files, ,Commands to Specify Files}, for a discussion of how +++@value{GDBN} reads symbols (in the description of @code{symbol-file}). +++ +++@kindex maint info symtabs +++@kindex maint info psymtabs +++@cindex listing @value{GDBN}'s internal symbol tables +++@cindex symbol tables, listing @value{GDBN}'s internal +++@cindex full symbol tables, listing @value{GDBN}'s internal +++@cindex partial symbol tables, listing @value{GDBN}'s internal +++@item maint info symtabs @r{[} @var{regexp} @r{]} +++@itemx maint info psymtabs @r{[} @var{regexp} @r{]} +++ +++List the @code{struct symtab} or @code{struct partial_symtab} +++structures whose names match @var{regexp}. If @var{regexp} is not +++given, list them all. The output includes expressions which you can +++copy into a @value{GDBN} debugging this one to examine a particular +++structure in more detail. For example: +++ +++@smallexample +++(@value{GDBP}) maint info psymtabs dwarf2read +++@{ objfile /home/gnu/build/gdb/gdb +++ ((struct objfile *) 0x82e69d0) +++ @{ psymtab /home/gnu/src/gdb/dwarf2read.c +++ ((struct partial_symtab *) 0x8474b10) +++ readin no +++ fullname (null) +++ text addresses 0x814d3c8 -- 0x8158074 +++ globals (* (struct partial_symbol **) 0x8507a08 @@ 9) +++ statics (* (struct partial_symbol **) 0x40e95b78 @@ 2882) +++ dependencies (none) +++ @} +++@} +++(@value{GDBP}) maint info symtabs +++(@value{GDBP}) +++@end smallexample +++@noindent +++We see that there is one partial symbol table whose filename contains +++the string @samp{dwarf2read}, belonging to the @samp{gdb} executable; +++and we see that @value{GDBN} has not read in any symtabs yet at all. +++If we set a breakpoint on a function, that will cause @value{GDBN} to +++read the symtab for the compilation unit containing that function: +++ +++@smallexample +++(@value{GDBP}) break dwarf2_psymtab_to_symtab +++Breakpoint 1 at 0x814e5da: file /home/gnu/src/gdb/dwarf2read.c, +++line 1574. +++(@value{GDBP}) maint info symtabs +++@{ objfile /home/gnu/build/gdb/gdb +++ ((struct objfile *) 0x82e69d0) +++ @{ symtab /home/gnu/src/gdb/dwarf2read.c +++ ((struct symtab *) 0x86c1f38) +++ dirname (null) +++ fullname (null) +++ blockvector ((struct blockvector *) 0x86c1bd0) (primary) +++ linetable ((struct linetable *) 0x8370fa0) +++ debugformat DWARF 2 +++ @} +++@} +++(@value{GDBP}) +++@end smallexample +++ +++@kindex maint info line-table +++@cindex listing @value{GDBN}'s internal line tables +++@cindex line tables, listing @value{GDBN}'s internal +++@item maint info line-table @r{[} @var{regexp} @r{]} +++ +++List the @code{struct linetable} from all @code{struct symtab} +++instances whose name matches @var{regexp}. If @var{regexp} is not +++given, list the @code{struct linetable} from all @code{struct symtab}. +++ +++@kindex maint set symbol-cache-size +++@cindex symbol cache size +++@item maint set symbol-cache-size @var{size} +++Set the size of the symbol cache to @var{size}. +++The default size is intended to be good enough for debugging +++most applications. This option exists to allow for experimenting +++with different sizes. +++ +++@kindex maint show symbol-cache-size +++@item maint show symbol-cache-size +++Show the size of the symbol cache. +++ +++@kindex maint print symbol-cache +++@cindex symbol cache, printing its contents +++@item maint print symbol-cache +++Print the contents of the symbol cache. +++This is useful when debugging symbol cache issues. +++ +++@kindex maint print symbol-cache-statistics +++@cindex symbol cache, printing usage statistics +++@item maint print symbol-cache-statistics +++Print symbol cache usage statistics. +++This helps determine how well the cache is being utilized. +++ +++@kindex maint flush-symbol-cache +++@cindex symbol cache, flushing +++@item maint flush-symbol-cache +++Flush the contents of the symbol cache, all entries are removed. +++This command is useful when debugging the symbol cache. +++It is also useful when collecting performance data. +++ +++@end table +++ +++@node Altering +++@chapter Altering Execution +++ +++Once you think you have found an error in your program, you might want to +++find out for certain whether correcting the apparent error would lead to +++correct results in the rest of the run. You can find the answer by +++experiment, using the @value{GDBN} features for altering execution of the +++program. +++ +++For example, you can store new values into variables or memory +++locations, give your program a signal, restart it at a different +++address, or even return prematurely from a function. +++ +++@menu +++* Assignment:: Assignment to variables +++* Jumping:: Continuing at a different address +++* Signaling:: Giving your program a signal +++* Returning:: Returning from a function +++* Calling:: Calling your program's functions +++* Patching:: Patching your program +++* Compiling and Injecting Code:: Compiling and injecting code in @value{GDBN} +++@end menu +++ +++@node Assignment +++@section Assignment to Variables +++ +++@cindex assignment +++@cindex setting variables +++To alter the value of a variable, evaluate an assignment expression. +++@xref{Expressions, ,Expressions}. For example, +++ +++@smallexample +++print x=4 +++@end smallexample +++ +++@noindent +++stores the value 4 into the variable @code{x}, and then prints the +++value of the assignment expression (which is 4). +++@xref{Languages, ,Using @value{GDBN} with Different Languages}, for more +++information on operators in supported languages. +++ +++@kindex set variable +++@cindex variables, setting +++If you are not interested in seeing the value of the assignment, use the +++@code{set} command instead of the @code{print} command. @code{set} is +++really the same as @code{print} except that the expression's value is +++not printed and is not put in the value history (@pxref{Value History, +++,Value History}). The expression is evaluated only for its effects. +++ +++If the beginning of the argument string of the @code{set} command +++appears identical to a @code{set} subcommand, use the @code{set +++variable} command instead of just @code{set}. This command is identical +++to @code{set} except for its lack of subcommands. For example, if your +++program has a variable @code{width}, you get an error if you try to set +++a new value with just @samp{set width=13}, because @value{GDBN} has the +++command @code{set width}: +++ +++@smallexample +++(@value{GDBP}) whatis width +++type = double +++(@value{GDBP}) p width +++$4 = 13 +++(@value{GDBP}) set width=47 +++Invalid syntax in expression. +++@end smallexample +++ +++@noindent +++The invalid expression, of course, is @samp{=47}. In +++order to actually set the program's variable @code{width}, use +++ +++@smallexample +++(@value{GDBP}) set var width=47 +++@end smallexample +++ +++Because the @code{set} command has many subcommands that can conflict +++with the names of program variables, it is a good idea to use the +++@code{set variable} command instead of just @code{set}. For example, if +++your program has a variable @code{g}, you run into problems if you try +++to set a new value with just @samp{set g=4}, because @value{GDBN} has +++the command @code{set gnutarget}, abbreviated @code{set g}: +++ +++@smallexample +++@group +++(@value{GDBP}) whatis g +++type = double +++(@value{GDBP}) p g +++$1 = 1 +++(@value{GDBP}) set g=4 +++(@value{GDBP}) p g +++$2 = 1 +++(@value{GDBP}) r +++The program being debugged has been started already. +++Start it from the beginning? (y or n) y +++Starting program: /home/smith/cc_progs/a.out +++"/home/smith/cc_progs/a.out": can't open to read symbols: +++ Invalid bfd target. +++(@value{GDBP}) show g +++The current BFD target is "=4". +++@end group +++@end smallexample +++ +++@noindent +++The program variable @code{g} did not change, and you silently set the +++@code{gnutarget} to an invalid value. In order to set the variable +++@code{g}, use +++ +++@smallexample +++(@value{GDBP}) set var g=4 +++@end smallexample +++ +++@value{GDBN} allows more implicit conversions in assignments than C; you can +++freely store an integer value into a pointer variable or vice versa, +++and you can convert any structure to any other structure that is the +++same length or shorter. +++@comment FIXME: how do structs align/pad in these conversions? +++@comment /doc@cygnus.com 18dec1990 +++ +++To store values into arbitrary places in memory, use the @samp{@{@dots{}@}} +++construct to generate a value of specified type at a specified address +++(@pxref{Expressions, ,Expressions}). For example, @code{@{int@}0x83040} refers +++to memory location @code{0x83040} as an integer (which implies a certain size +++and representation in memory), and +++ +++@smallexample +++set @{int@}0x83040 = 4 +++@end smallexample +++ +++@noindent +++stores the value 4 into that memory location. +++ +++@node Jumping +++@section Continuing at a Different Address +++ +++Ordinarily, when you continue your program, you do so at the place where +++it stopped, with the @code{continue} command. You can instead continue at +++an address of your own choosing, with the following commands: +++ +++@table @code +++@kindex jump +++@kindex j @r{(@code{jump})} +++@item jump @var{location} +++@itemx j @var{location} +++Resume execution at @var{location}. Execution stops again immediately +++if there is a breakpoint there. @xref{Specify Location}, for a description +++of the different forms of @var{location}. It is common +++practice to use the @code{tbreak} command in conjunction with +++@code{jump}. @xref{Set Breaks, ,Setting Breakpoints}. +++ +++The @code{jump} command does not change the current stack frame, or +++the stack pointer, or the contents of any memory location or any +++register other than the program counter. If @var{location} is in +++a different function from the one currently executing, the results may +++be bizarre if the two functions expect different patterns of arguments or +++of local variables. For this reason, the @code{jump} command requests +++confirmation if the specified line is not in the function currently +++executing. However, even bizarre results are predictable if you are +++well acquainted with the machine-language code of your program. +++@end table +++ +++On many systems, you can get much the same effect as the @code{jump} +++command by storing a new value into the register @code{$pc}. The +++difference is that this does not start your program running; it only +++changes the address of where it @emph{will} run when you continue. For +++example, +++ +++@smallexample +++set $pc = 0x485 +++@end smallexample +++ +++@noindent +++makes the next @code{continue} command or stepping command execute at +++address @code{0x485}, rather than at the address where your program stopped. +++@xref{Continuing and Stepping, ,Continuing and Stepping}. +++ +++The most common occasion to use the @code{jump} command is to back +++up---perhaps with more breakpoints set---over a portion of a program +++that has already executed, in order to examine its execution in more +++detail. +++ +++@c @group +++@node Signaling +++@section Giving your Program a Signal +++@cindex deliver a signal to a program +++ +++@table @code +++@kindex signal +++@item signal @var{signal} +++Resume execution where your program is stopped, but immediately give it the +++signal @var{signal}. The @var{signal} can be the name or the number of a +++signal. For example, on many systems @code{signal 2} and @code{signal +++SIGINT} are both ways of sending an interrupt signal. +++ +++Alternatively, if @var{signal} is zero, continue execution without +++giving a signal. This is useful when your program stopped on account of +++a signal and would ordinarily see the signal when resumed with the +++@code{continue} command; @samp{signal 0} causes it to resume without a +++signal. +++ +++@emph{Note:} When resuming a multi-threaded program, @var{signal} is +++delivered to the currently selected thread, not the thread that last +++reported a stop. This includes the situation where a thread was +++stopped due to a signal. So if you want to continue execution +++suppressing the signal that stopped a thread, you should select that +++same thread before issuing the @samp{signal 0} command. If you issue +++the @samp{signal 0} command with another thread as the selected one, +++@value{GDBN} detects that and asks for confirmation. +++ +++Invoking the @code{signal} command is not the same as invoking the +++@code{kill} utility from the shell. Sending a signal with @code{kill} +++causes @value{GDBN} to decide what to do with the signal depending on +++the signal handling tables (@pxref{Signals}). The @code{signal} command +++passes the signal directly to your program. +++ +++@code{signal} does not repeat when you press @key{RET} a second time +++after executing the command. +++ +++@kindex queue-signal +++@item queue-signal @var{signal} +++Queue @var{signal} to be delivered immediately to the current thread +++when execution of the thread resumes. The @var{signal} can be the name or +++the number of a signal. For example, on many systems @code{signal 2} and +++@code{signal SIGINT} are both ways of sending an interrupt signal. +++The handling of the signal must be set to pass the signal to the program, +++otherwise @value{GDBN} will report an error. +++You can control the handling of signals from @value{GDBN} with the +++@code{handle} command (@pxref{Signals}). +++ +++Alternatively, if @var{signal} is zero, any currently queued signal +++for the current thread is discarded and when execution resumes no signal +++will be delivered. This is useful when your program stopped on account +++of a signal and would ordinarily see the signal when resumed with the +++@code{continue} command. +++ +++This command differs from the @code{signal} command in that the signal +++is just queued, execution is not resumed. And @code{queue-signal} cannot +++be used to pass a signal whose handling state has been set to @code{nopass} +++(@pxref{Signals}). +++@end table +++@c @end group +++ +++@xref{stepping into signal handlers}, for information on how stepping +++commands behave when the thread has a signal queued. +++ +++@node Returning +++@section Returning from a Function +++ +++@table @code +++@cindex returning from a function +++@kindex return +++@item return +++@itemx return @var{expression} +++You can cancel execution of a function call with the @code{return} +++command. If you give an +++@var{expression} argument, its value is used as the function's return +++value. +++@end table +++ +++When you use @code{return}, @value{GDBN} discards the selected stack frame +++(and all frames within it). You can think of this as making the +++discarded frame return prematurely. If you wish to specify a value to +++be returned, give that value as the argument to @code{return}. +++ +++This pops the selected stack frame (@pxref{Selection, ,Selecting a +++Frame}), and any other frames inside of it, leaving its caller as the +++innermost remaining frame. That frame becomes selected. The +++specified value is stored in the registers used for returning values +++of functions. +++ +++The @code{return} command does not resume execution; it leaves the +++program stopped in the state that would exist if the function had just +++returned. In contrast, the @code{finish} command (@pxref{Continuing +++and Stepping, ,Continuing and Stepping}) resumes execution until the +++selected stack frame returns naturally. +++ +++@value{GDBN} needs to know how the @var{expression} argument should be set for +++the inferior. The concrete registers assignment depends on the OS ABI and the +++type being returned by the selected stack frame. For example it is common for +++OS ABI to return floating point values in FPU registers while integer values in +++CPU registers. Still some ABIs return even floating point values in CPU +++registers. Larger integer widths (such as @code{long long int}) also have +++specific placement rules. @value{GDBN} already knows the OS ABI from its +++current target so it needs to find out also the type being returned to make the +++assignment into the right register(s). +++ +++Normally, the selected stack frame has debug info. @value{GDBN} will always +++use the debug info instead of the implicit type of @var{expression} when the +++debug info is available. For example, if you type @kbd{return -1}, and the +++function in the current stack frame is declared to return a @code{long long +++int}, @value{GDBN} transparently converts the implicit @code{int} value of -1 +++into a @code{long long int}: +++ +++@smallexample +++Breakpoint 1, func () at gdb.base/return-nodebug.c:29 +++29 return 31; +++(@value{GDBP}) return -1 +++Make func return now? (y or n) y +++#0 0x004004f6 in main () at gdb.base/return-nodebug.c:43 +++43 printf ("result=%lld\n", func ()); +++(@value{GDBP}) +++@end smallexample +++ +++However, if the selected stack frame does not have a debug info, e.g., if the +++function was compiled without debug info, @value{GDBN} has to find out the type +++to return from user. Specifying a different type by mistake may set the value +++in different inferior registers than the caller code expects. For example, +++typing @kbd{return -1} with its implicit type @code{int} would set only a part +++of a @code{long long int} result for a debug info less function (on 32-bit +++architectures). Therefore the user is required to specify the return type by +++an appropriate cast explicitly: +++ +++@smallexample +++Breakpoint 2, 0x0040050b in func () +++(@value{GDBP}) return -1 +++Return value type not available for selected stack frame. +++Please use an explicit cast of the value to return. +++(@value{GDBP}) return (long long int) -1 +++Make selected stack frame return now? (y or n) y +++#0 0x00400526 in main () +++(@value{GDBP}) +++@end smallexample +++ +++@node Calling +++@section Calling Program Functions +++ +++@table @code +++@cindex calling functions +++@cindex inferior functions, calling +++@item print @var{expr} +++Evaluate the expression @var{expr} and display the resulting value. +++The expression may include calls to functions in the program being +++debugged. +++ +++@kindex call +++@item call @var{expr} +++Evaluate the expression @var{expr} without displaying @code{void} +++returned values. +++ +++You can use this variant of the @code{print} command if you want to +++execute a function from your program that does not return anything +++(a.k.a.@: @dfn{a void function}), but without cluttering the output +++with @code{void} returned values that @value{GDBN} will otherwise +++print. If the result is not void, it is printed and saved in the +++value history. +++@end table +++ +++It is possible for the function you call via the @code{print} or +++@code{call} command to generate a signal (e.g., if there's a bug in +++the function, or if you passed it incorrect arguments). What happens +++in that case is controlled by the @code{set unwindonsignal} command. +++ +++Similarly, with a C@t{++} program it is possible for the function you +++call via the @code{print} or @code{call} command to generate an +++exception that is not handled due to the constraints of the dummy +++frame. In this case, any exception that is raised in the frame, but has +++an out-of-frame exception handler will not be found. GDB builds a +++dummy-frame for the inferior function call, and the unwinder cannot +++seek for exception handlers outside of this dummy-frame. What happens +++in that case is controlled by the +++@code{set unwind-on-terminating-exception} command. +++ +++@table @code +++@item set unwindonsignal +++@kindex set unwindonsignal +++@cindex unwind stack in called functions +++@cindex call dummy stack unwinding +++Set unwinding of the stack if a signal is received while in a function +++that @value{GDBN} called in the program being debugged. If set to on, +++@value{GDBN} unwinds the stack it created for the call and restores +++the context to what it was before the call. If set to off (the +++default), @value{GDBN} stops in the frame where the signal was +++received. +++ +++@item show unwindonsignal +++@kindex show unwindonsignal +++Show the current setting of stack unwinding in the functions called by +++@value{GDBN}. +++ +++@item set unwind-on-terminating-exception +++@kindex set unwind-on-terminating-exception +++@cindex unwind stack in called functions with unhandled exceptions +++@cindex call dummy stack unwinding on unhandled exception. +++Set unwinding of the stack if a C@t{++} exception is raised, but left +++unhandled while in a function that @value{GDBN} called in the program being +++debugged. If set to on (the default), @value{GDBN} unwinds the stack +++it created for the call and restores the context to what it was before +++the call. If set to off, @value{GDBN} the exception is delivered to +++the default C@t{++} exception handler and the inferior terminated. +++ +++@item show unwind-on-terminating-exception +++@kindex show unwind-on-terminating-exception +++Show the current setting of stack unwinding in the functions called by +++@value{GDBN}. +++ +++@item set may-call-functions +++@kindex set may-call-functions +++@cindex disabling calling functions in the program +++@cindex calling functions in the program, disabling +++Set permission to call functions in the program. +++This controls whether @value{GDBN} will attempt to call functions in +++the program, such as with expressions in the @code{print} command. It +++defaults to @code{on}. +++ +++To call a function in the program, @value{GDBN} has to temporarily +++modify the state of the inferior. This has potentially undesired side +++effects. Also, having @value{GDBN} call nested functions is likely to +++be erroneous and may even crash the program being debugged. You can +++avoid such hazards by forbidding @value{GDBN} from calling functions +++in the program being debugged. If calling functions in the program +++is forbidden, GDB will throw an error when a command (such as printing +++an expression) starts a function call in the program. +++ +++@item show may-call-functions +++@kindex show may-call-functions +++Show permission to call functions in the program. +++ +++@end table +++ +++@subsection Calling functions with no debug info +++ +++@cindex no debug info functions +++Sometimes, a function you wish to call is missing debug information. +++In such case, @value{GDBN} does not know the type of the function, +++including the types of the function's parameters. To avoid calling +++the inferior function incorrectly, which could result in the called +++function functioning erroneously and even crash, @value{GDBN} refuses +++to call the function unless you tell it the type of the function. +++ +++For prototyped (i.e.@: ANSI/ISO style) functions, there are two ways +++to do that. The simplest is to cast the call to the function's +++declared return type. For example: +++ +++@smallexample +++(@value{GDBP}) p getenv ("PATH") +++'getenv' has unknown return type; cast the call to its declared return type +++(@value{GDBP}) p (char *) getenv ("PATH") +++$1 = 0x7fffffffe7ba "/usr/local/bin:/"... +++@end smallexample +++ +++Casting the return type of a no-debug function is equivalent to +++casting the function to a pointer to a prototyped function that has a +++prototype that matches the types of the passed-in arguments, and +++calling that. I.e., the call above is equivalent to: +++ +++@smallexample +++(@value{GDBP}) p ((char * (*) (const char *)) getenv) ("PATH") +++@end smallexample +++ +++@noindent +++and given this prototyped C or C++ function with float parameters: +++ +++@smallexample +++float multiply (float v1, float v2) @{ return v1 * v2; @} +++@end smallexample +++ +++@noindent +++these calls are equivalent: +++ +++@smallexample +++(@value{GDBP}) p (float) multiply (2.0f, 3.0f) +++(@value{GDBP}) p ((float (*) (float, float)) multiply) (2.0f, 3.0f) +++@end smallexample +++ +++If the function you wish to call is declared as unprototyped (i.e.@: +++old K&R style), you must use the cast-to-function-pointer syntax, so +++that @value{GDBN} knows that it needs to apply default argument +++promotions (promote float arguments to double). @xref{ABI, float +++promotion}. For example, given this unprototyped C function with +++float parameters, and no debug info: +++ +++@smallexample +++float +++multiply_noproto (v1, v2) +++ float v1, v2; +++@{ +++ return v1 * v2; +++@} +++@end smallexample +++ +++@noindent +++you call it like this: +++ +++@smallexample +++ (@value{GDBP}) p ((float (*) ()) multiply_noproto) (2.0f, 3.0f) +++@end smallexample +++ +++@node Patching +++@section Patching Programs +++ +++@cindex patching binaries +++@cindex writing into executables +++@cindex writing into corefiles +++ +++By default, @value{GDBN} opens the file containing your program's +++executable code (or the corefile) read-only. This prevents accidental +++alterations to machine code; but it also prevents you from intentionally +++patching your program's binary. +++ +++If you'd like to be able to patch the binary, you can specify that +++explicitly with the @code{set write} command. For example, you might +++want to turn on internal debugging flags, or even to make emergency +++repairs. +++ +++@table @code +++@kindex set write +++@item set write on +++@itemx set write off +++If you specify @samp{set write on}, @value{GDBN} opens executable and +++core files for both reading and writing; if you specify @kbd{set write +++off} (the default), @value{GDBN} opens them read-only. +++ +++If you have already loaded a file, you must load it again (using the +++@code{exec-file} or @code{core-file} command) after changing @code{set +++write}, for your new setting to take effect. +++ +++@item show write +++@kindex show write +++Display whether executable files and core files are opened for writing +++as well as reading. +++@end table +++ +++@node Compiling and Injecting Code +++@section Compiling and injecting code in @value{GDBN} +++@cindex injecting code +++@cindex writing into executables +++@cindex compiling code +++ +++@value{GDBN} supports on-demand compilation and code injection into +++programs running under @value{GDBN}. GCC 5.0 or higher built with +++@file{libcc1.so} must be installed for this functionality to be enabled. +++This functionality is implemented with the following commands. +++ +++@table @code +++@kindex compile code +++@item compile code @var{source-code} +++@itemx compile code -raw @var{--} @var{source-code} +++Compile @var{source-code} with the compiler language found as the current +++language in @value{GDBN} (@pxref{Languages}). If compilation and +++injection is not supported with the current language specified in +++@value{GDBN}, or the compiler does not support this feature, an error +++message will be printed. If @var{source-code} compiles and links +++successfully, @value{GDBN} will load the object-code emitted, +++and execute it within the context of the currently selected inferior. +++It is important to note that the compiled code is executed immediately. +++After execution, the compiled code is removed from @value{GDBN} and any +++new types or variables you have defined will be deleted. +++ +++The command allows you to specify @var{source-code} in two ways. +++The simplest method is to provide a single line of code to the command. +++E.g.: +++ +++@smallexample +++compile code printf ("hello world\n"); +++@end smallexample +++ +++If you specify options on the command line as well as source code, they +++may conflict. The @samp{--} delimiter can be used to separate options +++from actual source code. E.g.: +++ +++@smallexample +++compile code -r -- printf ("hello world\n"); +++@end smallexample +++ +++Alternatively you can enter source code as multiple lines of text. To +++enter this mode, invoke the @samp{compile code} command without any text +++following the command. This will start the multiple-line editor and +++allow you to type as many lines of source code as required. When you +++have completed typing, enter @samp{end} on its own line to exit the +++editor. +++ +++@smallexample +++compile code +++>printf ("hello\n"); +++>printf ("world\n"); +++>end +++@end smallexample +++ +++Specifying @samp{-raw}, prohibits @value{GDBN} from wrapping the +++provided @var{source-code} in a callable scope. In this case, you must +++specify the entry point of the code by defining a function named +++@code{_gdb_expr_}. The @samp{-raw} code cannot access variables of the +++inferior. Using @samp{-raw} option may be needed for example when +++@var{source-code} requires @samp{#include} lines which may conflict with +++inferior symbols otherwise. +++ +++@kindex compile file +++@item compile file @var{filename} +++@itemx compile file -raw @var{filename} +++Like @code{compile code}, but take the source code from @var{filename}. +++ +++@smallexample +++compile file /home/user/example.c +++@end smallexample +++@end table +++ +++@table @code +++@item compile print [[@var{options}] --] @var{expr} +++@itemx compile print [[@var{options}] --] /@var{f} @var{expr} +++Compile and execute @var{expr} with the compiler language found as the +++current language in @value{GDBN} (@pxref{Languages}). By default the +++value of @var{expr} is printed in a format appropriate to its data type; +++you can choose a different format by specifying @samp{/@var{f}}, where +++@var{f} is a letter specifying the format; see @ref{Output Formats,,Output +++Formats}. The @code{compile print} command accepts the same options +++as the @code{print} command; see @ref{print options}. +++ +++@item compile print [[@var{options}] --] +++@itemx compile print [[@var{options}] --] /@var{f} +++@cindex reprint the last value +++Alternatively you can enter the expression (source code producing it) as +++multiple lines of text. To enter this mode, invoke the @samp{compile print} +++command without any text following the command. This will start the +++multiple-line editor. +++@end table +++ +++@noindent +++The process of compiling and injecting the code can be inspected using: +++ +++@table @code +++@anchor{set debug compile} +++@item set debug compile +++@cindex compile command debugging info +++Turns on or off display of @value{GDBN} process of compiling and +++injecting the code. The default is off. +++ +++@item show debug compile +++Displays the current state of displaying @value{GDBN} process of +++compiling and injecting the code. +++ +++@anchor{set debug compile-cplus-types} +++@item set debug compile-cplus-types +++@cindex compile C@t{++} type conversion +++Turns on or off the display of C@t{++} type conversion debugging information. +++The default is off. +++ +++@item show debug compile-cplus-types +++Displays the current state of displaying debugging information for +++C@t{++} type conversion. +++@end table +++ +++@subsection Compilation options for the @code{compile} command +++ +++@value{GDBN} needs to specify the right compilation options for the code +++to be injected, in part to make its ABI compatible with the inferior +++and in part to make the injected code compatible with @value{GDBN}'s +++injecting process. +++ +++@noindent +++The options used, in increasing precedence: +++ +++@table @asis +++@item target architecture and OS options (@code{gdbarch}) +++These options depend on target processor type and target operating +++system, usually they specify at least 32-bit (@code{-m32}) or 64-bit +++(@code{-m64}) compilation option. +++ +++@item compilation options recorded in the target +++@value{NGCC} (since version 4.7) stores the options used for compilation +++into @code{DW_AT_producer} part of DWARF debugging information according +++to the @value{NGCC} option @code{-grecord-gcc-switches}. One has to +++explicitly specify @code{-g} during inferior compilation otherwise +++@value{NGCC} produces no DWARF. This feature is only relevant for +++platforms where @code{-g} produces DWARF by default, otherwise one may +++try to enforce DWARF by using @code{-gdwarf-4}. +++ +++@item compilation options set by @code{set compile-args} +++@end table +++ +++@noindent +++You can override compilation options using the following command: +++ +++@table @code +++@item set compile-args +++@cindex compile command options override +++Set compilation options used for compiling and injecting code with the +++@code{compile} commands. These options override any conflicting ones +++from the target architecture and/or options stored during inferior +++compilation. +++ +++@item show compile-args +++Displays the current state of compilation options override. +++This does not show all the options actually used during compilation, +++use @ref{set debug compile} for that. +++@end table +++ +++@subsection Caveats when using the @code{compile} command +++ +++There are a few caveats to keep in mind when using the @code{compile} +++command. As the caveats are different per language, the table below +++highlights specific issues on a per language basis. +++ +++@table @asis +++@item C code examples and caveats +++When the language in @value{GDBN} is set to @samp{C}, the compiler will +++attempt to compile the source code with a @samp{C} compiler. The source +++code provided to the @code{compile} command will have much the same +++access to variables and types as it normally would if it were part of +++the program currently being debugged in @value{GDBN}. +++ +++Below is a sample program that forms the basis of the examples that +++follow. This program has been compiled and loaded into @value{GDBN}, +++much like any other normal debugging session. +++ +++@smallexample +++void function1 (void) +++@{ +++ int i = 42; +++ printf ("function 1\n"); +++@} +++ +++void function2 (void) +++@{ +++ int j = 12; +++ function1 (); +++@} +++ +++int main(void) +++@{ +++ int k = 6; +++ int *p; +++ function2 (); +++ return 0; +++@} +++@end smallexample +++ +++For the purposes of the examples in this section, the program above has +++been compiled, loaded into @value{GDBN}, stopped at the function +++@code{main}, and @value{GDBN} is awaiting input from the user. +++ +++To access variables and types for any program in @value{GDBN}, the +++program must be compiled and packaged with debug information. The +++@code{compile} command is not an exception to this rule. Without debug +++information, you can still use the @code{compile} command, but you will +++be very limited in what variables and types you can access. +++ +++So with that in mind, the example above has been compiled with debug +++information enabled. The @code{compile} command will have access to +++all variables and types (except those that may have been optimized +++out). Currently, as @value{GDBN} has stopped the program in the +++@code{main} function, the @code{compile} command would have access to +++the variable @code{k}. You could invoke the @code{compile} command +++and type some source code to set the value of @code{k}. You can also +++read it, or do anything with that variable you would normally do in +++@code{C}. Be aware that changes to inferior variables in the +++@code{compile} command are persistent. In the following example: +++ +++@smallexample +++compile code k = 3; +++@end smallexample +++ +++@noindent +++the variable @code{k} is now 3. It will retain that value until +++something else in the example program changes it, or another +++@code{compile} command changes it. +++ +++Normal scope and access rules apply to source code compiled and +++injected by the @code{compile} command. In the example, the variables +++@code{j} and @code{k} are not accessible yet, because the program is +++currently stopped in the @code{main} function, where these variables +++are not in scope. Therefore, the following command +++ +++@smallexample +++compile code j = 3; +++@end smallexample +++ +++@noindent +++will result in a compilation error message. +++ +++Once the program is continued, execution will bring these variables in +++scope, and they will become accessible; then the code you specify via +++the @code{compile} command will be able to access them. +++ +++You can create variables and types with the @code{compile} command as +++part of your source code. Variables and types that are created as part +++of the @code{compile} command are not visible to the rest of the program for +++the duration of its run. This example is valid: +++ +++@smallexample +++compile code int ff = 5; printf ("ff is %d\n", ff); +++@end smallexample +++ +++However, if you were to type the following into @value{GDBN} after that +++command has completed: +++ +++@smallexample +++compile code printf ("ff is %d\n'', ff); +++@end smallexample +++ +++@noindent +++a compiler error would be raised as the variable @code{ff} no longer +++exists. Object code generated and injected by the @code{compile} +++command is removed when its execution ends. Caution is advised +++when assigning to program variables values of variables created by the +++code submitted to the @code{compile} command. This example is valid: +++ +++@smallexample +++compile code int ff = 5; k = ff; +++@end smallexample +++ +++The value of the variable @code{ff} is assigned to @code{k}. The variable +++@code{k} does not require the existence of @code{ff} to maintain the value +++it has been assigned. However, pointers require particular care in +++assignment. If the source code compiled with the @code{compile} command +++changed the address of a pointer in the example program, perhaps to a +++variable created in the @code{compile} command, that pointer would point +++to an invalid location when the command exits. The following example +++would likely cause issues with your debugged program: +++ +++@smallexample +++compile code int ff = 5; p = &ff; +++@end smallexample +++ +++In this example, @code{p} would point to @code{ff} when the +++@code{compile} command is executing the source code provided to it. +++However, as variables in the (example) program persist with their +++assigned values, the variable @code{p} would point to an invalid +++location when the command exists. A general rule should be followed +++in that you should either assign @code{NULL} to any assigned pointers, +++or restore a valid location to the pointer before the command exits. +++ +++Similar caution must be exercised with any structs, unions, and typedefs +++defined in @code{compile} command. Types defined in the @code{compile} +++command will no longer be available in the next @code{compile} command. +++Therefore, if you cast a variable to a type defined in the +++@code{compile} command, care must be taken to ensure that any future +++need to resolve the type can be achieved. +++ +++@smallexample +++(gdb) compile code static struct a @{ int a; @} v = @{ 42 @}; argv = &v; +++(gdb) compile code printf ("%d\n", ((struct a *) argv)->a); +++gdb command line:1:36: error: dereferencing pointer to incomplete type ‘struct a’ +++Compilation failed. +++(gdb) compile code struct a @{ int a; @}; printf ("%d\n", ((struct a *) argv)->a); +++42 +++@end smallexample +++ +++Variables that have been optimized away by the compiler are not +++accessible to the code submitted to the @code{compile} command. +++Access to those variables will generate a compiler error which @value{GDBN} +++will print to the console. +++@end table +++ +++@subsection Compiler search for the @code{compile} command +++ +++@value{GDBN} needs to find @value{NGCC} for the inferior being debugged +++which may not be obvious for remote targets of different architecture +++than where @value{GDBN} is running. Environment variable @code{PATH} on +++@value{GDBN} host is searched for @value{NGCC} binary matching the +++target architecture and operating system. This search can be overriden +++by @code{set compile-gcc} @value{GDBN} command below. @code{PATH} is +++taken from shell that executed @value{GDBN}, it is not the value set by +++@value{GDBN} command @code{set environment}). @xref{Environment}. +++ +++ +++Specifically @code{PATH} is searched for binaries matching regular expression +++@code{@var{arch}(-[^-]*)?-@var{os}-gcc} according to the inferior target being +++debugged. @var{arch} is processor name --- multiarch is supported, so for +++example both @code{i386} and @code{x86_64} targets look for pattern +++@code{(x86_64|i.86)} and both @code{s390} and @code{s390x} targets look +++for pattern @code{s390x?}. @var{os} is currently supported only for +++pattern @code{linux(-gnu)?}. +++ +++On Posix hosts the compiler driver @value{GDBN} needs to find also +++shared library @file{libcc1.so} from the compiler. It is searched in +++default shared library search path (overridable with usual environment +++variable @code{LD_LIBRARY_PATH}), unrelated to @code{PATH} or @code{set +++compile-gcc} settings. Contrary to it @file{libcc1plugin.so} is found +++according to the installation of the found compiler --- as possibly +++specified by the @code{set compile-gcc} command. +++ +++@table @code +++@item set compile-gcc +++@cindex compile command driver filename override +++Set compilation command used for compiling and injecting code with the +++@code{compile} commands. If this option is not set (it is set to +++an empty string), the search described above will occur --- that is the +++default. +++ +++@item show compile-gcc +++Displays the current compile command @value{NGCC} driver filename. +++If set, it is the main command @command{gcc}, found usually for example +++under name @file{x86_64-linux-gnu-gcc}. +++@end table +++ +++@node GDB Files +++@chapter @value{GDBN} Files +++ +++@value{GDBN} needs to know the file name of the program to be debugged, +++both in order to read its symbol table and in order to start your +++program. To debug a core dump of a previous run, you must also tell +++@value{GDBN} the name of the core dump file. +++ +++@menu +++* Files:: Commands to specify files +++* File Caching:: Information about @value{GDBN}'s file caching +++* Separate Debug Files:: Debugging information in separate files +++* MiniDebugInfo:: Debugging information in a special section +++* Index Files:: Index files speed up GDB +++* Symbol Errors:: Errors reading symbol files +++* Data Files:: GDB data files +++@end menu +++ +++@node Files +++@section Commands to Specify Files +++ +++@cindex symbol table +++@cindex core dump file +++ +++You may want to specify executable and core dump file names. The usual +++way to do this is at start-up time, using the arguments to +++@value{GDBN}'s start-up commands (@pxref{Invocation, , Getting In and +++Out of @value{GDBN}}). +++ +++Occasionally it is necessary to change to a different file during a +++@value{GDBN} session. Or you may run @value{GDBN} and forget to +++specify a file you want to use. Or you are debugging a remote target +++via @code{gdbserver} (@pxref{Server, file, Using the @code{gdbserver} +++Program}). In these situations the @value{GDBN} commands to specify +++new files are useful. +++ +++@table @code +++@cindex executable file +++@kindex file +++@item file @var{filename} +++Use @var{filename} as the program to be debugged. It is read for its +++symbols and for the contents of pure memory. It is also the program +++executed when you use the @code{run} command. If you do not specify a +++directory and the file is not found in the @value{GDBN} working directory, +++@value{GDBN} uses the environment variable @code{PATH} as a list of +++directories to search, just as the shell does when looking for a program +++to run. You can change the value of this variable, for both @value{GDBN} +++and your program, using the @code{path} command. +++ +++@cindex unlinked object files +++@cindex patching object files +++You can load unlinked object @file{.o} files into @value{GDBN} using +++the @code{file} command. You will not be able to ``run'' an object +++file, but you can disassemble functions and inspect variables. Also, +++if the underlying BFD functionality supports it, you could use +++@kbd{gdb -write} to patch object files using this technique. Note +++that @value{GDBN} can neither interpret nor modify relocations in this +++case, so branches and some initialized variables will appear to go to +++the wrong place. But this feature is still handy from time to time. +++ +++@item file +++@code{file} with no argument makes @value{GDBN} discard any information it +++has on both executable file and the symbol table. +++ +++@kindex exec-file +++@item exec-file @r{[} @var{filename} @r{]} +++Specify that the program to be run (but not the symbol table) is found +++in @var{filename}. @value{GDBN} searches the environment variable @code{PATH} +++if necessary to locate your program. Omitting @var{filename} means to +++discard information on the executable file. +++ +++@kindex symbol-file +++@item symbol-file @r{[} @var{filename} @r{[} -o @var{offset} @r{]]} +++Read symbol table information from file @var{filename}. @code{PATH} is +++searched when necessary. Use the @code{file} command to get both symbol +++table and program to run from the same file. +++ +++If an optional @var{offset} is specified, it is added to the start +++address of each section in the symbol file. This is useful if the +++program is relocated at runtime, such as the Linux kernel with kASLR +++enabled. +++ +++@code{symbol-file} with no argument clears out @value{GDBN} information on your +++program's symbol table. +++ +++The @code{symbol-file} command causes @value{GDBN} to forget the contents of +++some breakpoints and auto-display expressions. This is because they may +++contain pointers to the internal data recording symbols and data types, +++which are part of the old symbol table data being discarded inside +++@value{GDBN}. +++ +++@code{symbol-file} does not repeat if you press @key{RET} again after +++executing it once. +++ +++When @value{GDBN} is configured for a particular environment, it +++understands debugging information in whatever format is the standard +++generated for that environment; you may use either a @sc{gnu} compiler, or +++other compilers that adhere to the local conventions. +++Best results are usually obtained from @sc{gnu} compilers; for example, +++using @code{@value{NGCC}} you can generate debugging information for +++optimized code. +++ +++For most kinds of object files, with the exception of old SVR3 systems +++using COFF, the @code{symbol-file} command does not normally read the +++symbol table in full right away. Instead, it scans the symbol table +++quickly to find which source files and which symbols are present. The +++details are read later, one source file at a time, as they are needed. +++ +++The purpose of this two-stage reading strategy is to make @value{GDBN} +++start up faster. For the most part, it is invisible except for +++occasional pauses while the symbol table details for a particular source +++file are being read. (The @code{set verbose} command can turn these +++pauses into messages if desired. @xref{Messages/Warnings, ,Optional +++Warnings and Messages}.) +++ +++We have not implemented the two-stage strategy for COFF yet. When the +++symbol table is stored in COFF format, @code{symbol-file} reads the +++symbol table data in full right away. Note that ``stabs-in-COFF'' +++still does the two-stage strategy, since the debug info is actually +++in stabs format. +++ +++@kindex readnow +++@cindex reading symbols immediately +++@cindex symbols, reading immediately +++@item symbol-file @r{[} -readnow @r{]} @var{filename} +++@itemx file @r{[} -readnow @r{]} @var{filename} +++You can override the @value{GDBN} two-stage strategy for reading symbol +++tables by using the @samp{-readnow} option with any of the commands that +++load symbol table information, if you want to be sure @value{GDBN} has the +++entire symbol table available. +++ +++@cindex @code{-readnever}, option for symbol-file command +++@cindex never read symbols +++@cindex symbols, never read +++@item symbol-file @r{[} -readnever @r{]} @var{filename} +++@itemx file @r{[} -readnever @r{]} @var{filename} +++You can instruct @value{GDBN} to never read the symbolic information +++contained in @var{filename} by using the @samp{-readnever} option. +++@xref{--readnever}. +++ +++@c FIXME: for now no mention of directories, since this seems to be in +++@c flux. 13mar1992 status is that in theory GDB would look either in +++@c current dir or in same dir as myprog; but issues like competing +++@c GDB's, or clutter in system dirs, mean that in practice right now +++@c only current dir is used. FFish says maybe a special GDB hierarchy +++@c (eg rooted in val of env var GDBSYMS) could exist for mappable symbol +++@c files. +++ +++@kindex core-file +++@item core-file @r{[}@var{filename}@r{]} +++@itemx core +++Specify the whereabouts of a core dump file to be used as the ``contents +++of memory''. Traditionally, core files contain only some parts of the +++address space of the process that generated them; @value{GDBN} can access the +++executable file itself for other parts. +++ +++@code{core-file} with no argument specifies that no core file is +++to be used. +++ +++Note that the core file is ignored when your program is actually running +++under @value{GDBN}. So, if you have been running your program and you +++wish to debug a core file instead, you must kill the subprocess in which +++the program is running. To do this, use the @code{kill} command +++(@pxref{Kill Process, ,Killing the Child Process}). +++ +++@kindex add-symbol-file +++@cindex dynamic linking +++@item add-symbol-file @var{filename} @r{[} -readnow @r{|} -readnever @r{]} @r{[} -o @var{offset} @r{]} @r{[} @var{textaddress} @r{]} @r{[} -s @var{section} @var{address} @dots{} @r{]} +++The @code{add-symbol-file} command reads additional symbol table +++information from the file @var{filename}. You would use this command +++when @var{filename} has been dynamically loaded (by some other means) +++into the program that is running. The @var{textaddress} parameter gives +++the memory address at which the file's text section has been loaded. +++You can additionally specify the base address of other sections using +++an arbitrary number of @samp{-s @var{section} @var{address}} pairs. +++If a section is omitted, @value{GDBN} will use its default addresses +++as found in @var{filename}. Any @var{address} or @var{textaddress} +++can be given as an expression. +++ +++If an optional @var{offset} is specified, it is added to the start +++address of each section, except those for which the address was +++specified explicitly. +++ +++The symbol table of the file @var{filename} is added to the symbol table +++originally read with the @code{symbol-file} command. You can use the +++@code{add-symbol-file} command any number of times; the new symbol data +++thus read is kept in addition to the old. +++ +++Changes can be reverted using the command @code{remove-symbol-file}. +++ +++@cindex relocatable object files, reading symbols from +++@cindex object files, relocatable, reading symbols from +++@cindex reading symbols from relocatable object files +++@cindex symbols, reading from relocatable object files +++@cindex @file{.o} files, reading symbols from +++Although @var{filename} is typically a shared library file, an +++executable file, or some other object file which has been fully +++relocated for loading into a process, you can also load symbolic +++information from relocatable @file{.o} files, as long as: +++ +++@itemize @bullet +++@item +++the file's symbolic information refers only to linker symbols defined in +++that file, not to symbols defined by other object files, +++@item +++every section the file's symbolic information refers to has actually +++been loaded into the inferior, as it appears in the file, and +++@item +++you can determine the address at which every section was loaded, and +++provide these to the @code{add-symbol-file} command. +++@end itemize +++ +++@noindent +++Some embedded operating systems, like Sun Chorus and VxWorks, can load +++relocatable files into an already running program; such systems +++typically make the requirements above easy to meet. However, it's +++important to recognize that many native systems use complex link +++procedures (@code{.linkonce} section factoring and C@t{++} constructor table +++assembly, for example) that make the requirements difficult to meet. In +++general, one cannot assume that using @code{add-symbol-file} to read a +++relocatable object file's symbolic information will have the same effect +++as linking the relocatable object file into the program in the normal +++way. +++ +++@code{add-symbol-file} does not repeat if you press @key{RET} after using it. +++ +++@kindex remove-symbol-file +++@item remove-symbol-file @var{filename} +++@item remove-symbol-file -a @var{address} +++Remove a symbol file added via the @code{add-symbol-file} command. The +++file to remove can be identified by its @var{filename} or by an @var{address} +++that lies within the boundaries of this symbol file in memory. Example: +++ +++@smallexample +++(gdb) add-symbol-file /home/user/gdb/mylib.so 0x7ffff7ff9480 +++add symbol table from file "/home/user/gdb/mylib.so" at +++ .text_addr = 0x7ffff7ff9480 +++(y or n) y +++Reading symbols from /home/user/gdb/mylib.so... +++(gdb) remove-symbol-file -a 0x7ffff7ff9480 +++Remove symbol table from file "/home/user/gdb/mylib.so"? (y or n) y +++(gdb) +++@end smallexample +++ +++ +++@code{remove-symbol-file} does not repeat if you press @key{RET} after using it. +++ +++@kindex add-symbol-file-from-memory +++@cindex @code{syscall DSO} +++@cindex load symbols from memory +++@item add-symbol-file-from-memory @var{address} +++Load symbols from the given @var{address} in a dynamically loaded +++object file whose image is mapped directly into the inferior's memory. +++For example, the Linux kernel maps a @code{syscall DSO} into each +++process's address space; this DSO provides kernel-specific code for +++some system calls. The argument can be any expression whose +++evaluation yields the address of the file's shared object file header. +++For this command to work, you must have used @code{symbol-file} or +++@code{exec-file} commands in advance. +++ +++@kindex section +++@item section @var{section} @var{addr} +++The @code{section} command changes the base address of the named +++@var{section} of the exec file to @var{addr}. This can be used if the +++exec file does not contain section addresses, (such as in the +++@code{a.out} format), or when the addresses specified in the file +++itself are wrong. Each section must be changed separately. The +++@code{info files} command, described below, lists all the sections and +++their addresses. +++ +++@kindex info files +++@kindex info target +++@item info files +++@itemx info target +++@code{info files} and @code{info target} are synonymous; both print the +++current target (@pxref{Targets, ,Specifying a Debugging Target}), +++including the names of the executable and core dump files currently in +++use by @value{GDBN}, and the files from which symbols were loaded. The +++command @code{help target} lists all possible targets rather than +++current ones. +++ +++@kindex maint info sections +++@item maint info sections +++Another command that can give you extra information about program sections +++is @code{maint info sections}. In addition to the section information +++displayed by @code{info files}, this command displays the flags and file +++offset of each section in the executable and core dump files. In addition, +++@code{maint info sections} provides the following command options (which +++may be arbitrarily combined): +++ +++@table @code +++@item ALLOBJ +++Display sections for all loaded object files, including shared libraries. +++@item @var{sections} +++Display info only for named @var{sections}. +++@item @var{section-flags} +++Display info only for sections for which @var{section-flags} are true. +++The section flags that @value{GDBN} currently knows about are: +++@table @code +++@item ALLOC +++Section will have space allocated in the process when loaded. +++Set for all sections except those containing debug information. +++@item LOAD +++Section will be loaded from the file into the child process memory. +++Set for pre-initialized code and data, clear for @code{.bss} sections. +++@item RELOC +++Section needs to be relocated before loading. +++@item READONLY +++Section cannot be modified by the child process. +++@item CODE +++Section contains executable code only. +++@item DATA +++Section contains data only (no executable code). +++@item ROM +++Section will reside in ROM. +++@item CONSTRUCTOR +++Section contains data for constructor/destructor lists. +++@item HAS_CONTENTS +++Section is not empty. +++@item NEVER_LOAD +++An instruction to the linker to not output the section. +++@item COFF_SHARED_LIBRARY +++A notification to the linker that the section contains +++COFF shared library information. +++@item IS_COMMON +++Section contains common symbols. +++@end table +++@end table +++@kindex set trust-readonly-sections +++@cindex read-only sections +++@item set trust-readonly-sections on +++Tell @value{GDBN} that readonly sections in your object file +++really are read-only (i.e.@: that their contents will not change). +++In that case, @value{GDBN} can fetch values from these sections +++out of the object file, rather than from the target program. +++For some targets (notably embedded ones), this can be a significant +++enhancement to debugging performance. +++ +++The default is off. +++ +++@item set trust-readonly-sections off +++Tell @value{GDBN} not to trust readonly sections. This means that +++the contents of the section might change while the program is running, +++and must therefore be fetched from the target when needed. +++ +++@item show trust-readonly-sections +++Show the current setting of trusting readonly sections. +++@end table +++ +++All file-specifying commands allow both absolute and relative file names +++as arguments. @value{GDBN} always converts the file name to an absolute file +++name and remembers it that way. +++ +++@cindex shared libraries +++@anchor{Shared Libraries} +++@value{GDBN} supports @sc{gnu}/Linux, MS-Windows, SunOS, +++Darwin/Mach-O, SVr4, IBM RS/6000 AIX, QNX Neutrino, FDPIC (FR-V), and +++DSBT (TIC6X) shared libraries. +++ +++On MS-Windows @value{GDBN} must be linked with the Expat library to support +++shared libraries. @xref{Expat}. +++ +++@value{GDBN} automatically loads symbol definitions from shared libraries +++when you use the @code{run} command, or when you examine a core file. +++(Before you issue the @code{run} command, @value{GDBN} does not understand +++references to a function in a shared library, however---unless you are +++debugging a core file). +++ +++@c FIXME: some @value{GDBN} release may permit some refs to undef +++@c FIXME...symbols---eg in a break cmd---assuming they are from a shared +++@c FIXME...lib; check this from time to time when updating manual +++ +++There are times, however, when you may wish to not automatically load +++symbol definitions from shared libraries, such as when they are +++particularly large or there are many of them. +++ +++To control the automatic loading of shared library symbols, use the +++commands: +++ +++@table @code +++@kindex set auto-solib-add +++@item set auto-solib-add @var{mode} +++If @var{mode} is @code{on}, symbols from all shared object libraries +++will be loaded automatically when the inferior begins execution, you +++attach to an independently started inferior, or when the dynamic linker +++informs @value{GDBN} that a new library has been loaded. If @var{mode} +++is @code{off}, symbols must be loaded manually, using the +++@code{sharedlibrary} command. The default value is @code{on}. +++ +++@cindex memory used for symbol tables +++If your program uses lots of shared libraries with debug info that +++takes large amounts of memory, you can decrease the @value{GDBN} +++memory footprint by preventing it from automatically loading the +++symbols from shared libraries. To that end, type @kbd{set +++auto-solib-add off} before running the inferior, then load each +++library whose debug symbols you do need with @kbd{sharedlibrary +++@var{regexp}}, where @var{regexp} is a regular expression that matches +++the libraries whose symbols you want to be loaded. +++ +++@kindex show auto-solib-add +++@item show auto-solib-add +++Display the current autoloading mode. +++@end table +++ +++@cindex load shared library +++To explicitly load shared library symbols, use the @code{sharedlibrary} +++command: +++ +++@table @code +++@kindex info sharedlibrary +++@kindex info share +++@item info share @var{regex} +++@itemx info sharedlibrary @var{regex} +++Print the names of the shared libraries which are currently loaded +++that match @var{regex}. If @var{regex} is omitted then print +++all shared libraries that are loaded. +++ +++@kindex info dll +++@item info dll @var{regex} +++This is an alias of @code{info sharedlibrary}. +++ +++@kindex sharedlibrary +++@kindex share +++@item sharedlibrary @var{regex} +++@itemx share @var{regex} +++Load shared object library symbols for files matching a +++Unix regular expression. +++As with files loaded automatically, it only loads shared libraries +++required by your program for a core file or after typing @code{run}. If +++@var{regex} is omitted all shared libraries required by your program are +++loaded. +++ +++@item nosharedlibrary +++@kindex nosharedlibrary +++@cindex unload symbols from shared libraries +++Unload all shared object library symbols. This discards all symbols +++that have been loaded from all shared libraries. Symbols from shared +++libraries that were loaded by explicit user requests are not +++discarded. +++@end table +++ +++Sometimes you may wish that @value{GDBN} stops and gives you control +++when any of shared library events happen. The best way to do this is +++to use @code{catch load} and @code{catch unload} (@pxref{Set +++Catchpoints}). +++ +++@value{GDBN} also supports the @code{set stop-on-solib-events} +++command for this. This command exists for historical reasons. It is +++less useful than setting a catchpoint, because it does not allow for +++conditions or commands as a catchpoint does. +++ +++@table @code +++@item set stop-on-solib-events +++@kindex set stop-on-solib-events +++This command controls whether @value{GDBN} should give you control +++when the dynamic linker notifies it about some shared library event. +++The most common event of interest is loading or unloading of a new +++shared library. +++ +++@item show stop-on-solib-events +++@kindex show stop-on-solib-events +++Show whether @value{GDBN} stops and gives you control when shared +++library events happen. +++@end table +++ +++Shared libraries are also supported in many cross or remote debugging +++configurations. @value{GDBN} needs to have access to the target's libraries; +++this can be accomplished either by providing copies of the libraries +++on the host system, or by asking @value{GDBN} to automatically retrieve the +++libraries from the target. If copies of the target libraries are +++provided, they need to be the same as the target libraries, although the +++copies on the target can be stripped as long as the copies on the host are +++not. +++ +++@cindex where to look for shared libraries +++For remote debugging, you need to tell @value{GDBN} where the target +++libraries are, so that it can load the correct copies---otherwise, it +++may try to load the host's libraries. @value{GDBN} has two variables +++to specify the search directories for target libraries. +++ +++@table @code +++@cindex prefix for executable and shared library file names +++@cindex system root, alternate +++@kindex set solib-absolute-prefix +++@kindex set sysroot +++@item set sysroot @var{path} +++Use @var{path} as the system root for the program being debugged. Any +++absolute shared library paths will be prefixed with @var{path}; many +++runtime loaders store the absolute paths to the shared library in the +++target program's memory. When starting processes remotely, and when +++attaching to already-running processes (local or remote), their +++executable filenames will be prefixed with @var{path} if reported to +++@value{GDBN} as absolute by the operating system. If you use +++@code{set sysroot} to find executables and shared libraries, they need +++to be laid out in the same way that they are on the target, with +++e.g.@: a @file{/bin}, @file{/lib} and @file{/usr/lib} hierarchy under +++@var{path}. +++ +++If @var{path} starts with the sequence @file{target:} and the target +++system is remote then @value{GDBN} will retrieve the target binaries +++from the remote system. This is only supported when using a remote +++target that supports the @code{remote get} command (@pxref{File +++Transfer,,Sending files to a remote system}). The part of @var{path} +++following the initial @file{target:} (if present) is used as system +++root prefix on the remote file system. If @var{path} starts with the +++sequence @file{remote:} this is converted to the sequence +++@file{target:} by @code{set sysroot}@footnote{Historically the +++functionality to retrieve binaries from the remote system was +++provided by prefixing @var{path} with @file{remote:}}. If you want +++to specify a local system root using a directory that happens to be +++named @file{target:} or @file{remote:}, you need to use some +++equivalent variant of the name like @file{./target:}. +++ +++For targets with an MS-DOS based filesystem, such as MS-Windows and +++SymbianOS, @value{GDBN} tries prefixing a few variants of the target +++absolute file name with @var{path}. But first, on Unix hosts, +++@value{GDBN} converts all backslash directory separators into forward +++slashes, because the backslash is not a directory separator on Unix: +++ +++@smallexample +++ c:\foo\bar.dll @result{} c:/foo/bar.dll +++@end smallexample +++ +++Then, @value{GDBN} attempts prefixing the target file name with +++@var{path}, and looks for the resulting file name in the host file +++system: +++ +++@smallexample +++ c:/foo/bar.dll @result{} /path/to/sysroot/c:/foo/bar.dll +++@end smallexample +++ +++If that does not find the binary, @value{GDBN} tries removing +++the @samp{:} character from the drive spec, both for convenience, and, +++for the case of the host file system not supporting file names with +++colons: +++ +++@smallexample +++ c:/foo/bar.dll @result{} /path/to/sysroot/c/foo/bar.dll +++@end smallexample +++ +++This makes it possible to have a system root that mirrors a target +++with more than one drive. E.g., you may want to setup your local +++copies of the target system shared libraries like so (note @samp{c} vs +++@samp{z}): +++ +++@smallexample +++ @file{/path/to/sysroot/c/sys/bin/foo.dll} +++ @file{/path/to/sysroot/c/sys/bin/bar.dll} +++ @file{/path/to/sysroot/z/sys/bin/bar.dll} +++@end smallexample +++ +++@noindent +++and point the system root at @file{/path/to/sysroot}, so that +++@value{GDBN} can find the correct copies of both +++@file{c:\sys\bin\foo.dll}, and @file{z:\sys\bin\bar.dll}. +++ +++If that still does not find the binary, @value{GDBN} tries +++removing the whole drive spec from the target file name: +++ +++@smallexample +++ c:/foo/bar.dll @result{} /path/to/sysroot/foo/bar.dll +++@end smallexample +++ +++This last lookup makes it possible to not care about the drive name, +++if you don't want or need to. +++ +++The @code{set solib-absolute-prefix} command is an alias for @code{set +++sysroot}. +++ +++@cindex default system root +++@cindex @samp{--with-sysroot} +++You can set the default system root by using the configure-time +++@samp{--with-sysroot} option. If the system root is inside +++@value{GDBN}'s configured binary prefix (set with @samp{--prefix} or +++@samp{--exec-prefix}), then the default system root will be updated +++automatically if the installed @value{GDBN} is moved to a new +++location. +++ +++@kindex show sysroot +++@item show sysroot +++Display the current executable and shared library prefix. +++ +++@kindex set solib-search-path +++@item set solib-search-path @var{path} +++If this variable is set, @var{path} is a colon-separated list of +++directories to search for shared libraries. @samp{solib-search-path} +++is used after @samp{sysroot} fails to locate the library, or if the +++path to the library is relative instead of absolute. If you want to +++use @samp{solib-search-path} instead of @samp{sysroot}, be sure to set +++@samp{sysroot} to a nonexistent directory to prevent @value{GDBN} from +++finding your host's libraries. @samp{sysroot} is preferred; setting +++it to a nonexistent directory may interfere with automatic loading +++of shared library symbols. +++ +++@kindex show solib-search-path +++@item show solib-search-path +++Display the current shared library search path. +++ +++@cindex DOS file-name semantics of file names. +++@kindex set target-file-system-kind (unix|dos-based|auto) +++@kindex show target-file-system-kind +++@item set target-file-system-kind @var{kind} +++Set assumed file system kind for target reported file names. +++ +++Shared library file names as reported by the target system may not +++make sense as is on the system @value{GDBN} is running on. For +++example, when remote debugging a target that has MS-DOS based file +++system semantics, from a Unix host, the target may be reporting to +++@value{GDBN} a list of loaded shared libraries with file names such as +++@file{c:\Windows\kernel32.dll}. On Unix hosts, there's no concept of +++drive letters, so the @samp{c:\} prefix is not normally understood as +++indicating an absolute file name, and neither is the backslash +++normally considered a directory separator character. In that case, +++the native file system would interpret this whole absolute file name +++as a relative file name with no directory components. This would make +++it impossible to point @value{GDBN} at a copy of the remote target's +++shared libraries on the host using @code{set sysroot}, and impractical +++with @code{set solib-search-path}. Setting +++@code{target-file-system-kind} to @code{dos-based} tells @value{GDBN} +++to interpret such file names similarly to how the target would, and to +++map them to file names valid on @value{GDBN}'s native file system +++semantics. The value of @var{kind} can be @code{"auto"}, in addition +++to one of the supported file system kinds. In that case, @value{GDBN} +++tries to determine the appropriate file system variant based on the +++current target's operating system (@pxref{ABI, ,Configuring the +++Current ABI}). The supported file system settings are: +++ +++@table @code +++@item unix +++Instruct @value{GDBN} to assume the target file system is of Unix +++kind. Only file names starting the forward slash (@samp{/}) character +++are considered absolute, and the directory separator character is also +++the forward slash. +++ +++@item dos-based +++Instruct @value{GDBN} to assume the target file system is DOS based. +++File names starting with either a forward slash, or a drive letter +++followed by a colon (e.g., @samp{c:}), are considered absolute, and +++both the slash (@samp{/}) and the backslash (@samp{\\}) characters are +++considered directory separators. +++ +++@item auto +++Instruct @value{GDBN} to use the file system kind associated with the +++target operating system (@pxref{ABI, ,Configuring the Current ABI}). +++This is the default. +++@end table +++@end table +++ +++@cindex file name canonicalization +++@cindex base name differences +++When processing file names provided by the user, @value{GDBN} +++frequently needs to compare them to the file names recorded in the +++program's debug info. Normally, @value{GDBN} compares just the +++@dfn{base names} of the files as strings, which is reasonably fast +++even for very large programs. (The base name of a file is the last +++portion of its name, after stripping all the leading directories.) +++This shortcut in comparison is based upon the assumption that files +++cannot have more than one base name. This is usually true, but +++references to files that use symlinks or similar filesystem +++facilities violate that assumption. If your program records files +++using such facilities, or if you provide file names to @value{GDBN} +++using symlinks etc., you can set @code{basenames-may-differ} to +++@code{true} to instruct @value{GDBN} to completely canonicalize each +++pair of file names it needs to compare. This will make file-name +++comparisons accurate, but at a price of a significant slowdown. +++ +++@table @code +++@item set basenames-may-differ +++@kindex set basenames-may-differ +++Set whether a source file may have multiple base names. +++ +++@item show basenames-may-differ +++@kindex show basenames-may-differ +++Show whether a source file may have multiple base names. +++@end table +++ +++@node File Caching +++@section File Caching +++@cindex caching of opened files +++@cindex caching of bfd objects +++ +++To speed up file loading, and reduce memory usage, @value{GDBN} will +++reuse the @code{bfd} objects used to track open files. @xref{Top, , +++BFD, bfd, The Binary File Descriptor Library}. The following commands +++allow visibility and control of the caching behavior. +++ +++@table @code +++@kindex maint info bfds +++@item maint info bfds +++This prints information about each @code{bfd} object that is known to +++@value{GDBN}. +++ +++@kindex maint set bfd-sharing +++@kindex maint show bfd-sharing +++@kindex bfd caching +++@item maint set bfd-sharing +++@item maint show bfd-sharing +++Control whether @code{bfd} objects can be shared. When sharing is +++enabled @value{GDBN} reuses already open @code{bfd} objects rather +++than reopening the same file. Turning sharing off does not cause +++already shared @code{bfd} objects to be unshared, but all future files +++that are opened will create a new @code{bfd} object. Similarly, +++re-enabling sharing does not cause multiple existing @code{bfd} +++objects to be collapsed into a single shared @code{bfd} object. +++ +++@kindex set debug bfd-cache @var{level} +++@kindex bfd caching +++@item set debug bfd-cache @var{level} +++Turns on debugging of the bfd cache, setting the level to @var{level}. +++ +++@kindex show debug bfd-cache +++@kindex bfd caching +++@item show debug bfd-cache +++Show the current debugging level of the bfd cache. +++@end table +++ +++@node Separate Debug Files +++@section Debugging Information in Separate Files +++@cindex separate debugging information files +++@cindex debugging information in separate files +++@cindex @file{.debug} subdirectories +++@cindex debugging information directory, global +++@cindex global debugging information directories +++@cindex build ID, and separate debugging files +++@cindex @file{.build-id} directory +++ +++@value{GDBN} allows you to put a program's debugging information in a +++file separate from the executable itself, in a way that allows +++@value{GDBN} to find and load the debugging information automatically. +++Since debugging information can be very large---sometimes larger +++than the executable code itself---some systems distribute debugging +++information for their executables in separate files, which users can +++install only when they need to debug a problem. +++ +++@value{GDBN} supports two ways of specifying the separate debug info +++file: +++ +++@itemize @bullet +++@item +++The executable contains a @dfn{debug link} that specifies the name of +++the separate debug info file. The separate debug file's name is +++usually @file{@var{executable}.debug}, where @var{executable} is the +++name of the corresponding executable file without leading directories +++(e.g., @file{ls.debug} for @file{/usr/bin/ls}). In addition, the +++debug link specifies a 32-bit @dfn{Cyclic Redundancy Check} (CRC) +++checksum for the debug file, which @value{GDBN} uses to validate that +++the executable and the debug file came from the same build. +++ +++@item +++@anchor{build ID} +++The executable contains a @dfn{build ID}, a unique bit string that is +++also present in the corresponding debug info file. (This is supported +++only on some operating systems, when using the ELF or PE file formats +++for binary files and the @sc{gnu} Binutils.) For more details about +++this feature, see the description of the @option{--build-id} +++command-line option in @ref{Options, , Command Line Options, ld, +++The GNU Linker}. The debug info file's name is not specified +++explicitly by the build ID, but can be computed from the build ID, see +++below. +++@end itemize +++ +++Depending on the way the debug info file is specified, @value{GDBN} +++uses two different methods of looking for the debug file: +++ +++@itemize @bullet +++@item +++For the ``debug link'' method, @value{GDBN} looks up the named file in +++the directory of the executable file, then in a subdirectory of that +++directory named @file{.debug}, and finally under each one of the +++global debug directories, in a subdirectory whose name is identical to +++the leading directories of the executable's absolute file name. (On +++MS-Windows/MS-DOS, the drive letter of the executable's leading +++directories is converted to a one-letter subdirectory, i.e.@: +++@file{d:/usr/bin/} is converted to @file{/d/usr/bin/}, because Windows +++filesystems disallow colons in file names.) +++ +++@item +++For the ``build ID'' method, @value{GDBN} looks in the +++@file{.build-id} subdirectory of each one of the global debug directories for +++a file named @file{@var{nn}/@var{nnnnnnnn}.debug}, where @var{nn} are the +++first 2 hex characters of the build ID bit string, and @var{nnnnnnnn} +++are the rest of the bit string. (Real build ID strings are 32 or more +++hex characters, not 10.) +++@end itemize +++ +++So, for example, suppose you ask @value{GDBN} to debug +++@file{/usr/bin/ls}, which has a debug link that specifies the +++file @file{ls.debug}, and a build ID whose value in hex is +++@code{abcdef1234}. If the list of the global debug directories includes +++@file{/usr/lib/debug}, then @value{GDBN} will look for the following +++debug information files, in the indicated order: +++ +++@itemize @minus +++@item +++@file{/usr/lib/debug/.build-id/ab/cdef1234.debug} +++@item +++@file{/usr/bin/ls.debug} +++@item +++@file{/usr/bin/.debug/ls.debug} +++@item +++@file{/usr/lib/debug/usr/bin/ls.debug}. +++@end itemize +++ +++@anchor{debug-file-directory} +++Global debugging info directories default to what is set by @value{GDBN} +++configure option @option{--with-separate-debug-dir}. During @value{GDBN} run +++you can also set the global debugging info directories, and view the list +++@value{GDBN} is currently using. +++ +++@table @code +++ +++@kindex set debug-file-directory +++@item set debug-file-directory @var{directories} +++Set the directories which @value{GDBN} searches for separate debugging +++information files to @var{directory}. Multiple path components can be set +++concatenating them by a path separator. +++ +++@kindex show debug-file-directory +++@item show debug-file-directory +++Show the directories @value{GDBN} searches for separate debugging +++information files. +++ +++@end table +++ +++@cindex @code{.gnu_debuglink} sections +++@cindex debug link sections +++A debug link is a special section of the executable file named +++@code{.gnu_debuglink}. The section must contain: +++ +++@itemize +++@item +++A filename, with any leading directory components removed, followed by +++a zero byte, +++@item +++zero to three bytes of padding, as needed to reach the next four-byte +++boundary within the section, and +++@item +++a four-byte CRC checksum, stored in the same endianness used for the +++executable file itself. The checksum is computed on the debugging +++information file's full contents by the function given below, passing +++zero as the @var{crc} argument. +++@end itemize +++ +++Any executable file format can carry a debug link, as long as it can +++contain a section named @code{.gnu_debuglink} with the contents +++described above. +++ +++@cindex @code{.note.gnu.build-id} sections +++@cindex build ID sections +++The build ID is a special section in the executable file (and in other +++ELF binary files that @value{GDBN} may consider). This section is +++often named @code{.note.gnu.build-id}, but that name is not mandatory. +++It contains unique identification for the built files---the ID remains +++the same across multiple builds of the same build tree. The default +++algorithm SHA1 produces 160 bits (40 hexadecimal characters) of the +++content for the build ID string. The same section with an identical +++value is present in the original built binary with symbols, in its +++stripped variant, and in the separate debugging information file. +++ +++The debugging information file itself should be an ordinary +++executable, containing a full set of linker symbols, sections, and +++debugging information. The sections of the debugging information file +++should have the same names, addresses, and sizes as the original file, +++but they need not contain any data---much like a @code{.bss} section +++in an ordinary executable. +++ +++The @sc{gnu} binary utilities (Binutils) package includes the +++@samp{objcopy} utility that can produce +++the separated executable / debugging information file pairs using the +++following commands: +++ +++@smallexample +++@kbd{objcopy --only-keep-debug foo foo.debug} +++@kbd{strip -g foo} +++@end smallexample +++ +++@noindent +++These commands remove the debugging +++information from the executable file @file{foo} and place it in the file +++@file{foo.debug}. You can use the first, second or both methods to link the +++two files: +++ +++@itemize @bullet +++@item +++The debug link method needs the following additional command to also leave +++behind a debug link in @file{foo}: +++ +++@smallexample +++@kbd{objcopy --add-gnu-debuglink=foo.debug foo} +++@end smallexample +++ +++Ulrich Drepper's @file{elfutils} package, starting with version 0.53, contains +++a version of the @code{strip} command such that the command @kbd{strip foo -f +++foo.debug} has the same functionality as the two @code{objcopy} commands and +++the @code{ln -s} command above, together. +++ +++@item +++Build ID gets embedded into the main executable using @code{ld --build-id} or +++the @value{NGCC} counterpart @code{gcc -Wl,--build-id}. Build ID support plus +++compatibility fixes for debug files separation are present in @sc{gnu} binary +++utilities (Binutils) package since version 2.18. +++@end itemize +++ +++@noindent +++ +++@cindex CRC algorithm definition +++The CRC used in @code{.gnu_debuglink} is the CRC-32 defined in +++IEEE 802.3 using the polynomial: +++ +++@c TexInfo requires naked braces for multi-digit exponents for Tex +++@c output, but this causes HTML output to barf. HTML has to be set using +++@c raw commands. So we end up having to specify this equation in 2 +++@c different ways! +++@ifhtml +++@display +++@html +++ x32 + x26 + x23 + x22 + x16 + x12 + x11 +++ + x10 + x8 + x7 + x5 + x4 + x2 + x + 1 +++@end html +++@end display +++@end ifhtml +++@ifnothtml +++@display +++ @math{x^{32} + x^{26} + x^{23} + x^{22} + x^{16} + x^{12} + x^{11}} +++ @math{+ x^{10} + x^8 + x^7 + x^5 + x^4 + x^2 + x + 1} +++@end display +++@end ifnothtml +++ +++The function is computed byte at a time, taking the least +++significant bit of each byte first. The initial pattern +++@code{0xffffffff} is used, to ensure leading zeros affect the CRC and +++the final result is inverted to ensure trailing zeros also affect the +++CRC. +++ +++@emph{Note:} This is the same CRC polynomial as used in handling the +++@dfn{Remote Serial Protocol} @code{qCRC} packet (@pxref{qCRC packet}). +++However in the case of the Remote Serial Protocol, the CRC is computed +++@emph{most} significant bit first, and the result is not inverted, so +++trailing zeros have no effect on the CRC value. +++ +++To complete the description, we show below the code of the function +++which produces the CRC used in @code{.gnu_debuglink}. Inverting the +++initially supplied @code{crc} argument means that an initial call to +++this function passing in zero will start computing the CRC using +++@code{0xffffffff}. +++ +++@kindex gnu_debuglink_crc32 +++@smallexample +++unsigned long +++gnu_debuglink_crc32 (unsigned long crc, +++ unsigned char *buf, size_t len) +++@{ +++ static const unsigned long crc32_table[256] = +++ @{ +++ 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, +++ 0x706af48f, 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, +++ 0xe0d5e91e, 0x97d2d988, 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, +++ 0x90bf1d91, 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de, +++ 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, 0x136c9856, +++ 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9, +++ 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, +++ 0xa2677172, 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, +++ 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, +++ 0x45df5c75, 0xdcd60dcf, 0xabd13d59, 0x26d930ac, 0x51de003a, +++ 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, 0xcfba9599, +++ 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, +++ 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, +++ 0x01db7106, 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, +++ 0x9fbfe4a5, 0xe8b8d433, 0x7807c9a2, 0x0f00f934, 0x9609a88e, +++ 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01, +++ 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, 0x6c0695ed, +++ 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950, +++ 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, +++ 0xfbd44c65, 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, +++ 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, +++ 0x346ed9fc, 0xad678846, 0xda60b8d0, 0x44042d73, 0x33031de5, +++ 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa, 0xbe0b1010, +++ 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f, +++ 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, +++ 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, +++ 0x03b6e20c, 0x74b1d29a, 0xead54739, 0x9dd277af, 0x04db2615, +++ 0x73dc1683, 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8, +++ 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, 0xf00f9344, +++ 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb, +++ 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, +++ 0x67dd4acc, 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, +++ 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, +++ 0xa6bc5767, 0x3fb506dd, 0x48b2364b, 0xd80d2bda, 0xaf0a1b4c, +++ 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, 0x316e8eef, +++ 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, +++ 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, +++ 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, +++ 0x2cd99e8b, 0x5bdeae1d, 0x9b64c2b0, 0xec63f226, 0x756aa39c, +++ 0x026d930a, 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713, +++ 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, 0x92d28e9b, +++ 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242, +++ 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, +++ 0x18b74777, 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, +++ 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45, 0xa00ae278, +++ 0xd70dd2ee, 0x4e048354, 0x3903b3c2, 0xa7672661, 0xd06016f7, +++ 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc, 0x40df0b66, +++ 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9, +++ 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, +++ 0xcdd70693, 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, +++ 0x5d681b02, 0x2a6f2b94, 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, +++ 0x2d02ef8d +++ @}; +++ unsigned char *end; +++ +++ crc = ~crc & 0xffffffff; +++ for (end = buf + len; buf < end; ++buf) +++ crc = crc32_table[(crc ^ *buf) & 0xff] ^ (crc >> 8); +++ return ~crc & 0xffffffff; +++@} +++@end smallexample +++ +++@noindent +++This computation does not apply to the ``build ID'' method. +++ +++@node MiniDebugInfo +++@section Debugging information in a special section +++@cindex separate debug sections +++@cindex @samp{.gnu_debugdata} section +++ +++Some systems ship pre-built executables and libraries that have a +++special @samp{.gnu_debugdata} section. This feature is called +++@dfn{MiniDebugInfo}. This section holds an LZMA-compressed object and +++is used to supply extra symbols for backtraces. +++ +++The intent of this section is to provide extra minimal debugging +++information for use in simple backtraces. It is not intended to be a +++replacement for full separate debugging information (@pxref{Separate +++Debug Files}). The example below shows the intended use; however, +++@value{GDBN} does not currently put restrictions on what sort of +++debugging information might be included in the section. +++ +++@value{GDBN} has support for this extension. If the section exists, +++then it is used provided that no other source of debugging information +++can be found, and that @value{GDBN} was configured with LZMA support. +++ +++This section can be easily created using @command{objcopy} and other +++standard utilities: +++ +++@smallexample +++# Extract the dynamic symbols from the main binary, there is no need +++# to also have these in the normal symbol table. +++nm -D @var{binary} --format=posix --defined-only \ +++ | awk '@{ print $1 @}' | sort > dynsyms +++ +++# Extract all the text (i.e. function) symbols from the debuginfo. +++# (Note that we actually also accept "D" symbols, for the benefit +++# of platforms like PowerPC64 that use function descriptors.) +++nm @var{binary} --format=posix --defined-only \ +++ | awk '@{ if ($2 == "T" || $2 == "t" || $2 == "D") print $1 @}' \ +++ | sort > funcsyms +++ +++# Keep all the function symbols not already in the dynamic symbol +++# table. +++comm -13 dynsyms funcsyms > keep_symbols +++ +++# Separate full debug info into debug binary. +++objcopy --only-keep-debug @var{binary} debug +++ +++# Copy the full debuginfo, keeping only a minimal set of symbols and +++# removing some unnecessary sections. +++objcopy -S --remove-section .gdb_index --remove-section .comment \ +++ --keep-symbols=keep_symbols debug mini_debuginfo +++ +++# Drop the full debug info from the original binary. +++strip --strip-all -R .comment @var{binary} +++ +++# Inject the compressed data into the .gnu_debugdata section of the +++# original binary. +++xz mini_debuginfo +++objcopy --add-section .gnu_debugdata=mini_debuginfo.xz @var{binary} +++@end smallexample +++ +++@node Index Files +++@section Index Files Speed Up @value{GDBN} +++@cindex index files +++@cindex @samp{.gdb_index} section +++ +++When @value{GDBN} finds a symbol file, it scans the symbols in the +++file in order to construct an internal symbol table. This lets most +++@value{GDBN} operations work quickly---at the cost of a delay early +++on. For large programs, this delay can be quite lengthy, so +++@value{GDBN} provides a way to build an index, which speeds up +++startup. +++ +++For convenience, @value{GDBN} comes with a program, +++@command{gdb-add-index}, which can be used to add the index to a +++symbol file. It takes the symbol file as its only argument: +++ +++@smallexample +++$ gdb-add-index symfile +++@end smallexample +++ +++@xref{gdb-add-index}. +++ +++It is also possible to do the work manually. Here is what +++@command{gdb-add-index} does behind the curtains. +++ +++The index is stored as a section in the symbol file. @value{GDBN} can +++write the index to a file, then you can put it into the symbol file +++using @command{objcopy}. +++ +++To create an index file, use the @code{save gdb-index} command: +++ +++@table @code +++@item save gdb-index [-dwarf-5] @var{directory} +++@kindex save gdb-index +++Create index files for all symbol files currently known by +++@value{GDBN}. For each known @var{symbol-file}, this command by +++default creates it produces a single file +++@file{@var{symbol-file}.gdb-index}. If you invoke this command with +++the @option{-dwarf-5} option, it produces 2 files: +++@file{@var{symbol-file}.debug_names} and +++@file{@var{symbol-file}.debug_str}. The files are created in the +++given @var{directory}. +++@end table +++ +++Once you have created an index file you can merge it into your symbol +++file, here named @file{symfile}, using @command{objcopy}: +++ +++@smallexample +++$ objcopy --add-section .gdb_index=symfile.gdb-index \ +++ --set-section-flags .gdb_index=readonly symfile symfile +++@end smallexample +++ +++Or for @code{-dwarf-5}: +++ +++@smallexample +++$ objcopy --dump-section .debug_str=symfile.debug_str.new symfile +++$ cat symfile.debug_str >>symfile.debug_str.new +++$ objcopy --add-section .debug_names=symfile.gdb-index \ +++ --set-section-flags .debug_names=readonly \ +++ --update-section .debug_str=symfile.debug_str.new symfile symfile +++@end smallexample +++ +++@value{GDBN} will normally ignore older versions of @file{.gdb_index} +++sections that have been deprecated. Usually they are deprecated because +++they are missing a new feature or have performance issues. +++To tell @value{GDBN} to use a deprecated index section anyway +++specify @code{set use-deprecated-index-sections on}. +++The default is @code{off}. +++This can speed up startup, but may result in some functionality being lost. +++@xref{Index Section Format}. +++ +++@emph{Warning:} Setting @code{use-deprecated-index-sections} to @code{on} +++must be done before gdb reads the file. The following will not work: +++ +++@smallexample +++$ gdb -ex "set use-deprecated-index-sections on" +++@end smallexample +++ +++Instead you must do, for example, +++ +++@smallexample +++$ gdb -iex "set use-deprecated-index-sections on" +++@end smallexample +++ +++Indices only work when using DWARF debugging information, not stabs. +++ +++@subsection Automatic symbol index cache +++ +++@cindex automatic symbol index cache +++It is possible for @value{GDBN} to automatically save a copy of this index in a +++cache on disk and retrieve it from there when loading the same binary in the +++future. This feature can be turned on with @kbd{set index-cache on}. The +++following commands can be used to tweak the behavior of the index cache. +++ +++@table @code +++ +++@kindex set index-cache +++@item set index-cache on +++@itemx set index-cache off +++Enable or disable the use of the symbol index cache. +++ +++@item set index-cache directory @var{directory} +++@kindex show index-cache +++@itemx show index-cache directory +++Set/show the directory where index files will be saved. +++ +++The default value for this directory depends on the host platform. On +++most systems, the index is cached in the @file{gdb} subdirectory of +++the directory pointed to by the @env{XDG_CACHE_HOME} environment +++variable, if it is defined, else in the @file{.cache/gdb} subdirectory +++of your home directory. However, on some systems, the default may +++differ according to local convention. +++ +++There is no limit on the disk space used by index cache. It is perfectly safe +++to delete the content of that directory to free up disk space. +++ +++@item show index-cache stats +++Print the number of cache hits and misses since the launch of @value{GDBN}. +++ +++@end table +++ +++@node Symbol Errors +++@section Errors Reading Symbol Files +++ +++While reading a symbol file, @value{GDBN} occasionally encounters problems, +++such as symbol types it does not recognize, or known bugs in compiler +++output. By default, @value{GDBN} does not notify you of such problems, since +++they are relatively common and primarily of interest to people +++debugging compilers. If you are interested in seeing information +++about ill-constructed symbol tables, you can either ask @value{GDBN} to print +++only one message about each such type of problem, no matter how many +++times the problem occurs; or you can ask @value{GDBN} to print more messages, +++to see how many times the problems occur, with the @code{set +++complaints} command (@pxref{Messages/Warnings, ,Optional Warnings and +++Messages}). +++ +++The messages currently printed, and their meanings, include: +++ +++@table @code +++@item inner block not inside outer block in @var{symbol} +++ +++The symbol information shows where symbol scopes begin and end +++(such as at the start of a function or a block of statements). This +++error indicates that an inner scope block is not fully contained +++in its outer scope blocks. +++ +++@value{GDBN} circumvents the problem by treating the inner block as if it had +++the same scope as the outer block. In the error message, @var{symbol} +++may be shown as ``@code{(don't know)}'' if the outer block is not a +++function. +++ +++@item block at @var{address} out of order +++ +++The symbol information for symbol scope blocks should occur in +++order of increasing addresses. This error indicates that it does not +++do so. +++ +++@value{GDBN} does not circumvent this problem, and has trouble +++locating symbols in the source file whose symbols it is reading. (You +++can often determine what source file is affected by specifying +++@code{set verbose on}. @xref{Messages/Warnings, ,Optional Warnings and +++Messages}.) +++ +++@item bad block start address patched +++ +++The symbol information for a symbol scope block has a start address +++smaller than the address of the preceding source line. This is known +++to occur in the SunOS 4.1.1 (and earlier) C compiler. +++ +++@value{GDBN} circumvents the problem by treating the symbol scope block as +++starting on the previous source line. +++ +++@item bad string table offset in symbol @var{n} +++ +++@cindex foo +++Symbol number @var{n} contains a pointer into the string table which is +++larger than the size of the string table. +++ +++@value{GDBN} circumvents the problem by considering the symbol to have the +++name @code{foo}, which may cause other problems if many symbols end up +++with this name. +++ +++@item unknown symbol type @code{0x@var{nn}} +++ +++The symbol information contains new data types that @value{GDBN} does +++not yet know how to read. @code{0x@var{nn}} is the symbol type of the +++uncomprehended information, in hexadecimal. +++ +++@value{GDBN} circumvents the error by ignoring this symbol information. +++This usually allows you to debug your program, though certain symbols +++are not accessible. If you encounter such a problem and feel like +++debugging it, you can debug @code{@value{GDBP}} with itself, breakpoint +++on @code{complain}, then go up to the function @code{read_dbx_symtab} +++and examine @code{*bufp} to see the symbol. +++ +++@item stub type has NULL name +++ +++@value{GDBN} could not find the full definition for a struct or class. +++ +++@item const/volatile indicator missing (ok if using g++ v1.x), got@dots{} +++The symbol information for a C@t{++} member function is missing some +++information that recent versions of the compiler should have output for +++it. +++ +++@item info mismatch between compiler and debugger +++ +++@value{GDBN} could not parse a type specification output by the compiler. +++ +++@end table +++ +++@node Data Files +++@section GDB Data Files +++ +++@cindex prefix for data files +++@value{GDBN} will sometimes read an auxiliary data file. These files +++are kept in a directory known as the @dfn{data directory}. +++ +++You can set the data directory's name, and view the name @value{GDBN} +++is currently using. +++ +++@table @code +++@kindex set data-directory +++@item set data-directory @var{directory} +++Set the directory which @value{GDBN} searches for auxiliary data files +++to @var{directory}. +++ +++@kindex show data-directory +++@item show data-directory +++Show the directory @value{GDBN} searches for auxiliary data files. +++@end table +++ +++@cindex default data directory +++@cindex @samp{--with-gdb-datadir} +++You can set the default data directory by using the configure-time +++@samp{--with-gdb-datadir} option. If the data directory is inside +++@value{GDBN}'s configured binary prefix (set with @samp{--prefix} or +++@samp{--exec-prefix}), then the default data directory will be updated +++automatically if the installed @value{GDBN} is moved to a new +++location. +++ +++The data directory may also be specified with the +++@code{--data-directory} command line option. +++@xref{Mode Options}. +++ +++@node Targets +++@chapter Specifying a Debugging Target +++ +++@cindex debugging target +++A @dfn{target} is the execution environment occupied by your program. +++ +++Often, @value{GDBN} runs in the same host environment as your program; +++in that case, the debugging target is specified as a side effect when +++you use the @code{file} or @code{core} commands. When you need more +++flexibility---for example, running @value{GDBN} on a physically separate +++host, or controlling a standalone system over a serial port or a +++realtime system over a TCP/IP connection---you can use the @code{target} +++command to specify one of the target types configured for @value{GDBN} +++(@pxref{Target Commands, ,Commands for Managing Targets}). +++ +++@cindex target architecture +++It is possible to build @value{GDBN} for several different @dfn{target +++architectures}. When @value{GDBN} is built like that, you can choose +++one of the available architectures with the @kbd{set architecture} +++command. +++ +++@table @code +++@kindex set architecture +++@kindex show architecture +++@item set architecture @var{arch} +++This command sets the current target architecture to @var{arch}. The +++value of @var{arch} can be @code{"auto"}, in addition to one of the +++supported architectures. +++ +++@item show architecture +++Show the current target architecture. +++ +++@item set processor +++@itemx processor +++@kindex set processor +++@kindex show processor +++These are alias commands for, respectively, @code{set architecture} +++and @code{show architecture}. +++@end table +++ +++@menu +++* Active Targets:: Active targets +++* Target Commands:: Commands for managing targets +++* Byte Order:: Choosing target byte order +++@end menu +++ +++@node Active Targets +++@section Active Targets +++ +++@cindex stacking targets +++@cindex active targets +++@cindex multiple targets +++ +++There are multiple classes of targets such as: processes, executable files or +++recording sessions. Core files belong to the process class, making core file +++and process mutually exclusive. Otherwise, @value{GDBN} can work concurrently +++on multiple active targets, one in each class. This allows you to (for +++example) start a process and inspect its activity, while still having access to +++the executable file after the process finishes. Or if you start process +++recording (@pxref{Reverse Execution}) and @code{reverse-step} there, you are +++presented a virtual layer of the recording target, while the process target +++remains stopped at the chronologically last point of the process execution. +++ +++Use the @code{core-file} and @code{exec-file} commands to select a new core +++file or executable target (@pxref{Files, ,Commands to Specify Files}). To +++specify as a target a process that is already running, use the @code{attach} +++command (@pxref{Attach, ,Debugging an Already-running Process}). +++ +++@node Target Commands +++@section Commands for Managing Targets +++ +++@table @code +++@item target @var{type} @var{parameters} +++Connects the @value{GDBN} host environment to a target machine or +++process. A target is typically a protocol for talking to debugging +++facilities. You use the argument @var{type} to specify the type or +++protocol of the target machine. +++ +++Further @var{parameters} are interpreted by the target protocol, but +++typically include things like device names or host names to connect +++with, process numbers, and baud rates. +++ +++The @code{target} command does not repeat if you press @key{RET} again +++after executing the command. +++ +++@kindex help target +++@item help target +++Displays the names of all targets available. To display targets +++currently selected, use either @code{info target} or @code{info files} +++(@pxref{Files, ,Commands to Specify Files}). +++ +++@item help target @var{name} +++Describe a particular target, including any parameters necessary to +++select it. +++ +++@kindex set gnutarget +++@item set gnutarget @var{args} +++@value{GDBN} uses its own library BFD to read your files. @value{GDBN} +++knows whether it is reading an @dfn{executable}, +++a @dfn{core}, or a @dfn{.o} file; however, you can specify the file format +++with the @code{set gnutarget} command. Unlike most @code{target} commands, +++with @code{gnutarget} the @code{target} refers to a program, not a machine. +++ +++@quotation +++@emph{Warning:} To specify a file format with @code{set gnutarget}, +++you must know the actual BFD name. +++@end quotation +++ +++@noindent +++@xref{Files, , Commands to Specify Files}. +++ +++@kindex show gnutarget +++@item show gnutarget +++Use the @code{show gnutarget} command to display what file format +++@code{gnutarget} is set to read. If you have not set @code{gnutarget}, +++@value{GDBN} will determine the file format for each file automatically, +++and @code{show gnutarget} displays @samp{The current BFD target is "auto"}. +++@end table +++ +++@cindex common targets +++Here are some common targets (available, or not, depending on the GDB +++configuration): +++ +++@table @code +++@kindex target +++@item target exec @var{program} +++@cindex executable file target +++An executable file. @samp{target exec @var{program}} is the same as +++@samp{exec-file @var{program}}. +++ +++@item target core @var{filename} +++@cindex core dump file target +++A core dump file. @samp{target core @var{filename}} is the same as +++@samp{core-file @var{filename}}. +++ +++@item target remote @var{medium} +++@cindex remote target +++A remote system connected to @value{GDBN} via a serial line or network +++connection. This command tells @value{GDBN} to use its own remote +++protocol over @var{medium} for debugging. @xref{Remote Debugging}. +++ +++For example, if you have a board connected to @file{/dev/ttya} on the +++machine running @value{GDBN}, you could say: +++ +++@smallexample +++target remote /dev/ttya +++@end smallexample +++ +++@code{target remote} supports the @code{load} command. This is only +++useful if you have some other way of getting the stub to the target +++system, and you can put it somewhere in memory where it won't get +++clobbered by the download. +++ +++@item target sim @r{[}@var{simargs}@r{]} @dots{} +++@cindex built-in simulator target +++Builtin CPU simulator. @value{GDBN} includes simulators for most architectures. +++In general, +++@smallexample +++ target sim +++ load +++ run +++@end smallexample +++@noindent +++works; however, you cannot assume that a specific memory map, device +++drivers, or even basic I/O is available, although some simulators do +++provide these. For info about any processor-specific simulator details, +++see the appropriate section in @ref{Embedded Processors, ,Embedded +++Processors}. +++ +++@item target native +++@cindex native target +++Setup for local/native process debugging. Useful to make the +++@code{run} command spawn native processes (likewise @code{attach}, +++etc.@:) even when @code{set auto-connect-native-target} is @code{off} +++(@pxref{set auto-connect-native-target}). +++ +++@end table +++ +++Different targets are available on different configurations of @value{GDBN}; +++your configuration may have more or fewer targets. +++ +++Many remote targets require you to download the executable's code once +++you've successfully established a connection. You may wish to control +++various aspects of this process. +++ +++@table @code +++ +++@item set hash +++@kindex set hash@r{, for remote monitors} +++@cindex hash mark while downloading +++This command controls whether a hash mark @samp{#} is displayed while +++downloading a file to the remote monitor. If on, a hash mark is +++displayed after each S-record is successfully downloaded to the +++monitor. +++ +++@item show hash +++@kindex show hash@r{, for remote monitors} +++Show the current status of displaying the hash mark. +++ +++@item set debug monitor +++@kindex set debug monitor +++@cindex display remote monitor communications +++Enable or disable display of communications messages between +++@value{GDBN} and the remote monitor. +++ +++@item show debug monitor +++@kindex show debug monitor +++Show the current status of displaying communications between +++@value{GDBN} and the remote monitor. +++@end table +++ +++@table @code +++ +++@kindex load @var{filename} @var{offset} +++@item load @var{filename} @var{offset} +++@anchor{load} +++Depending on what remote debugging facilities are configured into +++@value{GDBN}, the @code{load} command may be available. Where it exists, it +++is meant to make @var{filename} (an executable) available for debugging +++on the remote system---by downloading, or dynamic linking, for example. +++@code{load} also records the @var{filename} symbol table in @value{GDBN}, like +++the @code{add-symbol-file} command. +++ +++If your @value{GDBN} does not have a @code{load} command, attempting to +++execute it gets the error message ``@code{You can't do that when your +++target is @dots{}}'' +++ +++The file is loaded at whatever address is specified in the executable. +++For some object file formats, you can specify the load address when you +++link the program; for other formats, like a.out, the object file format +++specifies a fixed address. +++@c FIXME! This would be a good place for an xref to the GNU linker doc. +++ +++It is also possible to tell @value{GDBN} to load the executable file at a +++specific offset described by the optional argument @var{offset}. When +++@var{offset} is provided, @var{filename} must also be provided. +++ +++Depending on the remote side capabilities, @value{GDBN} may be able to +++load programs into flash memory. +++ +++@code{load} does not repeat if you press @key{RET} again after using it. +++@end table +++ +++@table @code +++ +++@kindex flash-erase +++@item flash-erase +++@anchor{flash-erase} +++ +++Erases all known flash memory regions on the target. +++ +++@end table +++ +++@node Byte Order +++@section Choosing Target Byte Order +++ +++@cindex choosing target byte order +++@cindex target byte order +++ +++Some types of processors, such as the @acronym{MIPS}, PowerPC, and Renesas SH, +++offer the ability to run either big-endian or little-endian byte +++orders. Usually the executable or symbol will include a bit to +++designate the endian-ness, and you will not need to worry about +++which to use. However, you may still find it useful to adjust +++@value{GDBN}'s idea of processor endian-ness manually. +++ +++@table @code +++@kindex set endian +++@item set endian big +++Instruct @value{GDBN} to assume the target is big-endian. +++ +++@item set endian little +++Instruct @value{GDBN} to assume the target is little-endian. +++ +++@item set endian auto +++Instruct @value{GDBN} to use the byte order associated with the +++executable. +++ +++@item show endian +++Display @value{GDBN}'s current idea of the target byte order. +++ +++@end table +++ +++If the @code{set endian auto} mode is in effect and no executable has +++been selected, then the endianness used is the last one chosen either +++by one of the @code{set endian big} and @code{set endian little} +++commands or by inferring from the last executable used. If no +++endianness has been previously chosen, then the default for this mode +++is inferred from the target @value{GDBN} has been built for, and is +++@code{little} if the name of the target CPU has an @code{el} suffix +++and @code{big} otherwise. +++ +++Note that these commands merely adjust interpretation of symbolic +++data on the host, and that they have absolutely no effect on the +++target system. +++ +++ +++@node Remote Debugging +++@chapter Debugging Remote Programs +++@cindex remote debugging +++ +++If you are trying to debug a program running on a machine that cannot run +++@value{GDBN} in the usual way, it is often useful to use remote debugging. +++For example, you might use remote debugging on an operating system kernel, +++or on a small system which does not have a general purpose operating system +++powerful enough to run a full-featured debugger. +++ +++Some configurations of @value{GDBN} have special serial or TCP/IP interfaces +++to make this work with particular debugging targets. In addition, +++@value{GDBN} comes with a generic serial protocol (specific to @value{GDBN}, +++but not specific to any particular target system) which you can use if you +++write the remote stubs---the code that runs on the remote system to +++communicate with @value{GDBN}. +++ +++Other remote targets may be available in your +++configuration of @value{GDBN}; use @code{help target} to list them. +++ +++@menu +++* Connecting:: Connecting to a remote target +++* File Transfer:: Sending files to a remote system +++* Server:: Using the gdbserver program +++* Remote Configuration:: Remote configuration +++* Remote Stub:: Implementing a remote stub +++@end menu +++ +++@node Connecting +++@section Connecting to a Remote Target +++@cindex remote debugging, connecting +++@cindex @code{gdbserver}, connecting +++@cindex remote debugging, types of connections +++@cindex @code{gdbserver}, types of connections +++@cindex @code{gdbserver}, @code{target remote} mode +++@cindex @code{gdbserver}, @code{target extended-remote} mode +++ +++This section describes how to connect to a remote target, including the +++types of connections and their differences, how to set up executable and +++symbol files on the host and target, and the commands used for +++connecting to and disconnecting from the remote target. +++ +++@subsection Types of Remote Connections +++ +++@value{GDBN} supports two types of remote connections, @code{target remote} +++mode and @code{target extended-remote} mode. Note that many remote targets +++support only @code{target remote} mode. There are several major +++differences between the two types of connections, enumerated here: +++ +++@table @asis +++ +++@cindex remote debugging, detach and program exit +++@item Result of detach or program exit +++@strong{With target remote mode:} When the debugged program exits or you +++detach from it, @value{GDBN} disconnects from the target. When using +++@code{gdbserver}, @code{gdbserver} will exit. +++ +++@strong{With target extended-remote mode:} When the debugged program exits or +++you detach from it, @value{GDBN} remains connected to the target, even +++though no program is running. You can rerun the program, attach to a +++running program, or use @code{monitor} commands specific to the target. +++ +++When using @code{gdbserver} in this case, it does not exit unless it was +++invoked using the @option{--once} option. If the @option{--once} option +++was not used, you can ask @code{gdbserver} to exit using the +++@code{monitor exit} command (@pxref{Monitor Commands for gdbserver}). +++ +++@item Specifying the program to debug +++For both connection types you use the @code{file} command to specify the +++program on the host system. If you are using @code{gdbserver} there are +++some differences in how to specify the location of the program on the +++target. +++ +++@strong{With target remote mode:} You must either specify the program to debug +++on the @code{gdbserver} command line or use the @option{--attach} option +++(@pxref{Attaching to a program,,Attaching to a Running Program}). +++ +++@cindex @option{--multi}, @code{gdbserver} option +++@strong{With target extended-remote mode:} You may specify the program to debug +++on the @code{gdbserver} command line, or you can load the program or attach +++to it using @value{GDBN} commands after connecting to @code{gdbserver}. +++ +++@anchor{--multi Option in Types of Remote Connnections} +++You can start @code{gdbserver} without supplying an initial command to run +++or process ID to attach. To do this, use the @option{--multi} command line +++option. Then you can connect using @code{target extended-remote} and start +++the program you want to debug (see below for details on using the +++@code{run} command in this scenario). Note that the conditions under which +++@code{gdbserver} terminates depend on how @value{GDBN} connects to it +++(@code{target remote} or @code{target extended-remote}). The +++@option{--multi} option to @code{gdbserver} has no influence on that. +++ +++@item The @code{run} command +++@strong{With target remote mode:} The @code{run} command is not +++supported. Once a connection has been established, you can use all +++the usual @value{GDBN} commands to examine and change data. The +++remote program is already running, so you can use commands like +++@kbd{step} and @kbd{continue}. +++ +++@strong{With target extended-remote mode:} The @code{run} command is +++supported. The @code{run} command uses the value set by +++@code{set remote exec-file} (@pxref{set remote exec-file}) to select +++the program to run. Command line arguments are supported, except for +++wildcard expansion and I/O redirection (@pxref{Arguments}). +++ +++If you specify the program to debug on the command line, then the +++@code{run} command is not required to start execution, and you can +++resume using commands like @kbd{step} and @kbd{continue} as with +++@code{target remote} mode. +++ +++@anchor{Attaching in Types of Remote Connections} +++@item Attaching +++@strong{With target remote mode:} The @value{GDBN} command @code{attach} is +++not supported. To attach to a running program using @code{gdbserver}, you +++must use the @option{--attach} option (@pxref{Running gdbserver}). +++ +++@strong{With target extended-remote mode:} To attach to a running program, +++you may use the @code{attach} command after the connection has been +++established. If you are using @code{gdbserver}, you may also invoke +++@code{gdbserver} using the @option{--attach} option +++(@pxref{Running gdbserver}). +++ +++Some remote targets allow @value{GDBN} to determine the executable file running +++in the process the debugger is attaching to. In such a case, @value{GDBN} +++uses the value of @code{exec-file-mismatch} to handle a possible mismatch +++between the executable file name running in the process and the name of the +++current exec-file loaded by @value{GDBN} (@pxref{set exec-file-mismatch}). +++ +++@end table +++ +++@anchor{Host and target files} +++@subsection Host and Target Files +++@cindex remote debugging, symbol files +++@cindex symbol files, remote debugging +++ +++@value{GDBN}, running on the host, needs access to symbol and debugging +++information for your program running on the target. This requires +++access to an unstripped copy of your program, and possibly any associated +++symbol files. Note that this section applies equally to both @code{target +++remote} mode and @code{target extended-remote} mode. +++ +++Some remote targets (@pxref{qXfer executable filename read}, and +++@pxref{Host I/O Packets}) allow @value{GDBN} to access program files over +++the same connection used to communicate with @value{GDBN}. With such a +++target, if the remote program is unstripped, the only command you need is +++@code{target remote} (or @code{target extended-remote}). +++ +++If the remote program is stripped, or the target does not support remote +++program file access, start up @value{GDBN} using the name of the local +++unstripped copy of your program as the first argument, or use the +++@code{file} command. Use @code{set sysroot} to specify the location (on +++the host) of target libraries (unless your @value{GDBN} was compiled with +++the correct sysroot using @code{--with-sysroot}). Alternatively, you +++may use @code{set solib-search-path} to specify how @value{GDBN} locates +++target libraries. +++ +++The symbol file and target libraries must exactly match the executable +++and libraries on the target, with one exception: the files on the host +++system should not be stripped, even if the files on the target system +++are. Mismatched or missing files will lead to confusing results +++during debugging. On @sc{gnu}/Linux targets, mismatched or missing +++files may also prevent @code{gdbserver} from debugging multi-threaded +++programs. +++ +++@subsection Remote Connection Commands +++@cindex remote connection commands +++@value{GDBN} can communicate with the target over a serial line, a +++local Unix domain socket, or +++over an @acronym{IP} network using @acronym{TCP} or @acronym{UDP}. In +++each case, @value{GDBN} uses the same protocol for debugging your +++program; only the medium carrying the debugging packets varies. The +++@code{target remote} and @code{target extended-remote} commands +++establish a connection to the target. Both commands accept the same +++arguments, which indicate the medium to use: +++ +++@table @code +++ +++@item target remote @var{serial-device} +++@itemx target extended-remote @var{serial-device} +++@cindex serial line, @code{target remote} +++Use @var{serial-device} to communicate with the target. For example, +++to use a serial line connected to the device named @file{/dev/ttyb}: +++ +++@smallexample +++target remote /dev/ttyb +++@end smallexample +++ +++If you're using a serial line, you may want to give @value{GDBN} the +++@samp{--baud} option, or use the @code{set serial baud} command +++(@pxref{Remote Configuration, set serial baud}) before the +++@code{target} command. +++ +++@item target remote @var{local-socket} +++@itemx target extended-remote @var{local-socket} +++@cindex local socket, @code{target remote} +++@cindex Unix domain socket +++Use @var{local-socket} to communicate with the target. For example, +++to use a local Unix domain socket bound to the file system entry @file{/tmp/gdb-socket0}: +++ +++@smallexample +++target remote /tmp/gdb-socket0 +++@end smallexample +++ +++Note that this command has the same form as the command to connect +++to a serial line. @value{GDBN} will automatically determine which +++kind of file you have specified and will make the appropriate kind +++of connection. +++This feature is not available if the host system does not support +++Unix domain sockets. +++ +++@item target remote @code{@var{host}:@var{port}} +++@itemx target remote @code{[@var{host}]:@var{port}} +++@itemx target remote @code{tcp:@var{host}:@var{port}} +++@itemx target remote @code{tcp:[@var{host}]:@var{port}} +++@itemx target remote @code{tcp4:@var{host}:@var{port}} +++@itemx target remote @code{tcp6:@var{host}:@var{port}} +++@itemx target remote @code{tcp6:[@var{host}]:@var{port}} +++@itemx target extended-remote @code{@var{host}:@var{port}} +++@itemx target extended-remote @code{[@var{host}]:@var{port}} +++@itemx target extended-remote @code{tcp:@var{host}:@var{port}} +++@itemx target extended-remote @code{tcp:[@var{host}]:@var{port}} +++@itemx target extended-remote @code{tcp4:@var{host}:@var{port}} +++@itemx target extended-remote @code{tcp6:@var{host}:@var{port}} +++@itemx target extended-remote @code{tcp6:[@var{host}]:@var{port}} +++@cindex @acronym{TCP} port, @code{target remote} +++Debug using a @acronym{TCP} connection to @var{port} on @var{host}. +++The @var{host} may be either a host name, a numeric @acronym{IPv4} +++address, or a numeric @acronym{IPv6} address (with or without the +++square brackets to separate the address from the port); @var{port} +++must be a decimal number. The @var{host} could be the target machine +++itself, if it is directly connected to the net, or it might be a +++terminal server which in turn has a serial line to the target. +++ +++For example, to connect to port 2828 on a terminal server named +++@code{manyfarms}: +++ +++@smallexample +++target remote manyfarms:2828 +++@end smallexample +++ +++To connect to port 2828 on a terminal server whose address is +++@code{2001:0db8:85a3:0000:0000:8a2e:0370:7334}, you can either use the +++square bracket syntax: +++ +++@smallexample +++target remote [2001:0db8:85a3:0000:0000:8a2e:0370:7334]:2828 +++@end smallexample +++ +++@noindent +++or explicitly specify the @acronym{IPv6} protocol: +++ +++@smallexample +++target remote tcp6:2001:0db8:85a3:0000:0000:8a2e:0370:7334:2828 +++@end smallexample +++ +++This last example may be confusing to the reader, because there is no +++visible separation between the hostname and the port number. +++Therefore, we recommend the user to provide @acronym{IPv6} addresses +++using square brackets for clarity. However, it is important to +++mention that for @value{GDBN} there is no ambiguity: the number after +++the last colon is considered to be the port number. +++ +++If your remote target is actually running on the same machine as your +++debugger session (e.g.@: a simulator for your target running on the +++same host), you can omit the hostname. For example, to connect to +++port 1234 on your local machine: +++ +++@smallexample +++target remote :1234 +++@end smallexample +++@noindent +++ +++Note that the colon is still required here. +++ +++@item target remote @code{udp:@var{host}:@var{port}} +++@itemx target remote @code{udp:[@var{host}]:@var{port}} +++@itemx target remote @code{udp4:@var{host}:@var{port}} +++@itemx target remote @code{udp6:[@var{host}]:@var{port}} +++@itemx target extended-remote @code{udp:@var{host}:@var{port}} +++@itemx target extended-remote @code{udp:@var{host}:@var{port}} +++@itemx target extended-remote @code{udp:[@var{host}]:@var{port}} +++@itemx target extended-remote @code{udp4:@var{host}:@var{port}} +++@itemx target extended-remote @code{udp6:@var{host}:@var{port}} +++@itemx target extended-remote @code{udp6:[@var{host}]:@var{port}} +++@cindex @acronym{UDP} port, @code{target remote} +++Debug using @acronym{UDP} packets to @var{port} on @var{host}. For example, to +++connect to @acronym{UDP} port 2828 on a terminal server named @code{manyfarms}: +++ +++@smallexample +++target remote udp:manyfarms:2828 +++@end smallexample +++ +++When using a @acronym{UDP} connection for remote debugging, you should +++keep in mind that the `U' stands for ``Unreliable''. @acronym{UDP} +++can silently drop packets on busy or unreliable networks, which will +++cause havoc with your debugging session. +++ +++@item target remote | @var{command} +++@itemx target extended-remote | @var{command} +++@cindex pipe, @code{target remote} to +++Run @var{command} in the background and communicate with it using a +++pipe. The @var{command} is a shell command, to be parsed and expanded +++by the system's command shell, @code{/bin/sh}; it should expect remote +++protocol packets on its standard input, and send replies on its +++standard output. You could use this to run a stand-alone simulator +++that speaks the remote debugging protocol, to make net connections +++using programs like @code{ssh}, or for other similar tricks. +++ +++If @var{command} closes its standard output (perhaps by exiting), +++@value{GDBN} will try to send it a @code{SIGTERM} signal. (If the +++program has already exited, this will have no effect.) +++ +++@end table +++ +++@cindex interrupting remote programs +++@cindex remote programs, interrupting +++Whenever @value{GDBN} is waiting for the remote program, if you type the +++interrupt character (often @kbd{Ctrl-c}), @value{GDBN} attempts to stop the +++program. This may or may not succeed, depending in part on the hardware +++and the serial drivers the remote system uses. If you type the +++interrupt character once again, @value{GDBN} displays this prompt: +++ +++@smallexample +++Interrupted while waiting for the program. +++Give up (and stop debugging it)? (y or n) +++@end smallexample +++ +++In @code{target remote} mode, if you type @kbd{y}, @value{GDBN} abandons +++the remote debugging session. (If you decide you want to try again later, +++you can use @kbd{target remote} again to connect once more.) If you type +++@kbd{n}, @value{GDBN} goes back to waiting. +++ +++In @code{target extended-remote} mode, typing @kbd{n} will leave +++@value{GDBN} connected to the target. +++ +++@table @code +++@kindex detach (remote) +++@item detach +++When you have finished debugging the remote program, you can use the +++@code{detach} command to release it from @value{GDBN} control. +++Detaching from the target normally resumes its execution, but the results +++will depend on your particular remote stub. After the @code{detach} +++command in @code{target remote} mode, @value{GDBN} is free to connect to +++another target. In @code{target extended-remote} mode, @value{GDBN} is +++still connected to the target. +++ +++@kindex disconnect +++@item disconnect +++The @code{disconnect} command closes the connection to the target, and +++the target is generally not resumed. It will wait for @value{GDBN} +++(this instance or another one) to connect and continue debugging. After +++the @code{disconnect} command, @value{GDBN} is again free to connect to +++another target. +++ +++@cindex send command to remote monitor +++@cindex extend @value{GDBN} for remote targets +++@cindex add new commands for external monitor +++@kindex monitor +++@item monitor @var{cmd} +++This command allows you to send arbitrary commands directly to the +++remote monitor. Since @value{GDBN} doesn't care about the commands it +++sends like this, this command is the way to extend @value{GDBN}---you +++can add new commands that only the external monitor will understand +++and implement. +++@end table +++ +++@node File Transfer +++@section Sending files to a remote system +++@cindex remote target, file transfer +++@cindex file transfer +++@cindex sending files to remote systems +++ +++Some remote targets offer the ability to transfer files over the same +++connection used to communicate with @value{GDBN}. This is convenient +++for targets accessible through other means, e.g.@: @sc{gnu}/Linux systems +++running @code{gdbserver} over a network interface. For other targets, +++e.g.@: embedded devices with only a single serial port, this may be +++the only way to upload or download files. +++ +++Not all remote targets support these commands. +++ +++@table @code +++@kindex remote put +++@item remote put @var{hostfile} @var{targetfile} +++Copy file @var{hostfile} from the host system (the machine running +++@value{GDBN}) to @var{targetfile} on the target system. +++ +++@kindex remote get +++@item remote get @var{targetfile} @var{hostfile} +++Copy file @var{targetfile} from the target system to @var{hostfile} +++on the host system. +++ +++@kindex remote delete +++@item remote delete @var{targetfile} +++Delete @var{targetfile} from the target system. +++ +++@end table +++ +++@node Server +++@section Using the @code{gdbserver} Program +++ +++@kindex gdbserver +++@cindex remote connection without stubs +++@code{gdbserver} is a control program for Unix-like systems, which +++allows you to connect your program with a remote @value{GDBN} via +++@code{target remote} or @code{target extended-remote}---but without +++linking in the usual debugging stub. +++ +++@code{gdbserver} is not a complete replacement for the debugging stubs, +++because it requires essentially the same operating-system facilities +++that @value{GDBN} itself does. In fact, a system that can run +++@code{gdbserver} to connect to a remote @value{GDBN} could also run +++@value{GDBN} locally! @code{gdbserver} is sometimes useful nevertheless, +++because it is a much smaller program than @value{GDBN} itself. It is +++also easier to port than all of @value{GDBN}, so you may be able to get +++started more quickly on a new system by using @code{gdbserver}. +++Finally, if you develop code for real-time systems, you may find that +++the tradeoffs involved in real-time operation make it more convenient to +++do as much development work as possible on another system, for example +++by cross-compiling. You can use @code{gdbserver} to make a similar +++choice for debugging. +++ +++@value{GDBN} and @code{gdbserver} communicate via either a serial line +++or a TCP connection, using the standard @value{GDBN} remote serial +++protocol. +++ +++@quotation +++@emph{Warning:} @code{gdbserver} does not have any built-in security. +++Do not run @code{gdbserver} connected to any public network; a +++@value{GDBN} connection to @code{gdbserver} provides access to the +++target system with the same privileges as the user running +++@code{gdbserver}. +++@end quotation +++ +++@anchor{Running gdbserver} +++@subsection Running @code{gdbserver} +++@cindex arguments, to @code{gdbserver} +++@cindex @code{gdbserver}, command-line arguments +++ +++Run @code{gdbserver} on the target system. You need a copy of the +++program you want to debug, including any libraries it requires. +++@code{gdbserver} does not need your program's symbol table, so you can +++strip the program if necessary to save space. @value{GDBN} on the host +++system does all the symbol handling. +++ +++To use the server, you must tell it how to communicate with @value{GDBN}; +++the name of your program; and the arguments for your program. The usual +++syntax is: +++ +++@smallexample +++target> gdbserver @var{comm} @var{program} [ @var{args} @dots{} ] +++@end smallexample +++ +++@var{comm} is either a device name (to use a serial line), or a TCP +++hostname and portnumber, or @code{-} or @code{stdio} to use +++stdin/stdout of @code{gdbserver}. +++For example, to debug Emacs with the argument +++@samp{foo.txt} and communicate with @value{GDBN} over the serial port +++@file{/dev/com1}: +++ +++@smallexample +++target> gdbserver /dev/com1 emacs foo.txt +++@end smallexample +++ +++@code{gdbserver} waits passively for the host @value{GDBN} to communicate +++with it. +++ +++To use a TCP connection instead of a serial line: +++ +++@smallexample +++target> gdbserver host:2345 emacs foo.txt +++@end smallexample +++ +++The only difference from the previous example is the first argument, +++specifying that you are communicating with the host @value{GDBN} via +++TCP. The @samp{host:2345} argument means that @code{gdbserver} is to +++expect a TCP connection from machine @samp{host} to local TCP port 2345. +++(Currently, the @samp{host} part is ignored.) You can choose any number +++you want for the port number as long as it does not conflict with any +++TCP ports already in use on the target system (for example, @code{23} is +++reserved for @code{telnet}).@footnote{If you choose a port number that +++conflicts with another service, @code{gdbserver} prints an error message +++and exits.} You must use the same port number with the host @value{GDBN} +++@code{target remote} command. +++ +++The @code{stdio} connection is useful when starting @code{gdbserver} +++with ssh: +++ +++@smallexample +++(gdb) target remote | ssh -T hostname gdbserver - hello +++@end smallexample +++ +++The @samp{-T} option to ssh is provided because we don't need a remote pty, +++and we don't want escape-character handling. Ssh does this by default when +++a command is provided, the flag is provided to make it explicit. +++You could elide it if you want to. +++ +++Programs started with stdio-connected gdbserver have @file{/dev/null} for +++@code{stdin}, and @code{stdout},@code{stderr} are sent back to gdb for +++display through a pipe connected to gdbserver. +++Both @code{stdout} and @code{stderr} use the same pipe. +++ +++@anchor{Attaching to a program} +++@subsubsection Attaching to a Running Program +++@cindex attach to a program, @code{gdbserver} +++@cindex @option{--attach}, @code{gdbserver} option +++ +++On some targets, @code{gdbserver} can also attach to running programs. +++This is accomplished via the @code{--attach} argument. The syntax is: +++ +++@smallexample +++target> gdbserver --attach @var{comm} @var{pid} +++@end smallexample +++ +++@var{pid} is the process ID of a currently running process. It isn't +++necessary to point @code{gdbserver} at a binary for the running process. +++ +++In @code{target extended-remote} mode, you can also attach using the +++@value{GDBN} attach command +++(@pxref{Attaching in Types of Remote Connections}). +++ +++@pindex pidof +++You can debug processes by name instead of process ID if your target has the +++@code{pidof} utility: +++ +++@smallexample +++target> gdbserver --attach @var{comm} `pidof @var{program}` +++@end smallexample +++ +++In case more than one copy of @var{program} is running, or @var{program} +++has multiple threads, most versions of @code{pidof} support the +++@code{-s} option to only return the first process ID. +++ +++@subsubsection TCP port allocation lifecycle of @code{gdbserver} +++ +++This section applies only when @code{gdbserver} is run to listen on a TCP +++port. +++ +++@code{gdbserver} normally terminates after all of its debugged processes have +++terminated in @kbd{target remote} mode. On the other hand, for @kbd{target +++extended-remote}, @code{gdbserver} stays running even with no processes left. +++@value{GDBN} normally terminates the spawned debugged process on its exit, +++which normally also terminates @code{gdbserver} in the @kbd{target remote} +++mode. Therefore, when the connection drops unexpectedly, and @value{GDBN} +++cannot ask @code{gdbserver} to kill its debugged processes, @code{gdbserver} +++stays running even in the @kbd{target remote} mode. +++ +++When @code{gdbserver} stays running, @value{GDBN} can connect to it again later. +++Such reconnecting is useful for features like @ref{disconnected tracing}. For +++completeness, at most one @value{GDBN} can be connected at a time. +++ +++@cindex @option{--once}, @code{gdbserver} option +++By default, @code{gdbserver} keeps the listening TCP port open, so that +++subsequent connections are possible. However, if you start @code{gdbserver} +++with the @option{--once} option, it will stop listening for any further +++connection attempts after connecting to the first @value{GDBN} session. This +++means no further connections to @code{gdbserver} will be possible after the +++first one. It also means @code{gdbserver} will terminate after the first +++connection with remote @value{GDBN} has closed, even for unexpectedly closed +++connections and even in the @kbd{target extended-remote} mode. The +++@option{--once} option allows reusing the same port number for connecting to +++multiple instances of @code{gdbserver} running on the same host, since each +++instance closes its port after the first connection. +++ +++@anchor{Other Command-Line Arguments for gdbserver} +++@subsubsection Other Command-Line Arguments for @code{gdbserver} +++ +++You can use the @option{--multi} option to start @code{gdbserver} without +++specifying a program to debug or a process to attach to. Then you can +++attach in @code{target extended-remote} mode and run or attach to a +++program. For more information, +++@pxref{--multi Option in Types of Remote Connnections}. +++ +++@cindex @option{--debug}, @code{gdbserver} option +++The @option{--debug} option tells @code{gdbserver} to display extra +++status information about the debugging process. +++@cindex @option{--remote-debug}, @code{gdbserver} option +++The @option{--remote-debug} option tells @code{gdbserver} to display +++remote protocol debug output. +++@cindex @option{--debug-file}, @code{gdbserver} option +++@cindex @code{gdbserver}, send all debug output to a single file +++The @option{--debug-file=@var{filename}} option tells @code{gdbserver} to +++write any debug output to the given @var{filename}. These options are intended +++for @code{gdbserver} development and for bug reports to the developers. +++ +++@cindex @option{--debug-format}, @code{gdbserver} option +++The @option{--debug-format=option1[,option2,...]} option tells +++@code{gdbserver} to include additional information in each output. +++Possible options are: +++ +++@table @code +++@item none +++Turn off all extra information in debugging output. +++@item all +++Turn on all extra information in debugging output. +++@item timestamps +++Include a timestamp in each line of debugging output. +++@end table +++ +++Options are processed in order. Thus, for example, if @option{none} +++appears last then no additional information is added to debugging output. +++ +++@cindex @option{--wrapper}, @code{gdbserver} option +++The @option{--wrapper} option specifies a wrapper to launch programs +++for debugging. The option should be followed by the name of the +++wrapper, then any command-line arguments to pass to the wrapper, then +++@kbd{--} indicating the end of the wrapper arguments. +++ +++@code{gdbserver} runs the specified wrapper program with a combined +++command line including the wrapper arguments, then the name of the +++program to debug, then any arguments to the program. The wrapper +++runs until it executes your program, and then @value{GDBN} gains control. +++ +++You can use any program that eventually calls @code{execve} with +++its arguments as a wrapper. Several standard Unix utilities do +++this, e.g.@: @code{env} and @code{nohup}. Any Unix shell script ending +++with @code{exec "$@@"} will also work. +++ +++For example, you can use @code{env} to pass an environment variable to +++the debugged program, without setting the variable in @code{gdbserver}'s +++environment: +++ +++@smallexample +++$ gdbserver --wrapper env LD_PRELOAD=libtest.so -- :2222 ./testprog +++@end smallexample +++ +++@cindex @option{--selftest} +++The @option{--selftest} option runs the self tests in @code{gdbserver}: +++ +++@smallexample +++$ gdbserver --selftest +++Ran 2 unit tests, 0 failed +++@end smallexample +++ +++These tests are disabled in release. +++@subsection Connecting to @code{gdbserver} +++ +++The basic procedure for connecting to the remote target is: +++@itemize +++ +++@item +++Run @value{GDBN} on the host system. +++ +++@item +++Make sure you have the necessary symbol files +++(@pxref{Host and target files}). +++Load symbols for your application using the @code{file} command before you +++connect. Use @code{set sysroot} to locate target libraries (unless your +++@value{GDBN} was compiled with the correct sysroot using +++@code{--with-sysroot}). +++ +++@item +++Connect to your target (@pxref{Connecting,,Connecting to a Remote Target}). +++For TCP connections, you must start up @code{gdbserver} prior to using +++the @code{target} command. Otherwise you may get an error whose +++text depends on the host system, but which usually looks something like +++@samp{Connection refused}. Don't use the @code{load} +++command in @value{GDBN} when using @code{target remote} mode, since the +++program is already on the target. +++ +++@end itemize +++ +++@anchor{Monitor Commands for gdbserver} +++@subsection Monitor Commands for @code{gdbserver} +++@cindex monitor commands, for @code{gdbserver} +++ +++During a @value{GDBN} session using @code{gdbserver}, you can use the +++@code{monitor} command to send special requests to @code{gdbserver}. +++Here are the available commands. +++ +++@table @code +++@item monitor help +++List the available monitor commands. +++ +++@item monitor set debug 0 +++@itemx monitor set debug 1 +++Disable or enable general debugging messages. +++ +++@item monitor set remote-debug 0 +++@itemx monitor set remote-debug 1 +++Disable or enable specific debugging messages associated with the remote +++protocol (@pxref{Remote Protocol}). +++ +++@item monitor set debug-file filename +++@itemx monitor set debug-file +++Send any debug output to the given file, or to stderr. +++ +++@item monitor set debug-format option1@r{[},option2,...@r{]} +++Specify additional text to add to debugging messages. +++Possible options are: +++ +++@table @code +++@item none +++Turn off all extra information in debugging output. +++@item all +++Turn on all extra information in debugging output. +++@item timestamps +++Include a timestamp in each line of debugging output. +++@end table +++ +++Options are processed in order. Thus, for example, if @option{none} +++appears last then no additional information is added to debugging output. +++ +++@item monitor set libthread-db-search-path [PATH] +++@cindex gdbserver, search path for @code{libthread_db} +++When this command is issued, @var{path} is a colon-separated list of +++directories to search for @code{libthread_db} (@pxref{Threads,,set +++libthread-db-search-path}). If you omit @var{path}, +++@samp{libthread-db-search-path} will be reset to its default value. +++ +++The special entry @samp{$pdir} for @samp{libthread-db-search-path} is +++not supported in @code{gdbserver}. +++ +++@item monitor exit +++Tell gdbserver to exit immediately. This command should be followed by +++@code{disconnect} to close the debugging session. @code{gdbserver} will +++detach from any attached processes and kill any processes it created. +++Use @code{monitor exit} to terminate @code{gdbserver} at the end +++of a multi-process mode debug session. +++ +++@end table +++ +++@subsection Tracepoints support in @code{gdbserver} +++@cindex tracepoints support in @code{gdbserver} +++ +++On some targets, @code{gdbserver} supports tracepoints, fast +++tracepoints and static tracepoints. +++ +++For fast or static tracepoints to work, a special library called the +++@dfn{in-process agent} (IPA), must be loaded in the inferior process. +++This library is built and distributed as an integral part of +++@code{gdbserver}. In addition, support for static tracepoints +++requires building the in-process agent library with static tracepoints +++support. At present, the UST (LTTng Userspace Tracer, +++@url{http://lttng.org/ust}) tracing engine is supported. This support +++is automatically available if UST development headers are found in the +++standard include path when @code{gdbserver} is built, or if +++@code{gdbserver} was explicitly configured using @option{--with-ust} +++to point at such headers. You can explicitly disable the support +++using @option{--with-ust=no}. +++ +++There are several ways to load the in-process agent in your program: +++ +++@table @code +++@item Specifying it as dependency at link time +++ +++You can link your program dynamically with the in-process agent +++library. On most systems, this is accomplished by adding +++@code{-linproctrace} to the link command. +++ +++@item Using the system's preloading mechanisms +++ +++You can force loading the in-process agent at startup time by using +++your system's support for preloading shared libraries. Many Unixes +++support the concept of preloading user defined libraries. In most +++cases, you do that by specifying @code{LD_PRELOAD=libinproctrace.so} +++in the environment. See also the description of @code{gdbserver}'s +++@option{--wrapper} command line option. +++ +++@item Using @value{GDBN} to force loading the agent at run time +++ +++On some systems, you can force the inferior to load a shared library, +++by calling a dynamic loader function in the inferior that takes care +++of dynamically looking up and loading a shared library. On most Unix +++systems, the function is @code{dlopen}. You'll use the @code{call} +++command for that. For example: +++ +++@smallexample +++(@value{GDBP}) call dlopen ("libinproctrace.so", ...) +++@end smallexample +++ +++Note that on most Unix systems, for the @code{dlopen} function to be +++available, the program needs to be linked with @code{-ldl}. +++@end table +++ +++On systems that have a userspace dynamic loader, like most Unix +++systems, when you connect to @code{gdbserver} using @code{target +++remote}, you'll find that the program is stopped at the dynamic +++loader's entry point, and no shared library has been loaded in the +++program's address space yet, including the in-process agent. In that +++case, before being able to use any of the fast or static tracepoints +++features, you need to let the loader run and load the shared +++libraries. The simplest way to do that is to run the program to the +++main procedure. E.g., if debugging a C or C@t{++} program, start +++@code{gdbserver} like so: +++ +++@smallexample +++$ gdbserver :9999 myprogram +++@end smallexample +++ +++Start GDB and connect to @code{gdbserver} like so, and run to main: +++ +++@smallexample +++$ gdb myprogram +++(@value{GDBP}) target remote myhost:9999 +++0x00007f215893ba60 in ?? () from /lib64/ld-linux-x86-64.so.2 +++(@value{GDBP}) b main +++(@value{GDBP}) continue +++@end smallexample +++ +++The in-process tracing agent library should now be loaded into the +++process; you can confirm it with the @code{info sharedlibrary} +++command, which will list @file{libinproctrace.so} as loaded in the +++process. You are now ready to install fast tracepoints, list static +++tracepoint markers, probe static tracepoints markers, and start +++tracing. +++ +++@node Remote Configuration +++@section Remote Configuration +++ +++@kindex set remote +++@kindex show remote +++This section documents the configuration options available when +++debugging remote programs. For the options related to the File I/O +++extensions of the remote protocol, see @ref{system, +++system-call-allowed}. +++ +++@table @code +++@item set remoteaddresssize @var{bits} +++@cindex address size for remote targets +++@cindex bits in remote address +++Set the maximum size of address in a memory packet to the specified +++number of bits. @value{GDBN} will mask off the address bits above +++that number, when it passes addresses to the remote target. The +++default value is the number of bits in the target's address. +++ +++@item show remoteaddresssize +++Show the current value of remote address size in bits. +++ +++@item set serial baud @var{n} +++@cindex baud rate for remote targets +++Set the baud rate for the remote serial I/O to @var{n} baud. The +++value is used to set the speed of the serial port used for debugging +++remote targets. +++ +++@item show serial baud +++Show the current speed of the remote connection. +++ +++@item set serial parity @var{parity} +++Set the parity for the remote serial I/O. Supported values of @var{parity} are: +++@code{even}, @code{none}, and @code{odd}. The default is @code{none}. +++ +++@item show serial parity +++Show the current parity of the serial port. +++ +++@item set remotebreak +++@cindex interrupt remote programs +++@cindex BREAK signal instead of Ctrl-C +++@anchor{set remotebreak} +++If set to on, @value{GDBN} sends a @code{BREAK} signal to the remote +++when you type @kbd{Ctrl-c} to interrupt the program running +++on the remote. If set to off, @value{GDBN} sends the @samp{Ctrl-C} +++character instead. The default is off, since most remote systems +++expect to see @samp{Ctrl-C} as the interrupt signal. +++ +++@item show remotebreak +++Show whether @value{GDBN} sends @code{BREAK} or @samp{Ctrl-C} to +++interrupt the remote program. +++ +++@item set remoteflow on +++@itemx set remoteflow off +++@kindex set remoteflow +++Enable or disable hardware flow control (@code{RTS}/@code{CTS}) +++on the serial port used to communicate to the remote target. +++ +++@item show remoteflow +++@kindex show remoteflow +++Show the current setting of hardware flow control. +++ +++@item set remotelogbase @var{base} +++Set the base (a.k.a.@: radix) of logging serial protocol +++communications to @var{base}. Supported values of @var{base} are: +++@code{ascii}, @code{octal}, and @code{hex}. The default is +++@code{ascii}. +++ +++@item show remotelogbase +++Show the current setting of the radix for logging remote serial +++protocol. +++ +++@item set remotelogfile @var{file} +++@cindex record serial communications on file +++Record remote serial communications on the named @var{file}. The +++default is not to record at all. +++ +++@item show remotelogfile +++Show the current setting of the file name on which to record the +++serial communications. +++ +++@item set remotetimeout @var{num} +++@cindex timeout for serial communications +++@cindex remote timeout +++Set the timeout limit to wait for the remote target to respond to +++@var{num} seconds. The default is 2 seconds. +++ +++@item show remotetimeout +++Show the current number of seconds to wait for the remote target +++responses. +++ +++@cindex limit hardware breakpoints and watchpoints +++@cindex remote target, limit break- and watchpoints +++@anchor{set remote hardware-watchpoint-limit} +++@anchor{set remote hardware-breakpoint-limit} +++@item set remote hardware-watchpoint-limit @var{limit} +++@itemx set remote hardware-breakpoint-limit @var{limit} +++Restrict @value{GDBN} to using @var{limit} remote hardware watchpoints +++or breakpoints. The @var{limit} can be set to 0 to disable hardware +++watchpoints or breakpoints, and @code{unlimited} for unlimited +++watchpoints or breakpoints. +++ +++@item show remote hardware-watchpoint-limit +++@itemx show remote hardware-breakpoint-limit +++Show the current limit for the number of hardware watchpoints or +++breakpoints that @value{GDBN} can use. +++ +++@cindex limit hardware watchpoints length +++@cindex remote target, limit watchpoints length +++@anchor{set remote hardware-watchpoint-length-limit} +++@item set remote hardware-watchpoint-length-limit @var{limit} +++Restrict @value{GDBN} to using @var{limit} bytes for the maximum +++length of a remote hardware watchpoint. A @var{limit} of 0 disables +++hardware watchpoints and @code{unlimited} allows watchpoints of any +++length. +++ +++@item show remote hardware-watchpoint-length-limit +++Show the current limit (in bytes) of the maximum length of +++a remote hardware watchpoint. +++ +++@item set remote exec-file @var{filename} +++@itemx show remote exec-file +++@anchor{set remote exec-file} +++@cindex executable file, for remote target +++Select the file used for @code{run} with @code{target +++extended-remote}. This should be set to a filename valid on the +++target system. If it is not set, the target will use a default +++filename (e.g.@: the last program run). +++ +++@item set remote interrupt-sequence +++@cindex interrupt remote programs +++@cindex select Ctrl-C, BREAK or BREAK-g +++Allow the user to select one of @samp{Ctrl-C}, a @code{BREAK} or +++@samp{BREAK-g} as the +++sequence to the remote target in order to interrupt the execution. +++@samp{Ctrl-C} is a default. Some system prefers @code{BREAK} which +++is high level of serial line for some certain time. +++Linux kernel prefers @samp{BREAK-g}, a.k.a Magic SysRq g. +++It is @code{BREAK} signal followed by character @code{g}. +++ +++@item show interrupt-sequence +++Show which of @samp{Ctrl-C}, @code{BREAK} or @code{BREAK-g} +++is sent by @value{GDBN} to interrupt the remote program. +++@code{BREAK-g} is BREAK signal followed by @code{g} and +++also known as Magic SysRq g. +++ +++@item set remote interrupt-on-connect +++@cindex send interrupt-sequence on start +++Specify whether interrupt-sequence is sent to remote target when +++@value{GDBN} connects to it. This is mostly needed when you debug +++Linux kernel. Linux kernel expects @code{BREAK} followed by @code{g} +++which is known as Magic SysRq g in order to connect @value{GDBN}. +++ +++@item show interrupt-on-connect +++Show whether interrupt-sequence is sent +++to remote target when @value{GDBN} connects to it. +++ +++@kindex set tcp +++@kindex show tcp +++@item set tcp auto-retry on +++@cindex auto-retry, for remote TCP target +++Enable auto-retry for remote TCP connections. This is useful if the remote +++debugging agent is launched in parallel with @value{GDBN}; there is a race +++condition because the agent may not become ready to accept the connection +++before @value{GDBN} attempts to connect. When auto-retry is +++enabled, if the initial attempt to connect fails, @value{GDBN} reattempts +++to establish the connection using the timeout specified by +++@code{set tcp connect-timeout}. +++ +++@item set tcp auto-retry off +++Do not auto-retry failed TCP connections. +++ +++@item show tcp auto-retry +++Show the current auto-retry setting. +++ +++@item set tcp connect-timeout @var{seconds} +++@itemx set tcp connect-timeout unlimited +++@cindex connection timeout, for remote TCP target +++@cindex timeout, for remote target connection +++Set the timeout for establishing a TCP connection to the remote target to +++@var{seconds}. The timeout affects both polling to retry failed connections +++(enabled by @code{set tcp auto-retry on}) and waiting for connections +++that are merely slow to complete, and represents an approximate cumulative +++value. If @var{seconds} is @code{unlimited}, there is no timeout and +++@value{GDBN} will keep attempting to establish a connection forever, +++unless interrupted with @kbd{Ctrl-c}. The default is 15 seconds. +++ +++@item show tcp connect-timeout +++Show the current connection timeout setting. +++@end table +++ +++@cindex remote packets, enabling and disabling +++The @value{GDBN} remote protocol autodetects the packets supported by +++your debugging stub. If you need to override the autodetection, you +++can use these commands to enable or disable individual packets. Each +++packet can be set to @samp{on} (the remote target supports this +++packet), @samp{off} (the remote target does not support this packet), +++or @samp{auto} (detect remote target support for this packet). They +++all default to @samp{auto}. For more information about each packet, +++see @ref{Remote Protocol}. +++ +++During normal use, you should not have to use any of these commands. +++If you do, that may be a bug in your remote debugging stub, or a bug +++in @value{GDBN}. You may want to report the problem to the +++@value{GDBN} developers. +++ +++For each packet @var{name}, the command to enable or disable the +++packet is @code{set remote @var{name}-packet}. The available settings +++are: +++ +++@multitable @columnfractions 0.28 0.32 0.25 +++@item Command Name +++@tab Remote Packet +++@tab Related Features +++ +++@item @code{fetch-register} +++@tab @code{p} +++@tab @code{info registers} +++ +++@item @code{set-register} +++@tab @code{P} +++@tab @code{set} +++ +++@item @code{binary-download} +++@tab @code{X} +++@tab @code{load}, @code{set} +++ +++@item @code{read-aux-vector} +++@tab @code{qXfer:auxv:read} +++@tab @code{info auxv} +++ +++@item @code{symbol-lookup} +++@tab @code{qSymbol} +++@tab Detecting multiple threads +++ +++@item @code{attach} +++@tab @code{vAttach} +++@tab @code{attach} +++ +++@item @code{verbose-resume} +++@tab @code{vCont} +++@tab Stepping or resuming multiple threads +++ +++@item @code{run} +++@tab @code{vRun} +++@tab @code{run} +++ +++@item @code{software-breakpoint} +++@tab @code{Z0} +++@tab @code{break} +++ +++@item @code{hardware-breakpoint} +++@tab @code{Z1} +++@tab @code{hbreak} +++ +++@item @code{write-watchpoint} +++@tab @code{Z2} +++@tab @code{watch} +++ +++@item @code{read-watchpoint} +++@tab @code{Z3} +++@tab @code{rwatch} +++ +++@item @code{access-watchpoint} +++@tab @code{Z4} +++@tab @code{awatch} +++ +++@item @code{pid-to-exec-file} +++@tab @code{qXfer:exec-file:read} +++@tab @code{attach}, @code{run} +++ +++@item @code{target-features} +++@tab @code{qXfer:features:read} +++@tab @code{set architecture} +++ +++@item @code{library-info} +++@tab @code{qXfer:libraries:read} +++@tab @code{info sharedlibrary} +++ +++@item @code{memory-map} +++@tab @code{qXfer:memory-map:read} +++@tab @code{info mem} +++ +++@item @code{read-sdata-object} +++@tab @code{qXfer:sdata:read} +++@tab @code{print $_sdata} +++ +++@item @code{read-siginfo-object} +++@tab @code{qXfer:siginfo:read} +++@tab @code{print $_siginfo} +++ +++@item @code{write-siginfo-object} +++@tab @code{qXfer:siginfo:write} +++@tab @code{set $_siginfo} +++ +++@item @code{threads} +++@tab @code{qXfer:threads:read} +++@tab @code{info threads} +++ +++@item @code{get-thread-local-@*storage-address} +++@tab @code{qGetTLSAddr} +++@tab Displaying @code{__thread} variables +++ +++@item @code{get-thread-information-block-address} +++@tab @code{qGetTIBAddr} +++@tab Display MS-Windows Thread Information Block. +++ +++@item @code{search-memory} +++@tab @code{qSearch:memory} +++@tab @code{find} +++ +++@item @code{supported-packets} +++@tab @code{qSupported} +++@tab Remote communications parameters +++ +++@item @code{catch-syscalls} +++@tab @code{QCatchSyscalls} +++@tab @code{catch syscall} +++ +++@item @code{pass-signals} +++@tab @code{QPassSignals} +++@tab @code{handle @var{signal}} +++ +++@item @code{program-signals} +++@tab @code{QProgramSignals} +++@tab @code{handle @var{signal}} +++ +++@item @code{hostio-close-packet} +++@tab @code{vFile:close} +++@tab @code{remote get}, @code{remote put} +++ +++@item @code{hostio-open-packet} +++@tab @code{vFile:open} +++@tab @code{remote get}, @code{remote put} +++ +++@item @code{hostio-pread-packet} +++@tab @code{vFile:pread} +++@tab @code{remote get}, @code{remote put} +++ +++@item @code{hostio-pwrite-packet} +++@tab @code{vFile:pwrite} +++@tab @code{remote get}, @code{remote put} +++ +++@item @code{hostio-unlink-packet} +++@tab @code{vFile:unlink} +++@tab @code{remote delete} +++ +++@item @code{hostio-readlink-packet} +++@tab @code{vFile:readlink} +++@tab Host I/O +++ +++@item @code{hostio-fstat-packet} +++@tab @code{vFile:fstat} +++@tab Host I/O +++ +++@item @code{hostio-setfs-packet} +++@tab @code{vFile:setfs} +++@tab Host I/O +++ +++@item @code{noack-packet} +++@tab @code{QStartNoAckMode} +++@tab Packet acknowledgment +++ +++@item @code{osdata} +++@tab @code{qXfer:osdata:read} +++@tab @code{info os} +++ +++@item @code{query-attached} +++@tab @code{qAttached} +++@tab Querying remote process attach state. +++ +++@item @code{trace-buffer-size} +++@tab @code{QTBuffer:size} +++@tab @code{set trace-buffer-size} +++ +++@item @code{trace-status} +++@tab @code{qTStatus} +++@tab @code{tstatus} +++ +++@item @code{traceframe-info} +++@tab @code{qXfer:traceframe-info:read} +++@tab Traceframe info +++ +++@item @code{install-in-trace} +++@tab @code{InstallInTrace} +++@tab Install tracepoint in tracing +++ +++@item @code{disable-randomization} +++@tab @code{QDisableRandomization} +++@tab @code{set disable-randomization} +++ +++@item @code{startup-with-shell} +++@tab @code{QStartupWithShell} +++@tab @code{set startup-with-shell} +++ +++@item @code{environment-hex-encoded} +++@tab @code{QEnvironmentHexEncoded} +++@tab @code{set environment} +++ +++@item @code{environment-unset} +++@tab @code{QEnvironmentUnset} +++@tab @code{unset environment} +++ +++@item @code{environment-reset} +++@tab @code{QEnvironmentReset} +++@tab @code{Reset the inferior environment (i.e., unset user-set variables)} +++ +++@item @code{set-working-dir} +++@tab @code{QSetWorkingDir} +++@tab @code{set cwd} +++ +++@item @code{conditional-breakpoints-packet} +++@tab @code{Z0 and Z1} +++@tab @code{Support for target-side breakpoint condition evaluation} +++ +++@item @code{multiprocess-extensions} +++@tab @code{multiprocess extensions} +++@tab Debug multiple processes and remote process PID awareness +++ +++@item @code{swbreak-feature} +++@tab @code{swbreak stop reason} +++@tab @code{break} +++ +++@item @code{hwbreak-feature} +++@tab @code{hwbreak stop reason} +++@tab @code{hbreak} +++ +++@item @code{fork-event-feature} +++@tab @code{fork stop reason} +++@tab @code{fork} +++ +++@item @code{vfork-event-feature} +++@tab @code{vfork stop reason} +++@tab @code{vfork} +++ +++@item @code{exec-event-feature} +++@tab @code{exec stop reason} +++@tab @code{exec} +++ +++@item @code{thread-events} +++@tab @code{QThreadEvents} +++@tab Tracking thread lifetime. +++ +++@item @code{no-resumed-stop-reply} +++@tab @code{no resumed thread left stop reply} +++@tab Tracking thread lifetime. +++ +++@end multitable +++ +++@node Remote Stub +++@section Implementing a Remote Stub +++ +++@cindex debugging stub, example +++@cindex remote stub, example +++@cindex stub example, remote debugging +++The stub files provided with @value{GDBN} implement the target side of the +++communication protocol, and the @value{GDBN} side is implemented in the +++@value{GDBN} source file @file{remote.c}. Normally, you can simply allow +++these subroutines to communicate, and ignore the details. (If you're +++implementing your own stub file, you can still ignore the details: start +++with one of the existing stub files. @file{sparc-stub.c} is the best +++organized, and therefore the easiest to read.) +++ +++@cindex remote serial debugging, overview +++To debug a program running on another machine (the debugging +++@dfn{target} machine), you must first arrange for all the usual +++prerequisites for the program to run by itself. For example, for a C +++program, you need: +++ +++@enumerate +++@item +++A startup routine to set up the C runtime environment; these usually +++have a name like @file{crt0}. The startup routine may be supplied by +++your hardware supplier, or you may have to write your own. +++ +++@item +++A C subroutine library to support your program's +++subroutine calls, notably managing input and output. +++ +++@item +++A way of getting your program to the other machine---for example, a +++download program. These are often supplied by the hardware +++manufacturer, but you may have to write your own from hardware +++documentation. +++@end enumerate +++ +++The next step is to arrange for your program to use a serial port to +++communicate with the machine where @value{GDBN} is running (the @dfn{host} +++machine). In general terms, the scheme looks like this: +++ +++@table @emph +++@item On the host, +++@value{GDBN} already understands how to use this protocol; when everything +++else is set up, you can simply use the @samp{target remote} command +++(@pxref{Targets,,Specifying a Debugging Target}). +++ +++@item On the target, +++you must link with your program a few special-purpose subroutines that +++implement the @value{GDBN} remote serial protocol. The file containing these +++subroutines is called a @dfn{debugging stub}. +++ +++On certain remote targets, you can use an auxiliary program +++@code{gdbserver} instead of linking a stub into your program. +++@xref{Server,,Using the @code{gdbserver} Program}, for details. +++@end table +++ +++The debugging stub is specific to the architecture of the remote +++machine; for example, use @file{sparc-stub.c} to debug programs on +++@sc{sparc} boards. +++ +++@cindex remote serial stub list +++These working remote stubs are distributed with @value{GDBN}: +++ +++@table @code +++ +++@item i386-stub.c +++@cindex @file{i386-stub.c} +++@cindex Intel +++@cindex i386 +++For Intel 386 and compatible architectures. +++ +++@item m68k-stub.c +++@cindex @file{m68k-stub.c} +++@cindex Motorola 680x0 +++@cindex m680x0 +++For Motorola 680x0 architectures. +++ +++@item sh-stub.c +++@cindex @file{sh-stub.c} +++@cindex Renesas +++@cindex SH +++For Renesas SH architectures. +++ +++@item sparc-stub.c +++@cindex @file{sparc-stub.c} +++@cindex Sparc +++For @sc{sparc} architectures. +++ +++@item sparcl-stub.c +++@cindex @file{sparcl-stub.c} +++@cindex Fujitsu +++@cindex SparcLite +++For Fujitsu @sc{sparclite} architectures. +++ +++@end table +++ +++The @file{README} file in the @value{GDBN} distribution may list other +++recently added stubs. +++ +++@menu +++* Stub Contents:: What the stub can do for you +++* Bootstrapping:: What you must do for the stub +++* Debug Session:: Putting it all together +++@end menu +++ +++@node Stub Contents +++@subsection What the Stub Can Do for You +++ +++@cindex remote serial stub +++The debugging stub for your architecture supplies these three +++subroutines: +++ +++@table @code +++@item set_debug_traps +++@findex set_debug_traps +++@cindex remote serial stub, initialization +++This routine arranges for @code{handle_exception} to run when your +++program stops. You must call this subroutine explicitly in your +++program's startup code. +++ +++@item handle_exception +++@findex handle_exception +++@cindex remote serial stub, main routine +++This is the central workhorse, but your program never calls it +++explicitly---the setup code arranges for @code{handle_exception} to +++run when a trap is triggered. +++ +++@code{handle_exception} takes control when your program stops during +++execution (for example, on a breakpoint), and mediates communications +++with @value{GDBN} on the host machine. This is where the communications +++protocol is implemented; @code{handle_exception} acts as the @value{GDBN} +++representative on the target machine. It begins by sending summary +++information on the state of your program, then continues to execute, +++retrieving and transmitting any information @value{GDBN} needs, until you +++execute a @value{GDBN} command that makes your program resume; at that point, +++@code{handle_exception} returns control to your own code on the target +++machine. +++ +++@item breakpoint +++@cindex @code{breakpoint} subroutine, remote +++Use this auxiliary subroutine to make your program contain a +++breakpoint. Depending on the particular situation, this may be the only +++way for @value{GDBN} to get control. For instance, if your target +++machine has some sort of interrupt button, you won't need to call this; +++pressing the interrupt button transfers control to +++@code{handle_exception}---in effect, to @value{GDBN}. On some machines, +++simply receiving characters on the serial port may also trigger a trap; +++again, in that situation, you don't need to call @code{breakpoint} from +++your own program---simply running @samp{target remote} from the host +++@value{GDBN} session gets control. +++ +++Call @code{breakpoint} if none of these is true, or if you simply want +++to make certain your program stops at a predetermined point for the +++start of your debugging session. +++@end table +++ +++@node Bootstrapping +++@subsection What You Must Do for the Stub +++ +++@cindex remote stub, support routines +++The debugging stubs that come with @value{GDBN} are set up for a particular +++chip architecture, but they have no information about the rest of your +++debugging target machine. +++ +++First of all you need to tell the stub how to communicate with the +++serial port. +++ +++@table @code +++@item int getDebugChar() +++@findex getDebugChar +++Write this subroutine to read a single character from the serial port. +++It may be identical to @code{getchar} for your target system; a +++different name is used to allow you to distinguish the two if you wish. +++ +++@item void putDebugChar(int) +++@findex putDebugChar +++Write this subroutine to write a single character to the serial port. +++It may be identical to @code{putchar} for your target system; a +++different name is used to allow you to distinguish the two if you wish. +++@end table +++ +++@cindex control C, and remote debugging +++@cindex interrupting remote targets +++If you want @value{GDBN} to be able to stop your program while it is +++running, you need to use an interrupt-driven serial driver, and arrange +++for it to stop when it receives a @code{^C} (@samp{\003}, the control-C +++character). That is the character which @value{GDBN} uses to tell the +++remote system to stop. +++ +++Getting the debugging target to return the proper status to @value{GDBN} +++probably requires changes to the standard stub; one quick and dirty way +++is to just execute a breakpoint instruction (the ``dirty'' part is that +++@value{GDBN} reports a @code{SIGTRAP} instead of a @code{SIGINT}). +++ +++Other routines you need to supply are: +++ +++@table @code +++@item void exceptionHandler (int @var{exception_number}, void *@var{exception_address}) +++@findex exceptionHandler +++Write this function to install @var{exception_address} in the exception +++handling tables. You need to do this because the stub does not have any +++way of knowing what the exception handling tables on your target system +++are like (for example, the processor's table might be in @sc{rom}, +++containing entries which point to a table in @sc{ram}). +++The @var{exception_number} specifies the exception which should be changed; +++its meaning is architecture-dependent (for example, different numbers +++might represent divide by zero, misaligned access, etc). When this +++exception occurs, control should be transferred directly to +++@var{exception_address}, and the processor state (stack, registers, +++and so on) should be just as it is when a processor exception occurs. So if +++you want to use a jump instruction to reach @var{exception_address}, it +++should be a simple jump, not a jump to subroutine. +++ +++For the 386, @var{exception_address} should be installed as an interrupt +++gate so that interrupts are masked while the handler runs. The gate +++should be at privilege level 0 (the most privileged level). The +++@sc{sparc} and 68k stubs are able to mask interrupts themselves without +++help from @code{exceptionHandler}. +++ +++@item void flush_i_cache() +++@findex flush_i_cache +++On @sc{sparc} and @sc{sparclite} only, write this subroutine to flush the +++instruction cache, if any, on your target machine. If there is no +++instruction cache, this subroutine may be a no-op. +++ +++On target machines that have instruction caches, @value{GDBN} requires this +++function to make certain that the state of your program is stable. +++@end table +++ +++@noindent +++You must also make sure this library routine is available: +++ +++@table @code +++@item void *memset(void *, int, int) +++@findex memset +++This is the standard library function @code{memset} that sets an area of +++memory to a known value. If you have one of the free versions of +++@code{libc.a}, @code{memset} can be found there; otherwise, you must +++either obtain it from your hardware manufacturer, or write your own. +++@end table +++ +++If you do not use the GNU C compiler, you may need other standard +++library subroutines as well; this varies from one stub to another, +++but in general the stubs are likely to use any of the common library +++subroutines which @code{@value{NGCC}} generates as inline code. +++ +++ +++@node Debug Session +++@subsection Putting it All Together +++ +++@cindex remote serial debugging summary +++In summary, when your program is ready to debug, you must follow these +++steps. +++ +++@enumerate +++@item +++Make sure you have defined the supporting low-level routines +++(@pxref{Bootstrapping,,What You Must Do for the Stub}): +++@display +++@code{getDebugChar}, @code{putDebugChar}, +++@code{flush_i_cache}, @code{memset}, @code{exceptionHandler}. +++@end display +++ +++@item +++Insert these lines in your program's startup code, before the main +++procedure is called: +++ +++@smallexample +++set_debug_traps(); +++breakpoint(); +++@end smallexample +++ +++On some machines, when a breakpoint trap is raised, the hardware +++automatically makes the PC point to the instruction after the +++breakpoint. If your machine doesn't do that, you may need to adjust +++@code{handle_exception} to arrange for it to return to the instruction +++after the breakpoint on this first invocation, so that your program +++doesn't keep hitting the initial breakpoint instead of making +++progress. +++ +++@item +++For the 680x0 stub only, you need to provide a variable called +++@code{exceptionHook}. Normally you just use: +++ +++@smallexample +++void (*exceptionHook)() = 0; +++@end smallexample +++ +++@noindent +++but if before calling @code{set_debug_traps}, you set it to point to a +++function in your program, that function is called when +++@code{@value{GDBN}} continues after stopping on a trap (for example, bus +++error). The function indicated by @code{exceptionHook} is called with +++one parameter: an @code{int} which is the exception number. +++ +++@item +++Compile and link together: your program, the @value{GDBN} debugging stub for +++your target architecture, and the supporting subroutines. +++ +++@item +++Make sure you have a serial connection between your target machine and +++the @value{GDBN} host, and identify the serial port on the host. +++ +++@item +++@c The "remote" target now provides a `load' command, so we should +++@c document that. FIXME. +++Download your program to your target machine (or get it there by +++whatever means the manufacturer provides), and start it. +++ +++@item +++Start @value{GDBN} on the host, and connect to the target +++(@pxref{Connecting,,Connecting to a Remote Target}). +++ +++@end enumerate +++ +++@node Configurations +++@chapter Configuration-Specific Information +++ +++While nearly all @value{GDBN} commands are available for all native and +++cross versions of the debugger, there are some exceptions. This chapter +++describes things that are only available in certain configurations. +++ +++There are three major categories of configurations: native +++configurations, where the host and target are the same, embedded +++operating system configurations, which are usually the same for several +++different processor architectures, and bare embedded processors, which +++are quite different from each other. +++ +++@menu +++* Native:: +++* Embedded OS:: +++* Embedded Processors:: +++* Architectures:: +++@end menu +++ +++@node Native +++@section Native +++ +++This section describes details specific to particular native +++configurations. +++ +++@menu +++* BSD libkvm Interface:: Debugging BSD kernel memory images +++* Process Information:: Process information +++* DJGPP Native:: Features specific to the DJGPP port +++* Cygwin Native:: Features specific to the Cygwin port +++* Hurd Native:: Features specific to @sc{gnu} Hurd +++* Darwin:: Features specific to Darwin +++* FreeBSD:: Features specific to FreeBSD +++@end menu +++ +++@node BSD libkvm Interface +++@subsection BSD libkvm Interface +++ +++@cindex libkvm +++@cindex kernel memory image +++@cindex kernel crash dump +++ +++BSD-derived systems (FreeBSD/NetBSD/OpenBSD) have a kernel memory +++interface that provides a uniform interface for accessing kernel virtual +++memory images, including live systems and crash dumps. @value{GDBN} +++uses this interface to allow you to debug live kernels and kernel crash +++dumps on many native BSD configurations. This is implemented as a +++special @code{kvm} debugging target. For debugging a live system, load +++the currently running kernel into @value{GDBN} and connect to the +++@code{kvm} target: +++ +++@smallexample +++(@value{GDBP}) @b{target kvm} +++@end smallexample +++ +++For debugging crash dumps, provide the file name of the crash dump as an +++argument: +++ +++@smallexample +++(@value{GDBP}) @b{target kvm /var/crash/bsd.0} +++@end smallexample +++ +++Once connected to the @code{kvm} target, the following commands are +++available: +++ +++@table @code +++@kindex kvm +++@item kvm pcb +++Set current context from the @dfn{Process Control Block} (PCB) address. +++ +++@item kvm proc +++Set current context from proc address. This command isn't available on +++modern FreeBSD systems. +++@end table +++ +++@node Process Information +++@subsection Process Information +++@cindex /proc +++@cindex examine process image +++@cindex process info via @file{/proc} +++ +++Some operating systems provide interfaces to fetch additional +++information about running processes beyond memory and per-thread +++register state. If @value{GDBN} is configured for an operating system +++with a supported interface, the command @code{info proc} is available +++to report information about the process running your program, or about +++any process running on your system. +++ +++One supported interface is a facility called @samp{/proc} that can be +++used to examine the image of a running process using file-system +++subroutines. This facility is supported on @sc{gnu}/Linux and Solaris +++systems. +++ +++On FreeBSD and NetBSD systems, system control nodes are used to query +++process information. +++ +++In addition, some systems may provide additional process information +++in core files. Note that a core file may include a subset of the +++information available from a live process. Process information is +++currently available from cores created on @sc{gnu}/Linux and FreeBSD +++systems. +++ +++@table @code +++@kindex info proc +++@cindex process ID +++@item info proc +++@itemx info proc @var{process-id} +++Summarize available information about a process. If a +++process ID is specified by @var{process-id}, display information about +++that process; otherwise display information about the program being +++debugged. The summary includes the debugged process ID, the command +++line used to invoke it, its current working directory, and its +++executable file's absolute file name. +++ +++On some systems, @var{process-id} can be of the form +++@samp{[@var{pid}]/@var{tid}} which specifies a certain thread ID +++within a process. If the optional @var{pid} part is missing, it means +++a thread from the process being debugged (the leading @samp{/} still +++needs to be present, or else @value{GDBN} will interpret the number as +++a process ID rather than a thread ID). +++ +++@item info proc cmdline +++@cindex info proc cmdline +++Show the original command line of the process. This command is +++supported on @sc{gnu}/Linux, FreeBSD and NetBSD. +++ +++@item info proc cwd +++@cindex info proc cwd +++Show the current working directory of the process. This command is +++supported on @sc{gnu}/Linux, FreeBSD and NetBSD. +++ +++@item info proc exe +++@cindex info proc exe +++Show the name of executable of the process. This command is supported +++on @sc{gnu}/Linux, FreeBSD and NetBSD. +++ +++@item info proc files +++@cindex info proc files +++Show the file descriptors open by the process. For each open file +++descriptor, @value{GDBN} shows its number, type (file, directory, +++character device, socket), file pointer offset, and the name of the +++resource open on the descriptor. The resource name can be a file name +++(for files, directories, and devices) or a protocol followed by socket +++address (for network connections). This command is supported on +++FreeBSD. +++ +++This example shows the open file descriptors for a process using a +++tty for standard input and output as well as two network sockets: +++ +++@smallexample +++(gdb) info proc files 22136 +++process 22136 +++Open files: +++ +++ FD Type Offset Flags Name +++ text file - r-------- /usr/bin/ssh +++ ctty chr - rw------- /dev/pts/20 +++ cwd dir - r-------- /usr/home/john +++ root dir - r-------- / +++ 0 chr 0x32933a4 rw------- /dev/pts/20 +++ 1 chr 0x32933a4 rw------- /dev/pts/20 +++ 2 chr 0x32933a4 rw------- /dev/pts/20 +++ 3 socket 0x0 rw----n-- tcp4 10.0.1.2:53014 -> 10.0.1.10:22 +++ 4 socket 0x0 rw------- unix stream:/tmp/ssh-FIt89oAzOn5f/agent.2456 +++@end smallexample +++ +++@item info proc mappings +++@cindex memory address space mappings +++Report the memory address space ranges accessible in a process. On +++Solaris, FreeBSD and NetBSD systems, each memory range includes information +++on whether the process has read, write, or execute access rights to each +++range. On @sc{gnu}/Linux, FreeBSD and NetBSD systems, each memory range +++includes the object file which is mapped to that range. +++ +++@item info proc stat +++@itemx info proc status +++@cindex process detailed status information +++Show additional process-related information, including the user ID and +++group ID; virtual memory usage; the signals that are pending, blocked, +++and ignored; its TTY; its consumption of system and user time; its +++stack size; its @samp{nice} value; etc. These commands are supported +++on @sc{gnu}/Linux, FreeBSD and NetBSD. +++ +++For @sc{gnu}/Linux systems, see the @samp{proc} man page for more +++information (type @kbd{man 5 proc} from your shell prompt). +++ +++For FreeBSD and NetBSD systems, @code{info proc stat} is an alias for +++@code{info proc status}. +++ +++@item info proc all +++Show all the information about the process described under all of the +++above @code{info proc} subcommands. +++ +++@ignore +++@comment These sub-options of 'info proc' were not included when +++@comment procfs.c was re-written. Keep their descriptions around +++@comment against the day when someone finds the time to put them back in. +++@kindex info proc times +++@item info proc times +++Starting time, user CPU time, and system CPU time for your program and +++its children. +++ +++@kindex info proc id +++@item info proc id +++Report on the process IDs related to your program: its own process ID, +++the ID of its parent, the process group ID, and the session ID. +++@end ignore +++ +++@item set procfs-trace +++@kindex set procfs-trace +++@cindex @code{procfs} API calls +++This command enables and disables tracing of @code{procfs} API calls. +++ +++@item show procfs-trace +++@kindex show procfs-trace +++Show the current state of @code{procfs} API call tracing. +++ +++@item set procfs-file @var{file} +++@kindex set procfs-file +++Tell @value{GDBN} to write @code{procfs} API trace to the named +++@var{file}. @value{GDBN} appends the trace info to the previous +++contents of the file. The default is to display the trace on the +++standard output. +++ +++@item show procfs-file +++@kindex show procfs-file +++Show the file to which @code{procfs} API trace is written. +++ +++@item proc-trace-entry +++@itemx proc-trace-exit +++@itemx proc-untrace-entry +++@itemx proc-untrace-exit +++@kindex proc-trace-entry +++@kindex proc-trace-exit +++@kindex proc-untrace-entry +++@kindex proc-untrace-exit +++These commands enable and disable tracing of entries into and exits +++from the @code{syscall} interface. +++ +++@item info pidlist +++@kindex info pidlist +++@cindex process list, QNX Neutrino +++For QNX Neutrino only, this command displays the list of all the +++processes and all the threads within each process. +++ +++@item info meminfo +++@kindex info meminfo +++@cindex mapinfo list, QNX Neutrino +++For QNX Neutrino only, this command displays the list of all mapinfos. +++@end table +++ +++@node DJGPP Native +++@subsection Features for Debugging @sc{djgpp} Programs +++@cindex @sc{djgpp} debugging +++@cindex native @sc{djgpp} debugging +++@cindex MS-DOS-specific commands +++ +++@cindex DPMI +++@sc{djgpp} is a port of the @sc{gnu} development tools to MS-DOS and +++MS-Windows. @sc{djgpp} programs are 32-bit protected-mode programs +++that use the @dfn{DPMI} (DOS Protected-Mode Interface) API to run on +++top of real-mode DOS systems and their emulations. +++ +++@value{GDBN} supports native debugging of @sc{djgpp} programs, and +++defines a few commands specific to the @sc{djgpp} port. This +++subsection describes those commands. +++ +++@table @code +++@kindex info dos +++@item info dos +++This is a prefix of @sc{djgpp}-specific commands which print +++information about the target system and important OS structures. +++ +++@kindex sysinfo +++@cindex MS-DOS system info +++@cindex free memory information (MS-DOS) +++@item info dos sysinfo +++This command displays assorted information about the underlying +++platform: the CPU type and features, the OS version and flavor, the +++DPMI version, and the available conventional and DPMI memory. +++ +++@cindex GDT +++@cindex LDT +++@cindex IDT +++@cindex segment descriptor tables +++@cindex descriptor tables display +++@item info dos gdt +++@itemx info dos ldt +++@itemx info dos idt +++These 3 commands display entries from, respectively, Global, Local, +++and Interrupt Descriptor Tables (GDT, LDT, and IDT). The descriptor +++tables are data structures which store a descriptor for each segment +++that is currently in use. The segment's selector is an index into a +++descriptor table; the table entry for that index holds the +++descriptor's base address and limit, and its attributes and access +++rights. +++ +++A typical @sc{djgpp} program uses 3 segments: a code segment, a data +++segment (used for both data and the stack), and a DOS segment (which +++allows access to DOS/BIOS data structures and absolute addresses in +++conventional memory). However, the DPMI host will usually define +++additional segments in order to support the DPMI environment. +++ +++@cindex garbled pointers +++These commands allow to display entries from the descriptor tables. +++Without an argument, all entries from the specified table are +++displayed. An argument, which should be an integer expression, means +++display a single entry whose index is given by the argument. For +++example, here's a convenient way to display information about the +++debugged program's data segment: +++ +++@smallexample +++@exdent @code{(@value{GDBP}) info dos ldt $ds} +++@exdent @code{0x13f: base=0x11970000 limit=0x0009ffff 32-Bit Data (Read/Write, Exp-up)} +++@end smallexample +++ +++@noindent +++This comes in handy when you want to see whether a pointer is outside +++the data segment's limit (i.e.@: @dfn{garbled}). +++ +++@cindex page tables display (MS-DOS) +++@item info dos pde +++@itemx info dos pte +++These two commands display entries from, respectively, the Page +++Directory and the Page Tables. Page Directories and Page Tables are +++data structures which control how virtual memory addresses are mapped +++into physical addresses. A Page Table includes an entry for every +++page of memory that is mapped into the program's address space; there +++may be several Page Tables, each one holding up to 4096 entries. A +++Page Directory has up to 4096 entries, one each for every Page Table +++that is currently in use. +++ +++Without an argument, @kbd{info dos pde} displays the entire Page +++Directory, and @kbd{info dos pte} displays all the entries in all of +++the Page Tables. An argument, an integer expression, given to the +++@kbd{info dos pde} command means display only that entry from the Page +++Directory table. An argument given to the @kbd{info dos pte} command +++means display entries from a single Page Table, the one pointed to by +++the specified entry in the Page Directory. +++ +++@cindex direct memory access (DMA) on MS-DOS +++These commands are useful when your program uses @dfn{DMA} (Direct +++Memory Access), which needs physical addresses to program the DMA +++controller. +++ +++These commands are supported only with some DPMI servers. +++ +++@cindex physical address from linear address +++@item info dos address-pte @var{addr} +++This command displays the Page Table entry for a specified linear +++address. The argument @var{addr} is a linear address which should +++already have the appropriate segment's base address added to it, +++because this command accepts addresses which may belong to @emph{any} +++segment. For example, here's how to display the Page Table entry for +++the page where a variable @code{i} is stored: +++ +++@smallexample +++@exdent @code{(@value{GDBP}) info dos address-pte __djgpp_base_address + (char *)&i} +++@exdent @code{Page Table entry for address 0x11a00d30:} +++@exdent @code{Base=0x02698000 Dirty Acc. Not-Cached Write-Back Usr Read-Write +0xd30} +++@end smallexample +++ +++@noindent +++This says that @code{i} is stored at offset @code{0xd30} from the page +++whose physical base address is @code{0x02698000}, and shows all the +++attributes of that page. +++ +++Note that you must cast the addresses of variables to a @code{char *}, +++since otherwise the value of @code{__djgpp_base_address}, the base +++address of all variables and functions in a @sc{djgpp} program, will +++be added using the rules of C pointer arithmetics: if @code{i} is +++declared an @code{int}, @value{GDBN} will add 4 times the value of +++@code{__djgpp_base_address} to the address of @code{i}. +++ +++Here's another example, it displays the Page Table entry for the +++transfer buffer: +++ +++@smallexample +++@exdent @code{(@value{GDBP}) info dos address-pte *((unsigned *)&_go32_info_block + 3)} +++@exdent @code{Page Table entry for address 0x29110:} +++@exdent @code{Base=0x00029000 Dirty Acc. Not-Cached Write-Back Usr Read-Write +0x110} +++@end smallexample +++ +++@noindent +++(The @code{+ 3} offset is because the transfer buffer's address is the +++3rd member of the @code{_go32_info_block} structure.) The output +++clearly shows that this DPMI server maps the addresses in conventional +++memory 1:1, i.e.@: the physical (@code{0x00029000} + @code{0x110}) and +++linear (@code{0x29110}) addresses are identical. +++ +++This command is supported only with some DPMI servers. +++@end table +++ +++@cindex DOS serial data link, remote debugging +++In addition to native debugging, the DJGPP port supports remote +++debugging via a serial data link. The following commands are specific +++to remote serial debugging in the DJGPP port of @value{GDBN}. +++ +++@table @code +++@kindex set com1base +++@kindex set com1irq +++@kindex set com2base +++@kindex set com2irq +++@kindex set com3base +++@kindex set com3irq +++@kindex set com4base +++@kindex set com4irq +++@item set com1base @var{addr} +++This command sets the base I/O port address of the @file{COM1} serial +++port. +++ +++@item set com1irq @var{irq} +++This command sets the @dfn{Interrupt Request} (@code{IRQ}) line to use +++for the @file{COM1} serial port. +++ +++There are similar commands @samp{set com2base}, @samp{set com3irq}, +++etc.@: for setting the port address and the @code{IRQ} lines for the +++other 3 COM ports. +++ +++@kindex show com1base +++@kindex show com1irq +++@kindex show com2base +++@kindex show com2irq +++@kindex show com3base +++@kindex show com3irq +++@kindex show com4base +++@kindex show com4irq +++The related commands @samp{show com1base}, @samp{show com1irq} etc.@: +++display the current settings of the base address and the @code{IRQ} +++lines used by the COM ports. +++ +++@item info serial +++@kindex info serial +++@cindex DOS serial port status +++This command prints the status of the 4 DOS serial ports. For each +++port, it prints whether it's active or not, its I/O base address and +++IRQ number, whether it uses a 16550-style FIFO, its baudrate, and the +++counts of various errors encountered so far. +++@end table +++ +++ +++@node Cygwin Native +++@subsection Features for Debugging MS Windows PE Executables +++@cindex MS Windows debugging +++@cindex native Cygwin debugging +++@cindex Cygwin-specific commands +++ +++@value{GDBN} supports native debugging of MS Windows programs, including +++DLLs with and without symbolic debugging information. +++ +++@cindex Ctrl-BREAK, MS-Windows +++@cindex interrupt debuggee on MS-Windows +++MS-Windows programs that call @code{SetConsoleMode} to switch off the +++special meaning of the @samp{Ctrl-C} keystroke cannot be interrupted +++by typing @kbd{C-c}. For this reason, @value{GDBN} on MS-Windows +++supports @kbd{C-@key{BREAK}} as an alternative interrupt key +++sequence, which can be used to interrupt the debuggee even if it +++ignores @kbd{C-c}. +++ +++There are various additional Cygwin-specific commands, described in +++this section. Working with DLLs that have no debugging symbols is +++described in @ref{Non-debug DLL Symbols}. +++ +++@table @code +++@kindex info w32 +++@item info w32 +++This is a prefix of MS Windows-specific commands which print +++information about the target system and important OS structures. +++ +++@item info w32 selector +++This command displays information returned by +++the Win32 API @code{GetThreadSelectorEntry} function. +++It takes an optional argument that is evaluated to +++a long value to give the information about this given selector. +++Without argument, this command displays information +++about the six segment registers. +++ +++@item info w32 thread-information-block +++This command displays thread specific information stored in the +++Thread Information Block (readable on the X86 CPU family using @code{$fs} +++selector for 32-bit programs and @code{$gs} for 64-bit programs). +++ +++@kindex signal-event +++@item signal-event @var{id} +++This command signals an event with user-provided @var{id}. Used to resume +++crashing process when attached to it using MS-Windows JIT debugging (AeDebug). +++ +++To use it, create or edit the following keys in +++@code{HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\AeDebug} and/or +++@code{HKLM\SOFTWARE\Wow6432Node\Microsoft\Windows NT\CurrentVersion\AeDebug} +++(for x86_64 versions): +++ +++@itemize @minus +++@item +++@code{Debugger} (REG_SZ) --- a command to launch the debugger. +++Suggested command is: @code{@var{fully-qualified-path-to-gdb.exe} -ex +++"attach %ld" -ex "signal-event %ld" -ex "continue"}. +++ +++The first @code{%ld} will be replaced by the process ID of the +++crashing process, the second @code{%ld} will be replaced by the ID of +++the event that blocks the crashing process, waiting for @value{GDBN} +++to attach. +++ +++@item +++@code{Auto} (REG_SZ) --- either @code{1} or @code{0}. @code{1} will +++make the system run debugger specified by the Debugger key +++automatically, @code{0} will cause a dialog box with ``OK'' and +++``Cancel'' buttons to appear, which allows the user to either +++terminate the crashing process (OK) or debug it (Cancel). +++@end itemize +++ +++@kindex set cygwin-exceptions +++@cindex debugging the Cygwin DLL +++@cindex Cygwin DLL, debugging +++@item set cygwin-exceptions @var{mode} +++If @var{mode} is @code{on}, @value{GDBN} will break on exceptions that +++happen inside the Cygwin DLL. If @var{mode} is @code{off}, +++@value{GDBN} will delay recognition of exceptions, and may ignore some +++exceptions which seem to be caused by internal Cygwin DLL +++``bookkeeping''. This option is meant primarily for debugging the +++Cygwin DLL itself; the default value is @code{off} to avoid annoying +++@value{GDBN} users with false @code{SIGSEGV} signals. +++ +++@kindex show cygwin-exceptions +++@item show cygwin-exceptions +++Displays whether @value{GDBN} will break on exceptions that happen +++inside the Cygwin DLL itself. +++ +++@kindex set new-console +++@item set new-console @var{mode} +++If @var{mode} is @code{on} the debuggee will +++be started in a new console on next start. +++If @var{mode} is @code{off}, the debuggee will +++be started in the same console as the debugger. +++ +++@kindex show new-console +++@item show new-console +++Displays whether a new console is used +++when the debuggee is started. +++ +++@kindex set new-group +++@item set new-group @var{mode} +++This boolean value controls whether the debuggee should +++start a new group or stay in the same group as the debugger. +++This affects the way the Windows OS handles +++@samp{Ctrl-C}. +++ +++@kindex show new-group +++@item show new-group +++Displays current value of new-group boolean. +++ +++@kindex set debugevents +++@item set debugevents +++This boolean value adds debug output concerning kernel events related +++to the debuggee seen by the debugger. This includes events that +++signal thread and process creation and exit, DLL loading and +++unloading, console interrupts, and debugging messages produced by the +++Windows @code{OutputDebugString} API call. +++ +++@kindex set debugexec +++@item set debugexec +++This boolean value adds debug output concerning execute events +++(such as resume thread) seen by the debugger. +++ +++@kindex set debugexceptions +++@item set debugexceptions +++This boolean value adds debug output concerning exceptions in the +++debuggee seen by the debugger. +++ +++@kindex set debugmemory +++@item set debugmemory +++This boolean value adds debug output concerning debuggee memory reads +++and writes by the debugger. +++ +++@kindex set shell +++@item set shell +++This boolean values specifies whether the debuggee is called +++via a shell or directly (default value is on). +++ +++@kindex show shell +++@item show shell +++Displays if the debuggee will be started with a shell. +++ +++@end table +++ +++@menu +++* Non-debug DLL Symbols:: Support for DLLs without debugging symbols +++@end menu +++ +++@node Non-debug DLL Symbols +++@subsubsection Support for DLLs without Debugging Symbols +++@cindex DLLs with no debugging symbols +++@cindex Minimal symbols and DLLs +++ +++Very often on windows, some of the DLLs that your program relies on do +++not include symbolic debugging information (for example, +++@file{kernel32.dll}). When @value{GDBN} doesn't recognize any debugging +++symbols in a DLL, it relies on the minimal amount of symbolic +++information contained in the DLL's export table. This section +++describes working with such symbols, known internally to @value{GDBN} as +++``minimal symbols''. +++ +++Note that before the debugged program has started execution, no DLLs +++will have been loaded. The easiest way around this problem is simply to +++start the program --- either by setting a breakpoint or letting the +++program run once to completion. +++ +++@subsubsection DLL Name Prefixes +++ +++In keeping with the naming conventions used by the Microsoft debugging +++tools, DLL export symbols are made available with a prefix based on the +++DLL name, for instance @code{KERNEL32!CreateFileA}. The plain name is +++also entered into the symbol table, so @code{CreateFileA} is often +++sufficient. In some cases there will be name clashes within a program +++(particularly if the executable itself includes full debugging symbols) +++necessitating the use of the fully qualified name when referring to the +++contents of the DLL. Use single-quotes around the name to avoid the +++exclamation mark (``!'') being interpreted as a language operator. +++ +++Note that the internal name of the DLL may be all upper-case, even +++though the file name of the DLL is lower-case, or vice-versa. Since +++symbols within @value{GDBN} are @emph{case-sensitive} this may cause +++some confusion. If in doubt, try the @code{info functions} and +++@code{info variables} commands or even @code{maint print msymbols} +++(@pxref{Symbols}). Here's an example: +++ +++@smallexample +++(@value{GDBP}) info function CreateFileA +++All functions matching regular expression "CreateFileA": +++ +++Non-debugging symbols: +++0x77e885f4 CreateFileA +++0x77e885f4 KERNEL32!CreateFileA +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) info function ! +++All functions matching regular expression "!": +++ +++Non-debugging symbols: +++0x6100114c cygwin1!__assert +++0x61004034 cygwin1!_dll_crt0@@0 +++0x61004240 cygwin1!dll_crt0(per_process *) +++[etc...] +++@end smallexample +++ +++@subsubsection Working with Minimal Symbols +++ +++Symbols extracted from a DLL's export table do not contain very much +++type information. All that @value{GDBN} can do is guess whether a symbol +++refers to a function or variable depending on the linker section that +++contains the symbol. Also note that the actual contents of the memory +++contained in a DLL are not available unless the program is running. This +++means that you cannot examine the contents of a variable or disassemble +++a function within a DLL without a running program. +++ +++Variables are generally treated as pointers and dereferenced +++automatically. For this reason, it is often necessary to prefix a +++variable name with the address-of operator (``&'') and provide explicit +++type information in the command. Here's an example of the type of +++problem: +++ +++@smallexample +++(@value{GDBP}) print 'cygwin1!__argv' +++'cygwin1!__argv' has unknown type; cast it to its declared type +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) x 'cygwin1!__argv' +++'cygwin1!__argv' has unknown type; cast it to its declared type +++@end smallexample +++ +++And two possible solutions: +++ +++@smallexample +++(@value{GDBP}) print ((char **)'cygwin1!__argv')[0] +++$2 = 0x22fd98 "/cygdrive/c/mydirectory/myprogram" +++@end smallexample +++ +++@smallexample +++(@value{GDBP}) x/2x &'cygwin1!__argv' +++0x610c0aa8 : 0x10021608 0x00000000 +++(@value{GDBP}) x/x 0x10021608 +++0x10021608: 0x0022fd98 +++(@value{GDBP}) x/s 0x0022fd98 +++0x22fd98: "/cygdrive/c/mydirectory/myprogram" +++@end smallexample +++ +++Setting a break point within a DLL is possible even before the program +++starts execution. However, under these circumstances, @value{GDBN} can't +++examine the initial instructions of the function in order to skip the +++function's frame set-up code. You can work around this by using ``*&'' +++to set the breakpoint at a raw memory address: +++ +++@smallexample +++(@value{GDBP}) break *&'python22!PyOS_Readline' +++Breakpoint 1 at 0x1e04eff0 +++@end smallexample +++ +++The author of these extensions is not entirely convinced that setting a +++break point within a shared DLL like @file{kernel32.dll} is completely +++safe. +++ +++@node Hurd Native +++@subsection Commands Specific to @sc{gnu} Hurd Systems +++@cindex @sc{gnu} Hurd debugging +++ +++This subsection describes @value{GDBN} commands specific to the +++@sc{gnu} Hurd native debugging. +++ +++@table @code +++@item set signals +++@itemx set sigs +++@kindex set signals@r{, Hurd command} +++@kindex set sigs@r{, Hurd command} +++This command toggles the state of inferior signal interception by +++@value{GDBN}. Mach exceptions, such as breakpoint traps, are not +++affected by this command. @code{sigs} is a shorthand alias for +++@code{signals}. +++ +++@item show signals +++@itemx show sigs +++@kindex show signals@r{, Hurd command} +++@kindex show sigs@r{, Hurd command} +++Show the current state of intercepting inferior's signals. +++ +++@item set signal-thread +++@itemx set sigthread +++@kindex set signal-thread +++@kindex set sigthread +++This command tells @value{GDBN} which thread is the @code{libc} signal +++thread. That thread is run when a signal is delivered to a running +++process. @code{set sigthread} is the shorthand alias of @code{set +++signal-thread}. +++ +++@item show signal-thread +++@itemx show sigthread +++@kindex show signal-thread +++@kindex show sigthread +++These two commands show which thread will run when the inferior is +++delivered a signal. +++ +++@item set stopped +++@kindex set stopped@r{, Hurd command} +++This commands tells @value{GDBN} that the inferior process is stopped, +++as with the @code{SIGSTOP} signal. The stopped process can be +++continued by delivering a signal to it. +++ +++@item show stopped +++@kindex show stopped@r{, Hurd command} +++This command shows whether @value{GDBN} thinks the debuggee is +++stopped. +++ +++@item set exceptions +++@kindex set exceptions@r{, Hurd command} +++Use this command to turn off trapping of exceptions in the inferior. +++When exception trapping is off, neither breakpoints nor +++single-stepping will work. To restore the default, set exception +++trapping on. +++ +++@item show exceptions +++@kindex show exceptions@r{, Hurd command} +++Show the current state of trapping exceptions in the inferior. +++ +++@item set task pause +++@kindex set task@r{, Hurd commands} +++@cindex task attributes (@sc{gnu} Hurd) +++@cindex pause current task (@sc{gnu} Hurd) +++This command toggles task suspension when @value{GDBN} has control. +++Setting it to on takes effect immediately, and the task is suspended +++whenever @value{GDBN} gets control. Setting it to off will take +++effect the next time the inferior is continued. If this option is set +++to off, you can use @code{set thread default pause on} or @code{set +++thread pause on} (see below) to pause individual threads. +++ +++@item show task pause +++@kindex show task@r{, Hurd commands} +++Show the current state of task suspension. +++ +++@item set task detach-suspend-count +++@cindex task suspend count +++@cindex detach from task, @sc{gnu} Hurd +++This command sets the suspend count the task will be left with when +++@value{GDBN} detaches from it. +++ +++@item show task detach-suspend-count +++Show the suspend count the task will be left with when detaching. +++ +++@item set task exception-port +++@itemx set task excp +++@cindex task exception port, @sc{gnu} Hurd +++This command sets the task exception port to which @value{GDBN} will +++forward exceptions. The argument should be the value of the @dfn{send +++rights} of the task. @code{set task excp} is a shorthand alias. +++ +++@item set noninvasive +++@cindex noninvasive task options +++This command switches @value{GDBN} to a mode that is the least +++invasive as far as interfering with the inferior is concerned. This +++is the same as using @code{set task pause}, @code{set exceptions}, and +++@code{set signals} to values opposite to the defaults. +++ +++@item info send-rights +++@itemx info receive-rights +++@itemx info port-rights +++@itemx info port-sets +++@itemx info dead-names +++@itemx info ports +++@itemx info psets +++@cindex send rights, @sc{gnu} Hurd +++@cindex receive rights, @sc{gnu} Hurd +++@cindex port rights, @sc{gnu} Hurd +++@cindex port sets, @sc{gnu} Hurd +++@cindex dead names, @sc{gnu} Hurd +++These commands display information about, respectively, send rights, +++receive rights, port rights, port sets, and dead names of a task. +++There are also shorthand aliases: @code{info ports} for @code{info +++port-rights} and @code{info psets} for @code{info port-sets}. +++ +++@item set thread pause +++@kindex set thread@r{, Hurd command} +++@cindex thread properties, @sc{gnu} Hurd +++@cindex pause current thread (@sc{gnu} Hurd) +++This command toggles current thread suspension when @value{GDBN} has +++control. Setting it to on takes effect immediately, and the current +++thread is suspended whenever @value{GDBN} gets control. Setting it to +++off will take effect the next time the inferior is continued. +++Normally, this command has no effect, since when @value{GDBN} has +++control, the whole task is suspended. However, if you used @code{set +++task pause off} (see above), this command comes in handy to suspend +++only the current thread. +++ +++@item show thread pause +++@kindex show thread@r{, Hurd command} +++This command shows the state of current thread suspension. +++ +++@item set thread run +++This command sets whether the current thread is allowed to run. +++ +++@item show thread run +++Show whether the current thread is allowed to run. +++ +++@item set thread detach-suspend-count +++@cindex thread suspend count, @sc{gnu} Hurd +++@cindex detach from thread, @sc{gnu} Hurd +++This command sets the suspend count @value{GDBN} will leave on a +++thread when detaching. This number is relative to the suspend count +++found by @value{GDBN} when it notices the thread; use @code{set thread +++takeover-suspend-count} to force it to an absolute value. +++ +++@item show thread detach-suspend-count +++Show the suspend count @value{GDBN} will leave on the thread when +++detaching. +++ +++@item set thread exception-port +++@itemx set thread excp +++Set the thread exception port to which to forward exceptions. This +++overrides the port set by @code{set task exception-port} (see above). +++@code{set thread excp} is the shorthand alias. +++ +++@item set thread takeover-suspend-count +++Normally, @value{GDBN}'s thread suspend counts are relative to the +++value @value{GDBN} finds when it notices each thread. This command +++changes the suspend counts to be absolute instead. +++ +++@item set thread default +++@itemx show thread default +++@cindex thread default settings, @sc{gnu} Hurd +++Each of the above @code{set thread} commands has a @code{set thread +++default} counterpart (e.g., @code{set thread default pause}, @code{set +++thread default exception-port}, etc.). The @code{thread default} +++variety of commands sets the default thread properties for all +++threads; you can then change the properties of individual threads with +++the non-default commands. +++@end table +++ +++@node Darwin +++@subsection Darwin +++@cindex Darwin +++ +++@value{GDBN} provides the following commands specific to the Darwin target: +++ +++@table @code +++@item set debug darwin @var{num} +++@kindex set debug darwin +++When set to a non zero value, enables debugging messages specific to +++the Darwin support. Higher values produce more verbose output. +++ +++@item show debug darwin +++@kindex show debug darwin +++Show the current state of Darwin messages. +++ +++@item set debug mach-o @var{num} +++@kindex set debug mach-o +++When set to a non zero value, enables debugging messages while +++@value{GDBN} is reading Darwin object files. (@dfn{Mach-O} is the +++file format used on Darwin for object and executable files.) Higher +++values produce more verbose output. This is a command to diagnose +++problems internal to @value{GDBN} and should not be needed in normal +++usage. +++ +++@item show debug mach-o +++@kindex show debug mach-o +++Show the current state of Mach-O file messages. +++ +++@item set mach-exceptions on +++@itemx set mach-exceptions off +++@kindex set mach-exceptions +++On Darwin, faults are first reported as a Mach exception and are then +++mapped to a Posix signal. Use this command to turn on trapping of +++Mach exceptions in the inferior. This might be sometimes useful to +++better understand the cause of a fault. The default is off. +++ +++@item show mach-exceptions +++@kindex show mach-exceptions +++Show the current state of exceptions trapping. +++@end table +++ +++@node FreeBSD +++@subsection FreeBSD +++@cindex FreeBSD +++ +++When the ABI of a system call is changed in the FreeBSD kernel, this +++is implemented by leaving a compatibility system call using the old +++ABI at the existing number and allocating a new system call number for +++the version using the new ABI. As a convenience, when a system call +++is caught by name (@pxref{catch syscall}), compatibility system calls +++are also caught. +++ +++For example, FreeBSD 12 introduced a new variant of the @code{kevent} +++system call and catching the @code{kevent} system call by name catches +++both variants: +++ +++@smallexample +++(@value{GDBP}) catch syscall kevent +++Catchpoint 1 (syscalls 'freebsd11_kevent' [363] 'kevent' [560]) +++(@value{GDBP}) +++@end smallexample +++ +++ +++@node Embedded OS +++@section Embedded Operating Systems +++ +++This section describes configurations involving the debugging of +++embedded operating systems that are available for several different +++architectures. +++ +++@value{GDBN} includes the ability to debug programs running on +++various real-time operating systems. +++ +++@node Embedded Processors +++@section Embedded Processors +++ +++This section goes into details specific to particular embedded +++configurations. +++ +++@cindex send command to simulator +++Whenever a specific embedded processor has a simulator, @value{GDBN} +++allows to send an arbitrary command to the simulator. +++ +++@table @code +++@item sim @var{command} +++@kindex sim@r{, a command} +++Send an arbitrary @var{command} string to the simulator. Consult the +++documentation for the specific simulator in use for information about +++acceptable commands. +++@end table +++ +++ +++@menu +++* ARC:: Synopsys ARC +++* ARM:: ARM +++* BPF:: eBPF +++* M68K:: Motorola M68K +++* MicroBlaze:: Xilinx MicroBlaze +++* MIPS Embedded:: MIPS Embedded +++* OpenRISC 1000:: OpenRISC 1000 (or1k) +++* PowerPC Embedded:: PowerPC Embedded +++* AVR:: Atmel AVR +++* CRIS:: CRIS +++* Super-H:: Renesas Super-H +++@end menu +++ +++@node ARC +++@subsection Synopsys ARC +++@cindex Synopsys ARC +++@cindex ARC specific commands +++@cindex ARC600 +++@cindex ARC700 +++@cindex ARC EM +++@cindex ARC HS +++ +++@value{GDBN} provides the following ARC-specific commands: +++ +++@table @code +++@item set debug arc +++@kindex set debug arc +++Control the level of ARC specific debug messages. Use 0 for no messages (the +++default), 1 for debug messages, and 2 for even more debug messages. +++ +++@item show debug arc +++@kindex show debug arc +++Show the level of ARC specific debugging in operation. +++ +++@item maint print arc arc-instruction @var{address} +++@kindex maint print arc arc-instruction +++Print internal disassembler information about instruction at a given address. +++ +++@end table +++ +++@node ARM +++@subsection ARM +++ +++@value{GDBN} provides the following ARM-specific commands: +++ +++@table @code +++@item set arm disassembler +++@kindex set arm +++This commands selects from a list of disassembly styles. The +++@code{"std"} style is the standard style. +++ +++@item show arm disassembler +++@kindex show arm +++Show the current disassembly style. +++ +++@item set arm apcs32 +++@cindex ARM 32-bit mode +++This command toggles ARM operation mode between 32-bit and 26-bit. +++ +++@item show arm apcs32 +++Display the current usage of the ARM 32-bit mode. +++ +++@item set arm fpu @var{fputype} +++This command sets the ARM floating-point unit (FPU) type. The +++argument @var{fputype} can be one of these: +++ +++@table @code +++@item auto +++Determine the FPU type by querying the OS ABI. +++@item softfpa +++Software FPU, with mixed-endian doubles on little-endian ARM +++processors. +++@item fpa +++GCC-compiled FPA co-processor. +++@item softvfp +++Software FPU with pure-endian doubles. +++@item vfp +++VFP co-processor. +++@end table +++ +++@item show arm fpu +++Show the current type of the FPU. +++ +++@item set arm abi +++This command forces @value{GDBN} to use the specified ABI. +++ +++@item show arm abi +++Show the currently used ABI. +++ +++@item set arm fallback-mode (arm|thumb|auto) +++@value{GDBN} uses the symbol table, when available, to determine +++whether instructions are ARM or Thumb. This command controls +++@value{GDBN}'s default behavior when the symbol table is not +++available. The default is @samp{auto}, which causes @value{GDBN} to +++use the current execution mode (from the @code{T} bit in the @code{CPSR} +++register). +++ +++@item show arm fallback-mode +++Show the current fallback instruction mode. +++ +++@item set arm force-mode (arm|thumb|auto) +++This command overrides use of the symbol table to determine whether +++instructions are ARM or Thumb. The default is @samp{auto}, which +++causes @value{GDBN} to use the symbol table and then the setting +++of @samp{set arm fallback-mode}. +++ +++@item show arm force-mode +++Show the current forced instruction mode. +++ +++@item set debug arm +++Toggle whether to display ARM-specific debugging messages from the ARM +++target support subsystem. +++ +++@item show debug arm +++Show whether ARM-specific debugging messages are enabled. +++@end table +++ +++@table @code +++@item target sim @r{[}@var{simargs}@r{]} @dots{} +++The @value{GDBN} ARM simulator accepts the following optional arguments. +++ +++@table @code +++@item --swi-support=@var{type} +++Tell the simulator which SWI interfaces to support. The argument +++@var{type} may be a comma separated list of the following values. +++The default value is @code{all}. +++ +++@table @code +++@item none +++@item demon +++@item angel +++@item redboot +++@item all +++@end table +++@end table +++@end table +++ +++@node BPF +++@subsection BPF +++ +++@table @code +++@item target sim @r{[}@var{simargs}@r{]} @dots{} +++The @value{GDBN} BPF simulator accepts the following optional arguments. +++ +++@table @code +++@item --skb-data-offset=@var{offset} +++Tell the simulator the offset, measured in bytes, of the +++@code{skb_data} field in the kernel @code{struct sk_buff} structure. +++This offset is used by some BPF specific-purpose load/store +++instructions. Defaults to 0. +++@end table +++@end table +++ +++@node M68K +++@subsection M68k +++ +++The Motorola m68k configuration includes ColdFire support. +++ +++@node MicroBlaze +++@subsection MicroBlaze +++@cindex Xilinx MicroBlaze +++@cindex XMD, Xilinx Microprocessor Debugger +++ +++The MicroBlaze is a soft-core processor supported on various Xilinx +++FPGAs, such as Spartan or Virtex series. Boards with these processors +++usually have JTAG ports which connect to a host system running the Xilinx +++Embedded Development Kit (EDK) or Software Development Kit (SDK). +++This host system is used to download the configuration bitstream to +++the target FPGA. The Xilinx Microprocessor Debugger (XMD) program +++communicates with the target board using the JTAG interface and +++presents a @code{gdbserver} interface to the board. By default +++@code{xmd} uses port @code{1234}. (While it is possible to change +++this default port, it requires the use of undocumented @code{xmd} +++commands. Contact Xilinx support if you need to do this.) +++ +++Use these GDB commands to connect to the MicroBlaze target processor. +++ +++@table @code +++@item target remote :1234 +++Use this command to connect to the target if you are running @value{GDBN} +++on the same system as @code{xmd}. +++ +++@item target remote @var{xmd-host}:1234 +++Use this command to connect to the target if it is connected to @code{xmd} +++running on a different system named @var{xmd-host}. +++ +++@item load +++Use this command to download a program to the MicroBlaze target. +++ +++@item set debug microblaze @var{n} +++Enable MicroBlaze-specific debugging messages if non-zero. +++ +++@item show debug microblaze @var{n} +++Show MicroBlaze-specific debugging level. +++@end table +++ +++@node MIPS Embedded +++@subsection @acronym{MIPS} Embedded +++ +++@noindent +++@value{GDBN} supports these special commands for @acronym{MIPS} targets: +++ +++@table @code +++@item set mipsfpu double +++@itemx set mipsfpu single +++@itemx set mipsfpu none +++@itemx set mipsfpu auto +++@itemx show mipsfpu +++@kindex set mipsfpu +++@kindex show mipsfpu +++@cindex @acronym{MIPS} remote floating point +++@cindex floating point, @acronym{MIPS} remote +++If your target board does not support the @acronym{MIPS} floating point +++coprocessor, you should use the command @samp{set mipsfpu none} (if you +++need this, you may wish to put the command in your @value{GDBN} init +++file). This tells @value{GDBN} how to find the return value of +++functions which return floating point values. It also allows +++@value{GDBN} to avoid saving the floating point registers when calling +++functions on the board. If you are using a floating point coprocessor +++with only single precision floating point support, as on the @sc{r4650} +++processor, use the command @samp{set mipsfpu single}. The default +++double precision floating point coprocessor may be selected using +++@samp{set mipsfpu double}. +++ +++In previous versions the only choices were double precision or no +++floating point, so @samp{set mipsfpu on} will select double precision +++and @samp{set mipsfpu off} will select no floating point. +++ +++As usual, you can inquire about the @code{mipsfpu} variable with +++@samp{show mipsfpu}. +++@end table +++ +++@node OpenRISC 1000 +++@subsection OpenRISC 1000 +++@cindex OpenRISC 1000 +++ +++@noindent +++The OpenRISC 1000 provides a free RISC instruction set architecture. It is +++mainly provided as a soft-core which can run on Xilinx, Altera and other +++FPGA's. +++ +++@value{GDBN} for OpenRISC supports the below commands when connecting to +++a target: +++ +++@table @code +++ +++@kindex target sim +++@item target sim +++ +++Runs the builtin CPU simulator which can run very basic +++programs but does not support most hardware functions like MMU. +++For more complex use cases the user is advised to run an external +++target, and connect using @samp{target remote}. +++ +++Example: @code{target sim} +++ +++@item set debug or1k +++Toggle whether to display OpenRISC-specific debugging messages from the +++OpenRISC target support subsystem. +++ +++@item show debug or1k +++Show whether OpenRISC-specific debugging messages are enabled. +++@end table +++ +++@node PowerPC Embedded +++@subsection PowerPC Embedded +++ +++@cindex DVC register +++@value{GDBN} supports using the DVC (Data Value Compare) register to +++implement in hardware simple hardware watchpoint conditions of the form: +++ +++@smallexample +++(@value{GDBP}) watch @var{ADDRESS|VARIABLE} \ +++ if @var{ADDRESS|VARIABLE} == @var{CONSTANT EXPRESSION} +++@end smallexample +++ +++The DVC register will be automatically used when @value{GDBN} detects +++such pattern in a condition expression, and the created watchpoint uses one +++debug register (either the @code{exact-watchpoints} option is on and the +++variable is scalar, or the variable has a length of one byte). This feature +++is available in native @value{GDBN} running on a Linux kernel version 2.6.34 +++or newer. +++ +++When running on PowerPC embedded processors, @value{GDBN} automatically uses +++ranged hardware watchpoints, unless the @code{exact-watchpoints} option is on, +++in which case watchpoints using only one debug register are created when +++watching variables of scalar types. +++ +++You can create an artificial array to watch an arbitrary memory +++region using one of the following commands (@pxref{Expressions}): +++ +++@smallexample +++(@value{GDBP}) watch *((char *) @var{address})@@@var{length} +++(@value{GDBP}) watch @{char[@var{length}]@} @var{address} +++@end smallexample +++ +++PowerPC embedded processors support masked watchpoints. See the discussion +++about the @code{mask} argument in @ref{Set Watchpoints}. +++ +++@cindex ranged breakpoint +++PowerPC embedded processors support hardware accelerated +++@dfn{ranged breakpoints}. A ranged breakpoint stops execution of +++the inferior whenever it executes an instruction at any address within +++the range it specifies. To set a ranged breakpoint in @value{GDBN}, +++use the @code{break-range} command. +++ +++@value{GDBN} provides the following PowerPC-specific commands: +++ +++@table @code +++@kindex break-range +++@item break-range @var{start-location}, @var{end-location} +++Set a breakpoint for an address range given by +++@var{start-location} and @var{end-location}, which can specify a function name, +++a line number, an offset of lines from the current line or from the start +++location, or an address of an instruction (see @ref{Specify Location}, +++for a list of all the possible ways to specify a @var{location}.) +++The breakpoint will stop execution of the inferior whenever it +++executes an instruction at any address within the specified range, +++(including @var{start-location} and @var{end-location}.) +++ +++@kindex set powerpc +++@item set powerpc soft-float +++@itemx show powerpc soft-float +++Force @value{GDBN} to use (or not use) a software floating point calling +++convention. By default, @value{GDBN} selects the calling convention based +++on the selected architecture and the provided executable file. +++ +++@item set powerpc vector-abi +++@itemx show powerpc vector-abi +++Force @value{GDBN} to use the specified calling convention for vector +++arguments and return values. The valid options are @samp{auto}; +++@samp{generic}, to avoid vector registers even if they are present; +++@samp{altivec}, to use AltiVec registers; and @samp{spe} to use SPE +++registers. By default, @value{GDBN} selects the calling convention +++based on the selected architecture and the provided executable file. +++ +++@item set powerpc exact-watchpoints +++@itemx show powerpc exact-watchpoints +++Allow @value{GDBN} to use only one debug register when watching a variable +++of scalar type, thus assuming that the variable is accessed through the +++address of its first byte. +++ +++@end table +++ +++@node AVR +++@subsection Atmel AVR +++@cindex AVR +++ +++When configured for debugging the Atmel AVR, @value{GDBN} supports the +++following AVR-specific commands: +++ +++@table @code +++@item info io_registers +++@kindex info io_registers@r{, AVR} +++@cindex I/O registers (Atmel AVR) +++This command displays information about the AVR I/O registers. For +++each register, @value{GDBN} prints its number and value. +++@end table +++ +++@node CRIS +++@subsection CRIS +++@cindex CRIS +++ +++When configured for debugging CRIS, @value{GDBN} provides the +++following CRIS-specific commands: +++ +++@table @code +++@item set cris-version @var{ver} +++@cindex CRIS version +++Set the current CRIS version to @var{ver}, either @samp{10} or @samp{32}. +++The CRIS version affects register names and sizes. This command is useful in +++case autodetection of the CRIS version fails. +++ +++@item show cris-version +++Show the current CRIS version. +++ +++@item set cris-dwarf2-cfi +++@cindex DWARF-2 CFI and CRIS +++Set the usage of DWARF-2 CFI for CRIS debugging. The default is @samp{on}. +++Change to @samp{off} when using @code{gcc-cris} whose version is below +++@code{R59}. +++ +++@item show cris-dwarf2-cfi +++Show the current state of using DWARF-2 CFI. +++ +++@item set cris-mode @var{mode} +++@cindex CRIS mode +++Set the current CRIS mode to @var{mode}. It should only be changed when +++debugging in guru mode, in which case it should be set to +++@samp{guru} (the default is @samp{normal}). +++ +++@item show cris-mode +++Show the current CRIS mode. +++@end table +++ +++@node Super-H +++@subsection Renesas Super-H +++@cindex Super-H +++ +++For the Renesas Super-H processor, @value{GDBN} provides these +++commands: +++ +++@table @code +++@item set sh calling-convention @var{convention} +++@kindex set sh calling-convention +++Set the calling-convention used when calling functions from @value{GDBN}. +++Allowed values are @samp{gcc}, which is the default setting, and @samp{renesas}. +++With the @samp{gcc} setting, functions are called using the @value{NGCC} calling +++convention. If the DWARF-2 information of the called function specifies +++that the function follows the Renesas calling convention, the function +++is called using the Renesas calling convention. If the calling convention +++is set to @samp{renesas}, the Renesas calling convention is always used, +++regardless of the DWARF-2 information. This can be used to override the +++default of @samp{gcc} if debug information is missing, or the compiler +++does not emit the DWARF-2 calling convention entry for a function. +++ +++@item show sh calling-convention +++@kindex show sh calling-convention +++Show the current calling convention setting. +++ +++@end table +++ +++ +++@node Architectures +++@section Architectures +++ +++This section describes characteristics of architectures that affect +++all uses of @value{GDBN} with the architecture, both native and cross. +++ +++@menu +++* AArch64:: +++* i386:: +++* Alpha:: +++* MIPS:: +++* HPPA:: HP PA architecture +++* PowerPC:: +++* Nios II:: +++* Sparc64:: +++* S12Z:: +++@end menu +++ +++@node AArch64 +++@subsection AArch64 +++@cindex AArch64 support +++ +++When @value{GDBN} is debugging the AArch64 architecture, it provides the +++following special commands: +++ +++@table @code +++@item set debug aarch64 +++@kindex set debug aarch64 +++This command determines whether AArch64 architecture-specific debugging +++messages are to be displayed. +++ +++@item show debug aarch64 +++Show whether AArch64 debugging messages are displayed. +++ +++@end table +++ +++@subsubsection AArch64 SVE. +++@cindex AArch64 SVE. +++ +++When @value{GDBN} is debugging the AArch64 architecture, if the Scalable Vector +++Extension (SVE) is present, then @value{GDBN} will provide the vector registers +++@code{$z0} through @code{$z31}, vector predicate registers @code{$p0} through +++@code{$p15}, and the @code{$ffr} register. In addition, the pseudo register +++@code{$vg} will be provided. This is the vector granule for the current thread +++and represents the number of 64-bit chunks in an SVE @code{z} register. +++ +++If the vector length changes, then the @code{$vg} register will be updated, +++but the lengths of the @code{z} and @code{p} registers will not change. This +++is a known limitation of @value{GDBN} and does not affect the execution of the +++target process. +++ +++@subsubsection AArch64 Pointer Authentication. +++@cindex AArch64 Pointer Authentication. +++ +++When @value{GDBN} is debugging the AArch64 architecture, and the program is +++using the v8.3-A feature Pointer Authentication (PAC), then whenever the link +++register @code{$lr} is pointing to an PAC function its value will be masked. +++When GDB prints a backtrace, any addresses that required unmasking will be +++postfixed with the marker [PAC]. When using the MI, this is printed as part +++of the @code{addr_flags} field. +++ +++@node i386 +++@subsection x86 Architecture-specific Issues +++ +++@table @code +++@item set struct-convention @var{mode} +++@kindex set struct-convention +++@cindex struct return convention +++@cindex struct/union returned in registers +++Set the convention used by the inferior to return @code{struct}s and +++@code{union}s from functions to @var{mode}. Possible values of +++@var{mode} are @code{"pcc"}, @code{"reg"}, and @code{"default"} (the +++default). @code{"default"} or @code{"pcc"} means that @code{struct}s +++are returned on the stack, while @code{"reg"} means that a +++@code{struct} or a @code{union} whose size is 1, 2, 4, or 8 bytes will +++be returned in a register. +++ +++@item show struct-convention +++@kindex show struct-convention +++Show the current setting of the convention to return @code{struct}s +++from functions. +++@end table +++ +++ +++@subsubsection Intel @dfn{Memory Protection Extensions} (MPX). +++@cindex Intel Memory Protection Extensions (MPX). +++ +++Memory Protection Extension (MPX) adds the bound registers @samp{BND0} +++@footnote{The register named with capital letters represent the architecture +++registers.} through @samp{BND3}. Bound registers store a pair of 64-bit values +++which are the lower bound and upper bound. Bounds are effective addresses or +++memory locations. The upper bounds are architecturally represented in 1's +++complement form. A bound having lower bound = 0, and upper bound = 0 +++(1's complement of all bits set) will allow access to the entire address space. +++ +++@samp{BND0} through @samp{BND3} are represented in @value{GDBN} as @samp{bnd0raw} +++through @samp{bnd3raw}. Pseudo registers @samp{bnd0} through @samp{bnd3} +++display the upper bound performing the complement of one operation on the +++upper bound value, i.e.@ when upper bound in @samp{bnd0raw} is 0 in the +++@value{GDBN} @samp{bnd0} it will be @code{0xfff@dots{}}. In this sense it +++can also be noted that the upper bounds are inclusive. +++ +++As an example, assume that the register BND0 holds bounds for a pointer having +++access allowed for the range between 0x32 and 0x71. The values present on +++bnd0raw and bnd registers are presented as follows: +++ +++@smallexample +++ bnd0raw = @{0x32, 0xffffffff8e@} +++ bnd0 = @{lbound = 0x32, ubound = 0x71@} : size 64 +++@end smallexample +++ +++This way the raw value can be accessed via bnd0raw@dots{}bnd3raw. Any +++change on bnd0@dots{}bnd3 or bnd0raw@dots{}bnd3raw is reflect on its +++counterpart. When the bnd0@dots{}bnd3 registers are displayed via +++Python, the display includes the memory size, in bits, accessible to +++the pointer. +++ +++Bounds can also be stored in bounds tables, which are stored in +++application memory. These tables store bounds for pointers by specifying +++the bounds pointer's value along with its bounds. Evaluating and changing +++bounds located in bound tables is therefore interesting while investigating +++bugs on MPX context. @value{GDBN} provides commands for this purpose: +++ +++@table @code +++@item show mpx bound @var{pointer} +++@kindex show mpx bound +++Display bounds of the given @var{pointer}. +++ +++@item set mpx bound @var{pointer}, @var{lbound}, @var{ubound} +++@kindex set mpx bound +++Set the bounds of a pointer in the bound table. +++This command takes three parameters: @var{pointer} is the pointers +++whose bounds are to be changed, @var{lbound} and @var{ubound} are new values +++for lower and upper bounds respectively. +++@end table +++ +++When you call an inferior function on an Intel MPX enabled program, +++GDB sets the inferior's bound registers to the init (disabled) state +++before calling the function. As a consequence, bounds checks for the +++pointer arguments passed to the function will always pass. +++ +++This is necessary because when you call an inferior function, the +++program is usually in the middle of the execution of other function. +++Since at that point bound registers are in an arbitrary state, not +++clearing them would lead to random bound violations in the called +++function. +++ +++You can still examine the influence of the bound registers on the +++execution of the called function by stopping the execution of the +++called function at its prologue, setting bound registers, and +++continuing the execution. For example: +++ +++@smallexample +++ $ break *upper +++ Breakpoint 2 at 0x4009de: file i386-mpx-call.c, line 47. +++ $ print upper (a, b, c, d, 1) +++ Breakpoint 2, upper (a=0x0, b=0x6e0000005b, c=0x0, d=0x0, len=48).... +++ $ print $bnd0 +++ @{lbound = 0x0, ubound = ffffffff@} : size -1 +++@end smallexample +++ +++At this last step the value of bnd0 can be changed for investigation of bound +++violations caused along the execution of the call. In order to know how to +++set the bound registers or bound table for the call consult the ABI. +++ +++@node Alpha +++@subsection Alpha +++ +++See the following section. +++ +++@node MIPS +++@subsection @acronym{MIPS} +++ +++@cindex stack on Alpha +++@cindex stack on @acronym{MIPS} +++@cindex Alpha stack +++@cindex @acronym{MIPS} stack +++Alpha- and @acronym{MIPS}-based computers use an unusual stack frame, which +++sometimes requires @value{GDBN} to search backward in the object code to +++find the beginning of a function. +++ +++@cindex response time, @acronym{MIPS} debugging +++To improve response time (especially for embedded applications, where +++@value{GDBN} may be restricted to a slow serial line for this search) +++you may want to limit the size of this search, using one of these +++commands: +++ +++@table @code +++@cindex @code{heuristic-fence-post} (Alpha, @acronym{MIPS}) +++@item set heuristic-fence-post @var{limit} +++Restrict @value{GDBN} to examining at most @var{limit} bytes in its +++search for the beginning of a function. A value of @var{0} (the +++default) means there is no limit. However, except for @var{0}, the +++larger the limit the more bytes @code{heuristic-fence-post} must search +++and therefore the longer it takes to run. You should only need to use +++this command when debugging a stripped executable. +++ +++@item show heuristic-fence-post +++Display the current limit. +++@end table +++ +++@noindent +++These commands are available @emph{only} when @value{GDBN} is configured +++for debugging programs on Alpha or @acronym{MIPS} processors. +++ +++Several @acronym{MIPS}-specific commands are available when debugging @acronym{MIPS} +++programs: +++ +++@table @code +++@item set mips abi @var{arg} +++@kindex set mips abi +++@cindex set ABI for @acronym{MIPS} +++Tell @value{GDBN} which @acronym{MIPS} ABI is used by the inferior. Possible +++values of @var{arg} are: +++ +++@table @samp +++@item auto +++The default ABI associated with the current binary (this is the +++default). +++@item o32 +++@item o64 +++@item n32 +++@item n64 +++@item eabi32 +++@item eabi64 +++@end table +++ +++@item show mips abi +++@kindex show mips abi +++Show the @acronym{MIPS} ABI used by @value{GDBN} to debug the inferior. +++ +++@item set mips compression @var{arg} +++@kindex set mips compression +++@cindex code compression, @acronym{MIPS} +++Tell @value{GDBN} which @acronym{MIPS} compressed +++@acronym{ISA, Instruction Set Architecture} encoding is used by the +++inferior. @value{GDBN} uses this for code disassembly and other +++internal interpretation purposes. This setting is only referred to +++when no executable has been associated with the debugging session or +++the executable does not provide information about the encoding it uses. +++Otherwise this setting is automatically updated from information +++provided by the executable. +++ +++Possible values of @var{arg} are @samp{mips16} and @samp{micromips}. +++The default compressed @acronym{ISA} encoding is @samp{mips16}, as +++executables containing @acronym{MIPS16} code frequently are not +++identified as such. +++ +++This setting is ``sticky''; that is, it retains its value across +++debugging sessions until reset either explicitly with this command or +++implicitly from an executable. +++ +++The compiler and/or assembler typically add symbol table annotations to +++identify functions compiled for the @acronym{MIPS16} or +++@acronym{microMIPS} @acronym{ISA}s. If these function-scope annotations +++are present, @value{GDBN} uses them in preference to the global +++compressed @acronym{ISA} encoding setting. +++ +++@item show mips compression +++@kindex show mips compression +++Show the @acronym{MIPS} compressed @acronym{ISA} encoding used by +++@value{GDBN} to debug the inferior. +++ +++@item set mipsfpu +++@itemx show mipsfpu +++@xref{MIPS Embedded, set mipsfpu}. +++ +++@item set mips mask-address @var{arg} +++@kindex set mips mask-address +++@cindex @acronym{MIPS} addresses, masking +++This command determines whether the most-significant 32 bits of 64-bit +++@acronym{MIPS} addresses are masked off. The argument @var{arg} can be +++@samp{on}, @samp{off}, or @samp{auto}. The latter is the default +++setting, which lets @value{GDBN} determine the correct value. +++ +++@item show mips mask-address +++@kindex show mips mask-address +++Show whether the upper 32 bits of @acronym{MIPS} addresses are masked off or +++not. +++ +++@item set remote-mips64-transfers-32bit-regs +++@kindex set remote-mips64-transfers-32bit-regs +++This command controls compatibility with 64-bit @acronym{MIPS} targets that +++transfer data in 32-bit quantities. If you have an old @acronym{MIPS} 64 target +++that transfers 32 bits for some registers, like @sc{sr} and @sc{fsr}, +++and 64 bits for other registers, set this option to @samp{on}. +++ +++@item show remote-mips64-transfers-32bit-regs +++@kindex show remote-mips64-transfers-32bit-regs +++Show the current setting of compatibility with older @acronym{MIPS} 64 targets. +++ +++@item set debug mips +++@kindex set debug mips +++This command turns on and off debugging messages for the @acronym{MIPS}-specific +++target code in @value{GDBN}. +++ +++@item show debug mips +++@kindex show debug mips +++Show the current setting of @acronym{MIPS} debugging messages. +++@end table +++ +++ +++@node HPPA +++@subsection HPPA +++@cindex HPPA support +++ +++When @value{GDBN} is debugging the HP PA architecture, it provides the +++following special commands: +++ +++@table @code +++@item set debug hppa +++@kindex set debug hppa +++This command determines whether HPPA architecture-specific debugging +++messages are to be displayed. +++ +++@item show debug hppa +++Show whether HPPA debugging messages are displayed. +++ +++@item maint print unwind @var{address} +++@kindex maint print unwind@r{, HPPA} +++This command displays the contents of the unwind table entry at the +++given @var{address}. +++ +++@end table +++ +++ +++@node PowerPC +++@subsection PowerPC +++@cindex PowerPC architecture +++ +++When @value{GDBN} is debugging the PowerPC architecture, it provides a set of +++pseudo-registers to enable inspection of 128-bit wide Decimal Floating Point +++numbers stored in the floating point registers. These values must be stored +++in two consecutive registers, always starting at an even register like +++@code{f0} or @code{f2}. +++ +++The pseudo-registers go from @code{$dl0} through @code{$dl15}, and are formed +++by joining the even/odd register pairs @code{f0} and @code{f1} for @code{$dl0}, +++@code{f2} and @code{f3} for @code{$dl1} and so on. +++ +++For POWER7 processors, @value{GDBN} provides a set of pseudo-registers, the 64-bit +++wide Extended Floating Point Registers (@samp{f32} through @samp{f63}). +++ +++@node Nios II +++@subsection Nios II +++@cindex Nios II architecture +++ +++When @value{GDBN} is debugging the Nios II architecture, +++it provides the following special commands: +++ +++@table @code +++ +++@item set debug nios2 +++@kindex set debug nios2 +++This command turns on and off debugging messages for the Nios II +++target code in @value{GDBN}. +++ +++@item show debug nios2 +++@kindex show debug nios2 +++Show the current setting of Nios II debugging messages. +++@end table +++ +++@node Sparc64 +++@subsection Sparc64 +++@cindex Sparc64 support +++@cindex Application Data Integrity +++@subsubsection ADI Support +++ +++The M7 processor supports an Application Data Integrity (ADI) feature that +++detects invalid data accesses. When software allocates memory and enables +++ADI on the allocated memory, it chooses a 4-bit version number, sets the +++version in the upper 4 bits of the 64-bit pointer to that data, and stores +++the 4-bit version in every cacheline of that data. Hardware saves the latter +++in spare bits in the cache and memory hierarchy. On each load and store, +++the processor compares the upper 4 VA (virtual address) bits to the +++cacheline's version. If there is a mismatch, the processor generates a +++version mismatch trap which can be either precise or disrupting. The trap +++is an error condition which the kernel delivers to the process as a SIGSEGV +++signal. +++ +++Note that only 64-bit applications can use ADI and need to be built with +++ADI-enabled. +++ +++Values of the ADI version tags, which are in granularity of a +++cacheline (64 bytes), can be viewed or modified. +++ +++ +++@table @code +++@kindex adi examine +++@item adi (examine | x) [ / @var{n} ] @var{addr} +++ +++The @code{adi examine} command displays the value of one ADI version tag per +++cacheline. +++ +++@var{n} is a decimal integer specifying the number in bytes; the default +++is 1. It specifies how much ADI version information, at the ratio of 1:ADI +++block size, to display. +++ +++@var{addr} is the address in user address space where you want @value{GDBN} +++to begin displaying the ADI version tags. +++ +++Below is an example of displaying ADI versions of variable "shmaddr". +++ +++@smallexample +++(@value{GDBP}) adi x/100 shmaddr +++ 0xfff800010002c000: 0 0 +++@end smallexample +++ +++@kindex adi assign +++@item adi (assign | a) [ / @var{n} ] @var{addr} = @var{tag} +++ +++The @code{adi assign} command is used to assign new ADI version tag +++to an address. +++ +++@var{n} is a decimal integer specifying the number in bytes; +++the default is 1. It specifies how much ADI version information, at the +++ratio of 1:ADI block size, to modify. +++ +++@var{addr} is the address in user address space where you want @value{GDBN} +++to begin modifying the ADI version tags. +++ +++@var{tag} is the new ADI version tag. +++ +++For example, do the following to modify then verify ADI versions of +++variable "shmaddr": +++ +++@smallexample +++(@value{GDBP}) adi a/100 shmaddr = 7 +++(@value{GDBP}) adi x/100 shmaddr +++ 0xfff800010002c000: 7 7 +++@end smallexample +++ +++@end table +++ +++@node S12Z +++@subsection S12Z +++@cindex S12Z support +++ +++When @value{GDBN} is debugging the S12Z architecture, +++it provides the following special command: +++ +++@table @code +++@item maint info bdccsr +++@kindex maint info bdccsr@r{, S12Z} +++This command displays the current value of the microprocessor's +++BDCCSR register. +++@end table +++ +++ +++@node Controlling GDB +++@chapter Controlling @value{GDBN} +++ +++You can alter the way @value{GDBN} interacts with you by using the +++@code{set} command. For commands controlling how @value{GDBN} displays +++data, see @ref{Print Settings, ,Print Settings}. Other settings are +++described here. +++ +++@menu +++* Prompt:: Prompt +++* Editing:: Command editing +++* Command History:: Command history +++* Screen Size:: Screen size +++* Output Styling:: Output styling +++* Numbers:: Numbers +++* ABI:: Configuring the current ABI +++* Auto-loading:: Automatically loading associated files +++* Messages/Warnings:: Optional warnings and messages +++* Debugging Output:: Optional messages about internal happenings +++* Other Misc Settings:: Other Miscellaneous Settings +++@end menu +++ +++@node Prompt +++@section Prompt +++ +++@cindex prompt +++ +++@value{GDBN} indicates its readiness to read a command by printing a string +++called the @dfn{prompt}. This string is normally @samp{(@value{GDBP})}. You +++can change the prompt string with the @code{set prompt} command. For +++instance, when debugging @value{GDBN} with @value{GDBN}, it is useful to change +++the prompt in one of the @value{GDBN} sessions so that you can always tell +++which one you are talking to. +++ +++@emph{Note:} @code{set prompt} does not add a space for you after the +++prompt you set. This allows you to set a prompt which ends in a space +++or a prompt that does not. +++ +++@table @code +++@kindex set prompt +++@item set prompt @var{newprompt} +++Directs @value{GDBN} to use @var{newprompt} as its prompt string henceforth. +++ +++@kindex show prompt +++@item show prompt +++Prints a line of the form: @samp{Gdb's prompt is: @var{your-prompt}} +++@end table +++ +++Versions of @value{GDBN} that ship with Python scripting enabled have +++prompt extensions. The commands for interacting with these extensions +++are: +++ +++@table @code +++@kindex set extended-prompt +++@item set extended-prompt @var{prompt} +++Set an extended prompt that allows for substitutions. +++@xref{gdb.prompt}, for a list of escape sequences that can be used for +++substitution. Any escape sequences specified as part of the prompt +++string are replaced with the corresponding strings each time the prompt +++is displayed. +++ +++For example: +++ +++@smallexample +++set extended-prompt Current working directory: \w (gdb) +++@end smallexample +++ +++Note that when an extended-prompt is set, it takes control of the +++@var{prompt_hook} hook. @xref{prompt_hook}, for further information. +++ +++@kindex show extended-prompt +++@item show extended-prompt +++Prints the extended prompt. Any escape sequences specified as part of +++the prompt string with @code{set extended-prompt}, are replaced with the +++corresponding strings each time the prompt is displayed. +++@end table +++ +++@node Editing +++@section Command Editing +++@cindex readline +++@cindex command line editing +++ +++@value{GDBN} reads its input commands via the @dfn{Readline} interface. This +++@sc{gnu} library provides consistent behavior for programs which provide a +++command line interface to the user. Advantages are @sc{gnu} Emacs-style +++or @dfn{vi}-style inline editing of commands, @code{csh}-like history +++substitution, and a storage and recall of command history across +++debugging sessions. +++ +++You may control the behavior of command line editing in @value{GDBN} with the +++command @code{set}. +++ +++@table @code +++@kindex set editing +++@cindex editing +++@item set editing +++@itemx set editing on +++Enable command line editing (enabled by default). +++ +++@item set editing off +++Disable command line editing. +++ +++@kindex show editing +++@item show editing +++Show whether command line editing is enabled. +++@end table +++ +++@ifset SYSTEM_READLINE +++@xref{Command Line Editing, , , rluserman, GNU Readline Library}, +++@end ifset +++@ifclear SYSTEM_READLINE +++@xref{Command Line Editing}, +++@end ifclear +++for more details about the Readline +++interface. Users unfamiliar with @sc{gnu} Emacs or @code{vi} are +++encouraged to read that chapter. +++ +++@cindex Readline application name +++@value{GDBN} sets the Readline application name to @samp{gdb}. This +++is useful for conditions in @file{.inputrc}. +++ +++@cindex operate-and-get-next +++@value{GDBN} defines a bindable Readline command, +++@code{operate-and-get-next}. This is bound to @kbd{C-o} by default. +++This command accepts the current line for execution and fetches the +++next line relative to the current line from the history for editing. +++Any argument is ignored. +++ +++@node Command History +++@section Command History +++@cindex command history +++ +++@value{GDBN} can keep track of the commands you type during your +++debugging sessions, so that you can be certain of precisely what +++happened. Use these commands to manage the @value{GDBN} command +++history facility. +++ +++@value{GDBN} uses the @sc{gnu} History library, a part of the Readline +++package, to provide the history facility. +++@ifset SYSTEM_READLINE +++@xref{Using History Interactively, , , history, GNU History Library}, +++@end ifset +++@ifclear SYSTEM_READLINE +++@xref{Using History Interactively}, +++@end ifclear +++for the detailed description of the History library. +++ +++To issue a command to @value{GDBN} without affecting certain aspects of +++the state which is seen by users, prefix it with @samp{server } +++(@pxref{Server Prefix}). This +++means that this command will not affect the command history, nor will it +++affect @value{GDBN}'s notion of which command to repeat if @key{RET} is +++pressed on a line by itself. +++ +++@cindex @code{server}, command prefix +++The server prefix does not affect the recording of values into the value +++history; to print a value without recording it into the value history, +++use the @code{output} command instead of the @code{print} command. +++ +++Here is the description of @value{GDBN} commands related to command +++history. +++ +++@table @code +++@cindex history substitution +++@cindex history file +++@kindex set history filename +++@cindex @env{GDBHISTFILE}, environment variable +++@item set history filename @r{[}@var{fname}@r{]} +++Set the name of the @value{GDBN} command history file to @var{fname}. +++This is the file where @value{GDBN} reads an initial command history +++list, and where it writes the command history from this session when it +++exits. You can access this list through history expansion or through +++the history command editing characters listed below. This file defaults +++to the value of the environment variable @code{GDBHISTFILE}, or to +++@file{./.gdb_history} (@file{./_gdb_history} on MS-DOS) if this variable +++is not set. +++ +++The @code{GDBHISTFILE} environment variable is read after processing +++any @value{GDBN} initialization files (@pxref{Startup}) and after +++processing any commands passed using command line options (for +++example, @code{-ex}). +++ +++If the @var{fname} argument is not given, or if the @code{GDBHISTFILE} +++is the empty string then @value{GDBN} will neither try to load an +++existing history file, nor will it try to save the history on exit. +++ +++@cindex save command history +++@kindex set history save +++@item set history save +++@itemx set history save on +++Record command history in a file, whose name may be specified with the +++@code{set history filename} command. By default, this option is +++disabled. The command history will be recorded when @value{GDBN} +++exits. If @code{set history filename} is set to the empty string then +++history saving is disabled, even when @code{set history save} is +++@code{on}. +++ +++@item set history save off +++Don't record the command history into the file specified by @code{set +++history filename} when @value{GDBN} exits. +++ +++@cindex history size +++@kindex set history size +++@cindex @env{GDBHISTSIZE}, environment variable +++@item set history size @var{size} +++@itemx set history size unlimited +++Set the number of commands which @value{GDBN} keeps in its history list. +++This defaults to the value of the environment variable @env{GDBHISTSIZE}, or +++to 256 if this variable is not set. Non-numeric values of @env{GDBHISTSIZE} +++are ignored. If @var{size} is @code{unlimited} or if @env{GDBHISTSIZE} is +++either a negative number or the empty string, then the number of commands +++@value{GDBN} keeps in the history list is unlimited. +++ +++The @code{GDBHISTSIZE} environment variable is read after processing +++any @value{GDBN} initialization files (@pxref{Startup}) and after +++processing any commands passed using command line options (for +++example, @code{-ex}). +++ +++@cindex remove duplicate history +++@kindex set history remove-duplicates +++@item set history remove-duplicates @var{count} +++@itemx set history remove-duplicates unlimited +++Control the removal of duplicate history entries in the command history list. +++If @var{count} is non-zero, @value{GDBN} will look back at the last @var{count} +++history entries and remove the first entry that is a duplicate of the current +++entry being added to the command history list. If @var{count} is +++@code{unlimited} then this lookbehind is unbounded. If @var{count} is 0, then +++removal of duplicate history entries is disabled. +++ +++Only history entries added during the current session are considered for +++removal. This option is set to 0 by default. +++ +++@end table +++ +++History expansion assigns special meaning to the character @kbd{!}. +++@ifset SYSTEM_READLINE +++@xref{Event Designators, , , history, GNU History Library}, +++@end ifset +++@ifclear SYSTEM_READLINE +++@xref{Event Designators}, +++@end ifclear +++for more details. +++ +++@cindex history expansion, turn on/off +++Since @kbd{!} is also the logical not operator in C, history expansion +++is off by default. If you decide to enable history expansion with the +++@code{set history expansion on} command, you may sometimes need to +++follow @kbd{!} (when it is used as logical not, in an expression) with +++a space or a tab to prevent it from being expanded. The readline +++history facilities do not attempt substitution on the strings +++@kbd{!=} and @kbd{!(}, even when history expansion is enabled. +++ +++The commands to control history expansion are: +++ +++@table @code +++@item set history expansion on +++@itemx set history expansion +++@kindex set history expansion +++Enable history expansion. History expansion is off by default. +++ +++@item set history expansion off +++Disable history expansion. +++ +++@c @group +++@kindex show history +++@item show history +++@itemx show history filename +++@itemx show history save +++@itemx show history size +++@itemx show history expansion +++These commands display the state of the @value{GDBN} history parameters. +++@code{show history} by itself displays all four states. +++@c @end group +++@end table +++ +++@table @code +++@kindex show commands +++@cindex show last commands +++@cindex display command history +++@item show commands +++Display the last ten commands in the command history. +++ +++@item show commands @var{n} +++Print ten commands centered on command number @var{n}. +++ +++@item show commands + +++Print ten commands just after the commands last printed. +++@end table +++ +++@node Screen Size +++@section Screen Size +++@cindex size of screen +++@cindex screen size +++@cindex pagination +++@cindex page size +++@cindex pauses in output +++ +++Certain commands to @value{GDBN} may produce large amounts of +++information output to the screen. To help you read all of it, +++@value{GDBN} pauses and asks you for input at the end of each page of +++output. Type @key{RET} when you want to see one more page of output, +++@kbd{q} to discard the remaining output, or @kbd{c} to continue +++without paging for the rest of the current command. Also, the screen +++width setting determines when to wrap lines of output. Depending on +++what is being printed, @value{GDBN} tries to break the line at a +++readable place, rather than simply letting it overflow onto the +++following line. +++ +++Normally @value{GDBN} knows the size of the screen from the terminal +++driver software. For example, on Unix @value{GDBN} uses the termcap data base +++together with the value of the @code{TERM} environment variable and the +++@code{stty rows} and @code{stty cols} settings. If this is not correct, +++you can override it with the @code{set height} and @code{set +++width} commands: +++ +++@table @code +++@kindex set height +++@kindex set width +++@kindex show width +++@kindex show height +++@item set height @var{lpp} +++@itemx set height unlimited +++@itemx show height +++@itemx set width @var{cpl} +++@itemx set width unlimited +++@itemx show width +++These @code{set} commands specify a screen height of @var{lpp} lines and +++a screen width of @var{cpl} characters. The associated @code{show} +++commands display the current settings. +++ +++If you specify a height of either @code{unlimited} or zero lines, +++@value{GDBN} does not pause during output no matter how long the +++output is. This is useful if output is to a file or to an editor +++buffer. +++ +++Likewise, you can specify @samp{set width unlimited} or @samp{set +++width 0} to prevent @value{GDBN} from wrapping its output. +++ +++@item set pagination on +++@itemx set pagination off +++@kindex set pagination +++Turn the output pagination on or off; the default is on. Turning +++pagination off is the alternative to @code{set height unlimited}. Note that +++running @value{GDBN} with the @option{--batch} option (@pxref{Mode +++Options, -batch}) also automatically disables pagination. +++ +++@item show pagination +++@kindex show pagination +++Show the current pagination mode. +++@end table +++ +++@node Output Styling +++@section Output Styling +++@cindex styling +++@cindex colors +++ +++@kindex set style +++@kindex show style +++@value{GDBN} can style its output on a capable terminal. This is +++enabled by default on most systems, but disabled by default when in +++batch mode (@pxref{Mode Options}). Various style settings are available; +++and styles can also be disabled entirely. +++ +++@table @code +++@item set style enabled @samp{on|off} +++Enable or disable all styling. The default is host-dependent, with +++most hosts defaulting to @samp{on}. +++ +++@item show style enabled +++Show the current state of styling. +++ +++@item set style sources @samp{on|off} +++Enable or disable source code styling. This affects whether source +++code, such as the output of the @code{list} command, is styled. Note +++that source styling only works if styling in general is enabled, and +++if @value{GDBN} was linked with the GNU Source Highlight library. The +++default is @samp{on}. +++ +++@item show style sources +++Show the current state of source code styling. +++@end table +++ +++Subcommands of @code{set style} control specific forms of styling. +++These subcommands all follow the same pattern: each style-able object +++can be styled with a foreground color, a background color, and an +++intensity. +++ +++For example, the style of file names can be controlled using the +++@code{set style filename} group of commands: +++ +++@table @code +++@item set style filename background @var{color} +++Set the background to @var{color}. Valid colors are @samp{none} +++(meaning the terminal's default color), @samp{black}, @samp{red}, +++@samp{green}, @samp{yellow}, @samp{blue}, @samp{magenta}, @samp{cyan}, +++and@samp{white}. +++ +++@item set style filename foreground @var{color} +++Set the foreground to @var{color}. Valid colors are @samp{none} +++(meaning the terminal's default color), @samp{black}, @samp{red}, +++@samp{green}, @samp{yellow}, @samp{blue}, @samp{magenta}, @samp{cyan}, +++and@samp{white}. +++ +++@item set style filename intensity @var{value} +++Set the intensity to @var{value}. Valid intensities are @samp{normal} +++(the default), @samp{bold}, and @samp{dim}. +++@end table +++ +++The @code{show style} command and its subcommands are styling +++a style name in their output using its own style. +++So, use @command{show style} to see the complete list of styles, +++their characteristics and the visual aspect of each style. +++ +++The style-able objects are: +++@table @code +++@item filename +++Control the styling of file names. By default, this style's +++foreground color is green. +++ +++@item function +++Control the styling of function names. These are managed with the +++@code{set style function} family of commands. By default, this +++style's foreground color is yellow. +++ +++@item variable +++Control the styling of variable names. These are managed with the +++@code{set style variable} family of commands. By default, this style's +++foreground color is cyan. +++ +++@item address +++Control the styling of addresses. These are managed with the +++@code{set style address} family of commands. By default, this style's +++foreground color is blue. +++ +++@item title +++Control the styling of titles. These are managed with the +++@code{set style title} family of commands. By default, this style's +++intensity is bold. Commands are using the title style to improve +++the readability of large output. For example, the commands +++@command{apropos} and @command{help} are using the title style +++for the command names. +++ +++@item highlight +++Control the styling of highlightings. These are managed with the +++@code{set style highlight} family of commands. By default, this style's +++foreground color is red. Commands are using the highlight style to draw +++the user attention to some specific parts of their output. For example, +++the command @command{apropos -v REGEXP} uses the highlight style to +++mark the documentation parts matching @var{regexp}. +++ +++@item tui-border +++Control the styling of the TUI border. Note that, unlike other +++styling options, only the color of the border can be controlled via +++@code{set style}. This was done for compatibility reasons, as TUI +++controls to set the border's intensity predated the addition of +++general styling to @value{GDBN}. @xref{TUI Configuration}. +++ +++@item tui-active-border +++Control the styling of the active TUI border; that is, the TUI window +++that has the focus. +++ +++@end table +++ +++@node Numbers +++@section Numbers +++@cindex number representation +++@cindex entering numbers +++ +++You can always enter numbers in octal, decimal, or hexadecimal in +++@value{GDBN} by the usual conventions: octal numbers begin with +++@samp{0}, decimal numbers end with @samp{.}, and hexadecimal numbers +++begin with @samp{0x}. Numbers that neither begin with @samp{0} or +++@samp{0x}, nor end with a @samp{.} are, by default, entered in base +++10; likewise, the default display for numbers---when no particular +++format is specified---is base 10. You can change the default base for +++both input and output with the commands described below. +++ +++@table @code +++@kindex set input-radix +++@item set input-radix @var{base} +++Set the default base for numeric input. Supported choices +++for @var{base} are decimal 8, 10, or 16. The base must itself be +++specified either unambiguously or using the current input radix; for +++example, any of +++ +++@smallexample +++set input-radix 012 +++set input-radix 10. +++set input-radix 0xa +++@end smallexample +++ +++@noindent +++sets the input base to decimal. On the other hand, @samp{set input-radix 10} +++leaves the input radix unchanged, no matter what it was, since +++@samp{10}, being without any leading or trailing signs of its base, is +++interpreted in the current radix. Thus, if the current radix is 16, +++@samp{10} is interpreted in hex, i.e.@: as 16 decimal, which doesn't +++change the radix. +++ +++@kindex set output-radix +++@item set output-radix @var{base} +++Set the default base for numeric display. Supported choices +++for @var{base} are decimal 8, 10, or 16. The base must itself be +++specified either unambiguously or using the current input radix. +++ +++@kindex show input-radix +++@item show input-radix +++Display the current default base for numeric input. +++ +++@kindex show output-radix +++@item show output-radix +++Display the current default base for numeric display. +++ +++@item set radix @r{[}@var{base}@r{]} +++@itemx show radix +++@kindex set radix +++@kindex show radix +++These commands set and show the default base for both input and output +++of numbers. @code{set radix} sets the radix of input and output to +++the same base; without an argument, it resets the radix back to its +++default value of 10. +++ +++@end table +++ +++@node ABI +++@section Configuring the Current ABI +++ +++@value{GDBN} can determine the @dfn{ABI} (Application Binary Interface) of your +++application automatically. However, sometimes you need to override its +++conclusions. Use these commands to manage @value{GDBN}'s view of the +++current ABI. +++ +++@cindex OS ABI +++@kindex set osabi +++@kindex show osabi +++@cindex Newlib OS ABI and its influence on the longjmp handling +++ +++One @value{GDBN} configuration can debug binaries for multiple operating +++system targets, either via remote debugging or native emulation. +++@value{GDBN} will autodetect the @dfn{OS ABI} (Operating System ABI) in use, +++but you can override its conclusion using the @code{set osabi} command. +++One example where this is useful is in debugging of binaries which use +++an alternate C library (e.g.@: @sc{uClibc} for @sc{gnu}/Linux) which does +++not have the same identifying marks that the standard C library for your +++platform provides. +++ +++When @value{GDBN} is debugging the AArch64 architecture, it provides a +++``Newlib'' OS ABI. This is useful for handling @code{setjmp} and +++@code{longjmp} when debugging binaries that use the @sc{newlib} C library. +++The ``Newlib'' OS ABI can be selected by @code{set osabi Newlib}. +++ +++@table @code +++@item show osabi +++Show the OS ABI currently in use. +++ +++@item set osabi +++With no argument, show the list of registered available OS ABI's. +++ +++@item set osabi @var{abi} +++Set the current OS ABI to @var{abi}. +++@end table +++ +++@cindex float promotion +++ +++Generally, the way that an argument of type @code{float} is passed to a +++function depends on whether the function is prototyped. For a prototyped +++(i.e.@: ANSI/ISO style) function, @code{float} arguments are passed unchanged, +++according to the architecture's convention for @code{float}. For unprototyped +++(i.e.@: K&R style) functions, @code{float} arguments are first promoted to type +++@code{double} and then passed. +++ +++Unfortunately, some forms of debug information do not reliably indicate whether +++a function is prototyped. If @value{GDBN} calls a function that is not marked +++as prototyped, it consults @kbd{set coerce-float-to-double}. +++ +++@table @code +++@kindex set coerce-float-to-double +++@item set coerce-float-to-double +++@itemx set coerce-float-to-double on +++Arguments of type @code{float} will be promoted to @code{double} when passed +++to an unprototyped function. This is the default setting. +++ +++@item set coerce-float-to-double off +++Arguments of type @code{float} will be passed directly to unprototyped +++functions. +++ +++@kindex show coerce-float-to-double +++@item show coerce-float-to-double +++Show the current setting of promoting @code{float} to @code{double}. +++@end table +++ +++@kindex set cp-abi +++@kindex show cp-abi +++@value{GDBN} needs to know the ABI used for your program's C@t{++} +++objects. The correct C@t{++} ABI depends on which C@t{++} compiler was +++used to build your application. @value{GDBN} only fully supports +++programs with a single C@t{++} ABI; if your program contains code using +++multiple C@t{++} ABI's or if @value{GDBN} can not identify your +++program's ABI correctly, you can tell @value{GDBN} which ABI to use. +++Currently supported ABI's include ``gnu-v2'', for @code{g++} versions +++before 3.0, ``gnu-v3'', for @code{g++} versions 3.0 and later, and +++``hpaCC'' for the HP ANSI C@t{++} compiler. Other C@t{++} compilers may +++use the ``gnu-v2'' or ``gnu-v3'' ABI's as well. The default setting is +++``auto''. +++ +++@table @code +++@item show cp-abi +++Show the C@t{++} ABI currently in use. +++ +++@item set cp-abi +++With no argument, show the list of supported C@t{++} ABI's. +++ +++@item set cp-abi @var{abi} +++@itemx set cp-abi auto +++Set the current C@t{++} ABI to @var{abi}, or return to automatic detection. +++@end table +++ +++@node Auto-loading +++@section Automatically loading associated files +++@cindex auto-loading +++ +++@value{GDBN} sometimes reads files with commands and settings automatically, +++without being explicitly told so by the user. We call this feature +++@dfn{auto-loading}. While auto-loading is useful for automatically adapting +++@value{GDBN} to the needs of your project, it can sometimes produce unexpected +++results or introduce security risks (e.g., if the file comes from untrusted +++sources). +++ +++@menu +++* Init File in the Current Directory:: @samp{set/show/info auto-load local-gdbinit} +++* libthread_db.so.1 file:: @samp{set/show/info auto-load libthread-db} +++ +++* Auto-loading safe path:: @samp{set/show/info auto-load safe-path} +++* Auto-loading verbose mode:: @samp{set/show debug auto-load} +++@end menu +++ +++There are various kinds of files @value{GDBN} can automatically load. +++In addition to these files, @value{GDBN} supports auto-loading code written +++in various extension languages. @xref{Auto-loading extensions}. +++ +++Note that loading of these associated files (including the local @file{.gdbinit} +++file) requires accordingly configured @code{auto-load safe-path} +++(@pxref{Auto-loading safe path}). +++ +++For these reasons, @value{GDBN} includes commands and options to let you +++control when to auto-load files and which files should be auto-loaded. +++ +++@table @code +++@anchor{set auto-load off} +++@kindex set auto-load off +++@item set auto-load off +++Globally disable loading of all auto-loaded files. +++You may want to use this command with the @samp{-iex} option +++(@pxref{Option -init-eval-command}) such as: +++@smallexample +++$ @kbd{gdb -iex "set auto-load off" untrusted-executable corefile} +++@end smallexample +++ +++Be aware that system init file (@pxref{System-wide configuration}) +++and init files from your home directory (@pxref{Home Directory Init File}) +++still get read (as they come from generally trusted directories). +++To prevent @value{GDBN} from auto-loading even those init files, use the +++@option{-nx} option (@pxref{Mode Options}), in addition to +++@code{set auto-load no}. +++ +++@anchor{show auto-load} +++@kindex show auto-load +++@item show auto-load +++Show whether auto-loading of each specific @samp{auto-load} file(s) is enabled +++or disabled. +++ +++@smallexample +++(gdb) show auto-load +++gdb-scripts: Auto-loading of canned sequences of commands scripts is on. +++libthread-db: Auto-loading of inferior specific libthread_db is on. +++local-gdbinit: Auto-loading of .gdbinit script from current directory +++ is on. +++python-scripts: Auto-loading of Python scripts is on. +++safe-path: List of directories from which it is safe to auto-load files +++ is $debugdir:$datadir/auto-load. +++scripts-directory: List of directories from which to load auto-loaded scripts +++ is $debugdir:$datadir/auto-load. +++@end smallexample +++ +++@anchor{info auto-load} +++@kindex info auto-load +++@item info auto-load +++Print whether each specific @samp{auto-load} file(s) have been auto-loaded or +++not. +++ +++@smallexample +++(gdb) info auto-load +++gdb-scripts: +++Loaded Script +++Yes /home/user/gdb/gdb-gdb.gdb +++libthread-db: No auto-loaded libthread-db. +++local-gdbinit: Local .gdbinit file "/home/user/gdb/.gdbinit" has been +++ loaded. +++python-scripts: +++Loaded Script +++Yes /home/user/gdb/gdb-gdb.py +++@end smallexample +++@end table +++ +++These are @value{GDBN} control commands for the auto-loading: +++ +++@multitable @columnfractions .5 .5 +++@item @xref{set auto-load off}. +++@tab Disable auto-loading globally. +++@item @xref{show auto-load}. +++@tab Show setting of all kinds of files. +++@item @xref{info auto-load}. +++@tab Show state of all kinds of files. +++@item @xref{set auto-load gdb-scripts}. +++@tab Control for @value{GDBN} command scripts. +++@item @xref{show auto-load gdb-scripts}. +++@tab Show setting of @value{GDBN} command scripts. +++@item @xref{info auto-load gdb-scripts}. +++@tab Show state of @value{GDBN} command scripts. +++@item @xref{set auto-load python-scripts}. +++@tab Control for @value{GDBN} Python scripts. +++@item @xref{show auto-load python-scripts}. +++@tab Show setting of @value{GDBN} Python scripts. +++@item @xref{info auto-load python-scripts}. +++@tab Show state of @value{GDBN} Python scripts. +++@item @xref{set auto-load guile-scripts}. +++@tab Control for @value{GDBN} Guile scripts. +++@item @xref{show auto-load guile-scripts}. +++@tab Show setting of @value{GDBN} Guile scripts. +++@item @xref{info auto-load guile-scripts}. +++@tab Show state of @value{GDBN} Guile scripts. +++@item @xref{set auto-load scripts-directory}. +++@tab Control for @value{GDBN} auto-loaded scripts location. +++@item @xref{show auto-load scripts-directory}. +++@tab Show @value{GDBN} auto-loaded scripts location. +++@item @xref{add-auto-load-scripts-directory}. +++@tab Add directory for auto-loaded scripts location list. +++@item @xref{set auto-load local-gdbinit}. +++@tab Control for init file in the current directory. +++@item @xref{show auto-load local-gdbinit}. +++@tab Show setting of init file in the current directory. +++@item @xref{info auto-load local-gdbinit}. +++@tab Show state of init file in the current directory. +++@item @xref{set auto-load libthread-db}. +++@tab Control for thread debugging library. +++@item @xref{show auto-load libthread-db}. +++@tab Show setting of thread debugging library. +++@item @xref{info auto-load libthread-db}. +++@tab Show state of thread debugging library. +++@item @xref{set auto-load safe-path}. +++@tab Control directories trusted for automatic loading. +++@item @xref{show auto-load safe-path}. +++@tab Show directories trusted for automatic loading. +++@item @xref{add-auto-load-safe-path}. +++@tab Add directory trusted for automatic loading. +++@end multitable +++ +++@node Init File in the Current Directory +++@subsection Automatically loading init file in the current directory +++@cindex auto-loading init file in the current directory +++ +++By default, @value{GDBN} reads and executes the canned sequences of commands +++from init file (if any) in the current working directory, +++see @ref{Init File in the Current Directory during Startup}. +++ +++Note that loading of this local @file{.gdbinit} file also requires accordingly +++configured @code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++ +++@table @code +++@anchor{set auto-load local-gdbinit} +++@kindex set auto-load local-gdbinit +++@item set auto-load local-gdbinit [on|off] +++Enable or disable the auto-loading of canned sequences of commands +++(@pxref{Sequences}) found in init file in the current directory. +++ +++@anchor{show auto-load local-gdbinit} +++@kindex show auto-load local-gdbinit +++@item show auto-load local-gdbinit +++Show whether auto-loading of canned sequences of commands from init file in the +++current directory is enabled or disabled. +++ +++@anchor{info auto-load local-gdbinit} +++@kindex info auto-load local-gdbinit +++@item info auto-load local-gdbinit +++Print whether canned sequences of commands from init file in the +++current directory have been auto-loaded. +++@end table +++ +++@node libthread_db.so.1 file +++@subsection Automatically loading thread debugging library +++@cindex auto-loading libthread_db.so.1 +++ +++This feature is currently present only on @sc{gnu}/Linux native hosts. +++ +++@value{GDBN} reads in some cases thread debugging library from places specific +++to the inferior (@pxref{set libthread-db-search-path}). +++ +++The special @samp{libthread-db-search-path} entry @samp{$sdir} is processed +++without checking this @samp{set auto-load libthread-db} switch as system +++libraries have to be trusted in general. In all other cases of +++@samp{libthread-db-search-path} entries @value{GDBN} checks first if @samp{set +++auto-load libthread-db} is enabled before trying to open such thread debugging +++library. +++ +++Note that loading of this debugging library also requires accordingly configured +++@code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++ +++@table @code +++@anchor{set auto-load libthread-db} +++@kindex set auto-load libthread-db +++@item set auto-load libthread-db [on|off] +++Enable or disable the auto-loading of inferior specific thread debugging library. +++ +++@anchor{show auto-load libthread-db} +++@kindex show auto-load libthread-db +++@item show auto-load libthread-db +++Show whether auto-loading of inferior specific thread debugging library is +++enabled or disabled. +++ +++@anchor{info auto-load libthread-db} +++@kindex info auto-load libthread-db +++@item info auto-load libthread-db +++Print the list of all loaded inferior specific thread debugging libraries and +++for each such library print list of inferior @var{pid}s using it. +++@end table +++ +++@node Auto-loading safe path +++@subsection Security restriction for auto-loading +++@cindex auto-loading safe-path +++ +++As the files of inferior can come from untrusted source (such as submitted by +++an application user) @value{GDBN} does not always load any files automatically. +++@value{GDBN} provides the @samp{set auto-load safe-path} setting to list +++directories trusted for loading files not explicitly requested by user. +++Each directory can also be a shell wildcard pattern. +++ +++If the path is not set properly you will see a warning and the file will not +++get loaded: +++ +++@smallexample +++$ ./gdb -q ./gdb +++Reading symbols from /home/user/gdb/gdb... +++warning: File "/home/user/gdb/gdb-gdb.gdb" auto-loading has been +++ declined by your `auto-load safe-path' set +++ to "$debugdir:$datadir/auto-load". +++warning: File "/home/user/gdb/gdb-gdb.py" auto-loading has been +++ declined by your `auto-load safe-path' set +++ to "$debugdir:$datadir/auto-load". +++@end smallexample +++ +++@noindent +++To instruct @value{GDBN} to go ahead and use the init files anyway, +++invoke @value{GDBN} like this: +++ +++@smallexample +++$ gdb -q -iex "set auto-load safe-path /home/user/gdb" ./gdb +++@end smallexample +++ +++The list of trusted directories is controlled by the following commands: +++ +++@table @code +++@anchor{set auto-load safe-path} +++@kindex set auto-load safe-path +++@item set auto-load safe-path @r{[}@var{directories}@r{]} +++Set the list of directories (and their subdirectories) trusted for automatic +++loading and execution of scripts. You can also enter a specific trusted file. +++Each directory can also be a shell wildcard pattern; wildcards do not match +++directory separator - see @code{FNM_PATHNAME} for system function @code{fnmatch} +++(@pxref{Wildcard Matching, fnmatch, , libc, GNU C Library Reference Manual}). +++If you omit @var{directories}, @samp{auto-load safe-path} will be reset to +++its default value as specified during @value{GDBN} compilation. +++ +++The list of directories uses path separator (@samp{:} on GNU and Unix +++systems, @samp{;} on MS-Windows and MS-DOS) to separate directories, similarly +++to the @env{PATH} environment variable. +++ +++@anchor{show auto-load safe-path} +++@kindex show auto-load safe-path +++@item show auto-load safe-path +++Show the list of directories trusted for automatic loading and execution of +++scripts. +++ +++@anchor{add-auto-load-safe-path} +++@kindex add-auto-load-safe-path +++@item add-auto-load-safe-path +++Add an entry (or list of entries) to the list of directories trusted for +++automatic loading and execution of scripts. Multiple entries may be delimited +++by the host platform path separator in use. +++@end table +++ +++This variable defaults to what @code{--with-auto-load-dir} has been configured +++to (@pxref{with-auto-load-dir}). @file{$debugdir} and @file{$datadir} +++substitution applies the same as for @ref{set auto-load scripts-directory}. +++The default @code{set auto-load safe-path} value can be also overriden by +++@value{GDBN} configuration option @option{--with-auto-load-safe-path}. +++ +++Setting this variable to @file{/} disables this security protection, +++corresponding @value{GDBN} configuration option is +++@option{--without-auto-load-safe-path}. +++This variable is supposed to be set to the system directories writable by the +++system superuser only. Users can add their source directories in init files in +++their home directories (@pxref{Home Directory Init File}). See also deprecated +++init file in the current directory +++(@pxref{Init File in the Current Directory during Startup}). +++ +++To force @value{GDBN} to load the files it declined to load in the previous +++example, you could use one of the following ways: +++ +++@table @asis +++@item @file{~/.gdbinit}: @samp{add-auto-load-safe-path ~/src/gdb} +++Specify this trusted directory (or a file) as additional component of the list. +++You have to specify also any existing directories displayed by +++by @samp{show auto-load safe-path} (such as @samp{/usr:/bin} in this example). +++ +++@item @kbd{gdb -iex "set auto-load safe-path /usr:/bin:~/src/gdb" @dots{}} +++Specify this directory as in the previous case but just for a single +++@value{GDBN} session. +++ +++@item @kbd{gdb -iex "set auto-load safe-path /" @dots{}} +++Disable auto-loading safety for a single @value{GDBN} session. +++This assumes all the files you debug during this @value{GDBN} session will come +++from trusted sources. +++ +++@item @kbd{./configure --without-auto-load-safe-path} +++During compilation of @value{GDBN} you may disable any auto-loading safety. +++This assumes all the files you will ever debug with this @value{GDBN} come from +++trusted sources. +++@end table +++ +++On the other hand you can also explicitly forbid automatic files loading which +++also suppresses any such warning messages: +++ +++@table @asis +++@item @kbd{gdb -iex "set auto-load no" @dots{}} +++You can use @value{GDBN} command-line option for a single @value{GDBN} session. +++ +++@item @file{~/.gdbinit}: @samp{set auto-load no} +++Disable auto-loading globally for the user +++(@pxref{Home Directory Init File}). While it is improbable, you could also +++use system init file instead (@pxref{System-wide configuration}). +++@end table +++ +++This setting applies to the file names as entered by user. If no entry matches +++@value{GDBN} tries as a last resort to also resolve all the file names into +++their canonical form (typically resolving symbolic links) and compare the +++entries again. @value{GDBN} already canonicalizes most of the filenames on its +++own before starting the comparison so a canonical form of directories is +++recommended to be entered. +++ +++@node Auto-loading verbose mode +++@subsection Displaying files tried for auto-load +++@cindex auto-loading verbose mode +++ +++For better visibility of all the file locations where you can place scripts to +++be auto-loaded with inferior --- or to protect yourself against accidental +++execution of untrusted scripts --- @value{GDBN} provides a feature for printing +++all the files attempted to be loaded. Both existing and non-existing files may +++be printed. +++ +++For example the list of directories from which it is safe to auto-load files +++(@pxref{Auto-loading safe path}) applies also to canonicalized filenames which +++may not be too obvious while setting it up. +++ +++@smallexample +++(gdb) set debug auto-load on +++(gdb) file ~/src/t/true +++auto-load: Loading canned sequences of commands script "/tmp/true-gdb.gdb" +++ for objfile "/tmp/true". +++auto-load: Updating directories of "/usr:/opt". +++auto-load: Using directory "/usr". +++auto-load: Using directory "/opt". +++warning: File "/tmp/true-gdb.gdb" auto-loading has been declined +++ by your `auto-load safe-path' set to "/usr:/opt". +++@end smallexample +++ +++@table @code +++@anchor{set debug auto-load} +++@kindex set debug auto-load +++@item set debug auto-load [on|off] +++Set whether to print the filenames attempted to be auto-loaded. +++ +++@anchor{show debug auto-load} +++@kindex show debug auto-load +++@item show debug auto-load +++Show whether printing of the filenames attempted to be auto-loaded is turned +++on or off. +++@end table +++ +++@node Messages/Warnings +++@section Optional Warnings and Messages +++ +++@cindex verbose operation +++@cindex optional warnings +++By default, @value{GDBN} is silent about its inner workings. If you are +++running on a slow machine, you may want to use the @code{set verbose} +++command. This makes @value{GDBN} tell you when it does a lengthy +++internal operation, so you will not think it has crashed. +++ +++Currently, the messages controlled by @code{set verbose} are those +++which announce that the symbol table for a source file is being read; +++see @code{symbol-file} in @ref{Files, ,Commands to Specify Files}. +++ +++@table @code +++@kindex set verbose +++@item set verbose on +++Enables @value{GDBN} output of certain informational messages. +++ +++@item set verbose off +++Disables @value{GDBN} output of certain informational messages. +++ +++@kindex show verbose +++@item show verbose +++Displays whether @code{set verbose} is on or off. +++@end table +++ +++By default, if @value{GDBN} encounters bugs in the symbol table of an +++object file, it is silent; but if you are debugging a compiler, you may +++find this information useful (@pxref{Symbol Errors, ,Errors Reading +++Symbol Files}). +++ +++@table @code +++ +++@kindex set complaints +++@item set complaints @var{limit} +++Permits @value{GDBN} to output @var{limit} complaints about each type of +++unusual symbols before becoming silent about the problem. Set +++@var{limit} to zero to suppress all complaints; set it to a large number +++to prevent complaints from being suppressed. +++ +++@kindex show complaints +++@item show complaints +++Displays how many symbol complaints @value{GDBN} is permitted to produce. +++ +++@end table +++ +++@anchor{confirmation requests} +++By default, @value{GDBN} is cautious, and asks what sometimes seems to be a +++lot of stupid questions to confirm certain commands. For example, if +++you try to run a program which is already running: +++ +++@smallexample +++(@value{GDBP}) run +++The program being debugged has been started already. +++Start it from the beginning? (y or n) +++@end smallexample +++ +++If you are willing to unflinchingly face the consequences of your own +++commands, you can disable this ``feature'': +++ +++@table @code +++ +++@kindex set confirm +++@cindex flinching +++@cindex confirmation +++@cindex stupid questions +++@item set confirm off +++Disables confirmation requests. Note that running @value{GDBN} with +++the @option{--batch} option (@pxref{Mode Options, -batch}) also +++automatically disables confirmation requests. +++ +++@item set confirm on +++Enables confirmation requests (the default). +++ +++@kindex show confirm +++@item show confirm +++Displays state of confirmation requests. +++ +++@end table +++ +++@cindex command tracing +++If you need to debug user-defined commands or sourced files you may find it +++useful to enable @dfn{command tracing}. In this mode each command will be +++printed as it is executed, prefixed with one or more @samp{+} symbols, the +++quantity denoting the call depth of each command. +++ +++@table @code +++@kindex set trace-commands +++@cindex command scripts, debugging +++@item set trace-commands on +++Enable command tracing. +++@item set trace-commands off +++Disable command tracing. +++@item show trace-commands +++Display the current state of command tracing. +++@end table +++ +++@node Debugging Output +++@section Optional Messages about Internal Happenings +++@cindex optional debugging messages +++ +++@value{GDBN} has commands that enable optional debugging messages from +++various @value{GDBN} subsystems; normally these commands are of +++interest to @value{GDBN} maintainers, or when reporting a bug. This +++section documents those commands. +++ +++@table @code +++@kindex set exec-done-display +++@item set exec-done-display +++Turns on or off the notification of asynchronous commands' +++completion. When on, @value{GDBN} will print a message when an +++asynchronous command finishes its execution. The default is off. +++@kindex show exec-done-display +++@item show exec-done-display +++Displays the current setting of asynchronous command completion +++notification. +++@kindex set debug +++@cindex ARM AArch64 +++@item set debug aarch64 +++Turns on or off display of debugging messages related to ARM AArch64. +++The default is off. +++@kindex show debug +++@item show debug aarch64 +++Displays the current state of displaying debugging messages related to +++ARM AArch64. +++@cindex gdbarch debugging info +++@cindex architecture debugging info +++@item set debug arch +++Turns on or off display of gdbarch debugging info. The default is off +++@item show debug arch +++Displays the current state of displaying gdbarch debugging info. +++@item set debug aix-solib +++@cindex AIX shared library debugging +++Control display of debugging messages from the AIX shared library +++support module. The default is off. +++@item show debug aix-thread +++Show the current state of displaying AIX shared library debugging messages. +++@item set debug aix-thread +++@cindex AIX threads +++Display debugging messages about inner workings of the AIX thread +++module. +++@item show debug aix-thread +++Show the current state of AIX thread debugging info display. +++@item set debug check-physname +++@cindex physname +++Check the results of the ``physname'' computation. When reading DWARF +++debugging information for C@t{++}, @value{GDBN} attempts to compute +++each entity's name. @value{GDBN} can do this computation in two +++different ways, depending on exactly what information is present. +++When enabled, this setting causes @value{GDBN} to compute the names +++both ways and display any discrepancies. +++@item show debug check-physname +++Show the current state of ``physname'' checking. +++@item set debug coff-pe-read +++@cindex COFF/PE exported symbols +++Control display of debugging messages related to reading of COFF/PE +++exported symbols. The default is off. +++@item show debug coff-pe-read +++Displays the current state of displaying debugging messages related to +++reading of COFF/PE exported symbols. +++@item set debug dwarf-die +++@cindex DWARF DIEs +++Dump DWARF DIEs after they are read in. +++The value is the number of nesting levels to print. +++A value of zero turns off the display. +++@item show debug dwarf-die +++Show the current state of DWARF DIE debugging. +++@item set debug dwarf-line +++@cindex DWARF Line Tables +++Turns on or off display of debugging messages related to reading +++DWARF line tables. The default is 0 (off). +++A value of 1 provides basic information. +++A value greater than 1 provides more verbose information. +++@item show debug dwarf-line +++Show the current state of DWARF line table debugging. +++@item set debug dwarf-read +++@cindex DWARF Reading +++Turns on or off display of debugging messages related to reading +++DWARF debug info. The default is 0 (off). +++A value of 1 provides basic information. +++A value greater than 1 provides more verbose information. +++@item show debug dwarf-read +++Show the current state of DWARF reader debugging. +++@item set debug displaced +++@cindex displaced stepping debugging info +++Turns on or off display of @value{GDBN} debugging info for the +++displaced stepping support. The default is off. +++@item show debug displaced +++Displays the current state of displaying @value{GDBN} debugging info +++related to displaced stepping. +++@item set debug event +++@cindex event debugging info +++Turns on or off display of @value{GDBN} event debugging info. The +++default is off. +++@item show debug event +++Displays the current state of displaying @value{GDBN} event debugging +++info. +++@item set debug expression +++@cindex expression debugging info +++Turns on or off display of debugging info about @value{GDBN} +++expression parsing. The default is off. +++@item show debug expression +++Displays the current state of displaying debugging info about +++@value{GDBN} expression parsing. +++@item set debug fbsd-lwp +++@cindex FreeBSD LWP debug messages +++Turns on or off debugging messages from the FreeBSD LWP debug support. +++@item show debug fbsd-lwp +++Show the current state of FreeBSD LWP debugging messages. +++@item set debug fbsd-nat +++@cindex FreeBSD native target debug messages +++Turns on or off debugging messages from the FreeBSD native target. +++@item show debug fbsd-nat +++Show the current state of FreeBSD native target debugging messages. +++@item set debug frame +++@cindex frame debugging info +++Turns on or off display of @value{GDBN} frame debugging info. The +++default is off. +++@item show debug frame +++Displays the current state of displaying @value{GDBN} frame debugging +++info. +++@item set debug gnu-nat +++@cindex @sc{gnu}/Hurd debug messages +++Turn on or off debugging messages from the @sc{gnu}/Hurd debug support. +++@item show debug gnu-nat +++Show the current state of @sc{gnu}/Hurd debugging messages. +++@item set debug infrun +++@cindex inferior debugging info +++Turns on or off display of @value{GDBN} debugging info for running the inferior. +++The default is off. @file{infrun.c} contains GDB's runtime state machine used +++for implementing operations such as single-stepping the inferior. +++@item show debug infrun +++Displays the current state of @value{GDBN} inferior debugging. +++@item set debug jit +++@cindex just-in-time compilation, debugging messages +++Turn on or off debugging messages from JIT debug support. +++@item show debug jit +++Displays the current state of @value{GDBN} JIT debugging. +++@item set debug lin-lwp +++@cindex @sc{gnu}/Linux LWP debug messages +++@cindex Linux lightweight processes +++Turn on or off debugging messages from the Linux LWP debug support. +++@item show debug lin-lwp +++Show the current state of Linux LWP debugging messages. +++@item set debug linux-namespaces +++@cindex @sc{gnu}/Linux namespaces debug messages +++Turn on or off debugging messages from the Linux namespaces debug support. +++@item show debug linux-namespaces +++Show the current state of Linux namespaces debugging messages. +++@item set debug mach-o +++@cindex Mach-O symbols processing +++Control display of debugging messages related to Mach-O symbols +++processing. The default is off. +++@item show debug mach-o +++Displays the current state of displaying debugging messages related to +++reading of COFF/PE exported symbols. +++@item set debug notification +++@cindex remote async notification debugging info +++Turn on or off debugging messages about remote async notification. +++The default is off. +++@item show debug notification +++Displays the current state of remote async notification debugging messages. +++@item set debug observer +++@cindex observer debugging info +++Turns on or off display of @value{GDBN} observer debugging. This +++includes info such as the notification of observable events. +++@item show debug observer +++Displays the current state of observer debugging. +++@item set debug overload +++@cindex C@t{++} overload debugging info +++Turns on or off display of @value{GDBN} C@t{++} overload debugging +++info. This includes info such as ranking of functions, etc. The default +++is off. +++@item show debug overload +++Displays the current state of displaying @value{GDBN} C@t{++} overload +++debugging info. +++@cindex expression parser, debugging info +++@cindex debug expression parser +++@item set debug parser +++Turns on or off the display of expression parser debugging output. +++Internally, this sets the @code{yydebug} variable in the expression +++parser. @xref{Tracing, , Tracing Your Parser, bison, Bison}, for +++details. The default is off. +++@item show debug parser +++Show the current state of expression parser debugging. +++@cindex packets, reporting on stdout +++@cindex serial connections, debugging +++@cindex debug remote protocol +++@cindex remote protocol debugging +++@cindex display remote packets +++@item set debug remote +++Turns on or off display of reports on all packets sent back and forth across +++the serial line to the remote machine. The info is printed on the +++@value{GDBN} standard output stream. The default is off. +++@item show debug remote +++Displays the state of display of remote packets. +++ +++@item set debug remote-packet-max-chars +++Sets the maximum number of characters to display for each remote packet when +++@code{set debug remote} is on. This is useful to prevent @value{GDBN} from +++displaying lengthy remote packets and polluting the console. +++ +++The default value is @code{512}, which means @value{GDBN} will truncate each +++remote packet after 512 bytes. +++ +++Setting this option to @code{unlimited} will disable truncation and will output +++the full length of the remote packets. +++@item show debug remote-packet-max-chars +++Displays the number of bytes to output for remote packet debugging. +++ +++@item set debug separate-debug-file +++Turns on or off display of debug output about separate debug file search. +++@item show debug separate-debug-file +++Displays the state of separate debug file search debug output. +++ +++@item set debug serial +++Turns on or off display of @value{GDBN} serial debugging info. The +++default is off. +++@item show debug serial +++Displays the current state of displaying @value{GDBN} serial debugging +++info. +++@item set debug solib-frv +++@cindex FR-V shared-library debugging +++Turn on or off debugging messages for FR-V shared-library code. +++@item show debug solib-frv +++Display the current state of FR-V shared-library code debugging +++messages. +++@item set debug symbol-lookup +++@cindex symbol lookup +++Turns on or off display of debugging messages related to symbol lookup. +++The default is 0 (off). +++A value of 1 provides basic information. +++A value greater than 1 provides more verbose information. +++@item show debug symbol-lookup +++Show the current state of symbol lookup debugging messages. +++@item set debug symfile +++@cindex symbol file functions +++Turns on or off display of debugging messages related to symbol file functions. +++The default is off. @xref{Files}. +++@item show debug symfile +++Show the current state of symbol file debugging messages. +++@item set debug symtab-create +++@cindex symbol table creation +++Turns on or off display of debugging messages related to symbol table creation. +++The default is 0 (off). +++A value of 1 provides basic information. +++A value greater than 1 provides more verbose information. +++@item show debug symtab-create +++Show the current state of symbol table creation debugging. +++@item set debug target +++@cindex target debugging info +++Turns on or off display of @value{GDBN} target debugging info. This info +++includes what is going on at the target level of GDB, as it happens. The +++default is 0. Set it to 1 to track events, and to 2 to also track the +++value of large memory transfers. +++@item show debug target +++Displays the current state of displaying @value{GDBN} target debugging +++info. +++@item set debug timestamp +++@cindex timestamping debugging info +++Turns on or off display of timestamps with @value{GDBN} debugging info. +++When enabled, seconds and microseconds are displayed before each debugging +++message. +++@item show debug timestamp +++Displays the current state of displaying timestamps with @value{GDBN} +++debugging info. +++@item set debug varobj +++@cindex variable object debugging info +++Turns on or off display of @value{GDBN} variable object debugging +++info. The default is off. +++@item show debug varobj +++Displays the current state of displaying @value{GDBN} variable object +++debugging info. +++@item set debug xml +++@cindex XML parser debugging +++Turn on or off debugging messages for built-in XML parsers. +++@item show debug xml +++Displays the current state of XML debugging messages. +++@end table +++ +++@node Other Misc Settings +++@section Other Miscellaneous Settings +++@cindex miscellaneous settings +++ +++@table @code +++@kindex set interactive-mode +++@item set interactive-mode +++If @code{on}, forces @value{GDBN} to assume that GDB was started +++in a terminal. In practice, this means that @value{GDBN} should wait +++for the user to answer queries generated by commands entered at +++the command prompt. If @code{off}, forces @value{GDBN} to operate +++in the opposite mode, and it uses the default answers to all queries. +++If @code{auto} (the default), @value{GDBN} tries to determine whether +++its standard input is a terminal, and works in interactive-mode if it +++is, non-interactively otherwise. +++ +++In the vast majority of cases, the debugger should be able to guess +++correctly which mode should be used. But this setting can be useful +++in certain specific cases, such as running a MinGW @value{GDBN} +++inside a cygwin window. +++ +++@kindex show interactive-mode +++@item show interactive-mode +++Displays whether the debugger is operating in interactive mode or not. +++@end table +++ +++@node Extending GDB +++@chapter Extending @value{GDBN} +++@cindex extending GDB +++ +++@value{GDBN} provides several mechanisms for extension. +++@value{GDBN} also provides the ability to automatically load +++extensions when it reads a file for debugging. This allows the +++user to automatically customize @value{GDBN} for the program +++being debugged. +++ +++@menu +++* Sequences:: Canned Sequences of @value{GDBN} Commands +++* Python:: Extending @value{GDBN} using Python +++* Guile:: Extending @value{GDBN} using Guile +++* Auto-loading extensions:: Automatically loading extensions +++* Multiple Extension Languages:: Working with multiple extension languages +++* Aliases:: Creating new spellings of existing commands +++@end menu +++ +++To facilitate the use of extension languages, @value{GDBN} is capable +++of evaluating the contents of a file. When doing so, @value{GDBN} +++can recognize which extension language is being used by looking at +++the filename extension. Files with an unrecognized filename extension +++are always treated as a @value{GDBN} Command Files. +++@xref{Command Files,, Command files}. +++ +++You can control how @value{GDBN} evaluates these files with the following +++setting: +++ +++@table @code +++@kindex set script-extension +++@kindex show script-extension +++@item set script-extension off +++All scripts are always evaluated as @value{GDBN} Command Files. +++ +++@item set script-extension soft +++The debugger determines the scripting language based on filename +++extension. If this scripting language is supported, @value{GDBN} +++evaluates the script using that language. Otherwise, it evaluates +++the file as a @value{GDBN} Command File. +++ +++@item set script-extension strict +++The debugger determines the scripting language based on filename +++extension, and evaluates the script using that language. If the +++language is not supported, then the evaluation fails. +++ +++@item show script-extension +++Display the current value of the @code{script-extension} option. +++ +++@end table +++ +++@ifset SYSTEM_GDBINIT_DIR +++This setting is not used for files in the system-wide gdbinit directory. +++Files in that directory must have an extension matching their language, +++or have a @file{.gdb} extension to be interpreted as regular @value{GDBN} +++commands. @xref{Startup}. +++@end ifset +++ +++@node Sequences +++@section Canned Sequences of Commands +++ +++Aside from breakpoint commands (@pxref{Break Commands, ,Breakpoint +++Command Lists}), @value{GDBN} provides two ways to store sequences of +++commands for execution as a unit: user-defined commands and command +++files. +++ +++@menu +++* Define:: How to define your own commands +++* Hooks:: Hooks for user-defined commands +++* Command Files:: How to write scripts of commands to be stored in a file +++* Output:: Commands for controlled output +++* Auto-loading sequences:: Controlling auto-loaded command files +++@end menu +++ +++@node Define +++@subsection User-defined Commands +++ +++@cindex user-defined command +++@cindex arguments, to user-defined commands +++A @dfn{user-defined command} is a sequence of @value{GDBN} commands to +++which you assign a new name as a command. This is done with the +++@code{define} command. User commands may accept an unlimited number of arguments +++separated by whitespace. Arguments are accessed within the user command +++via @code{$arg0@dots{}$argN}. A trivial example: +++ +++@smallexample +++define adder +++ print $arg0 + $arg1 + $arg2 +++end +++@end smallexample +++ +++@noindent +++To execute the command use: +++ +++@smallexample +++adder 1 2 3 +++@end smallexample +++ +++@noindent +++This defines the command @code{adder}, which prints the sum of +++its three arguments. Note the arguments are text substitutions, so they may +++reference variables, use complex expressions, or even perform inferior +++functions calls. +++ +++@cindex argument count in user-defined commands +++@cindex how many arguments (user-defined commands) +++In addition, @code{$argc} may be used to find out how many arguments have +++been passed. +++ +++@smallexample +++define adder +++ if $argc == 2 +++ print $arg0 + $arg1 +++ end +++ if $argc == 3 +++ print $arg0 + $arg1 + $arg2 +++ end +++end +++@end smallexample +++ +++Combining with the @code{eval} command (@pxref{eval}) makes it easier +++to process a variable number of arguments: +++ +++@smallexample +++define adder +++ set $i = 0 +++ set $sum = 0 +++ while $i < $argc +++ eval "set $sum = $sum + $arg%d", $i +++ set $i = $i + 1 +++ end +++ print $sum +++end +++@end smallexample +++ +++@table @code +++ +++@kindex define +++@item define @var{commandname} +++Define a command named @var{commandname}. If there is already a command +++by that name, you are asked to confirm that you want to redefine it. +++The argument @var{commandname} may be a bare command name consisting of letters, +++numbers, dashes, dots, and underscores. It may also start with any +++predefined or user-defined prefix command. +++For example, @samp{define target my-target} creates +++a user-defined @samp{target my-target} command. +++ +++The definition of the command is made up of other @value{GDBN} command lines, +++which are given following the @code{define} command. The end of these +++commands is marked by a line containing @code{end}. +++ +++@kindex document +++@kindex end@r{ (user-defined commands)} +++@item document @var{commandname} +++Document the user-defined command @var{commandname}, so that it can be +++accessed by @code{help}. The command @var{commandname} must already be +++defined. This command reads lines of documentation just as @code{define} +++reads the lines of the command definition, ending with @code{end}. +++After the @code{document} command is finished, @code{help} on command +++@var{commandname} displays the documentation you have written. +++ +++You may use the @code{document} command again to change the +++documentation of a command. Redefining the command with @code{define} +++does not change the documentation. +++ +++@kindex define-prefix +++@item define-prefix @var{commandname} +++Define or mark the command @var{commandname} as a user-defined prefix +++command. Once marked, @var{commandname} can be used as prefix command +++by the @code{define} command. +++Note that @code{define-prefix} can be used with a not yet defined +++@var{commandname}. In such a case, @var{commandname} is defined as +++an empty user-defined command. +++In case you redefine a command that was marked as a user-defined +++prefix command, the subcommands of the redefined command are kept +++(and @value{GDBN} indicates so to the user). +++ +++Example: +++@example +++(gdb) define-prefix abc +++(gdb) define-prefix abc def +++(gdb) define abc def +++Type commands for definition of "abc def". +++End with a line saying just "end". +++>echo command initial def\n +++>end +++(gdb) define abc def ghi +++Type commands for definition of "abc def ghi". +++End with a line saying just "end". +++>echo command ghi\n +++>end +++(gdb) define abc def +++Keeping subcommands of prefix command "def". +++Redefine command "def"? (y or n) y +++Type commands for definition of "abc def". +++End with a line saying just "end". +++>echo command def\n +++>end +++(gdb) abc def ghi +++command ghi +++(gdb) abc def +++command def +++(gdb) +++@end example +++ +++@kindex dont-repeat +++@cindex don't repeat command +++@item dont-repeat +++Used inside a user-defined command, this tells @value{GDBN} that this +++command should not be repeated when the user hits @key{RET} +++(@pxref{Command Syntax, repeat last command}). +++ +++@kindex help user-defined +++@item help user-defined +++List all user-defined commands and all python commands defined in class +++COMMAND_USER. The first line of the documentation or docstring is +++included (if any). +++ +++@kindex show user +++@item show user +++@itemx show user @var{commandname} +++Display the @value{GDBN} commands used to define @var{commandname} (but +++not its documentation). If no @var{commandname} is given, display the +++definitions for all user-defined commands. +++This does not work for user-defined python commands. +++ +++@cindex infinite recursion in user-defined commands +++@kindex show max-user-call-depth +++@kindex set max-user-call-depth +++@item show max-user-call-depth +++@itemx set max-user-call-depth +++The value of @code{max-user-call-depth} controls how many recursion +++levels are allowed in user-defined commands before @value{GDBN} suspects an +++infinite recursion and aborts the command. +++This does not apply to user-defined python commands. +++@end table +++ +++In addition to the above commands, user-defined commands frequently +++use control flow commands, described in @ref{Command Files}. +++ +++When user-defined commands are executed, the +++commands of the definition are not printed. An error in any command +++stops execution of the user-defined command. +++ +++If used interactively, commands that would ask for confirmation proceed +++without asking when used inside a user-defined command. Many @value{GDBN} +++commands that normally print messages to say what they are doing omit the +++messages when used in a user-defined command. +++ +++@node Hooks +++@subsection User-defined Command Hooks +++@cindex command hooks +++@cindex hooks, for commands +++@cindex hooks, pre-command +++ +++@kindex hook +++You may define @dfn{hooks}, which are a special kind of user-defined +++command. Whenever you run the command @samp{foo}, if the user-defined +++command @samp{hook-foo} exists, it is executed (with no arguments) +++before that command. +++ +++@cindex hooks, post-command +++@kindex hookpost +++A hook may also be defined which is run after the command you executed. +++Whenever you run the command @samp{foo}, if the user-defined command +++@samp{hookpost-foo} exists, it is executed (with no arguments) after +++that command. Post-execution hooks may exist simultaneously with +++pre-execution hooks, for the same command. +++ +++It is valid for a hook to call the command which it hooks. If this +++occurs, the hook is not re-executed, thereby avoiding infinite recursion. +++ +++@c It would be nice if hookpost could be passed a parameter indicating +++@c if the command it hooks executed properly or not. FIXME! +++ +++@kindex stop@r{, a pseudo-command} +++In addition, a pseudo-command, @samp{stop} exists. Defining +++(@samp{hook-stop}) makes the associated commands execute every time +++execution stops in your program: before breakpoint commands are run, +++displays are printed, or the stack frame is printed. +++ +++For example, to ignore @code{SIGALRM} signals while +++single-stepping, but treat them normally during normal execution, +++you could define: +++ +++@smallexample +++define hook-stop +++handle SIGALRM nopass +++end +++ +++define hook-run +++handle SIGALRM pass +++end +++ +++define hook-continue +++handle SIGALRM pass +++end +++@end smallexample +++ +++As a further example, to hook at the beginning and end of the @code{echo} +++command, and to add extra text to the beginning and end of the message, +++you could define: +++ +++@smallexample +++define hook-echo +++echo <<<--- +++end +++ +++define hookpost-echo +++echo --->>>\n +++end +++ +++(@value{GDBP}) echo Hello World +++<<<---Hello World--->>> +++(@value{GDBP}) +++ +++@end smallexample +++ +++You can define a hook for any single-word command in @value{GDBN}, but +++not for command aliases; you should define a hook for the basic command +++name, e.g.@: @code{backtrace} rather than @code{bt}. +++@c FIXME! So how does Joe User discover whether a command is an alias +++@c or not? +++You can hook a multi-word command by adding @code{hook-} or +++@code{hookpost-} to the last word of the command, e.g.@: +++@samp{define target hook-remote} to add a hook to @samp{target remote}. +++ +++If an error occurs during the execution of your hook, execution of +++@value{GDBN} commands stops and @value{GDBN} issues a prompt +++(before the command that you actually typed had a chance to run). +++ +++If you try to define a hook which does not match any known command, you +++get a warning from the @code{define} command. +++ +++@node Command Files +++@subsection Command Files +++ +++@cindex command files +++@cindex scripting commands +++A command file for @value{GDBN} is a text file made of lines that are +++@value{GDBN} commands. Comments (lines starting with @kbd{#}) may +++also be included. An empty line in a command file does nothing; it +++does not mean to repeat the last command, as it would from the +++terminal. +++ +++You can request the execution of a command file with the @code{source} +++command. Note that the @code{source} command is also used to evaluate +++scripts that are not Command Files. The exact behavior can be configured +++using the @code{script-extension} setting. +++@xref{Extending GDB,, Extending GDB}. +++ +++@table @code +++@kindex source +++@cindex execute commands from a file +++@item source [-s] [-v] @var{filename} +++Execute the command file @var{filename}. +++@end table +++ +++The lines in a command file are generally executed sequentially, +++unless the order of execution is changed by one of the +++@emph{flow-control commands} described below. The commands are not +++printed as they are executed. An error in any command terminates +++execution of the command file and control is returned to the console. +++ +++@value{GDBN} first searches for @var{filename} in the current directory. +++If the file is not found there, and @var{filename} does not specify a +++directory, then @value{GDBN} also looks for the file on the source search path +++(specified with the @samp{directory} command); +++except that @file{$cdir} is not searched because the compilation directory +++is not relevant to scripts. +++ +++If @code{-s} is specified, then @value{GDBN} searches for @var{filename} +++on the search path even if @var{filename} specifies a directory. +++The search is done by appending @var{filename} to each element of the +++search path. So, for example, if @var{filename} is @file{mylib/myscript} +++and the search path contains @file{/home/user} then @value{GDBN} will +++look for the script @file{/home/user/mylib/myscript}. +++The search is also done if @var{filename} is an absolute path. +++For example, if @var{filename} is @file{/tmp/myscript} and +++the search path contains @file{/home/user} then @value{GDBN} will +++look for the script @file{/home/user/tmp/myscript}. +++For DOS-like systems, if @var{filename} contains a drive specification, +++it is stripped before concatenation. For example, if @var{filename} is +++@file{d:myscript} and the search path contains @file{c:/tmp} then @value{GDBN} +++will look for the script @file{c:/tmp/myscript}. +++ +++If @code{-v}, for verbose mode, is given then @value{GDBN} displays +++each command as it is executed. The option must be given before +++@var{filename}, and is interpreted as part of the filename anywhere else. +++ +++Commands that would ask for confirmation if used interactively proceed +++without asking when used in a command file. Many @value{GDBN} commands that +++normally print messages to say what they are doing omit the messages +++when called from command files. +++ +++@value{GDBN} also accepts command input from standard input. In this +++mode, normal output goes to standard output and error output goes to +++standard error. Errors in a command file supplied on standard input do +++not terminate execution of the command file---execution continues with +++the next command. +++ +++@smallexample +++gdb < cmds > log 2>&1 +++@end smallexample +++ +++(The syntax above will vary depending on the shell used.) This example +++will execute commands from the file @file{cmds}. All output and errors +++would be directed to @file{log}. +++ +++Since commands stored on command files tend to be more general than +++commands typed interactively, they frequently need to deal with +++complicated situations, such as different or unexpected values of +++variables and symbols, changes in how the program being debugged is +++built, etc. @value{GDBN} provides a set of flow-control commands to +++deal with these complexities. Using these commands, you can write +++complex scripts that loop over data structures, execute commands +++conditionally, etc. +++ +++@table @code +++@kindex if +++@kindex else +++@item if +++@itemx else +++This command allows to include in your script conditionally executed +++commands. The @code{if} command takes a single argument, which is an +++expression to evaluate. It is followed by a series of commands that +++are executed only if the expression is true (its value is nonzero). +++There can then optionally be an @code{else} line, followed by a series +++of commands that are only executed if the expression was false. The +++end of the list is marked by a line containing @code{end}. +++ +++@kindex while +++@item while +++This command allows to write loops. Its syntax is similar to +++@code{if}: the command takes a single argument, which is an expression +++to evaluate, and must be followed by the commands to execute, one per +++line, terminated by an @code{end}. These commands are called the +++@dfn{body} of the loop. The commands in the body of @code{while} are +++executed repeatedly as long as the expression evaluates to true. +++ +++@kindex loop_break +++@item loop_break +++This command exits the @code{while} loop in whose body it is included. +++Execution of the script continues after that @code{while}s @code{end} +++line. +++ +++@kindex loop_continue +++@item loop_continue +++This command skips the execution of the rest of the body of commands +++in the @code{while} loop in whose body it is included. Execution +++branches to the beginning of the @code{while} loop, where it evaluates +++the controlling expression. +++ +++@kindex end@r{ (if/else/while commands)} +++@item end +++Terminate the block of commands that are the body of @code{if}, +++@code{else}, or @code{while} flow-control commands. +++@end table +++ +++ +++@node Output +++@subsection Commands for Controlled Output +++ +++During the execution of a command file or a user-defined command, normal +++@value{GDBN} output is suppressed; the only output that appears is what is +++explicitly printed by the commands in the definition. This section +++describes three commands useful for generating exactly the output you +++want. +++ +++@table @code +++@kindex echo +++@item echo @var{text} +++@c I do not consider backslash-space a standard C escape sequence +++@c because it is not in ANSI. +++Print @var{text}. Nonprinting characters can be included in +++@var{text} using C escape sequences, such as @samp{\n} to print a +++newline. @strong{No newline is printed unless you specify one.} +++In addition to the standard C escape sequences, a backslash followed +++by a space stands for a space. This is useful for displaying a +++string with spaces at the beginning or the end, since leading and +++trailing spaces are otherwise trimmed from all arguments. +++To print @samp{@w{ }and foo =@w{ }}, use the command +++@samp{echo \@w{ }and foo = \@w{ }}. +++ +++A backslash at the end of @var{text} can be used, as in C, to continue +++the command onto subsequent lines. For example, +++ +++@smallexample +++echo This is some text\n\ +++which is continued\n\ +++onto several lines.\n +++@end smallexample +++ +++produces the same output as +++ +++@smallexample +++echo This is some text\n +++echo which is continued\n +++echo onto several lines.\n +++@end smallexample +++ +++@kindex output +++@item output @var{expression} +++Print the value of @var{expression} and nothing but that value: no +++newlines, no @samp{$@var{nn} = }. The value is not entered in the +++value history either. @xref{Expressions, ,Expressions}, for more information +++on expressions. +++ +++@item output/@var{fmt} @var{expression} +++Print the value of @var{expression} in format @var{fmt}. You can use +++the same formats as for @code{print}. @xref{Output Formats,,Output +++Formats}, for more information. +++ +++@kindex printf +++@item printf @var{template}, @var{expressions}@dots{} +++Print the values of one or more @var{expressions} under the control of +++the string @var{template}. To print several values, make +++@var{expressions} be a comma-separated list of individual expressions, +++which may be either numbers or pointers. Their values are printed as +++specified by @var{template}, exactly as a C program would do by +++executing the code below: +++ +++@smallexample +++printf (@var{template}, @var{expressions}@dots{}); +++@end smallexample +++ +++As in @code{C} @code{printf}, ordinary characters in @var{template} +++are printed verbatim, while @dfn{conversion specification} introduced +++by the @samp{%} character cause subsequent @var{expressions} to be +++evaluated, their values converted and formatted according to type and +++style information encoded in the conversion specifications, and then +++printed. +++ +++For example, you can print two values in hex like this: +++ +++@smallexample +++printf "foo, bar-foo = 0x%x, 0x%x\n", foo, bar-foo +++@end smallexample +++ +++@code{printf} supports all the standard @code{C} conversion +++specifications, including the flags and modifiers between the @samp{%} +++character and the conversion letter, with the following exceptions: +++ +++@itemize @bullet +++@item +++The argument-ordering modifiers, such as @samp{2$}, are not supported. +++ +++@item +++The modifier @samp{*} is not supported for specifying precision or +++width. +++ +++@item +++The @samp{'} flag (for separation of digits into groups according to +++@code{LC_NUMERIC'}) is not supported. +++ +++@item +++The type modifiers @samp{hh}, @samp{j}, @samp{t}, and @samp{z} are not +++supported. +++ +++@item +++The conversion letter @samp{n} (as in @samp{%n}) is not supported. +++ +++@item +++The conversion letters @samp{a} and @samp{A} are not supported. +++@end itemize +++ +++@noindent +++Note that the @samp{ll} type modifier is supported only if the +++underlying @code{C} implementation used to build @value{GDBN} supports +++the @code{long long int} type, and the @samp{L} type modifier is +++supported only if @code{long double} type is available. +++ +++As in @code{C}, @code{printf} supports simple backslash-escape +++sequences, such as @code{\n}, @samp{\t}, @samp{\\}, @samp{\"}, +++@samp{\a}, and @samp{\f}, that consist of backslash followed by a +++single character. Octal and hexadecimal escape sequences are not +++supported. +++ +++Additionally, @code{printf} supports conversion specifications for DFP +++(@dfn{Decimal Floating Point}) types using the following length modifiers +++together with a floating point specifier. +++letters: +++ +++@itemize @bullet +++@item +++@samp{H} for printing @code{Decimal32} types. +++ +++@item +++@samp{D} for printing @code{Decimal64} types. +++ +++@item +++@samp{DD} for printing @code{Decimal128} types. +++@end itemize +++ +++If the underlying @code{C} implementation used to build @value{GDBN} has +++support for the three length modifiers for DFP types, other modifiers +++such as width and precision will also be available for @value{GDBN} to use. +++ +++In case there is no such @code{C} support, no additional modifiers will be +++available and the value will be printed in the standard way. +++ +++Here's an example of printing DFP types using the above conversion letters: +++@smallexample +++printf "D32: %Hf - D64: %Df - D128: %DDf\n",1.2345df,1.2E10dd,1.2E1dl +++@end smallexample +++ +++@anchor{eval} +++@kindex eval +++@item eval @var{template}, @var{expressions}@dots{} +++Convert the values of one or more @var{expressions} under the control of +++the string @var{template} to a command line, and call it. +++ +++@end table +++ +++@node Auto-loading sequences +++@subsection Controlling auto-loading native @value{GDBN} scripts +++@cindex native script auto-loading +++ +++When a new object file is read (for example, due to the @code{file} +++command, or because the inferior has loaded a shared library), +++@value{GDBN} will look for the command file @file{@var{objfile}-gdb.gdb}. +++@xref{Auto-loading extensions}. +++ +++Auto-loading can be enabled or disabled, +++and the list of auto-loaded scripts can be printed. +++ +++@table @code +++@anchor{set auto-load gdb-scripts} +++@kindex set auto-load gdb-scripts +++@item set auto-load gdb-scripts [on|off] +++Enable or disable the auto-loading of canned sequences of commands scripts. +++ +++@anchor{show auto-load gdb-scripts} +++@kindex show auto-load gdb-scripts +++@item show auto-load gdb-scripts +++Show whether auto-loading of canned sequences of commands scripts is enabled or +++disabled. +++ +++@anchor{info auto-load gdb-scripts} +++@kindex info auto-load gdb-scripts +++@cindex print list of auto-loaded canned sequences of commands scripts +++@item info auto-load gdb-scripts [@var{regexp}] +++Print the list of all canned sequences of commands scripts that @value{GDBN} +++auto-loaded. +++@end table +++ +++If @var{regexp} is supplied only canned sequences of commands scripts with +++matching names are printed. +++ +++@c Python docs live in a separate file. +++@include python.texi +++ +++@c Guile docs live in a separate file. +++@include guile.texi +++ +++@node Auto-loading extensions +++@section Auto-loading extensions +++@cindex auto-loading extensions +++ +++@value{GDBN} provides two mechanisms for automatically loading extensions +++when a new object file is read (for example, due to the @code{file} +++command, or because the inferior has loaded a shared library): +++@file{@var{objfile}-gdb.@var{ext}} and the @code{.debug_gdb_scripts} +++section of modern file formats like ELF. +++ +++@menu +++* objfile-gdb.ext file: objfile-gdbdotext file. The @file{@var{objfile}-gdb.@var{ext}} file +++* .debug_gdb_scripts section: dotdebug_gdb_scripts section. The @code{.debug_gdb_scripts} section +++* Which flavor to choose?:: +++@end menu +++ +++The auto-loading feature is useful for supplying application-specific +++debugging commands and features. +++ +++Auto-loading can be enabled or disabled, +++and the list of auto-loaded scripts can be printed. +++See the @samp{auto-loading} section of each extension language +++for more information. +++For @value{GDBN} command files see @ref{Auto-loading sequences}. +++For Python files see @ref{Python Auto-loading}. +++ +++Note that loading of this script file also requires accordingly configured +++@code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++ +++@node objfile-gdbdotext file +++@subsection The @file{@var{objfile}-gdb.@var{ext}} file +++@cindex @file{@var{objfile}-gdb.gdb} +++@cindex @file{@var{objfile}-gdb.py} +++@cindex @file{@var{objfile}-gdb.scm} +++ +++When a new object file is read, @value{GDBN} looks for a file named +++@file{@var{objfile}-gdb.@var{ext}} (we call it @var{script-name} below), +++where @var{objfile} is the object file's name and +++where @var{ext} is the file extension for the extension language: +++ +++@table @code +++@item @file{@var{objfile}-gdb.gdb} +++GDB's own command language +++@item @file{@var{objfile}-gdb.py} +++Python +++@item @file{@var{objfile}-gdb.scm} +++Guile +++@end table +++ +++@var{script-name} is formed by ensuring that the file name of @var{objfile} +++is absolute, following all symlinks, and resolving @code{.} and @code{..} +++components, and appending the @file{-gdb.@var{ext}} suffix. +++If this file exists and is readable, @value{GDBN} will evaluate it as a +++script in the specified extension language. +++ +++If this file does not exist, then @value{GDBN} will look for +++@var{script-name} file in all of the directories as specified below. +++(On MS-Windows/MS-DOS, the drive letter of the executable's leading +++directories is converted to a one-letter subdirectory, i.e.@: +++@file{d:/usr/bin/} is converted to @file{/d/usr/bin/}, because Windows +++filesystems disallow colons in file names.) +++ +++Note that loading of these files requires an accordingly configured +++@code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++ +++For object files using @file{.exe} suffix @value{GDBN} tries to load first the +++scripts normally according to its @file{.exe} filename. But if no scripts are +++found @value{GDBN} also tries script filenames matching the object file without +++its @file{.exe} suffix. This @file{.exe} stripping is case insensitive and it +++is attempted on any platform. This makes the script filenames compatible +++between Unix and MS-Windows hosts. +++ +++@table @code +++@anchor{set auto-load scripts-directory} +++@kindex set auto-load scripts-directory +++@item set auto-load scripts-directory @r{[}@var{directories}@r{]} +++Control @value{GDBN} auto-loaded scripts location. Multiple directory entries +++may be delimited by the host platform path separator in use +++(@samp{:} on Unix, @samp{;} on MS-Windows and MS-DOS). +++ +++Each entry here needs to be covered also by the security setting +++@code{set auto-load safe-path} (@pxref{set auto-load safe-path}). +++ +++@anchor{with-auto-load-dir} +++This variable defaults to @file{$debugdir:$datadir/auto-load}. The default +++@code{set auto-load safe-path} value can be also overriden by @value{GDBN} +++configuration option @option{--with-auto-load-dir}. +++ +++Any reference to @file{$debugdir} will get replaced by +++@var{debug-file-directory} value (@pxref{Separate Debug Files}) and any +++reference to @file{$datadir} will get replaced by @var{data-directory} which is +++determined at @value{GDBN} startup (@pxref{Data Files}). @file{$debugdir} and +++@file{$datadir} must be placed as a directory component --- either alone or +++delimited by @file{/} or @file{\} directory separators, depending on the host +++platform. +++ +++The list of directories uses path separator (@samp{:} on GNU and Unix +++systems, @samp{;} on MS-Windows and MS-DOS) to separate directories, similarly +++to the @env{PATH} environment variable. +++ +++@anchor{show auto-load scripts-directory} +++@kindex show auto-load scripts-directory +++@item show auto-load scripts-directory +++Show @value{GDBN} auto-loaded scripts location. +++ +++@anchor{add-auto-load-scripts-directory} +++@kindex add-auto-load-scripts-directory +++@item add-auto-load-scripts-directory @r{[}@var{directories}@dots{}@r{]} +++Add an entry (or list of entries) to the list of auto-loaded scripts locations. +++Multiple entries may be delimited by the host platform path separator in use. +++@end table +++ +++@value{GDBN} does not track which files it has already auto-loaded this way. +++@value{GDBN} will load the associated script every time the corresponding +++@var{objfile} is opened. +++So your @file{-gdb.@var{ext}} file should be careful to avoid errors if it +++is evaluated more than once. +++ +++@node dotdebug_gdb_scripts section +++@subsection The @code{.debug_gdb_scripts} section +++@cindex @code{.debug_gdb_scripts} section +++ +++For systems using file formats like ELF and COFF, +++when @value{GDBN} loads a new object file +++it will look for a special section named @code{.debug_gdb_scripts}. +++If this section exists, its contents is a list of null-terminated entries +++specifying scripts to load. Each entry begins with a non-null prefix byte that +++specifies the kind of entry, typically the extension language and whether the +++script is in a file or inlined in @code{.debug_gdb_scripts}. +++ +++The following entries are supported: +++ +++@table @code +++@item SECTION_SCRIPT_ID_PYTHON_FILE = 1 +++@item SECTION_SCRIPT_ID_SCHEME_FILE = 3 +++@item SECTION_SCRIPT_ID_PYTHON_TEXT = 4 +++@item SECTION_SCRIPT_ID_SCHEME_TEXT = 6 +++@end table +++ +++@subsubsection Script File Entries +++ +++If the entry specifies a file, @value{GDBN} will look for the file first +++in the current directory and then along the source search path +++(@pxref{Source Path, ,Specifying Source Directories}), +++except that @file{$cdir} is not searched, since the compilation +++directory is not relevant to scripts. +++ +++File entries can be placed in section @code{.debug_gdb_scripts} with, +++for example, this GCC macro for Python scripts. +++ +++@example +++/* Note: The "MS" section flags are to remove duplicates. */ +++#define DEFINE_GDB_PY_SCRIPT(script_name) \ +++ asm("\ +++.pushsection \".debug_gdb_scripts\", \"MS\",@@progbits,1\n\ +++.byte 1 /* Python */\n\ +++.asciz \"" script_name "\"\n\ +++.popsection \n\ +++"); +++@end example +++ +++@noindent +++For Guile scripts, replace @code{.byte 1} with @code{.byte 3}. +++Then one can reference the macro in a header or source file like this: +++ +++@example +++DEFINE_GDB_PY_SCRIPT ("my-app-scripts.py") +++@end example +++ +++The script name may include directories if desired. +++ +++Note that loading of this script file also requires accordingly configured +++@code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++ +++If the macro invocation is put in a header, any application or library +++using this header will get a reference to the specified script, +++and with the use of @code{"MS"} attributes on the section, the linker +++will remove duplicates. +++ +++@subsubsection Script Text Entries +++ +++Script text entries allow to put the executable script in the entry +++itself instead of loading it from a file. +++The first line of the entry, everything after the prefix byte and up to +++the first newline (@code{0xa}) character, is the script name, and must not +++contain any kind of space character, e.g., spaces or tabs. +++The rest of the entry, up to the trailing null byte, is the script to +++execute in the specified language. The name needs to be unique among +++all script names, as @value{GDBN} executes each script only once based +++on its name. +++ +++Here is an example from file @file{py-section-script.c} in the @value{GDBN} +++testsuite. +++ +++@example +++#include "symcat.h" +++#include "gdb/section-scripts.h" +++asm( +++".pushsection \".debug_gdb_scripts\", \"MS\",@@progbits,1\n" +++".byte " XSTRING (SECTION_SCRIPT_ID_PYTHON_TEXT) "\n" +++".ascii \"gdb.inlined-script\\n\"\n" +++".ascii \"class test_cmd (gdb.Command):\\n\"\n" +++".ascii \" def __init__ (self):\\n\"\n" +++".ascii \" super (test_cmd, self).__init__ (" +++ "\\\"test-cmd\\\", gdb.COMMAND_OBSCURE)\\n\"\n" +++".ascii \" def invoke (self, arg, from_tty):\\n\"\n" +++".ascii \" print (\\\"test-cmd output, arg = %s\\\" % arg)\\n\"\n" +++".ascii \"test_cmd ()\\n\"\n" +++".byte 0\n" +++".popsection\n" +++); +++@end example +++ +++Loading of inlined scripts requires a properly configured +++@code{auto-load safe-path} (@pxref{Auto-loading safe path}). +++The path to specify in @code{auto-load safe-path} is the path of the file +++containing the @code{.debug_gdb_scripts} section. +++ +++@node Which flavor to choose? +++@subsection Which flavor to choose? +++ +++Given the multiple ways of auto-loading extensions, it might not always +++be clear which one to choose. This section provides some guidance. +++ +++@noindent +++Benefits of the @file{-gdb.@var{ext}} way: +++ +++@itemize @bullet +++@item +++Can be used with file formats that don't support multiple sections. +++ +++@item +++Ease of finding scripts for public libraries. +++ +++Scripts specified in the @code{.debug_gdb_scripts} section are searched for +++in the source search path. +++For publicly installed libraries, e.g., @file{libstdc++}, there typically +++isn't a source directory in which to find the script. +++ +++@item +++Doesn't require source code additions. +++@end itemize +++ +++@noindent +++Benefits of the @code{.debug_gdb_scripts} way: +++ +++@itemize @bullet +++@item +++Works with static linking. +++ +++Scripts for libraries done the @file{-gdb.@var{ext}} way require an objfile to +++trigger their loading. When an application is statically linked the only +++objfile available is the executable, and it is cumbersome to attach all the +++scripts from all the input libraries to the executable's +++@file{-gdb.@var{ext}} script. +++ +++@item +++Works with classes that are entirely inlined. +++ +++Some classes can be entirely inlined, and thus there may not be an associated +++shared library to attach a @file{-gdb.@var{ext}} script to. +++ +++@item +++Scripts needn't be copied out of the source tree. +++ +++In some circumstances, apps can be built out of large collections of internal +++libraries, and the build infrastructure necessary to install the +++@file{-gdb.@var{ext}} scripts in a place where @value{GDBN} can find them is +++cumbersome. It may be easier to specify the scripts in the +++@code{.debug_gdb_scripts} section as relative paths, and add a path to the +++top of the source tree to the source search path. +++@end itemize +++ +++@node Multiple Extension Languages +++@section Multiple Extension Languages +++ +++The Guile and Python extension languages do not share any state, +++and generally do not interfere with each other. +++There are some things to be aware of, however. +++ +++@subsection Python comes first +++ +++Python was @value{GDBN}'s first extension language, and to avoid breaking +++existing behaviour Python comes first. This is generally solved by the +++``first one wins'' principle. @value{GDBN} maintains a list of enabled +++extension languages, and when it makes a call to an extension language, +++(say to pretty-print a value), it tries each in turn until an extension +++language indicates it has performed the request (e.g., has returned the +++pretty-printed form of a value). +++This extends to errors while performing such requests: If an error happens +++while, for example, trying to pretty-print an object then the error is +++reported and any following extension languages are not tried. +++ +++@node Aliases +++@section Creating new spellings of existing commands +++@cindex aliases for commands +++ +++It is often useful to define alternate spellings of existing commands. +++For example, if a new @value{GDBN} command defined in Python has +++a long name to type, it is handy to have an abbreviated version of it +++that involves less typing. +++ +++@value{GDBN} itself uses aliases. For example @samp{s} is an alias +++of the @samp{step} command even though it is otherwise an ambiguous +++abbreviation of other commands like @samp{set} and @samp{show}. +++ +++Aliases are also used to provide shortened or more common versions +++of multi-word commands. For example, @value{GDBN} provides the +++@samp{tty} alias of the @samp{set inferior-tty} command. +++ +++You can define a new alias with the @samp{alias} command. +++ +++@table @code +++ +++@kindex alias +++@item alias [-a] [--] @var{ALIAS} = @var{COMMAND} [DEFAULT-ARGS...] +++ +++@end table +++ +++@var{ALIAS} specifies the name of the new alias. +++Each word of @var{ALIAS} must consist of letters, numbers, dashes and +++underscores. +++ +++@var{COMMAND} specifies the name of an existing command +++that is being aliased. +++ +++@var{COMMAND} can also be the name of an existing alias. In this case, +++@var{COMMAND} cannot be an alias that has default arguments. +++ +++The @samp{-a} option specifies that the new alias is an abbreviation +++of the command. Abbreviations are not used in command completion. +++ +++The @samp{--} option specifies the end of options, +++and is useful when @var{ALIAS} begins with a dash. +++ +++You can specify @var{default-args} for your alias. +++These @var{default-args} will be automatically added before the alias +++arguments typed explicitly on the command line. +++ +++For example, the below defines an alias @code{btfullall} that shows all local +++variables and all frame arguments: +++@smallexample +++(@value{GDBP}) alias btfullall = backtrace -full -frame-arguments all +++@end smallexample +++ +++For more information about @var{default-args}, see @ref{Command aliases default args, +++,Automatically prepend default arguments to user-defined aliases}. +++ +++Here is a simple example showing how to make an abbreviation +++of a command so that there is less to type. +++Suppose you were tired of typing @samp{disas}, the current +++shortest unambiguous abbreviation of the @samp{disassemble} command +++and you wanted an even shorter version named @samp{di}. +++The following will accomplish this. +++ +++@smallexample +++(gdb) alias -a di = disas +++@end smallexample +++ +++Note that aliases are different from user-defined commands. +++With a user-defined command, you also need to write documentation +++for it with the @samp{document} command. +++An alias automatically picks up the documentation of the existing command. +++ +++Here is an example where we make @samp{elms} an abbreviation of +++@samp{elements} in the @samp{set print elements} command. +++This is to show that you can make an abbreviation of any part +++of a command. +++ +++@smallexample +++(gdb) alias -a set print elms = set print elements +++(gdb) alias -a show print elms = show print elements +++(gdb) set p elms 20 +++(gdb) show p elms +++Limit on string chars or array elements to print is 200. +++@end smallexample +++ +++Note that if you are defining an alias of a @samp{set} command, +++and you want to have an alias for the corresponding @samp{show} +++command, then you need to define the latter separately. +++ +++Unambiguously abbreviated commands are allowed in @var{COMMAND} and +++@var{ALIAS}, just as they are normally. +++ +++@smallexample +++(gdb) alias -a set pr elms = set p ele +++@end smallexample +++ +++Finally, here is an example showing the creation of a one word +++alias for a more complex command. +++This creates alias @samp{spe} of the command @samp{set print elements}. +++ +++@smallexample +++(gdb) alias spe = set print elements +++(gdb) spe 20 +++@end smallexample +++ +++@node Interpreters +++@chapter Command Interpreters +++@cindex command interpreters +++ +++@value{GDBN} supports multiple command interpreters, and some command +++infrastructure to allow users or user interface writers to switch +++between interpreters or run commands in other interpreters. +++ +++@value{GDBN} currently supports two command interpreters, the console +++interpreter (sometimes called the command-line interpreter or @sc{cli}) +++and the machine interface interpreter (or @sc{gdb/mi}). This manual +++describes both of these interfaces in great detail. +++ +++By default, @value{GDBN} will start with the console interpreter. +++However, the user may choose to start @value{GDBN} with another +++interpreter by specifying the @option{-i} or @option{--interpreter} +++startup options. Defined interpreters include: +++ +++@table @code +++@item console +++@cindex console interpreter +++The traditional console or command-line interpreter. This is the most often +++used interpreter with @value{GDBN}. With no interpreter specified at runtime, +++@value{GDBN} will use this interpreter. +++ +++@item mi +++@cindex mi interpreter +++The newest @sc{gdb/mi} interface (currently @code{mi3}). Used primarily +++by programs wishing to use @value{GDBN} as a backend for a debugger GUI +++or an IDE. For more information, see @ref{GDB/MI, ,The @sc{gdb/mi} +++Interface}. +++ +++@item mi3 +++@cindex mi3 interpreter +++The @sc{gdb/mi} interface introduced in @value{GDBN} 9.1. +++ +++@item mi2 +++@cindex mi2 interpreter +++The @sc{gdb/mi} interface introduced in @value{GDBN} 6.0. +++ +++@item mi1 +++@cindex mi1 interpreter +++The @sc{gdb/mi} interface introduced in @value{GDBN} 5.1. +++ +++@end table +++ +++@cindex invoke another interpreter +++ +++@kindex interpreter-exec +++You may execute commands in any interpreter from the current +++interpreter using the appropriate command. If you are running the +++console interpreter, simply use the @code{interpreter-exec} command: +++ +++@smallexample +++interpreter-exec mi "-data-list-register-names" +++@end smallexample +++ +++@sc{gdb/mi} has a similar command, although it is only available in versions of +++@value{GDBN} which support @sc{gdb/mi} version 2 (or greater). +++ +++Note that @code{interpreter-exec} only changes the interpreter for the +++duration of the specified command. It does not change the interpreter +++permanently. +++ +++@cindex start a new independent interpreter +++ +++Although you may only choose a single interpreter at startup, it is +++possible to run an independent interpreter on a specified input/output +++device (usually a tty). +++ +++For example, consider a debugger GUI or IDE that wants to provide a +++@value{GDBN} console view. It may do so by embedding a terminal +++emulator widget in its GUI, starting @value{GDBN} in the traditional +++command-line mode with stdin/stdout/stderr redirected to that +++terminal, and then creating an MI interpreter running on a specified +++input/output device. The console interpreter created by @value{GDBN} +++at startup handles commands the user types in the terminal widget, +++while the GUI controls and synchronizes state with @value{GDBN} using +++the separate MI interpreter. +++ +++To start a new secondary @dfn{user interface} running MI, use the +++@code{new-ui} command: +++ +++@kindex new-ui +++@cindex new user interface +++@smallexample +++new-ui @var{interpreter} @var{tty} +++@end smallexample +++ +++The @var{interpreter} parameter specifies the interpreter to run. +++This accepts the same values as the @code{interpreter-exec} command. +++For example, @samp{console}, @samp{mi}, @samp{mi2}, etc. The +++@var{tty} parameter specifies the name of the bidirectional file the +++interpreter uses for input/output, usually the name of a +++pseudoterminal slave on Unix systems. For example: +++ +++@smallexample +++(@value{GDBP}) new-ui mi /dev/pts/9 +++@end smallexample +++ +++@noindent +++runs an MI interpreter on @file{/dev/pts/9}. +++ +++@node TUI +++@chapter @value{GDBN} Text User Interface +++@cindex TUI +++@cindex Text User Interface +++ +++@menu +++* TUI Overview:: TUI overview +++* TUI Keys:: TUI key bindings +++* TUI Single Key Mode:: TUI single key mode +++* TUI Commands:: TUI-specific commands +++* TUI Configuration:: TUI configuration variables +++@end menu +++ +++The @value{GDBN} Text User Interface (TUI) is a terminal +++interface which uses the @code{curses} library to show the source +++file, the assembly output, the program registers and @value{GDBN} +++commands in separate text windows. The TUI mode is supported only +++on platforms where a suitable version of the @code{curses} library +++is available. +++ +++The TUI mode is enabled by default when you invoke @value{GDBN} as +++@samp{@value{GDBP} -tui}. +++You can also switch in and out of TUI mode while @value{GDBN} runs by +++using various TUI commands and key bindings, such as @command{tui +++enable} or @kbd{C-x C-a}. @xref{TUI Commands, ,TUI Commands}, and +++@ref{TUI Keys, ,TUI Key Bindings}. +++ +++@node TUI Overview +++@section TUI Overview +++ +++In TUI mode, @value{GDBN} can display several text windows: +++ +++@table @emph +++@item command +++This window is the @value{GDBN} command window with the @value{GDBN} +++prompt and the @value{GDBN} output. The @value{GDBN} input is still +++managed using readline. +++ +++@item source +++The source window shows the source file of the program. The current +++line and active breakpoints are displayed in this window. +++ +++@item assembly +++The assembly window shows the disassembly output of the program. +++ +++@item register +++This window shows the processor registers. Registers are highlighted +++when their values change. +++@end table +++ +++The source and assembly windows show the current program position +++by highlighting the current line and marking it with a @samp{>} marker. +++Breakpoints are indicated with two markers. The first marker +++indicates the breakpoint type: +++ +++@table @code +++@item B +++Breakpoint which was hit at least once. +++ +++@item b +++Breakpoint which was never hit. +++ +++@item H +++Hardware breakpoint which was hit at least once. +++ +++@item h +++Hardware breakpoint which was never hit. +++@end table +++ +++The second marker indicates whether the breakpoint is enabled or not: +++ +++@table @code +++@item + +++Breakpoint is enabled. +++ +++@item - +++Breakpoint is disabled. +++@end table +++ +++The source, assembly and register windows are updated when the current +++thread changes, when the frame changes, or when the program counter +++changes. +++ +++These windows are not all visible at the same time. The command +++window is always visible. The others can be arranged in several +++layouts: +++ +++@itemize @bullet +++@item +++source only, +++ +++@item +++assembly only, +++ +++@item +++source and assembly, +++ +++@item +++source and registers, or +++ +++@item +++assembly and registers. +++@end itemize +++ +++These are the standard layouts, but other layouts can be defined. +++ +++A status line above the command window shows the following information: +++ +++@table @emph +++@item target +++Indicates the current @value{GDBN} target. +++(@pxref{Targets, ,Specifying a Debugging Target}). +++ +++@item process +++Gives the current process or thread number. +++When no process is being debugged, this field is set to @code{No process}. +++ +++@item function +++Gives the current function name for the selected frame. +++The name is demangled if demangling is turned on (@pxref{Print Settings}). +++When there is no symbol corresponding to the current program counter, +++the string @code{??} is displayed. +++ +++@item line +++Indicates the current line number for the selected frame. +++When the current line number is not known, the string @code{??} is displayed. +++ +++@item pc +++Indicates the current program counter address. +++@end table +++ +++@node TUI Keys +++@section TUI Key Bindings +++@cindex TUI key bindings +++ +++The TUI installs several key bindings in the readline keymaps +++@ifset SYSTEM_READLINE +++(@pxref{Command Line Editing, , , rluserman, GNU Readline Library}). +++@end ifset +++@ifclear SYSTEM_READLINE +++(@pxref{Command Line Editing}). +++@end ifclear +++The following key bindings are installed for both TUI mode and the +++@value{GDBN} standard mode. +++ +++@table @kbd +++@kindex C-x C-a +++@item C-x C-a +++@kindex C-x a +++@itemx C-x a +++@kindex C-x A +++@itemx C-x A +++Enter or leave the TUI mode. When leaving the TUI mode, +++the curses window management stops and @value{GDBN} operates using +++its standard mode, writing on the terminal directly. When reentering +++the TUI mode, control is given back to the curses windows. +++The screen is then refreshed. +++ +++This key binding uses the bindable Readline function +++@code{tui-switch-mode}. +++ +++@kindex C-x 1 +++@item C-x 1 +++Use a TUI layout with only one window. The layout will +++either be @samp{source} or @samp{assembly}. When the TUI mode +++is not active, it will switch to the TUI mode. +++ +++Think of this key binding as the Emacs @kbd{C-x 1} binding. +++ +++This key binding uses the bindable Readline function +++@code{tui-delete-other-windows}. +++ +++@kindex C-x 2 +++@item C-x 2 +++Use a TUI layout with at least two windows. When the current +++layout already has two windows, the next layout with two windows is used. +++When a new layout is chosen, one window will always be common to the +++previous layout and the new one. +++ +++Think of it as the Emacs @kbd{C-x 2} binding. +++ +++This key binding uses the bindable Readline function +++@code{tui-change-windows}. +++ +++@kindex C-x o +++@item C-x o +++Change the active window. The TUI associates several key bindings +++(like scrolling and arrow keys) with the active window. This command +++gives the focus to the next TUI window. +++ +++Think of it as the Emacs @kbd{C-x o} binding. +++ +++This key binding uses the bindable Readline function +++@code{tui-other-window}. +++ +++@kindex C-x s +++@item C-x s +++Switch in and out of the TUI SingleKey mode that binds single +++keys to @value{GDBN} commands (@pxref{TUI Single Key Mode}). +++ +++This key binding uses the bindable Readline function +++@code{next-keymap}. +++@end table +++ +++The following key bindings only work in the TUI mode: +++ +++@table @asis +++@kindex PgUp +++@item @key{PgUp} +++Scroll the active window one page up. +++ +++@kindex PgDn +++@item @key{PgDn} +++Scroll the active window one page down. +++ +++@kindex Up +++@item @key{Up} +++Scroll the active window one line up. +++ +++@kindex Down +++@item @key{Down} +++Scroll the active window one line down. +++ +++@kindex Left +++@item @key{Left} +++Scroll the active window one column left. +++ +++@kindex Right +++@item @key{Right} +++Scroll the active window one column right. +++ +++@kindex C-L +++@item @kbd{C-L} +++Refresh the screen. +++@end table +++ +++Because the arrow keys scroll the active window in the TUI mode, they +++are not available for their normal use by readline unless the command +++window has the focus. When another window is active, you must use +++other readline key bindings such as @kbd{C-p}, @kbd{C-n}, @kbd{C-b} +++and @kbd{C-f} to control the command window. +++ +++@node TUI Single Key Mode +++@section TUI Single Key Mode +++@cindex TUI single key mode +++ +++The TUI also provides a @dfn{SingleKey} mode, which binds several +++frequently used @value{GDBN} commands to single keys. Type @kbd{C-x s} to +++switch into this mode, where the following key bindings are used: +++ +++@table @kbd +++@kindex c @r{(SingleKey TUI key)} +++@item c +++continue +++ +++@kindex d @r{(SingleKey TUI key)} +++@item d +++down +++ +++@kindex f @r{(SingleKey TUI key)} +++@item f +++finish +++ +++@kindex n @r{(SingleKey TUI key)} +++@item n +++next +++ +++@kindex o @r{(SingleKey TUI key)} +++@item o +++nexti. The shortcut letter @samp{o} stands for ``step Over''. +++ +++@kindex q @r{(SingleKey TUI key)} +++@item q +++exit the SingleKey mode. +++ +++@kindex r @r{(SingleKey TUI key)} +++@item r +++run +++ +++@kindex s @r{(SingleKey TUI key)} +++@item s +++step +++ +++@kindex i @r{(SingleKey TUI key)} +++@item i +++stepi. The shortcut letter @samp{i} stands for ``step Into''. +++ +++@kindex u @r{(SingleKey TUI key)} +++@item u +++up +++ +++@kindex v @r{(SingleKey TUI key)} +++@item v +++info locals +++ +++@kindex w @r{(SingleKey TUI key)} +++@item w +++where +++@end table +++ +++Other keys temporarily switch to the @value{GDBN} command prompt. +++The key that was pressed is inserted in the editing buffer so that +++it is possible to type most @value{GDBN} commands without interaction +++with the TUI SingleKey mode. Once the command is entered the TUI +++SingleKey mode is restored. The only way to permanently leave +++this mode is by typing @kbd{q} or @kbd{C-x s}. +++ +++@cindex SingleKey keymap name +++If @value{GDBN} was built with Readline 8.0 or later, the TUI +++SingleKey keymap will be named @samp{SingleKey}. This can be used in +++@file{.inputrc} to add additional bindings to this keymap. +++ +++@node TUI Commands +++@section TUI-specific Commands +++@cindex TUI commands +++ +++The TUI has specific commands to control the text windows. +++These commands are always available, even when @value{GDBN} is not in +++the TUI mode. When @value{GDBN} is in the standard mode, most +++of these commands will automatically switch to the TUI mode. +++ +++Note that if @value{GDBN}'s @code{stdout} is not connected to a +++terminal, or @value{GDBN} has been started with the machine interface +++interpreter (@pxref{GDB/MI, ,The @sc{gdb/mi} Interface}), most of +++these commands will fail with an error, because it would not be +++possible or desirable to enable curses window management. +++ +++@table @code +++@item tui enable +++@kindex tui enable +++Activate TUI mode. The last active TUI window layout will be used if +++TUI mode has previously been used in the current debugging session, +++otherwise a default layout is used. +++ +++@item tui disable +++@kindex tui disable +++Disable TUI mode, returning to the console interpreter. +++ +++@item info win +++@kindex info win +++List and give the size of all displayed windows. +++ +++@item tui new-layout @var{name} @var{window} @var{weight} @r{[}@var{window} @var{weight}@dots{}@r{]} +++@kindex tui new-layout +++Create a new TUI layout. The new layout will be named @var{name}, and +++can be accessed using the @code{layout} command (see below). +++ +++Each @var{window} parameter is either the name of a window to display, +++or a window description. The windows will be displayed from top to +++bottom in the order listed. +++ +++The names of the windows are the same as the ones given to the +++@code{focus} command (see below); additional, the @code{status} +++window can be specified. Note that, because it is of fixed height, +++the weight assigned to the status window is of no importance. It is +++conventional to use @samp{0} here. +++ +++A window description looks a bit like an invocation of @code{tui +++new-layout}, and is of the form +++@{@r{[}@code{-horizontal}@r{]}@var{window} @var{weight} @r{[}@var{window} @var{weight}@dots{}@r{]}@}. +++ +++This specifies a sub-layout. If @code{-horizontal} is given, the +++windows in this description will be arranged side-by-side, rather than +++top-to-bottom. +++ +++Each @var{weight} is an integer. It is the weight of this window +++relative to all the other windows in the layout. These numbers are +++used to calculate how much of the screen is given to each window. +++ +++For example: +++ +++@example +++(gdb) tui new-layout example src 1 regs 1 status 0 cmd 1 +++@end example +++ +++Here, the new layout is called @samp{example}. It shows the source +++and register windows, followed by the status window, and then finally +++the command window. The non-status windows all have the same weight, +++so the terminal will be split into three roughly equal sections. +++ +++Here is a more complex example, showing a horizontal layout: +++ +++@example +++(gdb) tui new-layout example @{-horizontal src 1 asm 1@} 2 status 0 cmd 1 +++@end example +++ +++This will result in side-by-side source and assembly windows; with the +++status and command window being beneath these, filling the entire +++width of the terminal. Because they have weight 2, the source and +++assembly windows will be twice the height of the command window. +++ +++@item layout @var{name} +++@kindex layout +++Changes which TUI windows are displayed. The @var{name} parameter +++controls which layout is shown. It can be either one of the built-in +++layout names, or the name of a layout defined by the user using +++@code{tui new-layout}. +++ +++The built-in layouts are as follows: +++ +++@table @code +++@item next +++Display the next layout. +++ +++@item prev +++Display the previous layout. +++ +++@item src +++Display the source and command windows. +++ +++@item asm +++Display the assembly and command windows. +++ +++@item split +++Display the source, assembly, and command windows. +++ +++@item regs +++When in @code{src} layout display the register, source, and command +++windows. When in @code{asm} or @code{split} layout display the +++register, assembler, and command windows. +++@end table +++ +++@item focus @var{name} +++@kindex focus +++Changes which TUI window is currently active for scrolling. The +++@var{name} parameter can be any of the following: +++ +++@table @code +++@item next +++Make the next window active for scrolling. +++ +++@item prev +++Make the previous window active for scrolling. +++ +++@item src +++Make the source window active for scrolling. +++ +++@item asm +++Make the assembly window active for scrolling. +++ +++@item regs +++Make the register window active for scrolling. +++ +++@item cmd +++Make the command window active for scrolling. +++@end table +++ +++@item refresh +++@kindex refresh +++Refresh the screen. This is similar to typing @kbd{C-L}. +++ +++@item tui reg @var{group} +++@kindex tui reg +++Changes the register group displayed in the tui register window to +++@var{group}. If the register window is not currently displayed this +++command will cause the register window to be displayed. The list of +++register groups, as well as their order is target specific. The +++following groups are available on most targets: +++@table @code +++@item next +++Repeatedly selecting this group will cause the display to cycle +++through all of the available register groups. +++ +++@item prev +++Repeatedly selecting this group will cause the display to cycle +++through all of the available register groups in the reverse order to +++@var{next}. +++ +++@item general +++Display the general registers. +++@item float +++Display the floating point registers. +++@item system +++Display the system registers. +++@item vector +++Display the vector registers. +++@item all +++Display all registers. +++@end table +++ +++@item update +++@kindex update +++Update the source window and the current execution point. +++ +++@item winheight @var{name} +@var{count} +++@itemx winheight @var{name} -@var{count} +++@kindex winheight +++Change the height of the window @var{name} by @var{count} +++lines. Positive counts increase the height, while negative counts +++decrease it. The @var{name} parameter can be one of @code{src} (the +++source window), @code{cmd} (the command window), @code{asm} (the +++disassembly window), or @code{regs} (the register display window). +++@end table +++ +++@node TUI Configuration +++@section TUI Configuration Variables +++@cindex TUI configuration variables +++ +++Several configuration variables control the appearance of TUI windows. +++ +++@table @code +++@item set tui border-kind @var{kind} +++@kindex set tui border-kind +++Select the border appearance for the source, assembly and register windows. +++The possible values are the following: +++@table @code +++@item space +++Use a space character to draw the border. +++ +++@item ascii +++Use @sc{ascii} characters @samp{+}, @samp{-} and @samp{|} to draw the border. +++ +++@item acs +++Use the Alternate Character Set to draw the border. The border is +++drawn using character line graphics if the terminal supports them. +++@end table +++ +++@item set tui border-mode @var{mode} +++@kindex set tui border-mode +++@itemx set tui active-border-mode @var{mode} +++@kindex set tui active-border-mode +++Select the display attributes for the borders of the inactive windows +++or the active window. The @var{mode} can be one of the following: +++@table @code +++@item normal +++Use normal attributes to display the border. +++ +++@item standout +++Use standout mode. +++ +++@item reverse +++Use reverse video mode. +++ +++@item half +++Use half bright mode. +++ +++@item half-standout +++Use half bright and standout mode. +++ +++@item bold +++Use extra bright or bold mode. +++ +++@item bold-standout +++Use extra bright or bold and standout mode. +++@end table +++ +++@item set tui tab-width @var{nchars} +++@kindex set tui tab-width +++@kindex tabset +++Set the width of tab stops to be @var{nchars} characters. This +++setting affects the display of TAB characters in the source and +++assembly windows. +++ +++@item set tui compact-source @r{[}on@r{|}off@r{]} +++@kindex set tui compact-source +++Set whether the TUI source window is displayed in ``compact'' form. +++The default display uses more space for line numbers and starts the +++source text at the next tab stop; the compact display uses only as +++much space as is needed for the line numbers in the current file, and +++only a single space to separate the line numbers from the source. +++@end table +++ +++Note that the colors of the TUI borders can be controlled using the +++appropriate @code{set style} commands. @xref{Output Styling}. +++ +++@node Emacs +++@chapter Using @value{GDBN} under @sc{gnu} Emacs +++ +++@cindex Emacs +++@cindex @sc{gnu} Emacs +++A special interface allows you to use @sc{gnu} Emacs to view (and +++edit) the source files for the program you are debugging with +++@value{GDBN}. +++ +++To use this interface, use the command @kbd{M-x gdb} in Emacs. Give the +++executable file you want to debug as an argument. This command starts +++@value{GDBN} as a subprocess of Emacs, with input and output through a newly +++created Emacs buffer. +++@c (Do not use the @code{-tui} option to run @value{GDBN} from Emacs.) +++ +++Running @value{GDBN} under Emacs can be just like running @value{GDBN} normally except for two +++things: +++ +++@itemize @bullet +++@item +++All ``terminal'' input and output goes through an Emacs buffer, called +++the GUD buffer. +++ +++This applies both to @value{GDBN} commands and their output, and to the input +++and output done by the program you are debugging. +++ +++This is useful because it means that you can copy the text of previous +++commands and input them again; you can even use parts of the output +++in this way. +++ +++All the facilities of Emacs' Shell mode are available for interacting +++with your program. In particular, you can send signals the usual +++way---for example, @kbd{C-c C-c} for an interrupt, @kbd{C-c C-z} for a +++stop. +++ +++@item +++@value{GDBN} displays source code through Emacs. +++ +++Each time @value{GDBN} displays a stack frame, Emacs automatically finds the +++source file for that frame and puts an arrow (@samp{=>}) at the +++left margin of the current line. Emacs uses a separate buffer for +++source display, and splits the screen to show both your @value{GDBN} session +++and the source. +++ +++Explicit @value{GDBN} @code{list} or search commands still produce output as +++usual, but you probably have no reason to use them from Emacs. +++@end itemize +++ +++We call this @dfn{text command mode}. Emacs 22.1, and later, also uses +++a graphical mode, enabled by default, which provides further buffers +++that can control the execution and describe the state of your program. +++@xref{GDB Graphical Interface,,, Emacs, The @sc{gnu} Emacs Manual}. +++ +++If you specify an absolute file name when prompted for the @kbd{M-x +++gdb} argument, then Emacs sets your current working directory to where +++your program resides. If you only specify the file name, then Emacs +++sets your current working directory to the directory associated +++with the previous buffer. In this case, @value{GDBN} may find your +++program by searching your environment's @code{PATH} variable, but on +++some operating systems it might not find the source. So, although the +++@value{GDBN} input and output session proceeds normally, the auxiliary +++buffer does not display the current source and line of execution. +++ +++The initial working directory of @value{GDBN} is printed on the top +++line of the GUD buffer and this serves as a default for the commands +++that specify files for @value{GDBN} to operate on. @xref{Files, +++,Commands to Specify Files}. +++ +++By default, @kbd{M-x gdb} calls the program called @file{gdb}. If you +++need to call @value{GDBN} by a different name (for example, if you +++keep several configurations around, with different names) you can +++customize the Emacs variable @code{gud-gdb-command-name} to run the +++one you want. +++ +++In the GUD buffer, you can use these special Emacs commands in +++addition to the standard Shell mode commands: +++ +++@table @kbd +++@item C-h m +++Describe the features of Emacs' GUD Mode. +++ +++@item C-c C-s +++Execute to another source line, like the @value{GDBN} @code{step} command; also +++update the display window to show the current file and location. +++ +++@item C-c C-n +++Execute to next source line in this function, skipping all function +++calls, like the @value{GDBN} @code{next} command. Then update the display window +++to show the current file and location. +++ +++@item C-c C-i +++Execute one instruction, like the @value{GDBN} @code{stepi} command; update +++display window accordingly. +++ +++@item C-c C-f +++Execute until exit from the selected stack frame, like the @value{GDBN} +++@code{finish} command. +++ +++@item C-c C-r +++Continue execution of your program, like the @value{GDBN} @code{continue} +++command. +++ +++@item C-c < +++Go up the number of frames indicated by the numeric argument +++(@pxref{Arguments, , Numeric Arguments, Emacs, The @sc{gnu} Emacs Manual}), +++like the @value{GDBN} @code{up} command. +++ +++@item C-c > +++Go down the number of frames indicated by the numeric argument, like the +++@value{GDBN} @code{down} command. +++@end table +++ +++In any source file, the Emacs command @kbd{C-x @key{SPC}} (@code{gud-break}) +++tells @value{GDBN} to set a breakpoint on the source line point is on. +++ +++In text command mode, if you type @kbd{M-x speedbar}, Emacs displays a +++separate frame which shows a backtrace when the GUD buffer is current. +++Move point to any frame in the stack and type @key{RET} to make it +++become the current frame and display the associated source in the +++source buffer. Alternatively, click @kbd{Mouse-2} to make the +++selected frame become the current one. In graphical mode, the +++speedbar displays watch expressions. +++ +++If you accidentally delete the source-display buffer, an easy way to get +++it back is to type the command @code{f} in the @value{GDBN} buffer, to +++request a frame display; when you run under Emacs, this recreates +++the source buffer if necessary to show you the context of the current +++frame. +++ +++The source files displayed in Emacs are in ordinary Emacs buffers +++which are visiting the source files in the usual way. You can edit +++the files with these buffers if you wish; but keep in mind that @value{GDBN} +++communicates with Emacs in terms of line numbers. If you add or +++delete lines from the text, the line numbers that @value{GDBN} knows cease +++to correspond properly with the code. +++ +++A more detailed description of Emacs' interaction with @value{GDBN} is +++given in the Emacs manual (@pxref{Debuggers,,, Emacs, The @sc{gnu} +++Emacs Manual}). +++ +++@node GDB/MI +++@chapter The @sc{gdb/mi} Interface +++ +++@unnumberedsec Function and Purpose +++ +++@cindex @sc{gdb/mi}, its purpose +++@sc{gdb/mi} is a line based machine oriented text interface to +++@value{GDBN} and is activated by specifying using the +++@option{--interpreter} command line option (@pxref{Mode Options}). It +++is specifically intended to support the development of systems which +++use the debugger as just one small component of a larger system. +++ +++This chapter is a specification of the @sc{gdb/mi} interface. It is written +++in the form of a reference manual. +++ +++Note that @sc{gdb/mi} is still under construction, so some of the +++features described below are incomplete and subject to change +++(@pxref{GDB/MI Development and Front Ends, , @sc{gdb/mi} Development and Front Ends}). +++ +++@unnumberedsec Notation and Terminology +++ +++@cindex notational conventions, for @sc{gdb/mi} +++This chapter uses the following notation: +++ +++@itemize @bullet +++@item +++@code{|} separates two alternatives. +++ +++@item +++@code{[ @var{something} ]} indicates that @var{something} is optional: +++it may or may not be given. +++ +++@item +++@code{( @var{group} )*} means that @var{group} inside the parentheses +++may repeat zero or more times. +++ +++@item +++@code{( @var{group} )+} means that @var{group} inside the parentheses +++may repeat one or more times. +++ +++@item +++@code{"@var{string}"} means a literal @var{string}. +++@end itemize +++ +++@ignore +++@heading Dependencies +++@end ignore +++ +++@menu +++* GDB/MI General Design:: +++* GDB/MI Command Syntax:: +++* GDB/MI Compatibility with CLI:: +++* GDB/MI Development and Front Ends:: +++* GDB/MI Output Records:: +++* GDB/MI Simple Examples:: +++* GDB/MI Command Description Format:: +++* GDB/MI Breakpoint Commands:: +++* GDB/MI Catchpoint Commands:: +++* GDB/MI Program Context:: +++* GDB/MI Thread Commands:: +++* GDB/MI Ada Tasking Commands:: +++* GDB/MI Program Execution:: +++* GDB/MI Stack Manipulation:: +++* GDB/MI Variable Objects:: +++* GDB/MI Data Manipulation:: +++* GDB/MI Tracepoint Commands:: +++* GDB/MI Symbol Query:: +++* GDB/MI File Commands:: +++@ignore +++* GDB/MI Kod Commands:: +++* GDB/MI Memory Overlay Commands:: +++* GDB/MI Signal Handling Commands:: +++@end ignore +++* GDB/MI Target Manipulation:: +++* GDB/MI File Transfer Commands:: +++* GDB/MI Ada Exceptions Commands:: +++* GDB/MI Support Commands:: +++* GDB/MI Miscellaneous Commands:: +++@end menu +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI General Design +++@section @sc{gdb/mi} General Design +++@cindex GDB/MI General Design +++ +++Interaction of a @sc{GDB/MI} frontend with @value{GDBN} involves three +++parts---commands sent to @value{GDBN}, responses to those commands +++and notifications. Each command results in exactly one response, +++indicating either successful completion of the command, or an error. +++For the commands that do not resume the target, the response contains the +++requested information. For the commands that resume the target, the +++response only indicates whether the target was successfully resumed. +++Notifications is the mechanism for reporting changes in the state of the +++target, or in @value{GDBN} state, that cannot conveniently be associated with +++a command and reported as part of that command response. +++ +++The important examples of notifications are: +++@itemize @bullet +++ +++@item +++Exec notifications. These are used to report changes in +++target state---when a target is resumed, or stopped. It would not +++be feasible to include this information in response of resuming +++commands, because one resume commands can result in multiple events in +++different threads. Also, quite some time may pass before any event +++happens in the target, while a frontend needs to know whether the resuming +++command itself was successfully executed. +++ +++@item +++Console output, and status notifications. Console output +++notifications are used to report output of CLI commands, as well as +++diagnostics for other commands. Status notifications are used to +++report the progress of a long-running operation. Naturally, including +++this information in command response would mean no output is produced +++until the command is finished, which is undesirable. +++ +++@item +++General notifications. Commands may have various side effects on +++the @value{GDBN} or target state beyond their official purpose. For example, +++a command may change the selected thread. Although such changes can +++be included in command response, using notification allows for more +++orthogonal frontend design. +++ +++@end itemize +++ +++There's no guarantee that whenever an MI command reports an error, +++@value{GDBN} or the target are in any specific state, and especially, +++the state is not reverted to the state before the MI command was +++processed. Therefore, whenever an MI command results in an error, +++we recommend that the frontend refreshes all the information shown in +++the user interface. +++ +++ +++@menu +++* Context management:: +++* Asynchronous and non-stop modes:: +++* Thread groups:: +++@end menu +++ +++@node Context management +++@subsection Context management +++ +++@subsubsection Threads and Frames +++ +++In most cases when @value{GDBN} accesses the target, this access is +++done in context of a specific thread and frame (@pxref{Frames}). +++Often, even when accessing global data, the target requires that a thread +++be specified. The CLI interface maintains the selected thread and frame, +++and supplies them to target on each command. This is convenient, +++because a command line user would not want to specify that information +++explicitly on each command, and because user interacts with +++@value{GDBN} via a single terminal, so no confusion is possible as +++to what thread and frame are the current ones. +++ +++In the case of MI, the concept of selected thread and frame is less +++useful. First, a frontend can easily remember this information +++itself. Second, a graphical frontend can have more than one window, +++each one used for debugging a different thread, and the frontend might +++want to access additional threads for internal purposes. This +++increases the risk that by relying on implicitly selected thread, the +++frontend may be operating on a wrong one. Therefore, each MI command +++should explicitly specify which thread and frame to operate on. To +++make it possible, each MI command accepts the @samp{--thread} and +++@samp{--frame} options, the value to each is @value{GDBN} global +++identifier for thread and frame to operate on. +++ +++Usually, each top-level window in a frontend allows the user to select +++a thread and a frame, and remembers the user selection for further +++operations. However, in some cases @value{GDBN} may suggest that the +++current thread or frame be changed. For example, when stopping on a +++breakpoint it is reasonable to switch to the thread where breakpoint is +++hit. For another example, if the user issues the CLI @samp{thread} or +++@samp{frame} commands via the frontend, it is desirable to change the +++frontend's selection to the one specified by user. @value{GDBN} +++communicates the suggestion to change current thread and frame using the +++@samp{=thread-selected} notification. +++ +++Note that historically, MI shares the selected thread with CLI, so +++frontends used the @code{-thread-select} to execute commands in the +++right context. However, getting this to work right is cumbersome. The +++simplest way is for frontend to emit @code{-thread-select} command +++before every command. This doubles the number of commands that need +++to be sent. The alternative approach is to suppress @code{-thread-select} +++if the selected thread in @value{GDBN} is supposed to be identical to the +++thread the frontend wants to operate on. However, getting this +++optimization right can be tricky. In particular, if the frontend +++sends several commands to @value{GDBN}, and one of the commands changes the +++selected thread, then the behaviour of subsequent commands will +++change. So, a frontend should either wait for response from such +++problematic commands, or explicitly add @code{-thread-select} for +++all subsequent commands. No frontend is known to do this exactly +++right, so it is suggested to just always pass the @samp{--thread} and +++@samp{--frame} options. +++ +++@subsubsection Language +++ +++The execution of several commands depends on which language is selected. +++By default, the current language (@pxref{show language}) is used. +++But for commands known to be language-sensitive, it is recommended +++to use the @samp{--language} option. This option takes one argument, +++which is the name of the language to use while executing the command. +++For instance: +++ +++@smallexample +++-data-evaluate-expression --language c "sizeof (void*)" +++^done,value="4" +++(gdb) +++@end smallexample +++ +++The valid language names are the same names accepted by the +++@samp{set language} command (@pxref{Manually}), excluding @samp{auto}, +++@samp{local} or @samp{unknown}. +++ +++@node Asynchronous and non-stop modes +++@subsection Asynchronous command execution and non-stop mode +++ +++On some targets, @value{GDBN} is capable of processing MI commands +++even while the target is running. This is called @dfn{asynchronous +++command execution} (@pxref{Background Execution}). The frontend may +++specify a preference for asynchronous execution using the +++@code{-gdb-set mi-async 1} command, which should be emitted before +++either running the executable or attaching to the target. After the +++frontend has started the executable or attached to the target, it can +++find if asynchronous execution is enabled using the +++@code{-list-target-features} command. +++ +++@table @code +++@item -gdb-set mi-async on +++@item -gdb-set mi-async off +++Set whether MI is in asynchronous mode. +++ +++When @code{off}, which is the default, MI execution commands (e.g., +++@code{-exec-continue}) are foreground commands, and @value{GDBN} waits +++for the program to stop before processing further commands. +++ +++When @code{on}, MI execution commands are background execution +++commands (e.g., @code{-exec-continue} becomes the equivalent of the +++@code{c&} CLI command), and so @value{GDBN} is capable of processing +++MI commands even while the target is running. +++ +++@item -gdb-show mi-async +++Show whether MI asynchronous mode is enabled. +++@end table +++ +++Note: In @value{GDBN} version 7.7 and earlier, this option was called +++@code{target-async} instead of @code{mi-async}, and it had the effect +++of both putting MI in asynchronous mode and making CLI background +++commands possible. CLI background commands are now always possible +++``out of the box'' if the target supports them. The old spelling is +++kept as a deprecated alias for backwards compatibility. +++ +++Even if @value{GDBN} can accept a command while target is running, +++many commands that access the target do not work when the target is +++running. Therefore, asynchronous command execution is most useful +++when combined with non-stop mode (@pxref{Non-Stop Mode}). Then, +++it is possible to examine the state of one thread, while other threads +++are running. +++ +++When a given thread is running, MI commands that try to access the +++target in the context of that thread may not work, or may work only on +++some targets. In particular, commands that try to operate on thread's +++stack will not work, on any target. Commands that read memory, or +++modify breakpoints, may work or not work, depending on the target. Note +++that even commands that operate on global state, such as @code{print}, +++@code{set}, and breakpoint commands, still access the target in the +++context of a specific thread, so frontend should try to find a +++stopped thread and perform the operation on that thread (using the +++@samp{--thread} option). +++ +++Which commands will work in the context of a running thread is +++highly target dependent. However, the two commands +++@code{-exec-interrupt}, to stop a thread, and @code{-thread-info}, +++to find the state of a thread, will always work. +++ +++@node Thread groups +++@subsection Thread groups +++@value{GDBN} may be used to debug several processes at the same time. +++On some platforms, @value{GDBN} may support debugging of several +++hardware systems, each one having several cores with several different +++processes running on each core. This section describes the MI +++mechanism to support such debugging scenarios. +++ +++The key observation is that regardless of the structure of the +++target, MI can have a global list of threads, because most commands that +++accept the @samp{--thread} option do not need to know what process that +++thread belongs to. Therefore, it is not necessary to introduce +++neither additional @samp{--process} option, nor an notion of the +++current process in the MI interface. The only strictly new feature +++that is required is the ability to find how the threads are grouped +++into processes. +++ +++To allow the user to discover such grouping, and to support arbitrary +++hierarchy of machines/cores/processes, MI introduces the concept of a +++@dfn{thread group}. Thread group is a collection of threads and other +++thread groups. A thread group always has a string identifier, a type, +++and may have additional attributes specific to the type. A new +++command, @code{-list-thread-groups}, returns the list of top-level +++thread groups, which correspond to processes that @value{GDBN} is +++debugging at the moment. By passing an identifier of a thread group +++to the @code{-list-thread-groups} command, it is possible to obtain +++the members of specific thread group. +++ +++To allow the user to easily discover processes, and other objects, he +++wishes to debug, a concept of @dfn{available thread group} is +++introduced. Available thread group is an thread group that +++@value{GDBN} is not debugging, but that can be attached to, using the +++@code{-target-attach} command. The list of available top-level thread +++groups can be obtained using @samp{-list-thread-groups --available}. +++In general, the content of a thread group may be only retrieved only +++after attaching to that thread group. +++ +++Thread groups are related to inferiors (@pxref{Inferiors Connections and +++Programs}). Each inferior corresponds to a thread group of a special +++type @samp{process}, and some additional operations are permitted on +++such thread groups. +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Command Syntax +++@section @sc{gdb/mi} Command Syntax +++ +++@menu +++* GDB/MI Input Syntax:: +++* GDB/MI Output Syntax:: +++@end menu +++ +++@node GDB/MI Input Syntax +++@subsection @sc{gdb/mi} Input Syntax +++ +++@cindex input syntax for @sc{gdb/mi} +++@cindex @sc{gdb/mi}, input syntax +++@table @code +++@item @var{command} @expansion{} +++@code{@var{cli-command} | @var{mi-command}} +++ +++@item @var{cli-command} @expansion{} +++@code{[ @var{token} ] @var{cli-command} @var{nl}}, where +++@var{cli-command} is any existing @value{GDBN} CLI command. +++ +++@item @var{mi-command} @expansion{} +++@code{[ @var{token} ] "-" @var{operation} ( " " @var{option} )* +++@code{[} " --" @code{]} ( " " @var{parameter} )* @var{nl}} +++ +++@item @var{token} @expansion{} +++"any sequence of digits" +++ +++@item @var{option} @expansion{} +++@code{"-" @var{parameter} [ " " @var{parameter} ]} +++ +++@item @var{parameter} @expansion{} +++@code{@var{non-blank-sequence} | @var{c-string}} +++ +++@item @var{operation} @expansion{} +++@emph{any of the operations described in this chapter} +++ +++@item @var{non-blank-sequence} @expansion{} +++@emph{anything, provided it doesn't contain special characters such as +++"-", @var{nl}, """ and of course " "} +++ +++@item @var{c-string} @expansion{} +++@code{""" @var{seven-bit-iso-c-string-content} """} +++ +++@item @var{nl} @expansion{} +++@code{CR | CR-LF} +++@end table +++ +++@noindent +++Notes: +++ +++@itemize @bullet +++@item +++The CLI commands are still handled by the @sc{mi} interpreter; their +++output is described below. +++ +++@item +++The @code{@var{token}}, when present, is passed back when the command +++finishes. +++ +++@item +++Some @sc{mi} commands accept optional arguments as part of the parameter +++list. Each option is identified by a leading @samp{-} (dash) and may be +++followed by an optional argument parameter. Options occur first in the +++parameter list and can be delimited from normal parameters using +++@samp{--} (this is useful when some parameters begin with a dash). +++@end itemize +++ +++Pragmatics: +++ +++@itemize @bullet +++@item +++We want easy access to the existing CLI syntax (for debugging). +++ +++@item +++We want it to be easy to spot a @sc{mi} operation. +++@end itemize +++ +++@node GDB/MI Output Syntax +++@subsection @sc{gdb/mi} Output Syntax +++ +++@cindex output syntax of @sc{gdb/mi} +++@cindex @sc{gdb/mi}, output syntax +++The output from @sc{gdb/mi} consists of zero or more out-of-band records +++followed, optionally, by a single result record. This result record +++is for the most recent command. The sequence of output records is +++terminated by @samp{(gdb)}. +++ +++If an input command was prefixed with a @code{@var{token}} then the +++corresponding output for that command will also be prefixed by that same +++@var{token}. +++ +++@table @code +++@item @var{output} @expansion{} +++@code{( @var{out-of-band-record} )* [ @var{result-record} ] "(gdb)" @var{nl}} +++ +++@item @var{result-record} @expansion{} +++@code{ [ @var{token} ] "^" @var{result-class} ( "," @var{result} )* @var{nl}} +++ +++@item @var{out-of-band-record} @expansion{} +++@code{@var{async-record} | @var{stream-record}} +++ +++@item @var{async-record} @expansion{} +++@code{@var{exec-async-output} | @var{status-async-output} | @var{notify-async-output}} +++ +++@item @var{exec-async-output} @expansion{} +++@code{[ @var{token} ] "*" @var{async-output nl}} +++ +++@item @var{status-async-output} @expansion{} +++@code{[ @var{token} ] "+" @var{async-output nl}} +++ +++@item @var{notify-async-output} @expansion{} +++@code{[ @var{token} ] "=" @var{async-output nl}} +++ +++@item @var{async-output} @expansion{} +++@code{@var{async-class} ( "," @var{result} )*} +++ +++@item @var{result-class} @expansion{} +++@code{"done" | "running" | "connected" | "error" | "exit"} +++ +++@item @var{async-class} @expansion{} +++@code{"stopped" | @var{others}} (where @var{others} will be added +++depending on the needs---this is still in development). +++ +++@item @var{result} @expansion{} +++@code{ @var{variable} "=" @var{value}} +++ +++@item @var{variable} @expansion{} +++@code{ @var{string} } +++ +++@item @var{value} @expansion{} +++@code{ @var{const} | @var{tuple} | @var{list} } +++ +++@item @var{const} @expansion{} +++@code{@var{c-string}} +++ +++@item @var{tuple} @expansion{} +++@code{ "@{@}" | "@{" @var{result} ( "," @var{result} )* "@}" } +++ +++@item @var{list} @expansion{} +++@code{ "[]" | "[" @var{value} ( "," @var{value} )* "]" | "[" +++@var{result} ( "," @var{result} )* "]" } +++ +++@item @var{stream-record} @expansion{} +++@code{@var{console-stream-output} | @var{target-stream-output} | @var{log-stream-output}} +++ +++@item @var{console-stream-output} @expansion{} +++@code{"~" @var{c-string nl}} +++ +++@item @var{target-stream-output} @expansion{} +++@code{"@@" @var{c-string nl}} +++ +++@item @var{log-stream-output} @expansion{} +++@code{"&" @var{c-string nl}} +++ +++@item @var{nl} @expansion{} +++@code{CR | CR-LF} +++ +++@item @var{token} @expansion{} +++@emph{any sequence of digits}. +++@end table +++ +++@noindent +++Notes: +++ +++@itemize @bullet +++@item +++All output sequences end in a single line containing a period. +++ +++@item +++The @code{@var{token}} is from the corresponding request. Note that +++for all async output, while the token is allowed by the grammar and +++may be output by future versions of @value{GDBN} for select async +++output messages, it is generally omitted. Frontends should treat +++all async output as reporting general changes in the state of the +++target and there should be no need to associate async output to any +++prior command. +++ +++@item +++@cindex status output in @sc{gdb/mi} +++@var{status-async-output} contains on-going status information about the +++progress of a slow operation. It can be discarded. All status output is +++prefixed by @samp{+}. +++ +++@item +++@cindex async output in @sc{gdb/mi} +++@var{exec-async-output} contains asynchronous state change on the target +++(stopped, started, disappeared). All async output is prefixed by +++@samp{*}. +++ +++@item +++@cindex notify output in @sc{gdb/mi} +++@var{notify-async-output} contains supplementary information that the +++client should handle (e.g., a new breakpoint information). All notify +++output is prefixed by @samp{=}. +++ +++@item +++@cindex console output in @sc{gdb/mi} +++@var{console-stream-output} is output that should be displayed as is in the +++console. It is the textual response to a CLI command. All the console +++output is prefixed by @samp{~}. +++ +++@item +++@cindex target output in @sc{gdb/mi} +++@var{target-stream-output} is the output produced by the target program. +++All the target output is prefixed by @samp{@@}. +++ +++@item +++@cindex log output in @sc{gdb/mi} +++@var{log-stream-output} is output text coming from @value{GDBN}'s internals, for +++instance messages that should be displayed as part of an error log. All +++the log output is prefixed by @samp{&}. +++ +++@item +++@cindex list output in @sc{gdb/mi} +++New @sc{gdb/mi} commands should only output @var{lists} containing +++@var{values}. +++ +++ +++@end itemize +++ +++@xref{GDB/MI Stream Records, , @sc{gdb/mi} Stream Records}, for more +++details about the various output records. +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Compatibility with CLI +++@section @sc{gdb/mi} Compatibility with CLI +++ +++@cindex compatibility, @sc{gdb/mi} and CLI +++@cindex @sc{gdb/mi}, compatibility with CLI +++ +++For the developers convenience CLI commands can be entered directly, +++but there may be some unexpected behaviour. For example, commands +++that query the user will behave as if the user replied yes, breakpoint +++command lists are not executed and some CLI commands, such as +++@code{if}, @code{when} and @code{define}, prompt for further input with +++@samp{>}, which is not valid MI output. +++ +++This feature may be removed at some stage in the future and it is +++recommended that front ends use the @code{-interpreter-exec} command +++(@pxref{-interpreter-exec}). +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Development and Front Ends +++@section @sc{gdb/mi} Development and Front Ends +++@cindex @sc{gdb/mi} development +++ +++The application which takes the MI output and presents the state of the +++program being debugged to the user is called a @dfn{front end}. +++ +++Since @sc{gdb/mi} is used by a variety of front ends to @value{GDBN}, changes +++to the MI interface may break existing usage. This section describes how the +++protocol changes and how to request previous version of the protocol when it +++does. +++ +++Some changes in MI need not break a carefully designed front end, and +++for these the MI version will remain unchanged. The following is a +++list of changes that may occur within one level, so front ends should +++parse MI output in a way that can handle them: +++ +++@itemize @bullet +++@item +++New MI commands may be added. +++ +++@item +++New fields may be added to the output of any MI command. +++ +++@item +++The range of values for fields with specified values, e.g., +++@code{in_scope} (@pxref{-var-update}) may be extended. +++ +++@c The format of field's content e.g type prefix, may change so parse it +++@c at your own risk. Yes, in general? +++ +++@c The order of fields may change? Shouldn't really matter but it might +++@c resolve inconsistencies. +++@end itemize +++ +++If the changes are likely to break front ends, the MI version level +++will be increased by one. The new versions of the MI protocol are not compatible +++with the old versions. Old versions of MI remain available, allowing front ends +++to keep using them until they are modified to use the latest MI version. +++ +++Since @code{--interpreter=mi} always points to the latest MI version, it is +++recommended that front ends request a specific version of MI when launching +++@value{GDBN} (e.g. @code{--interpreter=mi2}) to make sure they get an +++interpreter with the MI version they expect. +++ +++The following table gives a summary of the released versions of the MI +++interface: the version number, the version of GDB in which it first appeared +++and the breaking changes compared to the previous version. +++ +++@multitable @columnfractions .05 .05 .9 +++@headitem MI version @tab GDB version @tab Breaking changes +++ +++@item +++@center 1 +++@tab +++@center 5.1 +++@tab +++None +++ +++@item +++@center 2 +++@tab +++@center 6.0 +++@tab +++ +++@itemize +++@item +++The @code{-environment-pwd}, @code{-environment-directory} and +++@code{-environment-path} commands now returns values using the MI output +++syntax, rather than CLI output syntax. +++ +++@item +++@code{-var-list-children}'s @code{children} result field is now a list, rather +++than a tuple. +++ +++@item +++@code{-var-update}'s @code{changelist} result field is now a list, rather than +++a tuple. +++@end itemize +++ +++@item +++@center 3 +++@tab +++@center 9.1 +++@tab +++ +++@itemize +++@item +++The output of information about multi-location breakpoints has changed in the +++responses to the @code{-break-insert} and @code{-break-info} commands, as well +++as in the @code{=breakpoint-created} and @code{=breakpoint-modified} events. +++The multiple locations are now placed in a @code{locations} field, whose value +++is a list. +++@end itemize +++ +++@end multitable +++ +++If your front end cannot yet migrate to a more recent version of the +++MI protocol, you can nevertheless selectively enable specific features +++available in those recent MI versions, using the following commands: +++ +++@table @code +++ +++@item -fix-multi-location-breakpoint-output +++Use the output for multi-location breakpoints which was introduced by +++MI 3, even when using MI versions 2 or 1. This command has no +++effect when using MI version 3 or later. +++ +++@end table +++ +++The best way to avoid unexpected changes in MI that might break your front +++end is to make your project known to @value{GDBN} developers and +++follow development on @email{gdb@@sourceware.org} and +++@email{gdb-patches@@sourceware.org}. +++@cindex mailing lists +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Output Records +++@section @sc{gdb/mi} Output Records +++ +++@menu +++* GDB/MI Result Records:: +++* GDB/MI Stream Records:: +++* GDB/MI Async Records:: +++* GDB/MI Breakpoint Information:: +++* GDB/MI Frame Information:: +++* GDB/MI Thread Information:: +++* GDB/MI Ada Exception Information:: +++@end menu +++ +++@node GDB/MI Result Records +++@subsection @sc{gdb/mi} Result Records +++ +++@cindex result records in @sc{gdb/mi} +++@cindex @sc{gdb/mi}, result records +++In addition to a number of out-of-band notifications, the response to a +++@sc{gdb/mi} command includes one of the following result indications: +++ +++@table @code +++@findex ^done +++@item "^done" [ "," @var{results} ] +++The synchronous operation was successful, @code{@var{results}} are the return +++values. +++ +++@item "^running" +++@findex ^running +++This result record is equivalent to @samp{^done}. Historically, it +++was output instead of @samp{^done} if the command has resumed the +++target. This behaviour is maintained for backward compatibility, but +++all frontends should treat @samp{^done} and @samp{^running} +++identically and rely on the @samp{*running} output record to determine +++which threads are resumed. +++ +++@item "^connected" +++@findex ^connected +++@value{GDBN} has connected to a remote target. +++ +++@item "^error" "," "msg=" @var{c-string} [ "," "code=" @var{c-string} ] +++@findex ^error +++The operation failed. The @code{msg=@var{c-string}} variable contains +++the corresponding error message. +++ +++If present, the @code{code=@var{c-string}} variable provides an error +++code on which consumers can rely on to detect the corresponding +++error condition. At present, only one error code is defined: +++ +++@table @samp +++@item "undefined-command" +++Indicates that the command causing the error does not exist. +++@end table +++ +++@item "^exit" +++@findex ^exit +++@value{GDBN} has terminated. +++ +++@end table +++ +++@node GDB/MI Stream Records +++@subsection @sc{gdb/mi} Stream Records +++ +++@cindex @sc{gdb/mi}, stream records +++@cindex stream records in @sc{gdb/mi} +++@value{GDBN} internally maintains a number of output streams: the console, the +++target, and the log. The output intended for each of these streams is +++funneled through the @sc{gdb/mi} interface using @dfn{stream records}. +++ +++Each stream record begins with a unique @dfn{prefix character} which +++identifies its stream (@pxref{GDB/MI Output Syntax, , @sc{gdb/mi} Output +++Syntax}). In addition to the prefix, each stream record contains a +++@code{@var{string-output}}. This is either raw text (with an implicit new +++line) or a quoted C string (which does not contain an implicit newline). +++ +++@table @code +++@item "~" @var{string-output} +++The console output stream contains text that should be displayed in the +++CLI console window. It contains the textual responses to CLI commands. +++ +++@item "@@" @var{string-output} +++The target output stream contains any textual output from the running +++target. This is only present when GDB's event loop is truly +++asynchronous, which is currently only the case for remote targets. +++ +++@item "&" @var{string-output} +++The log stream contains debugging messages being produced by @value{GDBN}'s +++internals. +++@end table +++ +++@node GDB/MI Async Records +++@subsection @sc{gdb/mi} Async Records +++ +++@cindex async records in @sc{gdb/mi} +++@cindex @sc{gdb/mi}, async records +++@dfn{Async} records are used to notify the @sc{gdb/mi} client of +++additional changes that have occurred. Those changes can either be a +++consequence of @sc{gdb/mi} commands (e.g., a breakpoint modified) or a result of +++target activity (e.g., target stopped). +++ +++The following is the list of possible async records: +++ +++@table @code +++ +++@item *running,thread-id="@var{thread}" +++The target is now running. The @var{thread} field can be the global +++thread ID of the thread that is now running, and it can be +++@samp{all} if all threads are running. The frontend should assume +++that no interaction with a running thread is possible after this +++notification is produced. The frontend should not assume that this +++notification is output only once for any command. @value{GDBN} may +++emit this notification several times, either for different threads, +++because it cannot resume all threads together, or even for a single +++thread, if the thread must be stepped though some code before letting +++it run freely. +++ +++@item *stopped,reason="@var{reason}",thread-id="@var{id}",stopped-threads="@var{stopped}",core="@var{core}" +++The target has stopped. The @var{reason} field can have one of the +++following values: +++ +++@table @code +++@item breakpoint-hit +++A breakpoint was reached. +++@item watchpoint-trigger +++A watchpoint was triggered. +++@item read-watchpoint-trigger +++A read watchpoint was triggered. +++@item access-watchpoint-trigger +++An access watchpoint was triggered. +++@item function-finished +++An -exec-finish or similar CLI command was accomplished. +++@item location-reached +++An -exec-until or similar CLI command was accomplished. +++@item watchpoint-scope +++A watchpoint has gone out of scope. +++@item end-stepping-range +++An -exec-next, -exec-next-instruction, -exec-step, -exec-step-instruction or +++similar CLI command was accomplished. +++@item exited-signalled +++The inferior exited because of a signal. +++@item exited +++The inferior exited. +++@item exited-normally +++The inferior exited normally. +++@item signal-received +++A signal was received by the inferior. +++@item solib-event +++The inferior has stopped due to a library being loaded or unloaded. +++This can happen when @code{stop-on-solib-events} (@pxref{Files}) is +++set or when a @code{catch load} or @code{catch unload} catchpoint is +++in use (@pxref{Set Catchpoints}). +++@item fork +++The inferior has forked. This is reported when @code{catch fork} +++(@pxref{Set Catchpoints}) has been used. +++@item vfork +++The inferior has vforked. This is reported in when @code{catch vfork} +++(@pxref{Set Catchpoints}) has been used. +++@item syscall-entry +++The inferior entered a system call. This is reported when @code{catch +++syscall} (@pxref{Set Catchpoints}) has been used. +++@item syscall-return +++The inferior returned from a system call. This is reported when +++@code{catch syscall} (@pxref{Set Catchpoints}) has been used. +++@item exec +++The inferior called @code{exec}. This is reported when @code{catch exec} +++(@pxref{Set Catchpoints}) has been used. +++@end table +++ +++The @var{id} field identifies the global thread ID of the thread +++that directly caused the stop -- for example by hitting a breakpoint. +++Depending on whether all-stop +++mode is in effect (@pxref{All-Stop Mode}), @value{GDBN} may either +++stop all threads, or only the thread that directly triggered the stop. +++If all threads are stopped, the @var{stopped} field will have the +++value of @code{"all"}. Otherwise, the value of the @var{stopped} +++field will be a list of thread identifiers. Presently, this list will +++always include a single thread, but frontend should be prepared to see +++several threads in the list. The @var{core} field reports the +++processor core on which the stop event has happened. This field may be absent +++if such information is not available. +++ +++@item =thread-group-added,id="@var{id}" +++@itemx =thread-group-removed,id="@var{id}" +++A thread group was either added or removed. The @var{id} field +++contains the @value{GDBN} identifier of the thread group. When a thread +++group is added, it generally might not be associated with a running +++process. When a thread group is removed, its id becomes invalid and +++cannot be used in any way. +++ +++@item =thread-group-started,id="@var{id}",pid="@var{pid}" +++A thread group became associated with a running program, +++either because the program was just started or the thread group +++was attached to a program. The @var{id} field contains the +++@value{GDBN} identifier of the thread group. The @var{pid} field +++contains process identifier, specific to the operating system. +++ +++@item =thread-group-exited,id="@var{id}"[,exit-code="@var{code}"] +++A thread group is no longer associated with a running program, +++either because the program has exited, or because it was detached +++from. The @var{id} field contains the @value{GDBN} identifier of the +++thread group. The @var{code} field is the exit code of the inferior; it exists +++only when the inferior exited with some code. +++ +++@item =thread-created,id="@var{id}",group-id="@var{gid}" +++@itemx =thread-exited,id="@var{id}",group-id="@var{gid}" +++A thread either was created, or has exited. The @var{id} field +++contains the global @value{GDBN} identifier of the thread. The @var{gid} +++field identifies the thread group this thread belongs to. +++ +++@item =thread-selected,id="@var{id}"[,frame="@var{frame}"] +++Informs that the selected thread or frame were changed. This notification +++is not emitted as result of the @code{-thread-select} or +++@code{-stack-select-frame} commands, but is emitted whenever an MI command +++that is not documented to change the selected thread and frame actually +++changes them. In particular, invoking, directly or indirectly +++(via user-defined command), the CLI @code{thread} or @code{frame} commands, +++will generate this notification. Changing the thread or frame from another +++user interface (see @ref{Interpreters}) will also generate this notification. +++ +++The @var{frame} field is only present if the newly selected thread is +++stopped. See @ref{GDB/MI Frame Information} for the format of its value. +++ +++We suggest that in response to this notification, front ends +++highlight the selected thread and cause subsequent commands to apply to +++that thread. +++ +++@item =library-loaded,... +++Reports that a new library file was loaded by the program. This +++notification has 5 fields---@var{id}, @var{target-name}, +++@var{host-name}, @var{symbols-loaded} and @var{ranges}. The @var{id} field is an +++opaque identifier of the library. For remote debugging case, +++@var{target-name} and @var{host-name} fields give the name of the +++library file on the target, and on the host respectively. For native +++debugging, both those fields have the same value. The +++@var{symbols-loaded} field is emitted only for backward compatibility +++and should not be relied on to convey any useful information. The +++@var{thread-group} field, if present, specifies the id of the thread +++group in whose context the library was loaded. If the field is +++absent, it means the library was loaded in the context of all present +++thread groups. The @var{ranges} field specifies the ranges of addresses belonging +++to this library. +++ +++@item =library-unloaded,... +++Reports that a library was unloaded by the program. This notification +++has 3 fields---@var{id}, @var{target-name} and @var{host-name} with +++the same meaning as for the @code{=library-loaded} notification. +++The @var{thread-group} field, if present, specifies the id of the +++thread group in whose context the library was unloaded. If the field is +++absent, it means the library was unloaded in the context of all present +++thread groups. +++ +++@item =traceframe-changed,num=@var{tfnum},tracepoint=@var{tpnum} +++@itemx =traceframe-changed,end +++Reports that the trace frame was changed and its new number is +++@var{tfnum}. The number of the tracepoint associated with this trace +++frame is @var{tpnum}. +++ +++@item =tsv-created,name=@var{name},initial=@var{initial} +++Reports that the new trace state variable @var{name} is created with +++initial value @var{initial}. +++ +++@item =tsv-deleted,name=@var{name} +++@itemx =tsv-deleted +++Reports that the trace state variable @var{name} is deleted or all +++trace state variables are deleted. +++ +++@item =tsv-modified,name=@var{name},initial=@var{initial}[,current=@var{current}] +++Reports that the trace state variable @var{name} is modified with +++the initial value @var{initial}. The current value @var{current} of +++trace state variable is optional and is reported if the current +++value of trace state variable is known. +++ +++@item =breakpoint-created,bkpt=@{...@} +++@itemx =breakpoint-modified,bkpt=@{...@} +++@itemx =breakpoint-deleted,id=@var{number} +++Reports that a breakpoint was created, modified, or deleted, +++respectively. Only user-visible breakpoints are reported to the MI +++user. +++ +++The @var{bkpt} argument is of the same form as returned by the various +++breakpoint commands; @xref{GDB/MI Breakpoint Commands}. The +++@var{number} is the ordinal number of the breakpoint. +++ +++Note that if a breakpoint is emitted in the result record of a +++command, then it will not also be emitted in an async record. +++ +++@item =record-started,thread-group="@var{id}",method="@var{method}"[,format="@var{format}"] +++@itemx =record-stopped,thread-group="@var{id}" +++Execution log recording was either started or stopped on an +++inferior. The @var{id} is the @value{GDBN} identifier of the thread +++group corresponding to the affected inferior. +++ +++The @var{method} field indicates the method used to record execution. If the +++method in use supports multiple recording formats, @var{format} will be present +++and contain the currently used format. @xref{Process Record and Replay}, +++for existing method and format values. +++ +++@item =cmd-param-changed,param=@var{param},value=@var{value} +++Reports that a parameter of the command @code{set @var{param}} is +++changed to @var{value}. In the multi-word @code{set} command, +++the @var{param} is the whole parameter list to @code{set} command. +++For example, In command @code{set check type on}, @var{param} +++is @code{check type} and @var{value} is @code{on}. +++ +++@item =memory-changed,thread-group=@var{id},addr=@var{addr},len=@var{len}[,type="code"] +++Reports that bytes from @var{addr} to @var{data} + @var{len} were +++written in an inferior. The @var{id} is the identifier of the +++thread group corresponding to the affected inferior. The optional +++@code{type="code"} part is reported if the memory written to holds +++executable code. +++@end table +++ +++@node GDB/MI Breakpoint Information +++@subsection @sc{gdb/mi} Breakpoint Information +++ +++When @value{GDBN} reports information about a breakpoint, a +++tracepoint, a watchpoint, or a catchpoint, it uses a tuple with the +++following fields: +++ +++@table @code +++@item number +++The breakpoint number. +++ +++@item type +++The type of the breakpoint. For ordinary breakpoints this will be +++@samp{breakpoint}, but many values are possible. +++ +++@item catch-type +++If the type of the breakpoint is @samp{catchpoint}, then this +++indicates the exact type of catchpoint. +++ +++@item disp +++This is the breakpoint disposition---either @samp{del}, meaning that +++the breakpoint will be deleted at the next stop, or @samp{keep}, +++meaning that the breakpoint will not be deleted. +++ +++@item enabled +++This indicates whether the breakpoint is enabled, in which case the +++value is @samp{y}, or disabled, in which case the value is @samp{n}. +++Note that this is not the same as the field @code{enable}. +++ +++@item addr +++The address of the breakpoint. This may be a hexidecimal number, +++giving the address; or the string @samp{}, for a pending +++breakpoint; or the string @samp{}, for a breakpoint with +++multiple locations. This field will not be present if no address can +++be determined. For example, a watchpoint does not have an address. +++ +++@item addr_flags +++Optional field containing any flags related to the address. These flags are +++architecture-dependent; see @ref{Architectures} for their meaning for a +++particular CPU. +++ +++@item func +++If known, the function in which the breakpoint appears. +++If not known, this field is not present. +++ +++@item filename +++The name of the source file which contains this function, if known. +++If not known, this field is not present. +++ +++@item fullname +++The full file name of the source file which contains this function, if +++known. If not known, this field is not present. +++ +++@item line +++The line number at which this breakpoint appears, if known. +++If not known, this field is not present. +++ +++@item at +++If the source file is not known, this field may be provided. If +++provided, this holds the address of the breakpoint, possibly followed +++by a symbol name. +++ +++@item pending +++If this breakpoint is pending, this field is present and holds the +++text used to set the breakpoint, as entered by the user. +++ +++@item evaluated-by +++Where this breakpoint's condition is evaluated, either @samp{host} or +++@samp{target}. +++ +++@item thread +++If this is a thread-specific breakpoint, then this identifies the +++thread in which the breakpoint can trigger. +++ +++@item task +++If this breakpoint is restricted to a particular Ada task, then this +++field will hold the task identifier. +++ +++@item cond +++If the breakpoint is conditional, this is the condition expression. +++ +++@item ignore +++The ignore count of the breakpoint. +++ +++@item enable +++The enable count of the breakpoint. +++ +++@item traceframe-usage +++FIXME. +++ +++@item static-tracepoint-marker-string-id +++For a static tracepoint, the name of the static tracepoint marker. +++ +++@item mask +++For a masked watchpoint, this is the mask. +++ +++@item pass +++A tracepoint's pass count. +++ +++@item original-location +++The location of the breakpoint as originally specified by the user. +++This field is optional. +++ +++@item times +++The number of times the breakpoint has been hit. +++ +++@item installed +++This field is only given for tracepoints. This is either @samp{y}, +++meaning that the tracepoint is installed, or @samp{n}, meaning that it +++is not. +++ +++@item what +++Some extra data, the exact contents of which are type-dependent. +++ +++@item locations +++This field is present if the breakpoint has multiple locations. It is also +++exceptionally present if the breakpoint is enabled and has a single, disabled +++location. +++ +++The value is a list of locations. The format of a location is described below. +++ +++@end table +++ +++A location in a multi-location breakpoint is represented as a tuple with the +++following fields: +++ +++@table @code +++ +++@item number +++The location number as a dotted pair, like @samp{1.2}. The first digit is the +++number of the parent breakpoint. The second digit is the number of the +++location within that breakpoint. +++ +++@item enabled +++This indicates whether the location is enabled, in which case the +++value is @samp{y}, or disabled, in which case the value is @samp{n}. +++Note that this is not the same as the field @code{enable}. +++ +++@item addr +++The address of this location as an hexidecimal number. +++ +++@item addr_flags +++Optional field containing any flags related to the address. These flags are +++architecture-dependent; see @ref{Architectures} for their meaning for a +++particular CPU. +++ +++@item func +++If known, the function in which the location appears. +++If not known, this field is not present. +++ +++@item file +++The name of the source file which contains this location, if known. +++If not known, this field is not present. +++ +++@item fullname +++The full file name of the source file which contains this location, if +++known. If not known, this field is not present. +++ +++@item line +++The line number at which this location appears, if known. +++If not known, this field is not present. +++ +++@item thread-groups +++The thread groups this location is in. +++ +++@end table +++ +++For example, here is what the output of @code{-break-insert} +++(@pxref{GDB/MI Breakpoint Commands}) might be: +++ +++@smallexample +++-> -break-insert main +++<- ^done,bkpt=@{number="1",type="breakpoint",disp="keep", +++ enabled="y",addr="0x08048564",func="main",file="myprog.c", +++ fullname="/home/nickrob/myprog.c",line="68",thread-groups=["i1"], +++ times="0"@} +++<- (gdb) +++@end smallexample +++ +++@node GDB/MI Frame Information +++@subsection @sc{gdb/mi} Frame Information +++ +++Response from many MI commands includes an information about stack +++frame. This information is a tuple that may have the following +++fields: +++ +++@table @code +++@item level +++The level of the stack frame. The innermost frame has the level of +++zero. This field is always present. +++ +++@item func +++The name of the function corresponding to the frame. This field may +++be absent if @value{GDBN} is unable to determine the function name. +++ +++@item addr +++The code address for the frame. This field is always present. +++ +++@item addr_flags +++Optional field containing any flags related to the address. These flags are +++architecture-dependent; see @ref{Architectures} for their meaning for a +++particular CPU. +++ +++@item file +++The name of the source files that correspond to the frame's code +++address. This field may be absent. +++ +++@item line +++The source line corresponding to the frames' code address. This field +++may be absent. +++ +++@item from +++The name of the binary file (either executable or shared library) the +++corresponds to the frame's code address. This field may be absent. +++ +++@end table +++ +++@node GDB/MI Thread Information +++@subsection @sc{gdb/mi} Thread Information +++ +++Whenever @value{GDBN} has to report an information about a thread, it +++uses a tuple with the following fields. The fields are always present unless +++stated otherwise. +++ +++@table @code +++@item id +++The global numeric id assigned to the thread by @value{GDBN}. +++ +++@item target-id +++The target-specific string identifying the thread. +++ +++@item details +++Additional information about the thread provided by the target. +++It is supposed to be human-readable and not interpreted by the +++frontend. This field is optional. +++ +++@item name +++The name of the thread. If the user specified a name using the +++@code{thread name} command, then this name is given. Otherwise, if +++@value{GDBN} can extract the thread name from the target, then that +++name is given. If @value{GDBN} cannot find the thread name, then this +++field is omitted. +++ +++@item state +++The execution state of the thread, either @samp{stopped} or @samp{running}, +++depending on whether the thread is presently running. +++ +++@item frame +++The stack frame currently executing in the thread. This field is only present +++if the thread is stopped. Its format is documented in +++@ref{GDB/MI Frame Information}. +++ +++@item core +++The value of this field is an integer number of the processor core the +++thread was last seen on. This field is optional. +++@end table +++ +++@node GDB/MI Ada Exception Information +++@subsection @sc{gdb/mi} Ada Exception Information +++ +++Whenever a @code{*stopped} record is emitted because the program +++stopped after hitting an exception catchpoint (@pxref{Set Catchpoints}), +++@value{GDBN} provides the name of the exception that was raised via +++the @code{exception-name} field. Also, for exceptions that were raised +++with an exception message, @value{GDBN} provides that message via +++the @code{exception-message} field. +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Simple Examples +++@section Simple Examples of @sc{gdb/mi} Interaction +++@cindex @sc{gdb/mi}, simple examples +++ +++This subsection presents several simple examples of interaction using +++the @sc{gdb/mi} interface. In these examples, @samp{->} means that the +++following line is passed to @sc{gdb/mi} as input, while @samp{<-} means +++the output received from @sc{gdb/mi}. +++ +++Note the line breaks shown in the examples are here only for +++readability, they don't appear in the real output. +++ +++@subheading Setting a Breakpoint +++ +++Setting a breakpoint generates synchronous output which contains detailed +++information of the breakpoint. +++ +++@smallexample +++-> -break-insert main +++<- ^done,bkpt=@{number="1",type="breakpoint",disp="keep", +++ enabled="y",addr="0x08048564",func="main",file="myprog.c", +++ fullname="/home/nickrob/myprog.c",line="68",thread-groups=["i1"], +++ times="0"@} +++<- (gdb) +++@end smallexample +++ +++@subheading Program Execution +++ +++Program execution generates asynchronous records and MI gives the +++reason that execution stopped. +++ +++@smallexample +++-> -exec-run +++<- ^running +++<- (gdb) +++<- *stopped,reason="breakpoint-hit",disp="keep",bkptno="1",thread-id="0", +++ frame=@{addr="0x08048564",func="main", +++ args=[@{name="argc",value="1"@},@{name="argv",value="0xbfc4d4d4"@}], +++ file="myprog.c",fullname="/home/nickrob/myprog.c",line="68", +++ arch="i386:x86_64"@} +++<- (gdb) +++-> -exec-continue +++<- ^running +++<- (gdb) +++<- *stopped,reason="exited-normally" +++<- (gdb) +++@end smallexample +++ +++@subheading Quitting @value{GDBN} +++ +++Quitting @value{GDBN} just prints the result class @samp{^exit}. +++ +++@smallexample +++-> (gdb) +++<- -gdb-exit +++<- ^exit +++@end smallexample +++ +++Please note that @samp{^exit} is printed immediately, but it might +++take some time for @value{GDBN} to actually exit. During that time, @value{GDBN} +++performs necessary cleanups, including killing programs being debugged +++or disconnecting from debug hardware, so the frontend should wait till +++@value{GDBN} exits and should only forcibly kill @value{GDBN} if it +++fails to exit in reasonable time. +++ +++@subheading A Bad Command +++ +++Here's what happens if you pass a non-existent command: +++ +++@smallexample +++-> -rubbish +++<- ^error,msg="Undefined MI command: rubbish" +++<- (gdb) +++@end smallexample +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Command Description Format +++@section @sc{gdb/mi} Command Description Format +++ +++The remaining sections describe blocks of commands. Each block of +++commands is laid out in a fashion similar to this section. +++ +++@subheading Motivation +++ +++The motivation for this collection of commands. +++ +++@subheading Introduction +++ +++A brief introduction to this collection of commands as a whole. +++ +++@subheading Commands +++ +++For each command in the block, the following is described: +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -command @var{args}@dots{} +++@end smallexample +++ +++@subsubheading Result +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} CLI command(s), if any. +++ +++@subsubheading Example +++ +++Example(s) formatted for readability. Some of the described commands have +++not been implemented yet and these are labeled N.A.@: (not available). +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Breakpoint Commands +++@section @sc{gdb/mi} Breakpoint Commands +++ +++@cindex breakpoint commands for @sc{gdb/mi} +++@cindex @sc{gdb/mi}, breakpoint commands +++This section documents @sc{gdb/mi} commands for manipulating +++breakpoints. +++ +++@subheading The @code{-break-after} Command +++@findex -break-after +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-after @var{number} @var{count} +++@end smallexample +++ +++The breakpoint number @var{number} is not in effect until it has been +++hit @var{count} times. To see how this is reflected in the output of +++the @samp{-break-list} command, see the description of the +++@samp{-break-list} command below. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{ignore}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-insert main +++^done,bkpt=@{number="1",type="breakpoint",disp="keep", +++enabled="y",addr="0x000100d0",func="main",file="hello.c", +++fullname="/home/foo/hello.c",line="5",thread-groups=["i1"], +++times="0"@} +++(gdb) +++-break-after 1 3 +++~ +++^done +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="1",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x000100d0",func="main",file="hello.c",fullname="/home/foo/hello.c", +++line="5",thread-groups=["i1"],times="0",ignore="3"@}]@} +++(gdb) +++@end smallexample +++ +++@ignore +++@subheading The @code{-break-catch} Command +++@findex -break-catch +++@end ignore +++ +++@subheading The @code{-break-commands} Command +++@findex -break-commands +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-commands @var{number} [ @var{command1} ... @var{commandN} ] +++@end smallexample +++ +++Specifies the CLI commands that should be executed when breakpoint +++@var{number} is hit. The parameters @var{command1} to @var{commandN} +++are the commands. If no command is specified, any previously-set +++commands are cleared. @xref{Break Commands}. Typical use of this +++functionality is tracing a program, that is, printing of values of +++some variables whenever breakpoint is hit and then continuing. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{commands}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-insert main +++^done,bkpt=@{number="1",type="breakpoint",disp="keep", +++enabled="y",addr="0x000100d0",func="main",file="hello.c", +++fullname="/home/foo/hello.c",line="5",thread-groups=["i1"], +++times="0"@} +++(gdb) +++-break-commands 1 "print v" "continue" +++^done +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-condition} Command +++@findex -break-condition +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-condition @var{number} @var{expr} +++@end smallexample +++ +++Breakpoint @var{number} will stop the program only if the condition in +++@var{expr} is true. The condition becomes part of the +++@samp{-break-list} output (see the description of the @samp{-break-list} +++command below). +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{condition}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-condition 1 1 +++^done +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="1",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x000100d0",func="main",file="hello.c",fullname="/home/foo/hello.c", +++line="5",cond="1",thread-groups=["i1"],times="0",ignore="3"@}]@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-delete} Command +++@findex -break-delete +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-delete ( @var{breakpoint} )+ +++@end smallexample +++ +++Delete the breakpoint(s) whose number(s) are specified in the argument +++list. This is obviously reflected in the breakpoint list. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{delete}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-delete 1 +++^done +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="0",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[]@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-disable} Command +++@findex -break-disable +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-disable ( @var{breakpoint} )+ +++@end smallexample +++ +++Disable the named @var{breakpoint}(s). The field @samp{enabled} in the +++break list is now set to @samp{n} for the named @var{breakpoint}(s). +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{disable}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-disable 2 +++^done +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="1",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="2",type="breakpoint",disp="keep",enabled="n", +++addr="0x000100d0",func="main",file="hello.c",fullname="/home/foo/hello.c", +++line="5",thread-groups=["i1"],times="0"@}]@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-enable} Command +++@findex -break-enable +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-enable ( @var{breakpoint} )+ +++@end smallexample +++ +++Enable (previously disabled) @var{breakpoint}(s). +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{enable}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-enable 2 +++^done +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="1",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="2",type="breakpoint",disp="keep",enabled="y", +++addr="0x000100d0",func="main",file="hello.c",fullname="/home/foo/hello.c", +++line="5",thread-groups=["i1"],times="0"@}]@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-info} Command +++@findex -break-info +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-info @var{breakpoint} +++@end smallexample +++ +++@c REDUNDANT??? +++Get information about a single breakpoint. +++ +++The result is a table of breakpoints. @xref{GDB/MI Breakpoint +++Information}, for details on the format of each breakpoint in the +++table. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info break @var{breakpoint}}. +++ +++@subsubheading Example +++N.A. +++ +++@subheading The @code{-break-insert} Command +++@findex -break-insert +++@anchor{-break-insert} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-insert [ -t ] [ -h ] [ -f ] [ -d ] [ -a ] +++ [ -c @var{condition} ] [ -i @var{ignore-count} ] +++ [ -p @var{thread-id} ] [ @var{location} ] +++@end smallexample +++ +++@noindent +++If specified, @var{location}, can be one of: +++ +++@table @var +++@item linespec location +++A linespec location. @xref{Linespec Locations}. +++ +++@item explicit location +++An explicit location. @sc{gdb/mi} explicit locations are +++analogous to the CLI's explicit locations using the option names +++listed below. @xref{Explicit Locations}. +++ +++@table @samp +++@item --source @var{filename} +++The source file name of the location. This option requires the use +++of either @samp{--function} or @samp{--line}. +++ +++@item --function @var{function} +++The name of a function or method. +++ +++@item --label @var{label} +++The name of a label. +++ +++@item --line @var{lineoffset} +++An absolute or relative line offset from the start of the location. +++@end table +++ +++@item address location +++An address location, *@var{address}. @xref{Address Locations}. +++@end table +++ +++@noindent +++The possible optional parameters of this command are: +++ +++@table @samp +++@item -t +++Insert a temporary breakpoint. +++@item -h +++Insert a hardware breakpoint. +++@item -f +++If @var{location} cannot be parsed (for example if it +++refers to unknown files or functions), create a pending +++breakpoint. Without this flag, @value{GDBN} will report +++an error, and won't create a breakpoint, if @var{location} +++cannot be parsed. +++@item -d +++Create a disabled breakpoint. +++@item -a +++Create a tracepoint. @xref{Tracepoints}. When this parameter +++is used together with @samp{-h}, a fast tracepoint is created. +++@item -c @var{condition} +++Make the breakpoint conditional on @var{condition}. +++@item -i @var{ignore-count} +++Initialize the @var{ignore-count}. +++@item -p @var{thread-id} +++Restrict the breakpoint to the thread with the specified global +++@var{thread-id}. +++@end table +++ +++@subsubheading Result +++ +++@xref{GDB/MI Breakpoint Information}, for details on the format of the +++resulting breakpoint. +++ +++Note: this format is open to change. +++@c An out-of-band breakpoint instead of part of the result? +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{break}, @samp{tbreak}, +++@samp{hbreak}, and @samp{thbreak}. @c and @samp{rbreak}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-insert main +++^done,bkpt=@{number="1",addr="0x0001072c",file="recursive2.c", +++fullname="/home/foo/recursive2.c,line="4",thread-groups=["i1"], +++times="0"@} +++(gdb) +++-break-insert -t foo +++^done,bkpt=@{number="2",addr="0x00010774",file="recursive2.c", +++fullname="/home/foo/recursive2.c,line="11",thread-groups=["i1"], +++times="0"@} +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="2",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x0001072c", func="main",file="recursive2.c", +++fullname="/home/foo/recursive2.c,"line="4",thread-groups=["i1"], +++times="0"@}, +++bkpt=@{number="2",type="breakpoint",disp="del",enabled="y", +++addr="0x00010774",func="foo",file="recursive2.c", +++fullname="/home/foo/recursive2.c",line="11",thread-groups=["i1"], +++times="0"@}]@} +++(gdb) +++@c -break-insert -r foo.* +++@c ~int foo(int, int); +++@c ^done,bkpt=@{number="3",addr="0x00010774",file="recursive2.c, +++@c "fullname="/home/foo/recursive2.c",line="11",thread-groups=["i1"], +++@c times="0"@} +++@c (gdb) +++@end smallexample +++ +++@subheading The @code{-dprintf-insert} Command +++@findex -dprintf-insert +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -dprintf-insert [ -t ] [ -f ] [ -d ] +++ [ -c @var{condition} ] [ -i @var{ignore-count} ] +++ [ -p @var{thread-id} ] [ @var{location} ] [ @var{format} ] +++ [ @var{argument} ] +++@end smallexample +++ +++@noindent +++If supplied, @var{location} may be specified the same way as for +++the @code{-break-insert} command. @xref{-break-insert}. +++ +++The possible optional parameters of this command are: +++ +++@table @samp +++@item -t +++Insert a temporary breakpoint. +++@item -f +++If @var{location} cannot be parsed (for example, if it +++refers to unknown files or functions), create a pending +++breakpoint. Without this flag, @value{GDBN} will report +++an error, and won't create a breakpoint, if @var{location} +++cannot be parsed. +++@item -d +++Create a disabled breakpoint. +++@item -c @var{condition} +++Make the breakpoint conditional on @var{condition}. +++@item -i @var{ignore-count} +++Set the ignore count of the breakpoint (@pxref{Conditions, ignore count}) +++to @var{ignore-count}. +++@item -p @var{thread-id} +++Restrict the breakpoint to the thread with the specified global +++@var{thread-id}. +++@end table +++ +++@subsubheading Result +++ +++@xref{GDB/MI Breakpoint Information}, for details on the format of the +++resulting breakpoint. +++ +++@c An out-of-band breakpoint instead of part of the result? +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{dprintf}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++4-dprintf-insert foo "At foo entry\n" +++4^done,bkpt=@{number="1",type="dprintf",disp="keep",enabled="y", +++addr="0x000000000040061b",func="foo",file="mi-dprintf.c", +++fullname="mi-dprintf.c",line="25",thread-groups=["i1"], +++times="0",script=@{"printf \"At foo entry\\n\"","continue"@}, +++original-location="foo"@} +++(gdb) +++5-dprintf-insert 26 "arg=%d, g=%d\n" arg g +++5^done,bkpt=@{number="2",type="dprintf",disp="keep",enabled="y", +++addr="0x000000000040062a",func="foo",file="mi-dprintf.c", +++fullname="mi-dprintf.c",line="26",thread-groups=["i1"], +++times="0",script=@{"printf \"arg=%d, g=%d\\n\", arg, g","continue"@}, +++original-location="mi-dprintf.c:26"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-list} Command +++@findex -break-list +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-list +++@end smallexample +++ +++Displays the list of inserted breakpoints, showing the following fields: +++ +++@table @samp +++@item Number +++number of the breakpoint +++@item Type +++type of the breakpoint: @samp{breakpoint} or @samp{watchpoint} +++@item Disposition +++should the breakpoint be deleted or disabled when it is hit: @samp{keep} +++or @samp{nokeep} +++@item Enabled +++is the breakpoint enabled or no: @samp{y} or @samp{n} +++@item Address +++memory location at which the breakpoint is set +++@item What +++logical location of the breakpoint, expressed by function name, file +++name, line number +++@item Thread-groups +++list of thread groups to which this breakpoint applies +++@item Times +++number of times the breakpoint has been hit +++@end table +++ +++If there are no breakpoints or watchpoints, the @code{BreakpointTable} +++@code{body} field is an empty list. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info break}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="2",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x000100d0",func="main",file="hello.c",line="5",thread-groups=["i1"], +++times="0"@}, +++bkpt=@{number="2",type="breakpoint",disp="keep",enabled="y", +++addr="0x00010114",func="foo",file="hello.c",fullname="/home/foo/hello.c", +++line="13",thread-groups=["i1"],times="0"@}]@} +++(gdb) +++@end smallexample +++ +++Here's an example of the result when there are no breakpoints: +++ +++@smallexample +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="0",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[]@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-break-passcount} Command +++@findex -break-passcount +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-passcount @var{tracepoint-number} @var{passcount} +++@end smallexample +++ +++Set the passcount for tracepoint @var{tracepoint-number} to +++@var{passcount}. If the breakpoint referred to by @var{tracepoint-number} +++is not a tracepoint, error is emitted. This corresponds to CLI +++command @samp{passcount}. +++ +++@subheading The @code{-break-watch} Command +++@findex -break-watch +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -break-watch [ -a | -r ] +++@end smallexample +++ +++Create a watchpoint. With the @samp{-a} option it will create an +++@dfn{access} watchpoint, i.e., a watchpoint that triggers either on a +++read from or on a write to the memory location. With the @samp{-r} +++option, the watchpoint created is a @dfn{read} watchpoint, i.e., it will +++trigger only when the memory location is accessed for reading. Without +++either of the options, the watchpoint created is a regular watchpoint, +++i.e., it will trigger when the memory location is accessed for writing. +++@xref{Set Watchpoints, , Setting Watchpoints}. +++ +++Note that @samp{-break-list} will report a single list of watchpoints and +++breakpoints inserted. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{watch}, @samp{awatch}, and +++@samp{rwatch}. +++ +++@subsubheading Example +++ +++Setting a watchpoint on a variable in the @code{main} function: +++ +++@smallexample +++(gdb) +++-break-watch x +++^done,wpt=@{number="2",exp="x"@} +++(gdb) +++-exec-continue +++^running +++(gdb) +++*stopped,reason="watchpoint-trigger",wpt=@{number="2",exp="x"@}, +++value=@{old="-268439212",new="55"@}, +++frame=@{func="main",args=[],file="recursive2.c", +++fullname="/home/foo/bar/recursive2.c",line="5",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++Setting a watchpoint on a variable local to a function. @value{GDBN} will stop +++the program execution twice: first for the variable changing value, then +++for the watchpoint going out of scope. +++ +++@smallexample +++(gdb) +++-break-watch C +++^done,wpt=@{number="5",exp="C"@} +++(gdb) +++-exec-continue +++^running +++(gdb) +++*stopped,reason="watchpoint-trigger", +++wpt=@{number="5",exp="C"@},value=@{old="-276895068",new="3"@}, +++frame=@{func="callee4",args=[], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="13", +++arch="i386:x86_64"@} +++(gdb) +++-exec-continue +++^running +++(gdb) +++*stopped,reason="watchpoint-scope",wpnum="5", +++frame=@{func="callee3",args=[@{name="strarg", +++value="0x11940 \"A string argument.\""@}], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="18", +++arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++Listing breakpoints and watchpoints, at different points in the program +++execution. Note that once the watchpoint goes out of scope, it is +++deleted. +++ +++@smallexample +++(gdb) +++-break-watch C +++^done,wpt=@{number="2",exp="C"@} +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="2",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x00010734",func="callee4", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/devo/gdb/testsuite/gdb.mi/basics.c"line="8",thread-groups=["i1"], +++times="1"@}, +++bkpt=@{number="2",type="watchpoint",disp="keep", +++enabled="y",addr="",what="C",thread-groups=["i1"],times="0"@}]@} +++(gdb) +++-exec-continue +++^running +++(gdb) +++*stopped,reason="watchpoint-trigger",wpt=@{number="2",exp="C"@}, +++value=@{old="-276895068",new="3"@}, +++frame=@{func="callee4",args=[], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="13", +++arch="i386:x86_64"@} +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="2",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x00010734",func="callee4", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/devo/gdb/testsuite/gdb.mi/basics.c",line="8",thread-groups=["i1"], +++times="1"@}, +++bkpt=@{number="2",type="watchpoint",disp="keep", +++enabled="y",addr="",what="C",thread-groups=["i1"],times="-5"@}]@} +++(gdb) +++-exec-continue +++^running +++^done,reason="watchpoint-scope",wpnum="2", +++frame=@{func="callee3",args=[@{name="strarg", +++value="0x11940 \"A string argument.\""@}], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="18", +++arch="i386:x86_64"@} +++(gdb) +++-break-list +++^done,BreakpointTable=@{nr_rows="1",nr_cols="6", +++hdr=[@{width="3",alignment="-1",col_name="number",colhdr="Num"@}, +++@{width="14",alignment="-1",col_name="type",colhdr="Type"@}, +++@{width="4",alignment="-1",col_name="disp",colhdr="Disp"@}, +++@{width="3",alignment="-1",col_name="enabled",colhdr="Enb"@}, +++@{width="10",alignment="-1",col_name="addr",colhdr="Address"@}, +++@{width="40",alignment="2",col_name="what",colhdr="What"@}], +++body=[bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x00010734",func="callee4", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/devo/gdb/testsuite/gdb.mi/basics.c",line="8", +++thread-groups=["i1"],times="1"@}]@} +++(gdb) +++@end smallexample +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Catchpoint Commands +++@section @sc{gdb/mi} Catchpoint Commands +++ +++This section documents @sc{gdb/mi} commands for manipulating +++catchpoints. +++ +++@menu +++* Shared Library GDB/MI Catchpoint Commands:: +++* Ada Exception GDB/MI Catchpoint Commands:: +++* C++ Exception GDB/MI Catchpoint Commands:: +++@end menu +++ +++@node Shared Library GDB/MI Catchpoint Commands +++@subsection Shared Library @sc{gdb/mi} Catchpoints +++ +++@subheading The @code{-catch-load} Command +++@findex -catch-load +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-load [ -t ] [ -d ] @var{regexp} +++@end smallexample +++ +++Add a catchpoint for library load events. If the @samp{-t} option is used, +++the catchpoint is a temporary one (@pxref{Set Breaks, ,Setting +++Breakpoints}). If the @samp{-d} option is used, the catchpoint is created +++in a disabled state. The @samp{regexp} argument is a regular +++expression used to match the name of the loaded library. +++ +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{catch load}. +++ +++@subsubheading Example +++ +++@smallexample +++-catch-load -t foo.so +++^done,bkpt=@{number="1",type="catchpoint",disp="del",enabled="y", +++what="load of library matching foo.so",catch-type="load",times="0"@} +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-catch-unload} Command +++@findex -catch-unload +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-unload [ -t ] [ -d ] @var{regexp} +++@end smallexample +++ +++Add a catchpoint for library unload events. If the @samp{-t} option is +++used, the catchpoint is a temporary one (@pxref{Set Breaks, ,Setting +++Breakpoints}). If the @samp{-d} option is used, the catchpoint is +++created in a disabled state. The @samp{regexp} argument is a regular +++expression used to match the name of the unloaded library. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{catch unload}. +++ +++@subsubheading Example +++ +++@smallexample +++-catch-unload -d bar.so +++^done,bkpt=@{number="2",type="catchpoint",disp="keep",enabled="n", +++what="load of library matching bar.so",catch-type="unload",times="0"@} +++(gdb) +++@end smallexample +++ +++@node Ada Exception GDB/MI Catchpoint Commands +++@subsection Ada Exception @sc{gdb/mi} Catchpoints +++ +++The following @sc{gdb/mi} commands can be used to create catchpoints +++that stop the execution when Ada exceptions are being raised. +++ +++@subheading The @code{-catch-assert} Command +++@findex -catch-assert +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-assert [ -c @var{condition}] [ -d ] [ -t ] +++@end smallexample +++ +++Add a catchpoint for failed Ada assertions. +++ +++The possible optional parameters for this command are: +++ +++@table @samp +++@item -c @var{condition} +++Make the catchpoint conditional on @var{condition}. +++@item -d +++Create a disabled catchpoint. +++@item -t +++Create a temporary catchpoint. +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{catch assert}. +++ +++@subsubheading Example +++ +++@smallexample +++-catch-assert +++^done,bkptno="5",bkpt=@{number="5",type="breakpoint",disp="keep", +++enabled="y",addr="0x0000000000404888",what="failed Ada assertions", +++thread-groups=["i1"],times="0", +++original-location="__gnat_debug_raise_assert_failure"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-catch-exception} Command +++@findex -catch-exception +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-exception [ -c @var{condition}] [ -d ] [ -e @var{exception-name} ] +++ [ -t ] [ -u ] +++@end smallexample +++ +++Add a catchpoint stopping when Ada exceptions are raised. +++By default, the command stops the program when any Ada exception +++gets raised. But it is also possible, by using some of the +++optional parameters described below, to create more selective +++catchpoints. +++ +++The possible optional parameters for this command are: +++ +++@table @samp +++@item -c @var{condition} +++Make the catchpoint conditional on @var{condition}. +++@item -d +++Create a disabled catchpoint. +++@item -e @var{exception-name} +++Only stop when @var{exception-name} is raised. This option cannot +++be used combined with @samp{-u}. +++@item -t +++Create a temporary catchpoint. +++@item -u +++Stop only when an unhandled exception gets raised. This option +++cannot be used combined with @samp{-e}. +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{catch exception} +++and @samp{catch exception unhandled}. +++ +++@subsubheading Example +++ +++@smallexample +++-catch-exception -e Program_Error +++^done,bkptno="4",bkpt=@{number="4",type="breakpoint",disp="keep", +++enabled="y",addr="0x0000000000404874", +++what="`Program_Error' Ada exception", thread-groups=["i1"], +++times="0",original-location="__gnat_debug_raise_exception"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-catch-handlers} Command +++@findex -catch-handlers +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-handlers [ -c @var{condition}] [ -d ] [ -e @var{exception-name} ] +++ [ -t ] +++@end smallexample +++ +++Add a catchpoint stopping when Ada exceptions are handled. +++By default, the command stops the program when any Ada exception +++gets handled. But it is also possible, by using some of the +++optional parameters described below, to create more selective +++catchpoints. +++ +++The possible optional parameters for this command are: +++ +++@table @samp +++@item -c @var{condition} +++Make the catchpoint conditional on @var{condition}. +++@item -d +++Create a disabled catchpoint. +++@item -e @var{exception-name} +++Only stop when @var{exception-name} is handled. +++@item -t +++Create a temporary catchpoint. +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{catch handlers}. +++ +++@subsubheading Example +++ +++@smallexample +++-catch-handlers -e Constraint_Error +++^done,bkptno="4",bkpt=@{number="4",type="breakpoint",disp="keep", +++enabled="y",addr="0x0000000000402f68", +++what="`Constraint_Error' Ada exception handlers",thread-groups=["i1"], +++times="0",original-location="__gnat_begin_handler"@} +++(gdb) +++@end smallexample +++ +++@node C++ Exception GDB/MI Catchpoint Commands +++@subsection C@t{++} Exception @sc{gdb/mi} Catchpoints +++ +++The following @sc{gdb/mi} commands can be used to create catchpoints +++that stop the execution when C@t{++} exceptions are being throw, rethrown, +++or caught. +++ +++@subheading The @code{-catch-throw} Command +++@findex -catch-throw +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-throw [ -t ] [ -r @var{regexp}] +++@end smallexample +++ +++Stop when the debuggee throws a C@t{++} exception. If @var{regexp} is +++given, then only exceptions whose type matches the regular expression +++will be caught. +++ +++If @samp{-t} is given, then the catchpoint is enabled only for one +++stop, the catchpoint is automatically deleted after stopping once for +++the event. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{catch throw} +++and @samp{tcatch throw} (@pxref{Set Catchpoints}). +++ +++@subsubheading Example +++ +++@smallexample +++-catch-throw -r exception_type +++^done,bkpt=@{number="1",type="catchpoint",disp="keep",enabled="y", +++ what="exception throw",catch-type="throw", +++ thread-groups=["i1"], +++ regexp="exception_type",times="0"@} +++(gdb) +++-exec-run +++^running +++(gdb) +++~"\n" +++~"Catchpoint 1 (exception thrown), 0x00007ffff7ae00ed +++ in __cxa_throw () from /lib64/libstdc++.so.6\n" +++*stopped,bkptno="1",reason="breakpoint-hit",disp="keep", +++ frame=@{addr="0x00007ffff7ae00ed",func="__cxa_throw", +++ args=[],from="/lib64/libstdc++.so.6",arch="i386:x86-64"@}, +++ thread-id="1",stopped-threads="all",core="6" +++(gdb) +++@end smallexample +++ +++@subheading The @code{-catch-rethrow} Command +++@findex -catch-rethrow +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-rethrow [ -t ] [ -r @var{regexp}] +++@end smallexample +++ +++Stop when a C@t{++} exception is re-thrown. If @var{regexp} is given, +++then only exceptions whose type matches the regular expression will be +++caught. +++ +++If @samp{-t} is given, then the catchpoint is enabled only for one +++stop, the catchpoint is automatically deleted after the first event is +++caught. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{catch rethrow} +++and @samp{tcatch rethrow} (@pxref{Set Catchpoints}). +++ +++@subsubheading Example +++ +++@smallexample +++-catch-rethrow -r exception_type +++^done,bkpt=@{number="1",type="catchpoint",disp="keep",enabled="y", +++ what="exception rethrow",catch-type="rethrow", +++ thread-groups=["i1"], +++ regexp="exception_type",times="0"@} +++(gdb) +++-exec-run +++^running +++(gdb) +++~"\n" +++~"Catchpoint 1 (exception rethrown), 0x00007ffff7ae00ed +++ in __cxa_rethrow () from /lib64/libstdc++.so.6\n" +++*stopped,bkptno="1",reason="breakpoint-hit",disp="keep", +++ frame=@{addr="0x00007ffff7ae00ed",func="__cxa_rethrow", +++ args=[],from="/lib64/libstdc++.so.6",arch="i386:x86-64"@}, +++ thread-id="1",stopped-threads="all",core="6" +++(gdb) +++@end smallexample +++ +++@subheading The @code{-catch-catch} Command +++@findex -catch-catch +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -catch-catch [ -t ] [ -r @var{regexp}] +++@end smallexample +++ +++Stop when the debuggee catches a C@t{++} exception. If @var{regexp} +++is given, then only exceptions whose type matches the regular +++expression will be caught. +++ +++If @samp{-t} is given, then the catchpoint is enabled only for one +++stop, the catchpoint is automatically deleted after the first event is +++caught. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{catch catch} +++and @samp{tcatch catch} (@pxref{Set Catchpoints}). +++ +++@subsubheading Example +++ +++@smallexample +++-catch-catch -r exception_type +++^done,bkpt=@{number="1",type="catchpoint",disp="keep",enabled="y", +++ what="exception catch",catch-type="catch", +++ thread-groups=["i1"], +++ regexp="exception_type",times="0"@} +++(gdb) +++-exec-run +++^running +++(gdb) +++~"\n" +++~"Catchpoint 1 (exception caught), 0x00007ffff7ae00ed +++ in __cxa_begin_catch () from /lib64/libstdc++.so.6\n" +++*stopped,bkptno="1",reason="breakpoint-hit",disp="keep", +++ frame=@{addr="0x00007ffff7ae00ed",func="__cxa_begin_catch", +++ args=[],from="/lib64/libstdc++.so.6",arch="i386:x86-64"@}, +++ thread-id="1",stopped-threads="all",core="6" +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Program Context +++@section @sc{gdb/mi} Program Context +++ +++@subheading The @code{-exec-arguments} Command +++@findex -exec-arguments +++ +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-arguments @var{args} +++@end smallexample +++ +++Set the inferior program arguments, to be used in the next +++@samp{-exec-run}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{set args}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-exec-arguments -v word +++^done +++(gdb) +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-exec-show-arguments} Command +++@findex -exec-show-arguments +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-show-arguments +++@end smallexample +++ +++Print the arguments of the program. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{show args}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-environment-cd} Command +++@findex -environment-cd +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -environment-cd @var{pathdir} +++@end smallexample +++ +++Set @value{GDBN}'s working directory. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{cd}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-environment-cd /kwikemart/marge/ezannoni/flathead-dev/devo/gdb +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-environment-directory} Command +++@findex -environment-directory +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -environment-directory [ -r ] [ @var{pathdir} ]+ +++@end smallexample +++ +++Add directories @var{pathdir} to beginning of search path for source files. +++If the @samp{-r} option is used, the search path is reset to the default +++search path. If directories @var{pathdir} are supplied in addition to the +++@samp{-r} option, the search path is first reset and then addition +++occurs as normal. +++Multiple directories may be specified, separated by blanks. Specifying +++multiple directories in a single command +++results in the directories added to the beginning of the +++search path in the same order they were presented in the command. +++If blanks are needed as +++part of a directory name, double-quotes should be used around +++the name. In the command output, the path will show up separated +++by the system directory-separator character. The directory-separator +++character must not be used +++in any directory name. +++If no directories are specified, the current search path is displayed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{dir}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-environment-directory /kwikemart/marge/ezannoni/flathead-dev/devo/gdb +++^done,source-path="/kwikemart/marge/ezannoni/flathead-dev/devo/gdb:$cdir:$cwd" +++(gdb) +++-environment-directory "" +++^done,source-path="/kwikemart/marge/ezannoni/flathead-dev/devo/gdb:$cdir:$cwd" +++(gdb) +++-environment-directory -r /home/jjohnstn/src/gdb /usr/src +++^done,source-path="/home/jjohnstn/src/gdb:/usr/src:$cdir:$cwd" +++(gdb) +++-environment-directory -r +++^done,source-path="$cdir:$cwd" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-environment-path} Command +++@findex -environment-path +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -environment-path [ -r ] [ @var{pathdir} ]+ +++@end smallexample +++ +++Add directories @var{pathdir} to beginning of search path for object files. +++If the @samp{-r} option is used, the search path is reset to the original +++search path that existed at gdb start-up. If directories @var{pathdir} are +++supplied in addition to the +++@samp{-r} option, the search path is first reset and then addition +++occurs as normal. +++Multiple directories may be specified, separated by blanks. Specifying +++multiple directories in a single command +++results in the directories added to the beginning of the +++search path in the same order they were presented in the command. +++If blanks are needed as +++part of a directory name, double-quotes should be used around +++the name. In the command output, the path will show up separated +++by the system directory-separator character. The directory-separator +++character must not be used +++in any directory name. +++If no directories are specified, the current path is displayed. +++ +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{path}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-environment-path +++^done,path="/usr/bin" +++(gdb) +++-environment-path /kwikemart/marge/ezannoni/flathead-dev/ppc-eabi/gdb /bin +++^done,path="/kwikemart/marge/ezannoni/flathead-dev/ppc-eabi/gdb:/bin:/usr/bin" +++(gdb) +++-environment-path -r /usr/local/bin +++^done,path="/usr/local/bin:/usr/bin" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-environment-pwd} Command +++@findex -environment-pwd +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -environment-pwd +++@end smallexample +++ +++Show the current working directory. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{pwd}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-environment-pwd +++^done,cwd="/kwikemart/marge/ezannoni/flathead-dev/devo/gdb" +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Thread Commands +++@section @sc{gdb/mi} Thread Commands +++ +++ +++@subheading The @code{-thread-info} Command +++@findex -thread-info +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -thread-info [ @var{thread-id} ] +++@end smallexample +++ +++Reports information about either a specific thread, if the +++@var{thread-id} parameter is present, or about all threads. +++@var{thread-id} is the thread's global thread ID. When printing +++information about all threads, also reports the global ID of the +++current thread. +++ +++@subsubheading @value{GDBN} Command +++ +++The @samp{info thread} command prints the same information +++about all threads. +++ +++@subsubheading Result +++ +++The result contains the following attributes: +++ +++@table @samp +++@item threads +++A list of threads. The format of the elements of the list is described in +++@ref{GDB/MI Thread Information}. +++ +++@item current-thread-id +++The global id of the currently selected thread. This field is omitted if there +++is no selected thread (for example, when the selected inferior is not running, +++and therefore has no threads) or if a @var{thread-id} argument was passed to +++the command. +++ +++@end table +++ +++@subsubheading Example +++ +++@smallexample +++-thread-info +++^done,threads=[ +++@{id="2",target-id="Thread 0xb7e14b90 (LWP 21257)", +++ frame=@{level="0",addr="0xffffe410",func="__kernel_vsyscall", +++ args=[]@},state="running"@}, +++@{id="1",target-id="Thread 0xb7e156b0 (LWP 21254)", +++ frame=@{level="0",addr="0x0804891f",func="foo", +++ args=[@{name="i",value="10"@}], +++ file="/tmp/a.c",fullname="/tmp/a.c",line="158",arch="i386:x86_64"@}, +++ state="running"@}], +++current-thread-id="1" +++(gdb) +++@end smallexample +++ +++@subheading The @code{-thread-list-ids} Command +++@findex -thread-list-ids +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -thread-list-ids +++@end smallexample +++ +++Produces a list of the currently known global @value{GDBN} thread ids. +++At the end of the list it also prints the total number of such +++threads. +++ +++This command is retained for historical reasons, the +++@code{-thread-info} command should be used instead. +++ +++@subsubheading @value{GDBN} Command +++ +++Part of @samp{info threads} supplies the same information. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-thread-list-ids +++^done,thread-ids=@{thread-id="3",thread-id="2",thread-id="1"@}, +++current-thread-id="1",number-of-threads="3" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-thread-select} Command +++@findex -thread-select +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -thread-select @var{thread-id} +++@end smallexample +++ +++Make thread with global thread number @var{thread-id} the current +++thread. It prints the number of the new current thread, and the +++topmost frame for that thread. +++ +++This command is deprecated in favor of explicitly using the +++@samp{--thread} option to each command. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{thread}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-exec-next +++^running +++(gdb) +++*stopped,reason="end-stepping-range",thread-id="2",line="187", +++file="../../../devo/gdb/testsuite/gdb.threads/linux-dp.c" +++(gdb) +++-thread-list-ids +++^done, +++thread-ids=@{thread-id="3",thread-id="2",thread-id="1"@}, +++number-of-threads="3" +++(gdb) +++-thread-select 3 +++^done,new-thread-id="3", +++frame=@{level="0",func="vprintf", +++args=[@{name="format",value="0x8048e9c \"%*s%c %d %c\\n\""@}, +++@{name="arg",value="0x2"@}],file="vprintf.c",line="31",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Ada Tasking Commands +++@section @sc{gdb/mi} Ada Tasking Commands +++ +++@subheading The @code{-ada-task-info} Command +++@findex -ada-task-info +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -ada-task-info [ @var{task-id} ] +++@end smallexample +++ +++Reports information about either a specific Ada task, if the +++@var{task-id} parameter is present, or about all Ada tasks. +++ +++@subsubheading @value{GDBN} Command +++ +++The @samp{info tasks} command prints the same information +++about all Ada tasks (@pxref{Ada Tasks}). +++ +++@subsubheading Result +++ +++The result is a table of Ada tasks. The following columns are +++defined for each Ada task: +++ +++@table @samp +++@item current +++This field exists only for the current thread. It has the value @samp{*}. +++ +++@item id +++The identifier that @value{GDBN} uses to refer to the Ada task. +++ +++@item task-id +++The identifier that the target uses to refer to the Ada task. +++ +++@item thread-id +++The global thread identifier of the thread corresponding to the Ada +++task. +++ +++This field should always exist, as Ada tasks are always implemented +++on top of a thread. But if @value{GDBN} cannot find this corresponding +++thread for any reason, the field is omitted. +++ +++@item parent-id +++This field exists only when the task was created by another task. +++In this case, it provides the ID of the parent task. +++ +++@item priority +++The base priority of the task. +++ +++@item state +++The current state of the task. For a detailed description of the +++possible states, see @ref{Ada Tasks}. +++ +++@item name +++The name of the task. +++ +++@end table +++ +++@subsubheading Example +++ +++@smallexample +++-ada-task-info +++^done,tasks=@{nr_rows="3",nr_cols="8", +++hdr=[@{width="1",alignment="-1",col_name="current",colhdr=""@}, +++@{width="3",alignment="1",col_name="id",colhdr="ID"@}, +++@{width="9",alignment="1",col_name="task-id",colhdr="TID"@}, +++@{width="4",alignment="1",col_name="thread-id",colhdr=""@}, +++@{width="4",alignment="1",col_name="parent-id",colhdr="P-ID"@}, +++@{width="3",alignment="1",col_name="priority",colhdr="Pri"@}, +++@{width="22",alignment="-1",col_name="state",colhdr="State"@}, +++@{width="1",alignment="2",col_name="name",colhdr="Name"@}], +++body=[@{current="*",id="1",task-id=" 644010",thread-id="1",priority="48", +++state="Child Termination Wait",name="main_task"@}]@} +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Program Execution +++@section @sc{gdb/mi} Program Execution +++ +++These are the asynchronous commands which generate the out-of-band +++record @samp{*stopped}. Currently @value{GDBN} only really executes +++asynchronously with remote targets and this interaction is mimicked in +++other cases. +++ +++@subheading The @code{-exec-continue} Command +++@findex -exec-continue +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-continue [--reverse] [--all|--thread-group N] +++@end smallexample +++ +++Resumes the execution of the inferior program, which will continue +++to execute until it reaches a debugger stop event. If the +++@samp{--reverse} option is specified, execution resumes in reverse until +++it reaches a stop event. Stop events may include +++@itemize @bullet +++@item +++breakpoints or watchpoints +++@item +++signals or exceptions +++@item +++the end of the process (or its beginning under @samp{--reverse}) +++@item +++the end or beginning of a replay log if one is being used. +++@end itemize +++In all-stop mode (@pxref{All-Stop +++Mode}), may resume only one thread, or all threads, depending on the +++value of the @samp{scheduler-locking} variable. If @samp{--all} is +++specified, all threads (in all inferiors) will be resumed. The @samp{--all} option is +++ignored in all-stop mode. If the @samp{--thread-group} options is +++specified, then all threads in that thread group are resumed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} corresponding is @samp{continue}. +++ +++@subsubheading Example +++ +++@smallexample +++-exec-continue +++^running +++(gdb) +++@@Hello world +++*stopped,reason="breakpoint-hit",disp="keep",bkptno="2",frame=@{ +++func="foo",args=[],file="hello.c",fullname="/home/foo/bar/hello.c", +++line="13",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-finish} Command +++@findex -exec-finish +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-finish [--reverse] +++@end smallexample +++ +++Resumes the execution of the inferior program until the current +++function is exited. Displays the results returned by the function. +++If the @samp{--reverse} option is specified, resumes the reverse +++execution of the inferior program until the point where current +++function was called. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{finish}. +++ +++@subsubheading Example +++ +++Function returning @code{void}. +++ +++@smallexample +++-exec-finish +++^running +++(gdb) +++@@hello from foo +++*stopped,reason="function-finished",frame=@{func="main",args=[], +++file="hello.c",fullname="/home/foo/bar/hello.c",line="7",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++Function returning other than @code{void}. The name of the internal +++@value{GDBN} variable storing the result is printed, together with the +++value itself. +++ +++@smallexample +++-exec-finish +++^running +++(gdb) +++*stopped,reason="function-finished",frame=@{addr="0x000107b0",func="foo", +++args=[@{name="a",value="1"],@{name="b",value="9"@}@}, +++file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++arch="i386:x86_64"@}, +++gdb-result-var="$1",return-value="0" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-interrupt} Command +++@findex -exec-interrupt +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-interrupt [--all|--thread-group N] +++@end smallexample +++ +++Interrupts the background execution of the target. Note how the token +++associated with the stop message is the one for the execution command +++that has been interrupted. The token for the interrupt itself only +++appears in the @samp{^done} output. If the user is trying to +++interrupt a non-running program, an error message will be printed. +++ +++Note that when asynchronous execution is enabled, this command is +++asynchronous just like other execution commands. That is, first the +++@samp{^done} response will be printed, and the target stop will be +++reported after that using the @samp{*stopped} notification. +++ +++In non-stop mode, only the context thread is interrupted by default. +++All threads (in all inferiors) will be interrupted if the +++@samp{--all} option is specified. If the @samp{--thread-group} +++option is specified, all threads in that group will be interrupted. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{interrupt}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++111-exec-continue +++111^running +++ +++(gdb) +++222-exec-interrupt +++222^done +++(gdb) +++111*stopped,signal-name="SIGINT",signal-meaning="Interrupt", +++frame=@{addr="0x00010140",func="foo",args=[],file="try.c", +++fullname="/home/foo/bar/try.c",line="13",arch="i386:x86_64"@} +++(gdb) +++ +++(gdb) +++-exec-interrupt +++^error,msg="mi_cmd_exec_interrupt: Inferior not executing." +++(gdb) +++@end smallexample +++ +++@subheading The @code{-exec-jump} Command +++@findex -exec-jump +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-jump @var{location} +++@end smallexample +++ +++Resumes execution of the inferior program at the location specified by +++parameter. @xref{Specify Location}, for a description of the +++different forms of @var{location}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{jump}. +++ +++@subsubheading Example +++ +++@smallexample +++-exec-jump foo.c:10 +++*running,thread-id="all" +++^running +++@end smallexample +++ +++ +++@subheading The @code{-exec-next} Command +++@findex -exec-next +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-next [--reverse] +++@end smallexample +++ +++Resumes execution of the inferior program, stopping when the beginning +++of the next source line is reached. +++ +++If the @samp{--reverse} option is specified, resumes reverse execution +++of the inferior program, stopping at the beginning of the previous +++source line. If you issue this command on the first line of a +++function, it will take you back to the caller of that function, to the +++source line where the function was called. +++ +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{next}. +++ +++@subsubheading Example +++ +++@smallexample +++-exec-next +++^running +++(gdb) +++*stopped,reason="end-stepping-range",line="8",file="hello.c" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-next-instruction} Command +++@findex -exec-next-instruction +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-next-instruction [--reverse] +++@end smallexample +++ +++Executes one machine instruction. If the instruction is a function +++call, continues until the function returns. If the program stops at an +++instruction in the middle of a source line, the address will be +++printed as well. +++ +++If the @samp{--reverse} option is specified, resumes reverse execution +++of the inferior program, stopping at the previous instruction. If the +++previously executed instruction was a return from another function, +++it will continue to execute in reverse until the call to that function +++(from the current stack frame) is reached. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{nexti}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-exec-next-instruction +++^running +++ +++(gdb) +++*stopped,reason="end-stepping-range", +++addr="0x000100d4",line="5",file="hello.c" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-return} Command +++@findex -exec-return +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-return +++@end smallexample +++ +++Makes current function return immediately. Doesn't execute the inferior. +++Displays the new current frame. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{return}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++200-break-insert callee4 +++200^done,bkpt=@{number="1",addr="0x00010734", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c",line="8"@} +++(gdb) +++000-exec-run +++000^running +++(gdb) +++000*stopped,reason="breakpoint-hit",disp="keep",bkptno="1", +++frame=@{func="callee4",args=[], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="8", +++arch="i386:x86_64"@} +++(gdb) +++205-break-delete +++205^done +++(gdb) +++111-exec-return +++111^done,frame=@{level="0",func="callee3", +++args=[@{name="strarg", +++value="0x11940 \"A string argument.\""@}], +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="18", +++arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-run} Command +++@findex -exec-run +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-run [ --all | --thread-group N ] [ --start ] +++@end smallexample +++ +++Starts execution of the inferior from the beginning. The inferior +++executes until either a breakpoint is encountered or the program +++exits. In the latter case the output will include an exit code, if +++the program has exited exceptionally. +++ +++When neither the @samp{--all} nor the @samp{--thread-group} option +++is specified, the current inferior is started. If the +++@samp{--thread-group} option is specified, it should refer to a thread +++group of type @samp{process}, and that thread group will be started. +++If the @samp{--all} option is specified, then all inferiors will be started. +++ +++Using the @samp{--start} option instructs the debugger to stop +++the execution at the start of the inferior's main subprogram, +++following the same behavior as the @code{start} command +++(@pxref{Starting}). +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{run}. +++ +++@subsubheading Examples +++ +++@smallexample +++(gdb) +++-break-insert main +++^done,bkpt=@{number="1",addr="0x0001072c",file="recursive2.c",line="4"@} +++(gdb) +++-exec-run +++^running +++(gdb) +++*stopped,reason="breakpoint-hit",disp="keep",bkptno="1", +++frame=@{func="main",args=[],file="recursive2.c", +++fullname="/home/foo/bar/recursive2.c",line="4",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++@noindent +++Program exited normally: +++ +++@smallexample +++(gdb) +++-exec-run +++^running +++(gdb) +++x = 55 +++*stopped,reason="exited-normally" +++(gdb) +++@end smallexample +++ +++@noindent +++Program exited exceptionally: +++ +++@smallexample +++(gdb) +++-exec-run +++^running +++(gdb) +++x = 55 +++*stopped,reason="exited",exit-code="01" +++(gdb) +++@end smallexample +++ +++Another way the program can terminate is if it receives a signal such as +++@code{SIGINT}. In this case, @sc{gdb/mi} displays this: +++ +++@smallexample +++(gdb) +++*stopped,reason="exited-signalled",signal-name="SIGINT", +++signal-meaning="Interrupt" +++@end smallexample +++ +++ +++@c @subheading -exec-signal +++ +++ +++@subheading The @code{-exec-step} Command +++@findex -exec-step +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-step [--reverse] +++@end smallexample +++ +++Resumes execution of the inferior program, stopping when the beginning +++of the next source line is reached, if the next source line is not a +++function call. If it is, stop at the first instruction of the called +++function. If the @samp{--reverse} option is specified, resumes reverse +++execution of the inferior program, stopping at the beginning of the +++previously executed source line. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{step}. +++ +++@subsubheading Example +++ +++Stepping into a function: +++ +++@smallexample +++-exec-step +++^running +++(gdb) +++*stopped,reason="end-stepping-range", +++frame=@{func="foo",args=[@{name="a",value="10"@}, +++@{name="b",value="0"@}],file="recursive2.c", +++fullname="/home/foo/bar/recursive2.c",line="11",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++Regular stepping: +++ +++@smallexample +++-exec-step +++^running +++(gdb) +++*stopped,reason="end-stepping-range",line="14",file="recursive2.c" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-step-instruction} Command +++@findex -exec-step-instruction +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-step-instruction [--reverse] +++@end smallexample +++ +++Resumes the inferior which executes one machine instruction. If the +++@samp{--reverse} option is specified, resumes reverse execution of the +++inferior program, stopping at the previously executed instruction. +++The output, once @value{GDBN} has stopped, will vary depending on +++whether we have stopped in the middle of a source line or not. In the +++former case, the address at which the program stopped will be printed +++as well. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{stepi}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-exec-step-instruction +++^running +++ +++(gdb) +++*stopped,reason="end-stepping-range", +++frame=@{func="foo",args=[],file="try.c", +++fullname="/home/foo/bar/try.c",line="10",arch="i386:x86_64"@} +++(gdb) +++-exec-step-instruction +++^running +++ +++(gdb) +++*stopped,reason="end-stepping-range", +++frame=@{addr="0x000100f4",func="foo",args=[],file="try.c", +++fullname="/home/foo/bar/try.c",line="10",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-exec-until} Command +++@findex -exec-until +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-until [ @var{location} ] +++@end smallexample +++ +++Executes the inferior until the @var{location} specified in the +++argument is reached. If there is no argument, the inferior executes +++until a source line greater than the current one is reached. The +++reason for stopping in this case will be @samp{location-reached}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{until}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-exec-until recursive2.c:6 +++^running +++(gdb) +++x = 55 +++*stopped,reason="location-reached",frame=@{func="main",args=[], +++file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="6", +++arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++@ignore +++@subheading -file-clear +++Is this going away???? +++@end ignore +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Stack Manipulation +++@section @sc{gdb/mi} Stack Manipulation Commands +++ +++@subheading The @code{-enable-frame-filters} Command +++@findex -enable-frame-filters +++ +++@smallexample +++-enable-frame-filters +++@end smallexample +++ +++@value{GDBN} allows Python-based frame filters to affect the output of +++the MI commands relating to stack traces. As there is no way to +++implement this in a fully backward-compatible way, a front end must +++request that this functionality be enabled. +++ +++Once enabled, this feature cannot be disabled. +++ +++Note that if Python support has not been compiled into @value{GDBN}, +++this command will still succeed (and do nothing). +++ +++@subheading The @code{-stack-info-frame} Command +++@findex -stack-info-frame +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-info-frame +++@end smallexample +++ +++Get info on the selected frame. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info frame} or @samp{frame} +++(without arguments). +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-stack-info-frame +++^done,frame=@{level="1",addr="0x0001076c",func="callee3", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="17", +++arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-stack-info-depth} Command +++@findex -stack-info-depth +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-info-depth [ @var{max-depth} ] +++@end smallexample +++ +++Return the depth of the stack. If the integer argument @var{max-depth} +++is specified, do not count beyond @var{max-depth} frames. +++ +++@subsubheading @value{GDBN} Command +++ +++There's no equivalent @value{GDBN} command. +++ +++@subsubheading Example +++ +++For a stack with frame levels 0 through 11: +++ +++@smallexample +++(gdb) +++-stack-info-depth +++^done,depth="12" +++(gdb) +++-stack-info-depth 4 +++^done,depth="4" +++(gdb) +++-stack-info-depth 12 +++^done,depth="12" +++(gdb) +++-stack-info-depth 11 +++^done,depth="11" +++(gdb) +++-stack-info-depth 13 +++^done,depth="12" +++(gdb) +++@end smallexample +++ +++@anchor{-stack-list-arguments} +++@subheading The @code{-stack-list-arguments} Command +++@findex -stack-list-arguments +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-list-arguments [ --no-frame-filters ] [ --skip-unavailable ] @var{print-values} +++ [ @var{low-frame} @var{high-frame} ] +++@end smallexample +++ +++Display a list of the arguments for the frames between @var{low-frame} +++and @var{high-frame} (inclusive). If @var{low-frame} and +++@var{high-frame} are not provided, list the arguments for the whole +++call stack. If the two arguments are equal, show the single frame +++at the corresponding level. It is an error if @var{low-frame} is +++larger than the actual number of frames. On the other hand, +++@var{high-frame} may be larger than the actual number of frames, in +++which case only existing frames will be returned. +++ +++If @var{print-values} is 0 or @code{--no-values}, print only the names of +++the variables; if it is 1 or @code{--all-values}, print also their +++values; and if it is 2 or @code{--simple-values}, print the name, +++type and value for simple data types, and the name and type for arrays, +++structures and unions. If the option @code{--no-frame-filters} is +++supplied, then Python frame filters will not be executed. +++ +++If the @code{--skip-unavailable} option is specified, arguments that +++are not available are not listed. Partially available arguments +++are still displayed, however. +++ +++Use of this command to obtain arguments in a single frame is +++deprecated in favor of the @samp{-stack-list-variables} command. +++ +++@subsubheading @value{GDBN} Command +++ +++@value{GDBN} does not have an equivalent command. @code{gdbtk} has a +++@samp{gdb_get_args} command which partially overlaps with the +++functionality of @samp{-stack-list-arguments}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-stack-list-frames +++^done, +++stack=[ +++frame=@{level="0",addr="0x00010734",func="callee4", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="8", +++arch="i386:x86_64"@}, +++frame=@{level="1",addr="0x0001076c",func="callee3", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="17", +++arch="i386:x86_64"@}, +++frame=@{level="2",addr="0x0001078c",func="callee2", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="22", +++arch="i386:x86_64"@}, +++frame=@{level="3",addr="0x000107b4",func="callee1", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="27", +++arch="i386:x86_64"@}, +++frame=@{level="4",addr="0x000107e0",func="main", +++file="../../../devo/gdb/testsuite/gdb.mi/basics.c", +++fullname="/home/foo/bar/devo/gdb/testsuite/gdb.mi/basics.c",line="32", +++arch="i386:x86_64"@}] +++(gdb) +++-stack-list-arguments 0 +++^done, +++stack-args=[ +++frame=@{level="0",args=[]@}, +++frame=@{level="1",args=[name="strarg"]@}, +++frame=@{level="2",args=[name="intarg",name="strarg"]@}, +++frame=@{level="3",args=[name="intarg",name="strarg",name="fltarg"]@}, +++frame=@{level="4",args=[]@}] +++(gdb) +++-stack-list-arguments 1 +++^done, +++stack-args=[ +++frame=@{level="0",args=[]@}, +++frame=@{level="1", +++ args=[@{name="strarg",value="0x11940 \"A string argument.\""@}]@}, +++frame=@{level="2",args=[ +++@{name="intarg",value="2"@}, +++@{name="strarg",value="0x11940 \"A string argument.\""@}]@}, +++@{frame=@{level="3",args=[ +++@{name="intarg",value="2"@}, +++@{name="strarg",value="0x11940 \"A string argument.\""@}, +++@{name="fltarg",value="3.5"@}]@}, +++frame=@{level="4",args=[]@}] +++(gdb) +++-stack-list-arguments 0 2 2 +++^done,stack-args=[frame=@{level="2",args=[name="intarg",name="strarg"]@}] +++(gdb) +++-stack-list-arguments 1 2 2 +++^done,stack-args=[frame=@{level="2", +++args=[@{name="intarg",value="2"@}, +++@{name="strarg",value="0x11940 \"A string argument.\""@}]@}] +++(gdb) +++@end smallexample +++ +++@c @subheading -stack-list-exception-handlers +++ +++ +++@anchor{-stack-list-frames} +++@subheading The @code{-stack-list-frames} Command +++@findex -stack-list-frames +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-list-frames [ --no-frame-filters @var{low-frame} @var{high-frame} ] +++@end smallexample +++ +++List the frames currently on the stack. For each frame it displays the +++following info: +++ +++@table @samp +++@item @var{level} +++The frame number, 0 being the topmost frame, i.e., the innermost function. +++@item @var{addr} +++The @code{$pc} value for that frame. +++@item @var{func} +++Function name. +++@item @var{file} +++File name of the source file where the function lives. +++@item @var{fullname} +++The full file name of the source file where the function lives. +++@item @var{line} +++Line number corresponding to the @code{$pc}. +++@item @var{from} +++The shared library where this function is defined. This is only given +++if the frame's function is not known. +++@item @var{arch} +++Frame's architecture. +++@end table +++ +++If invoked without arguments, this command prints a backtrace for the +++whole stack. If given two integer arguments, it shows the frames whose +++levels are between the two arguments (inclusive). If the two arguments +++are equal, it shows the single frame at the corresponding level. It is +++an error if @var{low-frame} is larger than the actual number of +++frames. On the other hand, @var{high-frame} may be larger than the +++actual number of frames, in which case only existing frames will be +++returned. If the option @code{--no-frame-filters} is supplied, then +++Python frame filters will not be executed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{backtrace} and @samp{where}. +++ +++@subsubheading Example +++ +++Full stack backtrace: +++ +++@smallexample +++(gdb) +++-stack-list-frames +++^done,stack= +++[frame=@{level="0",addr="0x0001076c",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="11", +++ arch="i386:x86_64"@}, +++frame=@{level="1",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="2",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="3",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="4",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="5",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="6",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="7",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="8",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="9",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="10",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="11",addr="0x00010738",func="main", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="4", +++ arch="i386:x86_64"@}] +++(gdb) +++@end smallexample +++ +++Show frames between @var{low_frame} and @var{high_frame}: +++ +++@smallexample +++(gdb) +++-stack-list-frames 3 5 +++^done,stack= +++[frame=@{level="3",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="4",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}, +++frame=@{level="5",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}] +++(gdb) +++@end smallexample +++ +++Show a single frame: +++ +++@smallexample +++(gdb) +++-stack-list-frames 3 3 +++^done,stack= +++[frame=@{level="3",addr="0x000107a4",func="foo", +++ file="recursive2.c",fullname="/home/foo/bar/recursive2.c",line="14", +++ arch="i386:x86_64"@}] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-stack-list-locals} Command +++@findex -stack-list-locals +++@anchor{-stack-list-locals} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-list-locals [ --no-frame-filters ] [ --skip-unavailable ] @var{print-values} +++@end smallexample +++ +++Display the local variable names for the selected frame. If +++@var{print-values} is 0 or @code{--no-values}, print only the names of +++the variables; if it is 1 or @code{--all-values}, print also their +++values; and if it is 2 or @code{--simple-values}, print the name, +++type and value for simple data types, and the name and type for arrays, +++structures and unions. In this last case, a frontend can immediately +++display the value of simple data types and create variable objects for +++other data types when the user wishes to explore their values in +++more detail. If the option @code{--no-frame-filters} is supplied, then +++Python frame filters will not be executed. +++ +++If the @code{--skip-unavailable} option is specified, local variables +++that are not available are not listed. Partially available local +++variables are still displayed, however. +++ +++This command is deprecated in favor of the +++@samp{-stack-list-variables} command. +++ +++@subsubheading @value{GDBN} Command +++ +++@samp{info locals} in @value{GDBN}, @samp{gdb_get_locals} in @code{gdbtk}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-stack-list-locals 0 +++^done,locals=[name="A",name="B",name="C"] +++(gdb) +++-stack-list-locals --all-values +++^done,locals=[@{name="A",value="1"@},@{name="B",value="2"@}, +++ @{name="C",value="@{1, 2, 3@}"@}] +++-stack-list-locals --simple-values +++^done,locals=[@{name="A",type="int",value="1"@}, +++ @{name="B",type="int",value="2"@},@{name="C",type="int [3]"@}] +++(gdb) +++@end smallexample +++ +++@anchor{-stack-list-variables} +++@subheading The @code{-stack-list-variables} Command +++@findex -stack-list-variables +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-list-variables [ --no-frame-filters ] [ --skip-unavailable ] @var{print-values} +++@end smallexample +++ +++Display the names of local variables and function arguments for the selected frame. If +++@var{print-values} is 0 or @code{--no-values}, print only the names of +++the variables; if it is 1 or @code{--all-values}, print also their +++values; and if it is 2 or @code{--simple-values}, print the name, +++type and value for simple data types, and the name and type for arrays, +++structures and unions. If the option @code{--no-frame-filters} is +++supplied, then Python frame filters will not be executed. +++ +++If the @code{--skip-unavailable} option is specified, local variables +++and arguments that are not available are not listed. Partially +++available arguments and local variables are still displayed, however. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-stack-list-variables --thread 1 --frame 0 --all-values +++^done,variables=[@{name="x",value="11"@},@{name="s",value="@{a = 1, b = 2@}"@}] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-stack-select-frame} Command +++@findex -stack-select-frame +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -stack-select-frame @var{framenum} +++@end smallexample +++ +++Change the selected frame. Select a different frame @var{framenum} on +++the stack. +++ +++This command in deprecated in favor of passing the @samp{--frame} +++option to every command. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{frame}, @samp{up}, +++@samp{down}, @samp{select-frame}, @samp{up-silent}, and @samp{down-silent}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-stack-select-frame 2 +++^done +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Variable Objects +++@section @sc{gdb/mi} Variable Objects +++ +++@ignore +++ +++@subheading Motivation for Variable Objects in @sc{gdb/mi} +++ +++For the implementation of a variable debugger window (locals, watched +++expressions, etc.), we are proposing the adaptation of the existing code +++used by @code{Insight}. +++ +++The two main reasons for that are: +++ +++@enumerate 1 +++@item +++It has been proven in practice (it is already on its second generation). +++ +++@item +++It will shorten development time (needless to say how important it is +++now). +++@end enumerate +++ +++The original interface was designed to be used by Tcl code, so it was +++slightly changed so it could be used through @sc{gdb/mi}. This section +++describes the @sc{gdb/mi} operations that will be available and gives some +++hints about their use. +++ +++@emph{Note}: In addition to the set of operations described here, we +++expect the @sc{gui} implementation of a variable window to require, at +++least, the following operations: +++ +++@itemize @bullet +++@item @code{-gdb-show} @code{output-radix} +++@item @code{-stack-list-arguments} +++@item @code{-stack-list-locals} +++@item @code{-stack-select-frame} +++@end itemize +++ +++@end ignore +++ +++@subheading Introduction to Variable Objects +++ +++@cindex variable objects in @sc{gdb/mi} +++ +++Variable objects are "object-oriented" MI interface for examining and +++changing values of expressions. Unlike some other MI interfaces that +++work with expressions, variable objects are specifically designed for +++simple and efficient presentation in the frontend. A variable object +++is identified by string name. When a variable object is created, the +++frontend specifies the expression for that variable object. The +++expression can be a simple variable, or it can be an arbitrary complex +++expression, and can even involve CPU registers. After creating a +++variable object, the frontend can invoke other variable object +++operations---for example to obtain or change the value of a variable +++object, or to change display format. +++ +++Variable objects have hierarchical tree structure. Any variable object +++that corresponds to a composite type, such as structure in C, has +++a number of child variable objects, for example corresponding to each +++element of a structure. A child variable object can itself have +++children, recursively. Recursion ends when we reach +++leaf variable objects, which always have built-in types. Child variable +++objects are created only by explicit request, so if a frontend +++is not interested in the children of a particular variable object, no +++child will be created. +++ +++For a leaf variable object it is possible to obtain its value as a +++string, or set the value from a string. String value can be also +++obtained for a non-leaf variable object, but it's generally a string +++that only indicates the type of the object, and does not list its +++contents. Assignment to a non-leaf variable object is not allowed. +++ +++A frontend does not need to read the values of all variable objects each time +++the program stops. Instead, MI provides an update command that lists all +++variable objects whose values has changed since the last update +++operation. This considerably reduces the amount of data that must +++be transferred to the frontend. As noted above, children variable +++objects are created on demand, and only leaf variable objects have a +++real value. As result, gdb will read target memory only for leaf +++variables that frontend has created. +++ +++The automatic update is not always desirable. For example, a frontend +++might want to keep a value of some expression for future reference, +++and never update it. For another example, fetching memory is +++relatively slow for embedded targets, so a frontend might want +++to disable automatic update for the variables that are either not +++visible on the screen, or ``closed''. This is possible using so +++called ``frozen variable objects''. Such variable objects are never +++implicitly updated. +++ +++Variable objects can be either @dfn{fixed} or @dfn{floating}. For the +++fixed variable object, the expression is parsed when the variable +++object is created, including associating identifiers to specific +++variables. The meaning of expression never changes. For a floating +++variable object the values of variables whose names appear in the +++expressions are re-evaluated every time in the context of the current +++frame. Consider this example: +++ +++@smallexample +++void do_work(...) +++@{ +++ struct work_state state; +++ +++ if (...) +++ do_work(...); +++@} +++@end smallexample +++ +++If a fixed variable object for the @code{state} variable is created in +++this function, and we enter the recursive call, the variable +++object will report the value of @code{state} in the top-level +++@code{do_work} invocation. On the other hand, a floating variable +++object will report the value of @code{state} in the current frame. +++ +++If an expression specified when creating a fixed variable object +++refers to a local variable, the variable object becomes bound to the +++thread and frame in which the variable object is created. When such +++variable object is updated, @value{GDBN} makes sure that the +++thread/frame combination the variable object is bound to still exists, +++and re-evaluates the variable object in context of that thread/frame. +++ +++The following is the complete set of @sc{gdb/mi} operations defined to +++access this functionality: +++ +++@multitable @columnfractions .4 .6 +++@item @strong{Operation} +++@tab @strong{Description} +++ +++@item @code{-enable-pretty-printing} +++@tab enable Python-based pretty-printing +++@item @code{-var-create} +++@tab create a variable object +++@item @code{-var-delete} +++@tab delete the variable object and/or its children +++@item @code{-var-set-format} +++@tab set the display format of this variable +++@item @code{-var-show-format} +++@tab show the display format of this variable +++@item @code{-var-info-num-children} +++@tab tells how many children this object has +++@item @code{-var-list-children} +++@tab return a list of the object's children +++@item @code{-var-info-type} +++@tab show the type of this variable object +++@item @code{-var-info-expression} +++@tab print parent-relative expression that this variable object represents +++@item @code{-var-info-path-expression} +++@tab print full expression that this variable object represents +++@item @code{-var-show-attributes} +++@tab is this variable editable? does it exist here? +++@item @code{-var-evaluate-expression} +++@tab get the value of this variable +++@item @code{-var-assign} +++@tab set the value of this variable +++@item @code{-var-update} +++@tab update the variable and its children +++@item @code{-var-set-frozen} +++@tab set frozenness attribute +++@item @code{-var-set-update-range} +++@tab set range of children to display on update +++@end multitable +++ +++In the next subsection we describe each operation in detail and suggest +++how it can be used. +++ +++@subheading Description And Use of Operations on Variable Objects +++ +++@subheading The @code{-enable-pretty-printing} Command +++@findex -enable-pretty-printing +++ +++@smallexample +++-enable-pretty-printing +++@end smallexample +++ +++@value{GDBN} allows Python-based visualizers to affect the output of the +++MI variable object commands. However, because there was no way to +++implement this in a fully backward-compatible way, a front end must +++request that this functionality be enabled. +++ +++Once enabled, this feature cannot be disabled. +++ +++Note that if Python support has not been compiled into @value{GDBN}, +++this command will still succeed (and do nothing). +++ +++This feature is currently (as of @value{GDBN} 7.0) experimental, and +++may work differently in future versions of @value{GDBN}. +++ +++@subheading The @code{-var-create} Command +++@findex -var-create +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-create @{@var{name} | "-"@} +++ @{@var{frame-addr} | "*" | "@@"@} @var{expression} +++@end smallexample +++ +++This operation creates a variable object, which allows the monitoring of +++a variable, the result of an expression, a memory cell or a CPU +++register. +++ +++The @var{name} parameter is the string by which the object can be +++referenced. It must be unique. If @samp{-} is specified, the varobj +++system will generate a string ``varNNNNNN'' automatically. It will be +++unique provided that one does not specify @var{name} of that format. +++The command fails if a duplicate name is found. +++ +++The frame under which the expression should be evaluated can be +++specified by @var{frame-addr}. A @samp{*} indicates that the current +++frame should be used. A @samp{@@} indicates that a floating variable +++object must be created. +++ +++@var{expression} is any expression valid on the current language set (must not +++begin with a @samp{*}), or one of the following: +++ +++@itemize @bullet +++@item +++@samp{*@var{addr}}, where @var{addr} is the address of a memory cell +++ +++@item +++@samp{*@var{addr}-@var{addr}} --- a memory address range (TBD) +++ +++@item +++@samp{$@var{regname}} --- a CPU register name +++@end itemize +++ +++@cindex dynamic varobj +++A varobj's contents may be provided by a Python-based pretty-printer. In this +++case the varobj is known as a @dfn{dynamic varobj}. Dynamic varobjs +++have slightly different semantics in some cases. If the +++@code{-enable-pretty-printing} command is not sent, then @value{GDBN} +++will never create a dynamic varobj. This ensures backward +++compatibility for existing clients. +++ +++@subsubheading Result +++ +++This operation returns attributes of the newly-created varobj. These +++are: +++ +++@table @samp +++@item name +++The name of the varobj. +++ +++@item numchild +++The number of children of the varobj. This number is not necessarily +++reliable for a dynamic varobj. Instead, you must examine the +++@samp{has_more} attribute. +++ +++@item value +++The varobj's scalar value. For a varobj whose type is some sort of +++aggregate (e.g., a @code{struct}), or for a dynamic varobj, this value +++will not be interesting. +++ +++@item type +++The varobj's type. This is a string representation of the type, as +++would be printed by the @value{GDBN} CLI. If @samp{print object} +++(@pxref{Print Settings, set print object}) is set to @code{on}, the +++@emph{actual} (derived) type of the object is shown rather than the +++@emph{declared} one. +++ +++@item thread-id +++If a variable object is bound to a specific thread, then this is the +++thread's global identifier. +++ +++@item has_more +++For a dynamic varobj, this indicates whether there appear to be any +++children available. For a non-dynamic varobj, this will be 0. +++ +++@item dynamic +++This attribute will be present and have the value @samp{1} if the +++varobj is a dynamic varobj. If the varobj is not a dynamic varobj, +++then this attribute will not be present. +++ +++@item displayhint +++A dynamic varobj can supply a display hint to the front end. The +++value comes directly from the Python pretty-printer object's +++@code{display_hint} method. @xref{Pretty Printing API}. +++@end table +++ +++Typical output will look like this: +++ +++@smallexample +++ name="@var{name}",numchild="@var{N}",type="@var{type}",thread-id="@var{M}", +++ has_more="@var{has_more}" +++@end smallexample +++ +++ +++@subheading The @code{-var-delete} Command +++@findex -var-delete +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-delete [ -c ] @var{name} +++@end smallexample +++ +++Deletes a previously created variable object and all of its children. +++With the @samp{-c} option, just deletes the children. +++ +++Returns an error if the object @var{name} is not found. +++ +++ +++@subheading The @code{-var-set-format} Command +++@findex -var-set-format +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-set-format @var{name} @var{format-spec} +++@end smallexample +++ +++Sets the output format for the value of the object @var{name} to be +++@var{format-spec}. +++ +++@anchor{-var-set-format} +++The syntax for the @var{format-spec} is as follows: +++ +++@smallexample +++ @var{format-spec} @expansion{} +++ @{binary | decimal | hexadecimal | octal | natural | zero-hexadecimal@} +++@end smallexample +++ +++The natural format is the default format choosen automatically +++based on the variable type (like decimal for an @code{int}, hex +++for pointers, etc.). +++ +++The zero-hexadecimal format has a representation similar to hexadecimal +++but with padding zeroes to the left of the value. For example, a 32-bit +++hexadecimal value of 0x1234 would be represented as 0x00001234 in the +++zero-hexadecimal format. +++ +++For a variable with children, the format is set only on the +++variable itself, and the children are not affected. +++ +++@subheading The @code{-var-show-format} Command +++@findex -var-show-format +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-show-format @var{name} +++@end smallexample +++ +++Returns the format used to display the value of the object @var{name}. +++ +++@smallexample +++ @var{format} @expansion{} +++ @var{format-spec} +++@end smallexample +++ +++ +++@subheading The @code{-var-info-num-children} Command +++@findex -var-info-num-children +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-info-num-children @var{name} +++@end smallexample +++ +++Returns the number of children of a variable object @var{name}: +++ +++@smallexample +++ numchild=@var{n} +++@end smallexample +++ +++Note that this number is not completely reliable for a dynamic varobj. +++It will return the current number of children, but more children may +++be available. +++ +++ +++@subheading The @code{-var-list-children} Command +++@findex -var-list-children +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-list-children [@var{print-values}] @var{name} [@var{from} @var{to}] +++@end smallexample +++@anchor{-var-list-children} +++ +++Return a list of the children of the specified variable object and +++create variable objects for them, if they do not already exist. With +++a single argument or if @var{print-values} has a value of 0 or +++@code{--no-values}, print only the names of the variables; if +++@var{print-values} is 1 or @code{--all-values}, also print their +++values; and if it is 2 or @code{--simple-values} print the name and +++value for simple data types and just the name for arrays, structures +++and unions. +++ +++@var{from} and @var{to}, if specified, indicate the range of children +++to report. If @var{from} or @var{to} is less than zero, the range is +++reset and all children will be reported. Otherwise, children starting +++at @var{from} (zero-based) and up to and excluding @var{to} will be +++reported. +++ +++If a child range is requested, it will only affect the current call to +++@code{-var-list-children}, but not future calls to @code{-var-update}. +++For this, you must instead use @code{-var-set-update-range}. The +++intent of this approach is to enable a front end to implement any +++update approach it likes; for example, scrolling a view may cause the +++front end to request more children with @code{-var-list-children}, and +++then the front end could call @code{-var-set-update-range} with a +++different range to ensure that future updates are restricted to just +++the visible items. +++ +++For each child the following results are returned: +++ +++@table @var +++ +++@item name +++Name of the variable object created for this child. +++ +++@item exp +++The expression to be shown to the user by the front end to designate this child. +++For example this may be the name of a structure member. +++ +++For a dynamic varobj, this value cannot be used to form an +++expression. There is no way to do this at all with a dynamic varobj. +++ +++For C/C@t{++} structures there are several pseudo children returned to +++designate access qualifiers. For these pseudo children @var{exp} is +++@samp{public}, @samp{private}, or @samp{protected}. In this case the +++type and value are not present. +++ +++A dynamic varobj will not report the access qualifying +++pseudo-children, regardless of the language. This information is not +++available at all with a dynamic varobj. +++ +++@item numchild +++Number of children this child has. For a dynamic varobj, this will be +++0. +++ +++@item type +++The type of the child. If @samp{print object} +++(@pxref{Print Settings, set print object}) is set to @code{on}, the +++@emph{actual} (derived) type of the object is shown rather than the +++@emph{declared} one. +++ +++@item value +++If values were requested, this is the value. +++ +++@item thread-id +++If this variable object is associated with a thread, this is the +++thread's global thread id. Otherwise this result is not present. +++ +++@item frozen +++If the variable object is frozen, this variable will be present with a value of 1. +++ +++@item displayhint +++A dynamic varobj can supply a display hint to the front end. The +++value comes directly from the Python pretty-printer object's +++@code{display_hint} method. @xref{Pretty Printing API}. +++ +++@item dynamic +++This attribute will be present and have the value @samp{1} if the +++varobj is a dynamic varobj. If the varobj is not a dynamic varobj, +++then this attribute will not be present. +++ +++@end table +++ +++The result may have its own attributes: +++ +++@table @samp +++@item displayhint +++A dynamic varobj can supply a display hint to the front end. The +++value comes directly from the Python pretty-printer object's +++@code{display_hint} method. @xref{Pretty Printing API}. +++ +++@item has_more +++This is an integer attribute which is nonzero if there are children +++remaining after the end of the selected range. +++@end table +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++ -var-list-children n +++ ^done,numchild=@var{n},children=[child=@{name=@var{name},exp=@var{exp}, +++ numchild=@var{n},type=@var{type}@},@r{(repeats N times)}] +++(gdb) +++ -var-list-children --all-values n +++ ^done,numchild=@var{n},children=[child=@{name=@var{name},exp=@var{exp}, +++ numchild=@var{n},value=@var{value},type=@var{type}@},@r{(repeats N times)}] +++@end smallexample +++ +++ +++@subheading The @code{-var-info-type} Command +++@findex -var-info-type +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-info-type @var{name} +++@end smallexample +++ +++Returns the type of the specified variable @var{name}. The type is +++returned as a string in the same format as it is output by the +++@value{GDBN} CLI: +++ +++@smallexample +++ type=@var{typename} +++@end smallexample +++ +++ +++@subheading The @code{-var-info-expression} Command +++@findex -var-info-expression +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-info-expression @var{name} +++@end smallexample +++ +++Returns a string that is suitable for presenting this +++variable object in user interface. The string is generally +++not valid expression in the current language, and cannot be evaluated. +++ +++For example, if @code{a} is an array, and variable object +++@code{A} was created for @code{a}, then we'll get this output: +++ +++@smallexample +++(gdb) -var-info-expression A.1 +++^done,lang="C",exp="1" +++@end smallexample +++ +++@noindent +++Here, the value of @code{lang} is the language name, which can be +++found in @ref{Supported Languages}. +++ +++Note that the output of the @code{-var-list-children} command also +++includes those expressions, so the @code{-var-info-expression} command +++is of limited use. +++ +++@subheading The @code{-var-info-path-expression} Command +++@findex -var-info-path-expression +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-info-path-expression @var{name} +++@end smallexample +++ +++Returns an expression that can be evaluated in the current +++context and will yield the same value that a variable object has. +++Compare this with the @code{-var-info-expression} command, which +++result can be used only for UI presentation. Typical use of +++the @code{-var-info-path-expression} command is creating a +++watchpoint from a variable object. +++ +++This command is currently not valid for children of a dynamic varobj, +++and will give an error when invoked on one. +++ +++For example, suppose @code{C} is a C@t{++} class, derived from class +++@code{Base}, and that the @code{Base} class has a member called +++@code{m_size}. Assume a variable @code{c} is has the type of +++@code{C} and a variable object @code{C} was created for variable +++@code{c}. Then, we'll get this output: +++@smallexample +++(gdb) -var-info-path-expression C.Base.public.m_size +++^done,path_expr=((Base)c).m_size) +++@end smallexample +++ +++@subheading The @code{-var-show-attributes} Command +++@findex -var-show-attributes +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-show-attributes @var{name} +++@end smallexample +++ +++List attributes of the specified variable object @var{name}: +++ +++@smallexample +++ status=@var{attr} [ ( ,@var{attr} )* ] +++@end smallexample +++ +++@noindent +++where @var{attr} is @code{@{ @{ editable | noneditable @} | TBD @}}. +++ +++@subheading The @code{-var-evaluate-expression} Command +++@findex -var-evaluate-expression +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-evaluate-expression [-f @var{format-spec}] @var{name} +++@end smallexample +++ +++Evaluates the expression that is represented by the specified variable +++object and returns its value as a string. The format of the string +++can be specified with the @samp{-f} option. The possible values of +++this option are the same as for @code{-var-set-format} +++(@pxref{-var-set-format}). If the @samp{-f} option is not specified, +++the current display format will be used. The current display format +++can be changed using the @code{-var-set-format} command. +++ +++@smallexample +++ value=@var{value} +++@end smallexample +++ +++Note that one must invoke @code{-var-list-children} for a variable +++before the value of a child variable can be evaluated. +++ +++@subheading The @code{-var-assign} Command +++@findex -var-assign +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-assign @var{name} @var{expression} +++@end smallexample +++ +++Assigns the value of @var{expression} to the variable object specified +++by @var{name}. The object must be @samp{editable}. If the variable's +++value is altered by the assign, the variable will show up in any +++subsequent @code{-var-update} list. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-var-assign var1 3 +++^done,value="3" +++(gdb) +++-var-update * +++^done,changelist=[@{name="var1",in_scope="true",type_changed="false"@}] +++(gdb) +++@end smallexample +++ +++@subheading The @code{-var-update} Command +++@findex -var-update +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-update [@var{print-values}] @{@var{name} | "*"@} +++@end smallexample +++ +++Reevaluate the expressions corresponding to the variable object +++@var{name} and all its direct and indirect children, and return the +++list of variable objects whose values have changed; @var{name} must +++be a root variable object. Here, ``changed'' means that the result of +++@code{-var-evaluate-expression} before and after the +++@code{-var-update} is different. If @samp{*} is used as the variable +++object names, all existing variable objects are updated, except +++for frozen ones (@pxref{-var-set-frozen}). The option +++@var{print-values} determines whether both names and values, or just +++names are printed. The possible values of this option are the same +++as for @code{-var-list-children} (@pxref{-var-list-children}). It is +++recommended to use the @samp{--all-values} option, to reduce the +++number of MI commands needed on each program stop. +++ +++With the @samp{*} parameter, if a variable object is bound to a +++currently running thread, it will not be updated, without any +++diagnostic. +++ +++If @code{-var-set-update-range} was previously used on a varobj, then +++only the selected range of children will be reported. +++ +++@code{-var-update} reports all the changed varobjs in a tuple named +++@samp{changelist}. +++ +++Each item in the change list is itself a tuple holding: +++ +++@table @samp +++@item name +++The name of the varobj. +++ +++@item value +++If values were requested for this update, then this field will be +++present and will hold the value of the varobj. +++ +++@item in_scope +++@anchor{-var-update} +++This field is a string which may take one of three values: +++ +++@table @code +++@item "true" +++The variable object's current value is valid. +++ +++@item "false" +++The variable object does not currently hold a valid value but it may +++hold one in the future if its associated expression comes back into +++scope. +++ +++@item "invalid" +++The variable object no longer holds a valid value. +++This can occur when the executable file being debugged has changed, +++either through recompilation or by using the @value{GDBN} @code{file} +++command. The front end should normally choose to delete these variable +++objects. +++@end table +++ +++In the future new values may be added to this list so the front should +++be prepared for this possibility. @xref{GDB/MI Development and Front Ends, ,@sc{GDB/MI} Development and Front Ends}. +++ +++@item type_changed +++This is only present if the varobj is still valid. If the type +++changed, then this will be the string @samp{true}; otherwise it will +++be @samp{false}. +++ +++When a varobj's type changes, its children are also likely to have +++become incorrect. Therefore, the varobj's children are automatically +++deleted when this attribute is @samp{true}. Also, the varobj's update +++range, when set using the @code{-var-set-update-range} command, is +++unset. +++ +++@item new_type +++If the varobj's type changed, then this field will be present and will +++hold the new type. +++ +++@item new_num_children +++For a dynamic varobj, if the number of children changed, or if the +++type changed, this will be the new number of children. +++ +++The @samp{numchild} field in other varobj responses is generally not +++valid for a dynamic varobj -- it will show the number of children that +++@value{GDBN} knows about, but because dynamic varobjs lazily +++instantiate their children, this will not reflect the number of +++children which may be available. +++ +++The @samp{new_num_children} attribute only reports changes to the +++number of children known by @value{GDBN}. This is the only way to +++detect whether an update has removed children (which necessarily can +++only happen at the end of the update range). +++ +++@item displayhint +++The display hint, if any. +++ +++@item has_more +++This is an integer value, which will be 1 if there are more children +++available outside the varobj's update range. +++ +++@item dynamic +++This attribute will be present and have the value @samp{1} if the +++varobj is a dynamic varobj. If the varobj is not a dynamic varobj, +++then this attribute will not be present. +++ +++@item new_children +++If new children were added to a dynamic varobj within the selected +++update range (as set by @code{-var-set-update-range}), then they will +++be listed in this attribute. +++@end table +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-var-assign var1 3 +++^done,value="3" +++(gdb) +++-var-update --all-values var1 +++^done,changelist=[@{name="var1",value="3",in_scope="true", +++type_changed="false"@}] +++(gdb) +++@end smallexample +++ +++@subheading The @code{-var-set-frozen} Command +++@findex -var-set-frozen +++@anchor{-var-set-frozen} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-set-frozen @var{name} @var{flag} +++@end smallexample +++ +++Set the frozenness flag on the variable object @var{name}. The +++@var{flag} parameter should be either @samp{1} to make the variable +++frozen or @samp{0} to make it unfrozen. If a variable object is +++frozen, then neither itself, nor any of its children, are +++implicitly updated by @code{-var-update} of +++a parent variable or by @code{-var-update *}. Only +++@code{-var-update} of the variable itself will update its value and +++values of its children. After a variable object is unfrozen, it is +++implicitly updated by all subsequent @code{-var-update} operations. +++Unfreezing a variable does not update it, only subsequent +++@code{-var-update} does. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-var-set-frozen V 1 +++^done +++(gdb) +++@end smallexample +++ +++@subheading The @code{-var-set-update-range} command +++@findex -var-set-update-range +++@anchor{-var-set-update-range} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-set-update-range @var{name} @var{from} @var{to} +++@end smallexample +++ +++Set the range of children to be returned by future invocations of +++@code{-var-update}. +++ +++@var{from} and @var{to} indicate the range of children to report. If +++@var{from} or @var{to} is less than zero, the range is reset and all +++children will be reported. Otherwise, children starting at @var{from} +++(zero-based) and up to and excluding @var{to} will be reported. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-var-set-update-range V 1 2 +++^done +++@end smallexample +++ +++@subheading The @code{-var-set-visualizer} command +++@findex -var-set-visualizer +++@anchor{-var-set-visualizer} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -var-set-visualizer @var{name} @var{visualizer} +++@end smallexample +++ +++Set a visualizer for the variable object @var{name}. +++ +++@var{visualizer} is the visualizer to use. The special value +++@samp{None} means to disable any visualizer in use. +++ +++If not @samp{None}, @var{visualizer} must be a Python expression. +++This expression must evaluate to a callable object which accepts a +++single argument. @value{GDBN} will call this object with the value of +++the varobj @var{name} as an argument (this is done so that the same +++Python pretty-printing code can be used for both the CLI and MI). +++When called, this object must return an object which conforms to the +++pretty-printing interface (@pxref{Pretty Printing API}). +++ +++The pre-defined function @code{gdb.default_visualizer} may be used to +++select a visualizer by following the built-in process +++(@pxref{Selecting Pretty-Printers}). This is done automatically when +++a varobj is created, and so ordinarily is not needed. +++ +++This feature is only available if Python support is enabled. The MI +++command @code{-list-features} (@pxref{GDB/MI Support Commands}) +++can be used to check this. +++ +++@subsubheading Example +++ +++Resetting the visualizer: +++ +++@smallexample +++(gdb) +++-var-set-visualizer V None +++^done +++@end smallexample +++ +++Reselecting the default (type-based) visualizer: +++ +++@smallexample +++(gdb) +++-var-set-visualizer V gdb.default_visualizer +++^done +++@end smallexample +++ +++Suppose @code{SomeClass} is a visualizer class. A lambda expression +++can be used to instantiate this class for a varobj: +++ +++@smallexample +++(gdb) +++-var-set-visualizer V "lambda val: SomeClass()" +++^done +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Data Manipulation +++@section @sc{gdb/mi} Data Manipulation +++ +++@cindex data manipulation, in @sc{gdb/mi} +++@cindex @sc{gdb/mi}, data manipulation +++This section describes the @sc{gdb/mi} commands that manipulate data: +++examine memory and registers, evaluate expressions, etc. +++ +++For details about what an addressable memory unit is, +++@pxref{addressable memory unit}. +++ +++@c REMOVED FROM THE INTERFACE. +++@c @subheading -data-assign +++@c Change the value of a program variable. Plenty of side effects. +++@c @subsubheading GDB Command +++@c set variable +++@c @subsubheading Example +++@c N.A. +++ +++@subheading The @code{-data-disassemble} Command +++@findex -data-disassemble +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-disassemble +++ [ -s @var{start-addr} -e @var{end-addr} ] +++ | [ -a @var{addr} ] +++ | [ -f @var{filename} -l @var{linenum} [ -n @var{lines} ] ] +++ -- @var{mode} +++@end smallexample +++ +++@noindent +++Where: +++ +++@table @samp +++@item @var{start-addr} +++is the beginning address (or @code{$pc}) +++@item @var{end-addr} +++is the end address +++@item @var{addr} +++is an address anywhere within (or the name of) the function to +++disassemble. If an address is specified, the whole function +++surrounding that address will be disassembled. If a name is +++specified, the whole function with that name will be disassembled. +++@item @var{filename} +++is the name of the file to disassemble +++@item @var{linenum} +++is the line number to disassemble around +++@item @var{lines} +++is the number of disassembly lines to be produced. If it is -1, +++the whole function will be disassembled, in case no @var{end-addr} is +++specified. If @var{end-addr} is specified as a non-zero value, and +++@var{lines} is lower than the number of disassembly lines between +++@var{start-addr} and @var{end-addr}, only @var{lines} lines are +++displayed; if @var{lines} is higher than the number of lines between +++@var{start-addr} and @var{end-addr}, only the lines up to @var{end-addr} +++are displayed. +++@item @var{mode} +++is one of: +++@itemize @bullet +++@item 0 disassembly only +++@item 1 mixed source and disassembly (deprecated) +++@item 2 disassembly with raw opcodes +++@item 3 mixed source and disassembly with raw opcodes (deprecated) +++@item 4 mixed source and disassembly +++@item 5 mixed source and disassembly with raw opcodes +++@end itemize +++ +++Modes 1 and 3 are deprecated. The output is ``source centric'' +++which hasn't proved useful in practice. +++@xref{Machine Code}, for a discussion of the difference between +++@code{/m} and @code{/s} output of the @code{disassemble} command. +++@end table +++ +++@subsubheading Result +++ +++The result of the @code{-data-disassemble} command will be a list named +++@samp{asm_insns}, the contents of this list depend on the @var{mode} +++used with the @code{-data-disassemble} command. +++ +++For modes 0 and 2 the @samp{asm_insns} list contains tuples with the +++following fields: +++ +++@table @code +++@item address +++The address at which this instruction was disassembled. +++ +++@item func-name +++The name of the function this instruction is within. +++ +++@item offset +++The decimal offset in bytes from the start of @samp{func-name}. +++ +++@item inst +++The text disassembly for this @samp{address}. +++ +++@item opcodes +++This field is only present for modes 2, 3 and 5. This contains the raw opcode +++bytes for the @samp{inst} field. +++ +++@end table +++ +++For modes 1, 3, 4 and 5 the @samp{asm_insns} list contains tuples named +++@samp{src_and_asm_line}, each of which has the following fields: +++ +++@table @code +++@item line +++The line number within @samp{file}. +++ +++@item file +++The file name from the compilation unit. This might be an absolute +++file name or a relative file name depending on the compile command +++used. +++ +++@item fullname +++Absolute file name of @samp{file}. It is converted to a canonical form +++using the source file search path +++(@pxref{Source Path, ,Specifying Source Directories}) +++and after resolving all the symbolic links. +++ +++If the source file is not found this field will contain the path as +++present in the debug information. +++ +++@item line_asm_insn +++This is a list of tuples containing the disassembly for @samp{line} in +++@samp{file}. The fields of each tuple are the same as for +++@code{-data-disassemble} in @var{mode} 0 and 2, so @samp{address}, +++@samp{func-name}, @samp{offset}, @samp{inst}, and optionally +++@samp{opcodes}. +++ +++@end table +++ +++Note that whatever included in the @samp{inst} field, is not +++manipulated directly by @sc{gdb/mi}, i.e., it is not possible to +++adjust its format. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{disassemble}. +++ +++@subsubheading Example +++ +++Disassemble from the current value of @code{$pc} to @code{$pc + 20}: +++ +++@smallexample +++(gdb) +++-data-disassemble -s $pc -e "$pc + 20" -- 0 +++^done, +++asm_insns=[ +++@{address="0x000107c0",func-name="main",offset="4", +++inst="mov 2, %o0"@}, +++@{address="0x000107c4",func-name="main",offset="8", +++inst="sethi %hi(0x11800), %o2"@}, +++@{address="0x000107c8",func-name="main",offset="12", +++inst="or %o2, 0x140, %o1\t! 0x11940 <_lib_version+8>"@}, +++@{address="0x000107cc",func-name="main",offset="16", +++inst="sethi %hi(0x11800), %o2"@}, +++@{address="0x000107d0",func-name="main",offset="20", +++inst="or %o2, 0x168, %o4\t! 0x11968 <_lib_version+48>"@}] +++(gdb) +++@end smallexample +++ +++Disassemble the whole @code{main} function. Line 32 is part of +++@code{main}. +++ +++@smallexample +++-data-disassemble -f basics.c -l 32 -- 0 +++^done,asm_insns=[ +++@{address="0x000107bc",func-name="main",offset="0", +++inst="save %sp, -112, %sp"@}, +++@{address="0x000107c0",func-name="main",offset="4", +++inst="mov 2, %o0"@}, +++@{address="0x000107c4",func-name="main",offset="8", +++inst="sethi %hi(0x11800), %o2"@}, +++[@dots{}] +++@{address="0x0001081c",func-name="main",offset="96",inst="ret "@}, +++@{address="0x00010820",func-name="main",offset="100",inst="restore "@}] +++(gdb) +++@end smallexample +++ +++Disassemble 3 instructions from the start of @code{main}: +++ +++@smallexample +++(gdb) +++-data-disassemble -f basics.c -l 32 -n 3 -- 0 +++^done,asm_insns=[ +++@{address="0x000107bc",func-name="main",offset="0", +++inst="save %sp, -112, %sp"@}, +++@{address="0x000107c0",func-name="main",offset="4", +++inst="mov 2, %o0"@}, +++@{address="0x000107c4",func-name="main",offset="8", +++inst="sethi %hi(0x11800), %o2"@}] +++(gdb) +++@end smallexample +++ +++Disassemble 3 instructions from the start of @code{main} in mixed mode: +++ +++@smallexample +++(gdb) +++-data-disassemble -f basics.c -l 32 -n 3 -- 1 +++^done,asm_insns=[ +++src_and_asm_line=@{line="31", +++file="../../../src/gdb/testsuite/gdb.mi/basics.c", +++fullname="/absolute/path/to/src/gdb/testsuite/gdb.mi/basics.c", +++line_asm_insn=[@{address="0x000107bc", +++func-name="main",offset="0",inst="save %sp, -112, %sp"@}]@}, +++src_and_asm_line=@{line="32", +++file="../../../src/gdb/testsuite/gdb.mi/basics.c", +++fullname="/absolute/path/to/src/gdb/testsuite/gdb.mi/basics.c", +++line_asm_insn=[@{address="0x000107c0", +++func-name="main",offset="4",inst="mov 2, %o0"@}, +++@{address="0x000107c4",func-name="main",offset="8", +++inst="sethi %hi(0x11800), %o2"@}]@}] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-data-evaluate-expression} Command +++@findex -data-evaluate-expression +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-evaluate-expression @var{expr} +++@end smallexample +++ +++Evaluate @var{expr} as an expression. The expression could contain an +++inferior function call. The function call will execute synchronously. +++If the expression contains spaces, it must be enclosed in double quotes. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{print}, @samp{output}, and +++@samp{call}. In @code{gdbtk} only, there's a corresponding +++@samp{gdb_eval} command. +++ +++@subsubheading Example +++ +++In the following example, the numbers that precede the commands are the +++@dfn{tokens} described in @ref{GDB/MI Command Syntax, ,@sc{gdb/mi} +++Command Syntax}. Notice how @sc{gdb/mi} returns the same tokens in its +++output. +++ +++@smallexample +++211-data-evaluate-expression A +++211^done,value="1" +++(gdb) +++311-data-evaluate-expression &A +++311^done,value="0xefffeb7c" +++(gdb) +++411-data-evaluate-expression A+3 +++411^done,value="4" +++(gdb) +++511-data-evaluate-expression "A + 3" +++511^done,value="4" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-data-list-changed-registers} Command +++@findex -data-list-changed-registers +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-list-changed-registers +++@end smallexample +++ +++Display a list of the registers that have changed. +++ +++@subsubheading @value{GDBN} Command +++ +++@value{GDBN} doesn't have a direct analog for this command; @code{gdbtk} +++has the corresponding command @samp{gdb_changed_register_list}. +++ +++@subsubheading Example +++ +++On a PPC MBX board: +++ +++@smallexample +++(gdb) +++-exec-continue +++^running +++ +++(gdb) +++*stopped,reason="breakpoint-hit",disp="keep",bkptno="1",frame=@{ +++func="main",args=[],file="try.c",fullname="/home/foo/bar/try.c", +++line="5",arch="powerpc"@} +++(gdb) +++-data-list-changed-registers +++^done,changed-registers=["0","1","2","4","5","6","7","8","9", +++"10","11","13","14","15","16","17","18","19","20","21","22","23", +++"24","25","26","27","28","30","31","64","65","66","67","69"] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-data-list-register-names} Command +++@findex -data-list-register-names +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-list-register-names [ ( @var{regno} )+ ] +++@end smallexample +++ +++Show a list of register names for the current target. If no arguments +++are given, it shows a list of the names of all the registers. If +++integer numbers are given as arguments, it will print a list of the +++names of the registers corresponding to the arguments. To ensure +++consistency between a register name and its number, the output list may +++include empty register names. +++ +++@subsubheading @value{GDBN} Command +++ +++@value{GDBN} does not have a command which corresponds to +++@samp{-data-list-register-names}. In @code{gdbtk} there is a +++corresponding command @samp{gdb_regnames}. +++ +++@subsubheading Example +++ +++For the PPC MBX board: +++@smallexample +++(gdb) +++-data-list-register-names +++^done,register-names=["r0","r1","r2","r3","r4","r5","r6","r7", +++"r8","r9","r10","r11","r12","r13","r14","r15","r16","r17","r18", +++"r19","r20","r21","r22","r23","r24","r25","r26","r27","r28","r29", +++"r30","r31","f0","f1","f2","f3","f4","f5","f6","f7","f8","f9", +++"f10","f11","f12","f13","f14","f15","f16","f17","f18","f19","f20", +++"f21","f22","f23","f24","f25","f26","f27","f28","f29","f30","f31", +++"", "pc","ps","cr","lr","ctr","xer"] +++(gdb) +++-data-list-register-names 1 2 3 +++^done,register-names=["r1","r2","r3"] +++(gdb) +++@end smallexample +++ +++@subheading The @code{-data-list-register-values} Command +++@findex -data-list-register-values +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-list-register-values +++ [ @code{--skip-unavailable} ] @var{fmt} [ ( @var{regno} )*] +++@end smallexample +++ +++Display the registers' contents. The format according to which the +++registers' contents are to be returned is given by @var{fmt}, followed +++by an optional list of numbers specifying the registers to display. A +++missing list of numbers indicates that the contents of all the +++registers must be returned. The @code{--skip-unavailable} option +++indicates that only the available registers are to be returned. +++ +++Allowed formats for @var{fmt} are: +++ +++@table @code +++@item x +++Hexadecimal +++@item o +++Octal +++@item t +++Binary +++@item d +++Decimal +++@item r +++Raw +++@item N +++Natural +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} commands are @samp{info reg}, @samp{info +++all-reg}, and (in @code{gdbtk}) @samp{gdb_fetch_registers}. +++ +++@subsubheading Example +++ +++For a PPC MBX board (note: line breaks are for readability only, they +++don't appear in the actual output): +++ +++@smallexample +++(gdb) +++-data-list-register-values r 64 65 +++^done,register-values=[@{number="64",value="0xfe00a300"@}, +++@{number="65",value="0x00029002"@}] +++(gdb) +++-data-list-register-values x +++^done,register-values=[@{number="0",value="0xfe0043c8"@}, +++@{number="1",value="0x3fff88"@},@{number="2",value="0xfffffffe"@}, +++@{number="3",value="0x0"@},@{number="4",value="0xa"@}, +++@{number="5",value="0x3fff68"@},@{number="6",value="0x3fff58"@}, +++@{number="7",value="0xfe011e98"@},@{number="8",value="0x2"@}, +++@{number="9",value="0xfa202820"@},@{number="10",value="0xfa202808"@}, +++@{number="11",value="0x1"@},@{number="12",value="0x0"@}, +++@{number="13",value="0x4544"@},@{number="14",value="0xffdfffff"@}, +++@{number="15",value="0xffffffff"@},@{number="16",value="0xfffffeff"@}, +++@{number="17",value="0xefffffed"@},@{number="18",value="0xfffffffe"@}, +++@{number="19",value="0xffffffff"@},@{number="20",value="0xffffffff"@}, +++@{number="21",value="0xffffffff"@},@{number="22",value="0xfffffff7"@}, +++@{number="23",value="0xffffffff"@},@{number="24",value="0xffffffff"@}, +++@{number="25",value="0xffffffff"@},@{number="26",value="0xfffffffb"@}, +++@{number="27",value="0xffffffff"@},@{number="28",value="0xf7bfffff"@}, +++@{number="29",value="0x0"@},@{number="30",value="0xfe010000"@}, +++@{number="31",value="0x0"@},@{number="32",value="0x0"@}, +++@{number="33",value="0x0"@},@{number="34",value="0x0"@}, +++@{number="35",value="0x0"@},@{number="36",value="0x0"@}, +++@{number="37",value="0x0"@},@{number="38",value="0x0"@}, +++@{number="39",value="0x0"@},@{number="40",value="0x0"@}, +++@{number="41",value="0x0"@},@{number="42",value="0x0"@}, +++@{number="43",value="0x0"@},@{number="44",value="0x0"@}, +++@{number="45",value="0x0"@},@{number="46",value="0x0"@}, +++@{number="47",value="0x0"@},@{number="48",value="0x0"@}, +++@{number="49",value="0x0"@},@{number="50",value="0x0"@}, +++@{number="51",value="0x0"@},@{number="52",value="0x0"@}, +++@{number="53",value="0x0"@},@{number="54",value="0x0"@}, +++@{number="55",value="0x0"@},@{number="56",value="0x0"@}, +++@{number="57",value="0x0"@},@{number="58",value="0x0"@}, +++@{number="59",value="0x0"@},@{number="60",value="0x0"@}, +++@{number="61",value="0x0"@},@{number="62",value="0x0"@}, +++@{number="63",value="0x0"@},@{number="64",value="0xfe00a300"@}, +++@{number="65",value="0x29002"@},@{number="66",value="0x202f04b5"@}, +++@{number="67",value="0xfe0043b0"@},@{number="68",value="0xfe00b3e4"@}, +++@{number="69",value="0x20002b03"@}] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-data-read-memory} Command +++@findex -data-read-memory +++ +++This command is deprecated, use @code{-data-read-memory-bytes} instead. +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-read-memory [ -o @var{byte-offset} ] +++ @var{address} @var{word-format} @var{word-size} +++ @var{nr-rows} @var{nr-cols} [ @var{aschar} ] +++@end smallexample +++ +++@noindent +++where: +++ +++@table @samp +++@item @var{address} +++An expression specifying the address of the first memory word to be +++read. Complex expressions containing embedded white space should be +++quoted using the C convention. +++ +++@item @var{word-format} +++The format to be used to print the memory words. The notation is the +++same as for @value{GDBN}'s @code{print} command (@pxref{Output Formats, +++,Output Formats}). +++ +++@item @var{word-size} +++The size of each memory word in bytes. +++ +++@item @var{nr-rows} +++The number of rows in the output table. +++ +++@item @var{nr-cols} +++The number of columns in the output table. +++ +++@item @var{aschar} +++If present, indicates that each row should include an @sc{ascii} dump. The +++value of @var{aschar} is used as a padding character when a byte is not a +++member of the printable @sc{ascii} character set (printable @sc{ascii} +++characters are those whose code is between 32 and 126, inclusively). +++ +++@item @var{byte-offset} +++An offset to add to the @var{address} before fetching memory. +++@end table +++ +++This command displays memory contents as a table of @var{nr-rows} by +++@var{nr-cols} words, each word being @var{word-size} bytes. In total, +++@code{@var{nr-rows} * @var{nr-cols} * @var{word-size}} bytes are read +++(returned as @samp{total-bytes}). Should less than the requested number +++of bytes be returned by the target, the missing words are identified +++using @samp{N/A}. The number of bytes read from the target is returned +++in @samp{nr-bytes} and the starting address used to read memory in +++@samp{addr}. +++ +++The address of the next/previous row or page is available in +++@samp{next-row} and @samp{prev-row}, @samp{next-page} and +++@samp{prev-page}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{x}. @code{gdbtk} has +++@samp{gdb_get_mem} memory read command. +++ +++@subsubheading Example +++ +++Read six bytes of memory starting at @code{bytes+6} but then offset by +++@code{-6} bytes. Format as three rows of two columns. One byte per +++word. Display each word in hex. +++ +++@smallexample +++(gdb) +++9-data-read-memory -o -6 -- bytes+6 x 1 3 2 +++9^done,addr="0x00001390",nr-bytes="6",total-bytes="6", +++next-row="0x00001396",prev-row="0x0000138e",next-page="0x00001396", +++prev-page="0x0000138a",memory=[ +++@{addr="0x00001390",data=["0x00","0x01"]@}, +++@{addr="0x00001392",data=["0x02","0x03"]@}, +++@{addr="0x00001394",data=["0x04","0x05"]@}] +++(gdb) +++@end smallexample +++ +++Read two bytes of memory starting at address @code{shorts + 64} and +++display as a single word formatted in decimal. +++ +++@smallexample +++(gdb) +++5-data-read-memory shorts+64 d 2 1 1 +++5^done,addr="0x00001510",nr-bytes="2",total-bytes="2", +++next-row="0x00001512",prev-row="0x0000150e", +++next-page="0x00001512",prev-page="0x0000150e",memory=[ +++@{addr="0x00001510",data=["128"]@}] +++(gdb) +++@end smallexample +++ +++Read thirty two bytes of memory starting at @code{bytes+16} and format +++as eight rows of four columns. Include a string encoding with @samp{x} +++used as the non-printable character. +++ +++@smallexample +++(gdb) +++4-data-read-memory bytes+16 x 1 8 4 x +++4^done,addr="0x000013a0",nr-bytes="32",total-bytes="32", +++next-row="0x000013c0",prev-row="0x0000139c", +++next-page="0x000013c0",prev-page="0x00001380",memory=[ +++@{addr="0x000013a0",data=["0x10","0x11","0x12","0x13"],ascii="xxxx"@}, +++@{addr="0x000013a4",data=["0x14","0x15","0x16","0x17"],ascii="xxxx"@}, +++@{addr="0x000013a8",data=["0x18","0x19","0x1a","0x1b"],ascii="xxxx"@}, +++@{addr="0x000013ac",data=["0x1c","0x1d","0x1e","0x1f"],ascii="xxxx"@}, +++@{addr="0x000013b0",data=["0x20","0x21","0x22","0x23"],ascii=" !\"#"@}, +++@{addr="0x000013b4",data=["0x24","0x25","0x26","0x27"],ascii="$%&'"@}, +++@{addr="0x000013b8",data=["0x28","0x29","0x2a","0x2b"],ascii="()*+"@}, +++@{addr="0x000013bc",data=["0x2c","0x2d","0x2e","0x2f"],ascii=",-./"@}] +++(gdb) +++@end smallexample +++ +++@subheading The @code{-data-read-memory-bytes} Command +++@findex -data-read-memory-bytes +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-read-memory-bytes [ -o @var{offset} ] +++ @var{address} @var{count} +++@end smallexample +++ +++@noindent +++where: +++ +++@table @samp +++@item @var{address} +++An expression specifying the address of the first addressable memory unit +++to be read. Complex expressions containing embedded white space should be +++quoted using the C convention. +++ +++@item @var{count} +++The number of addressable memory units to read. This should be an integer +++literal. +++ +++@item @var{offset} +++The offset relative to @var{address} at which to start reading. This +++should be an integer literal. This option is provided so that a frontend +++is not required to first evaluate address and then perform address +++arithmetics itself. +++ +++@end table +++ +++This command attempts to read all accessible memory regions in the +++specified range. First, all regions marked as unreadable in the memory +++map (if one is defined) will be skipped. @xref{Memory Region +++Attributes}. Second, @value{GDBN} will attempt to read the remaining +++regions. For each one, if reading full region results in an errors, +++@value{GDBN} will try to read a subset of the region. +++ +++In general, every single memory unit in the region may be readable or not, +++and the only way to read every readable unit is to try a read at +++every address, which is not practical. Therefore, @value{GDBN} will +++attempt to read all accessible memory units at either beginning or the end +++of the region, using a binary division scheme. This heuristic works +++well for reading across a memory map boundary. Note that if a region +++has a readable range that is neither at the beginning or the end, +++@value{GDBN} will not read it. +++ +++The result record (@pxref{GDB/MI Result Records}) that is output of +++the command includes a field named @samp{memory} whose content is a +++list of tuples. Each tuple represent a successfully read memory block +++and has the following fields: +++ +++@table @code +++@item begin +++The start address of the memory block, as hexadecimal literal. +++ +++@item end +++The end address of the memory block, as hexadecimal literal. +++ +++@item offset +++The offset of the memory block, as hexadecimal literal, relative to +++the start address passed to @code{-data-read-memory-bytes}. +++ +++@item contents +++The contents of the memory block, in hex. +++ +++@end table +++ +++ +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{x}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-data-read-memory-bytes &a 10 +++^done,memory=[@{begin="0xbffff154",offset="0x00000000", +++ end="0xbffff15e", +++ contents="01000000020000000300"@}] +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-data-write-memory-bytes} Command +++@findex -data-write-memory-bytes +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -data-write-memory-bytes @var{address} @var{contents} +++ -data-write-memory-bytes @var{address} @var{contents} @r{[}@var{count}@r{]} +++@end smallexample +++ +++@noindent +++where: +++ +++@table @samp +++@item @var{address} +++An expression specifying the address of the first addressable memory unit +++to be written. Complex expressions containing embedded white space should +++be quoted using the C convention. +++ +++@item @var{contents} +++The hex-encoded data to write. It is an error if @var{contents} does +++not represent an integral number of addressable memory units. +++ +++@item @var{count} +++Optional argument indicating the number of addressable memory units to be +++written. If @var{count} is greater than @var{contents}' length, +++@value{GDBN} will repeatedly write @var{contents} until it fills +++@var{count} memory units. +++ +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++There's no corresponding @value{GDBN} command. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-data-write-memory-bytes &a "aabbccdd" +++^done +++(gdb) +++@end smallexample +++ +++@smallexample +++(gdb) +++-data-write-memory-bytes &a "aabbccdd" 16e +++^done +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Tracepoint Commands +++@section @sc{gdb/mi} Tracepoint Commands +++ +++The commands defined in this section implement MI support for +++tracepoints. For detailed introduction, see @ref{Tracepoints}. +++ +++@subheading The @code{-trace-find} Command +++@findex -trace-find +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-find @var{mode} [@var{parameters}@dots{}] +++@end smallexample +++ +++Find a trace frame using criteria defined by @var{mode} and +++@var{parameters}. The following table lists permissible +++modes and their parameters. For details of operation, see @ref{tfind}. +++ +++@table @samp +++ +++@item none +++No parameters are required. Stops examining trace frames. +++ +++@item frame-number +++An integer is required as parameter. Selects tracepoint frame with +++that index. +++ +++@item tracepoint-number +++An integer is required as parameter. Finds next +++trace frame that corresponds to tracepoint with the specified number. +++ +++@item pc +++An address is required as parameter. Finds +++next trace frame that corresponds to any tracepoint at the specified +++address. +++ +++@item pc-inside-range +++Two addresses are required as parameters. Finds next trace +++frame that corresponds to a tracepoint at an address inside the +++specified range. Both bounds are considered to be inside the range. +++ +++@item pc-outside-range +++Two addresses are required as parameters. Finds +++next trace frame that corresponds to a tracepoint at an address outside +++the specified range. Both bounds are considered to be inside the range. +++ +++@item line +++Line specification is required as parameter. @xref{Specify Location}. +++Finds next trace frame that corresponds to a tracepoint at +++the specified location. +++ +++@end table +++ +++If @samp{none} was passed as @var{mode}, the response does not +++have fields. Otherwise, the response may have the following fields: +++ +++@table @samp +++@item found +++This field has either @samp{0} or @samp{1} as the value, depending +++on whether a matching tracepoint was found. +++ +++@item traceframe +++The index of the found traceframe. This field is present iff +++the @samp{found} field has value of @samp{1}. +++ +++@item tracepoint +++The index of the found tracepoint. This field is present iff +++the @samp{found} field has value of @samp{1}. +++ +++@item frame +++The information about the frame corresponding to the found trace +++frame. This field is present only if a trace frame was found. +++@xref{GDB/MI Frame Information}, for description of this field. +++ +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tfind}. +++ +++@subheading -trace-define-variable +++@findex -trace-define-variable +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-define-variable @var{name} [ @var{value} ] +++@end smallexample +++ +++Create trace variable @var{name} if it does not exist. If +++@var{value} is specified, sets the initial value of the specified +++trace variable to that value. Note that the @var{name} should start +++with the @samp{$} character. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tvariable}. +++ +++@subheading The @code{-trace-frame-collected} Command +++@findex -trace-frame-collected +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-frame-collected +++ [--var-print-values @var{var_pval}] +++ [--comp-print-values @var{comp_pval}] +++ [--registers-format @var{regformat}] +++ [--memory-contents] +++@end smallexample +++ +++This command returns the set of collected objects, register names, +++trace state variable names, memory ranges and computed expressions +++that have been collected at a particular trace frame. The optional +++parameters to the command affect the output format in different ways. +++See the output description table below for more details. +++ +++The reported names can be used in the normal manner to create +++varobjs and inspect the objects themselves. The items returned by +++this command are categorized so that it is clear which is a variable, +++which is a register, which is a trace state variable, which is a +++memory range and which is a computed expression. +++ +++For instance, if the actions were +++@smallexample +++collect myVar, myArray[myIndex], myObj.field, myPtr->field, myCount + 2 +++collect *(int*)0xaf02bef0@@40 +++@end smallexample +++ +++@noindent +++the object collected in its entirety would be @code{myVar}. The +++object @code{myArray} would be partially collected, because only the +++element at index @code{myIndex} would be collected. The remaining +++objects would be computed expressions. +++ +++An example output would be: +++ +++@smallexample +++(gdb) +++-trace-frame-collected +++^done, +++ explicit-variables=[@{name="myVar",value="1"@}], +++ computed-expressions=[@{name="myArray[myIndex]",value="0"@}, +++ @{name="myObj.field",value="0"@}, +++ @{name="myPtr->field",value="1"@}, +++ @{name="myCount + 2",value="3"@}, +++ @{name="$tvar1 + 1",value="43970027"@}], +++ registers=[@{number="0",value="0x7fe2c6e79ec8"@}, +++ @{number="1",value="0x0"@}, +++ @{number="2",value="0x4"@}, +++ ... +++ @{number="125",value="0x0"@}], +++ tvars=[@{name="$tvar1",current="43970026"@}], +++ memory=[@{address="0x0000000000602264",length="4"@}, +++ @{address="0x0000000000615bc0",length="4"@}] +++(gdb) +++@end smallexample +++ +++Where: +++ +++@table @code +++@item explicit-variables +++The set of objects that have been collected in their entirety (as +++opposed to collecting just a few elements of an array or a few struct +++members). For each object, its name and value are printed. +++The @code{--var-print-values} option affects how or whether the value +++field is output. If @var{var_pval} is 0, then print only the names; +++if it is 1, print also their values; and if it is 2, print the name, +++type and value for simple data types, and the name and type for +++arrays, structures and unions. +++ +++@item computed-expressions +++The set of computed expressions that have been collected at the +++current trace frame. The @code{--comp-print-values} option affects +++this set like the @code{--var-print-values} option affects the +++@code{explicit-variables} set. See above. +++ +++@item registers +++The registers that have been collected at the current trace frame. +++For each register collected, the name and current value are returned. +++The value is formatted according to the @code{--registers-format} +++option. See the @command{-data-list-register-values} command for a +++list of the allowed formats. The default is @samp{x}. +++ +++@item tvars +++The trace state variables that have been collected at the current +++trace frame. For each trace state variable collected, the name and +++current value are returned. +++ +++@item memory +++The set of memory ranges that have been collected at the current trace +++frame. Its content is a list of tuples. Each tuple represents a +++collected memory range and has the following fields: +++ +++@table @code +++@item address +++The start address of the memory range, as hexadecimal literal. +++ +++@item length +++The length of the memory range, as decimal literal. +++ +++@item contents +++The contents of the memory block, in hex. This field is only present +++if the @code{--memory-contents} option is specified. +++ +++@end table +++ +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++There is no corresponding @value{GDBN} command. +++ +++@subsubheading Example +++ +++@subheading -trace-list-variables +++@findex -trace-list-variables +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-list-variables +++@end smallexample +++ +++Return a table of all defined trace variables. Each element of the +++table has the following fields: +++ +++@table @samp +++@item name +++The name of the trace variable. This field is always present. +++ +++@item initial +++The initial value. This is a 64-bit signed integer. This +++field is always present. +++ +++@item current +++The value the trace variable has at the moment. This is a 64-bit +++signed integer. This field is absent iff current value is +++not defined, for example if the trace was never run, or is +++presently running. +++ +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tvariables}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-trace-list-variables +++^done,trace-variables=@{nr_rows="1",nr_cols="3", +++hdr=[@{width="15",alignment="-1",col_name="name",colhdr="Name"@}, +++ @{width="11",alignment="-1",col_name="initial",colhdr="Initial"@}, +++ @{width="11",alignment="-1",col_name="current",colhdr="Current"@}], +++body=[variable=@{name="$trace_timestamp",initial="0"@} +++ variable=@{name="$foo",initial="10",current="15"@}]@} +++(gdb) +++@end smallexample +++ +++@subheading -trace-save +++@findex -trace-save +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-save [ -r ] [ -ctf ] @var{filename} +++@end smallexample +++ +++Saves the collected trace data to @var{filename}. Without the +++@samp{-r} option, the data is downloaded from the target and saved +++in a local file. With the @samp{-r} option the target is asked +++to perform the save. +++ +++By default, this command will save the trace in the tfile format. You can +++supply the optional @samp{-ctf} argument to save it the CTF format. See +++@ref{Trace Files} for more information about CTF. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tsave}. +++ +++ +++@subheading -trace-start +++@findex -trace-start +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-start +++@end smallexample +++ +++Starts a tracing experiment. The result of this command does not +++have any fields. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tstart}. +++ +++@subheading -trace-status +++@findex -trace-status +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-status +++@end smallexample +++ +++Obtains the status of a tracing experiment. The result may include +++the following fields: +++ +++@table @samp +++ +++@item supported +++May have a value of either @samp{0}, when no tracing operations are +++supported, @samp{1}, when all tracing operations are supported, or +++@samp{file} when examining trace file. In the latter case, examining +++of trace frame is possible but new tracing experiement cannot be +++started. This field is always present. +++ +++@item running +++May have a value of either @samp{0} or @samp{1} depending on whether +++tracing experiement is in progress on target. This field is present +++if @samp{supported} field is not @samp{0}. +++ +++@item stop-reason +++Report the reason why the tracing was stopped last time. This field +++may be absent iff tracing was never stopped on target yet. The +++value of @samp{request} means the tracing was stopped as result of +++the @code{-trace-stop} command. The value of @samp{overflow} means +++the tracing buffer is full. The value of @samp{disconnection} means +++tracing was automatically stopped when @value{GDBN} has disconnected. +++The value of @samp{passcount} means tracing was stopped when a +++tracepoint was passed a maximal number of times for that tracepoint. +++This field is present if @samp{supported} field is not @samp{0}. +++ +++@item stopping-tracepoint +++The number of tracepoint whose passcount as exceeded. This field is +++present iff the @samp{stop-reason} field has the value of +++@samp{passcount}. +++ +++@item frames +++@itemx frames-created +++The @samp{frames} field is a count of the total number of trace frames +++in the trace buffer, while @samp{frames-created} is the total created +++during the run, including ones that were discarded, such as when a +++circular trace buffer filled up. Both fields are optional. +++ +++@item buffer-size +++@itemx buffer-free +++These fields tell the current size of the tracing buffer and the +++remaining space. These fields are optional. +++ +++@item circular +++The value of the circular trace buffer flag. @code{1} means that the +++trace buffer is circular and old trace frames will be discarded if +++necessary to make room, @code{0} means that the trace buffer is linear +++and may fill up. +++ +++@item disconnected +++The value of the disconnected tracing flag. @code{1} means that +++tracing will continue after @value{GDBN} disconnects, @code{0} means +++that the trace run will stop. +++ +++@item trace-file +++The filename of the trace file being examined. This field is +++optional, and only present when examining a trace file. +++ +++@end table +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tstatus}. +++ +++@subheading -trace-stop +++@findex -trace-stop +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -trace-stop +++@end smallexample +++ +++Stops a tracing experiment. The result of this command has the same +++fields as @code{-trace-status}, except that the @samp{supported} and +++@samp{running} fields are not output. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{tstop}. +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Symbol Query +++@section @sc{gdb/mi} Symbol Query Commands +++ +++ +++@ignore +++@subheading The @code{-symbol-info-address} Command +++@findex -symbol-info-address +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-address @var{symbol} +++@end smallexample +++ +++Describe where @var{symbol} is stored. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info address}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-info-file} Command +++@findex -symbol-info-file +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-file +++@end smallexample +++ +++Show the file for the symbol. +++ +++@subsubheading @value{GDBN} Command +++ +++There's no equivalent @value{GDBN} command. @code{gdbtk} has +++@samp{gdb_find_file}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++@subheading The @code{-symbol-info-functions} Command +++@findex -symbol-info-functions +++@anchor{-symbol-info-functions} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-functions [--include-nondebug] +++ [--type @var{type_regexp}] +++ [--name @var{name_regexp}] +++ [--max-results @var{limit}] +++@end smallexample +++ +++@noindent +++Return a list containing the names and types for all global functions +++taken from the debug information. The functions are grouped by source +++file, and shown with the line number on which each function is +++defined. +++ +++The @code{--include-nondebug} option causes the output to include +++code symbols from the symbol table. +++ +++The options @code{--type} and @code{--name} allow the symbols returned +++to be filtered based on either the name of the function, or the type +++signature of the function. +++ +++The option @code{--max-results} restricts the command to return no +++more than @var{limit} results. If exactly @var{limit} results are +++returned then there might be additional results available if a higher +++limit is used. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info functions}. +++ +++@subsubheading Example +++@smallexample +++@group +++(gdb) +++-symbol-info-functions +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"@}, +++ @{line="42", name="main", type="int ()", +++ description="int main();"@}, +++ @{line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="33", name="f2", type="float (another_float_t)", +++ description="float f2(another_float_t);"@}, +++ @{line="39", name="f3", type="int (another_int_t)", +++ description="int f3(another_int_t);"@}, +++ @{line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-functions --name f1 +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-functions --type void +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-functions --include-nondebug +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="36", name="f4", type="void (int *)", +++ description="void f4(int *);"@}, +++ @{line="42", name="main", type="int ()", +++ description="int main();"@}, +++ @{line="30", name="f1", type="my_int_t (int, int)", +++ description="static my_int_t f1(int, int);"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="33", name="f2", type="float (another_float_t)", +++ description="float f2(another_float_t);"@}, +++ @{line="39", name="f3", type="int (another_int_t)", +++ description="int f3(another_int_t);"@}, +++ @{line="27", name="f1", type="another_float_t (int)", +++ description="static another_float_t f1(int);"@}]@}], +++ nondebug= +++ [@{address="0x0000000000400398",name="_init"@}, +++ @{address="0x00000000004003b0",name="_start"@}, +++ ... +++ ]@} +++@end group +++@end smallexample +++ +++@subheading The @code{-symbol-info-module-functions} Command +++@findex -symbol-info-module-functions +++@anchor{-symbol-info-module-functions} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-module-functions [--module @var{module_regexp}] +++ [--name @var{name_regexp}] +++ [--type @var{type_regexp}] +++@end smallexample +++ +++@noindent +++Return a list containing the names of all known functions within all +++know Fortran modules. The functions are grouped by source file and +++containing module, and shown with the line number on which each +++function is defined. +++ +++The option @code{--module} only returns results for modules matching +++@var{module_regexp}. The option @code{--name} only returns functions +++whose name matches @var{name_regexp}, and @code{--type} only returns +++functions whose type matches @var{type_regexp}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info module functions}. +++ +++@subsubheading Example +++ +++@smallexample +++@group +++(gdb) +++-symbol-info-module-functions +++^done,symbols= +++ [@{module="mod1", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="21",name="mod1::check_all",type="void (void)", +++ description="void mod1::check_all(void);"@}]@}]@}, +++ @{module="mod2", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="30",name="mod2::check_var_i",type="void (void)", +++ description="void mod2::check_var_i(void);"@}]@}]@}, +++ @{module="mod3", +++ files=[@{filename="/projec/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/projec/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="21",name="mod3::check_all",type="void (void)", +++ description="void mod3::check_all(void);"@}, +++ @{line="27",name="mod3::check_mod2",type="void (void)", +++ description="void mod3::check_mod2(void);"@}]@}]@}, +++ @{module="modmany", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="35",name="modmany::check_some",type="void (void)", +++ description="void modmany::check_some(void);"@}]@}]@}, +++ @{module="moduse", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="44",name="moduse::check_all",type="void (void)", +++ description="void moduse::check_all(void);"@}, +++ @{line="49",name="moduse::check_var_x",type="void (void)", +++ description="void moduse::check_var_x(void);"@}]@}]@}] +++@end group +++@end smallexample +++ +++@subheading The @code{-symbol-info-module-variables} Command +++@findex -symbol-info-module-variables +++@anchor{-symbol-info-module-variables} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-module-variables [--module @var{module_regexp}] +++ [--name @var{name_regexp}] +++ [--type @var{type_regexp}] +++@end smallexample +++ +++@noindent +++Return a list containing the names of all known variables within all +++know Fortran modules. The variables are grouped by source file and +++containing module, and shown with the line number on which each +++variable is defined. +++ +++The option @code{--module} only returns results for modules matching +++@var{module_regexp}. The option @code{--name} only returns variables +++whose name matches @var{name_regexp}, and @code{--type} only returns +++variables whose type matches @var{type_regexp}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info module variables}. +++ +++@subsubheading Example +++ +++@smallexample +++@group +++(gdb) +++-symbol-info-module-variables +++^done,symbols= +++ [@{module="mod1", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="18",name="mod1::var_const",type="integer(kind=4)", +++ description="integer(kind=4) mod1::var_const;"@}, +++ @{line="17",name="mod1::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod1::var_i;"@}]@}]@}, +++ @{module="mod2", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="28",name="mod2::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod2::var_i;"@}]@}]@}, +++ @{module="mod3", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="18",name="mod3::mod1",type="integer(kind=4)", +++ description="integer(kind=4) mod3::mod1;"@}, +++ @{line="17",name="mod3::mod2",type="integer(kind=4)", +++ description="integer(kind=4) mod3::mod2;"@}, +++ @{line="19",name="mod3::var_i",type="integer(kind=4)", +++ description="integer(kind=4) mod3::var_i;"@}]@}]@}, +++ @{module="modmany", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="33",name="modmany::var_a",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_a;"@}, +++ @{line="33",name="modmany::var_b",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_b;"@}, +++ @{line="33",name="modmany::var_c",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_c;"@}, +++ @{line="33",name="modmany::var_i",type="integer(kind=4)", +++ description="integer(kind=4) modmany::var_i;"@}]@}]@}, +++ @{module="moduse", +++ files=[@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="42",name="moduse::var_x",type="integer(kind=4)", +++ description="integer(kind=4) moduse::var_x;"@}, +++ @{line="42",name="moduse::var_y",type="integer(kind=4)", +++ description="integer(kind=4) moduse::var_y;"@}]@}]@}] +++@end group +++@end smallexample +++ +++@subheading The @code{-symbol-info-modules} Command +++@findex -symbol-info-modules +++@anchor{-symbol-info-modules} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-modules [--name @var{name_regexp}] +++ [--max-results @var{limit}] +++ +++@end smallexample +++ +++@noindent +++Return a list containing the names of all known Fortran modules. The +++modules are grouped by source file, and shown with the line number on +++which each modules is defined. +++ +++The option @code{--name} allows the modules returned to be filtered +++based the name of the module. +++ +++The option @code{--max-results} restricts the command to return no +++more than @var{limit} results. If exactly @var{limit} results are +++returned then there might be additional results available if a higher +++limit is used. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info modules}. +++ +++@subsubheading Example +++@smallexample +++@group +++(gdb) +++-symbol-info-modules +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="16",name="mod1"@}, +++ @{line="22",name="mod2"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="16",name="mod3"@}, +++ @{line="22",name="modmany"@}, +++ @{line="26",name="moduse"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-modules --name mod[123] +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules-2.f90", +++ symbols=[@{line="16",name="mod1"@}, +++ @{line="22",name="mod2"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-fortran-modules.f90", +++ symbols=[@{line="16",name="mod3"@}]@}]@} +++@end group +++@end smallexample +++ +++@subheading The @code{-symbol-info-types} Command +++@findex -symbol-info-types +++@anchor{-symbol-info-types} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-types [--name @var{name_regexp}] +++ [--max-results @var{limit}] +++ +++@end smallexample +++ +++@noindent +++Return a list of all defined types. The types are grouped by source +++file, and shown with the line number on which each user defined type +++is defined. Some base types are not defined in the source code but +++are added to the debug information by the compiler, for example +++@code{int}, @code{float}, etc.; these types do not have an associated +++line number. +++ +++The option @code{--name} allows the list of types returned to be +++filtered by name. +++ +++The option @code{--max-results} restricts the command to return no +++more than @var{limit} results. If exactly @var{limit} results are +++returned then there might be additional results available if a higher +++limit is used. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info types}. +++ +++@subsubheading Example +++@smallexample +++@group +++(gdb) +++-symbol-info-types +++^done,symbols= +++ @{debug= +++ [@{filename="gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{name="float"@}, +++ @{name="int"@}, +++ @{line="27",name="typedef int my_int_t;"@}]@}, +++ @{filename="gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="24",name="typedef float another_float_t;"@}, +++ @{line="23",name="typedef int another_int_t;"@}, +++ @{name="float"@}, +++ @{name="int"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-types --name _int_ +++^done,symbols= +++ @{debug= +++ [@{filename="gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="27",name="typedef int my_int_t;"@}]@}, +++ @{filename="gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="23",name="typedef int another_int_t;"@}]@}]@} +++@end group +++@end smallexample +++ +++@subheading The @code{-symbol-info-variables} Command +++@findex -symbol-info-variables +++@anchor{-symbol-info-variables} +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-variables [--include-nondebug] +++ [--type @var{type_regexp}] +++ [--name @var{name_regexp}] +++ [--max-results @var{limit}] +++ +++@end smallexample +++ +++@noindent +++Return a list containing the names and types for all global variables +++taken from the debug information. The variables are grouped by source +++file, and shown with the line number on which each variable is +++defined. +++ +++The @code{--include-nondebug} option causes the output to include +++data symbols from the symbol table. +++ +++The options @code{--type} and @code{--name} allow the symbols returned +++to be filtered based on either the name of the variable, or the type +++of the variable. +++ +++The option @code{--max-results} restricts the command to return no +++more than @var{limit} results. If exactly @var{limit} results are +++returned then there might be additional results available if a higher +++limit is used. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info variables}. +++ +++@subsubheading Example +++@smallexample +++@group +++(gdb) +++-symbol-info-variables +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="25",name="global_f1",type="float", +++ description="static float global_f1;"@}, +++ @{line="24",name="global_i1",type="int", +++ description="static int global_i1;"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="21",name="global_f2",type="int", +++ description="int global_f2;"@}, +++ @{line="20",name="global_i2",type="int", +++ description="int global_i2;"@}, +++ @{line="19",name="global_f1",type="float", +++ description="static float global_f1;"@}, +++ @{line="18",name="global_i1",type="int", +++ description="static int global_i1;"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-variables --name f1 +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="25",name="global_f1",type="float", +++ description="static float global_f1;"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="19",name="global_f1",type="float", +++ description="static float global_f1;"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-variables --type float +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="25",name="global_f1",type="float", +++ description="static float global_f1;"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="19",name="global_f1",type="float", +++ description="static float global_f1;"@}]@}]@} +++@end group +++@group +++(gdb) +++-symbol-info-variables --include-nondebug +++^done,symbols= +++ @{debug= +++ [@{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-1.c", +++ symbols=[@{line="25",name="global_f1",type="float", +++ description="static float global_f1;"@}, +++ @{line="24",name="global_i1",type="int", +++ description="static int global_i1;"@}]@}, +++ @{filename="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ fullname="/project/gdb/testsuite/gdb.mi/mi-sym-info-2.c", +++ symbols=[@{line="21",name="global_f2",type="int", +++ description="int global_f2;"@}, +++ @{line="20",name="global_i2",type="int", +++ description="int global_i2;"@}, +++ @{line="19",name="global_f1",type="float", +++ description="static float global_f1;"@}, +++ @{line="18",name="global_i1",type="int", +++ description="static int global_i1;"@}]@}], +++ nondebug= +++ [@{address="0x00000000004005d0",name="_IO_stdin_used"@}, +++ @{address="0x00000000004005d8",name="__dso_handle"@} +++ ... +++ ]@} +++@end group +++@end smallexample +++ +++@ignore +++@subheading The @code{-symbol-info-line} Command +++@findex -symbol-info-line +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-line +++@end smallexample +++ +++Show the core addresses of the code for a source line. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info line}. +++@code{gdbtk} has the @samp{gdb_get_line} and @samp{gdb_get_file} commands. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-info-symbol} Command +++@findex -symbol-info-symbol +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-info-symbol @var{addr} +++@end smallexample +++ +++Describe what symbol is at location @var{addr}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info symbol}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-list-functions} Command +++@findex -symbol-list-functions +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-list-functions +++@end smallexample +++ +++List the functions in the executable. +++ +++@subsubheading @value{GDBN} Command +++ +++@samp{info functions} in @value{GDBN}, @samp{gdb_listfunc} and +++@samp{gdb_search} in @code{gdbtk}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-symbol-list-lines} Command +++@findex -symbol-list-lines +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-list-lines @var{filename} +++@end smallexample +++ +++Print the list of lines that contain code and their associated program +++addresses for the given source filename. The entries are sorted in +++ascending PC order. +++ +++@subsubheading @value{GDBN} Command +++ +++There is no corresponding @value{GDBN} command. +++ +++@subsubheading Example +++@smallexample +++(gdb) +++-symbol-list-lines basics.c +++^done,lines=[@{pc="0x08048554",line="7"@},@{pc="0x0804855a",line="8"@}] +++(gdb) +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-symbol-list-types} Command +++@findex -symbol-list-types +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-list-types +++@end smallexample +++ +++List all the type names. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding commands are @samp{info types} in @value{GDBN}, +++@samp{gdb_search} in @code{gdbtk}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-list-variables} Command +++@findex -symbol-list-variables +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-list-variables +++@end smallexample +++ +++List all the global and static variable names. +++ +++@subsubheading @value{GDBN} Command +++ +++@samp{info variables} in @value{GDBN}, @samp{gdb_search} in @code{gdbtk}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-locate} Command +++@findex -symbol-locate +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-locate +++@end smallexample +++ +++@subsubheading @value{GDBN} Command +++ +++@samp{gdb_loc} in @code{gdbtk}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-symbol-type} Command +++@findex -symbol-type +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -symbol-type @var{variable} +++@end smallexample +++ +++Show type of @var{variable}. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{ptype}, @code{gdbtk} has +++@samp{gdb_obj_variable}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI File Commands +++@section @sc{gdb/mi} File Commands +++ +++This section describes the GDB/MI commands to specify executable file names +++and to read in and obtain symbol table information. +++ +++@subheading The @code{-file-exec-and-symbols} Command +++@findex -file-exec-and-symbols +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-exec-and-symbols @var{file} +++@end smallexample +++ +++Specify the executable file to be debugged. This file is the one from +++which the symbol table is also read. If no file is specified, the +++command clears the executable and symbol information. If breakpoints +++are set when using this command with no arguments, @value{GDBN} will produce +++error messages. Otherwise, no output is produced, except a completion +++notification. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{file}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-file-exec-and-symbols /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-file-exec-file} Command +++@findex -file-exec-file +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-exec-file @var{file} +++@end smallexample +++ +++Specify the executable file to be debugged. Unlike +++@samp{-file-exec-and-symbols}, the symbol table is @emph{not} read +++from this file. If used without argument, @value{GDBN} clears the information +++about the executable file. No output is produced, except a completion +++notification. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{exec-file}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-file-exec-file /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++^done +++(gdb) +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-file-list-exec-sections} Command +++@findex -file-list-exec-sections +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-list-exec-sections +++@end smallexample +++ +++List the sections of the current executable file. +++ +++@subsubheading @value{GDBN} Command +++ +++The @value{GDBN} command @samp{info file} shows, among the rest, the same +++information as this command. @code{gdbtk} has a corresponding command +++@samp{gdb_load_info}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-file-list-exec-source-file} Command +++@findex -file-list-exec-source-file +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-list-exec-source-file +++@end smallexample +++ +++List the line number, the current source file, and the absolute path +++to the current source file for the current executable. The macro +++information field has a value of @samp{1} or @samp{0} depending on +++whether or not the file includes preprocessor macro information. +++ +++@subsubheading @value{GDBN} Command +++ +++The @value{GDBN} equivalent is @samp{info source} +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++123-file-list-exec-source-file +++123^done,line="1",file="foo.c",fullname="/home/bar/foo.c,macro-info="1" +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-file-list-exec-source-files} Command +++@findex -file-list-exec-source-files +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-list-exec-source-files +++@end smallexample +++ +++List the source files for the current executable. +++ +++It will always output both the filename and fullname (absolute file +++name) of a source file. +++ +++@subsubheading @value{GDBN} Command +++ +++The @value{GDBN} equivalent is @samp{info sources}. +++@code{gdbtk} has an analogous command @samp{gdb_listfiles}. +++ +++@subsubheading Example +++@smallexample +++(gdb) +++-file-list-exec-source-files +++^done,files=[ +++@{file=foo.c,fullname=/home/foo.c@}, +++@{file=/home/bar.c,fullname=/home/bar.c@}, +++@{file=gdb_could_not_find_fullpath.c@}] +++(gdb) +++@end smallexample +++ +++@subheading The @code{-file-list-shared-libraries} Command +++@findex -file-list-shared-libraries +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-list-shared-libraries [ @var{regexp} ] +++@end smallexample +++ +++List the shared libraries in the program. +++With a regular expression @var{regexp}, only those libraries whose +++names match @var{regexp} are listed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info shared}. The fields +++have a similar meaning to the @code{=library-loaded} notification. +++The @code{ranges} field specifies the multiple segments belonging to this +++library. Each range has the following fields: +++ +++@table @samp +++@item from +++The address defining the inclusive lower bound of the segment. +++@item to +++The address defining the exclusive upper bound of the segment. +++@end table +++ +++@subsubheading Example +++@smallexample +++(gdb) +++-file-list-exec-source-files +++^done,shared-libraries=[ +++@{id="/lib/libfoo.so",target-name="/lib/libfoo.so",host-name="/lib/libfoo.so",symbols-loaded="1",thread-group="i1",ranges=[@{from="0x72815989",to="0x728162c0"@}]@}, +++@{id="/lib/libbar.so",target-name="/lib/libbar.so",host-name="/lib/libbar.so",symbols-loaded="1",thread-group="i1",ranges=[@{from="0x76ee48c0",to="0x76ee9160"@}]@}] +++(gdb) +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-file-list-symbol-files} Command +++@findex -file-list-symbol-files +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-list-symbol-files +++@end smallexample +++ +++List symbol files. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info file} (part of it). +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-file-symbol-file} Command +++@findex -file-symbol-file +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -file-symbol-file @var{file} +++@end smallexample +++ +++Read symbol table info from the specified @var{file} argument. When +++used without arguments, clears @value{GDBN}'s symbol table info. No output is +++produced, except for a completion notification. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{symbol-file}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-file-symbol-file /kwikemart/marge/ezannoni/TRUNK/mbx/hello.mbx +++^done +++(gdb) +++@end smallexample +++ +++@ignore +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Memory Overlay Commands +++@section @sc{gdb/mi} Memory Overlay Commands +++ +++The memory overlay commands are not implemented. +++ +++@c @subheading -overlay-auto +++ +++@c @subheading -overlay-list-mapping-state +++ +++@c @subheading -overlay-list-overlays +++ +++@c @subheading -overlay-map +++ +++@c @subheading -overlay-off +++ +++@c @subheading -overlay-on +++ +++@c @subheading -overlay-unmap +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Signal Handling Commands +++@section @sc{gdb/mi} Signal Handling Commands +++ +++Signal handling commands are not implemented. +++ +++@c @subheading -signal-handle +++ +++@c @subheading -signal-list-handle-actions +++ +++@c @subheading -signal-list-signal-types +++@end ignore +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Target Manipulation +++@section @sc{gdb/mi} Target Manipulation Commands +++ +++ +++@subheading The @code{-target-attach} Command +++@findex -target-attach +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-attach @var{pid} | @var{gid} | @var{file} +++@end smallexample +++ +++Attach to a process @var{pid} or a file @var{file} outside of +++@value{GDBN}, or a thread group @var{gid}. If attaching to a thread +++group, the id previously returned by +++@samp{-list-thread-groups --available} must be used. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{attach}. +++ +++@subsubheading Example +++@smallexample +++(gdb) +++-target-attach 34 +++=thread-created,id="1" +++*stopped,thread-id="1",frame=@{addr="0xb7f7e410",func="bar",args=[]@} +++^done +++(gdb) +++@end smallexample +++ +++@ignore +++@subheading The @code{-target-compare-sections} Command +++@findex -target-compare-sections +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-compare-sections [ @var{section} ] +++@end smallexample +++ +++Compare data of section @var{section} on target to the exec file. +++Without the argument, all sections are compared. +++ +++@subsubheading @value{GDBN} Command +++ +++The @value{GDBN} equivalent is @samp{compare-sections}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-target-detach} Command +++@findex -target-detach +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-detach [ @var{pid} | @var{gid} ] +++@end smallexample +++ +++Detach from the remote target which normally resumes its execution. +++If either @var{pid} or @var{gid} is specified, detaches from either +++the specified process, or specified thread group. There's no output. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{detach}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-detach +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-target-disconnect} Command +++@findex -target-disconnect +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-disconnect +++@end smallexample +++ +++Disconnect from the remote target. There's no output and the target is +++generally not resumed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{disconnect}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-disconnect +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-target-download} Command +++@findex -target-download +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-download +++@end smallexample +++ +++Loads the executable onto the remote target. +++It prints out an update message every half second, which includes the fields: +++ +++@table @samp +++@item section +++The name of the section. +++@item section-sent +++The size of what has been sent so far for that section. +++@item section-size +++The size of the section. +++@item total-sent +++The total size of what was sent so far (the current and the previous sections). +++@item total-size +++The size of the overall executable to download. +++@end table +++ +++@noindent +++Each message is sent as status record (@pxref{GDB/MI Output Syntax, , +++@sc{gdb/mi} Output Syntax}). +++ +++In addition, it prints the name and size of the sections, as they are +++downloaded. These messages include the following fields: +++ +++@table @samp +++@item section +++The name of the section. +++@item section-size +++The size of the section. +++@item total-size +++The size of the overall executable to download. +++@end table +++ +++@noindent +++At the end, a summary is printed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{load}. +++ +++@subsubheading Example +++ +++Note: each status message appears on a single line. Here the messages +++have been broken down so that they can fit onto a page. +++ +++@smallexample +++(gdb) +++-target-download ++++download,@{section=".text",section-size="6668",total-size="9880"@} ++++download,@{section=".text",section-sent="512",section-size="6668", +++total-sent="512",total-size="9880"@} ++++download,@{section=".text",section-sent="1024",section-size="6668", +++total-sent="1024",total-size="9880"@} ++++download,@{section=".text",section-sent="1536",section-size="6668", +++total-sent="1536",total-size="9880"@} ++++download,@{section=".text",section-sent="2048",section-size="6668", +++total-sent="2048",total-size="9880"@} ++++download,@{section=".text",section-sent="2560",section-size="6668", +++total-sent="2560",total-size="9880"@} ++++download,@{section=".text",section-sent="3072",section-size="6668", +++total-sent="3072",total-size="9880"@} ++++download,@{section=".text",section-sent="3584",section-size="6668", +++total-sent="3584",total-size="9880"@} ++++download,@{section=".text",section-sent="4096",section-size="6668", +++total-sent="4096",total-size="9880"@} ++++download,@{section=".text",section-sent="4608",section-size="6668", +++total-sent="4608",total-size="9880"@} ++++download,@{section=".text",section-sent="5120",section-size="6668", +++total-sent="5120",total-size="9880"@} ++++download,@{section=".text",section-sent="5632",section-size="6668", +++total-sent="5632",total-size="9880"@} ++++download,@{section=".text",section-sent="6144",section-size="6668", +++total-sent="6144",total-size="9880"@} ++++download,@{section=".text",section-sent="6656",section-size="6668", +++total-sent="6656",total-size="9880"@} ++++download,@{section=".init",section-size="28",total-size="9880"@} ++++download,@{section=".fini",section-size="28",total-size="9880"@} ++++download,@{section=".data",section-size="3156",total-size="9880"@} ++++download,@{section=".data",section-sent="512",section-size="3156", +++total-sent="7236",total-size="9880"@} ++++download,@{section=".data",section-sent="1024",section-size="3156", +++total-sent="7748",total-size="9880"@} ++++download,@{section=".data",section-sent="1536",section-size="3156", +++total-sent="8260",total-size="9880"@} ++++download,@{section=".data",section-sent="2048",section-size="3156", +++total-sent="8772",total-size="9880"@} ++++download,@{section=".data",section-sent="2560",section-size="3156", +++total-sent="9284",total-size="9880"@} ++++download,@{section=".data",section-sent="3072",section-size="3156", +++total-sent="9796",total-size="9880"@} +++^done,address="0x10004",load-size="9880",transfer-rate="6586", +++write-rate="429" +++(gdb) +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-target-exec-status} Command +++@findex -target-exec-status +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-exec-status +++@end smallexample +++ +++Provide information on the state of the target (whether it is running or +++not, for instance). +++ +++@subsubheading @value{GDBN} Command +++ +++There's no equivalent @value{GDBN} command. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-target-list-available-targets} Command +++@findex -target-list-available-targets +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-list-available-targets +++@end smallexample +++ +++List the possible targets to connect to. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{help target}. +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-target-list-current-targets} Command +++@findex -target-list-current-targets +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-list-current-targets +++@end smallexample +++ +++Describe the current target. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding information is printed by @samp{info file} (among +++other things). +++ +++@subsubheading Example +++N.A. +++ +++ +++@subheading The @code{-target-list-parameters} Command +++@findex -target-list-parameters +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-list-parameters +++@end smallexample +++ +++@c ???? +++@end ignore +++ +++@subsubheading @value{GDBN} Command +++ +++No equivalent. +++ +++@subsubheading Example +++N.A. +++ +++@subheading The @code{-target-flash-erase} Command +++@findex -target-flash-erase +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-flash-erase +++@end smallexample +++ +++Erases all known flash memory regions on the target. +++ +++The corresponding @value{GDBN} command is @samp{flash-erase}. +++ +++The output is a list of flash regions that have been erased, with starting +++addresses and memory region sizes. +++ +++@smallexample +++(gdb) +++-target-flash-erase +++^done,erased-regions=@{address="0x0",size="0x40000"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-target-select} Command +++@findex -target-select +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-select @var{type} @var{parameters @dots{}} +++@end smallexample +++ +++Connect @value{GDBN} to the remote target. This command takes two args: +++ +++@table @samp +++@item @var{type} +++The type of target, for instance @samp{remote}, etc. +++@item @var{parameters} +++Device names, host names and the like. @xref{Target Commands, , +++Commands for Managing Targets}, for more details. +++@end table +++ +++The output is a connection notification, followed by the address at +++which the target program is, in the following form: +++ +++@smallexample +++^connected,addr="@var{address}",func="@var{function name}", +++ args=[@var{arg list}] +++@end smallexample +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{target}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-select remote /dev/ttya +++^connected,addr="0xfe00a300",func="??",args=[] +++(gdb) +++@end smallexample +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI File Transfer Commands +++@section @sc{gdb/mi} File Transfer Commands +++ +++ +++@subheading The @code{-target-file-put} Command +++@findex -target-file-put +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-file-put @var{hostfile} @var{targetfile} +++@end smallexample +++ +++Copy file @var{hostfile} from the host system (the machine running +++@value{GDBN}) to @var{targetfile} on the target system. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{remote put}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-file-put localfile remotefile +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-target-file-get} Command +++@findex -target-file-get +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-file-get @var{targetfile} @var{hostfile} +++@end smallexample +++ +++Copy file @var{targetfile} from the target system to @var{hostfile} +++on the host system. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{remote get}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-file-get remotefile localfile +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-target-file-delete} Command +++@findex -target-file-delete +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -target-file-delete @var{targetfile} +++@end smallexample +++ +++Delete @var{targetfile} from the target system. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{remote delete}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-target-file-delete remotefile +++^done +++(gdb) +++@end smallexample +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Ada Exceptions Commands +++@section Ada Exceptions @sc{gdb/mi} Commands +++ +++@subheading The @code{-info-ada-exceptions} Command +++@findex -info-ada-exceptions +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -info-ada-exceptions [ @var{regexp}] +++@end smallexample +++ +++List all Ada exceptions defined within the program being debugged. +++With a regular expression @var{regexp}, only those exceptions whose +++names match @var{regexp} are listed. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info exceptions}. +++ +++@subsubheading Result +++ +++The result is a table of Ada exceptions. The following columns are +++defined for each exception: +++ +++@table @samp +++@item name +++The name of the exception. +++ +++@item address +++The address of the exception. +++ +++@end table +++ +++@subsubheading Example +++ +++@smallexample +++-info-ada-exceptions aint +++^done,ada-exceptions=@{nr_rows="2",nr_cols="2", +++hdr=[@{width="1",alignment="-1",col_name="name",colhdr="Name"@}, +++@{width="1",alignment="-1",col_name="address",colhdr="Address"@}], +++body=[@{name="constraint_error",address="0x0000000000613da0"@}, +++@{name="const.aint_global_e",address="0x0000000000613b00"@}]@} +++@end smallexample +++ +++@subheading Catching Ada Exceptions +++ +++The commands describing how to ask @value{GDBN} to stop when a program +++raises an exception are described at @ref{Ada Exception GDB/MI +++Catchpoint Commands}. +++ +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Support Commands +++@section @sc{gdb/mi} Support Commands +++ +++Since new commands and features get regularly added to @sc{gdb/mi}, +++some commands are available to help front-ends query the debugger +++about support for these capabilities. Similarly, it is also possible +++to query @value{GDBN} about target support of certain features. +++ +++@subheading The @code{-info-gdb-mi-command} Command +++@cindex @code{-info-gdb-mi-command} +++@findex -info-gdb-mi-command +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -info-gdb-mi-command @var{cmd_name} +++@end smallexample +++ +++Query support for the @sc{gdb/mi} command named @var{cmd_name}. +++ +++Note that the dash (@code{-}) starting all @sc{gdb/mi} commands +++is technically not part of the command name (@pxref{GDB/MI Input +++Syntax}), and thus should be omitted in @var{cmd_name}. However, +++for ease of use, this command also accepts the form with the leading +++dash. +++ +++@subsubheading @value{GDBN} Command +++ +++There is no corresponding @value{GDBN} command. +++ +++@subsubheading Result +++ +++The result is a tuple. There is currently only one field: +++ +++@table @samp +++@item exists +++This field is equal to @code{"true"} if the @sc{gdb/mi} command exists, +++@code{"false"} otherwise. +++ +++@end table +++ +++@subsubheading Example +++ +++Here is an example where the @sc{gdb/mi} command does not exist: +++ +++@smallexample +++-info-gdb-mi-command unsupported-command +++^done,command=@{exists="false"@} +++@end smallexample +++ +++@noindent +++And here is an example where the @sc{gdb/mi} command is known +++to the debugger: +++ +++@smallexample +++-info-gdb-mi-command symbol-list-lines +++^done,command=@{exists="true"@} +++@end smallexample +++ +++@subheading The @code{-list-features} Command +++@findex -list-features +++@cindex supported @sc{gdb/mi} features, list +++ +++Returns a list of particular features of the MI protocol that +++this version of gdb implements. A feature can be a command, +++or a new field in an output of some command, or even an +++important bugfix. While a frontend can sometimes detect presence +++of a feature at runtime, it is easier to perform detection at debugger +++startup. +++ +++The command returns a list of strings, with each string naming an +++available feature. Each returned string is just a name, it does not +++have any internal structure. The list of possible feature names +++is given below. +++ +++Example output: +++ +++@smallexample +++(gdb) -list-features +++^done,result=["feature1","feature2"] +++@end smallexample +++ +++The current list of features is: +++ +++@ftable @samp +++@item frozen-varobjs +++Indicates support for the @code{-var-set-frozen} command, as well +++as possible presence of the @code{frozen} field in the output +++of @code{-varobj-create}. +++@item pending-breakpoints +++Indicates support for the @option{-f} option to the @code{-break-insert} +++command. +++@item python +++Indicates Python scripting support, Python-based +++pretty-printing commands, and possible presence of the +++@samp{display_hint} field in the output of @code{-var-list-children} +++@item thread-info +++Indicates support for the @code{-thread-info} command. +++@item data-read-memory-bytes +++Indicates support for the @code{-data-read-memory-bytes} and the +++@code{-data-write-memory-bytes} commands. +++@item breakpoint-notifications +++Indicates that changes to breakpoints and breakpoints created via the +++CLI will be announced via async records. +++@item ada-task-info +++Indicates support for the @code{-ada-task-info} command. +++@item language-option +++Indicates that all @sc{gdb/mi} commands accept the @option{--language} +++option (@pxref{Context management}). +++@item info-gdb-mi-command +++Indicates support for the @code{-info-gdb-mi-command} command. +++@item undefined-command-error-code +++Indicates support for the "undefined-command" error code in error result +++records, produced when trying to execute an undefined @sc{gdb/mi} command +++(@pxref{GDB/MI Result Records}). +++@item exec-run-start-option +++Indicates that the @code{-exec-run} command supports the @option{--start} +++option (@pxref{GDB/MI Program Execution}). +++@item data-disassemble-a-option +++Indicates that the @code{-data-disassemble} command supports the @option{-a} +++option (@pxref{GDB/MI Data Manipulation}). +++@end ftable +++ +++@subheading The @code{-list-target-features} Command +++@findex -list-target-features +++ +++Returns a list of particular features that are supported by the +++target. Those features affect the permitted MI commands, but +++unlike the features reported by the @code{-list-features} command, the +++features depend on which target GDB is using at the moment. Whenever +++a target can change, due to commands such as @code{-target-select}, +++@code{-target-attach} or @code{-exec-run}, the list of target features +++may change, and the frontend should obtain it again. +++Example output: +++ +++@smallexample +++(gdb) -list-target-features +++^done,result=["async"] +++@end smallexample +++ +++The current list of features is: +++ +++@table @samp +++@item async +++Indicates that the target is capable of asynchronous command +++execution, which means that @value{GDBN} will accept further commands +++while the target is running. +++ +++@item reverse +++Indicates that the target is capable of reverse execution. +++@xref{Reverse Execution}, for more information. +++ +++@end table +++ +++@c %%%%%%%%%%%%%%%%%%%%%%%%%%%% SECTION %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +++@node GDB/MI Miscellaneous Commands +++@section Miscellaneous @sc{gdb/mi} Commands +++ +++@c @subheading -gdb-complete +++ +++@subheading The @code{-gdb-exit} Command +++@findex -gdb-exit +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -gdb-exit +++@end smallexample +++ +++Exit @value{GDBN} immediately. +++ +++@subsubheading @value{GDBN} Command +++ +++Approximately corresponds to @samp{quit}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-gdb-exit +++^exit +++@end smallexample +++ +++ +++@ignore +++@subheading The @code{-exec-abort} Command +++@findex -exec-abort +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -exec-abort +++@end smallexample +++ +++Kill the inferior running program. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{kill}. +++ +++@subsubheading Example +++N.A. +++@end ignore +++ +++ +++@subheading The @code{-gdb-set} Command +++@findex -gdb-set +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -gdb-set +++@end smallexample +++ +++Set an internal @value{GDBN} variable. +++@c IS THIS A DOLLAR VARIABLE? OR SOMETHING LIKE ANNOTATE ????? +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{set}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-gdb-set $foo=3 +++^done +++(gdb) +++@end smallexample +++ +++ +++@subheading The @code{-gdb-show} Command +++@findex -gdb-show +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -gdb-show +++@end smallexample +++ +++Show the current value of a @value{GDBN} variable. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{show}. +++ +++@subsubheading Example +++ +++@smallexample +++(gdb) +++-gdb-show annotate +++^done,value="0" +++(gdb) +++@end smallexample +++ +++@c @subheading -gdb-source +++ +++ +++@subheading The @code{-gdb-version} Command +++@findex -gdb-version +++ +++@subsubheading Synopsis +++ +++@smallexample +++ -gdb-version +++@end smallexample +++ +++Show version information for @value{GDBN}. Used mostly in testing. +++ +++@subsubheading @value{GDBN} Command +++ +++The @value{GDBN} equivalent is @samp{show version}. @value{GDBN} by +++default shows this information when you start an interactive session. +++ +++@subsubheading Example +++ +++@c This example modifies the actual output from GDB to avoid overfull +++@c box in TeX. +++@smallexample +++(gdb) +++-gdb-version +++~GNU gdb 5.2.1 +++~Copyright 2000 Free Software Foundation, Inc. +++~GDB is free software, covered by the GNU General Public License, and +++~you are welcome to change it and/or distribute copies of it under +++~ certain conditions. +++~Type "show copying" to see the conditions. +++~There is absolutely no warranty for GDB. Type "show warranty" for +++~ details. +++~This GDB was configured as +++ "--host=sparc-sun-solaris2.5.1 --target=ppc-eabi". +++^done +++(gdb) +++@end smallexample +++ +++@subheading The @code{-list-thread-groups} Command +++@findex -list-thread-groups +++ +++@subheading Synopsis +++ +++@smallexample +++-list-thread-groups [ --available ] [ --recurse 1 ] [ @var{group} ... ] +++@end smallexample +++ +++Lists thread groups (@pxref{Thread groups}). When a single thread +++group is passed as the argument, lists the children of that group. +++When several thread group are passed, lists information about those +++thread groups. Without any parameters, lists information about all +++top-level thread groups. +++ +++Normally, thread groups that are being debugged are reported. +++With the @samp{--available} option, @value{GDBN} reports thread groups +++available on the target. +++ +++The output of this command may have either a @samp{threads} result or +++a @samp{groups} result. The @samp{thread} result has a list of tuples +++as value, with each tuple describing a thread (@pxref{GDB/MI Thread +++Information}). The @samp{groups} result has a list of tuples as value, +++each tuple describing a thread group. If top-level groups are +++requested (that is, no parameter is passed), or when several groups +++are passed, the output always has a @samp{groups} result. The format +++of the @samp{group} result is described below. +++ +++To reduce the number of roundtrips it's possible to list thread groups +++together with their children, by passing the @samp{--recurse} option +++and the recursion depth. Presently, only recursion depth of 1 is +++permitted. If this option is present, then every reported thread group +++will also include its children, either as @samp{group} or +++@samp{threads} field. +++ +++In general, any combination of option and parameters is permitted, with +++the following caveats: +++ +++@itemize @bullet +++@item +++When a single thread group is passed, the output will typically +++be the @samp{threads} result. Because threads may not contain +++anything, the @samp{recurse} option will be ignored. +++ +++@item +++When the @samp{--available} option is passed, limited information may +++be available. In particular, the list of threads of a process might +++be inaccessible. Further, specifying specific thread groups might +++not give any performance advantage over listing all thread groups. +++The frontend should assume that @samp{-list-thread-groups --available} +++is always an expensive operation and cache the results. +++ +++@end itemize +++ +++The @samp{groups} result is a list of tuples, where each tuple may +++have the following fields: +++ +++@table @code +++@item id +++Identifier of the thread group. This field is always present. +++The identifier is an opaque string; frontends should not try to +++convert it to an integer, even though it might look like one. +++ +++@item type +++The type of the thread group. At present, only @samp{process} is a +++valid type. +++ +++@item pid +++The target-specific process identifier. This field is only present +++for thread groups of type @samp{process} and only if the process exists. +++ +++@item exit-code +++The exit code of this group's last exited thread, formatted in octal. +++This field is only present for thread groups of type @samp{process} and +++only if the process is not running. +++ +++@item num_children +++The number of children this thread group has. This field may be +++absent for an available thread group. +++ +++@item threads +++This field has a list of tuples as value, each tuple describing a +++thread. It may be present if the @samp{--recurse} option is +++specified, and it's actually possible to obtain the threads. +++ +++@item cores +++This field is a list of integers, each identifying a core that one +++thread of the group is running on. This field may be absent if +++such information is not available. +++ +++@item executable +++The name of the executable file that corresponds to this thread group. +++The field is only present for thread groups of type @samp{process}, +++and only if there is a corresponding executable file. +++ +++@end table +++ +++@subheading Example +++ +++@smallexample +++@value{GDBP} +++-list-thread-groups +++^done,groups=[@{id="17",type="process",pid="yyy",num_children="2"@}] +++-list-thread-groups 17 +++^done,threads=[@{id="2",target-id="Thread 0xb7e14b90 (LWP 21257)", +++ frame=@{level="0",addr="0xffffe410",func="__kernel_vsyscall",args=[]@},state="running"@}, +++@{id="1",target-id="Thread 0xb7e156b0 (LWP 21254)", +++ frame=@{level="0",addr="0x0804891f",func="foo",args=[@{name="i",value="10"@}], +++ file="/tmp/a.c",fullname="/tmp/a.c",line="158",arch="i386:x86_64"@},state="running"@}]] +++-list-thread-groups --available +++^done,groups=[@{id="17",type="process",pid="yyy",num_children="2",cores=[1,2]@}] +++-list-thread-groups --available --recurse 1 +++ ^done,groups=[@{id="17", types="process",pid="yyy",num_children="2",cores=[1,2], +++ threads=[@{id="1",target-id="Thread 0xb7e14b90",cores=[1]@}, +++ @{id="2",target-id="Thread 0xb7e14b90",cores=[2]@}]@},..] +++-list-thread-groups --available --recurse 1 17 18 +++^done,groups=[@{id="17", types="process",pid="yyy",num_children="2",cores=[1,2], +++ threads=[@{id="1",target-id="Thread 0xb7e14b90",cores=[1]@}, +++ @{id="2",target-id="Thread 0xb7e14b90",cores=[2]@}]@},...] +++@end smallexample +++ +++@subheading The @code{-info-os} Command +++@findex -info-os +++ +++@subsubheading Synopsis +++ +++@smallexample +++-info-os [ @var{type} ] +++@end smallexample +++ +++If no argument is supplied, the command returns a table of available +++operating-system-specific information types. If one of these types is +++supplied as an argument @var{type}, then the command returns a table +++of data of that type. +++ +++The types of information available depend on the target operating +++system. +++ +++@subsubheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{info os}. +++ +++@subsubheading Example +++ +++When run on a @sc{gnu}/Linux system, the output will look something +++like this: +++ +++@smallexample +++@value{GDBP} +++-info-os +++^done,OSDataTable=@{nr_rows="10",nr_cols="3", +++hdr=[@{width="10",alignment="-1",col_name="col0",colhdr="Type"@}, +++ @{width="10",alignment="-1",col_name="col1",colhdr="Description"@}, +++ @{width="10",alignment="-1",col_name="col2",colhdr="Title"@}], +++body=[item=@{col0="cpus",col1="Listing of all cpus/cores on the system", +++ col2="CPUs"@}, +++ item=@{col0="files",col1="Listing of all file descriptors", +++ col2="File descriptors"@}, +++ item=@{col0="modules",col1="Listing of all loaded kernel modules", +++ col2="Kernel modules"@}, +++ item=@{col0="msg",col1="Listing of all message queues", +++ col2="Message queues"@}, +++ item=@{col0="processes",col1="Listing of all processes", +++ col2="Processes"@}, +++ item=@{col0="procgroups",col1="Listing of all process groups", +++ col2="Process groups"@}, +++ item=@{col0="semaphores",col1="Listing of all semaphores", +++ col2="Semaphores"@}, +++ item=@{col0="shm",col1="Listing of all shared-memory regions", +++ col2="Shared-memory regions"@}, +++ item=@{col0="sockets",col1="Listing of all internet-domain sockets", +++ col2="Sockets"@}, +++ item=@{col0="threads",col1="Listing of all threads", +++ col2="Threads"@}] +++@value{GDBP} +++-info-os processes +++^done,OSDataTable=@{nr_rows="190",nr_cols="4", +++hdr=[@{width="10",alignment="-1",col_name="col0",colhdr="pid"@}, +++ @{width="10",alignment="-1",col_name="col1",colhdr="user"@}, +++ @{width="10",alignment="-1",col_name="col2",colhdr="command"@}, +++ @{width="10",alignment="-1",col_name="col3",colhdr="cores"@}], +++body=[item=@{col0="1",col1="root",col2="/sbin/init",col3="0"@}, +++ item=@{col0="2",col1="root",col2="[kthreadd]",col3="1"@}, +++ item=@{col0="3",col1="root",col2="[ksoftirqd/0]",col3="0"@}, +++ ... +++ item=@{col0="26446",col1="stan",col2="bash",col3="0"@}, +++ item=@{col0="28152",col1="stan",col2="bash",col3="1"@}]@} +++(gdb) +++@end smallexample +++ +++(Note that the MI output here includes a @code{"Title"} column that +++does not appear in command-line @code{info os}; this column is useful +++for MI clients that want to enumerate the types of data, such as in a +++popup menu, but is needless clutter on the command line, and +++@code{info os} omits it.) +++ +++@subheading The @code{-add-inferior} Command +++@findex -add-inferior +++ +++@subheading Synopsis +++ +++@smallexample +++-add-inferior +++@end smallexample +++ +++Creates a new inferior (@pxref{Inferiors Connections and Programs}). The created +++inferior is not associated with any executable. Such association may +++be established with the @samp{-file-exec-and-symbols} command +++(@pxref{GDB/MI File Commands}). The command response has a single +++field, @samp{inferior}, whose value is the identifier of the +++thread group corresponding to the new inferior. +++ +++@subheading Example +++ +++@smallexample +++@value{GDBP} +++-add-inferior +++^done,inferior="i3" +++@end smallexample +++ +++@subheading The @code{-interpreter-exec} Command +++@findex -interpreter-exec +++ +++@subheading Synopsis +++ +++@smallexample +++-interpreter-exec @var{interpreter} @var{command} +++@end smallexample +++@anchor{-interpreter-exec} +++ +++Execute the specified @var{command} in the given @var{interpreter}. +++ +++@subheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{interpreter-exec}. +++ +++@subheading Example +++ +++@smallexample +++(gdb) +++-interpreter-exec console "break main" +++&"During symbol reading, couldn't parse type; debugger out of date?.\n" +++&"During symbol reading, bad structure-type format.\n" +++~"Breakpoint 1 at 0x8074fc6: file ../../src/gdb/main.c, line 743.\n" +++^done +++(gdb) +++@end smallexample +++ +++@subheading The @code{-inferior-tty-set} Command +++@findex -inferior-tty-set +++ +++@subheading Synopsis +++ +++@smallexample +++-inferior-tty-set /dev/pts/1 +++@end smallexample +++ +++Set terminal for future runs of the program being debugged. +++ +++@subheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{set inferior-tty} /dev/pts/1. +++ +++@subheading Example +++ +++@smallexample +++(gdb) +++-inferior-tty-set /dev/pts/1 +++^done +++(gdb) +++@end smallexample +++ +++@subheading The @code{-inferior-tty-show} Command +++@findex -inferior-tty-show +++ +++@subheading Synopsis +++ +++@smallexample +++-inferior-tty-show +++@end smallexample +++ +++Show terminal for future runs of program being debugged. +++ +++@subheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{show inferior-tty}. +++ +++@subheading Example +++ +++@smallexample +++(gdb) +++-inferior-tty-set /dev/pts/1 +++^done +++(gdb) +++-inferior-tty-show +++^done,inferior_tty_terminal="/dev/pts/1" +++(gdb) +++@end smallexample +++ +++@subheading The @code{-enable-timings} Command +++@findex -enable-timings +++ +++@subheading Synopsis +++ +++@smallexample +++-enable-timings [yes | no] +++@end smallexample +++ +++Toggle the printing of the wallclock, user and system times for an MI +++command as a field in its output. This command is to help frontend +++developers optimize the performance of their code. No argument is +++equivalent to @samp{yes}. +++ +++@subheading @value{GDBN} Command +++ +++No equivalent. +++ +++@subheading Example +++ +++@smallexample +++(gdb) +++-enable-timings +++^done +++(gdb) +++-break-insert main +++^done,bkpt=@{number="1",type="breakpoint",disp="keep",enabled="y", +++addr="0x080484ed",func="main",file="myprog.c", +++fullname="/home/nickrob/myprog.c",line="73",thread-groups=["i1"], +++times="0"@}, +++time=@{wallclock="0.05185",user="0.00800",system="0.00000"@} +++(gdb) +++-enable-timings no +++^done +++(gdb) +++-exec-run +++^running +++(gdb) +++*stopped,reason="breakpoint-hit",disp="keep",bkptno="1",thread-id="0", +++frame=@{addr="0x080484ed",func="main",args=[@{name="argc",value="1"@}, +++@{name="argv",value="0xbfb60364"@}],file="myprog.c", +++fullname="/home/nickrob/myprog.c",line="73",arch="i386:x86_64"@} +++(gdb) +++@end smallexample +++ +++@subheading The @code{-complete} Command +++@findex -complete +++ +++@subheading Synopsis +++ +++@smallexample +++-complete @var{command} +++@end smallexample +++ +++Show a list of completions for partially typed CLI @var{command}. +++ +++This command is intended for @sc{gdb/mi} frontends that cannot use two separate +++CLI and MI channels --- for example: because of lack of PTYs like on Windows or +++because @value{GDBN} is used remotely via a SSH connection. +++ +++@subheading Result +++ +++The result consists of two or three fields: +++ +++@table @samp +++@item completion +++This field contains the completed @var{command}. If @var{command} +++has no known completions, this field is omitted. +++ +++@item matches +++This field contains a (possibly empty) array of matches. It is always present. +++ +++@item max_completions_reached +++This field contains @code{1} if number of known completions is above +++@code{max-completions} limit (@pxref{Completion}), otherwise it contains +++@code{0}. It is always present. +++ +++@end table +++ +++@subheading @value{GDBN} Command +++ +++The corresponding @value{GDBN} command is @samp{complete}. +++ +++@subheading Example +++ +++@smallexample +++(gdb) +++-complete br +++^done,completion="break", +++ matches=["break","break-range"], +++ max_completions_reached="0" +++(gdb) +++-complete "b ma" +++^done,completion="b ma", +++ matches=["b madvise","b main"],max_completions_reached="0" +++(gdb) +++-complete "b push_b" +++^done,completion="b push_back(", +++ matches=[ +++ "b A::push_back(void*)", +++ "b std::string::push_back(char)", +++ "b std::vector >::push_back(int&&)"], +++ max_completions_reached="0" +++(gdb) +++-complete "nonexist" +++^done,matches=[],max_completions_reached="0" +++(gdb) +++ +++@end smallexample +++ +++@node Annotations +++@chapter @value{GDBN} Annotations +++ +++This chapter describes annotations in @value{GDBN}. Annotations were +++designed to interface @value{GDBN} to graphical user interfaces or other +++similar programs which want to interact with @value{GDBN} at a +++relatively high level. +++ +++The annotation mechanism has largely been superseded by @sc{gdb/mi} +++(@pxref{GDB/MI}). +++ +++@ignore +++This is Edition @value{EDITION}, @value{DATE}. +++@end ignore +++ +++@menu +++* Annotations Overview:: What annotations are; the general syntax. +++* Server Prefix:: Issuing a command without affecting user state. +++* Prompting:: Annotations marking @value{GDBN}'s need for input. +++* Errors:: Annotations for error messages. +++* Invalidation:: Some annotations describe things now invalid. +++* Annotations for Running:: +++ Whether the program is running, how it stopped, etc. +++* Source Annotations:: Annotations describing source code. +++@end menu +++ +++@node Annotations Overview +++@section What is an Annotation? +++@cindex annotations +++ +++Annotations start with a newline character, two @samp{control-z} +++characters, and the name of the annotation. If there is no additional +++information associated with this annotation, the name of the annotation +++is followed immediately by a newline. If there is additional +++information, the name of the annotation is followed by a space, the +++additional information, and a newline. The additional information +++cannot contain newline characters. +++ +++Any output not beginning with a newline and two @samp{control-z} +++characters denotes literal output from @value{GDBN}. Currently there is +++no need for @value{GDBN} to output a newline followed by two +++@samp{control-z} characters, but if there was such a need, the +++annotations could be extended with an @samp{escape} annotation which +++means those three characters as output. +++ +++The annotation @var{level}, which is specified using the +++@option{--annotate} command line option (@pxref{Mode Options}), controls +++how much information @value{GDBN} prints together with its prompt, +++values of expressions, source lines, and other types of output. Level 0 +++is for no annotations, level 1 is for use when @value{GDBN} is run as a +++subprocess of @sc{gnu} Emacs, level 3 is the maximum annotation suitable +++for programs that control @value{GDBN}, and level 2 annotations have +++been made obsolete (@pxref{Limitations, , Limitations of the Annotation +++Interface, annotate, GDB's Obsolete Annotations}). +++ +++@table @code +++@kindex set annotate +++@item set annotate @var{level} +++The @value{GDBN} command @code{set annotate} sets the level of +++annotations to the specified @var{level}. +++ +++@item show annotate +++@kindex show annotate +++Show the current annotation level. +++@end table +++ +++This chapter describes level 3 annotations. +++ +++A simple example of starting up @value{GDBN} with annotations is: +++ +++@smallexample +++$ @kbd{gdb --annotate=3} +++GNU gdb 6.0 +++Copyright 2003 Free Software Foundation, Inc. +++GDB is free software, covered by the GNU General Public License, +++and you are welcome to change it and/or distribute copies of it +++under certain conditions. +++Type "show copying" to see the conditions. +++There is absolutely no warranty for GDB. Type "show warranty" +++for details. +++This GDB was configured as "i386-pc-linux-gnu" +++ +++^Z^Zpre-prompt +++(@value{GDBP}) +++^Z^Zprompt +++@kbd{quit} +++ +++^Z^Zpost-prompt +++$ +++@end smallexample +++ +++Here @samp{quit} is input to @value{GDBN}; the rest is output from +++@value{GDBN}. The three lines beginning @samp{^Z^Z} (where @samp{^Z} +++denotes a @samp{control-z} character) are annotations; the rest is +++output from @value{GDBN}. +++ +++@node Server Prefix +++@section The Server Prefix +++@cindex server prefix +++ +++If you prefix a command with @samp{server } then it will not affect +++the command history, nor will it affect @value{GDBN}'s notion of which +++command to repeat if @key{RET} is pressed on a line by itself. This +++means that commands can be run behind a user's back by a front-end in +++a transparent manner. +++ +++The @code{server } prefix does not affect the recording of values into +++the value history; to print a value without recording it into the +++value history, use the @code{output} command instead of the +++@code{print} command. +++ +++Using this prefix also disables confirmation requests +++(@pxref{confirmation requests}). +++ +++@node Prompting +++@section Annotation for @value{GDBN} Input +++ +++@cindex annotations for prompts +++When @value{GDBN} prompts for input, it annotates this fact so it is possible +++to know when to send output, when the output from a given command is +++over, etc. +++ +++Different kinds of input each have a different @dfn{input type}. Each +++input type has three annotations: a @code{pre-} annotation, which +++denotes the beginning of any prompt which is being output, a plain +++annotation, which denotes the end of the prompt, and then a @code{post-} +++annotation which denotes the end of any echo which may (or may not) be +++associated with the input. For example, the @code{prompt} input type +++features the following annotations: +++ +++@smallexample +++^Z^Zpre-prompt +++^Z^Zprompt +++^Z^Zpost-prompt +++@end smallexample +++ +++The input types are +++ +++@table @code +++@findex pre-prompt annotation +++@findex prompt annotation +++@findex post-prompt annotation +++@item prompt +++When @value{GDBN} is prompting for a command (the main @value{GDBN} prompt). +++ +++@findex pre-commands annotation +++@findex commands annotation +++@findex post-commands annotation +++@item commands +++When @value{GDBN} prompts for a set of commands, like in the @code{commands} +++command. The annotations are repeated for each command which is input. +++ +++@findex pre-overload-choice annotation +++@findex overload-choice annotation +++@findex post-overload-choice annotation +++@item overload-choice +++When @value{GDBN} wants the user to select between various overloaded functions. +++ +++@findex pre-query annotation +++@findex query annotation +++@findex post-query annotation +++@item query +++When @value{GDBN} wants the user to confirm a potentially dangerous operation. +++ +++@findex pre-prompt-for-continue annotation +++@findex prompt-for-continue annotation +++@findex post-prompt-for-continue annotation +++@item prompt-for-continue +++When @value{GDBN} is asking the user to press return to continue. Note: Don't +++expect this to work well; instead use @code{set height 0} to disable +++prompting. This is because the counting of lines is buggy in the +++presence of annotations. +++@end table +++ +++@node Errors +++@section Errors +++@cindex annotations for errors, warnings and interrupts +++ +++@findex quit annotation +++@smallexample +++^Z^Zquit +++@end smallexample +++ +++This annotation occurs right before @value{GDBN} responds to an interrupt. +++ +++@findex error annotation +++@smallexample +++^Z^Zerror +++@end smallexample +++ +++This annotation occurs right before @value{GDBN} responds to an error. +++ +++Quit and error annotations indicate that any annotations which @value{GDBN} was +++in the middle of may end abruptly. For example, if a +++@code{value-history-begin} annotation is followed by a @code{error}, one +++cannot expect to receive the matching @code{value-history-end}. One +++cannot expect not to receive it either, however; an error annotation +++does not necessarily mean that @value{GDBN} is immediately returning all the way +++to the top level. +++ +++@findex error-begin annotation +++A quit or error annotation may be preceded by +++ +++@smallexample +++^Z^Zerror-begin +++@end smallexample +++ +++Any output between that and the quit or error annotation is the error +++message. +++ +++Warning messages are not yet annotated. +++@c If we want to change that, need to fix warning(), type_error(), +++@c range_error(), and possibly other places. +++ +++@node Invalidation +++@section Invalidation Notices +++ +++@cindex annotations for invalidation messages +++The following annotations say that certain pieces of state may have +++changed. +++ +++@table @code +++@findex frames-invalid annotation +++@item ^Z^Zframes-invalid +++ +++The frames (for example, output from the @code{backtrace} command) may +++have changed. +++ +++@findex breakpoints-invalid annotation +++@item ^Z^Zbreakpoints-invalid +++ +++The breakpoints may have changed. For example, the user just added or +++deleted a breakpoint. +++@end table +++ +++@node Annotations for Running +++@section Running the Program +++@cindex annotations for running programs +++ +++@findex starting annotation +++@findex stopping annotation +++When the program starts executing due to a @value{GDBN} command such as +++@code{step} or @code{continue}, +++ +++@smallexample +++^Z^Zstarting +++@end smallexample +++ +++is output. When the program stops, +++ +++@smallexample +++^Z^Zstopped +++@end smallexample +++ +++is output. Before the @code{stopped} annotation, a variety of +++annotations describe how the program stopped. +++ +++@table @code +++@findex exited annotation +++@item ^Z^Zexited @var{exit-status} +++The program exited, and @var{exit-status} is the exit status (zero for +++successful exit, otherwise nonzero). +++ +++@findex signalled annotation +++@findex signal-name annotation +++@findex signal-name-end annotation +++@findex signal-string annotation +++@findex signal-string-end annotation +++@item ^Z^Zsignalled +++The program exited with a signal. After the @code{^Z^Zsignalled}, the +++annotation continues: +++ +++@smallexample +++@var{intro-text} +++^Z^Zsignal-name +++@var{name} +++^Z^Zsignal-name-end +++@var{middle-text} +++^Z^Zsignal-string +++@var{string} +++^Z^Zsignal-string-end +++@var{end-text} +++@end smallexample +++ +++@noindent +++where @var{name} is the name of the signal, such as @code{SIGILL} or +++@code{SIGSEGV}, and @var{string} is the explanation of the signal, such +++as @code{Illegal Instruction} or @code{Segmentation fault}. The arguments +++@var{intro-text}, @var{middle-text}, and @var{end-text} are for the +++user's benefit and have no particular format. +++ +++@findex signal annotation +++@item ^Z^Zsignal +++The syntax of this annotation is just like @code{signalled}, but @value{GDBN} is +++just saying that the program received the signal, not that it was +++terminated with it. +++ +++@findex breakpoint annotation +++@item ^Z^Zbreakpoint @var{number} +++The program hit breakpoint number @var{number}. +++ +++@findex watchpoint annotation +++@item ^Z^Zwatchpoint @var{number} +++The program hit watchpoint number @var{number}. +++@end table +++ +++@node Source Annotations +++@section Displaying Source +++@cindex annotations for source display +++ +++@findex source annotation +++The following annotation is used instead of displaying source code: +++ +++@smallexample +++^Z^Zsource @var{filename}:@var{line}:@var{character}:@var{middle}:@var{addr} +++@end smallexample +++ +++where @var{filename} is an absolute file name indicating which source +++file, @var{line} is the line number within that file (where 1 is the +++first line in the file), @var{character} is the character position +++within the file (where 0 is the first character in the file) (for most +++debug formats this will necessarily point to the beginning of a line), +++@var{middle} is @samp{middle} if @var{addr} is in the middle of the +++line, or @samp{beg} if @var{addr} is at the beginning of the line, and +++@var{addr} is the address in the target program associated with the +++source which is being displayed. The @var{addr} is in the form @samp{0x} +++followed by one or more lowercase hex digits (note that this does not +++depend on the language). +++ +++@node JIT Interface +++@chapter JIT Compilation Interface +++@cindex just-in-time compilation +++@cindex JIT compilation interface +++ +++This chapter documents @value{GDBN}'s @dfn{just-in-time} (JIT) compilation +++interface. A JIT compiler is a program or library that generates native +++executable code at runtime and executes it, usually in order to achieve good +++performance while maintaining platform independence. +++ +++Programs that use JIT compilation are normally difficult to debug because +++portions of their code are generated at runtime, instead of being loaded from +++object files, which is where @value{GDBN} normally finds the program's symbols +++and debug information. In order to debug programs that use JIT compilation, +++@value{GDBN} has an interface that allows the program to register in-memory +++symbol files with @value{GDBN} at runtime. +++ +++If you are using @value{GDBN} to debug a program that uses this interface, then +++it should work transparently so long as you have not stripped the binary. If +++you are developing a JIT compiler, then the interface is documented in the rest +++of this chapter. At this time, the only known client of this interface is the +++LLVM JIT. +++ +++Broadly speaking, the JIT interface mirrors the dynamic loader interface. The +++JIT compiler communicates with @value{GDBN} by writing data into a global +++variable and calling a function at a well-known symbol. When @value{GDBN} +++attaches, it reads a linked list of symbol files from the global variable to +++find existing code, and puts a breakpoint in the function so that it can find +++out about additional code. +++ +++@menu +++* Declarations:: Relevant C struct declarations +++* Registering Code:: Steps to register code +++* Unregistering Code:: Steps to unregister code +++* Custom Debug Info:: Emit debug information in a custom format +++@end menu +++ +++@node Declarations +++@section JIT Declarations +++ +++These are the relevant struct declarations that a C program should include to +++implement the interface: +++ +++@smallexample +++typedef enum +++@{ +++ JIT_NOACTION = 0, +++ JIT_REGISTER_FN, +++ JIT_UNREGISTER_FN +++@} jit_actions_t; +++ +++struct jit_code_entry +++@{ +++ struct jit_code_entry *next_entry; +++ struct jit_code_entry *prev_entry; +++ const char *symfile_addr; +++ uint64_t symfile_size; +++@}; +++ +++struct jit_descriptor +++@{ +++ uint32_t version; +++ /* This type should be jit_actions_t, but we use uint32_t +++ to be explicit about the bitwidth. */ +++ uint32_t action_flag; +++ struct jit_code_entry *relevant_entry; +++ struct jit_code_entry *first_entry; +++@}; +++ +++/* GDB puts a breakpoint in this function. */ +++void __attribute__((noinline)) __jit_debug_register_code() @{ @}; +++ +++/* Make sure to specify the version statically, because the +++ debugger may check the version before we can set it. */ +++struct jit_descriptor __jit_debug_descriptor = @{ 1, 0, 0, 0 @}; +++@end smallexample +++ +++If the JIT is multi-threaded, then it is important that the JIT synchronize any +++modifications to this global data properly, which can easily be done by putting +++a global mutex around modifications to these structures. +++ +++@node Registering Code +++@section Registering Code +++ +++To register code with @value{GDBN}, the JIT should follow this protocol: +++ +++@itemize @bullet +++@item +++Generate an object file in memory with symbols and other desired debug +++information. The file must include the virtual addresses of the sections. +++ +++@item +++Create a code entry for the file, which gives the start and size of the symbol +++file. +++ +++@item +++Add it to the linked list in the JIT descriptor. +++ +++@item +++Point the relevant_entry field of the descriptor at the entry. +++ +++@item +++Set @code{action_flag} to @code{JIT_REGISTER} and call +++@code{__jit_debug_register_code}. +++@end itemize +++ +++When @value{GDBN} is attached and the breakpoint fires, @value{GDBN} uses the +++@code{relevant_entry} pointer so it doesn't have to walk the list looking for +++new code. However, the linked list must still be maintained in order to allow +++@value{GDBN} to attach to a running process and still find the symbol files. +++ +++@node Unregistering Code +++@section Unregistering Code +++ +++If code is freed, then the JIT should use the following protocol: +++ +++@itemize @bullet +++@item +++Remove the code entry corresponding to the code from the linked list. +++ +++@item +++Point the @code{relevant_entry} field of the descriptor at the code entry. +++ +++@item +++Set @code{action_flag} to @code{JIT_UNREGISTER} and call +++@code{__jit_debug_register_code}. +++@end itemize +++ +++If the JIT frees or recompiles code without unregistering it, then @value{GDBN} +++and the JIT will leak the memory used for the associated symbol files. +++ +++@node Custom Debug Info +++@section Custom Debug Info +++@cindex custom JIT debug info +++@cindex JIT debug info reader +++ +++Generating debug information in platform-native file formats (like ELF +++or COFF) may be an overkill for JIT compilers; especially if all the +++debug info is used for is displaying a meaningful backtrace. The +++issue can be resolved by having the JIT writers decide on a debug info +++format and also provide a reader that parses the debug info generated +++by the JIT compiler. This section gives a brief overview on writing +++such a parser. More specific details can be found in the source file +++@file{gdb/jit-reader.in}, which is also installed as a header at +++@file{@var{includedir}/gdb/jit-reader.h} for easy inclusion. +++ +++The reader is implemented as a shared object (so this functionality is +++not available on platforms which don't allow loading shared objects at +++runtime). Two @value{GDBN} commands, @code{jit-reader-load} and +++@code{jit-reader-unload} are provided, to be used to load and unload +++the readers from a preconfigured directory. Once loaded, the shared +++object is used the parse the debug information emitted by the JIT +++compiler. +++ +++@menu +++* Using JIT Debug Info Readers:: How to use supplied readers correctly +++* Writing JIT Debug Info Readers:: Creating a debug-info reader +++@end menu +++ +++@node Using JIT Debug Info Readers +++@subsection Using JIT Debug Info Readers +++@kindex jit-reader-load +++@kindex jit-reader-unload +++ +++Readers can be loaded and unloaded using the @code{jit-reader-load} +++and @code{jit-reader-unload} commands. +++ +++@table @code +++@item jit-reader-load @var{reader} +++Load the JIT reader named @var{reader}, which is a shared +++object specified as either an absolute or a relative file name. In +++the latter case, @value{GDBN} will try to load the reader from a +++pre-configured directory, usually @file{@var{libdir}/gdb/} on a UNIX +++system (here @var{libdir} is the system library directory, often +++@file{/usr/local/lib}). +++ +++Only one reader can be active at a time; trying to load a second +++reader when one is already loaded will result in @value{GDBN} +++reporting an error. A new JIT reader can be loaded by first unloading +++the current one using @code{jit-reader-unload} and then invoking +++@code{jit-reader-load}. +++ +++@item jit-reader-unload +++Unload the currently loaded JIT reader. +++ +++@end table +++ +++@node Writing JIT Debug Info Readers +++@subsection Writing JIT Debug Info Readers +++@cindex writing JIT debug info readers +++ +++As mentioned, a reader is essentially a shared object conforming to a +++certain ABI. This ABI is described in @file{jit-reader.h}. +++ +++@file{jit-reader.h} defines the structures, macros and functions +++required to write a reader. It is installed (along with +++@value{GDBN}), in @file{@var{includedir}/gdb} where @var{includedir} is +++the system include directory. +++ +++Readers need to be released under a GPL compatible license. A reader +++can be declared as released under such a license by placing the macro +++@code{GDB_DECLARE_GPL_COMPATIBLE_READER} in a source file. +++ +++The entry point for readers is the symbol @code{gdb_init_reader}, +++which is expected to be a function with the prototype +++ +++@findex gdb_init_reader +++@smallexample +++extern struct gdb_reader_funcs *gdb_init_reader (void); +++@end smallexample +++ +++@cindex @code{struct gdb_reader_funcs} +++ +++@code{struct gdb_reader_funcs} contains a set of pointers to callback +++functions. These functions are executed to read the debug info +++generated by the JIT compiler (@code{read}), to unwind stack frames +++(@code{unwind}) and to create canonical frame IDs +++(@code{get_frame_id}). It also has a callback that is called when the +++reader is being unloaded (@code{destroy}). The struct looks like this +++ +++@smallexample +++struct gdb_reader_funcs +++@{ +++ /* Must be set to GDB_READER_INTERFACE_VERSION. */ +++ int reader_version; +++ +++ /* For use by the reader. */ +++ void *priv_data; +++ +++ gdb_read_debug_info *read; +++ gdb_unwind_frame *unwind; +++ gdb_get_frame_id *get_frame_id; +++ gdb_destroy_reader *destroy; +++@}; +++@end smallexample +++ +++@cindex @code{struct gdb_symbol_callbacks} +++@cindex @code{struct gdb_unwind_callbacks} +++ +++The callbacks are provided with another set of callbacks by +++@value{GDBN} to do their job. For @code{read}, these callbacks are +++passed in a @code{struct gdb_symbol_callbacks} and for @code{unwind} +++and @code{get_frame_id}, in a @code{struct gdb_unwind_callbacks}. +++@code{struct gdb_symbol_callbacks} has callbacks to create new object +++files and new symbol tables inside those object files. @code{struct +++gdb_unwind_callbacks} has callbacks to read registers off the current +++frame and to write out the values of the registers in the previous +++frame. Both have a callback (@code{target_read}) to read bytes off the +++target's address space. +++ +++@node In-Process Agent +++@chapter In-Process Agent +++@cindex debugging agent +++The traditional debugging model is conceptually low-speed, but works fine, +++because most bugs can be reproduced in debugging-mode execution. However, +++as multi-core or many-core processors are becoming mainstream, and +++multi-threaded programs become more and more popular, there should be more +++and more bugs that only manifest themselves at normal-mode execution, for +++example, thread races, because debugger's interference with the program's +++timing may conceal the bugs. On the other hand, in some applications, +++it is not feasible for the debugger to interrupt the program's execution +++long enough for the developer to learn anything helpful about its behavior. +++If the program's correctness depends on its real-time behavior, delays +++introduced by a debugger might cause the program to fail, even when the +++code itself is correct. It is useful to be able to observe the program's +++behavior without interrupting it. +++ +++Therefore, traditional debugging model is too intrusive to reproduce +++some bugs. In order to reduce the interference with the program, we can +++reduce the number of operations performed by debugger. The +++@dfn{In-Process Agent}, a shared library, is running within the same +++process with inferior, and is able to perform some debugging operations +++itself. As a result, debugger is only involved when necessary, and +++performance of debugging can be improved accordingly. Note that +++interference with program can be reduced but can't be removed completely, +++because the in-process agent will still stop or slow down the program. +++ +++The in-process agent can interpret and execute Agent Expressions +++(@pxref{Agent Expressions}) during performing debugging operations. The +++agent expressions can be used for different purposes, such as collecting +++data in tracepoints, and condition evaluation in breakpoints. +++ +++@anchor{Control Agent} +++You can control whether the in-process agent is used as an aid for +++debugging with the following commands: +++ +++@table @code +++@kindex set agent on +++@item set agent on +++Causes the in-process agent to perform some operations on behalf of the +++debugger. Just which operations requested by the user will be done +++by the in-process agent depends on the its capabilities. For example, +++if you request to evaluate breakpoint conditions in the in-process agent, +++and the in-process agent has such capability as well, then breakpoint +++conditions will be evaluated in the in-process agent. +++ +++@kindex set agent off +++@item set agent off +++Disables execution of debugging operations by the in-process agent. All +++of the operations will be performed by @value{GDBN}. +++ +++@kindex show agent +++@item show agent +++Display the current setting of execution of debugging operations by +++the in-process agent. +++@end table +++ +++@menu +++* In-Process Agent Protocol:: +++@end menu +++ +++@node In-Process Agent Protocol +++@section In-Process Agent Protocol +++@cindex in-process agent protocol +++ +++The in-process agent is able to communicate with both @value{GDBN} and +++GDBserver (@pxref{In-Process Agent}). This section documents the protocol +++used for communications between @value{GDBN} or GDBserver and the IPA. +++In general, @value{GDBN} or GDBserver sends commands +++(@pxref{IPA Protocol Commands}) and data to in-process agent, and then +++in-process agent replies back with the return result of the command, or +++some other information. The data sent to in-process agent is composed +++of primitive data types, such as 4-byte or 8-byte type, and composite +++types, which are called objects (@pxref{IPA Protocol Objects}). +++ +++@menu +++* IPA Protocol Objects:: +++* IPA Protocol Commands:: +++@end menu +++ +++@node IPA Protocol Objects +++@subsection IPA Protocol Objects +++@cindex ipa protocol objects +++ +++The commands sent to and results received from agent may contain some +++complex data types called @dfn{objects}. +++ +++The in-process agent is running on the same machine with @value{GDBN} +++or GDBserver, so it doesn't have to handle as much differences between +++two ends as remote protocol (@pxref{Remote Protocol}) tries to handle. +++However, there are still some differences of two ends in two processes: +++ +++@enumerate +++@item +++word size. On some 64-bit machines, @value{GDBN} or GDBserver can be +++compiled as a 64-bit executable, while in-process agent is a 32-bit one. +++@item +++ABI. Some machines may have multiple types of ABI, @value{GDBN} or +++GDBserver is compiled with one, and in-process agent is compiled with +++the other one. +++@end enumerate +++ +++Here are the IPA Protocol Objects: +++ +++@enumerate +++@item +++agent expression object. It represents an agent expression +++(@pxref{Agent Expressions}). +++@anchor{agent expression object} +++@item +++tracepoint action object. It represents a tracepoint action +++(@pxref{Tracepoint Actions,,Tracepoint Action Lists}) to collect registers, +++memory, static trace data and to evaluate expression. +++@anchor{tracepoint action object} +++@item +++tracepoint object. It represents a tracepoint (@pxref{Tracepoints}). +++@anchor{tracepoint object} +++ +++@end enumerate +++ +++The following table describes important attributes of each IPA protocol +++object: +++ +++@multitable @columnfractions .30 .20 .50 +++@headitem Name @tab Size @tab Description +++@item @emph{agent expression object} @tab @tab +++@item length @tab 4 @tab length of bytes code +++@item byte code @tab @var{length} @tab contents of byte code +++@item @emph{tracepoint action for collecting memory} @tab @tab +++@item 'M' @tab 1 @tab type of tracepoint action +++@item addr @tab 8 @tab if @var{basereg} is @samp{-1}, @var{addr} is the +++address of the lowest byte to collect, otherwise @var{addr} is the offset +++of @var{basereg} for memory collecting. +++@item len @tab 8 @tab length of memory for collecting +++@item basereg @tab 4 @tab the register number containing the starting +++memory address for collecting. +++@item @emph{tracepoint action for collecting registers} @tab @tab +++@item 'R' @tab 1 @tab type of tracepoint action +++@item @emph{tracepoint action for collecting static trace data} @tab @tab +++@item 'L' @tab 1 @tab type of tracepoint action +++@item @emph{tracepoint action for expression evaluation} @tab @tab +++@item 'X' @tab 1 @tab type of tracepoint action +++@item agent expression @tab length of @tab @ref{agent expression object} +++@item @emph{tracepoint object} @tab @tab +++@item number @tab 4 @tab number of tracepoint +++@item address @tab 8 @tab address of tracepoint inserted on +++@item type @tab 4 @tab type of tracepoint +++@item enabled @tab 1 @tab enable or disable of tracepoint +++@item step_count @tab 8 @tab step +++@item pass_count @tab 8 @tab pass +++@item numactions @tab 4 @tab number of tracepoint actions +++@item hit count @tab 8 @tab hit count +++@item trace frame usage @tab 8 @tab trace frame usage +++@item compiled_cond @tab 8 @tab compiled condition +++@item orig_size @tab 8 @tab orig size +++@item condition @tab 4 if condition is NULL otherwise length of +++@ref{agent expression object} +++@tab zero if condition is NULL, otherwise is +++@ref{agent expression object} +++@item actions @tab variable +++@tab numactions number of @ref{tracepoint action object} +++@end multitable +++ +++@node IPA Protocol Commands +++@subsection IPA Protocol Commands +++@cindex ipa protocol commands +++ +++The spaces in each command are delimiters to ease reading this commands +++specification. They don't exist in real commands. +++ +++@table @samp +++ +++@item FastTrace:@var{tracepoint_object} @var{gdb_jump_pad_head} +++Installs a new fast tracepoint described by @var{tracepoint_object} +++(@pxref{tracepoint object}). The @var{gdb_jump_pad_head}, 8-byte long, is the +++head of @dfn{jumppad}, which is used to jump to data collection routine +++in IPA finally. +++ +++Replies: +++@table @samp +++@item OK @var{target_address} @var{gdb_jump_pad_head} @var{fjump_size} @var{fjump} +++@var{target_address} is address of tracepoint in the inferior. +++The @var{gdb_jump_pad_head} is updated head of jumppad. Both of +++@var{target_address} and @var{gdb_jump_pad_head} are 8-byte long. +++The @var{fjump} contains a sequence of instructions jump to jumppad entry. +++The @var{fjump_size}, 4-byte long, is the size of @var{fjump}. +++@item E @var{NN} +++for an error +++ +++@end table +++ +++@item close +++Closes the in-process agent. This command is sent when @value{GDBN} or GDBserver +++is about to kill inferiors. +++ +++@item qTfSTM +++@xref{qTfSTM}. +++@item qTsSTM +++@xref{qTsSTM}. +++@item qTSTMat +++@xref{qTSTMat}. +++@item probe_marker_at:@var{address} +++Asks in-process agent to probe the marker at @var{address}. +++ +++Replies: +++@table @samp +++@item E @var{NN} +++for an error +++@end table +++@item unprobe_marker_at:@var{address} +++Asks in-process agent to unprobe the marker at @var{address}. +++@end table +++ +++@node GDB Bugs +++@chapter Reporting Bugs in @value{GDBN} +++@cindex bugs in @value{GDBN} +++@cindex reporting bugs in @value{GDBN} +++ +++Your bug reports play an essential role in making @value{GDBN} reliable. +++ +++Reporting a bug may help you by bringing a solution to your problem, or it +++may not. But in any case the principal function of a bug report is to help +++the entire community by making the next version of @value{GDBN} work better. Bug +++reports are your contribution to the maintenance of @value{GDBN}. +++ +++In order for a bug report to serve its purpose, you must include the +++information that enables us to fix the bug. +++ +++@menu +++* Bug Criteria:: Have you found a bug? +++* Bug Reporting:: How to report bugs +++@end menu +++ +++@node Bug Criteria +++@section Have You Found a Bug? +++@cindex bug criteria +++ +++If you are not sure whether you have found a bug, here are some guidelines: +++ +++@itemize @bullet +++@cindex fatal signal +++@cindex debugger crash +++@cindex crash of debugger +++@item +++If the debugger gets a fatal signal, for any input whatever, that is a +++@value{GDBN} bug. Reliable debuggers never crash. +++ +++@cindex error on valid input +++@item +++If @value{GDBN} produces an error message for valid input, that is a +++bug. (Note that if you're cross debugging, the problem may also be +++somewhere in the connection to the target.) +++ +++@cindex invalid input +++@item +++If @value{GDBN} does not produce an error message for invalid input, +++that is a bug. However, you should note that your idea of +++``invalid input'' might be our idea of ``an extension'' or ``support +++for traditional practice''. +++ +++@item +++If you are an experienced user of debugging tools, your suggestions +++for improvement of @value{GDBN} are welcome in any case. +++@end itemize +++ +++@node Bug Reporting +++@section How to Report Bugs +++@cindex bug reports +++@cindex @value{GDBN} bugs, reporting +++ +++A number of companies and individuals offer support for @sc{gnu} products. +++If you obtained @value{GDBN} from a support organization, we recommend you +++contact that organization first. +++ +++You can find contact information for many support companies and +++individuals in the file @file{etc/SERVICE} in the @sc{gnu} Emacs +++distribution. +++@c should add a web page ref... +++ +++@ifset BUGURL +++@ifset BUGURL_DEFAULT +++In any event, we also recommend that you submit bug reports for +++@value{GDBN}. The preferred method is to submit them directly using +++@uref{http://www.gnu.org/software/gdb/bugs/, @value{GDBN}'s Bugs web +++page}. Alternatively, the @email{bug-gdb@@gnu.org, e-mail gateway} can +++be used. +++ +++@strong{Do not send bug reports to @samp{info-gdb}, or to +++@samp{help-gdb}, or to any newsgroups.} Most users of @value{GDBN} do +++not want to receive bug reports. Those that do have arranged to receive +++@samp{bug-gdb}. +++ +++The mailing list @samp{bug-gdb} has a newsgroup @samp{gnu.gdb.bug} which +++serves as a repeater. The mailing list and the newsgroup carry exactly +++the same messages. Often people think of posting bug reports to the +++newsgroup instead of mailing them. This appears to work, but it has one +++problem which can be crucial: a newsgroup posting often lacks a mail +++path back to the sender. Thus, if we need to ask for more information, +++we may be unable to reach you. For this reason, it is better to send +++bug reports to the mailing list. +++@end ifset +++@ifclear BUGURL_DEFAULT +++In any event, we also recommend that you submit bug reports for +++@value{GDBN} to @value{BUGURL}. +++@end ifclear +++@end ifset +++ +++The fundamental principle of reporting bugs usefully is this: +++@strong{report all the facts}. If you are not sure whether to state a +++fact or leave it out, state it! +++ +++Often people omit facts because they think they know what causes the +++problem and assume that some details do not matter. Thus, you might +++assume that the name of the variable you use in an example does not matter. +++Well, probably it does not, but one cannot be sure. Perhaps the bug is a +++stray memory reference which happens to fetch from the location where that +++name is stored in memory; perhaps, if the name were different, the contents +++of that location would fool the debugger into doing the right thing despite +++the bug. Play it safe and give a specific, complete example. That is the +++easiest thing for you to do, and the most helpful. +++ +++Keep in mind that the purpose of a bug report is to enable us to fix the +++bug. It may be that the bug has been reported previously, but neither +++you nor we can know that unless your bug report is complete and +++self-contained. +++ +++Sometimes people give a few sketchy facts and ask, ``Does this ring a +++bell?'' Those bug reports are useless, and we urge everyone to +++@emph{refuse to respond to them} except to chide the sender to report +++bugs properly. +++ +++To enable us to fix the bug, you should include all these things: +++ +++@itemize @bullet +++@item +++The version of @value{GDBN}. @value{GDBN} announces it if you start +++with no arguments; you can also print it at any time using @code{show +++version}. +++ +++Without this, we will not know whether there is any point in looking for +++the bug in the current version of @value{GDBN}. +++ +++@item +++The type of machine you are using, and the operating system name and +++version number. +++ +++@item +++The details of the @value{GDBN} build-time configuration. +++@value{GDBN} shows these details if you invoke it with the +++@option{--configuration} command-line option, or if you type +++@code{show configuration} at @value{GDBN}'s prompt. +++ +++@item +++What compiler (and its version) was used to compile @value{GDBN}---e.g.@: +++``@value{GCC}--2.8.1''. +++ +++@item +++What compiler (and its version) was used to compile the program you are +++debugging---e.g.@: ``@value{GCC}--2.8.1'', or ``HP92453-01 A.10.32.03 HP +++C Compiler''. For @value{NGCC}, you can say @kbd{@value{GCC} --version} +++to get this information; for other compilers, see the documentation for +++those compilers. +++ +++@item +++The command arguments you gave the compiler to compile your example and +++observe the bug. For example, did you use @samp{-O}? To guarantee +++you will not omit something important, list them all. A copy of the +++Makefile (or the output from make) is sufficient. +++ +++If we were to try to guess the arguments, we would probably guess wrong +++and then we might not encounter the bug. +++ +++@item +++A complete input script, and all necessary source files, that will +++reproduce the bug. +++ +++@item +++A description of what behavior you observe that you believe is +++incorrect. For example, ``It gets a fatal signal.'' +++ +++Of course, if the bug is that @value{GDBN} gets a fatal signal, then we +++will certainly notice it. But if the bug is incorrect output, we might +++not notice unless it is glaringly wrong. You might as well not give us +++a chance to make a mistake. +++ +++Even if the problem you experience is a fatal signal, you should still +++say so explicitly. Suppose something strange is going on, such as, your +++copy of @value{GDBN} is out of synch, or you have encountered a bug in +++the C library on your system. (This has happened!) Your copy might +++crash and ours would not. If you told us to expect a crash, then when +++ours fails to crash, we would know that the bug was not happening for +++us. If you had not told us to expect a crash, then we would not be able +++to draw any conclusion from our observations. +++ +++@pindex script +++@cindex recording a session script +++To collect all this information, you can use a session recording program +++such as @command{script}, which is available on many Unix systems. +++Just run your @value{GDBN} session inside @command{script} and then +++include the @file{typescript} file with your bug report. +++ +++Another way to record a @value{GDBN} session is to run @value{GDBN} +++inside Emacs and then save the entire buffer to a file. +++ +++@item +++If you wish to suggest changes to the @value{GDBN} source, send us context +++diffs. If you even discuss something in the @value{GDBN} source, refer to +++it by context, not by line number. +++ +++The line numbers in our development sources will not match those in your +++sources. Your line numbers would convey no useful information to us. +++ +++@end itemize +++ +++Here are some things that are not necessary: +++ +++@itemize @bullet +++@item +++A description of the envelope of the bug. +++ +++Often people who encounter a bug spend a lot of time investigating +++which changes to the input file will make the bug go away and which +++changes will not affect it. +++ +++This is often time consuming and not very useful, because the way we +++will find the bug is by running a single example under the debugger +++with breakpoints, not by pure deduction from a series of examples. +++We recommend that you save your time for something else. +++ +++Of course, if you can find a simpler example to report @emph{instead} +++of the original one, that is a convenience for us. Errors in the +++output will be easier to spot, running under the debugger will take +++less time, and so on. +++ +++However, simplification is not vital; if you do not want to do this, +++report the bug anyway and send us the entire test case you used. +++ +++@item +++A patch for the bug. +++ +++A patch for the bug does help us if it is a good one. But do not omit +++the necessary information, such as the test case, on the assumption that +++a patch is all we need. We might see problems with your patch and decide +++to fix the problem another way, or we might not understand it at all. +++ +++Sometimes with a program as complicated as @value{GDBN} it is very hard to +++construct an example that will make the program follow a certain path +++through the code. If you do not send us the example, we will not be able +++to construct one, so we will not be able to verify that the bug is fixed. +++ +++And if we cannot understand what bug you are trying to fix, or why your +++patch should be an improvement, we will not install it. A test case will +++help us to understand. +++ +++@item +++A guess about what the bug is or what it depends on. +++ +++Such guesses are usually wrong. Even we cannot guess right about such +++things without first using the debugger to find the facts. +++@end itemize +++ +++@c The readline documentation is distributed with the readline code +++@c and consists of the two following files: +++@c rluser.texi +++@c hsuser.texi +++@c Use -I with makeinfo to point to the appropriate directory, +++@c environment var TEXINPUTS with TeX. +++@ifclear SYSTEM_READLINE +++@include rluser.texi +++@include hsuser.texi +++@end ifclear +++ +++@node In Memoriam +++@appendix In Memoriam +++ +++The @value{GDBN} project mourns the loss of the following long-time +++contributors: +++ +++@table @code +++@item Fred Fish +++Fred was a long-standing contributor to @value{GDBN} (1991-2006), and +++to Free Software in general. Outside of @value{GDBN}, he was known in +++the Amiga world for his series of Fish Disks, and the GeekGadget project. +++ +++@item Michael Snyder +++Michael was one of the Global Maintainers of the @value{GDBN} project, +++with contributions recorded as early as 1996, until 2011. In addition +++to his day to day participation, he was a large driving force behind +++adding Reverse Debugging to @value{GDBN}. +++@end table +++ +++Beyond their technical contributions to the project, they were also +++enjoyable members of the Free Software Community. We will miss them. +++ +++@node Formatting Documentation +++@appendix Formatting Documentation +++ +++@cindex @value{GDBN} reference card +++@cindex reference card +++The @value{GDBN} 4 release includes an already-formatted reference card, ready +++for printing with PostScript or Ghostscript, in the @file{gdb} +++subdirectory of the main source directory@footnote{In +++@file{gdb-@value{GDBVN}/gdb/refcard.ps} of the version @value{GDBVN} +++release.}. If you can use PostScript or Ghostscript with your printer, +++you can print the reference card immediately with @file{refcard.ps}. +++ +++The release also includes the source for the reference card. You +++can format it, using @TeX{}, by typing: +++ +++@smallexample +++make refcard.dvi +++@end smallexample +++ +++The @value{GDBN} reference card is designed to print in @dfn{landscape} +++mode on US ``letter'' size paper; +++that is, on a sheet 11 inches wide by 8.5 inches +++high. You will need to specify this form of printing as an option to +++your @sc{dvi} output program. +++ +++@cindex documentation +++ +++All the documentation for @value{GDBN} comes as part of the machine-readable +++distribution. The documentation is written in Texinfo format, which is +++a documentation system that uses a single source file to produce both +++on-line information and a printed manual. You can use one of the Info +++formatting commands to create the on-line version of the documentation +++and @TeX{} (or @code{texi2roff}) to typeset the printed version. +++ +++@value{GDBN} includes an already formatted copy of the on-line Info +++version of this manual in the @file{gdb} subdirectory. The main Info +++file is @file{gdb-@value{GDBVN}/gdb/gdb.info}, and it refers to +++subordinate files matching @samp{gdb.info*} in the same directory. If +++necessary, you can print out these files, or read them with any editor; +++but they are easier to read using the @code{info} subsystem in @sc{gnu} +++Emacs or the standalone @code{info} program, available as part of the +++@sc{gnu} Texinfo distribution. +++ +++If you want to format these Info files yourself, you need one of the +++Info formatting programs, such as @code{texinfo-format-buffer} or +++@code{makeinfo}. +++ +++If you have @code{makeinfo} installed, and are in the top level +++@value{GDBN} source directory (@file{gdb-@value{GDBVN}}, in the case of +++version @value{GDBVN}), you can make the Info file by typing: +++ +++@smallexample +++cd gdb +++make gdb.info +++@end smallexample +++ +++If you want to typeset and print copies of this manual, you need @TeX{}, +++a program to print its @sc{dvi} output files, and @file{texinfo.tex}, the +++Texinfo definitions file. +++ +++@TeX{} is a typesetting program; it does not print files directly, but +++produces output files called @sc{dvi} files. To print a typeset +++document, you need a program to print @sc{dvi} files. If your system +++has @TeX{} installed, chances are it has such a program. The precise +++command to use depends on your system; @kbd{lpr -d} is common; another +++(for PostScript devices) is @kbd{dvips}. The @sc{dvi} print command may +++require a file name without any extension or a @samp{.dvi} extension. +++ +++@TeX{} also requires a macro definitions file called +++@file{texinfo.tex}. This file tells @TeX{} how to typeset a document +++written in Texinfo format. On its own, @TeX{} cannot either read or +++typeset a Texinfo file. @file{texinfo.tex} is distributed with GDB +++and is located in the @file{gdb-@var{version-number}/texinfo} +++directory. +++ +++If you have @TeX{} and a @sc{dvi} printer program installed, you can +++typeset and print this manual. First switch to the @file{gdb} +++subdirectory of the main source directory (for example, to +++@file{gdb-@value{GDBVN}/gdb}) and type: +++ +++@smallexample +++make gdb.dvi +++@end smallexample +++ +++Then give @file{gdb.dvi} to your @sc{dvi} printing program. +++ +++@node Installing GDB +++@appendix Installing @value{GDBN} +++@cindex installation +++ +++@menu +++* Requirements:: Requirements for building @value{GDBN} +++* Running Configure:: Invoking the @value{GDBN} @file{configure} script +++* Separate Objdir:: Compiling @value{GDBN} in another directory +++* Config Names:: Specifying names for hosts and targets +++* Configure Options:: Summary of options for configure +++* System-wide configuration:: Having a system-wide init file +++@end menu +++ +++@node Requirements +++@section Requirements for Building @value{GDBN} +++@cindex building @value{GDBN}, requirements for +++ +++Building @value{GDBN} requires various tools and packages to be available. +++Other packages will be used only if they are found. +++ +++@heading Tools/Packages Necessary for Building @value{GDBN} +++@table @asis +++@item C@t{++}11 compiler +++@value{GDBN} is written in C@t{++}11. It should be buildable with any +++recent C@t{++}11 compiler, e.g.@: GCC. +++ +++@item GNU make +++@value{GDBN}'s build system relies on features only found in the GNU +++make program. Other variants of @code{make} will not work. +++@end table +++ +++@heading Tools/Packages Optional for Building @value{GDBN} +++@table @asis +++@item Expat +++@anchor{Expat} +++@value{GDBN} can use the Expat XML parsing library. This library may be +++included with your operating system distribution; if it is not, you +++can get the latest version from @url{http://expat.sourceforge.net}. +++The @file{configure} script will search for this library in several +++standard locations; if it is installed in an unusual path, you can +++use the @option{--with-libexpat-prefix} option to specify its location. +++ +++Expat is used for: +++ +++@itemize @bullet +++@item +++Remote protocol memory maps (@pxref{Memory Map Format}) +++@item +++Target descriptions (@pxref{Target Descriptions}) +++@item +++Remote shared library lists (@xref{Library List Format}, +++or alternatively @pxref{Library List Format for SVR4 Targets}) +++@item +++MS-Windows shared libraries (@pxref{Shared Libraries}) +++@item +++Traceframe info (@pxref{Traceframe Info Format}) +++@item +++Branch trace (@pxref{Branch Trace Format}, +++@pxref{Branch Trace Configuration Format}) +++@end itemize +++ +++@item Guile +++@value{GDBN} can be scripted using GNU Guile. @xref{Guile}. By +++default, @value{GDBN} will be compiled if the Guile libraries are +++installed and are found by @file{configure}. You can use the +++@code{--with-guile} option to request Guile, and pass either the Guile +++version number or the file name of the relevant @code{pkg-config} +++program to choose a particular version of Guile. +++ +++@item iconv +++@value{GDBN}'s features related to character sets (@pxref{Character +++Sets}) require a functioning @code{iconv} implementation. If you are +++on a GNU system, then this is provided by the GNU C Library. Some +++other systems also provide a working @code{iconv}. +++ +++If @value{GDBN} is using the @code{iconv} program which is installed +++in a non-standard place, you will need to tell @value{GDBN} where to +++find it. This is done with @option{--with-iconv-bin} which specifies +++the directory that contains the @code{iconv} program. This program is +++run in order to make a list of the available character sets. +++ +++On systems without @code{iconv}, you can install GNU Libiconv. If +++Libiconv is installed in a standard place, @value{GDBN} will +++automatically use it if it is needed. If you have previously +++installed Libiconv in a non-standard place, you can use the +++@option{--with-libiconv-prefix} option to @file{configure}. +++ +++@value{GDBN}'s top-level @file{configure} and @file{Makefile} will +++arrange to build Libiconv if a directory named @file{libiconv} appears +++in the top-most source directory. If Libiconv is built this way, and +++if the operating system does not provide a suitable @code{iconv} +++implementation, then the just-built library will automatically be used +++by @value{GDBN}. One easy way to set this up is to download GNU +++Libiconv, unpack it inside the top-level directory of the @value{GDBN} +++source tree, and then rename the directory holding the Libiconv source +++code to @samp{libiconv}. +++ +++@item lzma +++@value{GDBN} can support debugging sections that are compressed with +++the LZMA library. @xref{MiniDebugInfo}. If this library is not +++included with your operating system, you can find it in the xz package +++at @url{http://tukaani.org/xz/}. If the LZMA library is available in +++the usual place, then the @file{configure} script will use it +++automatically. If it is installed in an unusual path, you can use the +++@option{--with-lzma-prefix} option to specify its location. +++ +++@item MPFR +++@anchor{MPFR} +++@value{GDBN} can use the GNU MPFR multiple-precision floating-point +++library. This library may be included with your operating system +++distribution; if it is not, you can get the latest version from +++@url{http://www.mpfr.org}. The @file{configure} script will search +++for this library in several standard locations; if it is installed +++in an unusual path, you can use the @option{--with-libmpfr-prefix} +++option to specify its location. +++ +++GNU MPFR is used to emulate target floating-point arithmetic during +++expression evaluation when the target uses different floating-point +++formats than the host. If GNU MPFR it is not available, @value{GDBN} +++will fall back to using host floating-point arithmetic. +++ +++@item Python +++@value{GDBN} can be scripted using Python language. @xref{Python}. +++By default, @value{GDBN} will be compiled if the Python libraries are +++installed and are found by @file{configure}. You can use the +++@code{--with-python} option to request Python, and pass either the +++file name of the relevant @code{python} executable, or the name of the +++directory in which Python is installed, to choose a particular +++installation of Python. +++ +++@item zlib +++@cindex compressed debug sections +++@value{GDBN} will use the @samp{zlib} library, if available, to read +++compressed debug sections. Some linkers, such as GNU gold, are capable +++of producing binaries with compressed debug sections. If @value{GDBN} +++is compiled with @samp{zlib}, it will be able to read the debug +++information in such binaries. +++ +++The @samp{zlib} library is likely included with your operating system +++distribution; if it is not, you can get the latest version from +++@url{http://zlib.net}. +++@end table +++ +++@node Running Configure +++@section Invoking the @value{GDBN} @file{configure} Script +++@cindex configuring @value{GDBN} +++@value{GDBN} comes with a @file{configure} script that automates the process +++of preparing @value{GDBN} for installation; you can then use @code{make} to +++build the @code{gdb} program. +++@iftex +++@c irrelevant in info file; it's as current as the code it lives with. +++@footnote{If you have a more recent version of @value{GDBN} than @value{GDBVN}, +++look at the @file{README} file in the sources; we may have improved the +++installation procedures since publishing this manual.} +++@end iftex +++ +++The @value{GDBN} distribution includes all the source code you need for +++@value{GDBN} in a single directory, whose name is usually composed by +++appending the version number to @samp{gdb}. +++ +++For example, the @value{GDBN} version @value{GDBVN} distribution is in the +++@file{gdb-@value{GDBVN}} directory. That directory contains: +++ +++@table @code +++@item gdb-@value{GDBVN}/configure @r{(and supporting files)} +++script for configuring @value{GDBN} and all its supporting libraries +++ +++@item gdb-@value{GDBVN}/gdb +++the source specific to @value{GDBN} itself +++ +++@item gdb-@value{GDBVN}/bfd +++source for the Binary File Descriptor library +++ +++@item gdb-@value{GDBVN}/include +++@sc{gnu} include files +++ +++@item gdb-@value{GDBVN}/libiberty +++source for the @samp{-liberty} free software library +++ +++@item gdb-@value{GDBVN}/opcodes +++source for the library of opcode tables and disassemblers +++ +++@item gdb-@value{GDBVN}/readline +++source for the @sc{gnu} command-line interface +++@end table +++ +++There may be other subdirectories as well. +++ +++The simplest way to configure and build @value{GDBN} is to run @file{configure} +++from the @file{gdb-@var{version-number}} source directory, which in +++this example is the @file{gdb-@value{GDBVN}} directory. +++ +++First switch to the @file{gdb-@var{version-number}} source directory +++if you are not already in it; then run @file{configure}. Pass the +++identifier for the platform on which @value{GDBN} will run as an +++argument. +++ +++For example: +++ +++@smallexample +++cd gdb-@value{GDBVN} +++./configure +++make +++@end smallexample +++ +++Running @samp{configure} and then running @code{make} builds the +++included supporting libraries, then @code{gdb} itself. The configured +++source files, and the binaries, are left in the corresponding source +++directories. +++ +++@need 750 +++@file{configure} is a Bourne-shell (@code{/bin/sh}) script; if your +++system does not recognize this automatically when you run a different +++shell, you may need to run @code{sh} on it explicitly: +++ +++@smallexample +++sh configure +++@end smallexample +++ +++You should run the @file{configure} script from the top directory in the +++source tree, the @file{gdb-@var{version-number}} directory. If you run +++@file{configure} from one of the subdirectories, you will configure only +++that subdirectory. That is usually not what you want. In particular, +++if you run the first @file{configure} from the @file{gdb} subdirectory +++of the @file{gdb-@var{version-number}} directory, you will omit the +++configuration of @file{bfd}, @file{readline}, and other sibling +++directories of the @file{gdb} subdirectory. This leads to build errors +++about missing include files such as @file{bfd/bfd.h}. +++ +++You can install @code{@value{GDBN}} anywhere. The best way to do this +++is to pass the @code{--prefix} option to @code{configure}, and then +++install it with @code{make install}. +++ +++@node Separate Objdir +++@section Compiling @value{GDBN} in Another Directory +++ +++If you want to run @value{GDBN} versions for several host or target machines, +++you need a different @code{gdb} compiled for each combination of +++host and target. @file{configure} is designed to make this easy by +++allowing you to generate each configuration in a separate subdirectory, +++rather than in the source directory. If your @code{make} program +++handles the @samp{VPATH} feature (@sc{gnu} @code{make} does), running +++@code{make} in each of these directories builds the @code{gdb} +++program specified there. +++ +++To build @code{gdb} in a separate directory, run @file{configure} +++with the @samp{--srcdir} option to specify where to find the source. +++(You also need to specify a path to find @file{configure} +++itself from your working directory. If the path to @file{configure} +++would be the same as the argument to @samp{--srcdir}, you can leave out +++the @samp{--srcdir} option; it is assumed.) +++ +++For example, with version @value{GDBVN}, you can build @value{GDBN} in a +++separate directory for a Sun 4 like this: +++ +++@smallexample +++@group +++cd gdb-@value{GDBVN} +++mkdir ../gdb-sun4 +++cd ../gdb-sun4 +++../gdb-@value{GDBVN}/configure +++make +++@end group +++@end smallexample +++ +++When @file{configure} builds a configuration using a remote source +++directory, it creates a tree for the binaries with the same structure +++(and using the same names) as the tree under the source directory. In +++the example, you'd find the Sun 4 library @file{libiberty.a} in the +++directory @file{gdb-sun4/libiberty}, and @value{GDBN} itself in +++@file{gdb-sun4/gdb}. +++ +++Make sure that your path to the @file{configure} script has just one +++instance of @file{gdb} in it. If your path to @file{configure} looks +++like @file{../gdb-@value{GDBVN}/gdb/configure}, you are configuring only +++one subdirectory of @value{GDBN}, not the whole package. This leads to +++build errors about missing include files such as @file{bfd/bfd.h}. +++ +++One popular reason to build several @value{GDBN} configurations in separate +++directories is to configure @value{GDBN} for cross-compiling (where +++@value{GDBN} runs on one machine---the @dfn{host}---while debugging +++programs that run on another machine---the @dfn{target}). +++You specify a cross-debugging target by +++giving the @samp{--target=@var{target}} option to @file{configure}. +++ +++When you run @code{make} to build a program or library, you must run +++it in a configured directory---whatever directory you were in when you +++called @file{configure} (or one of its subdirectories). +++ +++The @code{Makefile} that @file{configure} generates in each source +++directory also runs recursively. If you type @code{make} in a source +++directory such as @file{gdb-@value{GDBVN}} (or in a separate configured +++directory configured with @samp{--srcdir=@var{dirname}/gdb-@value{GDBVN}}), you +++will build all the required libraries, and then build GDB. +++ +++When you have multiple hosts or targets configured in separate +++directories, you can run @code{make} on them in parallel (for example, +++if they are NFS-mounted on each of the hosts); they will not interfere +++with each other. +++ +++@node Config Names +++@section Specifying Names for Hosts and Targets +++ +++The specifications used for hosts and targets in the @file{configure} +++script are based on a three-part naming scheme, but some short predefined +++aliases are also supported. The full naming scheme encodes three pieces +++of information in the following pattern: +++ +++@smallexample +++@var{architecture}-@var{vendor}-@var{os} +++@end smallexample +++ +++For example, you can use the alias @code{sun4} as a @var{host} argument, +++or as the value for @var{target} in a @code{--target=@var{target}} +++option. The equivalent full name is @samp{sparc-sun-sunos4}. +++ +++The @file{configure} script accompanying @value{GDBN} does not provide +++any query facility to list all supported host and target names or +++aliases. @file{configure} calls the Bourne shell script +++@code{config.sub} to map abbreviations to full names; you can read the +++script, if you wish, or you can use it to test your guesses on +++abbreviations---for example: +++ +++@smallexample +++% sh config.sub i386-linux +++i386-pc-linux-gnu +++% sh config.sub alpha-linux +++alpha-unknown-linux-gnu +++% sh config.sub sw_64-linux +++sw_64-unknown-linux-gnu +++% sh config.sub hp9k700 +++hppa1.1-hp-hpux +++% sh config.sub sun4 +++sparc-sun-sunos4.1.1 +++% sh config.sub sun3 +++m68k-sun-sunos4.1.1 +++% sh config.sub i986v +++Invalid configuration `i986v': machine `i986v' not recognized +++@end smallexample +++ +++@noindent +++@code{config.sub} is also distributed in the @value{GDBN} source +++directory (@file{gdb-@value{GDBVN}}, for version @value{GDBVN}). +++ +++@node Configure Options +++@section @file{configure} Options +++ +++Here is a summary of the @file{configure} options and arguments that +++are most often useful for building @value{GDBN}. @file{configure} +++also has several other options not listed here. @inforef{Running +++configure scripts,,autoconf.info}, for a full +++explanation of @file{configure}. +++ +++@smallexample +++configure @r{[}--help@r{]} +++ @r{[}--prefix=@var{dir}@r{]} +++ @r{[}--exec-prefix=@var{dir}@r{]} +++ @r{[}--srcdir=@var{dirname}@r{]} +++ @r{[}--target=@var{target}@r{]} +++@end smallexample +++ +++@noindent +++You may introduce options with a single @samp{-} rather than +++@samp{--} if you prefer; but you may abbreviate option names if you use +++@samp{--}. +++ +++@table @code +++@item --help +++Display a quick summary of how to invoke @file{configure}. +++ +++@item --prefix=@var{dir} +++Configure the source to install programs and files under directory +++@file{@var{dir}}. +++ +++@item --exec-prefix=@var{dir} +++Configure the source to install programs under directory +++@file{@var{dir}}. +++ +++@c avoid splitting the warning from the explanation: +++@need 2000 +++@item --srcdir=@var{dirname} +++Use this option to make configurations in directories separate from the +++@value{GDBN} source directories. Among other things, you can use this to +++build (or maintain) several configurations simultaneously, in separate +++directories. @file{configure} writes configuration-specific files in +++the current directory, but arranges for them to use the source in the +++directory @var{dirname}. @file{configure} creates directories under +++the working directory in parallel to the source directories below +++@var{dirname}. +++ +++@item --target=@var{target} +++Configure @value{GDBN} for cross-debugging programs running on the specified +++@var{target}. Without this option, @value{GDBN} is configured to debug +++programs that run on the same machine (@var{host}) as @value{GDBN} itself. +++ +++There is no convenient way to generate a list of all available +++targets. Also see the @code{--enable-targets} option, below. +++@end table +++ +++There are many other options that are specific to @value{GDBN}. This +++lists just the most common ones; there are some very specialized +++options not described here. +++ +++@table @code +++@item --enable-targets=@r{[}@var{target}@r{]}@dots{} +++@itemx --enable-targets=all +++Configure @value{GDBN} for cross-debugging programs running on the +++specified list of targets. The special value @samp{all} configures +++@value{GDBN} for debugging programs running on any target it supports. +++ +++@item --with-gdb-datadir=@var{path} +++Set the @value{GDBN}-specific data directory. @value{GDBN} will look +++here for certain supporting files or scripts. This defaults to the +++@file{gdb} subdirectory of @samp{datadir} (which can be set using +++@code{--datadir}). +++ +++@item --with-relocated-sources=@var{dir} +++Sets up the default source path substitution rule so that directory +++names recorded in debug information will be automatically adjusted for +++any directory under @var{dir}. @var{dir} should be a subdirectory of +++@value{GDBN}'s configured prefix, the one mentioned in the +++@code{--prefix} or @code{--exec-prefix} options to configure. This +++option is useful if GDB is supposed to be moved to a different place +++after it is built. +++ +++@item --enable-64-bit-bfd +++Enable 64-bit support in BFD on 32-bit hosts. +++ +++@item --disable-gdbmi +++Build @value{GDBN} without the GDB/MI machine interface +++(@pxref{GDB/MI}). +++ +++@item --enable-tui +++Build @value{GDBN} with the text-mode full-screen user interface +++(TUI). Requires a curses library (ncurses and cursesX are also +++supported). +++ +++@item --with-curses +++Use the curses library instead of the termcap library, for text-mode +++terminal operations. +++ +++@item --with-debuginfod +++Build @value{GDBN} with libdebuginfod, the debuginfod client library. +++Used to automatically fetch source files and separate debug files from +++debuginfod servers using the associated executable's build ID. Enabled +++by default if libdebuginfod is installed and found at configure time. +++debuginfod is packaged with elfutils, starting with version 0.178. You +++can get the latest version from `https://sourceware.org/elfutils/'. +++ +++@item --with-libunwind-ia64 +++Use the libunwind library for unwinding function call stack on ia64 +++target platforms. See http://www.nongnu.org/libunwind/index.html for +++details. +++ +++@item --with-system-readline +++Use the readline library installed on the host, rather than the +++library supplied as part of @value{GDBN}. Readline 7 or newer is +++required; this is enforced by the build system. +++ +++@item --with-system-zlib +++Use the zlib library installed on the host, rather than the library +++supplied as part of @value{GDBN}. +++ +++@item --with-expat +++Build @value{GDBN} with Expat, a library for XML parsing. (Done by +++default if libexpat is installed and found at configure time.) This +++library is used to read XML files supplied with @value{GDBN}. If it +++is unavailable, some features, such as remote protocol memory maps, +++target descriptions, and shared library lists, that are based on XML +++files, will not be available in @value{GDBN}. If your host does not +++have libexpat installed, you can get the latest version from +++`http://expat.sourceforge.net'. +++ +++@item --with-libiconv-prefix@r{[}=@var{dir}@r{]} +++ +++Build @value{GDBN} with GNU libiconv, a character set encoding +++conversion library. This is not done by default, as on GNU systems +++the @code{iconv} that is built in to the C library is sufficient. If +++your host does not have a working @code{iconv}, you can get the latest +++version of GNU iconv from `https://www.gnu.org/software/libiconv/'. +++ +++@value{GDBN}'s build system also supports building GNU libiconv as +++part of the overall build. @xref{Requirements}. +++ +++@item --with-lzma +++Build @value{GDBN} with LZMA, a compression library. (Done by default +++if liblzma is installed and found at configure time.) LZMA is used by +++@value{GDBN}'s "mini debuginfo" feature, which is only useful on +++platforms using the ELF object file format. If your host does not +++have liblzma installed, you can get the latest version from +++`https://tukaani.org/xz/'. +++ +++@item --with-mpfr +++Build @value{GDBN} with GNU MPFR, a library for multiple-precision +++floating-point computation with correct rounding. (Done by default if +++GNU MPFR is installed and found at configure time.) This library is +++used to emulate target floating-point arithmetic during expression +++evaluation when the target uses different floating-point formats than +++the host. If GNU MPFR is not available, @value{GDBN} will fall back +++to using host floating-point arithmetic. If your host does not have +++GNU MPFR installed, you can get the latest version from +++`http://www.mpfr.org'. +++ +++@item --with-python@r{[}=@var{python}@r{]} +++Build @value{GDBN} with Python scripting support. (Done by default if +++libpython is present and found at configure time.) Python makes +++@value{GDBN} scripting much more powerful than the restricted CLI +++scripting language. If your host does not have Python installed, you +++can find it on `http://www.python.org/download/'. The oldest version +++of Python supported by GDB is 2.6. The optional argument @var{python} +++is used to find the Python headers and libraries. It can be either +++the name of a Python executable, or the name of the directory in which +++Python is installed. +++ +++@item --with-guile[=GUILE]' +++Build @value{GDBN} with GNU Guile scripting support. (Done by default +++if libguile is present and found at configure time.) If your host +++does not have Guile installed, you can find it at +++`https://www.gnu.org/software/guile/'. The optional argument GUILE +++can be a version number, which will cause @code{configure} to try to +++use that version of Guile; or the file name of a @code{pkg-config} +++executable, which will be queried to find the information needed to +++compile and link against Guile. +++ +++@item --without-included-regex +++Don't use the regex library included with @value{GDBN} (as part of the +++libiberty library). This is the default on hosts with version 2 of +++the GNU C library. +++ +++@item --with-sysroot=@var{dir} +++Use @var{dir} as the default system root directory for libraries whose +++file names begin with @file{/lib}' or @file{/usr/lib'}. (The value of +++@var{dir} can be modified at run time by using the @command{set +++sysroot} command.) If @var{dir} is under the @value{GDBN} configured +++prefix (set with @code{--prefix} or @code{--exec-prefix options}, the +++default system root will be automatically adjusted if and when +++@value{GDBN} is moved to a different location. +++ +++@item --with-system-gdbinit=@var{file} +++Configure @value{GDBN} to automatically load a system-wide init file. +++@var{file} should be an absolute file name. If @var{file} is in a +++directory under the configured prefix, and @value{GDBN} is moved to +++another location after being built, the location of the system-wide +++init file will be adjusted accordingly. +++ +++@item --with-system-gdbinit-dir=@var{directory} +++Configure @value{GDBN} to automatically load init files from a +++system-wide directory. @var{directory} should be an absolute directory +++name. If @var{directory} is in a directory under the configured +++prefix, and @value{GDBN} is moved to another location after being +++built, the location of the system-wide init directory will be +++adjusted accordingly. +++ +++@item --enable-build-warnings +++When building the @value{GDBN} sources, ask the compiler to warn about +++any code which looks even vaguely suspicious. It passes many +++different warning flags, depending on the exact version of the +++compiler you are using. +++ +++@item --enable-werror +++Treat compiler warnings as werrors. It adds the @code{-Werror} flag +++to the compiler, which will fail the compilation if the compiler +++outputs any warning messages. +++ +++@item --enable-ubsan +++Enable the GCC undefined behavior sanitizer. This is disabled by +++default, but passing @code{--enable-ubsan=yes} or +++@code{--enable-ubsan=auto} to @code{configure} will enable it. The +++undefined behavior sanitizer checks for C@t{++} undefined behavior. +++It has a performance cost, so if you are looking at @value{GDBN}'s +++performance, you should disable it. The undefined behavior sanitizer +++was first introduced in GCC 4.9. +++@end table +++ +++@node System-wide configuration +++@section System-wide configuration and settings +++@cindex system-wide init file +++ +++@value{GDBN} can be configured to have a system-wide init file and a +++system-wide init file directory; this file and files in that directory +++(if they have a recognized file extension) will be read and executed at +++startup (@pxref{Startup, , What @value{GDBN} does during startup}). +++ +++Here are the corresponding configure options: +++ +++@table @code +++@item --with-system-gdbinit=@var{file} +++Specify that the default location of the system-wide init file is +++@var{file}. +++@item --with-system-gdbinit-dir=@var{directory} +++Specify that the default location of the system-wide init file directory +++is @var{directory}. +++@end table +++ +++If @value{GDBN} has been configured with the option @option{--prefix=$prefix}, +++they may be subject to relocation. Two possible cases: +++ +++@itemize @bullet +++@item +++If the default location of this init file/directory contains @file{$prefix}, +++it will be subject to relocation. Suppose that the configure options +++are @option{--prefix=$prefix --with-system-gdbinit=$prefix/etc/gdbinit}; +++if @value{GDBN} is moved from @file{$prefix} to @file{$install}, the system +++init file is looked for as @file{$install/etc/gdbinit} instead of +++@file{$prefix/etc/gdbinit}. +++ +++@item +++By contrast, if the default location does not contain the prefix, +++it will not be relocated. E.g.@: if @value{GDBN} has been configured with +++@option{--prefix=/usr/local --with-system-gdbinit=/usr/share/gdb/gdbinit}, +++then @value{GDBN} will always look for @file{/usr/share/gdb/gdbinit}, +++wherever @value{GDBN} is installed. +++@end itemize +++ +++If the configured location of the system-wide init file (as given by the +++@option{--with-system-gdbinit} option at configure time) is in the +++data-directory (as specified by @option{--with-gdb-datadir} at configure +++time) or in one of its subdirectories, then @value{GDBN} will look for the +++system-wide init file in the directory specified by the +++@option{--data-directory} command-line option. +++Note that the system-wide init file is only read once, during @value{GDBN} +++initialization. If the data-directory is changed after @value{GDBN} has +++started with the @code{set data-directory} command, the file will not be +++reread. +++ +++This applies similarly to the system-wide directory specified in +++@option{--with-system-gdbinit-dir}. +++ +++Any supported scripting language can be used for these init files, as long +++as the file extension matches the scripting language. To be interpreted +++as regular @value{GDBN} commands, the files needs to have a @file{.gdb} +++extension. +++ +++@menu +++* System-wide Configuration Scripts:: Installed System-wide Configuration Scripts +++@end menu +++ +++@node System-wide Configuration Scripts +++@subsection Installed System-wide Configuration Scripts +++@cindex system-wide configuration scripts +++ +++The @file{system-gdbinit} directory, located inside the data-directory +++(as specified by @option{--with-gdb-datadir} at configure time) contains +++a number of scripts which can be used as system-wide init files. To +++automatically source those scripts at startup, @value{GDBN} should be +++configured with @option{--with-system-gdbinit}. Otherwise, any user +++should be able to source them by hand as needed. +++ +++The following scripts are currently available: +++@itemize @bullet +++ +++@item @file{elinos.py} +++@pindex elinos.py +++@cindex ELinOS system-wide configuration script +++This script is useful when debugging a program on an ELinOS target. +++It takes advantage of the environment variables defined in a standard +++ELinOS environment in order to determine the location of the system +++shared libraries, and then sets the @samp{solib-absolute-prefix} +++and @samp{solib-search-path} variables appropriately. +++ +++@item @file{wrs-linux.py} +++@pindex wrs-linux.py +++@cindex Wind River Linux system-wide configuration script +++This script is useful when debugging a program on a target running +++Wind River Linux. It expects the @env{ENV_PREFIX} to be set to +++the host-side sysroot used by the target system. +++ +++@end itemize +++ +++@node Maintenance Commands +++@appendix Maintenance Commands +++@cindex maintenance commands +++@cindex internal commands +++ +++In addition to commands intended for @value{GDBN} users, @value{GDBN} +++includes a number of commands intended for @value{GDBN} developers, +++that are not documented elsewhere in this manual. These commands are +++provided here for reference. (For commands that turn on debugging +++messages, see @ref{Debugging Output}.) +++ +++@table @code +++@kindex maint agent +++@kindex maint agent-eval +++@item maint agent @r{[}-at @var{location}@r{,}@r{]} @var{expression} +++@itemx maint agent-eval @r{[}-at @var{location}@r{,}@r{]} @var{expression} +++Translate the given @var{expression} into remote agent bytecodes. +++This command is useful for debugging the Agent Expression mechanism +++(@pxref{Agent Expressions}). The @samp{agent} version produces an +++expression useful for data collection, such as by tracepoints, while +++@samp{maint agent-eval} produces an expression that evaluates directly +++to a result. For instance, a collection expression for @code{globa + +++globb} will include bytecodes to record four bytes of memory at each +++of the addresses of @code{globa} and @code{globb}, while discarding +++the result of the addition, while an evaluation expression will do the +++addition and return the sum. +++If @code{-at} is given, generate remote agent bytecode for @var{location}. +++If not, generate remote agent bytecode for current frame PC address. +++ +++@kindex maint agent-printf +++@item maint agent-printf @var{format},@var{expr},... +++Translate the given format string and list of argument expressions +++into remote agent bytecodes and display them as a disassembled list. +++This command is useful for debugging the agent version of dynamic +++printf (@pxref{Dynamic Printf}). +++ +++@kindex maint info breakpoints +++@item @anchor{maint info breakpoints}maint info breakpoints +++Using the same format as @samp{info breakpoints}, display both the +++breakpoints you've set explicitly, and those @value{GDBN} is using for +++internal purposes. Internal breakpoints are shown with negative +++breakpoint numbers. The type column identifies what kind of breakpoint +++is shown: +++ +++@table @code +++@item breakpoint +++Normal, explicitly set breakpoint. +++ +++@item watchpoint +++Normal, explicitly set watchpoint. +++ +++@item longjmp +++Internal breakpoint, used to handle correctly stepping through +++@code{longjmp} calls. +++ +++@item longjmp resume +++Internal breakpoint at the target of a @code{longjmp}. +++ +++@item until +++Temporary internal breakpoint used by the @value{GDBN} @code{until} command. +++ +++@item finish +++Temporary internal breakpoint used by the @value{GDBN} @code{finish} command. +++ +++@item shlib events +++Shared library events. +++ +++@end table +++ +++@kindex maint info btrace +++@item maint info btrace +++Pint information about raw branch tracing data. +++ +++@kindex maint btrace packet-history +++@item maint btrace packet-history +++Print the raw branch trace packets that are used to compute the +++execution history for the @samp{record btrace} command. Both the +++information and the format in which it is printed depend on the btrace +++recording format. +++ +++@table @code +++@item bts +++For the BTS recording format, print a list of blocks of sequential +++code. For each block, the following information is printed: +++ +++@table @asis +++@item Block number +++Newer blocks have higher numbers. The oldest block has number zero. +++@item Lowest @samp{PC} +++@item Highest @samp{PC} +++@end table +++ +++@item pt +++For the Intel Processor Trace recording format, print a list of +++Intel Processor Trace packets. For each packet, the following +++information is printed: +++ +++@table @asis +++@item Packet number +++Newer packets have higher numbers. The oldest packet has number zero. +++@item Trace offset +++The packet's offset in the trace stream. +++@item Packet opcode and payload +++@end table +++@end table +++ +++@kindex maint btrace clear-packet-history +++@item maint btrace clear-packet-history +++Discards the cached packet history printed by the @samp{maint btrace +++packet-history} command. The history will be computed again when +++needed. +++ +++@kindex maint btrace clear +++@item maint btrace clear +++Discard the branch trace data. The data will be fetched anew and the +++branch trace will be recomputed when needed. +++ +++This implicitly truncates the branch trace to a single branch trace +++buffer. When updating branch trace incrementally, the branch trace +++available to @value{GDBN} may be bigger than a single branch trace +++buffer. +++ +++@kindex maint set btrace pt skip-pad +++@item maint set btrace pt skip-pad +++@kindex maint show btrace pt skip-pad +++@item maint show btrace pt skip-pad +++Control whether @value{GDBN} will skip PAD packets when computing the +++packet history. +++ +++@kindex set displaced-stepping +++@kindex show displaced-stepping +++@cindex displaced stepping support +++@cindex out-of-line single-stepping +++@item set displaced-stepping +++@itemx show displaced-stepping +++Control whether or not @value{GDBN} will do @dfn{displaced stepping} +++if the target supports it. Displaced stepping is a way to single-step +++over breakpoints without removing them from the inferior, by executing +++an out-of-line copy of the instruction that was originally at the +++breakpoint location. It is also known as out-of-line single-stepping. +++ +++@table @code +++@item set displaced-stepping on +++If the target architecture supports it, @value{GDBN} will use +++displaced stepping to step over breakpoints. +++ +++@item set displaced-stepping off +++@value{GDBN} will not use displaced stepping to step over breakpoints, +++even if such is supported by the target architecture. +++ +++@cindex non-stop mode, and @samp{set displaced-stepping} +++@item set displaced-stepping auto +++This is the default mode. @value{GDBN} will use displaced stepping +++only if non-stop mode is active (@pxref{Non-Stop Mode}) and the target +++architecture supports displaced stepping. +++@end table +++ +++@kindex maint check-psymtabs +++@item maint check-psymtabs +++Check the consistency of currently expanded psymtabs versus symtabs. +++Use this to check, for example, whether a symbol is in one but not the other. +++ +++@kindex maint check-symtabs +++@item maint check-symtabs +++Check the consistency of currently expanded symtabs. +++ +++@kindex maint expand-symtabs +++@item maint expand-symtabs [@var{regexp}] +++Expand symbol tables. +++If @var{regexp} is specified, only expand symbol tables for file +++names matching @var{regexp}. +++ +++@kindex maint set catch-demangler-crashes +++@kindex maint show catch-demangler-crashes +++@cindex demangler crashes +++@item maint set catch-demangler-crashes [on|off] +++@itemx maint show catch-demangler-crashes +++Control whether @value{GDBN} should attempt to catch crashes in the +++symbol name demangler. The default is to attempt to catch crashes. +++If enabled, the first time a crash is caught, a core file is created, +++the offending symbol is displayed and the user is presented with the +++option to terminate the current session. +++ +++@kindex maint cplus first_component +++@item maint cplus first_component @var{name} +++Print the first C@t{++} class/namespace component of @var{name}. +++ +++@kindex maint cplus namespace +++@item maint cplus namespace +++Print the list of possible C@t{++} namespaces. +++ +++@kindex maint deprecate +++@kindex maint undeprecate +++@cindex deprecated commands +++@item maint deprecate @var{command} @r{[}@var{replacement}@r{]} +++@itemx maint undeprecate @var{command} +++Deprecate or undeprecate the named @var{command}. Deprecated commands +++cause @value{GDBN} to issue a warning when you use them. The optional +++argument @var{replacement} says which newer command should be used in +++favor of the deprecated one; if it is given, @value{GDBN} will mention +++the replacement as part of the warning. +++ +++@kindex maint dump-me +++@item maint dump-me +++@cindex @code{SIGQUIT} signal, dump core of @value{GDBN} +++Cause a fatal signal in the debugger and force it to dump its core. +++This is supported only on systems which support aborting a program +++with the @code{SIGQUIT} signal. +++ +++@kindex maint internal-error +++@kindex maint internal-warning +++@kindex maint demangler-warning +++@cindex demangler crashes +++@item maint internal-error @r{[}@var{message-text}@r{]} +++@itemx maint internal-warning @r{[}@var{message-text}@r{]} +++@itemx maint demangler-warning @r{[}@var{message-text}@r{]} +++ +++Cause @value{GDBN} to call the internal function @code{internal_error}, +++@code{internal_warning} or @code{demangler_warning} and hence behave +++as though an internal problem has been detected. In addition to +++reporting the internal problem, these functions give the user the +++opportunity to either quit @value{GDBN} or (for @code{internal_error} +++and @code{internal_warning}) create a core file of the current +++@value{GDBN} session. +++ +++These commands take an optional parameter @var{message-text} that is +++used as the text of the error or warning message. +++ +++Here's an example of using @code{internal-error}: +++ +++@smallexample +++(@value{GDBP}) @kbd{maint internal-error testing, 1, 2} +++@dots{}/maint.c:121: internal-error: testing, 1, 2 +++A problem internal to GDB has been detected. Further +++debugging may prove unreliable. +++Quit this debugging session? (y or n) @kbd{n} +++Create a core file? (y or n) @kbd{n} +++(@value{GDBP}) +++@end smallexample +++ +++@cindex @value{GDBN} internal error +++@cindex internal errors, control of @value{GDBN} behavior +++@cindex demangler crashes +++ +++@kindex maint set internal-error +++@kindex maint show internal-error +++@kindex maint set internal-warning +++@kindex maint show internal-warning +++@kindex maint set demangler-warning +++@kindex maint show demangler-warning +++@item maint set internal-error @var{action} [ask|yes|no] +++@itemx maint show internal-error @var{action} +++@itemx maint set internal-warning @var{action} [ask|yes|no] +++@itemx maint show internal-warning @var{action} +++@itemx maint set demangler-warning @var{action} [ask|yes|no] +++@itemx maint show demangler-warning @var{action} +++When @value{GDBN} reports an internal problem (error or warning) it +++gives the user the opportunity to both quit @value{GDBN} and create a +++core file of the current @value{GDBN} session. These commands let you +++override the default behaviour for each particular @var{action}, +++described in the table below. +++ +++@table @samp +++@item quit +++You can specify that @value{GDBN} should always (yes) or never (no) +++quit. The default is to ask the user what to do. +++ +++@item corefile +++You can specify that @value{GDBN} should always (yes) or never (no) +++create a core file. The default is to ask the user what to do. Note +++that there is no @code{corefile} option for @code{demangler-warning}: +++demangler warnings always create a core file and this cannot be +++disabled. +++@end table +++ +++@kindex maint packet +++@item maint packet @var{text} +++If @value{GDBN} is talking to an inferior via the serial protocol, +++then this command sends the string @var{text} to the inferior, and +++displays the response packet. @value{GDBN} supplies the initial +++@samp{$} character, the terminating @samp{#} character, and the +++checksum. +++ +++@kindex maint print architecture +++@item maint print architecture @r{[}@var{file}@r{]} +++Print the entire architecture configuration. The optional argument +++@var{file} names the file where the output goes. +++ +++@kindex maint print c-tdesc @r{[}@var{file}@r{]} +++@item maint print c-tdesc +++Print the target description (@pxref{Target Descriptions}) as +++a C source file. By default, the target description is for the current +++target, but if the optional argument @var{file} is provided, that file +++is used to produce the description. The @var{file} should be an XML +++document, of the form described in @ref{Target Description Format}. +++The created source file is built into @value{GDBN} when @value{GDBN} is +++built again. This command is used by developers after they add or +++modify XML target descriptions. +++ +++@kindex maint print xml-tdesc +++@item maint print xml-tdesc @r{[}@var{file}@r{]} +++Print the target description (@pxref{Target Descriptions}) as an XML +++file. By default print the target description for the current target, +++but if the optional argument @var{file} is provided, then that file is +++read in by GDB and then used to produce the description. The +++@var{file} should be an XML document, of the form described in +++@ref{Target Description Format}. +++ +++@kindex maint check xml-descriptions +++@item maint check xml-descriptions @var{dir} +++Check that the target descriptions dynamically created by @value{GDBN} +++equal the descriptions created from XML files found in @var{dir}. +++ +++@anchor{maint check libthread-db} +++@kindex maint check libthread-db +++@item maint check libthread-db +++Run integrity checks on the current inferior's thread debugging +++library. This exercises all @code{libthread_db} functionality used by +++@value{GDBN} on GNU/Linux systems, and by extension also exercises the +++@code{proc_service} functions provided by @value{GDBN} that +++@code{libthread_db} uses. Note that parts of the test may be skipped +++on some platforms when debugging core files. +++ +++@kindex maint print core-file-backed-mappings +++@cindex memory address space mappings +++@item maint print core-file-backed-mappings +++Print the file-backed mappings which were loaded from a core file note. +++This output represents state internal to @value{GDBN} and should be +++similar to the mappings displayed by the @code{info proc mappings} +++command. +++ +++@kindex maint print dummy-frames +++@item maint print dummy-frames +++Prints the contents of @value{GDBN}'s internal dummy-frame stack. +++ +++@smallexample +++(@value{GDBP}) @kbd{b add} +++@dots{} +++(@value{GDBP}) @kbd{print add(2,3)} +++Breakpoint 2, add (a=2, b=3) at @dots{} +++58 return (a + b); +++The program being debugged stopped while in a function called from GDB. +++@dots{} +++(@value{GDBP}) @kbd{maint print dummy-frames} +++0xa8206d8: id=@{stack=0xbfffe734,code=0xbfffe73f,!special@}, ptid=process 9353 +++(@value{GDBP}) +++@end smallexample +++ +++Takes an optional file parameter. +++ +++@kindex maint print registers +++@kindex maint print raw-registers +++@kindex maint print cooked-registers +++@kindex maint print register-groups +++@kindex maint print remote-registers +++@item maint print registers @r{[}@var{file}@r{]} +++@itemx maint print raw-registers @r{[}@var{file}@r{]} +++@itemx maint print cooked-registers @r{[}@var{file}@r{]} +++@itemx maint print register-groups @r{[}@var{file}@r{]} +++@itemx maint print remote-registers @r{[}@var{file}@r{]} +++Print @value{GDBN}'s internal register data structures. +++ +++The command @code{maint print raw-registers} includes the contents of +++the raw register cache; the command @code{maint print +++cooked-registers} includes the (cooked) value of all registers, +++including registers which aren't available on the target nor visible +++to user; the command @code{maint print register-groups} includes the +++groups that each register is a member of; and the command @code{maint +++print remote-registers} includes the remote target's register numbers +++and offsets in the `G' packets. +++ +++These commands take an optional parameter, a file name to which to +++write the information. +++ +++@kindex maint print reggroups +++@item maint print reggroups @r{[}@var{file}@r{]} +++Print @value{GDBN}'s internal register group data structures. The +++optional argument @var{file} tells to what file to write the +++information. +++ +++The register groups info looks like this: +++ +++@smallexample +++(@value{GDBP}) @kbd{maint print reggroups} +++ Group Type +++ general user +++ float user +++ all user +++ vector user +++ system user +++ save internal +++ restore internal +++@end smallexample +++ +++@kindex flushregs +++@item flushregs +++This command forces @value{GDBN} to flush its internal register cache. +++ +++@kindex maint print objfiles +++@cindex info for known object files +++@item maint print objfiles @r{[}@var{regexp}@r{]} +++Print a dump of all known object files. +++If @var{regexp} is specified, only print object files whose names +++match @var{regexp}. For each object file, this command prints its name, +++address in memory, and all of its psymtabs and symtabs. +++ +++@kindex maint print user-registers +++@cindex user registers +++@item maint print user-registers +++List all currently available @dfn{user registers}. User registers +++typically provide alternate names for actual hardware registers. They +++include the four ``standard'' registers @code{$fp}, @code{$pc}, +++@code{$sp}, and @code{$ps}. @xref{standard registers}. User +++registers can be used in expressions in the same way as the canonical +++register names, but only the latter are listed by the @code{info +++registers} and @code{maint print registers} commands. +++ +++@kindex maint print section-scripts +++@cindex info for known .debug_gdb_scripts-loaded scripts +++@item maint print section-scripts [@var{regexp}] +++Print a dump of scripts specified in the @code{.debug_gdb_section} section. +++If @var{regexp} is specified, only print scripts loaded by object files +++matching @var{regexp}. +++For each script, this command prints its name as specified in the objfile, +++and the full path if known. +++@xref{dotdebug_gdb_scripts section}. +++ +++@kindex maint print statistics +++@cindex bcache statistics +++@item maint print statistics +++This command prints, for each object file in the program, various data +++about that object file followed by the byte cache (@dfn{bcache}) +++statistics for the object file. The objfile data includes the number +++of minimal, partial, full, and stabs symbols, the number of types +++defined by the objfile, the number of as yet unexpanded psym tables, +++the number of line tables and string tables, and the amount of memory +++used by the various tables. The bcache statistics include the counts, +++sizes, and counts of duplicates of all and unique objects, max, +++average, and median entry size, total memory used and its overhead and +++savings, and various measures of the hash table size and chain +++lengths. +++ +++@kindex maint print target-stack +++@cindex target stack description +++@item maint print target-stack +++A @dfn{target} is an interface between the debugger and a particular +++kind of file or process. Targets can be stacked in @dfn{strata}, +++so that more than one target can potentially respond to a request. +++In particular, memory accesses will walk down the stack of targets +++until they find a target that is interested in handling that particular +++address. +++ +++This command prints a short description of each layer that was pushed on +++the @dfn{target stack}, starting from the top layer down to the bottom one. +++ +++@kindex maint print type +++@cindex type chain of a data type +++@item maint print type @var{expr} +++Print the type chain for a type specified by @var{expr}. The argument +++can be either a type name or a symbol. If it is a symbol, the type of +++that symbol is described. The type chain produced by this command is +++a recursive definition of the data type as stored in @value{GDBN}'s +++data structures, including its flags and contained types. +++ +++@kindex maint selftest +++@cindex self tests +++@item maint selftest @r{[}@var{filter}@r{]} +++Run any self tests that were compiled in to @value{GDBN}. This will +++print a message showing how many tests were run, and how many failed. +++If a @var{filter} is passed, only the tests with @var{filter} in their +++name will by ran. +++ +++@kindex maint info selftests +++@cindex self tests +++@item maint info selftests +++List the selftests compiled in to @value{GDBN}. +++ +++@kindex maint set dwarf always-disassemble +++@kindex maint show dwarf always-disassemble +++@item maint set dwarf always-disassemble +++@item maint show dwarf always-disassemble +++Control the behavior of @code{info address} when using DWARF debugging +++information. +++ +++The default is @code{off}, which means that @value{GDBN} should try to +++describe a variable's location in an easily readable format. When +++@code{on}, @value{GDBN} will instead display the DWARF location +++expression in an assembly-like format. Note that some locations are +++too complex for @value{GDBN} to describe simply; in this case you will +++always see the disassembly form. +++ +++Here is an example of the resulting disassembly: +++ +++@smallexample +++(gdb) info addr argc +++Symbol "argc" is a complex DWARF expression: +++ 1: DW_OP_fbreg 0 +++@end smallexample +++ +++For more information on these expressions, see +++@uref{http://www.dwarfstd.org/, the DWARF standard}. +++ +++@kindex maint set dwarf max-cache-age +++@kindex maint show dwarf max-cache-age +++@item maint set dwarf max-cache-age +++@itemx maint show dwarf max-cache-age +++Control the DWARF compilation unit cache. +++ +++@cindex DWARF compilation units cache +++In object files with inter-compilation-unit references, such as those +++produced by the GCC option @samp{-feliminate-dwarf2-dups}, the DWARF +++reader needs to frequently refer to previously read compilation units. +++This setting controls how long a compilation unit will remain in the +++cache if it is not referenced. A higher limit means that cached +++compilation units will be stored in memory longer, and more total +++memory will be used. Setting it to zero disables caching, which will +++slow down @value{GDBN} startup, but reduce memory consumption. +++ +++@kindex maint set dwarf unwinders +++@kindex maint show dwarf unwinders +++@item maint set dwarf unwinders +++@itemx maint show dwarf unwinders +++Control use of the DWARF frame unwinders. +++ +++@cindex DWARF frame unwinders +++Many targets that support DWARF debugging use @value{GDBN}'s DWARF +++frame unwinders to build the backtrace. Many of these targets will +++also have a second mechanism for building the backtrace for use in +++cases where DWARF information is not available, this second mechanism +++is often an analysis of a function's prologue. +++ +++In order to extend testing coverage of the second level stack +++unwinding mechanisms it is helpful to be able to disable the DWARF +++stack unwinders, this can be done with this switch. +++ +++In normal use of @value{GDBN} disabling the DWARF unwinders is not +++advisable, there are cases that are better handled through DWARF than +++prologue analysis, and the debug experience is likely to be better +++with the DWARF frame unwinders enabled. +++ +++If DWARF frame unwinders are not supported for a particular target +++architecture, then enabling this flag does not cause them to be used. +++ +++@kindex maint set worker-threads +++@kindex maint show worker-threads +++@item maint set worker-threads +++@item maint show worker-threads +++Control the number of worker threads that may be used by @value{GDBN}. +++On capable hosts, @value{GDBN} may use multiple threads to speed up +++certain CPU-intensive operations, such as demangling symbol names. +++While the number of threads used by @value{GDBN} may vary, this +++command can be used to set an upper bound on this number. The default +++is @code{unlimited}, which lets @value{GDBN} choose a reasonable +++number. Note that this only controls worker threads started by +++@value{GDBN} itself; libraries used by @value{GDBN} may start threads +++of their own. +++ +++@kindex maint set profile +++@kindex maint show profile +++@cindex profiling GDB +++@item maint set profile +++@itemx maint show profile +++Control profiling of @value{GDBN}. +++ +++Profiling will be disabled until you use the @samp{maint set profile} +++command to enable it. When you enable profiling, the system will begin +++collecting timing and execution count data; when you disable profiling or +++exit @value{GDBN}, the results will be written to a log file. Remember that +++if you use profiling, @value{GDBN} will overwrite the profiling log file +++(often called @file{gmon.out}). If you have a record of important profiling +++data in a @file{gmon.out} file, be sure to move it to a safe location. +++ +++Configuring with @samp{--enable-profiling} arranges for @value{GDBN} to be +++compiled with the @samp{-pg} compiler option. +++ +++@kindex maint set show-debug-regs +++@kindex maint show show-debug-regs +++@cindex hardware debug registers +++@item maint set show-debug-regs +++@itemx maint show show-debug-regs +++Control whether to show variables that mirror the hardware debug +++registers. Use @code{on} to enable, @code{off} to disable. If +++enabled, the debug registers values are shown when @value{GDBN} inserts or +++removes a hardware breakpoint or watchpoint, and when the inferior +++triggers a hardware-assisted breakpoint or watchpoint. +++ +++@kindex maint set show-all-tib +++@kindex maint show show-all-tib +++@item maint set show-all-tib +++@itemx maint show show-all-tib +++Control whether to show all non zero areas within a 1k block starting +++at thread local base, when using the @samp{info w32 thread-information-block} +++command. +++ +++@kindex maint set target-async +++@kindex maint show target-async +++@item maint set target-async +++@itemx maint show target-async +++This controls whether @value{GDBN} targets operate in synchronous or +++asynchronous mode (@pxref{Background Execution}). Normally the +++default is asynchronous, if it is available; but this can be changed +++to more easily debug problems occurring only in synchronous mode. +++ +++@kindex maint set target-non-stop @var{mode} [on|off|auto] +++@kindex maint show target-non-stop +++@item maint set target-non-stop +++@itemx maint show target-non-stop +++ +++This controls whether @value{GDBN} targets always operate in non-stop +++mode even if @code{set non-stop} is @code{off} (@pxref{Non-Stop +++Mode}). The default is @code{auto}, meaning non-stop mode is enabled +++if supported by the target. +++ +++@table @code +++@item maint set target-non-stop auto +++This is the default mode. @value{GDBN} controls the target in +++non-stop mode if the target supports it. +++ +++@item maint set target-non-stop on +++@value{GDBN} controls the target in non-stop mode even if the target +++does not indicate support. +++ +++@item maint set target-non-stop off +++@value{GDBN} does not control the target in non-stop mode even if the +++target supports it. +++@end table +++ +++@kindex maint set tui-resize-message +++@kindex maint show tui-resize-message +++@item maint set tui-resize-message +++@item maint show tui-resize-message +++Control whether @value{GDBN} displays a message each time the terminal +++is resized when in TUI mode. The default is @code{off}, which means +++that @value{GDBN} is silent during resizes. When @code{on}, +++@value{GDBN} will display a message after a resize is completed; the +++message will include a number indicating how many times the terminal +++has been resized. This setting is intended for use by the test suite, +++where it would otherwise be difficult to determine when a resize and +++refresh has been completed. +++ +++@kindex maint set per-command +++@kindex maint show per-command +++@item maint set per-command +++@itemx maint show per-command +++@cindex resources used by commands +++ +++@value{GDBN} can display the resources used by each command. +++This is useful in debugging performance problems. +++ +++@table @code +++@item maint set per-command space [on|off] +++@itemx maint show per-command space +++Enable or disable the printing of the memory used by GDB for each command. +++If enabled, @value{GDBN} will display how much memory each command +++took, following the command's own output. +++This can also be requested by invoking @value{GDBN} with the +++@option{--statistics} command-line switch (@pxref{Mode Options}). +++ +++@item maint set per-command time [on|off] +++@itemx maint show per-command time +++Enable or disable the printing of the execution time of @value{GDBN} +++for each command. +++If enabled, @value{GDBN} will display how much time it +++took to execute each command, following the command's own output. +++Both CPU time and wallclock time are printed. +++Printing both is useful when trying to determine whether the cost is +++CPU or, e.g., disk/network latency. +++Note that the CPU time printed is for @value{GDBN} only, it does not include +++the execution time of the inferior because there's no mechanism currently +++to compute how much time was spent by @value{GDBN} and how much time was +++spent by the program been debugged. +++This can also be requested by invoking @value{GDBN} with the +++@option{--statistics} command-line switch (@pxref{Mode Options}). +++ +++@item maint set per-command symtab [on|off] +++@itemx maint show per-command symtab +++Enable or disable the printing of basic symbol table statistics +++for each command. +++If enabled, @value{GDBN} will display the following information: +++ +++@enumerate a +++@item +++number of symbol tables +++@item +++number of primary symbol tables +++@item +++number of blocks in the blockvector +++@end enumerate +++@end table +++ +++@kindex maint set check-libthread-db +++@kindex maint show check-libthread-db +++@item maint set check-libthread-db [on|off] +++@itemx maint show check-libthread-db +++Control whether @value{GDBN} should run integrity checks on inferior +++specific thread debugging libraries as they are loaded. The default +++is not to perform such checks. If any check fails @value{GDBN} will +++unload the library and continue searching for a suitable candidate as +++described in @ref{set libthread-db-search-path}. For more information +++about the tests, see @ref{maint check libthread-db}. +++ +++@kindex maint space +++@cindex memory used by commands +++@item maint space @var{value} +++An alias for @code{maint set per-command space}. +++A non-zero value enables it, zero disables it. +++ +++@kindex maint time +++@cindex time of command execution +++@item maint time @var{value} +++An alias for @code{maint set per-command time}. +++A non-zero value enables it, zero disables it. +++ +++@kindex maint translate-address +++@item maint translate-address @r{[}@var{section}@r{]} @var{addr} +++Find the symbol stored at the location specified by the address +++@var{addr} and an optional section name @var{section}. If found, +++@value{GDBN} prints the name of the closest symbol and an offset from +++the symbol's location to the specified address. This is similar to +++the @code{info address} command (@pxref{Symbols}), except that this +++command also allows to find symbols in other sections. +++ +++If section was not specified, the section in which the symbol was found +++is also printed. For dynamically linked executables, the name of +++executable or shared library containing the symbol is printed as well. +++ +++@kindex maint test-options +++@item maint test-options require-delimiter +++@itemx maint test-options unknown-is-error +++@itemx maint test-options unknown-is-operand +++These commands are used by the testsuite to validate the command +++options framework. The @code{require-delimiter} variant requires a +++double-dash delimiter to indicate end of options. The +++@code{unknown-is-error} and @code{unknown-is-operand} do not. The +++@code{unknown-is-error} variant throws an error on unknown option, +++while @code{unknown-is-operand} treats unknown options as the start of +++the command's operands. When run, the commands output the result of +++the processed options. When completed, the commands store the +++internal result of completion in a variable exposed by the @code{maint +++show test-options-completion-result} command. +++ +++@kindex maint show test-options-completion-result +++@item maint show test-options-completion-result +++Shows the result of completing the @code{maint test-options} +++subcommands. This is used by the testsuite to validate completion +++support in the command options framework. +++ +++@kindex maint set test-settings +++@kindex maint show test-settings +++@item maint set test-settings @var{kind} +++@itemx maint show test-settings @var{kind} +++These are representative commands for each @var{kind} of setting type +++@value{GDBN} supports. They are used by the testsuite for exercising +++the settings infrastructure. +++ +++@kindex maint with +++@item maint with @var{setting} [@var{value}] [-- @var{command}] +++Like the @code{with} command, but works with @code{maintenance set} +++variables. This is used by the testsuite to exercise the @code{with} +++command's infrastructure. +++ +++@end table +++ +++The following command is useful for non-interactive invocations of +++@value{GDBN}, such as in the test suite. +++ +++@table @code +++@item set watchdog @var{nsec} +++@kindex set watchdog +++@cindex watchdog timer +++@cindex timeout for commands +++Set the maximum number of seconds @value{GDBN} will wait for the +++target operation to finish. If this time expires, @value{GDBN} +++reports and error and the command is aborted. +++ +++@item show watchdog +++Show the current setting of the target wait timeout. +++@end table +++ +++@node Remote Protocol +++@appendix @value{GDBN} Remote Serial Protocol +++ +++@menu +++* Overview:: +++* Packets:: +++* Stop Reply Packets:: +++* General Query Packets:: +++* Architecture-Specific Protocol Details:: +++* Tracepoint Packets:: +++* Host I/O Packets:: +++* Interrupts:: +++* Notification Packets:: +++* Remote Non-Stop:: +++* Packet Acknowledgment:: +++* Examples:: +++* File-I/O Remote Protocol Extension:: +++* Library List Format:: +++* Library List Format for SVR4 Targets:: +++* Memory Map Format:: +++* Thread List Format:: +++* Traceframe Info Format:: +++* Branch Trace Format:: +++* Branch Trace Configuration Format:: +++@end menu +++ +++@node Overview +++@section Overview +++ +++There may be occasions when you need to know something about the +++protocol---for example, if there is only one serial port to your target +++machine, you might want your program to do something special if it +++recognizes a packet meant for @value{GDBN}. +++ +++In the examples below, @samp{->} and @samp{<-} are used to indicate +++transmitted and received data, respectively. +++ +++@cindex protocol, @value{GDBN} remote serial +++@cindex serial protocol, @value{GDBN} remote +++@cindex remote serial protocol +++All @value{GDBN} commands and responses (other than acknowledgments +++and notifications, see @ref{Notification Packets}) are sent as a +++@var{packet}. A @var{packet} is introduced with the character +++@samp{$}, the actual @var{packet-data}, and the terminating character +++@samp{#} followed by a two-digit @var{checksum}: +++ +++@smallexample +++@code{$}@var{packet-data}@code{#}@var{checksum} +++@end smallexample +++@noindent +++ +++@cindex checksum, for @value{GDBN} remote +++@noindent +++The two-digit @var{checksum} is computed as the modulo 256 sum of all +++characters between the leading @samp{$} and the trailing @samp{#} (an +++eight bit unsigned checksum). +++ +++Implementors should note that prior to @value{GDBN} 5.0 the protocol +++specification also included an optional two-digit @var{sequence-id}: +++ +++@smallexample +++@code{$}@var{sequence-id}@code{:}@var{packet-data}@code{#}@var{checksum} +++@end smallexample +++ +++@cindex sequence-id, for @value{GDBN} remote +++@noindent +++That @var{sequence-id} was appended to the acknowledgment. @value{GDBN} +++has never output @var{sequence-id}s. Stubs that handle packets added +++since @value{GDBN} 5.0 must not accept @var{sequence-id}. +++ +++When either the host or the target machine receives a packet, the first +++response expected is an acknowledgment: either @samp{+} (to indicate +++the package was received correctly) or @samp{-} (to request +++retransmission): +++ +++@smallexample +++-> @code{$}@var{packet-data}@code{#}@var{checksum} +++<- @code{+} +++@end smallexample +++@noindent +++ +++The @samp{+}/@samp{-} acknowledgments can be disabled +++once a connection is established. +++@xref{Packet Acknowledgment}, for details. +++ +++The host (@value{GDBN}) sends @var{command}s, and the target (the +++debugging stub incorporated in your program) sends a @var{response}. In +++the case of step and continue @var{command}s, the response is only sent +++when the operation has completed, and the target has again stopped all +++threads in all attached processes. This is the default all-stop mode +++behavior, but the remote protocol also supports @value{GDBN}'s non-stop +++execution mode; see @ref{Remote Non-Stop}, for details. +++ +++@var{packet-data} consists of a sequence of characters with the +++exception of @samp{#} and @samp{$} (see @samp{X} packet for additional +++exceptions). +++ +++@cindex remote protocol, field separator +++Fields within the packet should be separated using @samp{,} @samp{;} or +++@samp{:}. Except where otherwise noted all numbers are represented in +++@sc{hex} with leading zeros suppressed. +++ +++Implementors should note that prior to @value{GDBN} 5.0, the character +++@samp{:} could not appear as the third character in a packet (as it +++would potentially conflict with the @var{sequence-id}). +++ +++@cindex remote protocol, binary data +++@anchor{Binary Data} +++Binary data in most packets is encoded either as two hexadecimal +++digits per byte of binary data. This allowed the traditional remote +++protocol to work over connections which were only seven-bit clean. +++Some packets designed more recently assume an eight-bit clean +++connection, and use a more efficient encoding to send and receive +++binary data. +++ +++The binary data representation uses @code{7d} (@sc{ascii} @samp{@}}) +++as an escape character. Any escaped byte is transmitted as the escape +++character followed by the original character XORed with @code{0x20}. +++For example, the byte @code{0x7d} would be transmitted as the two +++bytes @code{0x7d 0x5d}. The bytes @code{0x23} (@sc{ascii} @samp{#}), +++@code{0x24} (@sc{ascii} @samp{$}), and @code{0x7d} (@sc{ascii} +++@samp{@}}) must always be escaped. Responses sent by the stub +++must also escape @code{0x2a} (@sc{ascii} @samp{*}), so that it +++is not interpreted as the start of a run-length encoded sequence +++(described next). +++ +++Response @var{data} can be run-length encoded to save space. +++Run-length encoding replaces runs of identical characters with one +++instance of the repeated character, followed by a @samp{*} and a +++repeat count. The repeat count is itself sent encoded, to avoid +++binary characters in @var{data}: a value of @var{n} is sent as +++@code{@var{n}+29}. For a repeat count greater or equal to 3, this +++produces a printable @sc{ascii} character, e.g.@: a space (@sc{ascii} +++code 32) for a repeat count of 3. (This is because run-length +++encoding starts to win for counts 3 or more.) Thus, for example, +++@samp{0* } is a run-length encoding of ``0000'': the space character +++after @samp{*} means repeat the leading @code{0} @w{@code{32 - 29 = +++3}} more times. +++ +++The printable characters @samp{#} and @samp{$} or with a numeric value +++greater than 126 must not be used. Runs of six repeats (@samp{#}) or +++seven repeats (@samp{$}) can be expanded using a repeat count of only +++five (@samp{"}). For example, @samp{00000000} can be encoded as +++@samp{0*"00}. +++ +++The error response returned for some packets includes a two character +++error number. That number is not well defined. +++ +++@cindex empty response, for unsupported packets +++For any @var{command} not supported by the stub, an empty response +++(@samp{$#00}) should be returned. That way it is possible to extend the +++protocol. A newer @value{GDBN} can tell if a packet is supported based +++on that response. +++ +++At a minimum, a stub is required to support the @samp{?} command to +++tell @value{GDBN} the reason for halting, @samp{g} and @samp{G} +++commands for register access, and the @samp{m} and @samp{M} commands +++for memory access. Stubs that only control single-threaded targets +++can implement run control with the @samp{c} (continue) command, and if +++the target architecture supports hardware-assisted single-stepping, +++the @samp{s} (step) command. Stubs that support multi-threading +++targets should support the @samp{vCont} command. All other commands +++are optional. +++ +++@node Packets +++@section Packets +++ +++The following table provides a complete list of all currently defined +++@var{command}s and their corresponding response @var{data}. +++@xref{File-I/O Remote Protocol Extension}, for details about the File +++I/O extension of the remote protocol. +++ +++Each packet's description has a template showing the packet's overall +++syntax, followed by an explanation of the packet's meaning. We +++include spaces in some of the templates for clarity; these are not +++part of the packet's syntax. No @value{GDBN} packet uses spaces to +++separate its components. For example, a template like @samp{foo +++@var{bar} @var{baz}} describes a packet beginning with the three ASCII +++bytes @samp{foo}, followed by a @var{bar}, followed directly by a +++@var{baz}. @value{GDBN} does not transmit a space character between the +++@samp{foo} and the @var{bar}, or between the @var{bar} and the +++@var{baz}. +++ +++@cindex @var{thread-id}, in remote protocol +++@anchor{thread-id syntax} +++Several packets and replies include a @var{thread-id} field to identify +++a thread. Normally these are positive numbers with a target-specific +++interpretation, formatted as big-endian hex strings. A @var{thread-id} +++can also be a literal @samp{-1} to indicate all threads, or @samp{0} to +++pick any thread. +++ +++In addition, the remote protocol supports a multiprocess feature in +++which the @var{thread-id} syntax is extended to optionally include both +++process and thread ID fields, as @samp{p@var{pid}.@var{tid}}. +++The @var{pid} (process) and @var{tid} (thread) components each have the +++format described above: a positive number with target-specific +++interpretation formatted as a big-endian hex string, literal @samp{-1} +++to indicate all processes or threads (respectively), or @samp{0} to +++indicate an arbitrary process or thread. Specifying just a process, as +++@samp{p@var{pid}}, is equivalent to @samp{p@var{pid}.-1}. It is an +++error to specify all processes but a specific thread, such as +++@samp{p-1.@var{tid}}. Note that the @samp{p} prefix is @emph{not} used +++for those packets and replies explicitly documented to include a process +++ID, rather than a @var{thread-id}. +++ +++The multiprocess @var{thread-id} syntax extensions are only used if both +++@value{GDBN} and the stub report support for the @samp{multiprocess} +++feature using @samp{qSupported}. @xref{multiprocess extensions}, for +++more information. +++ +++Note that all packet forms beginning with an upper- or lower-case +++letter, other than those described here, are reserved for future use. +++ +++Here are the packet descriptions. +++ +++@table @samp +++ +++@item ! +++@cindex @samp{!} packet +++@anchor{extended mode} +++Enable extended mode. In extended mode, the remote server is made +++persistent. The @samp{R} packet is used to restart the program being +++debugged. +++ +++Reply: +++@table @samp +++@item OK +++The remote target both supports and has enabled extended mode. +++@end table +++ +++@item ? +++@cindex @samp{?} packet +++@anchor{? packet} +++Indicate the reason the target halted. The reply is the same as for +++step and continue. This packet has a special interpretation when the +++target is in non-stop mode; see @ref{Remote Non-Stop}. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item A @var{arglen},@var{argnum},@var{arg},@dots{} +++@cindex @samp{A} packet +++Initialized @code{argv[]} array passed into program. @var{arglen} +++specifies the number of bytes in the hex encoded byte stream +++@var{arg}. See @code{gdbserver} for more details. +++ +++Reply: +++@table @samp +++@item OK +++The arguments were set. +++@item E @var{NN} +++An error occurred. +++@end table +++ +++@item b @var{baud} +++@cindex @samp{b} packet +++(Don't use this packet; its behavior is not well-defined.) +++Change the serial line speed to @var{baud}. +++ +++JTC: @emph{When does the transport layer state change? When it's +++received, or after the ACK is transmitted. In either case, there are +++problems if the command or the acknowledgment packet is dropped.} +++ +++Stan: @emph{If people really wanted to add something like this, and get +++it working for the first time, they ought to modify ser-unix.c to send +++some kind of out-of-band message to a specially-setup stub and have the +++switch happen "in between" packets, so that from remote protocol's point +++of view, nothing actually happened.} +++ +++@item B @var{addr},@var{mode} +++@cindex @samp{B} packet +++Set (@var{mode} is @samp{S}) or clear (@var{mode} is @samp{C}) a +++breakpoint at @var{addr}. +++ +++Don't use this packet. Use the @samp{Z} and @samp{z} packets instead +++(@pxref{insert breakpoint or watchpoint packet}). +++ +++@cindex @samp{bc} packet +++@anchor{bc} +++@item bc +++Backward continue. Execute the target system in reverse. No parameter. +++@xref{Reverse Execution}, for more information. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@cindex @samp{bs} packet +++@anchor{bs} +++@item bs +++Backward single step. Execute one instruction in reverse. No parameter. +++@xref{Reverse Execution}, for more information. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item c @r{[}@var{addr}@r{]} +++@cindex @samp{c} packet +++Continue at @var{addr}, which is the address to resume. If @var{addr} +++is omitted, resume at current address. +++ +++This packet is deprecated for multi-threading support. @xref{vCont +++packet}. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item C @var{sig}@r{[};@var{addr}@r{]} +++@cindex @samp{C} packet +++Continue with signal @var{sig} (hex signal number). If +++@samp{;@var{addr}} is omitted, resume at same address. +++ +++This packet is deprecated for multi-threading support. @xref{vCont +++packet}. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item d +++@cindex @samp{d} packet +++Toggle debug flag. +++ +++Don't use this packet; instead, define a general set packet +++(@pxref{General Query Packets}). +++ +++@item D +++@itemx D;@var{pid} +++@cindex @samp{D} packet +++The first form of the packet is used to detach @value{GDBN} from the +++remote system. It is sent to the remote target +++before @value{GDBN} disconnects via the @code{detach} command. +++ +++The second form, including a process ID, is used when multiprocess +++protocol extensions are enabled (@pxref{multiprocess extensions}), to +++detach only a specific process. The @var{pid} is specified as a +++big-endian hex string. +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@item F @var{RC},@var{EE},@var{CF};@var{XX} +++@cindex @samp{F} packet +++A reply from @value{GDBN} to an @samp{F} packet sent by the target. +++This is part of the File-I/O protocol extension. @xref{File-I/O +++Remote Protocol Extension}, for the specification. +++ +++@item g +++@anchor{read registers packet} +++@cindex @samp{g} packet +++Read general registers. +++ +++Reply: +++@table @samp +++@item @var{XX@dots{}} +++Each byte of register data is described by two hex digits. The bytes +++with the register are transmitted in target byte order. The size of +++each register and their position within the @samp{g} packet are +++determined by the @value{GDBN} internal gdbarch functions +++@code{DEPRECATED_REGISTER_RAW_SIZE} and @code{gdbarch_register_name}. +++ +++When reading registers from a trace frame (@pxref{Analyze Collected +++Data,,Using the Collected Data}), the stub may also return a string of +++literal @samp{x}'s in place of the register data digits, to indicate +++that the corresponding register has not been collected, thus its value +++is unavailable. For example, for an architecture with 4 registers of +++4 bytes each, the following reply indicates to @value{GDBN} that +++registers 0 and 2 have not been collected, while registers 1 and 3 +++have been collected, and both have zero value: +++ +++@smallexample +++-> @code{g} +++<- @code{xxxxxxxx00000000xxxxxxxx00000000} +++@end smallexample +++ +++@item E @var{NN} +++for an error. +++@end table +++ +++@item G @var{XX@dots{}} +++@cindex @samp{G} packet +++Write general registers. @xref{read registers packet}, for a +++description of the @var{XX@dots{}} data. +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@item H @var{op} @var{thread-id} +++@cindex @samp{H} packet +++Set thread for subsequent operations (@samp{m}, @samp{M}, @samp{g}, +++@samp{G}, et.al.). Depending on the operation to be performed, @var{op} +++should be @samp{c} for step and continue operations (note that this +++is deprecated, supporting the @samp{vCont} command is a better +++option), and @samp{g} for other operations. The thread designator +++@var{thread-id} has the format and interpretation described in +++@ref{thread-id syntax}. +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@c FIXME: JTC: +++@c 'H': How restrictive (or permissive) is the thread model. If a +++@c thread is selected and stopped, are other threads allowed +++@c to continue to execute? As I mentioned above, I think the +++@c semantics of each command when a thread is selected must be +++@c described. For example: +++@c +++@c 'g': If the stub supports threads and a specific thread is +++@c selected, returns the register block from that thread; +++@c otherwise returns current registers. +++@c +++@c 'G' If the stub supports threads and a specific thread is +++@c selected, sets the registers of the register block of +++@c that thread; otherwise sets current registers. +++ +++@item i @r{[}@var{addr}@r{[},@var{nnn}@r{]]} +++@anchor{cycle step packet} +++@cindex @samp{i} packet +++Step the remote target by a single clock cycle. If @samp{,@var{nnn}} is +++present, cycle step @var{nnn} cycles. If @var{addr} is present, cycle +++step starting at that address. +++ +++@item I +++@cindex @samp{I} packet +++Signal, then cycle step. @xref{step with signal packet}. @xref{cycle +++step packet}. +++ +++@item k +++@cindex @samp{k} packet +++Kill request. +++ +++The exact effect of this packet is not specified. +++ +++For a bare-metal target, it may power cycle or reset the target +++system. For that reason, the @samp{k} packet has no reply. +++ +++For a single-process target, it may kill that process if possible. +++ +++A multiple-process target may choose to kill just one process, or all +++that are under @value{GDBN}'s control. For more precise control, use +++the vKill packet (@pxref{vKill packet}). +++ +++If the target system immediately closes the connection in response to +++@samp{k}, @value{GDBN} does not consider the lack of packet +++acknowledgment to be an error, and assumes the kill was successful. +++ +++If connected using @kbd{target extended-remote}, and the target does +++not close the connection in response to a kill request, @value{GDBN} +++probes the target state as if a new connection was opened +++(@pxref{? packet}). +++ +++@item m @var{addr},@var{length} +++@cindex @samp{m} packet +++Read @var{length} addressable memory units starting at address @var{addr} +++(@pxref{addressable memory unit}). Note that @var{addr} may not be aligned to +++any particular boundary. +++ +++The stub need not use any particular size or alignment when gathering +++data from memory for the response; even if @var{addr} is word-aligned +++and @var{length} is a multiple of the word size, the stub is free to +++use byte accesses, or not. For this reason, this packet may not be +++suitable for accessing memory-mapped I/O devices. +++@cindex alignment of remote memory accesses +++@cindex size of remote memory accesses +++@cindex memory, alignment and size of remote accesses +++ +++Reply: +++@table @samp +++@item @var{XX@dots{}} +++Memory contents; each byte is transmitted as a two-digit hexadecimal number. +++The reply may contain fewer addressable memory units than requested if the +++server was able to read only part of the region of memory. +++@item E @var{NN} +++@var{NN} is errno +++@end table +++ +++@item M @var{addr},@var{length}:@var{XX@dots{}} +++@cindex @samp{M} packet +++Write @var{length} addressable memory units starting at address @var{addr} +++(@pxref{addressable memory unit}). The data is given by @var{XX@dots{}}; each +++byte is transmitted as a two-digit hexadecimal number. +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error (this includes the case where only part of the data was +++written). +++@end table +++ +++@item p @var{n} +++@cindex @samp{p} packet +++Read the value of register @var{n}; @var{n} is in hex. +++@xref{read registers packet}, for a description of how the returned +++register value is encoded. +++ +++Reply: +++@table @samp +++@item @var{XX@dots{}} +++the register's value +++@item E @var{NN} +++for an error +++@item @w{} +++Indicating an unrecognized @var{query}. +++@end table +++ +++@item P @var{n@dots{}}=@var{r@dots{}} +++@anchor{write register packet} +++@cindex @samp{P} packet +++Write register @var{n@dots{}} with value @var{r@dots{}}. The register +++number @var{n} is in hexadecimal, and @var{r@dots{}} contains two hex +++digits for each byte in the register (target byte order). +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@item q @var{name} @var{params}@dots{} +++@itemx Q @var{name} @var{params}@dots{} +++@cindex @samp{q} packet +++@cindex @samp{Q} packet +++General query (@samp{q}) and set (@samp{Q}). These packets are +++described fully in @ref{General Query Packets}. +++ +++@item r +++@cindex @samp{r} packet +++Reset the entire system. +++ +++Don't use this packet; use the @samp{R} packet instead. +++ +++@item R @var{XX} +++@cindex @samp{R} packet +++Restart the program being debugged. The @var{XX}, while needed, is ignored. +++This packet is only available in extended mode (@pxref{extended mode}). +++ +++The @samp{R} packet has no reply. +++ +++@item s @r{[}@var{addr}@r{]} +++@cindex @samp{s} packet +++Single step, resuming at @var{addr}. If +++@var{addr} is omitted, resume at same address. +++ +++This packet is deprecated for multi-threading support. @xref{vCont +++packet}. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item S @var{sig}@r{[};@var{addr}@r{]} +++@anchor{step with signal packet} +++@cindex @samp{S} packet +++Step with signal. This is analogous to the @samp{C} packet, but +++requests a single-step, rather than a normal resumption of execution. +++ +++This packet is deprecated for multi-threading support. @xref{vCont +++packet}. +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item t @var{addr}:@var{PP},@var{MM} +++@cindex @samp{t} packet +++Search backwards starting at address @var{addr} for a match with pattern +++@var{PP} and mask @var{MM}, both of which are are 4 byte long. +++There must be at least 3 digits in @var{addr}. +++ +++@item T @var{thread-id} +++@cindex @samp{T} packet +++Find out if the thread @var{thread-id} is alive. @xref{thread-id syntax}. +++ +++Reply: +++@table @samp +++@item OK +++thread is still alive +++@item E @var{NN} +++thread is dead +++@end table +++ +++@item v +++Packets starting with @samp{v} are identified by a multi-letter name, +++up to the first @samp{;} or @samp{?} (or the end of the packet). +++ +++@item vAttach;@var{pid} +++@cindex @samp{vAttach} packet +++Attach to a new process with the specified process ID @var{pid}. +++The process ID is a +++hexadecimal integer identifying the process. In all-stop mode, all +++threads in the attached process are stopped; in non-stop mode, it may be +++attached without being stopped if that is supported by the target. +++ +++@c In non-stop mode, on a successful vAttach, the stub should set the +++@c current thread to a thread of the newly-attached process. After +++@c attaching, GDB queries for the attached process's thread ID with qC. +++@c Also note that, from a user perspective, whether or not the +++@c target is stopped on attach in non-stop mode depends on whether you +++@c use the foreground or background version of the attach command, not +++@c on what vAttach does; GDB does the right thing with respect to either +++@c stopping or restarting threads. +++ +++This packet is only available in extended mode (@pxref{extended mode}). +++ +++Reply: +++@table @samp +++@item E @var{nn} +++for an error +++@item @r{Any stop packet} +++for success in all-stop mode (@pxref{Stop Reply Packets}) +++@item OK +++for success in non-stop mode (@pxref{Remote Non-Stop}) +++@end table +++ +++@item vCont@r{[};@var{action}@r{[}:@var{thread-id}@r{]]}@dots{} +++@cindex @samp{vCont} packet +++@anchor{vCont packet} +++Resume the inferior, specifying different actions for each thread. +++ +++For each inferior thread, the leftmost action with a matching +++@var{thread-id} is applied. Threads that don't match any action +++remain in their current state. Thread IDs are specified using the +++syntax described in @ref{thread-id syntax}. If multiprocess +++extensions (@pxref{multiprocess extensions}) are supported, actions +++can be specified to match all threads in a process by using the +++@samp{p@var{pid}.-1} form of the @var{thread-id}. An action with no +++@var{thread-id} matches all threads. Specifying no actions is an +++error. +++ +++Currently supported actions are: +++ +++@table @samp +++@item c +++Continue. +++@item C @var{sig} +++Continue with signal @var{sig}. The signal @var{sig} should be two hex digits. +++@item s +++Step. +++@item S @var{sig} +++Step with signal @var{sig}. The signal @var{sig} should be two hex digits. +++@item t +++Stop. +++@item r @var{start},@var{end} +++Step once, and then keep stepping as long as the thread stops at +++addresses between @var{start} (inclusive) and @var{end} (exclusive). +++The remote stub reports a stop reply when either the thread goes out +++of the range or is stopped due to an unrelated reason, such as hitting +++a breakpoint. @xref{range stepping}. +++ +++If the range is empty (@var{start} == @var{end}), then the action +++becomes equivalent to the @samp{s} action. In other words, +++single-step once, and report the stop (even if the stepped instruction +++jumps to @var{start}). +++ +++(A stop reply may be sent at any point even if the PC is still within +++the stepping range; for example, it is valid to implement this packet +++in a degenerate way as a single instruction step operation.) +++ +++@end table +++ +++The optional argument @var{addr} normally associated with the +++@samp{c}, @samp{C}, @samp{s}, and @samp{S} packets is +++not supported in @samp{vCont}. +++ +++The @samp{t} action is only relevant in non-stop mode +++(@pxref{Remote Non-Stop}) and may be ignored by the stub otherwise. +++A stop reply should be generated for any affected thread not already stopped. +++When a thread is stopped by means of a @samp{t} action, +++the corresponding stop reply should indicate that the thread has stopped with +++signal @samp{0}, regardless of whether the target uses some other signal +++as an implementation detail. +++ +++The server must ignore @samp{c}, @samp{C}, @samp{s}, @samp{S}, and +++@samp{r} actions for threads that are already running. Conversely, +++the server must ignore @samp{t} actions for threads that are already +++stopped. +++ +++@emph{Note:} In non-stop mode, a thread is considered running until +++@value{GDBN} acknowledges an asynchronous stop notification for it with +++the @samp{vStopped} packet (@pxref{Remote Non-Stop}). +++ +++The stub must support @samp{vCont} if it reports support for +++multiprocess extensions (@pxref{multiprocess extensions}). +++ +++Reply: +++@xref{Stop Reply Packets}, for the reply specifications. +++ +++@item vCont? +++@cindex @samp{vCont?} packet +++Request a list of actions supported by the @samp{vCont} packet. +++ +++Reply: +++@table @samp +++@item vCont@r{[};@var{action}@dots{}@r{]} +++The @samp{vCont} packet is supported. Each @var{action} is a supported +++command in the @samp{vCont} packet. +++@item @w{} +++The @samp{vCont} packet is not supported. +++@end table +++ +++@anchor{vCtrlC packet} +++@item vCtrlC +++@cindex @samp{vCtrlC} packet +++Interrupt remote target as if a control-C was pressed on the remote +++terminal. This is the equivalent to reacting to the @code{^C} +++(@samp{\003}, the control-C character) character in all-stop mode +++while the target is running, except this works in non-stop mode. +++@xref{interrupting remote targets}, for more info on the all-stop +++variant. +++ +++Reply: +++@table @samp +++@item E @var{nn} +++for an error +++@item OK +++for success +++@end table +++ +++@item vFile:@var{operation}:@var{parameter}@dots{} +++@cindex @samp{vFile} packet +++Perform a file operation on the target system. For details, +++see @ref{Host I/O Packets}. +++ +++@item vFlashErase:@var{addr},@var{length} +++@cindex @samp{vFlashErase} packet +++Direct the stub to erase @var{length} bytes of flash starting at +++@var{addr}. The region may enclose any number of flash blocks, but +++its start and end must fall on block boundaries, as indicated by the +++flash block size appearing in the memory map (@pxref{Memory Map +++Format}). @value{GDBN} groups flash memory programming operations +++together, and sends a @samp{vFlashDone} request after each group; the +++stub is allowed to delay erase operation until the @samp{vFlashDone} +++packet is received. +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@item vFlashWrite:@var{addr}:@var{XX@dots{}} +++@cindex @samp{vFlashWrite} packet +++Direct the stub to write data to flash address @var{addr}. The data +++is passed in binary form using the same encoding as for the @samp{X} +++packet (@pxref{Binary Data}). The memory ranges specified by +++@samp{vFlashWrite} packets preceding a @samp{vFlashDone} packet must +++not overlap, and must appear in order of increasing addresses +++(although @samp{vFlashErase} packets for higher addresses may already +++have been received; the ordering is guaranteed only between +++@samp{vFlashWrite} packets). If a packet writes to an address that was +++neither erased by a preceding @samp{vFlashErase} packet nor by some other +++target-specific method, the results are unpredictable. +++ +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E.memtype +++for vFlashWrite addressing non-flash memory +++@item E @var{NN} +++for an error +++@end table +++ +++@item vFlashDone +++@cindex @samp{vFlashDone} packet +++Indicate to the stub that flash programming operation is finished. +++The stub is permitted to delay or batch the effects of a group of +++@samp{vFlashErase} and @samp{vFlashWrite} packets until a +++@samp{vFlashDone} packet is received. The contents of the affected +++regions of flash memory are unpredictable until the @samp{vFlashDone} +++request is completed. +++ +++@item vKill;@var{pid} +++@cindex @samp{vKill} packet +++@anchor{vKill packet} +++Kill the process with the specified process ID @var{pid}, which is a +++hexadecimal integer identifying the process. This packet is used in +++preference to @samp{k} when multiprocess protocol extensions are +++supported; see @ref{multiprocess extensions}. +++ +++Reply: +++@table @samp +++@item E @var{nn} +++for an error +++@item OK +++for success +++@end table +++ +++@item vMustReplyEmpty +++@cindex @samp{vMustReplyEmpty} packet +++The correct reply to an unknown @samp{v} packet is to return the empty +++string, however, some older versions of @command{gdbserver} would +++incorrectly return @samp{OK} for unknown @samp{v} packets. +++ +++The @samp{vMustReplyEmpty} is used as a feature test to check how +++@command{gdbserver} handles unknown packets, it is important that this +++packet be handled in the same way as other unknown @samp{v} packets. +++If this packet is handled differently to other unknown @samp{v} +++packets then it is possible that @value{GDBN} may run into problems in +++other areas, specifically around use of @samp{vFile:setfs:}. +++ +++@item vRun;@var{filename}@r{[};@var{argument}@r{]}@dots{} +++@cindex @samp{vRun} packet +++Run the program @var{filename}, passing it each @var{argument} on its +++command line. The file and arguments are hex-encoded strings. If +++@var{filename} is an empty string, the stub may use a default program +++(e.g.@: the last program run). The program is created in the stopped +++state. +++ +++@c FIXME: What about non-stop mode? +++ +++This packet is only available in extended mode (@pxref{extended mode}). +++ +++Reply: +++@table @samp +++@item E @var{nn} +++for an error +++@item @r{Any stop packet} +++for success (@pxref{Stop Reply Packets}) +++@end table +++ +++@item vStopped +++@cindex @samp{vStopped} packet +++@xref{Notification Packets}. +++ +++@item X @var{addr},@var{length}:@var{XX@dots{}} +++@anchor{X packet} +++@cindex @samp{X} packet +++Write data to memory, where the data is transmitted in binary. +++Memory is specified by its address @var{addr} and number of addressable memory +++units @var{length} (@pxref{addressable memory unit}); +++@samp{@var{XX}@dots{}} is binary data (@pxref{Binary Data}). +++ +++Reply: +++@table @samp +++@item OK +++for success +++@item E @var{NN} +++for an error +++@end table +++ +++@item z @var{type},@var{addr},@var{kind} +++@itemx Z @var{type},@var{addr},@var{kind} +++@anchor{insert breakpoint or watchpoint packet} +++@cindex @samp{z} packet +++@cindex @samp{Z} packets +++Insert (@samp{Z}) or remove (@samp{z}) a @var{type} breakpoint or +++watchpoint starting at address @var{address} of kind @var{kind}. +++ +++Each breakpoint and watchpoint packet @var{type} is documented +++separately. +++ +++@emph{Implementation notes: A remote target shall return an empty string +++for an unrecognized breakpoint or watchpoint packet @var{type}. A +++remote target shall support either both or neither of a given +++@samp{Z@var{type}@dots{}} and @samp{z@var{type}@dots{}} packet pair. To +++avoid potential problems with duplicate packets, the operations should +++be implemented in an idempotent way.} +++ +++@item z0,@var{addr},@var{kind} +++@itemx Z0,@var{addr},@var{kind}@r{[};@var{cond_list}@dots{}@r{]}@r{[};cmds:@var{persist},@var{cmd_list}@dots{}@r{]} +++@cindex @samp{z0} packet +++@cindex @samp{Z0} packet +++Insert (@samp{Z0}) or remove (@samp{z0}) a software breakpoint at address +++@var{addr} of type @var{kind}. +++ +++A software breakpoint is implemented by replacing the instruction at +++@var{addr} with a software breakpoint or trap instruction. The +++@var{kind} is target-specific and typically indicates the size of the +++breakpoint in bytes that should be inserted. E.g., the @sc{arm} and +++@sc{mips} can insert either a 2 or 4 byte breakpoint. Some +++architectures have additional meanings for @var{kind} +++(@pxref{Architecture-Specific Protocol Details}); if no +++architecture-specific value is being used, it should be @samp{0}. +++@var{kind} is hex-encoded. @var{cond_list} is an optional list of +++conditional expressions in bytecode form that should be evaluated on +++the target's side. These are the conditions that should be taken into +++consideration when deciding if the breakpoint trigger should be +++reported back to @value{GDBN}. +++ +++See also the @samp{swbreak} stop reason (@pxref{swbreak stop reason}) +++for how to best report a software breakpoint event to @value{GDBN}. +++ +++The @var{cond_list} parameter is comprised of a series of expressions, +++concatenated without separators. Each expression has the following form: +++ +++@table @samp +++ +++@item X @var{len},@var{expr} +++@var{len} is the length of the bytecode expression and @var{expr} is the +++actual conditional expression in bytecode form. +++ +++@end table +++ +++The optional @var{cmd_list} parameter introduces commands that may be +++run on the target, rather than being reported back to @value{GDBN}. +++The parameter starts with a numeric flag @var{persist}; if the flag is +++nonzero, then the breakpoint may remain active and the commands +++continue to be run even when @value{GDBN} disconnects from the target. +++Following this flag is a series of expressions concatenated with no +++separators. Each expression has the following form: +++ +++@table @samp +++ +++@item X @var{len},@var{expr} +++@var{len} is the length of the bytecode expression and @var{expr} is the +++actual commands expression in bytecode form. +++ +++@end table +++ +++@emph{Implementation note: It is possible for a target to copy or move +++code that contains software breakpoints (e.g., when implementing +++overlays). The behavior of this packet, in the presence of such a +++target, is not defined.} +++ +++Reply: +++@table @samp +++@item OK +++success +++@item @w{} +++not supported +++@item E @var{NN} +++for an error +++@end table +++ +++@item z1,@var{addr},@var{kind} +++@itemx Z1,@var{addr},@var{kind}@r{[};@var{cond_list}@dots{}@r{]}@r{[};cmds:@var{persist},@var{cmd_list}@dots{}@r{]} +++@cindex @samp{z1} packet +++@cindex @samp{Z1} packet +++Insert (@samp{Z1}) or remove (@samp{z1}) a hardware breakpoint at +++address @var{addr}. +++ +++A hardware breakpoint is implemented using a mechanism that is not +++dependent on being able to modify the target's memory. The +++@var{kind}, @var{cond_list}, and @var{cmd_list} arguments have the +++same meaning as in @samp{Z0} packets. +++ +++@emph{Implementation note: A hardware breakpoint is not affected by code +++movement.} +++ +++Reply: +++@table @samp +++@item OK +++success +++@item @w{} +++not supported +++@item E @var{NN} +++for an error +++@end table +++ +++@item z2,@var{addr},@var{kind} +++@itemx Z2,@var{addr},@var{kind} +++@cindex @samp{z2} packet +++@cindex @samp{Z2} packet +++Insert (@samp{Z2}) or remove (@samp{z2}) a write watchpoint at @var{addr}. +++The number of bytes to watch is specified by @var{kind}. +++ +++Reply: +++@table @samp +++@item OK +++success +++@item @w{} +++not supported +++@item E @var{NN} +++for an error +++@end table +++ +++@item z3,@var{addr},@var{kind} +++@itemx Z3,@var{addr},@var{kind} +++@cindex @samp{z3} packet +++@cindex @samp{Z3} packet +++Insert (@samp{Z3}) or remove (@samp{z3}) a read watchpoint at @var{addr}. +++The number of bytes to watch is specified by @var{kind}. +++ +++Reply: +++@table @samp +++@item OK +++success +++@item @w{} +++not supported +++@item E @var{NN} +++for an error +++@end table +++ +++@item z4,@var{addr},@var{kind} +++@itemx Z4,@var{addr},@var{kind} +++@cindex @samp{z4} packet +++@cindex @samp{Z4} packet +++Insert (@samp{Z4}) or remove (@samp{z4}) an access watchpoint at @var{addr}. +++The number of bytes to watch is specified by @var{kind}. +++ +++Reply: +++@table @samp +++@item OK +++success +++@item @w{} +++not supported +++@item E @var{NN} +++for an error +++@end table +++ +++@end table +++ +++@node Stop Reply Packets +++@section Stop Reply Packets +++@cindex stop reply packets +++ +++The @samp{C}, @samp{c}, @samp{S}, @samp{s}, @samp{vCont}, +++@samp{vAttach}, @samp{vRun}, @samp{vStopped}, and @samp{?} packets can +++receive any of the below as a reply. Except for @samp{?} +++and @samp{vStopped}, that reply is only returned +++when the target halts. In the below the exact meaning of @dfn{signal +++number} is defined by the header @file{include/gdb/signals.h} in the +++@value{GDBN} source code. +++ +++In non-stop mode, the server will simply reply @samp{OK} to commands +++such as @samp{vCont}; any stop will be the subject of a future +++notification. @xref{Remote Non-Stop}. +++ +++As in the description of request packets, we include spaces in the +++reply templates for clarity; these are not part of the reply packet's +++syntax. No @value{GDBN} stop reply packet uses spaces to separate its +++components. +++ +++@table @samp +++ +++@item S @var{AA} +++The program received signal number @var{AA} (a two-digit hexadecimal +++number). This is equivalent to a @samp{T} response with no +++@var{n}:@var{r} pairs. +++ +++@item T @var{AA} @var{n1}:@var{r1};@var{n2}:@var{r2};@dots{} +++@cindex @samp{T} packet reply +++The program received signal number @var{AA} (a two-digit hexadecimal +++number). This is equivalent to an @samp{S} response, except that the +++@samp{@var{n}:@var{r}} pairs can carry values of important registers +++and other information directly in the stop reply packet, reducing +++round-trip latency. Single-step and breakpoint traps are reported +++this way. Each @samp{@var{n}:@var{r}} pair is interpreted as follows: +++ +++@itemize @bullet +++@item +++If @var{n} is a hexadecimal number, it is a register number, and the +++corresponding @var{r} gives that register's value. The data @var{r} is a +++series of bytes in target byte order, with each byte given by a +++two-digit hex number. +++ +++@item +++If @var{n} is @samp{thread}, then @var{r} is the @var{thread-id} of +++the stopped thread, as specified in @ref{thread-id syntax}. +++ +++@item +++If @var{n} is @samp{core}, then @var{r} is the hexadecimal number of +++the core on which the stop event was detected. +++ +++@item +++If @var{n} is a recognized @dfn{stop reason}, it describes a more +++specific event that stopped the target. The currently defined stop +++reasons are listed below. The @var{aa} should be @samp{05}, the trap +++signal. At most one stop reason should be present. +++ +++@item +++Otherwise, @value{GDBN} should ignore this @samp{@var{n}:@var{r}} pair +++and go on to the next; this allows us to extend the protocol in the +++future. +++@end itemize +++ +++The currently defined stop reasons are: +++ +++@table @samp +++@item watch +++@itemx rwatch +++@itemx awatch +++The packet indicates a watchpoint hit, and @var{r} is the data address, in +++hex. +++ +++@item syscall_entry +++@itemx syscall_return +++The packet indicates a syscall entry or return, and @var{r} is the +++syscall number, in hex. +++ +++@cindex shared library events, remote reply +++@item library +++The packet indicates that the loaded libraries have changed. +++@value{GDBN} should use @samp{qXfer:libraries:read} to fetch a new +++list of loaded libraries. The @var{r} part is ignored. +++ +++@cindex replay log events, remote reply +++@item replaylog +++The packet indicates that the target cannot continue replaying +++logged execution events, because it has reached the end (or the +++beginning when executing backward) of the log. The value of @var{r} +++will be either @samp{begin} or @samp{end}. @xref{Reverse Execution}, +++for more information. +++ +++@item swbreak +++@anchor{swbreak stop reason} +++The packet indicates a software breakpoint instruction was executed, +++irrespective of whether it was @value{GDBN} that planted the +++breakpoint or the breakpoint is hardcoded in the program. The @var{r} +++part must be left empty. +++ +++On some architectures, such as x86, at the architecture level, when a +++breakpoint instruction executes the program counter points at the +++breakpoint address plus an offset. On such targets, the stub is +++responsible for adjusting the PC to point back at the breakpoint +++address. +++ +++This packet should not be sent by default; older @value{GDBN} versions +++did not support it. @value{GDBN} requests it, by supplying an +++appropriate @samp{qSupported} feature (@pxref{qSupported}). The +++remote stub must also supply the appropriate @samp{qSupported} feature +++indicating support. +++ +++This packet is required for correct non-stop mode operation. +++ +++@item hwbreak +++The packet indicates the target stopped for a hardware breakpoint. +++The @var{r} part must be left empty. +++ +++The same remarks about @samp{qSupported} and non-stop mode above +++apply. +++ +++@cindex fork events, remote reply +++@item fork +++The packet indicates that @code{fork} was called, and @var{r} +++is the thread ID of the new child process. Refer to +++@ref{thread-id syntax} for the format of the @var{thread-id} +++field. This packet is only applicable to targets that support +++fork events. +++ +++This packet should not be sent by default; older @value{GDBN} versions +++did not support it. @value{GDBN} requests it, by supplying an +++appropriate @samp{qSupported} feature (@pxref{qSupported}). The +++remote stub must also supply the appropriate @samp{qSupported} feature +++indicating support. +++ +++@cindex vfork events, remote reply +++@item vfork +++The packet indicates that @code{vfork} was called, and @var{r} +++is the thread ID of the new child process. Refer to +++@ref{thread-id syntax} for the format of the @var{thread-id} +++field. This packet is only applicable to targets that support +++vfork events. +++ +++This packet should not be sent by default; older @value{GDBN} versions +++did not support it. @value{GDBN} requests it, by supplying an +++appropriate @samp{qSupported} feature (@pxref{qSupported}). The +++remote stub must also supply the appropriate @samp{qSupported} feature +++indicating support. +++ +++@cindex vforkdone events, remote reply +++@item vforkdone +++The packet indicates that a child process created by a vfork +++has either called @code{exec} or terminated, so that the +++address spaces of the parent and child process are no longer +++shared. The @var{r} part is ignored. This packet is only +++applicable to targets that support vforkdone events. +++ +++This packet should not be sent by default; older @value{GDBN} versions +++did not support it. @value{GDBN} requests it, by supplying an +++appropriate @samp{qSupported} feature (@pxref{qSupported}). The +++remote stub must also supply the appropriate @samp{qSupported} feature +++indicating support. +++ +++@cindex exec events, remote reply +++@item exec +++The packet indicates that @code{execve} was called, and @var{r} +++is the absolute pathname of the file that was executed, in hex. +++This packet is only applicable to targets that support exec events. +++ +++This packet should not be sent by default; older @value{GDBN} versions +++did not support it. @value{GDBN} requests it, by supplying an +++appropriate @samp{qSupported} feature (@pxref{qSupported}). The +++remote stub must also supply the appropriate @samp{qSupported} feature +++indicating support. +++ +++@cindex thread create event, remote reply +++@anchor{thread create event} +++@item create +++The packet indicates that the thread was just created. The new thread +++is stopped until @value{GDBN} sets it running with a resumption packet +++(@pxref{vCont packet}). This packet should not be sent by default; +++@value{GDBN} requests it with the @ref{QThreadEvents} packet. See +++also the @samp{w} (@pxref{thread exit event}) remote reply below. The +++@var{r} part is ignored. +++ +++@end table +++ +++@item W @var{AA} +++@itemx W @var{AA} ; process:@var{pid} +++The process exited, and @var{AA} is the exit status. This is only +++applicable to certain targets. +++ +++The second form of the response, including the process ID of the +++exited process, can be used only when @value{GDBN} has reported +++support for multiprocess protocol extensions; see @ref{multiprocess +++extensions}. Both @var{AA} and @var{pid} are formatted as big-endian +++hex strings. +++ +++@item X @var{AA} +++@itemx X @var{AA} ; process:@var{pid} +++The process terminated with signal @var{AA}. +++ +++The second form of the response, including the process ID of the +++terminated process, can be used only when @value{GDBN} has reported +++support for multiprocess protocol extensions; see @ref{multiprocess +++extensions}. Both @var{AA} and @var{pid} are formatted as big-endian +++hex strings. +++ +++@anchor{thread exit event} +++@cindex thread exit event, remote reply +++@item w @var{AA} ; @var{tid} +++ +++The thread exited, and @var{AA} is the exit status. This response +++should not be sent by default; @value{GDBN} requests it with the +++@ref{QThreadEvents} packet. See also @ref{thread create event} above. +++@var{AA} is formatted as a big-endian hex string. +++ +++@item N +++There are no resumed threads left in the target. In other words, even +++though the process is alive, the last resumed thread has exited. For +++example, say the target process has two threads: thread 1 and thread +++2. The client leaves thread 1 stopped, and resumes thread 2, which +++subsequently exits. At this point, even though the process is still +++alive, and thus no @samp{W} stop reply is sent, no thread is actually +++executing either. The @samp{N} stop reply thus informs the client +++that it can stop waiting for stop replies. This packet should not be +++sent by default; older @value{GDBN} versions did not support it. +++@value{GDBN} requests it, by supplying an appropriate +++@samp{qSupported} feature (@pxref{qSupported}). The remote stub must +++also supply the appropriate @samp{qSupported} feature indicating +++support. +++ +++@item O @var{XX}@dots{} +++@samp{@var{XX}@dots{}} is hex encoding of @sc{ascii} data, to be +++written as the program's console output. This can happen at any time +++while the program is running and the debugger should continue to wait +++for @samp{W}, @samp{T}, etc. This reply is not permitted in non-stop mode. +++ +++@item F @var{call-id},@var{parameter}@dots{} +++@var{call-id} is the identifier which says which host system call should +++be called. This is just the name of the function. Translation into the +++correct system call is only applicable as it's defined in @value{GDBN}. +++@xref{File-I/O Remote Protocol Extension}, for a list of implemented +++system calls. +++ +++@samp{@var{parameter}@dots{}} is a list of parameters as defined for +++this very system call. +++ +++The target replies with this packet when it expects @value{GDBN} to +++call a host system call on behalf of the target. @value{GDBN} replies +++with an appropriate @samp{F} packet and keeps up waiting for the next +++reply packet from the target. The latest @samp{C}, @samp{c}, @samp{S} +++or @samp{s} action is expected to be continued. @xref{File-I/O Remote +++Protocol Extension}, for more details. +++ +++@end table +++ +++@node General Query Packets +++@section General Query Packets +++@cindex remote query requests +++ +++Packets starting with @samp{q} are @dfn{general query packets}; +++packets starting with @samp{Q} are @dfn{general set packets}. General +++query and set packets are a semi-unified form for retrieving and +++sending information to and from the stub. +++ +++The initial letter of a query or set packet is followed by a name +++indicating what sort of thing the packet applies to. For example, +++@value{GDBN} may use a @samp{qSymbol} packet to exchange symbol +++definitions with the stub. These packet names follow some +++conventions: +++ +++@itemize @bullet +++@item +++The name must not contain commas, colons or semicolons. +++@item +++Most @value{GDBN} query and set packets have a leading upper case +++letter. +++@item +++The names of custom vendor packets should use a company prefix, in +++lower case, followed by a period. For example, packets designed at +++the Acme Corporation might begin with @samp{qacme.foo} (for querying +++foos) or @samp{Qacme.bar} (for setting bars). +++@end itemize +++ +++The name of a query or set packet should be separated from any +++parameters by a @samp{:}; the parameters themselves should be +++separated by @samp{,} or @samp{;}. Stubs must be careful to match the +++full packet name, and check for a separator or the end of the packet, +++in case two packet names share a common prefix. New packets should not begin +++with @samp{qC}, @samp{qP}, or @samp{qL}@footnote{The @samp{qP} and @samp{qL} +++packets predate these conventions, and have arguments without any terminator +++for the packet name; we suspect they are in widespread use in places that +++are difficult to upgrade. The @samp{qC} packet has no arguments, but some +++existing stubs (e.g.@: RedBoot) are known to not check for the end of the +++packet.}. +++ +++Like the descriptions of the other packets, each description here +++has a template showing the packet's overall syntax, followed by an +++explanation of the packet's meaning. We include spaces in some of the +++templates for clarity; these are not part of the packet's syntax. No +++@value{GDBN} packet uses spaces to separate its components. +++ +++Here are the currently defined query and set packets: +++ +++@table @samp +++ +++@item QAgent:1 +++@itemx QAgent:0 +++Turn on or off the agent as a helper to perform some debugging operations +++delegated from @value{GDBN} (@pxref{Control Agent}). +++ +++@item QAllow:@var{op}:@var{val}@dots{} +++@cindex @samp{QAllow} packet +++Specify which operations @value{GDBN} expects to request of the +++target, as a semicolon-separated list of operation name and value +++pairs. Possible values for @var{op} include @samp{WriteReg}, +++@samp{WriteMem}, @samp{InsertBreak}, @samp{InsertTrace}, +++@samp{InsertFastTrace}, and @samp{Stop}. @var{val} is either 0, +++indicating that @value{GDBN} will not request the operation, or 1, +++indicating that it may. (The target can then use this to set up its +++own internals optimally, for instance if the debugger never expects to +++insert breakpoints, it may not need to install its own trap handler.) +++ +++@item qC +++@cindex current thread, remote request +++@cindex @samp{qC} packet +++Return the current thread ID. +++ +++Reply: +++@table @samp +++@item QC @var{thread-id} +++Where @var{thread-id} is a thread ID as documented in +++@ref{thread-id syntax}. +++@item @r{(anything else)} +++Any other reply implies the old thread ID. +++@end table +++ +++@item qCRC:@var{addr},@var{length} +++@cindex CRC of memory block, remote request +++@cindex @samp{qCRC} packet +++@anchor{qCRC packet} +++Compute the CRC checksum of a block of memory using CRC-32 defined in +++IEEE 802.3. The CRC is computed byte at a time, taking the most +++significant bit of each byte first. The initial pattern code +++@code{0xffffffff} is used to ensure leading zeros affect the CRC. +++ +++@emph{Note:} This is the same CRC used in validating separate debug +++files (@pxref{Separate Debug Files, , Debugging Information in Separate +++Files}). However the algorithm is slightly different. When validating +++separate debug files, the CRC is computed taking the @emph{least} +++significant bit of each byte first, and the final result is inverted to +++detect trailing zeros. +++ +++Reply: +++@table @samp +++@item E @var{NN} +++An error (such as memory fault) +++@item C @var{crc32} +++The specified memory region's checksum is @var{crc32}. +++@end table +++ +++@item QDisableRandomization:@var{value} +++@cindex disable address space randomization, remote request +++@cindex @samp{QDisableRandomization} packet +++Some target operating systems will randomize the virtual address space +++of the inferior process as a security feature, but provide a feature +++to disable such randomization, e.g.@: to allow for a more deterministic +++debugging experience. On such systems, this packet with a @var{value} +++of 1 directs the target to disable address space randomization for +++processes subsequently started via @samp{vRun} packets, while a packet +++with a @var{value} of 0 tells the target to enable address space +++randomization. +++ +++This packet is only available in extended mode (@pxref{extended mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QDisableRandomization} is not supported +++by the stub. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++This should only be done on targets that actually support disabling +++address space randomization. +++ +++@item QStartupWithShell:@var{value} +++@cindex startup with shell, remote request +++@cindex @samp{QStartupWithShell} packet +++On UNIX-like targets, it is possible to start the inferior using a +++shell program. This is the default behavior on both @value{GDBN} and +++@command{gdbserver} (@pxref{set startup-with-shell}). This packet is +++used to inform @command{gdbserver} whether it should start the +++inferior using a shell or not. +++ +++If @var{value} is @samp{0}, @command{gdbserver} will not use a shell +++to start the inferior. If @var{value} is @samp{1}, +++@command{gdbserver} will use a shell to start the inferior. All other +++values are considered an error. +++ +++This packet is only available in extended mode (@pxref{extended +++mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). This should only be done on targets that +++actually support starting the inferior using a shell. +++ +++Use of this packet is controlled by the @code{set startup-with-shell} +++command; @pxref{set startup-with-shell}. +++ +++@item QEnvironmentHexEncoded:@var{hex-value} +++@anchor{QEnvironmentHexEncoded} +++@cindex set environment variable, remote request +++@cindex @samp{QEnvironmentHexEncoded} packet +++On UNIX-like targets, it is possible to set environment variables that +++will be passed to the inferior during the startup process. This +++packet is used to inform @command{gdbserver} of an environment +++variable that has been defined by the user on @value{GDBN} (@pxref{set +++environment}). +++ +++The packet is composed by @var{hex-value}, an hex encoded +++representation of the @var{name=value} format representing an +++environment variable. The name of the environment variable is +++represented by @var{name}, and the value to be assigned to the +++environment variable is represented by @var{value}. If the variable +++has no value (i.e., the value is @code{null}), then @var{value} will +++not be present. +++ +++This packet is only available in extended mode (@pxref{extended +++mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). This should only be done on targets that +++actually support passing environment variables to the starting +++inferior. +++ +++This packet is related to the @code{set environment} command; +++@pxref{set environment}. +++ +++@item QEnvironmentUnset:@var{hex-value} +++@anchor{QEnvironmentUnset} +++@cindex unset environment variable, remote request +++@cindex @samp{QEnvironmentUnset} packet +++On UNIX-like targets, it is possible to unset environment variables +++before starting the inferior in the remote target. This packet is +++used to inform @command{gdbserver} of an environment variable that has +++been unset by the user on @value{GDBN} (@pxref{unset environment}). +++ +++The packet is composed by @var{hex-value}, an hex encoded +++representation of the name of the environment variable to be unset. +++ +++This packet is only available in extended mode (@pxref{extended +++mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). This should only be done on targets that +++actually support passing environment variables to the starting +++inferior. +++ +++This packet is related to the @code{unset environment} command; +++@pxref{unset environment}. +++ +++@item QEnvironmentReset +++@anchor{QEnvironmentReset} +++@cindex reset environment, remote request +++@cindex @samp{QEnvironmentReset} packet +++On UNIX-like targets, this packet is used to reset the state of +++environment variables in the remote target before starting the +++inferior. In this context, reset means unsetting all environment +++variables that were previously set by the user (i.e., were not +++initially present in the environment). It is sent to +++@command{gdbserver} before the @samp{QEnvironmentHexEncoded} +++(@pxref{QEnvironmentHexEncoded}) and the @samp{QEnvironmentUnset} +++(@pxref{QEnvironmentUnset}) packets. +++ +++This packet is only available in extended mode (@pxref{extended +++mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). This should only be done on targets that +++actually support passing environment variables to the starting +++inferior. +++ +++@item QSetWorkingDir:@r{[}@var{directory}@r{]} +++@anchor{QSetWorkingDir packet} +++@cindex set working directory, remote request +++@cindex @samp{QSetWorkingDir} packet +++This packet is used to inform the remote server of the intended +++current working directory for programs that are going to be executed. +++ +++The packet is composed by @var{directory}, an hex encoded +++representation of the directory that the remote inferior will use as +++its current working directory. If @var{directory} is an empty string, +++the remote server should reset the inferior's current working +++directory to its original, empty value. +++ +++This packet is only available in extended mode (@pxref{extended +++mode}). +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++@end table +++ +++@item qfThreadInfo +++@itemx qsThreadInfo +++@cindex list active threads, remote request +++@cindex @samp{qfThreadInfo} packet +++@cindex @samp{qsThreadInfo} packet +++Obtain a list of all active thread IDs from the target (OS). Since there +++may be too many active threads to fit into one reply packet, this query +++works iteratively: it may require more than one query/reply sequence to +++obtain the entire list of threads. The first query of the sequence will +++be the @samp{qfThreadInfo} query; subsequent queries in the +++sequence will be the @samp{qsThreadInfo} query. +++ +++NOTE: This packet replaces the @samp{qL} query (see below). +++ +++Reply: +++@table @samp +++@item m @var{thread-id} +++A single thread ID +++@item m @var{thread-id},@var{thread-id}@dots{} +++a comma-separated list of thread IDs +++@item l +++(lower case letter @samp{L}) denotes end of list. +++@end table +++ +++In response to each query, the target will reply with a list of one or +++more thread IDs, separated by commas. +++@value{GDBN} will respond to each reply with a request for more thread +++ids (using the @samp{qs} form of the query), until the target responds +++with @samp{l} (lower-case ell, for @dfn{last}). +++Refer to @ref{thread-id syntax}, for the format of the @var{thread-id} +++fields. +++ +++@emph{Note: @value{GDBN} will send the @code{qfThreadInfo} query during the +++initial connection with the remote target, and the very first thread ID +++mentioned in the reply will be stopped by @value{GDBN} in a subsequent +++message. Therefore, the stub should ensure that the first thread ID in +++the @code{qfThreadInfo} reply is suitable for being stopped by @value{GDBN}.} +++ +++@item qGetTLSAddr:@var{thread-id},@var{offset},@var{lm} +++@cindex get thread-local storage address, remote request +++@cindex @samp{qGetTLSAddr} packet +++Fetch the address associated with thread local storage specified +++by @var{thread-id}, @var{offset}, and @var{lm}. +++ +++@var{thread-id} is the thread ID associated with the +++thread for which to fetch the TLS address. @xref{thread-id syntax}. +++ +++@var{offset} is the (big endian, hex encoded) offset associated with the +++thread local variable. (This offset is obtained from the debug +++information associated with the variable.) +++ +++@var{lm} is the (big endian, hex encoded) OS/ABI-specific encoding of the +++load module associated with the thread local storage. For example, +++a @sc{gnu}/Linux system will pass the link map address of the shared +++object associated with the thread local storage under consideration. +++Other operating environments may choose to represent the load module +++differently, so the precise meaning of this parameter will vary. +++ +++Reply: +++@table @samp +++@item @var{XX}@dots{} +++Hex encoded (big endian) bytes representing the address of the thread +++local storage requested. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{qGetTLSAddr} is not supported by the stub. +++@end table +++ +++@item qGetTIBAddr:@var{thread-id} +++@cindex get thread information block address +++@cindex @samp{qGetTIBAddr} packet +++Fetch address of the Windows OS specific Thread Information Block. +++ +++@var{thread-id} is the thread ID associated with the thread. +++ +++Reply: +++@table @samp +++@item @var{XX}@dots{} +++Hex encoded (big endian) bytes representing the linear address of the +++thread information block. +++ +++@item E @var{nn} +++An error occured. This means that either the thread was not found, or the +++address could not be retrieved. +++ +++@item @w{} +++An empty reply indicates that @samp{qGetTIBAddr} is not supported by the stub. +++@end table +++ +++@item qL @var{startflag} @var{threadcount} @var{nextthread} +++Obtain thread information from RTOS. Where: @var{startflag} (one hex +++digit) is one to indicate the first query and zero to indicate a +++subsequent query; @var{threadcount} (two hex digits) is the maximum +++number of threads the response packet can contain; and @var{nextthread} +++(eight hex digits), for subsequent queries (@var{startflag} is zero), is +++returned in the response as @var{argthread}. +++ +++Don't use this packet; use the @samp{qfThreadInfo} query instead (see above). +++ +++Reply: +++@table @samp +++@item qM @var{count} @var{done} @var{argthread} @var{thread}@dots{} +++Where: @var{count} (two hex digits) is the number of threads being +++returned; @var{done} (one hex digit) is zero to indicate more threads +++and one indicates no further threads; @var{argthreadid} (eight hex +++digits) is @var{nextthread} from the request packet; @var{thread}@dots{} +++is a sequence of thread IDs, @var{threadid} (eight hex +++digits), from the target. See @code{remote.c:parse_threadlist_response()}. +++@end table +++ +++@item qOffsets +++@cindex section offsets, remote request +++@cindex @samp{qOffsets} packet +++Get section offsets that the target used when relocating the downloaded +++image. +++ +++Reply: +++@table @samp +++@item Text=@var{xxx};Data=@var{yyy}@r{[};Bss=@var{zzz}@r{]} +++Relocate the @code{Text} section by @var{xxx} from its original address. +++Relocate the @code{Data} section by @var{yyy} from its original address. +++If the object file format provides segment information (e.g.@: @sc{elf} +++@samp{PT_LOAD} program headers), @value{GDBN} will relocate entire +++segments by the supplied offsets. +++ +++@emph{Note: while a @code{Bss} offset may be included in the response, +++@value{GDBN} ignores this and instead applies the @code{Data} offset +++to the @code{Bss} section.} +++ +++@item TextSeg=@var{xxx}@r{[};DataSeg=@var{yyy}@r{]} +++Relocate the first segment of the object file, which conventionally +++contains program code, to a starting address of @var{xxx}. If +++@samp{DataSeg} is specified, relocate the second segment, which +++conventionally contains modifiable data, to a starting address of +++@var{yyy}. @value{GDBN} will report an error if the object file +++does not contain segment information, or does not contain at least +++as many segments as mentioned in the reply. Extra segments are +++kept at fixed offsets relative to the last relocated segment. +++@end table +++ +++@item qP @var{mode} @var{thread-id} +++@cindex thread information, remote request +++@cindex @samp{qP} packet +++Returns information on @var{thread-id}. Where: @var{mode} is a hex +++encoded 32 bit mode; @var{thread-id} is a thread ID +++(@pxref{thread-id syntax}). +++ +++Don't use this packet; use the @samp{qThreadExtraInfo} query instead +++(see below). +++ +++Reply: see @code{remote.c:remote_unpack_thread_info_response()}. +++ +++@item QNonStop:1 +++@itemx QNonStop:0 +++@cindex non-stop mode, remote request +++@cindex @samp{QNonStop} packet +++@anchor{QNonStop} +++Enter non-stop (@samp{QNonStop:1}) or all-stop (@samp{QNonStop:0}) mode. +++@xref{Remote Non-Stop}, for more information. +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QNonStop} is not supported by +++the stub. +++@end table +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++Use of this packet is controlled by the @code{set non-stop} command; +++@pxref{Non-Stop Mode}. +++ +++@item QCatchSyscalls:1 @r{[};@var{sysno}@r{]}@dots{} +++@itemx QCatchSyscalls:0 +++@cindex catch syscalls from inferior, remote request +++@cindex @samp{QCatchSyscalls} packet +++@anchor{QCatchSyscalls} +++Enable (@samp{QCatchSyscalls:1}) or disable (@samp{QCatchSyscalls:0}) +++catching syscalls from the inferior process. +++ +++For @samp{QCatchSyscalls:1}, each listed syscall @var{sysno} (encoded +++in hex) should be reported to @value{GDBN}. If no syscall @var{sysno} +++is listed, every system call should be reported. +++ +++Note that if a syscall not in the list is reported, @value{GDBN} will +++still filter the event according to its own list from all corresponding +++@code{catch syscall} commands. However, it is more efficient to only +++report the requested syscalls. +++ +++Multiple @samp{QCatchSyscalls:1} packets do not combine; any earlier +++@samp{QCatchSyscalls:1} list is completely replaced by the new list. +++ +++If the inferior process execs, the state of @samp{QCatchSyscalls} is +++kept for the new process too. On targets where exec may affect syscall +++numbers, for example with exec between 32 and 64-bit processes, the +++client should send a new packet with the new syscall list. +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. @var{nn} are hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QCatchSyscalls} is not supported by +++the stub. +++@end table +++ +++Use of this packet is controlled by the @code{set remote catch-syscalls} +++command (@pxref{Remote Configuration, set remote catch-syscalls}). +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item QPassSignals: @var{signal} @r{[};@var{signal}@r{]}@dots{} +++@cindex pass signals to inferior, remote request +++@cindex @samp{QPassSignals} packet +++@anchor{QPassSignals} +++Each listed @var{signal} should be passed directly to the inferior process. +++Signals are numbered identically to continue packets and stop replies +++(@pxref{Stop Reply Packets}). Each @var{signal} list item should be +++strictly greater than the previous item. These signals do not need to stop +++the inferior, or be reported to @value{GDBN}. All other signals should be +++reported to @value{GDBN}. Multiple @samp{QPassSignals} packets do not +++combine; any earlier @samp{QPassSignals} list is completely replaced by the +++new list. This packet improves performance when using @samp{handle +++@var{signal} nostop noprint pass}. +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QPassSignals} is not supported by +++the stub. +++@end table +++ +++Use of this packet is controlled by the @code{set remote pass-signals} +++command (@pxref{Remote Configuration, set remote pass-signals}). +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item QProgramSignals: @var{signal} @r{[};@var{signal}@r{]}@dots{} +++@cindex signals the inferior may see, remote request +++@cindex @samp{QProgramSignals} packet +++@anchor{QProgramSignals} +++Each listed @var{signal} may be delivered to the inferior process. +++Others should be silently discarded. +++ +++In some cases, the remote stub may need to decide whether to deliver a +++signal to the program or not without @value{GDBN} involvement. One +++example of that is while detaching --- the program's threads may have +++stopped for signals that haven't yet had a chance of being reported to +++@value{GDBN}, and so the remote stub can use the signal list specified +++by this packet to know whether to deliver or ignore those pending +++signals. +++ +++This does not influence whether to deliver a signal as requested by a +++resumption packet (@pxref{vCont packet}). +++ +++Signals are numbered identically to continue packets and stop replies +++(@pxref{Stop Reply Packets}). Each @var{signal} list item should be +++strictly greater than the previous item. Multiple +++@samp{QProgramSignals} packets do not combine; any earlier +++@samp{QProgramSignals} list is completely replaced by the new list. +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QProgramSignals} is not supported +++by the stub. +++@end table +++ +++Use of this packet is controlled by the @code{set remote program-signals} +++command (@pxref{Remote Configuration, set remote program-signals}). +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@anchor{QThreadEvents} +++@item QThreadEvents:1 +++@itemx QThreadEvents:0 +++@cindex thread create/exit events, remote request +++@cindex @samp{QThreadEvents} packet +++ +++Enable (@samp{QThreadEvents:1}) or disable (@samp{QThreadEvents:0}) +++reporting of thread create and exit events. @xref{thread create +++event}, for the reply specifications. For example, this is used in +++non-stop mode when @value{GDBN} stops a set of threads and +++synchronously waits for the their corresponding stop replies. Without +++exit events, if one of the threads exits, @value{GDBN} would hang +++forever not knowing that it should no longer expect a stop for that +++same thread. @value{GDBN} does not enable this feature unless the +++stub reports that it supports it by including @samp{QThreadEvents+} in +++its @samp{qSupported} reply. +++ +++Reply: +++@table @samp +++@item OK +++The request succeeded. +++ +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++ +++@item @w{} +++An empty reply indicates that @samp{QThreadEvents} is not supported by +++the stub. +++@end table +++ +++Use of this packet is controlled by the @code{set remote thread-events} +++command (@pxref{Remote Configuration, set remote thread-events}). +++ +++@item qRcmd,@var{command} +++@cindex execute remote command, remote request +++@cindex @samp{qRcmd} packet +++@var{command} (hex encoded) is passed to the local interpreter for +++execution. Invalid commands should be reported using the output +++string. Before the final result packet, the target may also respond +++with a number of intermediate @samp{O@var{output}} console output +++packets. @emph{Implementors should note that providing access to a +++stubs's interpreter may have security implications}. +++ +++Reply: +++@table @samp +++@item OK +++A command response with no output. +++@item @var{OUTPUT} +++A command response with the hex encoded output string @var{OUTPUT}. +++@item E @var{NN} +++Indicate a badly formed request. +++@item @w{} +++An empty reply indicates that @samp{qRcmd} is not recognized. +++@end table +++ +++(Note that the @code{qRcmd} packet's name is separated from the +++command by a @samp{,}, not a @samp{:}, contrary to the naming +++conventions above. Please don't use this packet as a model for new +++packets.) +++ +++@item qSearch:memory:@var{address};@var{length};@var{search-pattern} +++@cindex searching memory, in remote debugging +++@ifnotinfo +++@cindex @samp{qSearch:memory} packet +++@end ifnotinfo +++@cindex @samp{qSearch memory} packet +++@anchor{qSearch memory} +++Search @var{length} bytes at @var{address} for @var{search-pattern}. +++Both @var{address} and @var{length} are encoded in hex; +++@var{search-pattern} is a sequence of bytes, also hex encoded. +++ +++Reply: +++@table @samp +++@item 0 +++The pattern was not found. +++@item 1,address +++The pattern was found at @var{address}. +++@item E @var{NN} +++A badly formed request or an error was encountered while searching memory. +++@item @w{} +++An empty reply indicates that @samp{qSearch:memory} is not recognized. +++@end table +++ +++@item QStartNoAckMode +++@cindex @samp{QStartNoAckMode} packet +++@anchor{QStartNoAckMode} +++Request that the remote stub disable the normal @samp{+}/@samp{-} +++protocol acknowledgments (@pxref{Packet Acknowledgment}). +++ +++Reply: +++@table @samp +++@item OK +++The stub has switched to no-acknowledgment mode. +++@value{GDBN} acknowledges this response, +++but neither the stub nor @value{GDBN} shall send or expect further +++@samp{+}/@samp{-} acknowledgments in the current connection. +++@item @w{} +++An empty reply indicates that the stub does not support no-acknowledgment mode. +++@end table +++ +++@item qSupported @r{[}:@var{gdbfeature} @r{[};@var{gdbfeature}@r{]}@dots{} @r{]} +++@cindex supported packets, remote query +++@cindex features of the remote protocol +++@cindex @samp{qSupported} packet +++@anchor{qSupported} +++Tell the remote stub about features supported by @value{GDBN}, and +++query the stub for features it supports. This packet allows +++@value{GDBN} and the remote stub to take advantage of each others' +++features. @samp{qSupported} also consolidates multiple feature probes +++at startup, to improve @value{GDBN} performance---a single larger +++packet performs better than multiple smaller probe packets on +++high-latency links. Some features may enable behavior which must not +++be on by default, e.g.@: because it would confuse older clients or +++stubs. Other features may describe packets which could be +++automatically probed for, but are not. These features must be +++reported before @value{GDBN} will use them. This ``default +++unsupported'' behavior is not appropriate for all packets, but it +++helps to keep the initial connection time under control with new +++versions of @value{GDBN} which support increasing numbers of packets. +++ +++Reply: +++@table @samp +++@item @var{stubfeature} @r{[};@var{stubfeature}@r{]}@dots{} +++The stub supports or does not support each returned @var{stubfeature}, +++depending on the form of each @var{stubfeature} (see below for the +++possible forms). +++@item @w{} +++An empty reply indicates that @samp{qSupported} is not recognized, +++or that no features needed to be reported to @value{GDBN}. +++@end table +++ +++The allowed forms for each feature (either a @var{gdbfeature} in the +++@samp{qSupported} packet, or a @var{stubfeature} in the response) +++are: +++ +++@table @samp +++@item @var{name}=@var{value} +++The remote protocol feature @var{name} is supported, and associated +++with the specified @var{value}. The format of @var{value} depends +++on the feature, but it must not include a semicolon. +++@item @var{name}+ +++The remote protocol feature @var{name} is supported, and does not +++need an associated value. +++@item @var{name}- +++The remote protocol feature @var{name} is not supported. +++@item @var{name}? +++The remote protocol feature @var{name} may be supported, and +++@value{GDBN} should auto-detect support in some other way when it is +++needed. This form will not be used for @var{gdbfeature} notifications, +++but may be used for @var{stubfeature} responses. +++@end table +++ +++Whenever the stub receives a @samp{qSupported} request, the +++supplied set of @value{GDBN} features should override any previous +++request. This allows @value{GDBN} to put the stub in a known +++state, even if the stub had previously been communicating with +++a different version of @value{GDBN}. +++ +++The following values of @var{gdbfeature} (for the packet sent by @value{GDBN}) +++are defined: +++ +++@table @samp +++@item multiprocess +++This feature indicates whether @value{GDBN} supports multiprocess +++extensions to the remote protocol. @value{GDBN} does not use such +++extensions unless the stub also reports that it supports them by +++including @samp{multiprocess+} in its @samp{qSupported} reply. +++@xref{multiprocess extensions}, for details. +++ +++@item xmlRegisters +++This feature indicates that @value{GDBN} supports the XML target +++description. If the stub sees @samp{xmlRegisters=} with target +++specific strings separated by a comma, it will report register +++description. +++ +++@item qRelocInsn +++This feature indicates whether @value{GDBN} supports the +++@samp{qRelocInsn} packet (@pxref{Tracepoint Packets,,Relocate +++instruction reply packet}). +++ +++@item swbreak +++This feature indicates whether @value{GDBN} supports the swbreak stop +++reason in stop replies. @xref{swbreak stop reason}, for details. +++ +++@item hwbreak +++This feature indicates whether @value{GDBN} supports the hwbreak stop +++reason in stop replies. @xref{swbreak stop reason}, for details. +++ +++@item fork-events +++This feature indicates whether @value{GDBN} supports fork event +++extensions to the remote protocol. @value{GDBN} does not use such +++extensions unless the stub also reports that it supports them by +++including @samp{fork-events+} in its @samp{qSupported} reply. +++ +++@item vfork-events +++This feature indicates whether @value{GDBN} supports vfork event +++extensions to the remote protocol. @value{GDBN} does not use such +++extensions unless the stub also reports that it supports them by +++including @samp{vfork-events+} in its @samp{qSupported} reply. +++ +++@item exec-events +++This feature indicates whether @value{GDBN} supports exec event +++extensions to the remote protocol. @value{GDBN} does not use such +++extensions unless the stub also reports that it supports them by +++including @samp{exec-events+} in its @samp{qSupported} reply. +++ +++@item vContSupported +++This feature indicates whether @value{GDBN} wants to know the +++supported actions in the reply to @samp{vCont?} packet. +++@end table +++ +++Stubs should ignore any unknown values for +++@var{gdbfeature}. Any @value{GDBN} which sends a @samp{qSupported} +++packet supports receiving packets of unlimited length (earlier +++versions of @value{GDBN} may reject overly long responses). Additional values +++for @var{gdbfeature} may be defined in the future to let the stub take +++advantage of new features in @value{GDBN}, e.g.@: incompatible +++improvements in the remote protocol---the @samp{multiprocess} feature is +++an example of such a feature. The stub's reply should be independent +++of the @var{gdbfeature} entries sent by @value{GDBN}; first @value{GDBN} +++describes all the features it supports, and then the stub replies with +++all the features it supports. +++ +++Similarly, @value{GDBN} will silently ignore unrecognized stub feature +++responses, as long as each response uses one of the standard forms. +++ +++Some features are flags. A stub which supports a flag feature +++should respond with a @samp{+} form response. Other features +++require values, and the stub should respond with an @samp{=} +++form response. +++ +++Each feature has a default value, which @value{GDBN} will use if +++@samp{qSupported} is not available or if the feature is not mentioned +++in the @samp{qSupported} response. The default values are fixed; a +++stub is free to omit any feature responses that match the defaults. +++ +++Not all features can be probed, but for those which can, the probing +++mechanism is useful: in some cases, a stub's internal +++architecture may not allow the protocol layer to know some information +++about the underlying target in advance. This is especially common in +++stubs which may be configured for multiple targets. +++ +++These are the currently defined stub features and their properties: +++ +++@multitable @columnfractions 0.35 0.2 0.12 0.2 +++@c NOTE: The first row should be @headitem, but we do not yet require +++@c a new enough version of Texinfo (4.7) to use @headitem. +++@item Feature Name +++@tab Value Required +++@tab Default +++@tab Probe Allowed +++ +++@item @samp{PacketSize} +++@tab Yes +++@tab @samp{-} +++@tab No +++ +++@item @samp{qXfer:auxv:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:btrace:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:btrace-conf:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:exec-file:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:features:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:libraries:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:libraries-svr4:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{augmented-libraries-svr4-read} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{qXfer:memory-map:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:sdata:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:siginfo:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:siginfo:write} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:threads:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:traceframe-info:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:uib:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{qXfer:fdpic:read} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{Qbtrace:off} +++@tab Yes +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{Qbtrace:bts} +++@tab Yes +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{Qbtrace:pt} +++@tab Yes +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{Qbtrace-conf:bts:size} +++@tab Yes +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{Qbtrace-conf:pt:size} +++@tab Yes +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{QNonStop} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{QCatchSyscalls} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{QPassSignals} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{QStartNoAckMode} +++@tab No +++@tab @samp{-} +++@tab Yes +++ +++@item @samp{multiprocess} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{ConditionalBreakpoints} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{ConditionalTracepoints} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{ReverseContinue} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{ReverseStep} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{TracepointSource} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{QAgent} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{QAllow} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{QDisableRandomization} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{EnableDisableTracepoints} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{QTBuffer:size} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{tracenz} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{BreakpointCommands} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{swbreak} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{hwbreak} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{fork-events} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{vfork-events} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{exec-events} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{QThreadEvents} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@item @samp{no-resumed} +++@tab No +++@tab @samp{-} +++@tab No +++ +++@end multitable +++ +++These are the currently defined stub features, in more detail: +++ +++@table @samp +++@cindex packet size, remote protocol +++@item PacketSize=@var{bytes} +++The remote stub can accept packets up to at least @var{bytes} in +++length. @value{GDBN} will send packets up to this size for bulk +++transfers, and will never send larger packets. This is a limit on the +++data characters in the packet, including the frame and checksum. +++There is no trailing NUL byte in a remote protocol packet; if the stub +++stores packets in a NUL-terminated format, it should allow an extra +++byte in its buffer for the NUL. If this stub feature is not supported, +++@value{GDBN} guesses based on the size of the @samp{g} packet response. +++ +++@item qXfer:auxv:read +++The remote stub understands the @samp{qXfer:auxv:read} packet +++(@pxref{qXfer auxiliary vector read}). +++ +++@item qXfer:btrace:read +++The remote stub understands the @samp{qXfer:btrace:read} +++packet (@pxref{qXfer btrace read}). +++ +++@item qXfer:btrace-conf:read +++The remote stub understands the @samp{qXfer:btrace-conf:read} +++packet (@pxref{qXfer btrace-conf read}). +++ +++@item qXfer:exec-file:read +++The remote stub understands the @samp{qXfer:exec-file:read} packet +++(@pxref{qXfer executable filename read}). +++ +++@item qXfer:features:read +++The remote stub understands the @samp{qXfer:features:read} packet +++(@pxref{qXfer target description read}). +++ +++@item qXfer:libraries:read +++The remote stub understands the @samp{qXfer:libraries:read} packet +++(@pxref{qXfer library list read}). +++ +++@item qXfer:libraries-svr4:read +++The remote stub understands the @samp{qXfer:libraries-svr4:read} packet +++(@pxref{qXfer svr4 library list read}). +++ +++@item augmented-libraries-svr4-read +++The remote stub understands the augmented form of the +++@samp{qXfer:libraries-svr4:read} packet +++(@pxref{qXfer svr4 library list read}). +++ +++@item qXfer:memory-map:read +++The remote stub understands the @samp{qXfer:memory-map:read} packet +++(@pxref{qXfer memory map read}). +++ +++@item qXfer:sdata:read +++The remote stub understands the @samp{qXfer:sdata:read} packet +++(@pxref{qXfer sdata read}). +++ +++@item qXfer:siginfo:read +++The remote stub understands the @samp{qXfer:siginfo:read} packet +++(@pxref{qXfer siginfo read}). +++ +++@item qXfer:siginfo:write +++The remote stub understands the @samp{qXfer:siginfo:write} packet +++(@pxref{qXfer siginfo write}). +++ +++@item qXfer:threads:read +++The remote stub understands the @samp{qXfer:threads:read} packet +++(@pxref{qXfer threads read}). +++ +++@item qXfer:traceframe-info:read +++The remote stub understands the @samp{qXfer:traceframe-info:read} +++packet (@pxref{qXfer traceframe info read}). +++ +++@item qXfer:uib:read +++The remote stub understands the @samp{qXfer:uib:read} +++packet (@pxref{qXfer unwind info block}). +++ +++@item qXfer:fdpic:read +++The remote stub understands the @samp{qXfer:fdpic:read} +++packet (@pxref{qXfer fdpic loadmap read}). +++ +++@item QNonStop +++The remote stub understands the @samp{QNonStop} packet +++(@pxref{QNonStop}). +++ +++@item QCatchSyscalls +++The remote stub understands the @samp{QCatchSyscalls} packet +++(@pxref{QCatchSyscalls}). +++ +++@item QPassSignals +++The remote stub understands the @samp{QPassSignals} packet +++(@pxref{QPassSignals}). +++ +++@item QStartNoAckMode +++The remote stub understands the @samp{QStartNoAckMode} packet and +++prefers to operate in no-acknowledgment mode. @xref{Packet Acknowledgment}. +++ +++@item multiprocess +++@anchor{multiprocess extensions} +++@cindex multiprocess extensions, in remote protocol +++The remote stub understands the multiprocess extensions to the remote +++protocol syntax. The multiprocess extensions affect the syntax of +++thread IDs in both packets and replies (@pxref{thread-id syntax}), and +++add process IDs to the @samp{D} packet and @samp{W} and @samp{X} +++replies. Note that reporting this feature indicates support for the +++syntactic extensions only, not that the stub necessarily supports +++debugging of more than one process at a time. The stub must not use +++multiprocess extensions in packet replies unless @value{GDBN} has also +++indicated it supports them in its @samp{qSupported} request. +++ +++@item qXfer:osdata:read +++The remote stub understands the @samp{qXfer:osdata:read} packet +++((@pxref{qXfer osdata read}). +++ +++@item ConditionalBreakpoints +++The target accepts and implements evaluation of conditional expressions +++defined for breakpoints. The target will only report breakpoint triggers +++when such conditions are true (@pxref{Conditions, ,Break Conditions}). +++ +++@item ConditionalTracepoints +++The remote stub accepts and implements conditional expressions defined +++for tracepoints (@pxref{Tracepoint Conditions}). +++ +++@item ReverseContinue +++The remote stub accepts and implements the reverse continue packet +++(@pxref{bc}). +++ +++@item ReverseStep +++The remote stub accepts and implements the reverse step packet +++(@pxref{bs}). +++ +++@item TracepointSource +++The remote stub understands the @samp{QTDPsrc} packet that supplies +++the source form of tracepoint definitions. +++ +++@item QAgent +++The remote stub understands the @samp{QAgent} packet. +++ +++@item QAllow +++The remote stub understands the @samp{QAllow} packet. +++ +++@item QDisableRandomization +++The remote stub understands the @samp{QDisableRandomization} packet. +++ +++@item StaticTracepoint +++@cindex static tracepoints, in remote protocol +++The remote stub supports static tracepoints. +++ +++@item InstallInTrace +++@anchor{install tracepoint in tracing} +++The remote stub supports installing tracepoint in tracing. +++ +++@item EnableDisableTracepoints +++The remote stub supports the @samp{QTEnable} (@pxref{QTEnable}) and +++@samp{QTDisable} (@pxref{QTDisable}) packets that allow tracepoints +++to be enabled and disabled while a trace experiment is running. +++ +++@item QTBuffer:size +++The remote stub supports the @samp{QTBuffer:size} (@pxref{QTBuffer-size}) +++packet that allows to change the size of the trace buffer. +++ +++@item tracenz +++@cindex string tracing, in remote protocol +++The remote stub supports the @samp{tracenz} bytecode for collecting strings. +++See @ref{Bytecode Descriptions} for details about the bytecode. +++ +++@item BreakpointCommands +++@cindex breakpoint commands, in remote protocol +++The remote stub supports running a breakpoint's command list itself, +++rather than reporting the hit to @value{GDBN}. +++ +++@item Qbtrace:off +++The remote stub understands the @samp{Qbtrace:off} packet. +++ +++@item Qbtrace:bts +++The remote stub understands the @samp{Qbtrace:bts} packet. +++ +++@item Qbtrace:pt +++The remote stub understands the @samp{Qbtrace:pt} packet. +++ +++@item Qbtrace-conf:bts:size +++The remote stub understands the @samp{Qbtrace-conf:bts:size} packet. +++ +++@item Qbtrace-conf:pt:size +++The remote stub understands the @samp{Qbtrace-conf:pt:size} packet. +++ +++@item swbreak +++The remote stub reports the @samp{swbreak} stop reason for memory +++breakpoints. +++ +++@item hwbreak +++The remote stub reports the @samp{hwbreak} stop reason for hardware +++breakpoints. +++ +++@item fork-events +++The remote stub reports the @samp{fork} stop reason for fork events. +++ +++@item vfork-events +++The remote stub reports the @samp{vfork} stop reason for vfork events +++and vforkdone events. +++ +++@item exec-events +++The remote stub reports the @samp{exec} stop reason for exec events. +++ +++@item vContSupported +++The remote stub reports the supported actions in the reply to +++@samp{vCont?} packet. +++ +++@item QThreadEvents +++The remote stub understands the @samp{QThreadEvents} packet. +++ +++@item no-resumed +++The remote stub reports the @samp{N} stop reply. +++ +++@end table +++ +++@item qSymbol:: +++@cindex symbol lookup, remote request +++@cindex @samp{qSymbol} packet +++Notify the target that @value{GDBN} is prepared to serve symbol lookup +++requests. Accept requests from the target for the values of symbols. +++ +++Reply: +++@table @samp +++@item OK +++The target does not need to look up any (more) symbols. +++@item qSymbol:@var{sym_name} +++The target requests the value of symbol @var{sym_name} (hex encoded). +++@value{GDBN} may provide the value by using the +++@samp{qSymbol:@var{sym_value}:@var{sym_name}} message, described +++below. +++@end table +++ +++@item qSymbol:@var{sym_value}:@var{sym_name} +++Set the value of @var{sym_name} to @var{sym_value}. +++ +++@var{sym_name} (hex encoded) is the name of a symbol whose value the +++target has previously requested. +++ +++@var{sym_value} (hex) is the value for symbol @var{sym_name}. If +++@value{GDBN} cannot supply a value for @var{sym_name}, then this field +++will be empty. +++ +++Reply: +++@table @samp +++@item OK +++The target does not need to look up any (more) symbols. +++@item qSymbol:@var{sym_name} +++The target requests the value of a new symbol @var{sym_name} (hex +++encoded). @value{GDBN} will continue to supply the values of symbols +++(if available), until the target ceases to request them. +++@end table +++ +++@item qTBuffer +++@itemx QTBuffer +++@itemx QTDisconnected +++@itemx QTDP +++@itemx QTDPsrc +++@itemx QTDV +++@itemx qTfP +++@itemx qTfV +++@itemx QTFrame +++@itemx qTMinFTPILen +++ +++@xref{Tracepoint Packets}. +++ +++@item qThreadExtraInfo,@var{thread-id} +++@cindex thread attributes info, remote request +++@cindex @samp{qThreadExtraInfo} packet +++Obtain from the target OS a printable string description of thread +++attributes for the thread @var{thread-id}; see @ref{thread-id syntax}, +++for the forms of @var{thread-id}. This +++string may contain anything that the target OS thinks is interesting +++for @value{GDBN} to tell the user about the thread. The string is +++displayed in @value{GDBN}'s @code{info threads} display. Some +++examples of possible thread extra info strings are @samp{Runnable}, or +++@samp{Blocked on Mutex}. +++ +++Reply: +++@table @samp +++@item @var{XX}@dots{} +++Where @samp{@var{XX}@dots{}} is a hex encoding of @sc{ascii} data, +++comprising the printable string containing the extra information about +++the thread's attributes. +++@end table +++ +++(Note that the @code{qThreadExtraInfo} packet's name is separated from +++the command by a @samp{,}, not a @samp{:}, contrary to the naming +++conventions above. Please don't use this packet as a model for new +++packets.) +++ +++@item QTNotes +++@itemx qTP +++@itemx QTSave +++@itemx qTsP +++@itemx qTsV +++@itemx QTStart +++@itemx QTStop +++@itemx QTEnable +++@itemx QTDisable +++@itemx QTinit +++@itemx QTro +++@itemx qTStatus +++@itemx qTV +++@itemx qTfSTM +++@itemx qTsSTM +++@itemx qTSTMat +++@xref{Tracepoint Packets}. +++ +++@item qXfer:@var{object}:read:@var{annex}:@var{offset},@var{length} +++@cindex read special object, remote request +++@cindex @samp{qXfer} packet +++@anchor{qXfer read} +++Read uninterpreted bytes from the target's special data area +++identified by the keyword @var{object}. Request @var{length} bytes +++starting at @var{offset} bytes into the data. The content and +++encoding of @var{annex} is specific to @var{object}; it can supply +++additional details about what data to access. +++ +++Reply: +++@table @samp +++@item m @var{data} +++Data @var{data} (@pxref{Binary Data}) has been read from the +++target. There may be more data at a higher address (although +++it is permitted to return @samp{m} even for the last valid +++block of data, as long as at least one byte of data was read). +++It is possible for @var{data} to have fewer bytes than the @var{length} in the +++request. +++ +++@item l @var{data} +++Data @var{data} (@pxref{Binary Data}) has been read from the target. +++There is no more data to be read. It is possible for @var{data} to +++have fewer bytes than the @var{length} in the request. +++ +++@item l +++The @var{offset} in the request is at the end of the data. +++There is no more data to be read. +++ +++@item E00 +++The request was malformed, or @var{annex} was invalid. +++ +++@item E @var{nn} +++The offset was invalid, or there was an error encountered reading the data. +++The @var{nn} part is a hex-encoded @code{errno} value. +++ +++@item @w{} +++An empty reply indicates the @var{object} string was not recognized by +++the stub, or that the object does not support reading. +++@end table +++ +++Here are the specific requests of this form defined so far. All the +++@samp{qXfer:@var{object}:read:@dots{}} requests use the same reply +++formats, listed above. +++ +++@table @samp +++@item qXfer:auxv:read::@var{offset},@var{length} +++@anchor{qXfer auxiliary vector read} +++Access the target's @dfn{auxiliary vector}. @xref{OS Information, +++auxiliary vector}. Note @var{annex} must be empty. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:btrace:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer btrace read} +++ +++Return a description of the current branch trace. +++@xref{Branch Trace Format}. The annex part of the generic @samp{qXfer} +++packet may have one of the following values: +++ +++@table @code +++@item all +++Returns all available branch trace. +++ +++@item new +++Returns all available branch trace if the branch trace changed since +++the last read request. +++ +++@item delta +++Returns the new branch trace since the last read request. Adds a new +++block to the end of the trace that begins at zero and ends at the source +++location of the first branch in the trace buffer. This extra block is +++used to stitch traces together. +++ +++If the trace buffer overflowed, returns an error indicating the overflow. +++@end table +++ +++This packet is not probed by default; the remote stub must request it +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:btrace-conf:read::@var{offset},@var{length} +++@anchor{qXfer btrace-conf read} +++ +++Return a description of the current branch trace configuration. +++@xref{Branch Trace Configuration Format}. +++ +++This packet is not probed by default; the remote stub must request it +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:exec-file:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer executable filename read} +++Return the full absolute name of the file that was executed to create +++a process running on the remote system. The annex specifies the +++numeric process ID of the process to query, encoded as a hexadecimal +++number. If the annex part is empty the remote stub should return the +++filename corresponding to the currently executing process. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:features:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer target description read} +++Access the @dfn{target description}. @xref{Target Descriptions}. The +++annex specifies which XML document to access. The main description is +++always loaded from the @samp{target.xml} annex. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:libraries:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer library list read} +++Access the target's list of loaded libraries. @xref{Library List Format}. +++The annex part of the generic @samp{qXfer} packet must be empty +++(@pxref{qXfer read}). +++ +++Targets which maintain a list of libraries in the program's memory do +++not need to implement this packet; it is designed for platforms where +++the operating system manages the list of loaded libraries. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:libraries-svr4:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer svr4 library list read} +++Access the target's list of loaded libraries when the target is an SVR4 +++platform. @xref{Library List Format for SVR4 Targets}. The annex part +++of the generic @samp{qXfer} packet must be empty unless the remote +++stub indicated it supports the augmented form of this packet +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qXfer read}, @ref{qSupported}). +++ +++This packet is optional for better performance on SVR4 targets. +++@value{GDBN} uses memory read packets to read the SVR4 library list otherwise. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++If the remote stub indicates it supports the augmented form of this +++packet then the annex part of the generic @samp{qXfer} packet may +++contain a semicolon-separated list of @samp{@var{name}=@var{value}} +++arguments. The currently supported arguments are: +++ +++@table @code +++@item start=@var{address} +++A hexadecimal number specifying the address of the @samp{struct +++link_map} to start reading the library list from. If unset or zero +++then the first @samp{struct link_map} in the library list will be +++chosen as the starting point. +++ +++@item prev=@var{address} +++A hexadecimal number specifying the address of the @samp{struct +++link_map} immediately preceding the @samp{struct link_map} +++specified by the @samp{start} argument. If unset or zero then +++the remote stub will expect that no @samp{struct link_map} +++exists prior to the starting point. +++ +++@end table +++ +++Arguments that are not understood by the remote stub will be silently +++ignored. +++ +++@item qXfer:memory-map:read::@var{offset},@var{length} +++@anchor{qXfer memory map read} +++Access the target's @dfn{memory-map}. @xref{Memory Map Format}. The +++annex part of the generic @samp{qXfer} packet must be empty +++(@pxref{qXfer read}). +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:sdata:read::@var{offset},@var{length} +++@anchor{qXfer sdata read} +++ +++Read contents of the extra collected static tracepoint marker +++information. The annex part of the generic @samp{qXfer} packet must +++be empty (@pxref{qXfer read}). @xref{Tracepoint Actions,,Tracepoint +++Action Lists}. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). +++ +++@item qXfer:siginfo:read::@var{offset},@var{length} +++@anchor{qXfer siginfo read} +++Read contents of the extra signal information on the target +++system. The annex part of the generic @samp{qXfer} packet must be +++empty (@pxref{qXfer read}). +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). +++ +++@item qXfer:threads:read::@var{offset},@var{length} +++@anchor{qXfer threads read} +++Access the list of threads on target. @xref{Thread List Format}. The +++annex part of the generic @samp{qXfer} packet must be empty +++(@pxref{qXfer read}). +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:traceframe-info:read::@var{offset},@var{length} +++@anchor{qXfer traceframe info read} +++ +++Return a description of the current traceframe's contents. +++@xref{Traceframe Info Format}. The annex part of the generic +++@samp{qXfer} packet must be empty (@pxref{qXfer read}). +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:uib:read:@var{pc}:@var{offset},@var{length} +++@anchor{qXfer unwind info block} +++ +++Return the unwind information block for @var{pc}. This packet is used +++on OpenVMS/ia64 to ask the kernel unwind information. +++ +++This packet is not probed by default. +++ +++@item qXfer:fdpic:read:@var{annex}:@var{offset},@var{length} +++@anchor{qXfer fdpic loadmap read} +++Read contents of @code{loadmap}s on the target system. The +++annex, either @samp{exec} or @samp{interp}, specifies which @code{loadmap}, +++executable @code{loadmap} or interpreter @code{loadmap} to read. +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response (@pxref{qSupported}). +++ +++@item qXfer:osdata:read::@var{offset},@var{length} +++@anchor{qXfer osdata read} +++Access the target's @dfn{operating system information}. +++@xref{Operating System Information}. +++ +++@end table +++ +++@item qXfer:@var{object}:write:@var{annex}:@var{offset}:@var{data}@dots{} +++@cindex write data into object, remote request +++@anchor{qXfer write} +++Write uninterpreted bytes into the target's special data area +++identified by the keyword @var{object}, starting at @var{offset} bytes +++into the data. The binary-encoded data (@pxref{Binary Data}) to be +++written is given by @var{data}@dots{}. The content and encoding of @var{annex} +++is specific to @var{object}; it can supply additional details about what data +++to access. +++ +++Reply: +++@table @samp +++@item @var{nn} +++@var{nn} (hex encoded) is the number of bytes written. +++This may be fewer bytes than supplied in the request. +++ +++@item E00 +++The request was malformed, or @var{annex} was invalid. +++ +++@item E @var{nn} +++The offset was invalid, or there was an error encountered writing the data. +++The @var{nn} part is a hex-encoded @code{errno} value. +++ +++@item @w{} +++An empty reply indicates the @var{object} string was not +++recognized by the stub, or that the object does not support writing. +++@end table +++ +++Here are the specific requests of this form defined so far. All the +++@samp{qXfer:@var{object}:write:@dots{}} requests use the same reply +++formats, listed above. +++ +++@table @samp +++@item qXfer:siginfo:write::@var{offset}:@var{data}@dots{} +++@anchor{qXfer siginfo write} +++Write @var{data} to the extra signal information on the target system. +++The annex part of the generic @samp{qXfer} packet must be +++empty (@pxref{qXfer write}). +++ +++This packet is not probed by default; the remote stub must request it, +++by supplying an appropriate @samp{qSupported} response +++(@pxref{qSupported}). +++@end table +++ +++@item qXfer:@var{object}:@var{operation}:@dots{} +++Requests of this form may be added in the future. When a stub does +++not recognize the @var{object} keyword, or its support for +++@var{object} does not recognize the @var{operation} keyword, the stub +++must respond with an empty packet. +++ +++@item qAttached:@var{pid} +++@cindex query attached, remote request +++@cindex @samp{qAttached} packet +++Return an indication of whether the remote server attached to an +++existing process or created a new process. When the multiprocess +++protocol extensions are supported (@pxref{multiprocess extensions}), +++@var{pid} is an integer in hexadecimal format identifying the target +++process. Otherwise, @value{GDBN} will omit the @var{pid} field and +++the query packet will be simplified as @samp{qAttached}. +++ +++This query is used, for example, to know whether the remote process +++should be detached or killed when a @value{GDBN} session is ended with +++the @code{quit} command. +++ +++Reply: +++@table @samp +++@item 1 +++The remote server attached to an existing process. +++@item 0 +++The remote server created a new process. +++@item E @var{NN} +++A badly formed request or an error was encountered. +++@end table +++ +++@item Qbtrace:bts +++Enable branch tracing for the current thread using Branch Trace Store. +++ +++Reply: +++@table @samp +++@item OK +++Branch tracing has been enabled. +++@item E.errtext +++A badly formed request or an error was encountered. +++@end table +++ +++@item Qbtrace:pt +++Enable branch tracing for the current thread using Intel Processor Trace. +++ +++Reply: +++@table @samp +++@item OK +++Branch tracing has been enabled. +++@item E.errtext +++A badly formed request or an error was encountered. +++@end table +++ +++@item Qbtrace:off +++Disable branch tracing for the current thread. +++ +++Reply: +++@table @samp +++@item OK +++Branch tracing has been disabled. +++@item E.errtext +++A badly formed request or an error was encountered. +++@end table +++ +++@item Qbtrace-conf:bts:size=@var{value} +++Set the requested ring buffer size for new threads that use the +++btrace recording method in bts format. +++ +++Reply: +++@table @samp +++@item OK +++The ring buffer size has been set. +++@item E.errtext +++A badly formed request or an error was encountered. +++@end table +++ +++@item Qbtrace-conf:pt:size=@var{value} +++Set the requested ring buffer size for new threads that use the +++btrace recording method in pt format. +++ +++Reply: +++@table @samp +++@item OK +++The ring buffer size has been set. +++@item E.errtext +++A badly formed request or an error was encountered. +++@end table +++ +++@end table +++ +++@node Architecture-Specific Protocol Details +++@section Architecture-Specific Protocol Details +++ +++This section describes how the remote protocol is applied to specific +++target architectures. Also see @ref{Standard Target Features}, for +++details of XML target descriptions for each architecture. +++ +++@menu +++* ARM-Specific Protocol Details:: +++* MIPS-Specific Protocol Details:: +++@end menu +++ +++@node ARM-Specific Protocol Details +++@subsection @acronym{ARM}-specific Protocol Details +++ +++@menu +++* ARM Breakpoint Kinds:: +++@end menu +++ +++@node ARM Breakpoint Kinds +++@subsubsection @acronym{ARM} Breakpoint Kinds +++@cindex breakpoint kinds, @acronym{ARM} +++ +++These breakpoint kinds are defined for the @samp{Z0} and @samp{Z1} packets. +++ +++@table @r +++ +++@item 2 +++16-bit Thumb mode breakpoint. +++ +++@item 3 +++32-bit Thumb mode (Thumb-2) breakpoint. +++ +++@item 4 +++32-bit @acronym{ARM} mode breakpoint. +++ +++@end table +++ +++@node MIPS-Specific Protocol Details +++@subsection @acronym{MIPS}-specific Protocol Details +++ +++@menu +++* MIPS Register packet Format:: +++* MIPS Breakpoint Kinds:: +++@end menu +++ +++@node MIPS Register packet Format +++@subsubsection @acronym{MIPS} Register Packet Format +++@cindex register packet format, @acronym{MIPS} +++ +++The following @code{g}/@code{G} packets have previously been defined. +++In the below, some thirty-two bit registers are transferred as +++sixty-four bits. Those registers should be zero/sign extended (which?) +++to fill the space allocated. Register bytes are transferred in target +++byte order. The two nibbles within a register byte are transferred +++most-significant -- least-significant. +++ +++@table @r +++ +++@item MIPS32 +++All registers are transferred as thirty-two bit quantities in the order: +++32 general-purpose; sr; lo; hi; bad; cause; pc; 32 floating-point +++registers; fsr; fir; fp. +++ +++@item MIPS64 +++All registers are transferred as sixty-four bit quantities (including +++thirty-two bit registers such as @code{sr}). The ordering is the same +++as @code{MIPS32}. +++ +++@end table +++ +++@node MIPS Breakpoint Kinds +++@subsubsection @acronym{MIPS} Breakpoint Kinds +++@cindex breakpoint kinds, @acronym{MIPS} +++ +++These breakpoint kinds are defined for the @samp{Z0} and @samp{Z1} packets. +++ +++@table @r +++ +++@item 2 +++16-bit @acronym{MIPS16} mode breakpoint. +++ +++@item 3 +++16-bit @acronym{microMIPS} mode breakpoint. +++ +++@item 4 +++32-bit standard @acronym{MIPS} mode breakpoint. +++ +++@item 5 +++32-bit @acronym{microMIPS} mode breakpoint. +++ +++@end table +++ +++@node Tracepoint Packets +++@section Tracepoint Packets +++@cindex tracepoint packets +++@cindex packets, tracepoint +++ +++Here we describe the packets @value{GDBN} uses to implement +++tracepoints (@pxref{Tracepoints}). +++ +++@table @samp +++ +++@item QTDP:@var{n}:@var{addr}:@var{ena}:@var{step}:@var{pass}[:F@var{flen}][:X@var{len},@var{bytes}]@r{[}-@r{]} +++@cindex @samp{QTDP} packet +++Create a new tracepoint, number @var{n}, at @var{addr}. If @var{ena} +++is @samp{E}, then the tracepoint is enabled; if it is @samp{D}, then +++the tracepoint is disabled. The @var{step} gives the tracepoint's step +++count, and @var{pass} gives its pass count. If an @samp{F} is present, +++then the tracepoint is to be a fast tracepoint, and the @var{flen} is +++the number of bytes that the target should copy elsewhere to make room +++for the tracepoint. If an @samp{X} is present, it introduces a +++tracepoint condition, which consists of a hexadecimal length, followed +++by a comma and hex-encoded bytes, in a manner similar to action +++encodings as described below. If the trailing @samp{-} is present, +++further @samp{QTDP} packets will follow to specify this tracepoint's +++actions. +++ +++Replies: +++@table @samp +++@item OK +++The packet was understood and carried out. +++@item qRelocInsn +++@xref{Tracepoint Packets,,Relocate instruction reply packet}. +++@item @w{} +++The packet was not recognized. +++@end table +++ +++@item QTDP:-@var{n}:@var{addr}:@r{[}S@r{]}@var{action}@dots{}@r{[}-@r{]} +++Define actions to be taken when a tracepoint is hit. The @var{n} and +++@var{addr} must be the same as in the initial @samp{QTDP} packet for +++this tracepoint. This packet may only be sent immediately after +++another @samp{QTDP} packet that ended with a @samp{-}. If the +++trailing @samp{-} is present, further @samp{QTDP} packets will follow, +++specifying more actions for this tracepoint. +++ +++In the series of action packets for a given tracepoint, at most one +++can have an @samp{S} before its first @var{action}. If such a packet +++is sent, it and the following packets define ``while-stepping'' +++actions. Any prior packets define ordinary actions --- that is, those +++taken when the tracepoint is first hit. If no action packet has an +++@samp{S}, then all the packets in the series specify ordinary +++tracepoint actions. +++ +++The @samp{@var{action}@dots{}} portion of the packet is a series of +++actions, concatenated without separators. Each action has one of the +++following forms: +++ +++@table @samp +++ +++@item R @var{mask} +++Collect the registers whose bits are set in @var{mask}, +++a hexadecimal number whose @var{i}'th bit is set if register number +++@var{i} should be collected. (The least significant bit is numbered +++zero.) Note that @var{mask} may be any number of digits long; it may +++not fit in a 32-bit word. +++ +++@item M @var{basereg},@var{offset},@var{len} +++Collect @var{len} bytes of memory starting at the address in register +++number @var{basereg}, plus @var{offset}. If @var{basereg} is +++@samp{-1}, then the range has a fixed address: @var{offset} is the +++address of the lowest byte to collect. The @var{basereg}, +++@var{offset}, and @var{len} parameters are all unsigned hexadecimal +++values (the @samp{-1} value for @var{basereg} is a special case). +++ +++@item X @var{len},@var{expr} +++Evaluate @var{expr}, whose length is @var{len}, and collect memory as +++it directs. The agent expression @var{expr} is as described in +++@ref{Agent Expressions}. Each byte of the expression is encoded as a +++two-digit hex number in the packet; @var{len} is the number of bytes +++in the expression (and thus one-half the number of hex digits in the +++packet). +++ +++@end table +++ +++Any number of actions may be packed together in a single @samp{QTDP} +++packet, as long as the packet does not exceed the maximum packet +++length (400 bytes, for many stubs). There may be only one @samp{R} +++action per tracepoint, and it must precede any @samp{M} or @samp{X} +++actions. Any registers referred to by @samp{M} and @samp{X} actions +++must be collected by a preceding @samp{R} action. (The +++``while-stepping'' actions are treated as if they were attached to a +++separate tracepoint, as far as these restrictions are concerned.) +++ +++Replies: +++@table @samp +++@item OK +++The packet was understood and carried out. +++@item qRelocInsn +++@xref{Tracepoint Packets,,Relocate instruction reply packet}. +++@item @w{} +++The packet was not recognized. +++@end table +++ +++@item QTDPsrc:@var{n}:@var{addr}:@var{type}:@var{start}:@var{slen}:@var{bytes} +++@cindex @samp{QTDPsrc} packet +++Specify a source string of tracepoint @var{n} at address @var{addr}. +++This is useful to get accurate reproduction of the tracepoints +++originally downloaded at the beginning of the trace run. The @var{type} +++is the name of the tracepoint part, such as @samp{cond} for the +++tracepoint's conditional expression (see below for a list of types), while +++@var{bytes} is the string, encoded in hexadecimal. +++ +++@var{start} is the offset of the @var{bytes} within the overall source +++string, while @var{slen} is the total length of the source string. +++This is intended for handling source strings that are longer than will +++fit in a single packet. +++@c Add detailed example when this info is moved into a dedicated +++@c tracepoint descriptions section. +++ +++The available string types are @samp{at} for the location, +++@samp{cond} for the conditional, and @samp{cmd} for an action command. +++@value{GDBN} sends a separate packet for each command in the action +++list, in the same order in which the commands are stored in the list. +++ +++The target does not need to do anything with source strings except +++report them back as part of the replies to the @samp{qTfP}/@samp{qTsP} +++query packets. +++ +++Although this packet is optional, and @value{GDBN} will only send it +++if the target replies with @samp{TracepointSource} @xref{General +++Query Packets}, it makes both disconnected tracing and trace files +++much easier to use. Otherwise the user must be careful that the +++tracepoints in effect while looking at trace frames are identical to +++the ones in effect during the trace run; even a small discrepancy +++could cause @samp{tdump} not to work, or a particular trace frame not +++be found. +++ +++@item QTDV:@var{n}:@var{value}:@var{builtin}:@var{name} +++@cindex define trace state variable, remote request +++@cindex @samp{QTDV} packet +++Create a new trace state variable, number @var{n}, with an initial +++value of @var{value}, which is a 64-bit signed integer. Both @var{n} +++and @var{value} are encoded as hexadecimal values. @value{GDBN} has +++the option of not using this packet for initial values of zero; the +++target should simply create the trace state variables as they are +++mentioned in expressions. The value @var{builtin} should be 1 (one) +++if the trace state variable is builtin and 0 (zero) if it is not builtin. +++@value{GDBN} only sets @var{builtin} to 1 if a previous @samp{qTfV} or +++@samp{qTsV} packet had it set. The contents of @var{name} is the +++hex-encoded name (without the leading @samp{$}) of the trace state +++variable. +++ +++@item QTFrame:@var{n} +++@cindex @samp{QTFrame} packet +++Select the @var{n}'th tracepoint frame from the buffer, and use the +++register and memory contents recorded there to answer subsequent +++request packets from @value{GDBN}. +++ +++A successful reply from the stub indicates that the stub has found the +++requested frame. The response is a series of parts, concatenated +++without separators, describing the frame we selected. Each part has +++one of the following forms: +++ +++@table @samp +++@item F @var{f} +++The selected frame is number @var{n} in the trace frame buffer; +++@var{f} is a hexadecimal number. If @var{f} is @samp{-1}, then there +++was no frame matching the criteria in the request packet. +++ +++@item T @var{t} +++The selected trace frame records a hit of tracepoint number @var{t}; +++@var{t} is a hexadecimal number. +++ +++@end table +++ +++@item QTFrame:pc:@var{addr} +++Like @samp{QTFrame:@var{n}}, but select the first tracepoint frame after the +++currently selected frame whose PC is @var{addr}; +++@var{addr} is a hexadecimal number. +++ +++@item QTFrame:tdp:@var{t} +++Like @samp{QTFrame:@var{n}}, but select the first tracepoint frame after the +++currently selected frame that is a hit of tracepoint @var{t}; @var{t} +++is a hexadecimal number. +++ +++@item QTFrame:range:@var{start}:@var{end} +++Like @samp{QTFrame:@var{n}}, but select the first tracepoint frame after the +++currently selected frame whose PC is between @var{start} (inclusive) +++and @var{end} (inclusive); @var{start} and @var{end} are hexadecimal +++numbers. +++ +++@item QTFrame:outside:@var{start}:@var{end} +++Like @samp{QTFrame:range:@var{start}:@var{end}}, but select the first +++frame @emph{outside} the given range of addresses (exclusive). +++ +++@item qTMinFTPILen +++@cindex @samp{qTMinFTPILen} packet +++This packet requests the minimum length of instruction at which a fast +++tracepoint (@pxref{Set Tracepoints}) may be placed. For instance, on +++the 32-bit x86 architecture, it is possible to use a 4-byte jump, but +++it depends on the target system being able to create trampolines in +++the first 64K of memory, which might or might not be possible for that +++system. So the reply to this packet will be 4 if it is able to +++arrange for that. +++ +++Replies: +++ +++@table @samp +++@item 0 +++The minimum instruction length is currently unknown. +++@item @var{length} +++The minimum instruction length is @var{length}, where @var{length} +++is a hexadecimal number greater or equal to 1. A reply +++of 1 means that a fast tracepoint may be placed on any instruction +++regardless of size. +++@item E +++An error has occurred. +++@item @w{} +++An empty reply indicates that the request is not supported by the stub. +++@end table +++ +++@item QTStart +++@cindex @samp{QTStart} packet +++Begin the tracepoint experiment. Begin collecting data from +++tracepoint hits in the trace frame buffer. This packet supports the +++@samp{qRelocInsn} reply (@pxref{Tracepoint Packets,,Relocate +++instruction reply packet}). +++ +++@item QTStop +++@cindex @samp{QTStop} packet +++End the tracepoint experiment. Stop collecting trace frames. +++ +++@item QTEnable:@var{n}:@var{addr} +++@anchor{QTEnable} +++@cindex @samp{QTEnable} packet +++Enable tracepoint @var{n} at address @var{addr} in a started tracepoint +++experiment. If the tracepoint was previously disabled, then collection +++of data from it will resume. +++ +++@item QTDisable:@var{n}:@var{addr} +++@anchor{QTDisable} +++@cindex @samp{QTDisable} packet +++Disable tracepoint @var{n} at address @var{addr} in a started tracepoint +++experiment. No more data will be collected from the tracepoint unless +++@samp{QTEnable:@var{n}:@var{addr}} is subsequently issued. +++ +++@item QTinit +++@cindex @samp{QTinit} packet +++Clear the table of tracepoints, and empty the trace frame buffer. +++ +++@item QTro:@var{start1},@var{end1}:@var{start2},@var{end2}:@dots{} +++@cindex @samp{QTro} packet +++Establish the given ranges of memory as ``transparent''. The stub +++will answer requests for these ranges from memory's current contents, +++if they were not collected as part of the tracepoint hit. +++ +++@value{GDBN} uses this to mark read-only regions of memory, like those +++containing program code. Since these areas never change, they should +++still have the same contents they did when the tracepoint was hit, so +++there's no reason for the stub to refuse to provide their contents. +++ +++@item QTDisconnected:@var{value} +++@cindex @samp{QTDisconnected} packet +++Set the choice to what to do with the tracing run when @value{GDBN} +++disconnects from the target. A @var{value} of 1 directs the target to +++continue the tracing run, while 0 tells the target to stop tracing if +++@value{GDBN} is no longer in the picture. +++ +++@item qTStatus +++@cindex @samp{qTStatus} packet +++Ask the stub if there is a trace experiment running right now. +++ +++The reply has the form: +++ +++@table @samp +++ +++@item T@var{running}@r{[};@var{field}@r{]}@dots{} +++@var{running} is a single digit @code{1} if the trace is presently +++running, or @code{0} if not. It is followed by semicolon-separated +++optional fields that an agent may use to report additional status. +++ +++@end table +++ +++If the trace is not running, the agent may report any of several +++explanations as one of the optional fields: +++ +++@table @samp +++ +++@item tnotrun:0 +++No trace has been run yet. +++ +++@item tstop[:@var{text}]:0 +++The trace was stopped by a user-originated stop command. The optional +++@var{text} field is a user-supplied string supplied as part of the +++stop command (for instance, an explanation of why the trace was +++stopped manually). It is hex-encoded. +++ +++@item tfull:0 +++The trace stopped because the trace buffer filled up. +++ +++@item tdisconnected:0 +++The trace stopped because @value{GDBN} disconnected from the target. +++ +++@item tpasscount:@var{tpnum} +++The trace stopped because tracepoint @var{tpnum} exceeded its pass count. +++ +++@item terror:@var{text}:@var{tpnum} +++The trace stopped because tracepoint @var{tpnum} had an error. The +++string @var{text} is available to describe the nature of the error +++(for instance, a divide by zero in the condition expression); it +++is hex encoded. +++ +++@item tunknown:0 +++The trace stopped for some other reason. +++ +++@end table +++ +++Additional optional fields supply statistical and other information. +++Although not required, they are extremely useful for users monitoring +++the progress of a trace run. If a trace has stopped, and these +++numbers are reported, they must reflect the state of the just-stopped +++trace. +++ +++@table @samp +++ +++@item tframes:@var{n} +++The number of trace frames in the buffer. +++ +++@item tcreated:@var{n} +++The total number of trace frames created during the run. This may +++be larger than the trace frame count, if the buffer is circular. +++ +++@item tsize:@var{n} +++The total size of the trace buffer, in bytes. +++ +++@item tfree:@var{n} +++The number of bytes still unused in the buffer. +++ +++@item circular:@var{n} +++The value of the circular trace buffer flag. @code{1} means that the +++trace buffer is circular and old trace frames will be discarded if +++necessary to make room, @code{0} means that the trace buffer is linear +++and may fill up. +++ +++@item disconn:@var{n} +++The value of the disconnected tracing flag. @code{1} means that +++tracing will continue after @value{GDBN} disconnects, @code{0} means +++that the trace run will stop. +++ +++@end table +++ +++@item qTP:@var{tp}:@var{addr} +++@cindex tracepoint status, remote request +++@cindex @samp{qTP} packet +++Ask the stub for the current state of tracepoint number @var{tp} at +++address @var{addr}. +++ +++Replies: +++@table @samp +++@item V@var{hits}:@var{usage} +++The tracepoint has been hit @var{hits} times so far during the trace +++run, and accounts for @var{usage} in the trace buffer. Note that +++@code{while-stepping} steps are not counted as separate hits, but the +++steps' space consumption is added into the usage number. +++ +++@end table +++ +++@item qTV:@var{var} +++@cindex trace state variable value, remote request +++@cindex @samp{qTV} packet +++Ask the stub for the value of the trace state variable number @var{var}. +++ +++Replies: +++@table @samp +++@item V@var{value} +++The value of the variable is @var{value}. This will be the current +++value of the variable if the user is examining a running target, or a +++saved value if the variable was collected in the trace frame that the +++user is looking at. Note that multiple requests may result in +++different reply values, such as when requesting values while the +++program is running. +++ +++@item U +++The value of the variable is unknown. This would occur, for example, +++if the user is examining a trace frame in which the requested variable +++was not collected. +++@end table +++ +++@item qTfP +++@cindex @samp{qTfP} packet +++@itemx qTsP +++@cindex @samp{qTsP} packet +++These packets request data about tracepoints that are being used by +++the target. @value{GDBN} sends @code{qTfP} to get the first piece +++of data, and multiple @code{qTsP} to get additional pieces. Replies +++to these packets generally take the form of the @code{QTDP} packets +++that define tracepoints. (FIXME add detailed syntax) +++ +++@item qTfV +++@cindex @samp{qTfV} packet +++@itemx qTsV +++@cindex @samp{qTsV} packet +++These packets request data about trace state variables that are on the +++target. @value{GDBN} sends @code{qTfV} to get the first vari of data, +++and multiple @code{qTsV} to get additional variables. Replies to +++these packets follow the syntax of the @code{QTDV} packets that define +++trace state variables. +++ +++@item qTfSTM +++@itemx qTsSTM +++@anchor{qTfSTM} +++@anchor{qTsSTM} +++@cindex @samp{qTfSTM} packet +++@cindex @samp{qTsSTM} packet +++These packets request data about static tracepoint markers that exist +++in the target program. @value{GDBN} sends @code{qTfSTM} to get the +++first piece of data, and multiple @code{qTsSTM} to get additional +++pieces. Replies to these packets take the following form: +++ +++Reply: +++@table @samp +++@item m @var{address}:@var{id}:@var{extra} +++A single marker +++@item m @var{address}:@var{id}:@var{extra},@var{address}:@var{id}:@var{extra}@dots{} +++a comma-separated list of markers +++@item l +++(lower case letter @samp{L}) denotes end of list. +++@item E @var{nn} +++An error occurred. The error number @var{nn} is given as hex digits. +++@item @w{} +++An empty reply indicates that the request is not supported by the +++stub. +++@end table +++ +++The @var{address} is encoded in hex; +++@var{id} and @var{extra} are strings encoded in hex. +++ +++In response to each query, the target will reply with a list of one or +++more markers, separated by commas. @value{GDBN} will respond to each +++reply with a request for more markers (using the @samp{qs} form of the +++query), until the target responds with @samp{l} (lower-case ell, for +++@dfn{last}). +++ +++@item qTSTMat:@var{address} +++@anchor{qTSTMat} +++@cindex @samp{qTSTMat} packet +++This packets requests data about static tracepoint markers in the +++target program at @var{address}. Replies to this packet follow the +++syntax of the @samp{qTfSTM} and @code{qTsSTM} packets that list static +++tracepoint markers. +++ +++@item QTSave:@var{filename} +++@cindex @samp{QTSave} packet +++This packet directs the target to save trace data to the file name +++@var{filename} in the target's filesystem. The @var{filename} is encoded +++as a hex string; the interpretation of the file name (relative vs +++absolute, wild cards, etc) is up to the target. +++ +++@item qTBuffer:@var{offset},@var{len} +++@cindex @samp{qTBuffer} packet +++Return up to @var{len} bytes of the current contents of trace buffer, +++starting at @var{offset}. The trace buffer is treated as if it were +++a contiguous collection of traceframes, as per the trace file format. +++The reply consists as many hex-encoded bytes as the target can deliver +++in a packet; it is not an error to return fewer than were asked for. +++A reply consisting of just @code{l} indicates that no bytes are +++available. +++ +++@item QTBuffer:circular:@var{value} +++This packet directs the target to use a circular trace buffer if +++@var{value} is 1, or a linear buffer if the value is 0. +++ +++@item QTBuffer:size:@var{size} +++@anchor{QTBuffer-size} +++@cindex @samp{QTBuffer size} packet +++This packet directs the target to make the trace buffer be of size +++@var{size} if possible. A value of @code{-1} tells the target to +++use whatever size it prefers. +++ +++@item QTNotes:@r{[}@var{type}:@var{text}@r{]}@r{[};@var{type}:@var{text}@r{]}@dots{} +++@cindex @samp{QTNotes} packet +++This packet adds optional textual notes to the trace run. Allowable +++types include @code{user}, @code{notes}, and @code{tstop}, the +++@var{text} fields are arbitrary strings, hex-encoded. +++ +++@end table +++ +++@subsection Relocate instruction reply packet +++When installing fast tracepoints in memory, the target may need to +++relocate the instruction currently at the tracepoint address to a +++different address in memory. For most instructions, a simple copy is +++enough, but, for example, call instructions that implicitly push the +++return address on the stack, and relative branches or other +++PC-relative instructions require offset adjustment, so that the effect +++of executing the instruction at a different address is the same as if +++it had executed in the original location. +++ +++In response to several of the tracepoint packets, the target may also +++respond with a number of intermediate @samp{qRelocInsn} request +++packets before the final result packet, to have @value{GDBN} handle +++this relocation operation. If a packet supports this mechanism, its +++documentation will explicitly say so. See for example the above +++descriptions for the @samp{QTStart} and @samp{QTDP} packets. The +++format of the request is: +++ +++@table @samp +++@item qRelocInsn:@var{from};@var{to} +++ +++This requests @value{GDBN} to copy instruction at address @var{from} +++to address @var{to}, possibly adjusted so that executing the +++instruction at @var{to} has the same effect as executing it at +++@var{from}. @value{GDBN} writes the adjusted instruction to target +++memory starting at @var{to}. +++@end table +++ +++Replies: +++@table @samp +++@item qRelocInsn:@var{adjusted_size} +++Informs the stub the relocation is complete. The @var{adjusted_size} is +++the length in bytes of resulting relocated instruction sequence. +++@item E @var{NN} +++A badly formed request was detected, or an error was encountered while +++relocating the instruction. +++@end table +++ +++@node Host I/O Packets +++@section Host I/O Packets +++@cindex Host I/O, remote protocol +++@cindex file transfer, remote protocol +++ +++The @dfn{Host I/O} packets allow @value{GDBN} to perform I/O +++operations on the far side of a remote link. For example, Host I/O is +++used to upload and download files to a remote target with its own +++filesystem. Host I/O uses the same constant values and data structure +++layout as the target-initiated File-I/O protocol. However, the +++Host I/O packets are structured differently. The target-initiated +++protocol relies on target memory to store parameters and buffers. +++Host I/O requests are initiated by @value{GDBN}, and the +++target's memory is not involved. @xref{File-I/O Remote Protocol +++Extension}, for more details on the target-initiated protocol. +++ +++The Host I/O request packets all encode a single operation along with +++its arguments. They have this format: +++ +++@table @samp +++ +++@item vFile:@var{operation}: @var{parameter}@dots{} +++@var{operation} is the name of the particular request; the target +++should compare the entire packet name up to the second colon when checking +++for a supported operation. The format of @var{parameter} depends on +++the operation. Numbers are always passed in hexadecimal. Negative +++numbers have an explicit minus sign (i.e.@: two's complement is not +++used). Strings (e.g.@: filenames) are encoded as a series of +++hexadecimal bytes. The last argument to a system call may be a +++buffer of escaped binary data (@pxref{Binary Data}). +++ +++@end table +++ +++The valid responses to Host I/O packets are: +++ +++@table @samp +++ +++@item F @var{result} [, @var{errno}] [; @var{attachment}] +++@var{result} is the integer value returned by this operation, usually +++non-negative for success and -1 for errors. If an error has occured, +++@var{errno} will be included in the result specifying a +++value defined by the File-I/O protocol (@pxref{Errno Values}). For +++operations which return data, @var{attachment} supplies the data as a +++binary buffer. Binary buffers in response packets are escaped in the +++normal way (@pxref{Binary Data}). See the individual packet +++documentation for the interpretation of @var{result} and +++@var{attachment}. +++ +++@item @w{} +++An empty response indicates that this operation is not recognized. +++ +++@end table +++ +++These are the supported Host I/O operations: +++ +++@table @samp +++@item vFile:open: @var{filename}, @var{flags}, @var{mode} +++Open a file at @var{filename} and return a file descriptor for it, or +++return -1 if an error occurs. The @var{filename} is a string, +++@var{flags} is an integer indicating a mask of open flags +++(@pxref{Open Flags}), and @var{mode} is an integer indicating a mask +++of mode bits to use if the file is created (@pxref{mode_t Values}). +++@xref{open}, for details of the open flags and mode values. +++ +++@item vFile:close: @var{fd} +++Close the open file corresponding to @var{fd} and return 0, or +++-1 if an error occurs. +++ +++@item vFile:pread: @var{fd}, @var{count}, @var{offset} +++Read data from the open file corresponding to @var{fd}. Up to +++@var{count} bytes will be read from the file, starting at @var{offset} +++relative to the start of the file. The target may read fewer bytes; +++common reasons include packet size limits and an end-of-file +++condition. The number of bytes read is returned. Zero should only be +++returned for a successful read at the end of the file, or if +++@var{count} was zero. +++ +++The data read should be returned as a binary attachment on success. +++If zero bytes were read, the response should include an empty binary +++attachment (i.e.@: a trailing semicolon). The return value is the +++number of target bytes read; the binary attachment may be longer if +++some characters were escaped. +++ +++@item vFile:pwrite: @var{fd}, @var{offset}, @var{data} +++Write @var{data} (a binary buffer) to the open file corresponding +++to @var{fd}. Start the write at @var{offset} from the start of the +++file. Unlike many @code{write} system calls, there is no +++separate @var{count} argument; the length of @var{data} in the +++packet is used. @samp{vFile:pwrite} returns the number of bytes written, +++which may be shorter than the length of @var{data}, or -1 if an +++error occurred. +++ +++@item vFile:fstat: @var{fd} +++Get information about the open file corresponding to @var{fd}. +++On success the information is returned as a binary attachment +++and the return value is the size of this attachment in bytes. +++If an error occurs the return value is -1. The format of the +++returned binary attachment is as described in @ref{struct stat}. +++ +++@item vFile:unlink: @var{filename} +++Delete the file at @var{filename} on the target. Return 0, +++or -1 if an error occurs. The @var{filename} is a string. +++ +++@item vFile:readlink: @var{filename} +++Read value of symbolic link @var{filename} on the target. Return +++the number of bytes read, or -1 if an error occurs. +++ +++The data read should be returned as a binary attachment on success. +++If zero bytes were read, the response should include an empty binary +++attachment (i.e.@: a trailing semicolon). The return value is the +++number of target bytes read; the binary attachment may be longer if +++some characters were escaped. +++ +++@item vFile:setfs: @var{pid} +++Select the filesystem on which @code{vFile} operations with +++@var{filename} arguments will operate. This is required for +++@value{GDBN} to be able to access files on remote targets where +++the remote stub does not share a common filesystem with the +++inferior(s). +++ +++If @var{pid} is nonzero, select the filesystem as seen by process +++@var{pid}. If @var{pid} is zero, select the filesystem as seen by +++the remote stub. Return 0 on success, or -1 if an error occurs. +++If @code{vFile:setfs:} indicates success, the selected filesystem +++remains selected until the next successful @code{vFile:setfs:} +++operation. +++ +++@end table +++ +++@node Interrupts +++@section Interrupts +++@cindex interrupts (remote protocol) +++@anchor{interrupting remote targets} +++ +++In all-stop mode, when a program on the remote target is running, +++@value{GDBN} may attempt to interrupt it by sending a @samp{Ctrl-C}, +++@code{BREAK} or a @code{BREAK} followed by @code{g}, control of which +++is specified via @value{GDBN}'s @samp{interrupt-sequence}. +++ +++The precise meaning of @code{BREAK} is defined by the transport +++mechanism and may, in fact, be undefined. @value{GDBN} does not +++currently define a @code{BREAK} mechanism for any of the network +++interfaces except for TCP, in which case @value{GDBN} sends the +++@code{telnet} BREAK sequence. +++ +++@samp{Ctrl-C}, on the other hand, is defined and implemented for all +++transport mechanisms. It is represented by sending the single byte +++@code{0x03} without any of the usual packet overhead described in +++the Overview section (@pxref{Overview}). When a @code{0x03} byte is +++transmitted as part of a packet, it is considered to be packet data +++and does @emph{not} represent an interrupt. E.g., an @samp{X} packet +++(@pxref{X packet}), used for binary downloads, may include an unescaped +++@code{0x03} as part of its packet. +++ +++@code{BREAK} followed by @code{g} is also known as Magic SysRq g. +++When Linux kernel receives this sequence from serial port, +++it stops execution and connects to gdb. +++ +++In non-stop mode, because packet resumptions are asynchronous +++(@pxref{vCont packet}), @value{GDBN} is always free to send a remote +++command to the remote stub, even when the target is running. For that +++reason, @value{GDBN} instead sends a regular packet (@pxref{vCtrlC +++packet}) with the usual packet framing instead of the single byte +++@code{0x03}. +++ +++Stubs are not required to recognize these interrupt mechanisms and the +++precise meaning associated with receipt of the interrupt is +++implementation defined. If the target supports debugging of multiple +++threads and/or processes, it should attempt to interrupt all +++currently-executing threads and processes. +++If the stub is successful at interrupting the +++running program, it should send one of the stop +++reply packets (@pxref{Stop Reply Packets}) to @value{GDBN} as a result +++of successfully stopping the program in all-stop mode, and a stop reply +++for each stopped thread in non-stop mode. +++Interrupts received while the +++program is stopped are queued and the program will be interrupted when +++it is resumed next time. +++ +++@node Notification Packets +++@section Notification Packets +++@cindex notification packets +++@cindex packets, notification +++ +++The @value{GDBN} remote serial protocol includes @dfn{notifications}, +++packets that require no acknowledgment. Both the GDB and the stub +++may send notifications (although the only notifications defined at +++present are sent by the stub). Notifications carry information +++without incurring the round-trip latency of an acknowledgment, and so +++are useful for low-impact communications where occasional packet loss +++is not a problem. +++ +++A notification packet has the form @samp{% @var{data} # +++@var{checksum}}, where @var{data} is the content of the notification, +++and @var{checksum} is a checksum of @var{data}, computed and formatted +++as for ordinary @value{GDBN} packets. A notification's @var{data} +++never contains @samp{$}, @samp{%} or @samp{#} characters. Upon +++receiving a notification, the recipient sends no @samp{+} or @samp{-} +++to acknowledge the notification's receipt or to report its corruption. +++ +++Every notification's @var{data} begins with a name, which contains no +++colon characters, followed by a colon character. +++ +++Recipients should silently ignore corrupted notifications and +++notifications they do not understand. Recipients should restart +++timeout periods on receipt of a well-formed notification, whether or +++not they understand it. +++ +++Senders should only send the notifications described here when this +++protocol description specifies that they are permitted. In the +++future, we may extend the protocol to permit existing notifications in +++new contexts; this rule helps older senders avoid confusing newer +++recipients. +++ +++(Older versions of @value{GDBN} ignore bytes received until they see +++the @samp{$} byte that begins an ordinary packet, so new stubs may +++transmit notifications without fear of confusing older clients. There +++are no notifications defined for @value{GDBN} to send at the moment, but we +++assume that most older stubs would ignore them, as well.) +++ +++Each notification is comprised of three parts: +++@table @samp +++@item @var{name}:@var{event} +++The notification packet is sent by the side that initiates the +++exchange (currently, only the stub does that), with @var{event} +++carrying the specific information about the notification, and +++@var{name} specifying the name of the notification. +++@item @var{ack} +++The acknowledge sent by the other side, usually @value{GDBN}, to +++acknowledge the exchange and request the event. +++@end table +++ +++The purpose of an asynchronous notification mechanism is to report to +++@value{GDBN} that something interesting happened in the remote stub. +++ +++The remote stub may send notification @var{name}:@var{event} +++at any time, but @value{GDBN} acknowledges the notification when +++appropriate. The notification event is pending before @value{GDBN} +++acknowledges. Only one notification at a time may be pending; if +++additional events occur before @value{GDBN} has acknowledged the +++previous notification, they must be queued by the stub for later +++synchronous transmission in response to @var{ack} packets from +++@value{GDBN}. Because the notification mechanism is unreliable, +++the stub is permitted to resend a notification if it believes +++@value{GDBN} may not have received it. +++ +++Specifically, notifications may appear when @value{GDBN} is not +++otherwise reading input from the stub, or when @value{GDBN} is +++expecting to read a normal synchronous response or a +++@samp{+}/@samp{-} acknowledgment to a packet it has sent. +++Notification packets are distinct from any other communication from +++the stub so there is no ambiguity. +++ +++After receiving a notification, @value{GDBN} shall acknowledge it by +++sending a @var{ack} packet as a regular, synchronous request to the +++stub. Such acknowledgment is not required to happen immediately, as +++@value{GDBN} is permitted to send other, unrelated packets to the +++stub first, which the stub should process normally. +++ +++Upon receiving a @var{ack} packet, if the stub has other queued +++events to report to @value{GDBN}, it shall respond by sending a +++normal @var{event}. @value{GDBN} shall then send another @var{ack} +++packet to solicit further responses; again, it is permitted to send +++other, unrelated packets as well which the stub should process +++normally. +++ +++If the stub receives a @var{ack} packet and there are no additional +++@var{event} to report, the stub shall return an @samp{OK} response. +++At this point, @value{GDBN} has finished processing a notification +++and the stub has completed sending any queued events. @value{GDBN} +++won't accept any new notifications until the final @samp{OK} is +++received . If further notification events occur, the stub shall send +++a new notification, @value{GDBN} shall accept the notification, and +++the process shall be repeated. +++ +++The process of asynchronous notification can be illustrated by the +++following example: +++@smallexample +++<- @code{%Stop:T0505:98e7ffbf;04:4ce6ffbf;08:b1b6e54c;thread:p7526.7526;core:0;} +++@code{...} +++-> @code{vStopped} +++<- @code{T0505:68f37db7;04:40f37db7;08:63850408;thread:p7526.7528;core:0;} +++-> @code{vStopped} +++<- @code{T0505:68e3fdb6;04:40e3fdb6;08:63850408;thread:p7526.7529;core:0;} +++-> @code{vStopped} +++<- @code{OK} +++@end smallexample +++ +++The following notifications are defined: +++@multitable @columnfractions 0.12 0.12 0.38 0.38 +++ +++@item Notification +++@tab Ack +++@tab Event +++@tab Description +++ +++@item Stop +++@tab vStopped +++@tab @var{reply}. The @var{reply} has the form of a stop reply, as +++described in @ref{Stop Reply Packets}. Refer to @ref{Remote Non-Stop}, +++for information on how these notifications are acknowledged by +++@value{GDBN}. +++@tab Report an asynchronous stop event in non-stop mode. +++ +++@end multitable +++ +++@node Remote Non-Stop +++@section Remote Protocol Support for Non-Stop Mode +++ +++@value{GDBN}'s remote protocol supports non-stop debugging of +++multi-threaded programs, as described in @ref{Non-Stop Mode}. If the stub +++supports non-stop mode, it should report that to @value{GDBN} by including +++@samp{QNonStop+} in its @samp{qSupported} response (@pxref{qSupported}). +++ +++@value{GDBN} typically sends a @samp{QNonStop} packet only when +++establishing a new connection with the stub. Entering non-stop mode +++does not alter the state of any currently-running threads, but targets +++must stop all threads in any already-attached processes when entering +++all-stop mode. @value{GDBN} uses the @samp{?} packet as necessary to +++probe the target state after a mode change. +++ +++In non-stop mode, when an attached process encounters an event that +++would otherwise be reported with a stop reply, it uses the +++asynchronous notification mechanism (@pxref{Notification Packets}) to +++inform @value{GDBN}. In contrast to all-stop mode, where all threads +++in all processes are stopped when a stop reply is sent, in non-stop +++mode only the thread reporting the stop event is stopped. That is, +++when reporting a @samp{S} or @samp{T} response to indicate completion +++of a step operation, hitting a breakpoint, or a fault, only the +++affected thread is stopped; any other still-running threads continue +++to run. When reporting a @samp{W} or @samp{X} response, all running +++threads belonging to other attached processes continue to run. +++ +++In non-stop mode, the target shall respond to the @samp{?} packet as +++follows. First, any incomplete stop reply notification/@samp{vStopped} +++sequence in progress is abandoned. The target must begin a new +++sequence reporting stop events for all stopped threads, whether or not +++it has previously reported those events to @value{GDBN}. The first +++stop reply is sent as a synchronous reply to the @samp{?} packet, and +++subsequent stop replies are sent as responses to @samp{vStopped} packets +++using the mechanism described above. The target must not send +++asynchronous stop reply notifications until the sequence is complete. +++If all threads are running when the target receives the @samp{?} packet, +++or if the target is not attached to any process, it shall respond +++@samp{OK}. +++ +++If the stub supports non-stop mode, it should also support the +++@samp{swbreak} stop reason if software breakpoints are supported, and +++the @samp{hwbreak} stop reason if hardware breakpoints are supported +++(@pxref{swbreak stop reason}). This is because given the asynchronous +++nature of non-stop mode, between the time a thread hits a breakpoint +++and the time the event is finally processed by @value{GDBN}, the +++breakpoint may have already been removed from the target. Due to +++this, @value{GDBN} needs to be able to tell whether a trap stop was +++caused by a delayed breakpoint event, which should be ignored, as +++opposed to a random trap signal, which should be reported to the user. +++Note the @samp{swbreak} feature implies that the target is responsible +++for adjusting the PC when a software breakpoint triggers, if +++necessary, such as on the x86 architecture. +++ +++@node Packet Acknowledgment +++@section Packet Acknowledgment +++ +++@cindex acknowledgment, for @value{GDBN} remote +++@cindex packet acknowledgment, for @value{GDBN} remote +++By default, when either the host or the target machine receives a packet, +++the first response expected is an acknowledgment: either @samp{+} (to indicate +++the package was received correctly) or @samp{-} (to request retransmission). +++This mechanism allows the @value{GDBN} remote protocol to operate over +++unreliable transport mechanisms, such as a serial line. +++ +++In cases where the transport mechanism is itself reliable (such as a pipe or +++TCP connection), the @samp{+}/@samp{-} acknowledgments are redundant. +++It may be desirable to disable them in that case to reduce communication +++overhead, or for other reasons. This can be accomplished by means of the +++@samp{QStartNoAckMode} packet; @pxref{QStartNoAckMode}. +++ +++When in no-acknowledgment mode, neither the stub nor @value{GDBN} shall send or +++expect @samp{+}/@samp{-} protocol acknowledgments. The packet +++and response format still includes the normal checksum, as described in +++@ref{Overview}, but the checksum may be ignored by the receiver. +++ +++If the stub supports @samp{QStartNoAckMode} and prefers to operate in +++no-acknowledgment mode, it should report that to @value{GDBN} +++by including @samp{QStartNoAckMode+} in its response to @samp{qSupported}; +++@pxref{qSupported}. +++If @value{GDBN} also supports @samp{QStartNoAckMode} and it has not been +++disabled via the @code{set remote noack-packet off} command +++(@pxref{Remote Configuration}), +++@value{GDBN} may then send a @samp{QStartNoAckMode} packet to the stub. +++Only then may the stub actually turn off packet acknowledgments. +++@value{GDBN} sends a final @samp{+} acknowledgment of the stub's @samp{OK} +++response, which can be safely ignored by the stub. +++ +++Note that @code{set remote noack-packet} command only affects negotiation +++between @value{GDBN} and the stub when subsequent connections are made; +++it does not affect the protocol acknowledgment state for any current +++connection. +++Since @samp{+}/@samp{-} acknowledgments are enabled by default when a +++new connection is established, +++there is also no protocol request to re-enable the acknowledgments +++for the current connection, once disabled. +++ +++@node Examples +++@section Examples +++ +++Example sequence of a target being re-started. Notice how the restart +++does not get any direct output: +++ +++@smallexample +++-> @code{R00} +++<- @code{+} +++@emph{target restarts} +++-> @code{?} +++<- @code{+} +++<- @code{T001:1234123412341234} +++-> @code{+} +++@end smallexample +++ +++Example sequence of a target being stepped by a single instruction: +++ +++@smallexample +++-> @code{G1445@dots{}} +++<- @code{+} +++-> @code{s} +++<- @code{+} +++@emph{time passes} +++<- @code{T001:1234123412341234} +++-> @code{+} +++-> @code{g} +++<- @code{+} +++<- @code{1455@dots{}} +++-> @code{+} +++@end smallexample +++ +++@node File-I/O Remote Protocol Extension +++@section File-I/O Remote Protocol Extension +++@cindex File-I/O remote protocol extension +++ +++@menu +++* File-I/O Overview:: +++* Protocol Basics:: +++* The F Request Packet:: +++* The F Reply Packet:: +++* The Ctrl-C Message:: +++* Console I/O:: +++* List of Supported Calls:: +++* Protocol-specific Representation of Datatypes:: +++* Constants:: +++* File-I/O Examples:: +++@end menu +++ +++@node File-I/O Overview +++@subsection File-I/O Overview +++@cindex file-i/o overview +++ +++The @dfn{File I/O remote protocol extension} (short: File-I/O) allows the +++target to use the host's file system and console I/O to perform various +++system calls. System calls on the target system are translated into a +++remote protocol packet to the host system, which then performs the needed +++actions and returns a response packet to the target system. +++This simulates file system operations even on targets that lack file systems. +++ +++The protocol is defined to be independent of both the host and target systems. +++It uses its own internal representation of datatypes and values. Both +++@value{GDBN} and the target's @value{GDBN} stub are responsible for +++translating the system-dependent value representations into the internal +++protocol representations when data is transmitted. +++ +++The communication is synchronous. A system call is possible only when +++@value{GDBN} is waiting for a response from the @samp{C}, @samp{c}, @samp{S} +++or @samp{s} packets. While @value{GDBN} handles the request for a system call, +++the target is stopped to allow deterministic access to the target's +++memory. Therefore File-I/O is not interruptible by target signals. On +++the other hand, it is possible to interrupt File-I/O by a user interrupt +++(@samp{Ctrl-C}) within @value{GDBN}. +++ +++The target's request to perform a host system call does not finish +++the latest @samp{C}, @samp{c}, @samp{S} or @samp{s} action. That means, +++after finishing the system call, the target returns to continuing the +++previous activity (continue, step). No additional continue or step +++request from @value{GDBN} is required. +++ +++@smallexample +++(@value{GDBP}) continue +++ <- target requests 'system call X' +++ target is stopped, @value{GDBN} executes system call +++ -> @value{GDBN} returns result +++ ... target continues, @value{GDBN} returns to wait for the target +++ <- target hits breakpoint and sends a Txx packet +++@end smallexample +++ +++The protocol only supports I/O on the console and to regular files on +++the host file system. Character or block special devices, pipes, +++named pipes, sockets or any other communication method on the host +++system are not supported by this protocol. +++ +++File I/O is not supported in non-stop mode. +++ +++@node Protocol Basics +++@subsection Protocol Basics +++@cindex protocol basics, file-i/o +++ +++The File-I/O protocol uses the @code{F} packet as the request as well +++as reply packet. Since a File-I/O system call can only occur when +++@value{GDBN} is waiting for a response from the continuing or stepping target, +++the File-I/O request is a reply that @value{GDBN} has to expect as a result +++of a previous @samp{C}, @samp{c}, @samp{S} or @samp{s} packet. +++This @code{F} packet contains all information needed to allow @value{GDBN} +++to call the appropriate host system call: +++ +++@itemize @bullet +++@item +++A unique identifier for the requested system call. +++ +++@item +++All parameters to the system call. Pointers are given as addresses +++in the target memory address space. Pointers to strings are given as +++pointer/length pair. Numerical values are given as they are. +++Numerical control flags are given in a protocol-specific representation. +++ +++@end itemize +++ +++At this point, @value{GDBN} has to perform the following actions. +++ +++@itemize @bullet +++@item +++If the parameters include pointer values to data needed as input to a +++system call, @value{GDBN} requests this data from the target with a +++standard @code{m} packet request. This additional communication has to be +++expected by the target implementation and is handled as any other @code{m} +++packet. +++ +++@item +++@value{GDBN} translates all value from protocol representation to host +++representation as needed. Datatypes are coerced into the host types. +++ +++@item +++@value{GDBN} calls the system call. +++ +++@item +++It then coerces datatypes back to protocol representation. +++ +++@item +++If the system call is expected to return data in buffer space specified +++by pointer parameters to the call, the data is transmitted to the +++target using a @code{M} or @code{X} packet. This packet has to be expected +++by the target implementation and is handled as any other @code{M} or @code{X} +++packet. +++ +++@end itemize +++ +++Eventually @value{GDBN} replies with another @code{F} packet which contains all +++necessary information for the target to continue. This at least contains +++ +++@itemize @bullet +++@item +++Return value. +++ +++@item +++@code{errno}, if has been changed by the system call. +++ +++@item +++``Ctrl-C'' flag. +++ +++@end itemize +++ +++After having done the needed type and value coercion, the target continues +++the latest continue or step action. +++ +++@node The F Request Packet +++@subsection The @code{F} Request Packet +++@cindex file-i/o request packet +++@cindex @code{F} request packet +++ +++The @code{F} request packet has the following format: +++ +++@table @samp +++@item F@var{call-id},@var{parameter@dots{}} +++ +++@var{call-id} is the identifier to indicate the host system call to be called. +++This is just the name of the function. +++ +++@var{parameter@dots{}} are the parameters to the system call. +++Parameters are hexadecimal integer values, either the actual values in case +++of scalar datatypes, pointers to target buffer space in case of compound +++datatypes and unspecified memory areas, or pointer/length pairs in case +++of string parameters. These are appended to the @var{call-id} as a +++comma-delimited list. All values are transmitted in ASCII +++string representation, pointer/length pairs separated by a slash. +++ +++@end table +++ +++ +++ +++@node The F Reply Packet +++@subsection The @code{F} Reply Packet +++@cindex file-i/o reply packet +++@cindex @code{F} reply packet +++ +++The @code{F} reply packet has the following format: +++ +++@table @samp +++ +++@item F@var{retcode},@var{errno},@var{Ctrl-C flag};@var{call-specific attachment} +++ +++@var{retcode} is the return code of the system call as hexadecimal value. +++ +++@var{errno} is the @code{errno} set by the call, in protocol-specific +++representation. +++This parameter can be omitted if the call was successful. +++ +++@var{Ctrl-C flag} is only sent if the user requested a break. In this +++case, @var{errno} must be sent as well, even if the call was successful. +++The @var{Ctrl-C flag} itself consists of the character @samp{C}: +++ +++@smallexample +++F0,0,C +++@end smallexample +++ +++@noindent +++or, if the call was interrupted before the host call has been performed: +++ +++@smallexample +++F-1,4,C +++@end smallexample +++ +++@noindent +++assuming 4 is the protocol-specific representation of @code{EINTR}. +++ +++@end table +++ +++ +++@node The Ctrl-C Message +++@subsection The @samp{Ctrl-C} Message +++@cindex ctrl-c message, in file-i/o protocol +++ +++If the @samp{Ctrl-C} flag is set in the @value{GDBN} +++reply packet (@pxref{The F Reply Packet}), +++the target should behave as if it had +++gotten a break message. The meaning for the target is ``system call +++interrupted by @code{SIGINT}''. Consequentially, the target should actually stop +++(as with a break message) and return to @value{GDBN} with a @code{T02} +++packet. +++ +++It's important for the target to know in which +++state the system call was interrupted. There are two possible cases: +++ +++@itemize @bullet +++@item +++The system call hasn't been performed on the host yet. +++ +++@item +++The system call on the host has been finished. +++ +++@end itemize +++ +++These two states can be distinguished by the target by the value of the +++returned @code{errno}. If it's the protocol representation of @code{EINTR}, the system +++call hasn't been performed. This is equivalent to the @code{EINTR} handling +++on POSIX systems. In any other case, the target may presume that the +++system call has been finished --- successfully or not --- and should behave +++as if the break message arrived right after the system call. +++ +++@value{GDBN} must behave reliably. If the system call has not been called +++yet, @value{GDBN} may send the @code{F} reply immediately, setting @code{EINTR} as +++@code{errno} in the packet. If the system call on the host has been finished +++before the user requests a break, the full action must be finished by +++@value{GDBN}. This requires sending @code{M} or @code{X} packets as necessary. +++The @code{F} packet may only be sent when either nothing has happened +++or the full action has been completed. +++ +++@node Console I/O +++@subsection Console I/O +++@cindex console i/o as part of file-i/o +++ +++By default and if not explicitly closed by the target system, the file +++descriptors 0, 1 and 2 are connected to the @value{GDBN} console. Output +++on the @value{GDBN} console is handled as any other file output operation +++(@code{write(1, @dots{})} or @code{write(2, @dots{})}). Console input is handled +++by @value{GDBN} so that after the target read request from file descriptor +++0 all following typing is buffered until either one of the following +++conditions is met: +++ +++@itemize @bullet +++@item +++The user types @kbd{Ctrl-c}. The behaviour is as explained above, and the +++@code{read} +++system call is treated as finished. +++ +++@item +++The user presses @key{RET}. This is treated as end of input with a trailing +++newline. +++ +++@item +++The user types @kbd{Ctrl-d}. This is treated as end of input. No trailing +++character (neither newline nor @samp{Ctrl-D}) is appended to the input. +++ +++@end itemize +++ +++If the user has typed more characters than fit in the buffer given to +++the @code{read} call, the trailing characters are buffered in @value{GDBN} until +++either another @code{read(0, @dots{})} is requested by the target, or debugging +++is stopped at the user's request. +++ +++ +++@node List of Supported Calls +++@subsection List of Supported Calls +++@cindex list of supported file-i/o calls +++ +++@menu +++* open:: +++* close:: +++* read:: +++* write:: +++* lseek:: +++* rename:: +++* unlink:: +++* stat/fstat:: +++* gettimeofday:: +++* isatty:: +++* system:: +++@end menu +++ +++@node open +++@unnumberedsubsubsec open +++@cindex open, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int open(const char *pathname, int flags); +++int open(const char *pathname, int flags, mode_t mode); +++@end smallexample +++ +++@item Request: +++@samp{Fopen,@var{pathptr}/@var{len},@var{flags},@var{mode}} +++ +++@noindent +++@var{flags} is the bitwise @code{OR} of the following values: +++ +++@table @code +++@item O_CREAT +++If the file does not exist it will be created. The host +++rules apply as far as file ownership and time stamps +++are concerned. +++ +++@item O_EXCL +++When used with @code{O_CREAT}, if the file already exists it is +++an error and open() fails. +++ +++@item O_TRUNC +++If the file already exists and the open mode allows +++writing (@code{O_RDWR} or @code{O_WRONLY} is given) it will be +++truncated to zero length. +++ +++@item O_APPEND +++The file is opened in append mode. +++ +++@item O_RDONLY +++The file is opened for reading only. +++ +++@item O_WRONLY +++The file is opened for writing only. +++ +++@item O_RDWR +++The file is opened for reading and writing. +++@end table +++ +++@noindent +++Other bits are silently ignored. +++ +++ +++@noindent +++@var{mode} is the bitwise @code{OR} of the following values: +++ +++@table @code +++@item S_IRUSR +++User has read permission. +++ +++@item S_IWUSR +++User has write permission. +++ +++@item S_IRGRP +++Group has read permission. +++ +++@item S_IWGRP +++Group has write permission. +++ +++@item S_IROTH +++Others have read permission. +++ +++@item S_IWOTH +++Others have write permission. +++@end table +++ +++@noindent +++Other bits are silently ignored. +++ +++ +++@item Return value: +++@code{open} returns the new file descriptor or -1 if an error +++occurred. +++ +++@item Errors: +++ +++@table @code +++@item EEXIST +++@var{pathname} already exists and @code{O_CREAT} and @code{O_EXCL} were used. +++ +++@item EISDIR +++@var{pathname} refers to a directory. +++ +++@item EACCES +++The requested access is not allowed. +++ +++@item ENAMETOOLONG +++@var{pathname} was too long. +++ +++@item ENOENT +++A directory component in @var{pathname} does not exist. +++ +++@item ENODEV +++@var{pathname} refers to a device, pipe, named pipe or socket. +++ +++@item EROFS +++@var{pathname} refers to a file on a read-only filesystem and +++write access was requested. +++ +++@item EFAULT +++@var{pathname} is an invalid pointer value. +++ +++@item ENOSPC +++No space on device to create the file. +++ +++@item EMFILE +++The process already has the maximum number of files open. +++ +++@item ENFILE +++The limit on the total number of files open on the system +++has been reached. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node close +++@unnumberedsubsubsec close +++@cindex close, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int close(int fd); +++@end smallexample +++ +++@item Request: +++@samp{Fclose,@var{fd}} +++ +++@item Return value: +++@code{close} returns zero on success, or -1 if an error occurred. +++ +++@item Errors: +++ +++@table @code +++@item EBADF +++@var{fd} isn't a valid open file descriptor. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node read +++@unnumberedsubsubsec read +++@cindex read, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int read(int fd, void *buf, unsigned int count); +++@end smallexample +++ +++@item Request: +++@samp{Fread,@var{fd},@var{bufptr},@var{count}} +++ +++@item Return value: +++On success, the number of bytes read is returned. +++Zero indicates end of file. If count is zero, read +++returns zero as well. On error, -1 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EBADF +++@var{fd} is not a valid file descriptor or is not open for +++reading. +++ +++@item EFAULT +++@var{bufptr} is an invalid pointer value. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node write +++@unnumberedsubsubsec write +++@cindex write, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int write(int fd, const void *buf, unsigned int count); +++@end smallexample +++ +++@item Request: +++@samp{Fwrite,@var{fd},@var{bufptr},@var{count}} +++ +++@item Return value: +++On success, the number of bytes written are returned. +++Zero indicates nothing was written. On error, -1 +++is returned. +++ +++@item Errors: +++ +++@table @code +++@item EBADF +++@var{fd} is not a valid file descriptor or is not open for +++writing. +++ +++@item EFAULT +++@var{bufptr} is an invalid pointer value. +++ +++@item EFBIG +++An attempt was made to write a file that exceeds the +++host-specific maximum file size allowed. +++ +++@item ENOSPC +++No space on device to write the data. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node lseek +++@unnumberedsubsubsec lseek +++@cindex lseek, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++long lseek (int fd, long offset, int flag); +++@end smallexample +++ +++@item Request: +++@samp{Flseek,@var{fd},@var{offset},@var{flag}} +++ +++@var{flag} is one of: +++ +++@table @code +++@item SEEK_SET +++The offset is set to @var{offset} bytes. +++ +++@item SEEK_CUR +++The offset is set to its current location plus @var{offset} +++bytes. +++ +++@item SEEK_END +++The offset is set to the size of the file plus @var{offset} +++bytes. +++@end table +++ +++@item Return value: +++On success, the resulting unsigned offset in bytes from +++the beginning of the file is returned. Otherwise, a +++value of -1 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EBADF +++@var{fd} is not a valid open file descriptor. +++ +++@item ESPIPE +++@var{fd} is associated with the @value{GDBN} console. +++ +++@item EINVAL +++@var{flag} is not a proper value. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node rename +++@unnumberedsubsubsec rename +++@cindex rename, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int rename(const char *oldpath, const char *newpath); +++@end smallexample +++ +++@item Request: +++@samp{Frename,@var{oldpathptr}/@var{len},@var{newpathptr}/@var{len}} +++ +++@item Return value: +++On success, zero is returned. On error, -1 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EISDIR +++@var{newpath} is an existing directory, but @var{oldpath} is not a +++directory. +++ +++@item EEXIST +++@var{newpath} is a non-empty directory. +++ +++@item EBUSY +++@var{oldpath} or @var{newpath} is a directory that is in use by some +++process. +++ +++@item EINVAL +++An attempt was made to make a directory a subdirectory +++of itself. +++ +++@item ENOTDIR +++A component used as a directory in @var{oldpath} or new +++path is not a directory. Or @var{oldpath} is a directory +++and @var{newpath} exists but is not a directory. +++ +++@item EFAULT +++@var{oldpathptr} or @var{newpathptr} are invalid pointer values. +++ +++@item EACCES +++No access to the file or the path of the file. +++ +++@item ENAMETOOLONG +++ +++@var{oldpath} or @var{newpath} was too long. +++ +++@item ENOENT +++A directory component in @var{oldpath} or @var{newpath} does not exist. +++ +++@item EROFS +++The file is on a read-only filesystem. +++ +++@item ENOSPC +++The device containing the file has no room for the new +++directory entry. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node unlink +++@unnumberedsubsubsec unlink +++@cindex unlink, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int unlink(const char *pathname); +++@end smallexample +++ +++@item Request: +++@samp{Funlink,@var{pathnameptr}/@var{len}} +++ +++@item Return value: +++On success, zero is returned. On error, -1 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EACCES +++No access to the file or the path of the file. +++ +++@item EPERM +++The system does not allow unlinking of directories. +++ +++@item EBUSY +++The file @var{pathname} cannot be unlinked because it's +++being used by another process. +++ +++@item EFAULT +++@var{pathnameptr} is an invalid pointer value. +++ +++@item ENAMETOOLONG +++@var{pathname} was too long. +++ +++@item ENOENT +++A directory component in @var{pathname} does not exist. +++ +++@item ENOTDIR +++A component of the path is not a directory. +++ +++@item EROFS +++The file is on a read-only filesystem. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node stat/fstat +++@unnumberedsubsubsec stat/fstat +++@cindex fstat, file-i/o system call +++@cindex stat, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int stat(const char *pathname, struct stat *buf); +++int fstat(int fd, struct stat *buf); +++@end smallexample +++ +++@item Request: +++@samp{Fstat,@var{pathnameptr}/@var{len},@var{bufptr}}@* +++@samp{Ffstat,@var{fd},@var{bufptr}} +++ +++@item Return value: +++On success, zero is returned. On error, -1 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EBADF +++@var{fd} is not a valid open file. +++ +++@item ENOENT +++A directory component in @var{pathname} does not exist or the +++path is an empty string. +++ +++@item ENOTDIR +++A component of the path is not a directory. +++ +++@item EFAULT +++@var{pathnameptr} is an invalid pointer value. +++ +++@item EACCES +++No access to the file or the path of the file. +++ +++@item ENAMETOOLONG +++@var{pathname} was too long. +++ +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@node gettimeofday +++@unnumberedsubsubsec gettimeofday +++@cindex gettimeofday, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int gettimeofday(struct timeval *tv, void *tz); +++@end smallexample +++ +++@item Request: +++@samp{Fgettimeofday,@var{tvptr},@var{tzptr}} +++ +++@item Return value: +++On success, 0 is returned, -1 otherwise. +++ +++@item Errors: +++ +++@table @code +++@item EINVAL +++@var{tz} is a non-NULL pointer. +++ +++@item EFAULT +++@var{tvptr} and/or @var{tzptr} is an invalid pointer value. +++@end table +++ +++@end table +++ +++@node isatty +++@unnumberedsubsubsec isatty +++@cindex isatty, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int isatty(int fd); +++@end smallexample +++ +++@item Request: +++@samp{Fisatty,@var{fd}} +++ +++@item Return value: +++Returns 1 if @var{fd} refers to the @value{GDBN} console, 0 otherwise. +++ +++@item Errors: +++ +++@table @code +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++Note that the @code{isatty} call is treated as a special case: it returns +++1 to the target if the file descriptor is attached +++to the @value{GDBN} console, 0 otherwise. Implementing through system calls +++would require implementing @code{ioctl} and would be more complex than +++needed. +++ +++ +++@node system +++@unnumberedsubsubsec system +++@cindex system, file-i/o system call +++ +++@table @asis +++@item Synopsis: +++@smallexample +++int system(const char *command); +++@end smallexample +++ +++@item Request: +++@samp{Fsystem,@var{commandptr}/@var{len}} +++ +++@item Return value: +++If @var{len} is zero, the return value indicates whether a shell is +++available. A zero return value indicates a shell is not available. +++For non-zero @var{len}, the value returned is -1 on error and the +++return status of the command otherwise. Only the exit status of the +++command is returned, which is extracted from the host's @code{system} +++return value by calling @code{WEXITSTATUS(retval)}. In case +++@file{/bin/sh} could not be executed, 127 is returned. +++ +++@item Errors: +++ +++@table @code +++@item EINTR +++The call was interrupted by the user. +++@end table +++ +++@end table +++ +++@value{GDBN} takes over the full task of calling the necessary host calls +++to perform the @code{system} call. The return value of @code{system} on +++the host is simplified before it's returned +++to the target. Any termination signal information from the child process +++is discarded, and the return value consists +++entirely of the exit status of the called command. +++ +++Due to security concerns, the @code{system} call is by default refused +++by @value{GDBN}. The user has to allow this call explicitly with the +++@code{set remote system-call-allowed 1} command. +++ +++@table @code +++@item set remote system-call-allowed +++@kindex set remote system-call-allowed +++Control whether to allow the @code{system} calls in the File I/O +++protocol for the remote target. The default is zero (disabled). +++ +++@item show remote system-call-allowed +++@kindex show remote system-call-allowed +++Show whether the @code{system} calls are allowed in the File I/O +++protocol. +++@end table +++ +++@node Protocol-specific Representation of Datatypes +++@subsection Protocol-specific Representation of Datatypes +++@cindex protocol-specific representation of datatypes, in file-i/o protocol +++ +++@menu +++* Integral Datatypes:: +++* Pointer Values:: +++* Memory Transfer:: +++* struct stat:: +++* struct timeval:: +++@end menu +++ +++@node Integral Datatypes +++@unnumberedsubsubsec Integral Datatypes +++@cindex integral datatypes, in file-i/o protocol +++ +++The integral datatypes used in the system calls are @code{int}, +++@code{unsigned int}, @code{long}, @code{unsigned long}, +++@code{mode_t}, and @code{time_t}. +++ +++@code{int}, @code{unsigned int}, @code{mode_t} and @code{time_t} are +++implemented as 32 bit values in this protocol. +++ +++@code{long} and @code{unsigned long} are implemented as 64 bit types. +++ +++@xref{Limits}, for corresponding MIN and MAX values (similar to those +++in @file{limits.h}) to allow range checking on host and target. +++ +++@code{time_t} datatypes are defined as seconds since the Epoch. +++ +++All integral datatypes transferred as part of a memory read or write of a +++structured datatype e.g.@: a @code{struct stat} have to be given in big endian +++byte order. +++ +++@node Pointer Values +++@unnumberedsubsubsec Pointer Values +++@cindex pointer values, in file-i/o protocol +++ +++Pointers to target data are transmitted as they are. An exception +++is made for pointers to buffers for which the length isn't +++transmitted as part of the function call, namely strings. Strings +++are transmitted as a pointer/length pair, both as hex values, e.g.@: +++ +++@smallexample +++@code{1aaf/12} +++@end smallexample +++ +++@noindent +++which is a pointer to data of length 18 bytes at position 0x1aaf. +++The length is defined as the full string length in bytes, including +++the trailing null byte. For example, the string @code{"hello world"} +++at address 0x123456 is transmitted as +++ +++@smallexample +++@code{123456/d} +++@end smallexample +++ +++@node Memory Transfer +++@unnumberedsubsubsec Memory Transfer +++@cindex memory transfer, in file-i/o protocol +++ +++Structured data which is transferred using a memory read or write (for +++example, a @code{struct stat}) is expected to be in a protocol-specific format +++with all scalar multibyte datatypes being big endian. Translation to +++this representation needs to be done both by the target before the @code{F} +++packet is sent, and by @value{GDBN} before +++it transfers memory to the target. Transferred pointers to structured +++data should point to the already-coerced data at any time. +++ +++ +++@node struct stat +++@unnumberedsubsubsec struct stat +++@cindex struct stat, in file-i/o protocol +++ +++The buffer of type @code{struct stat} used by the target and @value{GDBN} +++is defined as follows: +++ +++@smallexample +++struct stat @{ +++ unsigned int st_dev; /* device */ +++ unsigned int st_ino; /* inode */ +++ mode_t st_mode; /* protection */ +++ unsigned int st_nlink; /* number of hard links */ +++ unsigned int st_uid; /* user ID of owner */ +++ unsigned int st_gid; /* group ID of owner */ +++ unsigned int st_rdev; /* device type (if inode device) */ +++ unsigned long st_size; /* total size, in bytes */ +++ unsigned long st_blksize; /* blocksize for filesystem I/O */ +++ unsigned long st_blocks; /* number of blocks allocated */ +++ time_t st_atime; /* time of last access */ +++ time_t st_mtime; /* time of last modification */ +++ time_t st_ctime; /* time of last change */ +++@}; +++@end smallexample +++ +++The integral datatypes conform to the definitions given in the +++appropriate section (see @ref{Integral Datatypes}, for details) so this +++structure is of size 64 bytes. +++ +++The values of several fields have a restricted meaning and/or +++range of values. +++ +++@table @code +++ +++@item st_dev +++A value of 0 represents a file, 1 the console. +++ +++@item st_ino +++No valid meaning for the target. Transmitted unchanged. +++ +++@item st_mode +++Valid mode bits are described in @ref{Constants}. Any other +++bits have currently no meaning for the target. +++ +++@item st_uid +++@itemx st_gid +++@itemx st_rdev +++No valid meaning for the target. Transmitted unchanged. +++ +++@item st_atime +++@itemx st_mtime +++@itemx st_ctime +++These values have a host and file system dependent +++accuracy. Especially on Windows hosts, the file system may not +++support exact timing values. +++@end table +++ +++The target gets a @code{struct stat} of the above representation and is +++responsible for coercing it to the target representation before +++continuing. +++ +++Note that due to size differences between the host, target, and protocol +++representations of @code{struct stat} members, these members could eventually +++get truncated on the target. +++ +++@node struct timeval +++@unnumberedsubsubsec struct timeval +++@cindex struct timeval, in file-i/o protocol +++ +++The buffer of type @code{struct timeval} used by the File-I/O protocol +++is defined as follows: +++ +++@smallexample +++struct timeval @{ +++ time_t tv_sec; /* second */ +++ long tv_usec; /* microsecond */ +++@}; +++@end smallexample +++ +++The integral datatypes conform to the definitions given in the +++appropriate section (see @ref{Integral Datatypes}, for details) so this +++structure is of size 8 bytes. +++ +++@node Constants +++@subsection Constants +++@cindex constants, in file-i/o protocol +++ +++The following values are used for the constants inside of the +++protocol. @value{GDBN} and target are responsible for translating these +++values before and after the call as needed. +++ +++@menu +++* Open Flags:: +++* mode_t Values:: +++* Errno Values:: +++* Lseek Flags:: +++* Limits:: +++@end menu +++ +++@node Open Flags +++@unnumberedsubsubsec Open Flags +++@cindex open flags, in file-i/o protocol +++ +++All values are given in hexadecimal representation. +++ +++@smallexample +++ O_RDONLY 0x0 +++ O_WRONLY 0x1 +++ O_RDWR 0x2 +++ O_APPEND 0x8 +++ O_CREAT 0x200 +++ O_TRUNC 0x400 +++ O_EXCL 0x800 +++@end smallexample +++ +++@node mode_t Values +++@unnumberedsubsubsec mode_t Values +++@cindex mode_t values, in file-i/o protocol +++ +++All values are given in octal representation. +++ +++@smallexample +++ S_IFREG 0100000 +++ S_IFDIR 040000 +++ S_IRUSR 0400 +++ S_IWUSR 0200 +++ S_IXUSR 0100 +++ S_IRGRP 040 +++ S_IWGRP 020 +++ S_IXGRP 010 +++ S_IROTH 04 +++ S_IWOTH 02 +++ S_IXOTH 01 +++@end smallexample +++ +++@node Errno Values +++@unnumberedsubsubsec Errno Values +++@cindex errno values, in file-i/o protocol +++ +++All values are given in decimal representation. +++ +++@smallexample +++ EPERM 1 +++ ENOENT 2 +++ EINTR 4 +++ EBADF 9 +++ EACCES 13 +++ EFAULT 14 +++ EBUSY 16 +++ EEXIST 17 +++ ENODEV 19 +++ ENOTDIR 20 +++ EISDIR 21 +++ EINVAL 22 +++ ENFILE 23 +++ EMFILE 24 +++ EFBIG 27 +++ ENOSPC 28 +++ ESPIPE 29 +++ EROFS 30 +++ ENAMETOOLONG 91 +++ EUNKNOWN 9999 +++@end smallexample +++ +++ @code{EUNKNOWN} is used as a fallback error value if a host system returns +++ any error value not in the list of supported error numbers. +++ +++@node Lseek Flags +++@unnumberedsubsubsec Lseek Flags +++@cindex lseek flags, in file-i/o protocol +++ +++@smallexample +++ SEEK_SET 0 +++ SEEK_CUR 1 +++ SEEK_END 2 +++@end smallexample +++ +++@node Limits +++@unnumberedsubsubsec Limits +++@cindex limits, in file-i/o protocol +++ +++All values are given in decimal representation. +++ +++@smallexample +++ INT_MIN -2147483648 +++ INT_MAX 2147483647 +++ UINT_MAX 4294967295 +++ LONG_MIN -9223372036854775808 +++ LONG_MAX 9223372036854775807 +++ ULONG_MAX 18446744073709551615 +++@end smallexample +++ +++@node File-I/O Examples +++@subsection File-I/O Examples +++@cindex file-i/o examples +++ +++Example sequence of a write call, file descriptor 3, buffer is at target +++address 0x1234, 6 bytes should be written: +++ +++@smallexample +++<- @code{Fwrite,3,1234,6} +++@emph{request memory read from target} +++-> @code{m1234,6} +++<- XXXXXX +++@emph{return "6 bytes written"} +++-> @code{F6} +++@end smallexample +++ +++Example sequence of a read call, file descriptor 3, buffer is at target +++address 0x1234, 6 bytes should be read: +++ +++@smallexample +++<- @code{Fread,3,1234,6} +++@emph{request memory write to target} +++-> @code{X1234,6:XXXXXX} +++@emph{return "6 bytes read"} +++-> @code{F6} +++@end smallexample +++ +++Example sequence of a read call, call fails on the host due to invalid +++file descriptor (@code{EBADF}): +++ +++@smallexample +++<- @code{Fread,3,1234,6} +++-> @code{F-1,9} +++@end smallexample +++ +++Example sequence of a read call, user presses @kbd{Ctrl-c} before syscall on +++host is called: +++ +++@smallexample +++<- @code{Fread,3,1234,6} +++-> @code{F-1,4,C} +++<- @code{T02} +++@end smallexample +++ +++Example sequence of a read call, user presses @kbd{Ctrl-c} after syscall on +++host is called: +++ +++@smallexample +++<- @code{Fread,3,1234,6} +++-> @code{X1234,6:XXXXXX} +++<- @code{T02} +++@end smallexample +++ +++@node Library List Format +++@section Library List Format +++@cindex library list format, remote protocol +++ +++On some platforms, a dynamic loader (e.g.@: @file{ld.so}) runs in the +++same process as your application to manage libraries. In this case, +++@value{GDBN} can use the loader's symbol table and normal memory +++operations to maintain a list of shared libraries. On other +++platforms, the operating system manages loaded libraries. +++@value{GDBN} can not retrieve the list of currently loaded libraries +++through memory operations, so it uses the @samp{qXfer:libraries:read} +++packet (@pxref{qXfer library list read}) instead. The remote stub +++queries the target's operating system and reports which libraries +++are loaded. +++ +++The @samp{qXfer:libraries:read} packet returns an XML document which +++lists loaded libraries and their offsets. Each library has an +++associated name and one or more segment or section base addresses, +++which report where the library was loaded in memory. +++ +++For the common case of libraries that are fully linked binaries, the +++library should have a list of segments. If the target supports +++dynamic linking of a relocatable object file, its library XML element +++should instead include a list of allocated sections. The segment or +++section bases are start addresses, not relocation offsets; they do not +++depend on the library's link-time base addresses. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++library lists. @xref{Expat}. +++ +++A simple memory map, with one loaded library relocated by a single +++offset, looks like this: +++ +++@smallexample +++ +++ +++ +++ +++ +++@end smallexample +++ +++Another simple memory map, with one loaded library with three +++allocated sections (.text, .data, .bss), looks like this: +++ +++@smallexample +++ +++ +++
+++
+++
+++ +++ +++@end smallexample +++ +++The format of a library list is described by this DTD: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++In addition, segments and section descriptors cannot be mixed within a +++single library element, and you must supply at least one segment or +++section for each library. +++ +++@node Library List Format for SVR4 Targets +++@section Library List Format for SVR4 Targets +++@cindex library list format, remote protocol +++ +++On SVR4 platforms @value{GDBN} can use the symbol table of a dynamic loader +++(e.g.@: @file{ld.so}) and normal memory operations to maintain a list of +++shared libraries. Still a special library list provided by this packet is +++more efficient for the @value{GDBN} remote protocol. +++ +++The @samp{qXfer:libraries-svr4:read} packet returns an XML document which lists +++loaded libraries and their SVR4 linker parameters. For each library on SVR4 +++target, the following parameters are reported: +++ +++@itemize @minus +++@item +++@code{name}, the absolute file name from the @code{l_name} field of +++@code{struct link_map}. +++@item +++@code{lm} with address of @code{struct link_map} used for TLS +++(Thread Local Storage) access. +++@item +++@code{l_addr}, the displacement as read from the field @code{l_addr} of +++@code{struct link_map}. For prelinked libraries this is not an absolute +++memory address. It is a displacement of absolute memory address against +++address the file was prelinked to during the library load. +++@item +++@code{l_ld}, which is memory address of the @code{PT_DYNAMIC} segment +++@end itemize +++ +++Additionally the single @code{main-lm} attribute specifies address of +++@code{struct link_map} used for the main executable. This parameter is used +++for TLS access and its presence is optional. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++SVR4 library lists. @xref{Expat}. +++ +++A simple memory map, with two loaded libraries (which do not use prelink), +++looks like this: +++ +++@smallexample +++ +++ +++ +++ +++@end smallexample +++ +++The format of an SVR4 library list is described by this DTD: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++@node Memory Map Format +++@section Memory Map Format +++@cindex memory map format +++ +++To be able to write into flash memory, @value{GDBN} needs to obtain a +++memory map from the target. This section describes the format of the +++memory map. +++ +++The memory map is obtained using the @samp{qXfer:memory-map:read} +++(@pxref{qXfer memory map read}) packet and is an XML document that +++lists memory regions. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++memory maps. @xref{Expat}. +++ +++The top-level structure of the document is shown below: +++ +++@smallexample +++ +++ +++ +++ region... +++ +++@end smallexample +++ +++Each region can be either: +++ +++@itemize +++ +++@item +++A region of RAM starting at @var{addr} and extending for @var{length} +++bytes from there: +++ +++@smallexample +++ +++@end smallexample +++ +++ +++@item +++A region of read-only memory: +++ +++@smallexample +++ +++@end smallexample +++ +++ +++@item +++A region of flash memory, with erasure blocks @var{blocksize} +++bytes in length: +++ +++@smallexample +++ +++ @var{blocksize} +++ +++@end smallexample +++ +++@end itemize +++ +++Regions must not overlap. @value{GDBN} assumes that areas of memory not covered +++by the memory map are RAM, and uses the ordinary @samp{M} and @samp{X} +++packets to write to addresses in such ranges. +++ +++The formal DTD for memory map format is given below: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++@node Thread List Format +++@section Thread List Format +++@cindex thread list format +++ +++To efficiently update the list of threads and their attributes, +++@value{GDBN} issues the @samp{qXfer:threads:read} packet +++(@pxref{qXfer threads read}) and obtains the XML document with +++the following structure: +++ +++@smallexample +++ +++ +++ +++ ... description ... +++ +++ +++@end smallexample +++ +++Each @samp{thread} element must have the @samp{id} attribute that +++identifies the thread (@pxref{thread-id syntax}). The +++@samp{core} attribute, if present, specifies which processor core +++the thread was last executing on. The @samp{name} attribute, if +++present, specifies the human-readable name of the thread. The content +++of the of @samp{thread} element is interpreted as human-readable +++auxiliary information. The @samp{handle} attribute, if present, +++is a hex encoded representation of the thread handle. +++ +++ +++@node Traceframe Info Format +++@section Traceframe Info Format +++@cindex traceframe info format +++ +++To be able to know which objects in the inferior can be examined when +++inspecting a tracepoint hit, @value{GDBN} needs to obtain the list of +++memory ranges, registers and trace state variables that have been +++collected in a traceframe. +++ +++This list is obtained using the @samp{qXfer:traceframe-info:read} +++(@pxref{qXfer traceframe info read}) packet and is an XML document. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++traceframe info discovery. @xref{Expat}. +++ +++The top-level structure of the document is shown below: +++ +++@smallexample +++ +++ +++ +++ block... +++ +++@end smallexample +++ +++Each traceframe block can be either: +++ +++@itemize +++ +++@item +++A region of collected memory starting at @var{addr} and extending for +++@var{length} bytes from there: +++ +++@smallexample +++ +++@end smallexample +++ +++@item +++A block indicating trace state variable numbered @var{number} has been +++collected: +++ +++@smallexample +++ +++@end smallexample +++ +++@end itemize +++ +++The formal DTD for the traceframe info format is given below: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++@node Branch Trace Format +++@section Branch Trace Format +++@cindex branch trace format +++ +++In order to display the branch trace of an inferior thread, +++@value{GDBN} needs to obtain the list of branches. This list is +++represented as list of sequential code blocks that are connected via +++branches. The code in each block has been executed sequentially. +++ +++This list is obtained using the @samp{qXfer:btrace:read} +++(@pxref{qXfer btrace read}) packet and is an XML document. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++traceframe info discovery. @xref{Expat}. +++ +++The top-level structure of the document is shown below: +++ +++@smallexample +++ +++ +++ +++ block... +++ +++@end smallexample +++ +++@itemize +++ +++@item +++A block of sequentially executed instructions starting at @var{begin} +++and ending at @var{end}: +++ +++@smallexample +++ +++@end smallexample +++ +++@end itemize +++ +++The formal DTD for the branch trace format is given below: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++@node Branch Trace Configuration Format +++@section Branch Trace Configuration Format +++@cindex branch trace configuration format +++ +++For each inferior thread, @value{GDBN} can obtain the branch trace +++configuration using the @samp{qXfer:btrace-conf:read} +++(@pxref{qXfer btrace-conf read}) packet. +++ +++The configuration describes the branch trace format and configuration +++settings for that format. The following information is described: +++ +++@table @code +++@item bts +++This thread uses the @dfn{Branch Trace Store} (@acronym{BTS}) format. +++@table @code +++@item size +++The size of the @acronym{BTS} ring buffer in bytes. +++@end table +++@item pt +++This thread uses the @dfn{Intel Processor Trace} (@acronym{Intel +++PT}) format. +++@table @code +++@item size +++The size of the @acronym{Intel PT} ring buffer in bytes. +++@end table +++@end table +++ +++@value{GDBN} must be linked with the Expat library to support XML +++branch trace configuration discovery. @xref{Expat}. +++ +++The formal DTD for the branch trace configuration format is given below: +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++@include agentexpr.texi +++ +++@node Target Descriptions +++@appendix Target Descriptions +++@cindex target descriptions +++ +++One of the challenges of using @value{GDBN} to debug embedded systems +++is that there are so many minor variants of each processor +++architecture in use. It is common practice for vendors to start with +++a standard processor core --- ARM, PowerPC, or @acronym{MIPS}, for example --- +++and then make changes to adapt it to a particular market niche. Some +++architectures have hundreds of variants, available from dozens of +++vendors. This leads to a number of problems: +++ +++@itemize @bullet +++@item +++With so many different customized processors, it is difficult for +++the @value{GDBN} maintainers to keep up with the changes. +++@item +++Since individual variants may have short lifetimes or limited +++audiences, it may not be worthwhile to carry information about every +++variant in the @value{GDBN} source tree. +++@item +++When @value{GDBN} does support the architecture of the embedded system +++at hand, the task of finding the correct architecture name to give the +++@command{set architecture} command can be error-prone. +++@end itemize +++ +++To address these problems, the @value{GDBN} remote protocol allows a +++target system to not only identify itself to @value{GDBN}, but to +++actually describe its own features. This lets @value{GDBN} support +++processor variants it has never seen before --- to the extent that the +++descriptions are accurate, and that @value{GDBN} understands them. +++ +++@value{GDBN} must be linked with the Expat library to support XML +++target descriptions. @xref{Expat}. +++ +++@menu +++* Retrieving Descriptions:: How descriptions are fetched from a target. +++* Target Description Format:: The contents of a target description. +++* Predefined Target Types:: Standard types available for target +++ descriptions. +++* Enum Target Types:: How to define enum target types. +++* Standard Target Features:: Features @value{GDBN} knows about. +++@end menu +++ +++@node Retrieving Descriptions +++@section Retrieving Descriptions +++ +++Target descriptions can be read from the target automatically, or +++specified by the user manually. The default behavior is to read the +++description from the target. @value{GDBN} retrieves it via the remote +++protocol using @samp{qXfer} requests (@pxref{General Query Packets, +++qXfer}). The @var{annex} in the @samp{qXfer} packet will be +++@samp{target.xml}. The contents of the @samp{target.xml} annex are an +++XML document, of the form described in @ref{Target Description +++Format}. +++ +++Alternatively, you can specify a file to read for the target description. +++If a file is set, the target will not be queried. The commands to +++specify a file are: +++ +++@table @code +++@cindex set tdesc filename +++@item set tdesc filename @var{path} +++Read the target description from @var{path}. +++ +++@cindex unset tdesc filename +++@item unset tdesc filename +++Do not read the XML target description from a file. @value{GDBN} +++will use the description supplied by the current target. +++ +++@cindex show tdesc filename +++@item show tdesc filename +++Show the filename to read for a target description, if any. +++@end table +++ +++ +++@node Target Description Format +++@section Target Description Format +++@cindex target descriptions, XML format +++ +++A target description annex is an @uref{http://www.w3.org/XML/, XML} +++document which complies with the Document Type Definition provided in +++the @value{GDBN} sources in @file{gdb/features/gdb-target.dtd}. This +++means you can use generally available tools like @command{xmllint} to +++check that your feature descriptions are well-formed and valid. +++However, to help people unfamiliar with XML write descriptions for +++their targets, we also describe the grammar here. +++ +++Target descriptions can identify the architecture of the remote target +++and (for some architectures) provide information about custom register +++sets. They can also identify the OS ABI of the remote target. +++@value{GDBN} can use this information to autoconfigure for your +++target, or to warn you if you connect to an unsupported target. +++ +++Here is a simple target description: +++ +++@smallexample +++ +++ i386:x86-64 +++ +++@end smallexample +++ +++@noindent +++This minimal description only says that the target uses +++the x86-64 architecture. +++ +++A target description has the following overall form, with [ ] marking +++optional elements and @dots{} marking repeatable elements. The elements +++are explained further below. +++ +++@smallexample +++ +++ +++ +++ @r{[}@var{architecture}@r{]} +++ @r{[}@var{osabi}@r{]} +++ @r{[}@var{compatible}@r{]} +++ @r{[}@var{feature}@dots{}@r{]} +++ +++@end smallexample +++ +++@noindent +++The description is generally insensitive to whitespace and line +++breaks, under the usual common-sense rules. The XML version +++declaration and document type declaration can generally be omitted +++(@value{GDBN} does not require them), but specifying them may be +++useful for XML validation tools. The @samp{version} attribute for +++@samp{} may also be omitted, but we recommend +++including it; if future versions of @value{GDBN} use an incompatible +++revision of @file{gdb-target.dtd}, they will detect and report +++the version mismatch. +++ +++@subsection Inclusion +++@cindex target descriptions, inclusion +++@cindex XInclude +++@ifnotinfo +++@cindex +++@end ifnotinfo +++ +++It can sometimes be valuable to split a target description up into +++several different annexes, either for organizational purposes, or to +++share files between different possible target descriptions. You can +++divide a description into multiple files by replacing any element of +++the target description with an inclusion directive of the form: +++ +++@smallexample +++ +++@end smallexample +++ +++@noindent +++When @value{GDBN} encounters an element of this form, it will retrieve +++the named XML @var{document}, and replace the inclusion directive with +++the contents of that document. If the current description was read +++using @samp{qXfer}, then so will be the included document; +++@var{document} will be interpreted as the name of an annex. If the +++current description was read from a file, @value{GDBN} will look for +++@var{document} as a file in the same directory where it found the +++original description. +++ +++@subsection Architecture +++@cindex +++ +++An @samp{} element has this form: +++ +++@smallexample +++ @var{arch} +++@end smallexample +++ +++@var{arch} is one of the architectures from the set accepted by +++@code{set architecture} (@pxref{Targets, ,Specifying a Debugging Target}). +++ +++@subsection OS ABI +++@cindex @code{} +++ +++This optional field was introduced in @value{GDBN} version 7.0. +++Previous versions of @value{GDBN} ignore it. +++ +++An @samp{} element has this form: +++ +++@smallexample +++ @var{abi-name} +++@end smallexample +++ +++@var{abi-name} is an OS ABI name from the same selection accepted by +++@w{@code{set osabi}} (@pxref{ABI, ,Configuring the Current ABI}). +++ +++@subsection Compatible Architecture +++@cindex @code{} +++ +++This optional field was introduced in @value{GDBN} version 7.0. +++Previous versions of @value{GDBN} ignore it. +++ +++A @samp{} element has this form: +++ +++@smallexample +++ @var{arch} +++@end smallexample +++ +++@var{arch} is one of the architectures from the set accepted by +++@code{set architecture} (@pxref{Targets, ,Specifying a Debugging Target}). +++ +++A @samp{} element is used to specify that the target +++is able to run binaries in some other than the main target architecture +++given by the @samp{} element. For example, on the +++Cell Broadband Engine, the main architecture is @code{powerpc:common} +++or @code{powerpc:common64}, but the system is able to run binaries +++in the @code{spu} architecture as well. The way to describe this +++capability with @samp{} is as follows: +++ +++@smallexample +++ powerpc:common +++ spu +++@end smallexample +++ +++@subsection Features +++@cindex +++ +++Each @samp{} describes some logical portion of the target +++system. Features are currently used to describe available CPU +++registers and the types of their contents. A @samp{} element +++has this form: +++ +++@smallexample +++ +++ @r{[}@var{type}@dots{}@r{]} +++ @var{reg}@dots{} +++ +++@end smallexample +++ +++@noindent +++Each feature's name should be unique within the description. The name +++of a feature does not matter unless @value{GDBN} has some special +++knowledge of the contents of that feature; if it does, the feature +++should have its standard name. @xref{Standard Target Features}. +++ +++@subsection Types +++ +++Any register's value is a collection of bits which @value{GDBN} must +++interpret. The default interpretation is a two's complement integer, +++but other types can be requested by name in the register description. +++Some predefined types are provided by @value{GDBN} (@pxref{Predefined +++Target Types}), and the description can define additional composite +++and enum types. +++ +++Each type element must have an @samp{id} attribute, which gives +++a unique (within the containing @samp{}) name to the type. +++Types must be defined before they are used. +++ +++@cindex +++Some targets offer vector registers, which can be treated as arrays +++of scalar elements. These types are written as @samp{} elements, +++specifying the array element type, @var{type}, and the number of elements, +++@var{count}: +++ +++@smallexample +++ +++@end smallexample +++ +++@cindex +++If a register's value is usefully viewed in multiple ways, define it +++with a union type containing the useful representations. The +++@samp{} element contains one or more @samp{} elements, +++each of which has a @var{name} and a @var{type}: +++ +++@smallexample +++ +++ +++ @dots{} +++ +++@end smallexample +++ +++@cindex +++@cindex +++If a register's value is composed from several separate values, define +++it with either a structure type or a flags type. +++A flags type may only contain bitfields. +++A structure type may either contain only bitfields or contain no bitfields. +++If the value contains only bitfields, its total size in bytes must be +++specified. +++ +++Non-bitfield values have a @var{name} and @var{type}. +++ +++@smallexample +++ +++ +++ @dots{} +++ +++@end smallexample +++ +++Both @var{name} and @var{type} values are required. +++No implicit padding is added. +++ +++Bitfield values have a @var{name}, @var{start}, @var{end} and @var{type}. +++ +++@smallexample +++ +++ +++ @dots{} +++ +++@end smallexample +++ +++@smallexample +++ +++ +++ @dots{} +++ +++@end smallexample +++ +++The @var{name} value is required. +++Bitfield values may be named with the empty string, @samp{""}, +++in which case the field is ``filler'' and its value is not printed. +++Not all bits need to be specified, so ``filler'' fields are optional. +++ +++The @var{start} and @var{end} values are required, and @var{type} +++is optional. +++The field's @var{start} must be less than or equal to its @var{end}, +++and zero represents the least significant bit. +++ +++The default value of @var{type} is @code{bool} for single bit fields, +++and an unsigned integer otherwise. +++ +++Which to choose? Structures or flags? +++ +++Registers defined with @samp{flags} have these advantages over +++defining them with @samp{struct}: +++ +++@itemize @bullet +++@item +++Arithmetic may be performed on them as if they were integers. +++@item +++They are printed in a more readable fashion. +++@end itemize +++ +++Registers defined with @samp{struct} have one advantage over +++defining them with @samp{flags}: +++ +++@itemize @bullet +++@item +++One can fetch individual fields like in @samp{C}. +++ +++@smallexample +++(gdb) print $my_struct_reg.field3 +++$1 = 42 +++@end smallexample +++ +++@end itemize +++ +++@subsection Registers +++@cindex +++ +++Each register is represented as an element with this form: +++ +++@smallexample +++ +++@end smallexample +++ +++@noindent +++The components are as follows: +++ +++@table @var +++ +++@item name +++The register's name; it must be unique within the target description. +++ +++@item bitsize +++The register's size, in bits. +++ +++@item regnum +++The register's number. If omitted, a register's number is one greater +++than that of the previous register (either in the current feature or in +++a preceding feature); the first register in the target description +++defaults to zero. This register number is used to read or write +++the register; e.g.@: it is used in the remote @code{p} and @code{P} +++packets, and registers appear in the @code{g} and @code{G} packets +++in order of increasing register number. +++ +++@item save-restore +++Whether the register should be preserved across inferior function +++calls; this must be either @code{yes} or @code{no}. The default is +++@code{yes}, which is appropriate for most registers except for +++some system control registers; this is not related to the target's +++ABI. +++ +++@item type +++The type of the register. It may be a predefined type, a type +++defined in the current feature, or one of the special types @code{int} +++and @code{float}. @code{int} is an integer type of the correct size +++for @var{bitsize}, and @code{float} is a floating point type (in the +++architecture's normal floating point format) of the correct size for +++@var{bitsize}. The default is @code{int}. +++ +++@item group +++The register group to which this register belongs. It can be one of the +++standard register groups @code{general}, @code{float}, @code{vector} or an +++arbitrary string. Group names should be limited to alphanumeric characters. +++If a group name is made up of multiple words the words may be separated by +++hyphens; e.g.@: @code{special-group} or @code{ultra-special-group}. If no +++@var{group} is specified, @value{GDBN} will not display the register in +++@code{info registers}. +++ +++@end table +++ +++@node Predefined Target Types +++@section Predefined Target Types +++@cindex target descriptions, predefined types +++ +++Type definitions in the self-description can build up composite types +++from basic building blocks, but can not define fundamental types. Instead, +++standard identifiers are provided by @value{GDBN} for the fundamental +++types. The currently supported types are: +++ +++@table @code +++ +++@item bool +++Boolean type, occupying a single bit. +++ +++@item int8 +++@itemx int16 +++@itemx int24 +++@itemx int32 +++@itemx int64 +++@itemx int128 +++Signed integer types holding the specified number of bits. +++ +++@item uint8 +++@itemx uint16 +++@itemx uint24 +++@itemx uint32 +++@itemx uint64 +++@itemx uint128 +++Unsigned integer types holding the specified number of bits. +++ +++@item code_ptr +++@itemx data_ptr +++Pointers to unspecified code and data. The program counter and +++any dedicated return address register may be marked as code +++pointers; printing a code pointer converts it into a symbolic +++address. The stack pointer and any dedicated address registers +++may be marked as data pointers. +++ +++@item ieee_single +++Single precision IEEE floating point. +++ +++@item ieee_double +++Double precision IEEE floating point. +++ +++@item arm_fpa_ext +++The 12-byte extended precision format used by ARM FPA registers. +++ +++@item i387_ext +++The 10-byte extended precision format used by x87 registers. +++ +++@item i386_eflags +++32bit @sc{eflags} register used by x86. +++ +++@item i386_mxcsr +++32bit @sc{mxcsr} register used by x86. +++ +++@end table +++ +++@node Enum Target Types +++@section Enum Target Types +++@cindex target descriptions, enum types +++ +++Enum target types are useful in @samp{struct} and @samp{flags} +++register descriptions. @xref{Target Description Format}. +++ +++Enum types have a name, size and a list of name/value pairs. +++ +++@smallexample +++ +++ +++ @dots{} +++ +++@end smallexample +++ +++Enums must be defined before they are used. +++ +++@smallexample +++ +++ +++ +++ +++ +++ +++ +++ +++ +++@end smallexample +++ +++Given that description, a value of 3 for the @samp{flags} register +++would be printed as: +++ +++@smallexample +++(gdb) info register flags +++flags 0x3 [ X LEVEL=high ] +++@end smallexample +++ +++@node Standard Target Features +++@section Standard Target Features +++@cindex target descriptions, standard features +++ +++A target description must contain either no registers or all the +++target's registers. If the description contains no registers, then +++@value{GDBN} will assume a default register layout, selected based on +++the architecture. If the description contains any registers, the +++default layout will not be used; the standard registers must be +++described in the target description, in such a way that @value{GDBN} +++can recognize them. +++ +++This is accomplished by giving specific names to feature elements +++which contain standard registers. @value{GDBN} will look for features +++with those names and verify that they contain the expected registers; +++if any known feature is missing required registers, or if any required +++feature is missing, @value{GDBN} will reject the target +++description. You can add additional registers to any of the +++standard features --- @value{GDBN} will display them just as if +++they were added to an unrecognized feature. +++ +++This section lists the known features and their expected contents. +++Sample XML documents for these features are included in the +++@value{GDBN} source tree, in the directory @file{gdb/features}. +++ +++Names recognized by @value{GDBN} should include the name of the +++company or organization which selected the name, and the overall +++architecture to which the feature applies; so e.g.@: the feature +++containing ARM core registers is named @samp{org.gnu.gdb.arm.core}. +++ +++The names of registers are not case sensitive for the purpose +++of recognizing standard features, but @value{GDBN} will only display +++registers using the capitalization used in the description. +++ +++@menu +++* AArch64 Features:: +++* ARC Features:: +++* ARM Features:: +++* i386 Features:: +++* MicroBlaze Features:: +++* MIPS Features:: +++* M68K Features:: +++* NDS32 Features:: +++* Nios II Features:: +++* OpenRISC 1000 Features:: +++* PowerPC Features:: +++* RISC-V Features:: +++* RX Features:: +++* S/390 and System z Features:: +++* Sparc Features:: +++* TIC6x Features:: +++@end menu +++ +++ +++@node AArch64 Features +++@subsection AArch64 Features +++@cindex target descriptions, AArch64 features +++ +++The @samp{org.gnu.gdb.aarch64.core} feature is required for AArch64 +++targets. It should contain registers @samp{x0} through @samp{x30}, +++@samp{sp}, @samp{pc}, and @samp{cpsr}. +++ +++The @samp{org.gnu.gdb.aarch64.fpu} feature is optional. If present, +++it should contain registers @samp{v0} through @samp{v31}, @samp{fpsr}, +++and @samp{fpcr}. +++ +++The @samp{org.gnu.gdb.aarch64.sve} feature is optional. If present, +++it should contain registers @samp{z0} through @samp{z31}, @samp{p0} +++through @samp{p15}, @samp{ffr} and @samp{vg}. +++ +++The @samp{org.gnu.gdb.aarch64.pauth} feature is optional. If present, +++it should contain registers @samp{pauth_dmask} and @samp{pauth_cmask}. +++ +++@node ARC Features +++@subsection ARC Features +++@cindex target descriptions, ARC Features +++ +++ARC processors are so configurable that even core registers and their numbers +++are not predetermined completely. Moreover, @emph{flags} and @emph{PC} +++registers, which are important to @value{GDBN}, are not ``core'' registers in +++ARC. Therefore, there are two features that their presence is mandatory: +++@samp{org.gnu.gdb.arc.core} and @samp{org.gnu.gdb.arc.aux}. +++ +++The @samp{org.gnu.gdb.arc.core} feature is required for all targets. It must +++contain registers: +++ +++@itemize @minus +++@item +++@samp{r0} through @samp{r25} for normal register file targets. +++@item +++@samp{r0} through @samp{r3}, and @samp{r10} through @samp{r15} for reduced +++register file targets. +++@item +++@samp{gp}, @samp{fp}, @samp{sp}, @samp{r30}@footnote{Not necessary for ARCv1.}, +++@samp{blink}, @samp{lp_count}, @samp{pcl}. +++@end itemize +++ +++In case of an ARCompact target (ARCv1 ISA), the @samp{org.gnu.gdb.arc.core} +++feature may contain registers @samp{ilink1} and @samp{ilink2}. While in case +++of ARC EM and ARC HS targets (ARCv2 ISA), register @samp{ilink} may be present. +++The difference between ARCv1 and ARCv2 is the naming of registers @emph{29th} +++and @emph{30th}. They are called @samp{ilink1} and @samp{ilink2} for ARCv1 and +++are optional. For ARCv2, they are called @samp{ilink} and @samp{r30} and only +++@samp{ilink} is optional. The optionality of @samp{ilink*} registers is +++because of their inaccessibility during user space debugging sessions. +++ +++Extension core registers @samp{r32} through @samp{r59} are optional and their +++existence depends on the configuration. When debugging GNU/Linux applications, +++i.e.@: user space debugging, these core registers are not available. +++ +++The @samp{org.gnu.gdb.arc.aux} feature is required for all ARC targets. Here +++is the list of registers pertinent to this feature: +++ +++@itemize @minus +++@item +++mandatory: @samp{pc} and @samp{status32}. +++@item +++optional: @samp{lp_start}, @samp{lp_end}, and @samp{bta}. +++@end itemize +++ +++@node ARM Features +++@subsection ARM Features +++@cindex target descriptions, ARM features +++ +++The @samp{org.gnu.gdb.arm.core} feature is required for non-M-profile +++ARM targets. +++It should contain registers @samp{r0} through @samp{r13}, @samp{sp}, +++@samp{lr}, @samp{pc}, and @samp{cpsr}. +++ +++For M-profile targets (e.g. Cortex-M3), the @samp{org.gnu.gdb.arm.core} +++feature is replaced by @samp{org.gnu.gdb.arm.m-profile}. It should contain +++registers @samp{r0} through @samp{r13}, @samp{sp}, @samp{lr}, @samp{pc}, +++and @samp{xpsr}. +++ +++The @samp{org.gnu.gdb.arm.fpa} feature is optional. If present, it +++should contain registers @samp{f0} through @samp{f7} and @samp{fps}. +++ +++The @samp{org.gnu.gdb.xscale.iwmmxt} feature is optional. If present, +++it should contain at least registers @samp{wR0} through @samp{wR15} and +++@samp{wCGR0} through @samp{wCGR3}. The @samp{wCID}, @samp{wCon}, +++@samp{wCSSF}, and @samp{wCASF} registers are optional. +++ +++The @samp{org.gnu.gdb.arm.vfp} feature is optional. If present, it +++should contain at least registers @samp{d0} through @samp{d15}. If +++they are present, @samp{d16} through @samp{d31} should also be included. +++@value{GDBN} will synthesize the single-precision registers from +++halves of the double-precision registers. +++ +++The @samp{org.gnu.gdb.arm.neon} feature is optional. It does not +++need to contain registers; it instructs @value{GDBN} to display the +++VFP double-precision registers as vectors and to synthesize the +++quad-precision registers from pairs of double-precision registers. +++If this feature is present, @samp{org.gnu.gdb.arm.vfp} must also +++be present and include 32 double-precision registers. +++ +++@node i386 Features +++@subsection i386 Features +++@cindex target descriptions, i386 features +++ +++The @samp{org.gnu.gdb.i386.core} feature is required for i386/amd64 +++targets. It should describe the following registers: +++ +++@itemize @minus +++@item +++@samp{eax} through @samp{edi} plus @samp{eip} for i386 +++@item +++@samp{rax} through @samp{r15} plus @samp{rip} for amd64 +++@item +++@samp{eflags}, @samp{cs}, @samp{ss}, @samp{ds}, @samp{es}, +++@samp{fs}, @samp{gs} +++@item +++@samp{st0} through @samp{st7} +++@item +++@samp{fctrl}, @samp{fstat}, @samp{ftag}, @samp{fiseg}, @samp{fioff}, +++@samp{foseg}, @samp{fooff} and @samp{fop} +++@end itemize +++ +++The register sets may be different, depending on the target. +++ +++The @samp{org.gnu.gdb.i386.sse} feature is optional. It should +++describe registers: +++ +++@itemize @minus +++@item +++@samp{xmm0} through @samp{xmm7} for i386 +++@item +++@samp{xmm0} through @samp{xmm15} for amd64 +++@item +++@samp{mxcsr} +++@end itemize +++ +++The @samp{org.gnu.gdb.i386.avx} feature is optional and requires the +++@samp{org.gnu.gdb.i386.sse} feature. It should +++describe the upper 128 bits of @sc{ymm} registers: +++ +++@itemize @minus +++@item +++@samp{ymm0h} through @samp{ymm7h} for i386 +++@item +++@samp{ymm0h} through @samp{ymm15h} for amd64 +++@end itemize +++ +++The @samp{org.gnu.gdb.i386.mpx} is an optional feature representing Intel +++Memory Protection Extension (MPX). It should describe the following registers: +++ +++@itemize @minus +++@item +++@samp{bnd0raw} through @samp{bnd3raw} for i386 and amd64. +++@item +++@samp{bndcfgu} and @samp{bndstatus} for i386 and amd64. +++@end itemize +++ +++The @samp{org.gnu.gdb.i386.linux} feature is optional. It should +++describe a single register, @samp{orig_eax}. +++ +++The @samp{org.gnu.gdb.i386.segments} feature is optional. It should +++describe two system registers: @samp{fs_base} and @samp{gs_base}. +++ +++The @samp{org.gnu.gdb.i386.avx512} feature is optional and requires the +++@samp{org.gnu.gdb.i386.avx} feature. It should +++describe additional @sc{xmm} registers: +++ +++@itemize @minus +++@item +++@samp{xmm16h} through @samp{xmm31h}, only valid for amd64. +++@end itemize +++ +++It should describe the upper 128 bits of additional @sc{ymm} registers: +++ +++@itemize @minus +++@item +++@samp{ymm16h} through @samp{ymm31h}, only valid for amd64. +++@end itemize +++ +++It should +++describe the upper 256 bits of @sc{zmm} registers: +++ +++@itemize @minus +++@item +++@samp{zmm0h} through @samp{zmm7h} for i386. +++@item +++@samp{zmm0h} through @samp{zmm15h} for amd64. +++@end itemize +++ +++It should +++describe the additional @sc{zmm} registers: +++ +++@itemize @minus +++@item +++@samp{zmm16h} through @samp{zmm31h}, only valid for amd64. +++@end itemize +++ +++The @samp{org.gnu.gdb.i386.pkeys} feature is optional. It should +++describe a single register, @samp{pkru}. It is a 32-bit register +++valid for i386 and amd64. +++ +++@node MicroBlaze Features +++@subsection MicroBlaze Features +++@cindex target descriptions, MicroBlaze features +++ +++The @samp{org.gnu.gdb.microblaze.core} feature is required for MicroBlaze +++targets. It should contain registers @samp{r0} through @samp{r31}, +++@samp{rpc}, @samp{rmsr}, @samp{rear}, @samp{resr}, @samp{rfsr}, @samp{rbtr}, +++@samp{rpvr}, @samp{rpvr1} through @samp{rpvr11}, @samp{redr}, @samp{rpid}, +++@samp{rzpr}, @samp{rtlbx}, @samp{rtlbsx}, @samp{rtlblo}, and @samp{rtlbhi}. +++ +++The @samp{org.gnu.gdb.microblaze.stack-protect} feature is optional. +++If present, it should contain registers @samp{rshr} and @samp{rslr} +++ +++@node MIPS Features +++@subsection @acronym{MIPS} Features +++@cindex target descriptions, @acronym{MIPS} features +++ +++The @samp{org.gnu.gdb.mips.cpu} feature is required for @acronym{MIPS} targets. +++It should contain registers @samp{r0} through @samp{r31}, @samp{lo}, +++@samp{hi}, and @samp{pc}. They may be 32-bit or 64-bit depending +++on the target. +++ +++The @samp{org.gnu.gdb.mips.cp0} feature is also required. It should +++contain at least the @samp{status}, @samp{badvaddr}, and @samp{cause} +++registers. They may be 32-bit or 64-bit depending on the target. +++ +++The @samp{org.gnu.gdb.mips.fpu} feature is currently required, though +++it may be optional in a future version of @value{GDBN}. It should +++contain registers @samp{f0} through @samp{f31}, @samp{fcsr}, and +++@samp{fir}. They may be 32-bit or 64-bit depending on the target. +++ +++The @samp{org.gnu.gdb.mips.dsp} feature is optional. It should +++contain registers @samp{hi1} through @samp{hi3}, @samp{lo1} through +++@samp{lo3}, and @samp{dspctl}. The @samp{dspctl} register should +++be 32-bit and the rest may be 32-bit or 64-bit depending on the target. +++ +++The @samp{org.gnu.gdb.mips.linux} feature is optional. It should +++contain a single register, @samp{restart}, which is used by the +++Linux kernel to control restartable syscalls. +++ +++@node M68K Features +++@subsection M68K Features +++@cindex target descriptions, M68K features +++ +++@table @code +++@item @samp{org.gnu.gdb.m68k.core} +++@itemx @samp{org.gnu.gdb.coldfire.core} +++@itemx @samp{org.gnu.gdb.fido.core} +++One of those features must be always present. +++The feature that is present determines which flavor of m68k is +++used. The feature that is present should contain registers +++@samp{d0} through @samp{d7}, @samp{a0} through @samp{a5}, @samp{fp}, +++@samp{sp}, @samp{ps} and @samp{pc}. +++ +++@item @samp{org.gnu.gdb.coldfire.fp} +++This feature is optional. If present, it should contain registers +++@samp{fp0} through @samp{fp7}, @samp{fpcontrol}, @samp{fpstatus} and +++@samp{fpiaddr}. +++ +++Note that, despite the fact that this feature's name says +++@samp{coldfire}, it is used to describe any floating point registers. +++The size of the registers must match the main m68k flavor; so, for +++example, if the primary feature is reported as @samp{coldfire}, then +++64-bit floating point registers are required. +++@end table +++ +++@node NDS32 Features +++@subsection NDS32 Features +++@cindex target descriptions, NDS32 features +++ +++The @samp{org.gnu.gdb.nds32.core} feature is required for NDS32 +++targets. It should contain at least registers @samp{r0} through +++@samp{r10}, @samp{r15}, @samp{fp}, @samp{gp}, @samp{lp}, @samp{sp}, +++and @samp{pc}. +++ +++The @samp{org.gnu.gdb.nds32.fpu} feature is optional. If present, +++it should contain 64-bit double-precision floating-point registers +++@samp{fd0} through @emph{fdN}, which should be @samp{fd3}, @samp{fd7}, +++@samp{fd15}, or @samp{fd31} based on the FPU configuration implemented. +++ +++@emph{Note:} The first sixteen 64-bit double-precision floating-point +++registers are overlapped with the thirty-two 32-bit single-precision +++floating-point registers. The 32-bit single-precision registers, if +++not being listed explicitly, will be synthesized from halves of the +++overlapping 64-bit double-precision registers. Listing 32-bit +++single-precision registers explicitly is deprecated, and the +++support to it could be totally removed some day. +++ +++@node Nios II Features +++@subsection Nios II Features +++@cindex target descriptions, Nios II features +++ +++The @samp{org.gnu.gdb.nios2.cpu} feature is required for Nios II +++targets. It should contain the 32 core registers (@samp{zero}, +++@samp{at}, @samp{r2} through @samp{r23}, @samp{et} through @samp{ra}), +++@samp{pc}, and the 16 control registers (@samp{status} through +++@samp{mpuacc}). +++ +++@node OpenRISC 1000 Features +++@subsection Openrisc 1000 Features +++@cindex target descriptions, OpenRISC 1000 features +++ +++The @samp{org.gnu.gdb.or1k.group0} feature is required for OpenRISC 1000 +++targets. It should contain the 32 general purpose registers (@samp{r0} +++through @samp{r31}), @samp{ppc}, @samp{npc} and @samp{sr}. +++ +++@node PowerPC Features +++@subsection PowerPC Features +++@cindex target descriptions, PowerPC features +++ +++The @samp{org.gnu.gdb.power.core} feature is required for PowerPC +++targets. It should contain registers @samp{r0} through @samp{r31}, +++@samp{pc}, @samp{msr}, @samp{cr}, @samp{lr}, @samp{ctr}, and +++@samp{xer}. They may be 32-bit or 64-bit depending on the target. +++ +++The @samp{org.gnu.gdb.power.fpu} feature is optional. It should +++contain registers @samp{f0} through @samp{f31} and @samp{fpscr}. +++ +++The @samp{org.gnu.gdb.power.altivec} feature is optional. It should +++contain registers @samp{vr0} through @samp{vr31}, @samp{vscr}, and +++@samp{vrsave}. @value{GDBN} will define pseudo-registers @samp{v0} +++through @samp{v31} as aliases for the corresponding @samp{vrX} +++registers. +++ +++The @samp{org.gnu.gdb.power.vsx} feature is optional. It should +++contain registers @samp{vs0h} through @samp{vs31h}. @value{GDBN} will +++combine these registers with the floating point registers (@samp{f0} +++through @samp{f31}) and the altivec registers (@samp{vr0} through +++@samp{vr31}) to present the 128-bit wide registers @samp{vs0} through +++@samp{vs63}, the set of vector-scalar registers for POWER7. +++Therefore, this feature requires both @samp{org.gnu.gdb.power.fpu} and +++@samp{org.gnu.gdb.power.altivec}. +++ +++The @samp{org.gnu.gdb.power.spe} feature is optional. It should +++contain registers @samp{ev0h} through @samp{ev31h}, @samp{acc}, and +++@samp{spefscr}. SPE targets should provide 32-bit registers in +++@samp{org.gnu.gdb.power.core} and provide the upper halves in +++@samp{ev0h} through @samp{ev31h}. @value{GDBN} will combine +++these to present registers @samp{ev0} through @samp{ev31} to the +++user. +++ +++The @samp{org.gnu.gdb.power.ppr} feature is optional. It should +++contain the 64-bit register @samp{ppr}. +++ +++The @samp{org.gnu.gdb.power.dscr} feature is optional. It should +++contain the 64-bit register @samp{dscr}. +++ +++The @samp{org.gnu.gdb.power.tar} feature is optional. It should +++contain the 64-bit register @samp{tar}. +++ +++The @samp{org.gnu.gdb.power.ebb} feature is optional. It should +++contain registers @samp{bescr}, @samp{ebbhr} and @samp{ebbrr}, all +++64-bit wide. +++ +++The @samp{org.gnu.gdb.power.linux.pmu} feature is optional. It should +++contain registers @samp{mmcr0}, @samp{mmcr2}, @samp{siar}, @samp{sdar} +++and @samp{sier}, all 64-bit wide. This is the subset of the isa 2.07 +++server PMU registers provided by @sc{gnu}/Linux. +++ +++The @samp{org.gnu.gdb.power.htm.spr} feature is optional. It should +++contain registers @samp{tfhar}, @samp{texasr} and @samp{tfiar}, all +++64-bit wide. +++ +++The @samp{org.gnu.gdb.power.htm.core} feature is optional. It should +++contain the checkpointed general-purpose registers @samp{cr0} through +++@samp{cr31}, as well as the checkpointed registers @samp{clr} and +++@samp{cctr}. These registers may all be either 32-bit or 64-bit +++depending on the target. It should also contain the checkpointed +++registers @samp{ccr} and @samp{cxer}, which should both be 32-bit +++wide. +++ +++The @samp{org.gnu.gdb.power.htm.fpu} feature is optional. It should +++contain the checkpointed 64-bit floating-point registers @samp{cf0} +++through @samp{cf31}, as well as the checkpointed 64-bit register +++@samp{cfpscr}. +++ +++The @samp{org.gnu.gdb.power.htm.altivec} feature is optional. It +++should contain the checkpointed altivec registers @samp{cvr0} through +++@samp{cvr31}, all 128-bit wide. It should also contain the +++checkpointed registers @samp{cvscr} and @samp{cvrsave}, both 32-bit +++wide. +++ +++The @samp{org.gnu.gdb.power.htm.vsx} feature is optional. It should +++contain registers @samp{cvs0h} through @samp{cvs31h}. @value{GDBN} +++will combine these registers with the checkpointed floating point +++registers (@samp{cf0} through @samp{cf31}) and the checkpointed +++altivec registers (@samp{cvr0} through @samp{cvr31}) to present the +++128-bit wide checkpointed vector-scalar registers @samp{cvs0} through +++@samp{cvs63}. Therefore, this feature requires both +++@samp{org.gnu.gdb.power.htm.altivec} and +++@samp{org.gnu.gdb.power.htm.fpu}. +++ +++The @samp{org.gnu.gdb.power.htm.ppr} feature is optional. It should +++contain the 64-bit checkpointed register @samp{cppr}. +++ +++The @samp{org.gnu.gdb.power.htm.dscr} feature is optional. It should +++contain the 64-bit checkpointed register @samp{cdscr}. +++ +++The @samp{org.gnu.gdb.power.htm.tar} feature is optional. It should +++contain the 64-bit checkpointed register @samp{ctar}. +++ +++ +++@node RISC-V Features +++@subsection RISC-V Features +++@cindex target descriptions, RISC-V Features +++ +++The @samp{org.gnu.gdb.riscv.cpu} feature is required for RISC-V +++targets. It should contain the registers @samp{x0} through +++@samp{x31}, and @samp{pc}. Either the architectural names (@samp{x0}, +++@samp{x1}, etc) can be used, or the ABI names (@samp{zero}, @samp{ra}, +++etc). +++ +++The @samp{org.gnu.gdb.riscv.fpu} feature is optional. If present, it +++should contain registers @samp{f0} through @samp{f31}, @samp{fflags}, +++@samp{frm}, and @samp{fcsr}. As with the cpu feature, either the +++architectural register names, or the ABI names can be used. +++ +++The @samp{org.gnu.gdb.riscv.virtual} feature is optional. If present, +++it should contain registers that are not backed by real registers on +++the target, but are instead virtual, where the register value is +++derived from other target state. In many ways these are like +++@value{GDBN}s pseudo-registers, except implemented by the target. +++Currently the only register expected in this set is the one byte +++@samp{priv} register that contains the target's privilege level in the +++least significant two bits. +++ +++The @samp{org.gnu.gdb.riscv.csr} feature is optional. If present, it +++should contain all of the target's standard CSRs. Standard CSRs are +++those defined in the RISC-V specification documents. There is some +++overlap between this feature and the fpu feature; the @samp{fflags}, +++@samp{frm}, and @samp{fcsr} registers could be in either feature. The +++expectation is that these registers will be in the fpu feature if the +++target has floating point hardware, but can be moved into the csr +++feature if the target has the floating point control registers, but no +++other floating point hardware. +++ +++@node RX Features +++@subsection RX Features +++@cindex target descriptions, RX Features +++ +++The @samp{org.gnu.gdb.rx.core} feature is required for RX +++targets. It should contain the registers @samp{r0} through +++@samp{r15}, @samp{usp}, @samp{isp}, @samp{psw}, @samp{pc}, @samp{intb}, +++@samp{bpsw}, @samp{bpc}, @samp{fintv}, @samp{fpsw}, and @samp{acc}. +++ +++@node S/390 and System z Features +++@subsection S/390 and System z Features +++@cindex target descriptions, S/390 features +++@cindex target descriptions, System z features +++ +++The @samp{org.gnu.gdb.s390.core} feature is required for S/390 and +++System z targets. It should contain the PSW and the 16 general +++registers. In particular, System z targets should provide the 64-bit +++registers @samp{pswm}, @samp{pswa}, and @samp{r0} through @samp{r15}. +++S/390 targets should provide the 32-bit versions of these registers. +++A System z target that runs in 31-bit addressing mode should provide +++32-bit versions of @samp{pswm} and @samp{pswa}, as well as the general +++register's upper halves @samp{r0h} through @samp{r15h}, and their +++lower halves @samp{r0l} through @samp{r15l}. +++ +++The @samp{org.gnu.gdb.s390.fpr} feature is required. It should +++contain the 64-bit registers @samp{f0} through @samp{f15}, and +++@samp{fpc}. +++ +++The @samp{org.gnu.gdb.s390.acr} feature is required. It should +++contain the 32-bit registers @samp{acr0} through @samp{acr15}. +++ +++The @samp{org.gnu.gdb.s390.linux} feature is optional. It should +++contain the register @samp{orig_r2}, which is 64-bit wide on System z +++targets and 32-bit otherwise. In addition, the feature may contain +++the @samp{last_break} register, whose width depends on the addressing +++mode, as well as the @samp{system_call} register, which is always +++32-bit wide. +++ +++The @samp{org.gnu.gdb.s390.tdb} feature is optional. It should +++contain the 64-bit registers @samp{tdb0}, @samp{tac}, @samp{tct}, +++@samp{atia}, and @samp{tr0} through @samp{tr15}. +++ +++The @samp{org.gnu.gdb.s390.vx} feature is optional. It should contain +++64-bit wide registers @samp{v0l} through @samp{v15l}, which will be +++combined by @value{GDBN} with the floating point registers @samp{f0} +++through @samp{f15} to present the 128-bit wide vector registers +++@samp{v0} through @samp{v15}. In addition, this feature should +++contain the 128-bit wide vector registers @samp{v16} through +++@samp{v31}. +++ +++The @samp{org.gnu.gdb.s390.gs} feature is optional. It should contain +++the 64-bit wide guarded-storage-control registers @samp{gsd}, +++@samp{gssm}, and @samp{gsepla}. +++ +++The @samp{org.gnu.gdb.s390.gsbc} feature is optional. It should contain +++the 64-bit wide guarded-storage broadcast control registers +++@samp{bc_gsd}, @samp{bc_gssm}, and @samp{bc_gsepla}. +++ +++@node Sparc Features +++@subsection Sparc Features +++@cindex target descriptions, sparc32 features +++@cindex target descriptions, sparc64 features +++The @samp{org.gnu.gdb.sparc.cpu} feature is required for sparc32/sparc64 +++targets. It should describe the following registers: +++ +++@itemize @minus +++@item +++@samp{g0} through @samp{g7} +++@item +++@samp{o0} through @samp{o7} +++@item +++@samp{l0} through @samp{l7} +++@item +++@samp{i0} through @samp{i7} +++@end itemize +++ +++They may be 32-bit or 64-bit depending on the target. +++ +++Also the @samp{org.gnu.gdb.sparc.fpu} feature is required for sparc32/sparc64 +++targets. It should describe the following registers: +++ +++@itemize @minus +++@item +++@samp{f0} through @samp{f31} +++@item +++@samp{f32} through @samp{f62} for sparc64 +++@end itemize +++ +++The @samp{org.gnu.gdb.sparc.cp0} feature is required for sparc32/sparc64 +++targets. It should describe the following registers: +++ +++@itemize @minus +++@item +++@samp{y}, @samp{psr}, @samp{wim}, @samp{tbr}, @samp{pc}, @samp{npc}, +++@samp{fsr}, and @samp{csr} for sparc32 +++@item +++@samp{pc}, @samp{npc}, @samp{state}, @samp{fsr}, @samp{fprs}, and @samp{y} +++for sparc64 +++@end itemize +++ +++@node TIC6x Features +++@subsection TMS320C6x Features +++@cindex target descriptions, TIC6x features +++@cindex target descriptions, TMS320C6x features +++The @samp{org.gnu.gdb.tic6x.core} feature is required for TMS320C6x +++targets. It should contain registers @samp{A0} through @samp{A15}, +++registers @samp{B0} through @samp{B15}, @samp{CSR} and @samp{PC}. +++ +++The @samp{org.gnu.gdb.tic6x.gp} feature is optional. It should +++contain registers @samp{A16} through @samp{A31} and @samp{B16} +++through @samp{B31}. +++ +++The @samp{org.gnu.gdb.tic6x.c6xp} feature is optional. It should +++contain registers @samp{TSR}, @samp{ILC} and @samp{RILC}. +++ +++@node Operating System Information +++@appendix Operating System Information +++@cindex operating system information +++ +++@menu +++* Process list:: +++@end menu +++ +++Users of @value{GDBN} often wish to obtain information about the state of +++the operating system running on the target---for example the list of +++processes, or the list of open files. This section describes the +++mechanism that makes it possible. This mechanism is similar to the +++target features mechanism (@pxref{Target Descriptions}), but focuses +++on a different aspect of target. +++ +++Operating system information is retrieved from the target via the +++remote protocol, using @samp{qXfer} requests (@pxref{qXfer osdata +++read}). The object name in the request should be @samp{osdata}, and +++the @var{annex} identifies the data to be fetched. +++ +++@node Process list +++@appendixsection Process list +++@cindex operating system information, process list +++ +++When requesting the process list, the @var{annex} field in the +++@samp{qXfer} request should be @samp{processes}. The returned data is +++an XML document. The formal syntax of this document is defined in +++@file{gdb/features/osdata.dtd}. +++ +++An example document is: +++ +++@smallexample +++ +++ +++ +++ +++ 1 +++ root +++ /sbin/init +++ 1,2,3 +++ +++ +++@end smallexample +++ +++Each item should include a column whose name is @samp{pid}. The value +++of that column should identify the process on the target. The +++@samp{user} and @samp{command} columns are optional, and will be +++displayed by @value{GDBN}. The @samp{cores} column, if present, +++should contain a comma-separated list of cores that this process +++is running on. Target may provide additional columns, +++which @value{GDBN} currently ignores. +++ +++@node Trace File Format +++@appendix Trace File Format +++@cindex trace file format +++ +++The trace file comes in three parts: a header, a textual description +++section, and a trace frame section with binary data. +++ +++The header has the form @code{\x7fTRACE0\n}. The first byte is +++@code{0x7f} so as to indicate that the file contains binary data, +++while the @code{0} is a version number that may have different values +++in the future. +++ +++The description section consists of multiple lines of @sc{ascii} text +++separated by newline characters (@code{0xa}). The lines may include a +++variety of optional descriptive or context-setting information, such +++as tracepoint definitions or register set size. @value{GDBN} will +++ignore any line that it does not recognize. An empty line marks the end +++of this section. +++ +++@table @code +++@item R @var{size} +++Specifies the size of a register block in bytes. This is equal to the +++size of a @code{g} packet payload in the remote protocol. @var{size} +++is an ascii decimal number. There should be only one such line in +++a single trace file. +++ +++@item status @var{status} +++Trace status. @var{status} has the same format as a @code{qTStatus} +++remote packet reply. There should be only one such line in a single trace +++file. +++ +++@item tp @var{payload} +++Tracepoint definition. The @var{payload} has the same format as +++@code{qTfP}/@code{qTsP} remote packet reply payload. A single tracepoint +++may take multiple lines of definition, corresponding to the multiple +++reply packets. +++ +++@item tsv @var{payload} +++Trace state variable definition. The @var{payload} has the same format as +++@code{qTfV}/@code{qTsV} remote packet reply payload. A single variable +++may take multiple lines of definition, corresponding to the multiple +++reply packets. +++ +++@item tdesc @var{payload} +++Target description in XML format. The @var{payload} is a single line of +++the XML file. All such lines should be concatenated together to get +++the original XML file. This file is in the same format as @code{qXfer} +++@code{features} payload, and corresponds to the main @code{target.xml} +++file. Includes are not allowed. +++ +++@end table +++ +++The trace frame section consists of a number of consecutive frames. +++Each frame begins with a two-byte tracepoint number, followed by a +++four-byte size giving the amount of data in the frame. The data in +++the frame consists of a number of blocks, each introduced by a +++character indicating its type (at least register, memory, and trace +++state variable). The data in this section is raw binary, not a +++hexadecimal or other encoding; its endianness matches the target's +++endianness. +++ +++@c FIXME bi-arch may require endianness/arch info in description section +++ +++@table @code +++@item R @var{bytes} +++Register block. The number and ordering of bytes matches that of a +++@code{g} packet in the remote protocol. Note that these are the +++actual bytes, in target order, not a hexadecimal encoding. +++ +++@item M @var{address} @var{length} @var{bytes}... +++Memory block. This is a contiguous block of memory, at the 8-byte +++address @var{address}, with a 2-byte length @var{length}, followed by +++@var{length} bytes. +++ +++@item V @var{number} @var{value} +++Trace state variable block. This records the 8-byte signed value +++@var{value} of trace state variable numbered @var{number}. +++ +++@end table +++ +++Future enhancements of the trace file format may include additional types +++of blocks. +++ +++@node Index Section Format +++@appendix @code{.gdb_index} section format +++@cindex .gdb_index section format +++@cindex index section format +++ +++This section documents the index section that is created by @code{save +++gdb-index} (@pxref{Index Files}). The index section is +++DWARF-specific; some knowledge of DWARF is assumed in this +++description. +++ +++The mapped index file format is designed to be directly +++@code{mmap}able on any architecture. In most cases, a datum is +++represented using a little-endian 32-bit integer value, called an +++@code{offset_type}. Big endian machines must byte-swap the values +++before using them. Exceptions to this rule are noted. The data is +++laid out such that alignment is always respected. +++ +++A mapped index consists of several areas, laid out in order. +++ +++@enumerate +++@item +++The file header. This is a sequence of values, of @code{offset_type} +++unless otherwise noted: +++ +++@enumerate +++@item +++The version number, currently 8. Versions 1, 2 and 3 are obsolete. +++Version 4 uses a different hashing function from versions 5 and 6. +++Version 6 includes symbols for inlined functions, whereas versions 4 +++and 5 do not. Version 7 adds attributes to the CU indices in the +++symbol table. Version 8 specifies that symbols from DWARF type units +++(@samp{DW_TAG_type_unit}) refer to the type unit's symbol table and not the +++compilation unit (@samp{DW_TAG_comp_unit}) using the type. +++ +++@value{GDBN} will only read version 4, 5, or 6 indices +++by specifying @code{set use-deprecated-index-sections on}. +++GDB has a workaround for potentially broken version 7 indices so it is +++currently not flagged as deprecated. +++ +++@item +++The offset, from the start of the file, of the CU list. +++ +++@item +++The offset, from the start of the file, of the types CU list. Note +++that this area can be empty, in which case this offset will be equal +++to the next offset. +++ +++@item +++The offset, from the start of the file, of the address area. +++ +++@item +++The offset, from the start of the file, of the symbol table. +++ +++@item +++The offset, from the start of the file, of the constant pool. +++@end enumerate +++ +++@item +++The CU list. This is a sequence of pairs of 64-bit little-endian +++values, sorted by the CU offset. The first element in each pair is +++the offset of a CU in the @code{.debug_info} section. The second +++element in each pair is the length of that CU. References to a CU +++elsewhere in the map are done using a CU index, which is just the +++0-based index into this table. Note that if there are type CUs, then +++conceptually CUs and type CUs form a single list for the purposes of +++CU indices. +++ +++@item +++The types CU list. This is a sequence of triplets of 64-bit +++little-endian values. In a triplet, the first value is the CU offset, +++the second value is the type offset in the CU, and the third value is +++the type signature. The types CU list is not sorted. +++ +++@item +++The address area. The address area consists of a sequence of address +++entries. Each address entry has three elements: +++ +++@enumerate +++@item +++The low address. This is a 64-bit little-endian value. +++ +++@item +++The high address. This is a 64-bit little-endian value. Like +++@code{DW_AT_high_pc}, the value is one byte beyond the end. +++ +++@item +++The CU index. This is an @code{offset_type} value. +++@end enumerate +++ +++@item +++The symbol table. This is an open-addressed hash table. The size of +++the hash table is always a power of 2. +++ +++Each slot in the hash table consists of a pair of @code{offset_type} +++values. The first value is the offset of the symbol's name in the +++constant pool. The second value is the offset of the CU vector in the +++constant pool. +++ +++If both values are 0, then this slot in the hash table is empty. This +++is ok because while 0 is a valid constant pool index, it cannot be a +++valid index for both a string and a CU vector. +++ +++The hash value for a table entry is computed by applying an +++iterative hash function to the symbol's name. Starting with an +++initial value of @code{r = 0}, each (unsigned) character @samp{c} in +++the string is incorporated into the hash using the formula depending on the +++index version: +++ +++@table @asis +++@item Version 4 +++The formula is @code{r = r * 67 + c - 113}. +++ +++@item Versions 5 to 7 +++The formula is @code{r = r * 67 + tolower (c) - 113}. +++@end table +++ +++The terminating @samp{\0} is not incorporated into the hash. +++ +++The step size used in the hash table is computed via +++@code{((hash * 17) & (size - 1)) | 1}, where @samp{hash} is the hash +++value, and @samp{size} is the size of the hash table. The step size +++is used to find the next candidate slot when handling a hash +++collision. +++ +++The names of C@t{++} symbols in the hash table are canonicalized. We +++don't currently have a simple description of the canonicalization +++algorithm; if you intend to create new index sections, you must read +++the code. +++ +++@item +++The constant pool. This is simply a bunch of bytes. It is organized +++so that alignment is correct: CU vectors are stored first, followed by +++strings. +++ +++A CU vector in the constant pool is a sequence of @code{offset_type} +++values. The first value is the number of CU indices in the vector. +++Each subsequent value is the index and symbol attributes of a CU in +++the CU list. This element in the hash table is used to indicate which +++CUs define the symbol and how the symbol is used. +++See below for the format of each CU index+attributes entry. +++ +++A string in the constant pool is zero-terminated. +++@end enumerate +++ +++Attributes were added to CU index values in @code{.gdb_index} version 7. +++If a symbol has multiple uses within a CU then there is one +++CU index+attributes value for each use. +++ +++The format of each CU index+attributes entry is as follows +++(bit 0 = LSB): +++ +++@table @asis +++ +++@item Bits 0-23 +++This is the index of the CU in the CU list. +++@item Bits 24-27 +++These bits are reserved for future purposes and must be zero. +++@item Bits 28-30 +++The kind of the symbol in the CU. +++ +++@table @asis +++@item 0 +++This value is reserved and should not be used. +++By reserving zero the full @code{offset_type} value is backwards compatible +++with previous versions of the index. +++@item 1 +++The symbol is a type. +++@item 2 +++The symbol is a variable or an enum value. +++@item 3 +++The symbol is a function. +++@item 4 +++Any other kind of symbol. +++@item 5,6,7 +++These values are reserved. +++@end table +++ +++@item Bit 31 +++This bit is zero if the value is global and one if it is static. +++ +++The determination of whether a symbol is global or static is complicated. +++The authorative reference is the file @file{dwarf2read.c} in +++@value{GDBN} sources. +++ +++@end table +++ +++This pseudo-code describes the computation of a symbol's kind and +++global/static attributes in the index. +++ +++@smallexample +++is_external = get_attribute (die, DW_AT_external); +++language = get_attribute (cu_die, DW_AT_language); +++switch (die->tag) +++ @{ +++ case DW_TAG_typedef: +++ case DW_TAG_base_type: +++ case DW_TAG_subrange_type: +++ kind = TYPE; +++ is_static = 1; +++ break; +++ case DW_TAG_enumerator: +++ kind = VARIABLE; +++ is_static = language != CPLUS; +++ break; +++ case DW_TAG_subprogram: +++ kind = FUNCTION; +++ is_static = ! (is_external || language == ADA); +++ break; +++ case DW_TAG_constant: +++ kind = VARIABLE; +++ is_static = ! is_external; +++ break; +++ case DW_TAG_variable: +++ kind = VARIABLE; +++ is_static = ! is_external; +++ break; +++ case DW_TAG_namespace: +++ kind = TYPE; +++ is_static = 0; +++ break; +++ case DW_TAG_class_type: +++ case DW_TAG_interface_type: +++ case DW_TAG_structure_type: +++ case DW_TAG_union_type: +++ case DW_TAG_enumeration_type: +++ kind = TYPE; +++ is_static = language != CPLUS; +++ break; +++ default: +++ assert (0); +++ @} +++@end smallexample +++ +++@node Man Pages +++@appendix Manual pages +++@cindex Man pages +++ +++@menu +++* gdb man:: The GNU Debugger man page +++* gdbserver man:: Remote Server for the GNU Debugger man page +++* gcore man:: Generate a core file of a running program +++* gdbinit man:: gdbinit scripts +++* gdb-add-index man:: Add index files to speed up GDB +++@end menu +++ +++@node gdb man +++@heading gdb man +++ +++@c man title gdb The GNU Debugger +++ +++@c man begin SYNOPSIS gdb +++gdb [@option{-help}] [@option{-nh}] [@option{-nx}] [@option{-q}] +++[@option{-batch}] [@option{-cd=}@var{dir}] [@option{-f}] +++[@option{-b}@w{ }@var{bps}] +++ [@option{-tty=}@var{dev}] [@option{-s} @var{symfile}] +++[@option{-e}@w{ }@var{prog}] [@option{-se}@w{ }@var{prog}] +++[@option{-c}@w{ }@var{core}] [@option{-p}@w{ }@var{procID}] +++ [@option{-x}@w{ }@var{cmds}] [@option{-d}@w{ }@var{dir}] +++[@var{prog}|@var{prog} @var{procID}|@var{prog} @var{core}] +++@c man end +++ +++@c man begin DESCRIPTION gdb +++The purpose of a debugger such as @value{GDBN} is to allow you to see what is +++going on ``inside'' another program while it executes -- or what another +++program was doing at the moment it crashed. +++ +++@value{GDBN} can do four main kinds of things (plus other things in support of +++these) to help you catch bugs in the act: +++ +++@itemize @bullet +++@item +++Start your program, specifying anything that might affect its behavior. +++ +++@item +++Make your program stop on specified conditions. +++ +++@item +++Examine what has happened, when your program has stopped. +++ +++@item +++Change things in your program, so you can experiment with correcting the +++effects of one bug and go on to learn about another. +++@end itemize +++ +++You can use @value{GDBN} to debug programs written in C, C@t{++}, Fortran and +++Modula-2. +++ +++@value{GDBN} is invoked with the shell command @code{gdb}. Once started, it reads +++commands from the terminal until you tell it to exit with the @value{GDBN} +++command @code{quit}. You can get online help from @value{GDBN} itself +++by using the command @code{help}. +++ +++You can run @code{gdb} with no arguments or options; but the most +++usual way to start @value{GDBN} is with one argument or two, specifying an +++executable program as the argument: +++ +++@smallexample +++gdb program +++@end smallexample +++ +++You can also start with both an executable program and a core file specified: +++ +++@smallexample +++gdb program core +++@end smallexample +++ +++You can, instead, specify a process ID as a second argument or use option +++@code{-p}, if you want to debug a running process: +++ +++@smallexample +++gdb program 1234 +++gdb -p 1234 +++@end smallexample +++ +++@noindent +++would attach @value{GDBN} to process @code{1234}. With option @option{-p} you +++can omit the @var{program} filename. +++ +++Here are some of the most frequently needed @value{GDBN} commands: +++ +++@c pod2man highlights the right hand side of the @item lines. +++@table @env +++@item break [@var{file}:]@var{function} +++Set a breakpoint at @var{function} (in @var{file}). +++ +++@item run [@var{arglist}] +++Start your program (with @var{arglist}, if specified). +++ +++@item bt +++Backtrace: display the program stack. +++ +++@item print @var{expr} +++Display the value of an expression. +++ +++@item c +++Continue running your program (after stopping, e.g. at a breakpoint). +++ +++@item next +++Execute next program line (after stopping); step @emph{over} any +++function calls in the line. +++ +++@item edit [@var{file}:]@var{function} +++look at the program line where it is presently stopped. +++ +++@item list [@var{file}:]@var{function} +++type the text of the program in the vicinity of where it is presently stopped. +++ +++@item step +++Execute next program line (after stopping); step @emph{into} any +++function calls in the line. +++ +++@item help [@var{name}] +++Show information about @value{GDBN} command @var{name}, or general information +++about using @value{GDBN}. +++ +++@item quit +++Exit from @value{GDBN}. +++@end table +++ +++@ifset man +++For full details on @value{GDBN}, +++see @cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++by Richard M. Stallman and Roland H. Pesch. The same text is available online +++as the @code{gdb} entry in the @code{info} program. +++@end ifset +++@c man end +++ +++@c man begin OPTIONS gdb +++Any arguments other than options specify an executable +++file and core file (or process ID); that is, the first argument +++encountered with no +++associated option flag is equivalent to a @option{-se} option, and the second, +++if any, is equivalent to a @option{-c} option if it's the name of a file. +++Many options have +++both long and short forms; both are shown here. The long forms are also +++recognized if you truncate them, so long as enough of the option is +++present to be unambiguous. (If you prefer, you can flag option +++arguments with @option{+} rather than @option{-}, though we illustrate the +++more usual convention.) +++ +++All the options and command line arguments you give are processed +++in sequential order. The order makes a difference when the @option{-x} +++option is used. +++ +++@table @env +++@item -help +++@itemx -h +++List all options, with brief explanations. +++ +++@item -symbols=@var{file} +++@itemx -s @var{file} +++Read symbol table from file @var{file}. +++ +++@item -write +++Enable writing into executable and core files. +++ +++@item -exec=@var{file} +++@itemx -e @var{file} +++Use file @var{file} as the executable file to execute when +++appropriate, and for examining pure data in conjunction with a core +++dump. +++ +++@item -se=@var{file} +++Read symbol table from file @var{file} and use it as the executable +++file. +++ +++@item -core=@var{file} +++@itemx -c @var{file} +++Use file @var{file} as a core dump to examine. +++ +++@item -command=@var{file} +++@itemx -x @var{file} +++Execute @value{GDBN} commands from file @var{file}. +++ +++@item -ex @var{command} +++Execute given @value{GDBN} @var{command}. +++ +++@item -directory=@var{directory} +++@itemx -d @var{directory} +++Add @var{directory} to the path to search for source files. +++ +++@item -nh +++Do not execute commands from @file{~/.gdbinit}. +++ +++@item -nx +++@itemx -n +++Do not execute commands from any @file{.gdbinit} initialization files. +++ +++@item -quiet +++@itemx -q +++``Quiet''. Do not print the introductory and copyright messages. These +++messages are also suppressed in batch mode. +++ +++@item -batch +++Run in batch mode. Exit with status @code{0} after processing all the command +++files specified with @option{-x} (and @file{.gdbinit}, if not inhibited). +++Exit with nonzero status if an error occurs in executing the @value{GDBN} +++commands in the command files. +++ +++Batch mode may be useful for running @value{GDBN} as a filter, for example to +++download and run a program on another computer; in order to make this +++more useful, the message +++ +++@smallexample +++Program exited normally. +++@end smallexample +++ +++@noindent +++(which is ordinarily issued whenever a program running under @value{GDBN} control +++terminates) is not issued when running in batch mode. +++ +++@item -cd=@var{directory} +++Run @value{GDBN} using @var{directory} as its working directory, +++instead of the current directory. +++ +++@item -fullname +++@itemx -f +++Emacs sets this option when it runs @value{GDBN} as a subprocess. It tells +++@value{GDBN} to output the full file name and line number in a standard, +++recognizable fashion each time a stack frame is displayed (which +++includes each time the program stops). This recognizable format looks +++like two @samp{\032} characters, followed by the file name, line number +++and character position separated by colons, and a newline. The +++Emacs-to-@value{GDBN} interface program uses the two @samp{\032} +++characters as a signal to display the source code for the frame. +++ +++@item -b @var{bps} +++Set the line speed (baud rate or bits per second) of any serial +++interface used by @value{GDBN} for remote debugging. +++ +++@item -tty=@var{device} +++Run using @var{device} for your program's standard input and output. +++@end table +++@c man end +++ +++@c man begin SEEALSO gdb +++@ifset man +++The full documentation for @value{GDBN} is maintained as a Texinfo manual. +++If the @code{info} and @code{gdb} programs and @value{GDBN}'s Texinfo +++documentation are properly installed at your site, the command +++ +++@smallexample +++info gdb +++@end smallexample +++ +++@noindent +++should give you access to the complete manual. +++ +++@cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++Richard M. Stallman and Roland H. Pesch, July 1991. +++@end ifset +++@c man end +++ +++@node gdbserver man +++@heading gdbserver man +++ +++@c man title gdbserver Remote Server for the GNU Debugger +++@format +++@c man begin SYNOPSIS gdbserver +++gdbserver @var{comm} @var{prog} [@var{args}@dots{}] +++ +++gdbserver --attach @var{comm} @var{pid} +++ +++gdbserver --multi @var{comm} +++@c man end +++@end format +++ +++@c man begin DESCRIPTION gdbserver +++@command{gdbserver} is a program that allows you to run @value{GDBN} on a different machine +++than the one which is running the program being debugged. +++ +++@ifclear man +++@subheading Usage (server (target) side) +++@end ifclear +++@ifset man +++Usage (server (target) side): +++@end ifset +++ +++First, you need to have a copy of the program you want to debug put onto +++the target system. The program can be stripped to save space if needed, as +++@command{gdbserver} doesn't care about symbols. All symbol handling is taken care of by +++the @value{GDBN} running on the host system. +++ +++To use the server, you log on to the target system, and run the @command{gdbserver} +++program. You must tell it (a) how to communicate with @value{GDBN}, (b) the name of +++your program, and (c) its arguments. The general syntax is: +++ +++@smallexample +++target> gdbserver @var{comm} @var{program} [@var{args} ...] +++@end smallexample +++ +++For example, using a serial port, you might say: +++ +++@smallexample +++@ifset man +++@c @file would wrap it as F. +++target> gdbserver /dev/com1 emacs foo.txt +++@end ifset +++@ifclear man +++target> gdbserver @file{/dev/com1} emacs foo.txt +++@end ifclear +++@end smallexample +++ +++This tells @command{gdbserver} to debug emacs with an argument of foo.txt, and +++to communicate with @value{GDBN} via @file{/dev/com1}. @command{gdbserver} now +++waits patiently for the host @value{GDBN} to communicate with it. +++ +++To use a TCP connection, you could say: +++ +++@smallexample +++target> gdbserver host:2345 emacs foo.txt +++@end smallexample +++ +++This says pretty much the same thing as the last example, except that we are +++going to communicate with the @code{host} @value{GDBN} via TCP. The @code{host:2345} argument means +++that we are expecting to see a TCP connection from @code{host} to local TCP port +++2345. (Currently, the @code{host} part is ignored.) You can choose any number you +++want for the port number as long as it does not conflict with any existing TCP +++ports on the target system. This same port number must be used in the host +++@value{GDBN}s @code{target remote} command, which will be described shortly. Note that if +++you chose a port number that conflicts with another service, @command{gdbserver} will +++print an error message and exit. +++ +++@command{gdbserver} can also attach to running programs. +++This is accomplished via the @option{--attach} argument. The syntax is: +++ +++@smallexample +++target> gdbserver --attach @var{comm} @var{pid} +++@end smallexample +++ +++@var{pid} is the process ID of a currently running process. It isn't +++necessary to point @command{gdbserver} at a binary for the running process. +++ +++To start @code{gdbserver} without supplying an initial command to run +++or process ID to attach, use the @option{--multi} command line option. +++In such case you should connect using @kbd{target extended-remote} to start +++the program you want to debug. +++ +++@smallexample +++target> gdbserver --multi @var{comm} +++@end smallexample +++ +++@ifclear man +++@subheading Usage (host side) +++@end ifclear +++@ifset man +++Usage (host side): +++@end ifset +++ +++You need an unstripped copy of the target program on your host system, since +++@value{GDBN} needs to examine its symbol tables and such. Start up @value{GDBN} as you normally +++would, with the target program as the first argument. (You may need to use the +++@option{--baud} option if the serial line is running at anything except 9600 baud.) +++That is @code{gdb TARGET-PROG}, or @code{gdb --baud BAUD TARGET-PROG}. After that, the only +++new command you need to know about is @code{target remote} +++(or @code{target extended-remote}). Its argument is either +++a device name (usually a serial device, like @file{/dev/ttyb}), or a @code{HOST:PORT} +++descriptor. For example: +++ +++@smallexample +++@ifset man +++@c @file would wrap it as F. +++(gdb) target remote /dev/ttyb +++@end ifset +++@ifclear man +++(gdb) target remote @file{/dev/ttyb} +++@end ifclear +++@end smallexample +++ +++@noindent +++communicates with the server via serial line @file{/dev/ttyb}, and: +++ +++@smallexample +++(gdb) target remote the-target:2345 +++@end smallexample +++ +++@noindent +++communicates via a TCP connection to port 2345 on host `the-target', where +++you previously started up @command{gdbserver} with the same port number. Note that for +++TCP connections, you must start up @command{gdbserver} prior to using the `target remote' +++command, otherwise you may get an error that looks something like +++`Connection refused'. +++ +++@command{gdbserver} can also debug multiple inferiors at once, +++described in +++@ifset man +++the @value{GDBN} manual in node @code{Inferiors Connections and Programs} +++-- shell command @code{info -f gdb -n 'Inferiors Connections and Programs'}. +++@end ifset +++@ifclear man +++@ref{Inferiors Connections and Programs}. +++@end ifclear +++In such case use the @code{extended-remote} @value{GDBN} command variant: +++ +++@smallexample +++(gdb) target extended-remote the-target:2345 +++@end smallexample +++ +++The @command{gdbserver} option @option{--multi} may or may not be used in such +++case. +++@c man end +++ +++@c man begin OPTIONS gdbserver +++There are three different modes for invoking @command{gdbserver}: +++ +++@itemize @bullet +++ +++@item +++Debug a specific program specified by its program name: +++ +++@smallexample +++gdbserver @var{comm} @var{prog} [@var{args}@dots{}] +++@end smallexample +++ +++The @var{comm} parameter specifies how should the server communicate +++with @value{GDBN}; it is either a device name (to use a serial line), +++a TCP port number (@code{:1234}), or @code{-} or @code{stdio} to use +++stdin/stdout of @code{gdbserver}. Specify the name of the program to +++debug in @var{prog}. Any remaining arguments will be passed to the +++program verbatim. When the program exits, @value{GDBN} will close the +++connection, and @code{gdbserver} will exit. +++ +++@item +++Debug a specific program by specifying the process ID of a running +++program: +++ +++@smallexample +++gdbserver --attach @var{comm} @var{pid} +++@end smallexample +++ +++The @var{comm} parameter is as described above. Supply the process ID +++of a running program in @var{pid}; @value{GDBN} will do everything +++else. Like with the previous mode, when the process @var{pid} exits, +++@value{GDBN} will close the connection, and @code{gdbserver} will exit. +++ +++@item +++Multi-process mode -- debug more than one program/process: +++ +++@smallexample +++gdbserver --multi @var{comm} +++@end smallexample +++ +++In this mode, @value{GDBN} can instruct @command{gdbserver} which +++command(s) to run. Unlike the other 2 modes, @value{GDBN} will not +++close the connection when a process being debugged exits, so you can +++debug several processes in the same session. +++@end itemize +++ +++In each of the modes you may specify these options: +++ +++@table @env +++ +++@item --help +++List all options, with brief explanations. +++ +++@item --version +++This option causes @command{gdbserver} to print its version number and exit. +++ +++@item --attach +++@command{gdbserver} will attach to a running program. The syntax is: +++ +++@smallexample +++target> gdbserver --attach @var{comm} @var{pid} +++@end smallexample +++ +++@var{pid} is the process ID of a currently running process. It isn't +++necessary to point @command{gdbserver} at a binary for the running process. +++ +++@item --multi +++To start @code{gdbserver} without supplying an initial command to run +++or process ID to attach, use this command line option. +++Then you can connect using @kbd{target extended-remote} and start +++the program you want to debug. The syntax is: +++ +++@smallexample +++target> gdbserver --multi @var{comm} +++@end smallexample +++ +++@item --debug +++Instruct @code{gdbserver} to display extra status information about the debugging +++process. +++This option is intended for @code{gdbserver} development and for bug reports to +++the developers. +++ +++@item --remote-debug +++Instruct @code{gdbserver} to display remote protocol debug output. +++This option is intended for @code{gdbserver} development and for bug reports to +++the developers. +++ +++@item --debug-file=@var{filename} +++Instruct @code{gdbserver} to send any debug output to the given @var{filename}. +++This option is intended for @code{gdbserver} development and for bug reports to +++the developers. +++ +++@item --debug-format=option1@r{[},option2,...@r{]} +++Instruct @code{gdbserver} to include extra information in each line +++of debugging output. +++@xref{Other Command-Line Arguments for gdbserver}. +++ +++@item --wrapper +++Specify a wrapper to launch programs +++for debugging. The option should be followed by the name of the +++wrapper, then any command-line arguments to pass to the wrapper, then +++@kbd{--} indicating the end of the wrapper arguments. +++ +++@item --once +++By default, @command{gdbserver} keeps the listening TCP port open, so that +++additional connections are possible. However, if you start @code{gdbserver} +++with the @option{--once} option, it will stop listening for any further +++connection attempts after connecting to the first @value{GDBN} session. +++ +++@c --disable-packet is not documented for users. +++ +++@c --disable-randomization and --no-disable-randomization are superseded by +++@c QDisableRandomization. +++ +++@end table +++@c man end +++ +++@c man begin SEEALSO gdbserver +++@ifset man +++The full documentation for @value{GDBN} is maintained as a Texinfo manual. +++If the @code{info} and @code{gdb} programs and @value{GDBN}'s Texinfo +++documentation are properly installed at your site, the command +++ +++@smallexample +++info gdb +++@end smallexample +++ +++should give you access to the complete manual. +++ +++@cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++Richard M. Stallman and Roland H. Pesch, July 1991. +++@end ifset +++@c man end +++ +++@node gcore man +++@heading gcore +++ +++@c man title gcore Generate a core file of a running program +++ +++@format +++@c man begin SYNOPSIS gcore +++gcore [-a] [-o @var{prefix}] @var{pid1} [@var{pid2}...@var{pidN}] +++@c man end +++@end format +++ +++@c man begin DESCRIPTION gcore +++Generate core dumps of one or more running programs with process IDs +++@var{pid1}, @var{pid2}, etc. A core file produced by @command{gcore} +++is equivalent to one produced by the kernel when the process crashes +++(and when @kbd{ulimit -c} was used to set up an appropriate core dump +++limit). However, unlike after a crash, after @command{gcore} finishes +++its job the program remains running without any change. +++@c man end +++ +++@c man begin OPTIONS gcore +++@table @env +++@item -a +++Dump all memory mappings. The actual effect of this option depends on +++the Operating System. On @sc{gnu}/Linux, it will disable +++@code{use-coredump-filter} (@pxref{set use-coredump-filter}) and +++enable @code{dump-excluded-mappings} (@pxref{set +++dump-excluded-mappings}). +++ +++@item -o @var{prefix} +++The optional argument @var{prefix} specifies the prefix to be used +++when composing the file names of the core dumps. The file name is +++composed as @file{@var{prefix}.@var{pid}}, where @var{pid} is the +++process ID of the running program being analyzed by @command{gcore}. +++If not specified, @var{prefix} defaults to @var{gcore}. +++@end table +++@c man end +++ +++@c man begin SEEALSO gcore +++@ifset man +++The full documentation for @value{GDBN} is maintained as a Texinfo manual. +++If the @code{info} and @code{gdb} programs and @value{GDBN}'s Texinfo +++documentation are properly installed at your site, the command +++ +++@smallexample +++info gdb +++@end smallexample +++ +++@noindent +++should give you access to the complete manual. +++ +++@cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++Richard M. Stallman and Roland H. Pesch, July 1991. +++@end ifset +++@c man end +++ +++@node gdbinit man +++@heading gdbinit +++ +++@c man title gdbinit GDB initialization scripts +++ +++@format +++@c man begin SYNOPSIS gdbinit +++@ifset SYSTEM_GDBINIT +++@value{SYSTEM_GDBINIT} +++@end ifset +++ +++@ifset SYSTEM_GDBINIT_DIR +++@value{SYSTEM_GDBINIT_DIR}/* +++@end ifset +++ +++~/.gdbinit +++ +++./.gdbinit +++@c man end +++@end format +++ +++@c man begin DESCRIPTION gdbinit +++These files contain @value{GDBN} commands to automatically execute during +++@value{GDBN} startup. The lines of contents are canned sequences of commands, +++described in +++@ifset man +++the @value{GDBN} manual in node @code{Sequences} +++-- shell command @code{info -f gdb -n Sequences}. +++@end ifset +++@ifclear man +++@ref{Sequences}. +++@end ifclear +++ +++Please read more in +++@ifset man +++the @value{GDBN} manual in node @code{Startup} +++-- shell command @code{info -f gdb -n Startup}. +++@end ifset +++@ifclear man +++@ref{Startup}. +++@end ifclear +++ +++@table @env +++@ifset SYSTEM_GDBINIT +++@item @value{SYSTEM_GDBINIT} +++@end ifset +++@ifclear SYSTEM_GDBINIT +++@item (not enabled with @code{--with-system-gdbinit} during compilation) +++@end ifclear +++System-wide initialization file. It is executed unless user specified +++@value{GDBN} option @code{-nx} or @code{-n}. +++See more in +++@ifset man +++the @value{GDBN} manual in node @code{System-wide configuration} +++-- shell command @code{info -f gdb -n 'System-wide configuration'}. +++@end ifset +++@ifset SYSTEM_GDBINIT_DIR +++@item @value{SYSTEM_GDBINIT_DIR} +++@end ifset +++@ifclear SYSTEM_GDBINIT_DIR +++@item (not enabled with @code{--with-system-gdbinit-dir} during compilation) +++@end ifclear +++System-wide initialization directory. All files in this directory are +++executed on startup unless user specified @value{GDBN} option @code{-nx} or +++@code{-n}, as long as they have a recognized file extension. +++See more in +++@ifset man +++the @value{GDBN} manual in node @code{System-wide configuration} +++-- shell command @code{info -f gdb -n 'System-wide configuration'}. +++@end ifset +++@ifclear man +++@ref{System-wide configuration}. +++@end ifclear +++ +++@item ~/.gdbinit +++User initialization file. It is executed unless user specified +++@value{GDBN} options @code{-nx}, @code{-n} or @code{-nh}. +++ +++@item ./.gdbinit +++Initialization file for current directory. It may need to be enabled with +++@value{GDBN} security command @code{set auto-load local-gdbinit}. +++See more in +++@ifset man +++the @value{GDBN} manual in node @code{Init File in the Current Directory} +++-- shell command @code{info -f gdb -n 'Init File in the Current Directory'}. +++@end ifset +++@ifclear man +++@ref{Init File in the Current Directory}. +++@end ifclear +++@end table +++@c man end +++ +++@c man begin SEEALSO gdbinit +++@ifset man +++gdb(1), @code{info -f gdb -n Startup} +++ +++The full documentation for @value{GDBN} is maintained as a Texinfo manual. +++If the @code{info} and @code{gdb} programs and @value{GDBN}'s Texinfo +++documentation are properly installed at your site, the command +++ +++@smallexample +++info gdb +++@end smallexample +++ +++should give you access to the complete manual. +++ +++@cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++Richard M. Stallman and Roland H. Pesch, July 1991. +++@end ifset +++@c man end +++ +++@node gdb-add-index man +++@heading gdb-add-index +++@pindex gdb-add-index +++@anchor{gdb-add-index} +++ +++@c man title gdb-add-index Add index files to speed up GDB +++ +++@c man begin SYNOPSIS gdb-add-index +++gdb-add-index @var{filename} +++@c man end +++ +++@c man begin DESCRIPTION gdb-add-index +++When @value{GDBN} finds a symbol file, it scans the symbols in the +++file in order to construct an internal symbol table. This lets most +++@value{GDBN} operations work quickly--at the cost of a delay early on. +++For large programs, this delay can be quite lengthy, so @value{GDBN} +++provides a way to build an index, which speeds up startup. +++ +++To determine whether a file contains such an index, use the command +++@kbd{readelf -S filename}: the index is stored in a section named +++@code{.gdb_index}. The index file can only be produced on systems +++which use ELF binaries and DWARF debug information (i.e., sections +++named @code{.debug_*}). +++ +++@command{gdb-add-index} uses @value{GDBN} and @command{objdump} found +++in the @env{PATH} environment variable. If you want to use different +++versions of these programs, you can specify them through the +++@env{GDB} and @env{OBJDUMP} environment variables. +++ +++See more in +++@ifset man +++the @value{GDBN} manual in node @code{Index Files} +++-- shell command @kbd{info -f gdb -n "Index Files"}. +++@end ifset +++@ifclear man +++@ref{Index Files}. +++@end ifclear +++@c man end +++ +++@c man begin SEEALSO gdb-add-index +++@ifset man +++The full documentation for @value{GDBN} is maintained as a Texinfo manual. +++If the @code{info} and @code{gdb} programs and @value{GDBN}'s Texinfo +++documentation are properly installed at your site, the command +++ +++@smallexample +++info gdb +++@end smallexample +++ +++should give you access to the complete manual. +++ +++@cite{Using GDB: A Guide to the GNU Source-Level Debugger}, +++Richard M. Stallman and Roland H. Pesch, July 1991. +++@end ifset +++@c man end +++ +++@include gpl.texi +++ +++@node GNU Free Documentation License +++@appendix GNU Free Documentation License +++@include fdl.texi +++ +++@node Concept Index +++@unnumbered Concept Index +++ +++@printindex cp +++ +++@node Command and Variable Index +++@unnumbered Command, Variable, and Function Index +++ +++@printindex fn +++ +++@tex +++% I think something like @@colophon should be in texinfo. In the +++% meantime: +++\long\def\colophon{\hbox to0pt{}\vfill +++\centerline{The body of this manual is set in} +++\centerline{\fontname\tenrm,} +++\centerline{with headings in {\bf\fontname\tenbf}} +++\centerline{and examples in {\tt\fontname\tentt}.} +++\centerline{{\it\fontname\tenit\/},} +++\centerline{{\bf\fontname\tenbf}, and} +++\centerline{{\sl\fontname\tensl\/}} +++\centerline{are used for emphasis.}\vfill} +++\page\colophon +++% Blame: doc@@cygnus.com, 1991. +++@end tex +++ +++@bye ++diff -Nuar gdb-10.2/gdb/gdbtypes.c gdb-10.2/gdb/gdbtypes.c ++--- gdb-10.2/gdb/gdbtypes.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/gdbtypes.c 2025-04-16 17:06:41.932086800 +0800 ++@@ -5492,27 +5492,25 @@ ++ } ++ ++ /* Make a copy of the given TYPE, except that the pointer & reference ++- types are not preserved. ++- ++- This function assumes that the given type has an associated objfile. ++- This objfile is used to allocate the new type. */ +++ types are not preserved. */ ++ ++ struct type * ++ copy_type (const struct type *type) ++ { ++- struct type *new_type; +++ struct type *new_type = alloc_type_copy (type); ++ ++- gdb_assert (TYPE_OBJFILE_OWNED (type)); ++- ++- new_type = alloc_type_copy (type); ++ TYPE_INSTANCE_FLAGS (new_type) = TYPE_INSTANCE_FLAGS (type); ++ TYPE_LENGTH (new_type) = TYPE_LENGTH (type); ++ memcpy (TYPE_MAIN_TYPE (new_type), TYPE_MAIN_TYPE (type), ++ sizeof (struct main_type)); ++ if (type->main_type->dyn_prop_list != NULL) ++- new_type->main_type->dyn_prop_list ++- = copy_dynamic_prop_list (&TYPE_OBJFILE (type) -> objfile_obstack, ++- type->main_type->dyn_prop_list); +++ { +++ struct obstack *storage = (TYPE_OBJFILE_OWNED (type) +++ ? &TYPE_OBJFILE (type)->objfile_obstack +++ : gdbarch_obstack (TYPE_OWNER (type).gdbarch)); +++ new_type->main_type->dyn_prop_list +++ = copy_dynamic_prop_list (storage, type->main_type->dyn_prop_list); +++ } ++ ++ return new_type; ++ } ++diff -Nuar gdb-10.2/gdb/linux-waitpid.c gdb-10.2/gdb/linux-waitpid.c ++--- gdb-10.2/gdb/linux-waitpid.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/linux-waitpid.c 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,74 @@ +++/* Wrapper implementation for waitpid for GNU/Linux (LWP layer). +++ +++ Copyright (C) 2001-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "gdbsupport/common-defs.h" +++ +++#ifdef GDBSERVER +++/* FIXME: server.h is required for the definition of debug_threads +++ which is used in the gdbserver-specific debug printing in +++ linux_debug. This code should be made available to GDB also, +++ but the lack of a suitable flag to enable it prevents this. */ +++#include "server.h" +++#endif +++ +++#include "linux-nat.h" +++#include "linux-waitpid.h" +++#include "gdbsupport/gdb_wait.h" +++ +++/* Convert wait status STATUS to a string. Used for printing debug +++ messages only. */ +++ +++char * +++status_to_str (int status) +++{ +++ static char buf[64]; +++ +++ if (WIFSTOPPED (status)) +++ { +++ if (WSTOPSIG (status) == SYSCALL_SIGTRAP) +++ snprintf (buf, sizeof (buf), "%s (stopped at syscall)", +++ strsignal (SIGTRAP)); +++ else +++ snprintf (buf, sizeof (buf), "%s (stopped)", +++ strsignal (WSTOPSIG (status))); +++ } +++ else if (WIFSIGNALED (status)) +++ snprintf (buf, sizeof (buf), "%s (terminated)", +++ strsignal (WTERMSIG (status))); +++ else +++ snprintf (buf, sizeof (buf), "%d (exited)", WEXITSTATUS (status)); +++ +++ return buf; +++} +++ +++/* See linux-waitpid.h. */ +++ +++int +++my_waitpid (int pid, int *status, int flags) +++{ +++ int ret; +++ +++ do +++ { +++ ret = waitpid (pid, status, flags); +++ } +++ while (ret == -1 && errno == EINTR); +++ +++ return ret; +++} ++diff -Nuar gdb-10.2/gdb/linux-waitpid.h gdb-10.2/gdb/linux-waitpid.h ++--- gdb-10.2/gdb/linux-waitpid.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/linux-waitpid.h 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,31 @@ +++/* Wrapper for waitpid for GNU/Linux (LWP layer). +++ +++ Copyright (C) 2000-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#ifndef NAT_LINUX_WAITPID_H +++#define NAT_LINUX_WAITPID_H +++ +++#define MAXCGS 4//sw_64-linux-watch.c +++/* Wrapper function for waitpid which handles EINTR. */ +++extern int my_waitpid (int pid, int *status, int flags); +++ +++/* Convert wait status STATUS to a string. Used for printing debug +++ messages only. */ +++extern char *status_to_str (int status); +++ +++#endif /* NAT_LINUX_WAITPID_H */ ++diff -Nuar gdb-10.2/gdb/main.c gdb-10.2/gdb/main.c ++--- gdb-10.2/gdb/main.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/main.c 2025-04-16 17:06:41.902086800 +0800 ++@@ -392,6 +392,14 @@ ++ return; ++ } ++ +++#ifdef CRASH_MERGE +++extern "C" void update_gdb_hooks(void); +++extern "C" void main_loop(void); +++extern "C" unsigned long crash_get_kaslr_offset(void); +++extern "C" int console(const char *, ...); +++void crash_target_init (void); +++#endif +++ ++ /* Call command_loop. */ ++ ++ /* Prevent inlining this function for the benefit of GDB's selftests ++@@ -925,7 +933,11 @@ ++ } ++ } ++ +++#ifdef CRASH_MERGE +++ save_original_signals_state (1); +++#else ++ save_original_signals_state (quiet); +++#endif ++ ++ /* Try to set up an alternate signal stack for SIGSEGV handlers. */ ++ gdb::alternate_signal_stack signal_stack; ++@@ -999,7 +1011,7 @@ ++ { ++ print_gdb_version (gdb_stdout, false); ++ wrap_here (""); ++- printf_filtered ("\n"); +++ printf_filtered ("\n\n"); ++ exit (0); ++ } ++ ++@@ -1038,6 +1050,10 @@ ++ look at things by now. Initialize the default interpreter. */ ++ set_top_level_interpreter (interpreter_p); ++ +++#ifdef CRASH_MERGE +++ update_gdb_hooks(); +++#endif +++ ++ /* FIXME: cagney/2003-02-03: The big hack (part 2 of 2) that lets ++ GDB retain the old MI1 interpreter startup behavior. Output the ++ copyright message after the interpreter is installed when it is ++@@ -1066,7 +1082,11 @@ ++ if (!system_gdbinit.empty () && !inhibit_gdbinit) ++ { ++ for (const std::string &file : system_gdbinit) +++#ifdef CRASH_MERGE +++ ret = catch_command_errors (source_script, file.c_str (), -1); +++#else ++ ret = catch_command_errors (source_script, file.c_str (), 0); +++#endif ++ } ++ ++ /* Read and execute $HOME/.gdbinit file, if it exists. This is done ++@@ -1075,7 +1095,11 @@ ++ debugging or what directory you are in. */ ++ ++ if (!home_gdbinit.empty () && !inhibit_gdbinit && !inhibit_home_gdbinit) +++#ifdef CRASH_MERGE +++ ret = catch_command_errors (source_script, home_gdbinit.c_str (), -1); +++#else ++ ret = catch_command_errors (source_script, home_gdbinit.c_str (), 0); +++#endif ++ ++ /* Process '-ix' and '-iex' options early. */ ++ for (i = 0; i < cmdarg_vec.size (); i++) ++@@ -1121,7 +1145,11 @@ ++ !batch_flag); ++ if (ret != 0) ++ ret = catch_command_errors (symbol_file_add_main_adapter, +++#ifdef CRASH_MERGE +++ symarg, 0); +++#else ++ symarg, !batch_flag); +++#endif ++ } ++ else ++ { ++@@ -1191,7 +1219,11 @@ ++ { ++ auto_load_local_gdbinit_loaded = 1; ++ +++#ifdef CRASH_MERGE +++ ret = catch_command_errors (source_script, local_gdbinit.c_str (), -1); +++#else ++ ret = catch_command_errors (source_script, local_gdbinit.c_str (), 0); +++#endif ++ } ++ } ++ ++@@ -1242,6 +1274,16 @@ ++ ++ captured_main_1 (context); ++ +++#ifdef CRASH_MERGE +++ /* Relocate the vmlinux. */ +++ objfile_rebase (symfile_objfile, crash_get_kaslr_offset()); +++ +++ crash_target_init(); +++ +++ /* Back to crash. */ +++ main_loop(); +++#endif +++ ++ /* NOTE: cagney/1999-11-07: There is probably no reason for not ++ moving this loop and the code found in captured_command_loop() ++ into the command_loop() proper. The main thing holding back that ++@@ -1256,6 +1298,9 @@ ++ { ++ exception_print (gdb_stderr, ex); ++ } +++#ifdef CRASH_MERGE +++ console("\n"); +++#endif ++ } ++ /* No exit -- exit is through quit_command. */ ++ } ++@@ -1277,6 +1322,22 @@ ++ return 1; ++ } ++ +++#ifdef CRASH_MERGE +++/* +++ * NOTE: adapted from gdb.c, which is no longer built in; changed name of +++ * original main() to gdb_main_entry() for use as crash entry point +++ */ +++int +++gdb_main_entry (int argc, char **argv) +++{ +++ struct captured_main_args args; +++ memset (&args, 0, sizeof args); +++ args.argc = argc; +++ args.argv = argv; +++ args.interpreter_p = INTERP_CONSOLE; +++ return gdb_main (&args); +++} +++#endif ++ ++ /* Don't use *_filtered for printing help. We don't want to prompt ++ for continue no matter how small the screen or how much we're going ++diff -Nuar gdb-10.2/gdb/Makefile.in gdb-10.2/gdb/Makefile.in ++--- gdb-10.2/gdb/Makefile.in 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/Makefile.in 2025-04-16 17:06:51.932086800 +0800 ++@@ -1,4 +1,4 @@ ++-# Copyright (C) 1989-2021 Free Software Foundation, Inc. +++# Copyright (C) 1989-2020 Free Software Foundation, Inc. ++ ++ # This file is part of GDB. ++ ++@@ -571,7 +571,7 @@ ++ # It is also possible that you will need to add -I/usr/include/sys if ++ # your system doesn't have fcntl.h in /usr/include (which is where it ++ # should be according to Posix). ++-DEFS = @DEFS@ +++DEFS = -DCRASH_MERGE @DEFS@ ++ GDB_CFLAGS = -I. -I$(srcdir) -I$(srcdir)/config \ ++ -DLOCALEDIR="\"$(localedir)\"" $(DEFS) ++ ++@@ -676,6 +676,14 @@ ++ alpha-nbsd-tdep.o \ ++ alpha-obsd-tdep.o \ ++ alpha-tdep.o \ +++ sw_64-bsd-tdep.o \ +++ sw_64-bsd-nat.o \ +++ sw_64-linux-tdep.o \ +++ sw_64-mdebug-tdep.o \ +++ sw_64-nbsd-tdep.o \ +++ sw_64-obsd-tdep.o \ +++ sw_64-tdep.o \ +++ sw_64-linux-nat.o \ ++ amd64-darwin-tdep.o \ ++ amd64-dicos-tdep.o \ ++ amd64-fbsd-tdep.o \ ++@@ -1135,6 +1143,7 @@ ++ symmisc.c \ ++ symtab.c \ ++ target.c \ +++ ../../crash_target.c \ ++ target-connection.c \ ++ target-dcache.c \ ++ target-descriptions.c \ ++@@ -1211,6 +1220,9 @@ ++ addrmap.h \ ++ alpha-bsd-tdep.h \ ++ alpha-tdep.h \ +++ sw_64-bsd-tdep.h \ +++ sw_64-tdep.h \ +++ nat/sw_64-linux-watch.h \ ++ amd64-darwin-tdep.h \ ++ amd64-linux-tdep.h \ ++ amd64-nat.h \ ++@@ -1564,7 +1576,7 @@ ++ $(SUBDIR_TARGET_OBS) \ ++ $(SUBDIR_GCC_COMPILE_OBS) ++ ++-SUBDIRS = doc @subdirs@ data-directory +++SUBDIRS = build_no_subdirs ++ CLEANDIRS = $(SUBDIRS) ++ ++ # List of subdirectories in the build tree that must exist. ++@@ -1606,8 +1618,8 @@ ++ # Flags needed to compile Python code ++ PYTHON_CFLAGS = @PYTHON_CFLAGS@ ++ ++-all: gdb$(EXEEXT) $(CONFIG_ALL) gdb-gdb.py gdb-gdb.gdb ++- @$(MAKE) $(FLAGS_TO_PASS) DO=all "DODIRS=`echo $(SUBDIRS) | sed 's/testsuite//'`" subdir_do +++all: gdb$(EXEEXT) gdb-gdb.py gdb-gdb.gdb +++ @$(MAKE) -s $(FLAGS_TO_PASS) DO=all "DODIRS=`echo $(SUBDIRS) | sed 's/testsuite//'`" subdir_do ++ ++ # Rule for compiling .c files in the top-level gdb directory. ++ # The order-only dependencies ensure that we create the build subdirectories. ++@@ -1864,9 +1876,10 @@ ++ # Removing the old gdb first works better if it is running, at least on SunOS. ++ gdb$(EXEEXT): gdb.o $(LIBGDB_OBS) $(CDEPS) $(TDEPLIBS) ++ $(SILENCE) rm -f gdb$(EXEEXT) +++ @$(MAKE) -C ../.. GDB_FLAGS=-DGDB_10_2 library ++ $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) $(WIN32LDAPP) \ ++- -o gdb$(EXEEXT) gdb.o $(LIBGDB_OBS) \ ++- $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) +++ -o $(shell /bin/cat mergeobj) $(LIBGDB_OBS) \ +++ $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) $(shell /bin/cat mergelibs) ++ ifneq ($(CODESIGN_CERT),) ++ $(ECHO_SIGN) $(CODESIGN) -s $(CODESIGN_CERT) gdb$(EXEEXT) ++ endif ++@@ -2122,6 +2135,14 @@ ++ alpha-nbsd-tdep.c \ ++ alpha-obsd-tdep.c \ ++ alpha-tdep.c \ +++ sw_64-bsd-nat.c \ +++ sw_64-bsd-tdep.c \ +++ sw_64-linux-nat.c \ +++ sw_64-linux-tdep.c \ +++ sw_64-mdebug-tdep.c \ +++ sw_64-nbsd-tdep.c \ +++ sw_64-obsd-tdep.c \ +++ sw_64-tdep.c \ ++ amd64-bsd-nat.c \ ++ amd64-darwin-tdep.c \ ++ amd64-dicos-tdep.c \ ++@@ -2530,9 +2551,9 @@ ++ # into place if the compile succeeds. We need this because gcc does ++ # not atomically write the dependency output file. ++ override COMPILE.post = -c -o $@ -MT $@ -MMD -MP \ ++- -MF $(@D)/$(DEPDIR)/$(basename $(@F)).Tpo ++-override POSTCOMPILE = @mv $(@D)/$(DEPDIR)/$(basename $(@F)).Tpo \ ++- $(@D)/$(DEPDIR)/$(basename $(@F)).Po +++ -MF $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo +++override POSTCOMPILE = @mv $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo \ +++ $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Po ++ else ++ override COMPILE.pre = source='$<' object='$@' libtool=no \ ++ DEPDIR=$(DEPDIR) $(DEPMODE) $(depcomp) \ ++diff -Nuar gdb-10.2/gdb/Makefile.in.orig gdb-10.2/gdb/Makefile.in.orig ++--- gdb-10.2/gdb/Makefile.in.orig 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/Makefile.in.orig 2025-04-16 17:06:41.922086800 +0800 ++@@ -0,0 +1,2571 @@ +++# Copyright (C) 1989-2021 Free Software Foundation, Inc. +++ +++# This file is part of GDB. +++ +++# This program is free software; you can redistribute it and/or modify +++# it under the terms of the GNU General Public License as published by +++# the Free Software Foundation; either version 3 of the License, or +++# (at your option) any later version. +++# +++# This program is distributed in the hope that it will be useful, +++# but WITHOUT ANY WARRANTY; without even the implied warranty of +++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++# GNU General Public License for more details. +++# +++# You should have received a copy of the GNU General Public License +++# along with this program. If not, see . +++ +++# Please keep lists in this file sorted alphabetically, with one item per line. +++# Here are the general guidelines for ordering files and directories: +++# +++# - Files come before directories. +++# - The extensions are not taken into account when comparing filenames, except +++# if the filenames are otherwise equal. +++# - A filename that is a prefix of another one comes before. +++# - Underscores and dashes are treated equally, and come before alphanumeric +++# characters. +++# +++# For example: +++# +++# SOME_FILES = \ +++# foo.c \ +++# foo.h \ +++# foo-bar.c \ +++# foobar.c \ +++# foo/bar.c +++ +++prefix = @prefix@ +++exec_prefix = @exec_prefix@ +++ +++host_alias = @host_alias@ +++target_alias = @target_alias@ +++program_transform_name = @program_transform_name@ +++bindir = @bindir@ +++libdir = @libdir@ +++tooldir = $(libdir)/$(target_alias) +++ +++datadir = @datadir@ +++localedir = @localedir@ +++mandir = @mandir@ +++man1dir = $(mandir)/man1 +++man2dir = $(mandir)/man2 +++man3dir = $(mandir)/man3 +++man4dir = $(mandir)/man4 +++man5dir = $(mandir)/man5 +++man6dir = $(mandir)/man6 +++man7dir = $(mandir)/man7 +++man8dir = $(mandir)/man8 +++man9dir = $(mandir)/man9 +++infodir = @infodir@ +++datarootdir = @datarootdir@ +++docdir = @docdir@ +++htmldir = @htmldir@ +++pdfdir = @pdfdir@ +++includedir = @includedir@ +++ +++install_sh = @install_sh@ +++ +++# This can be referenced by `LIBINTL' as computed by +++# ZW_GNU_GETTEXT_SISTER_DIR. +++top_builddir = . +++ +++SHELL = @SHELL@ +++EXEEXT = @EXEEXT@ +++ +++AWK = @AWK@ +++LN_S = @LN_S@ +++ +++INSTALL = @INSTALL@ +++INSTALL_PROGRAM = @INSTALL_PROGRAM@ +++INSTALL_SCRIPT = @INSTALL_SCRIPT@ +++INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +++INSTALL_DATA = @INSTALL_DATA@ +++ +++DESTDIR = +++ +++AR = @AR@ +++AR_FLAGS = qv +++RANLIB = @RANLIB@ +++DLLTOOL = @DLLTOOL@ +++WINDRES = @WINDRES@ +++MIG = @MIG@ +++STRIP = @STRIP@ +++ +++XGETTEXT = @XGETTEXT@ +++GMSGFMT = @GMSGFMT@ +++MSGMERGE = msgmerge +++ +++PACKAGE = @PACKAGE@ +++CATALOGS = @CATALOGS@ +++ +++CC = @CC@ +++CXX = @CXX@ +++CXX_DIALECT = @CXX_DIALECT@ +++ +++# Dependency tracking information. +++DEPMODE = @CCDEPMODE@ +++DEPDIR = @DEPDIR@ +++depcomp = $(SHELL) $(srcdir)/../depcomp +++ +++# Directory containing source files. +++srcdir = @srcdir@ +++VPATH = @srcdir@ +++top_srcdir = @top_srcdir@ +++ +++include $(srcdir)/silent-rules.mk +++ +++# Note that these are overridden by GNU make-specific code below if +++# GNU make is used. The overrides implement dependency tracking. +++COMPILE.pre = $(CXX) -x c++ $(CXX_DIALECT) +++COMPILE.post = -c -o $@ +++COMPILE = $(ECHO_CXX) $(COMPILE.pre) $(INTERNAL_CFLAGS) $(COMPILE.post) +++POSTCOMPILE = @true +++ +++YACC = @YACC@ +++ +++# This is used to rebuild ada-lex.c from ada-lex.l. If the program is +++# not defined, but ada-lex.c is present, compilation will continue, +++# possibly with a warning. +++FLEX = flex +++ +++YLWRAP = $(srcdir)/../ylwrap +++ +++# where to find makeinfo, preferably one designed for texinfo-2 +++MAKEINFO = @MAKEINFO@ +++MAKEINFOFLAGS = @MAKEINFOFLAGS@ +++MAKEINFO_EXTRA_FLAGS = @MAKEINFO_EXTRA_FLAGS@ +++MAKEINFO_CMD = $(MAKEINFO) $(MAKEINFOFLAGS) $(MAKEINFO_EXTRA_FLAGS) +++ +++MAKEHTML = $(MAKEINFO_CMD) --html +++MAKEHTMLFLAGS = +++ +++# Set this up with gcc if you have gnu ld and the loader will print out +++# line numbers for undefined references. +++#CC_LD = g++ -static +++CC_LD = $(CXX) $(CXX_DIALECT) +++ +++# Where is our "include" directory? Typically $(srcdir)/../include. +++# This is essentially the header file directory for the library +++# routines in libiberty. +++INCLUDE_DIR = $(srcdir)/../include +++INCLUDE_CFLAGS = -I$(INCLUDE_DIR) +++ +++# Where is the "-liberty" library? Typically in ../libiberty. +++LIBIBERTY = ../libiberty/libiberty.a +++ +++# Where is the CTF library? Typically in ../libctf. +++LIBCTF = @LIBCTF@ +++CTF_DEPS = @CTF_DEPS@ +++ +++# Where is the BFD library? Typically in ../bfd. +++BFD_DIR = ../bfd +++BFD = $(BFD_DIR)/libbfd.a +++BFD_SRC = $(srcdir)/$(BFD_DIR) +++BFD_CFLAGS = -I$(BFD_DIR) -I$(BFD_SRC) +++ +++# This is where we get zlib from. zlibdir is -L../zlib and zlibinc is +++# -I../zlib, unless we were configured with --with-system-zlib, in which +++# case both are empty. +++ZLIB = @zlibdir@ -lz +++ZLIBINC = @zlibinc@ +++ +++# Where is the decnumber library? Typically in ../libdecnumber. +++LIBDECNUMBER_DIR = ../libdecnumber +++LIBDECNUMBER = $(LIBDECNUMBER_DIR)/libdecnumber.a +++LIBDECNUMBER_SRC = $(srcdir)/$(LIBDECNUMBER_DIR) +++LIBDECNUMBER_CFLAGS = -I$(LIBDECNUMBER_DIR) -I$(LIBDECNUMBER_SRC) +++ +++# Where is the READLINE library? Typically in ../readline/readline. +++READLINE_DIR = ../readline/readline +++READLINE_SRC = $(srcdir)/$(READLINE_DIR) +++READLINE = @READLINE@ +++READLINE_DEPS = @READLINE_DEPS@ +++READLINE_CFLAGS = @READLINE_CFLAGS@ +++ +++# Where is expat? This will be empty if expat was not available. +++LIBEXPAT = @LIBEXPAT@ +++ +++# Where is lzma? This will be empty if lzma was not available. +++LIBLZMA = @LIBLZMA@ +++ +++# Where is libbabeltrace? This will be empty if libbabeltrace was not +++# available. +++LIBBABELTRACE = @LIBBABELTRACE@ +++ +++# Where is libxxhash? This will be empty if libxxhash was not +++# available. +++LIBXXHASH = @LIBXXHASH@ +++ +++# Where is libipt? This will be empty if libipt was not available. +++LIBIPT = @LIBIPT@ +++ +++# Where is libmpfr? This will be empty if libmpfr was not available. +++LIBMPFR = @LIBMPFR@ +++ +++# GNU source highlight library. +++SRCHIGH_LIBS = @SRCHIGH_LIBS@ +++SRCHIGH_CFLAGS = @SRCHIGH_CFLAGS@ +++ +++WARN_CFLAGS = @WARN_CFLAGS@ +++WERROR_CFLAGS = @WERROR_CFLAGS@ +++GDB_WARN_CFLAGS = $(WARN_CFLAGS) +++GDB_WERROR_CFLAGS = $(WERROR_CFLAGS) +++ +++PTHREAD_CFLAGS = @PTHREAD_CFLAGS@ +++PTHREAD_LIBS = @PTHREAD_LIBS@ +++ +++DEBUGINFOD_CFLAGS = @DEBUGINFOD_CFLAGS@ +++DEBUGINFOD_LIBS = @DEBUGINFOD_LIBS@ +++ +++RDYNAMIC = @RDYNAMIC@ +++ +++# Where is the INTL library? Typically in ../intl. +++INTL = @LIBINTL@ +++INTL_DEPS = @LIBINTL_DEP@ +++INTL_CFLAGS = @INCINTL@ +++ +++# Where is the ICONV library? This will be empty if in libc or not available. +++LIBICONV = @LIBICONV@ +++ +++# Did the user give us a --with-gdb-datadir option? +++GDB_DATADIR = @GDB_DATADIR@ +++ +++# Code signing. +++CODESIGN = codesign +++CODESIGN_CERT = @CODESIGN_CERT@ +++ +++# Flags to pass to gdb when invoked with "make run". +++GDBFLAGS = +++ +++# Helper code from gnulib. +++GNULIB_BUILDDIR = ../gnulib +++LIBGNU = $(GNULIB_BUILDDIR)/import/libgnu.a +++INCGNU = -I$(srcdir)/../gnulib/import -I$(GNULIB_BUILDDIR)/import +++ +++SUPPORT = ../gdbsupport +++LIBSUPPORT = $(SUPPORT)/libgdbsupport.a +++INCSUPPORT = -I$(srcdir)/.. -I.. +++ +++# +++# CLI sub directory definitons +++# +++SUBDIR_CLI_SRCS = \ +++ cli/cli-cmds.c \ +++ cli/cli-decode.c \ +++ cli/cli-dump.c \ +++ cli/cli-interp.c \ +++ cli/cli-logging.c \ +++ cli/cli-option.c \ +++ cli/cli-script.c \ +++ cli/cli-setshow.c \ +++ cli/cli-style.c \ +++ cli/cli-utils.c +++ +++SUBDIR_CLI_OBS = $(patsubst %.c,%.o,$(SUBDIR_CLI_SRCS)) +++ +++# +++# MI sub directory definitons +++# +++SUBDIR_MI_SRCS = \ +++ mi/mi-cmd-break.c \ +++ mi/mi-cmd-catch.c \ +++ mi/mi-cmd-disas.c \ +++ mi/mi-cmd-env.c \ +++ mi/mi-cmd-file.c \ +++ mi/mi-cmd-info.c \ +++ mi/mi-cmd-stack.c \ +++ mi/mi-cmd-target.c \ +++ mi/mi-cmd-var.c \ +++ mi/mi-cmds.c \ +++ mi/mi-console.c \ +++ mi/mi-getopt.c \ +++ mi/mi-interp.c \ +++ mi/mi-main.c \ +++ mi/mi-out.c \ +++ mi/mi-parse.c \ +++ mi/mi-symbol-cmds.c +++ +++SUBDIR_MI_OBS = $(patsubst %.c,%.o,$(SUBDIR_MI_SRCS)) +++ +++SUBDIR_MI_DEPS = +++SUBDIR_MI_LDFLAGS = +++SUBDIR_MI_CFLAGS = +++ +++# +++# TUI sub directory definitions +++# +++SUBDIR_TUI_SRCS = \ +++ tui/tui.c \ +++ tui/tui-command.c \ +++ tui/tui-data.c \ +++ tui/tui-disasm.c \ +++ tui/tui-file.c \ +++ tui/tui-hooks.c \ +++ tui/tui-interp.c \ +++ tui/tui-io.c \ +++ tui/tui-layout.c \ +++ tui/tui-out.c \ +++ tui/tui-regs.c \ +++ tui/tui-source.c \ +++ tui/tui-stack.c \ +++ tui/tui-win.c \ +++ tui/tui-wingeneral.c \ +++ tui/tui-winsource.c +++ +++SUBDIR_TUI_OBS = $(patsubst %.c,%.o,$(SUBDIR_TUI_SRCS)) +++ +++SUBDIR_TUI_DEPS = +++SUBDIR_TUI_LDFLAGS = +++SUBDIR_TUI_CFLAGS = -DTUI=1 +++ +++# +++# GCC Compile support sub-directory definitions +++# +++SUBDIR_GCC_COMPILE_SRCS = \ +++ compile/compile.c \ +++ compile/compile-c-support.c \ +++ compile/compile-c-symbols.c \ +++ compile/compile-c-types.c \ +++ compile/compile-cplus-symbols.c \ +++ compile/compile-cplus-types.c \ +++ compile/compile-loc2c.c \ +++ compile/compile-object-load.c \ +++ compile/compile-object-run.c +++ +++SUBDIR_GCC_COMPILE_OBS = $(patsubst %.c,%.o,$(filter %.c,$(SUBDIR_GCC_COMPILE_SRCS))) +++ +++# +++# Guile sub directory definitons for guile support. +++# +++SUBDIR_GUILE_SRCS = \ +++ guile/guile.c \ +++ guile/scm-arch.c \ +++ guile/scm-auto-load.c \ +++ guile/scm-block.c \ +++ guile/scm-breakpoint.c \ +++ guile/scm-cmd.c \ +++ guile/scm-disasm.c \ +++ guile/scm-exception.c \ +++ guile/scm-frame.c \ +++ guile/scm-gsmob.c \ +++ guile/scm-iterator.c \ +++ guile/scm-lazy-string.c \ +++ guile/scm-math.c \ +++ guile/scm-objfile.c \ +++ guile/scm-param.c \ +++ guile/scm-ports.c \ +++ guile/scm-pretty-print.c \ +++ guile/scm-progspace.c \ +++ guile/scm-safe-call.c \ +++ guile/scm-string.c \ +++ guile/scm-symbol.c \ +++ guile/scm-symtab.c \ +++ guile/scm-type.c \ +++ guile/scm-utils.c \ +++ guile/scm-value.c +++ +++SUBDIR_GUILE_OBS = $(patsubst %.c,%.o,$(SUBDIR_GUILE_SRCS)) +++ +++SUBDIR_GUILE_DEPS = +++SUBDIR_GUILE_LDFLAGS = +++SUBDIR_GUILE_CFLAGS = +++ +++# +++# python sub directory definitons +++# +++SUBDIR_PYTHON_SRCS = \ +++ python/py-arch.c \ +++ python/py-auto-load.c \ +++ python/py-block.c \ +++ python/py-bpevent.c \ +++ python/py-breakpoint.c \ +++ python/py-cmd.c \ +++ python/py-continueevent.c \ +++ python/py-event.c \ +++ python/py-evtregistry.c \ +++ python/py-evts.c \ +++ python/py-exitedevent.c \ +++ python/py-finishbreakpoint.c \ +++ python/py-frame.c \ +++ python/py-framefilter.c \ +++ python/py-function.c \ +++ python/py-gdb-readline.c \ +++ python/py-inferior.c \ +++ python/py-infevents.c \ +++ python/py-infthread.c \ +++ python/py-instruction.c \ +++ python/py-lazy-string.c \ +++ python/py-linetable.c \ +++ python/py-newobjfileevent.c \ +++ python/py-objfile.c \ +++ python/py-param.c \ +++ python/py-prettyprint.c \ +++ python/py-progspace.c \ +++ python/py-record.c \ +++ python/py-record-btrace.c \ +++ python/py-record-full.c \ +++ python/py-registers.c \ +++ python/py-signalevent.c \ +++ python/py-stopevent.c \ +++ python/py-symbol.c \ +++ python/py-symtab.c \ +++ python/py-threadevent.c \ +++ python/py-tui.c \ +++ python/py-type.c \ +++ python/py-unwind.c \ +++ python/py-utils.c \ +++ python/py-value.c \ +++ python/py-varobj.c \ +++ python/py-xmethods.c \ +++ python/python.c +++ +++SUBDIR_PYTHON_OBS = $(patsubst %.c,%.o,$(SUBDIR_PYTHON_SRCS)) +++ +++SUBDIR_PYTHON_DEPS = +++SUBDIR_PYTHON_LDFLAGS = +++SUBDIR_PYTHON_CFLAGS = +++ +++SELFTESTS_SRCS = \ +++ disasm-selftests.c \ +++ gdbarch-selftests.c \ +++ selftest-arch.c \ +++ unittests/array-view-selftests.c \ +++ unittests/child-path-selftests.c \ +++ unittests/cli-utils-selftests.c \ +++ unittests/command-def-selftests.c \ +++ unittests/common-utils-selftests.c \ +++ unittests/copy_bitwise-selftests.c \ +++ unittests/environ-selftests.c \ +++ unittests/filtered_iterator-selftests.c \ +++ unittests/format_pieces-selftests.c \ +++ unittests/function-view-selftests.c \ +++ unittests/lookup_name_info-selftests.c \ +++ unittests/memory-map-selftests.c \ +++ unittests/memrange-selftests.c \ +++ unittests/offset-type-selftests.c \ +++ unittests/observable-selftests.c \ +++ unittests/optional-selftests.c \ +++ unittests/parse-connection-spec-selftests.c \ +++ unittests/ptid-selftests.c \ +++ unittests/main-thread-selftests.c \ +++ unittests/mkdir-recursive-selftests.c \ +++ unittests/rsp-low-selftests.c \ +++ unittests/scoped_fd-selftests.c \ +++ unittests/scoped_mmap-selftests.c \ +++ unittests/scoped_restore-selftests.c \ +++ unittests/string_view-selftests.c \ +++ unittests/style-selftests.c \ +++ unittests/tracepoint-selftests.c \ +++ unittests/tui-selftests.c \ +++ unittests/unpack-selftests.c \ +++ unittests/utils-selftests.c \ +++ unittests/vec-utils-selftests.c \ +++ unittests/xml-utils-selftests.c +++ +++SELFTESTS_OBS = $(patsubst %.c,%.o,$(SELFTESTS_SRCS)) +++ +++SUBDIR_TARGET_SRCS = target/waitstatus.c +++SUBDIR_TARGET_OBS = $(patsubst %.c,%.o,$(SUBDIR_TARGET_SRCS)) +++ +++ +++# Opcodes currently live in one of two places. Either they are in the +++# opcode library, typically ../opcodes, or they are in a header file +++# in INCLUDE_DIR. +++# Where is the "-lopcodes" library, with (some of) the opcode tables and +++# disassemblers? +++OPCODES_DIR = ../opcodes +++OPCODES_SRC = $(srcdir)/$(OPCODES_DIR) +++OPCODES = $(OPCODES_DIR)/libopcodes.a +++# Where are the other opcode tables which only have header file +++# versions? +++OP_INCLUDE = $(INCLUDE_DIR)/opcode +++# See TOP_CFLAGS as well. +++OPCODES_CFLAGS = -I$(OP_INCLUDE) +++ +++# Allow includes like "opcodes/mumble.h". +++TOP_CFLAGS = -I$(top_srcdir)/.. +++ +++# The simulator is usually nonexistent; targets that include one +++# should set this to list all the .o or .a files to be linked in. +++SIM = @SIM@ +++ +++WIN32LIBS = @WIN32LIBS@ +++ +++# Tcl et al cflags and libraries +++TCL = @TCL_LIBRARY@ +++TCL_CFLAGS = @TCL_INCLUDE@ +++GDBTKLIBS = @GDBTKLIBS@ +++# Extra flags that the GDBTK files need: +++GDBTK_CFLAGS = @GDBTK_CFLAGS@ +++ +++TK = @TK_LIBRARY@ +++TK_CFLAGS = @TK_INCLUDE@ +++ +++X11_CFLAGS = @TK_XINCLUDES@ +++X11_LDFLAGS = +++X11_LIBS = +++ +++WIN32LDAPP = @WIN32LDAPP@ +++ +++LIBGUI = @LIBGUI@ +++GUI_CFLAGS_X = @GUI_CFLAGS_X@ +++IDE_CFLAGS = $(GUI_CFLAGS_X) $(IDE_CFLAGS_X) +++ +++ALL_TCL_CFLAGS = $(TCL_CFLAGS) $(TK_CFLAGS) +++ +++# The version of gdbtk we're building. This should be kept +++# in sync with GDBTK_VERSION and friends in gdbtk.h. +++GDBTK_VERSION = 1.0 +++GDBTK_LIBRARY = $(datadir)/insight$(GDBTK_VERSION) +++ +++# Gdbtk requires an absolute path to the source directory or +++# the testsuite won't run properly. +++GDBTK_SRC_DIR = @GDBTK_SRC_DIR@ +++ +++SUBDIR_GDBTK_OBS = \ +++ gdbtk.o \ +++ gdbtk-bp.o \ +++ gdbtk-cmds.o \ +++ gdbtk-hooks.o \ +++ gdbtk-interp.o \ +++ gdbtk-register.o \ +++ gdbtk-stack.o \ +++ gdbtk-varobj.o \ +++ gdbtk-wrapper.o +++ +++SUBDIR_GDBTK_SRCS = \ +++ gdbtk/generic/gdbtk.c \ +++ gdbtk/generic/gdbtk-bp.c \ +++ gdbtk/generic/gdbtk-cmds.c \ +++ gdbtk/generic/gdbtk-hooks.c \ +++ gdbtk/generic/gdbtk-interp.c \ +++ gdbtk/generic/gdbtk-main.c \ +++ gdbtk/generic/gdbtk-register.c \ +++ gdbtk/generic/gdbtk-stack.c \ +++ gdbtk/generic/gdbtk-varobj.c \ +++ gdbtk/generic/gdbtk-wrapper.c +++ +++SUBDIR_GDBTK_DEPS = $(LIBGUI) $(TCL_DEPS) $(TK_DEPS) +++SUBDIR_GDBTK_LDFLAGS = +++SUBDIR_GDBTK_CFLAGS = -DGDBTK +++ +++CONFIG_OBS = @CONFIG_OBS@ +++CONFIG_SRCS = @CONFIG_SRCS@ +++CONFIG_DEPS = @CONFIG_DEPS@ +++CONFIG_LDFLAGS = @CONFIG_LDFLAGS@ +++ENABLE_CFLAGS = @ENABLE_CFLAGS@ +++CONFIG_ALL = @CONFIG_ALL@ +++CONFIG_CLEAN = @CONFIG_CLEAN@ +++CONFIG_INSTALL = @CONFIG_INSTALL@ +++CONFIG_UNINSTALL = @CONFIG_UNINSTALL@ +++HAVE_NATIVE_GCORE_TARGET = @HAVE_NATIVE_GCORE_TARGET@ +++ +++CONFIG_SRC_SUBDIR = arch cli dwarf2 mi compile tui unittests guile python \ +++ target nat +++CONFIG_DEP_SUBDIR = $(addsuffix /$(DEPDIR),$(CONFIG_SRC_SUBDIR)) +++ +++# -I. for config files. +++# -I$(srcdir) for gdb internal headers. +++# -I$(srcdir)/config for more generic config files. +++ +++# It is also possible that you will need to add -I/usr/include/sys if +++# your system doesn't have fcntl.h in /usr/include (which is where it +++# should be according to Posix). +++DEFS = -DCRASH_MERGE @DEFS@ +++GDB_CFLAGS = -I. -I$(srcdir) -I$(srcdir)/config \ +++ -DLOCALEDIR="\"$(localedir)\"" $(DEFS) +++ +++# MH_CFLAGS, if defined, has host-dependent CFLAGS from the config directory. +++GLOBAL_CFLAGS = $(MH_CFLAGS) +++ +++PROFILE_CFLAGS = @PROFILE_CFLAGS@ +++ +++# These are specifically reserved for setting from the command line +++# when running make. I.E.: "make CFLAGS=-Wmissing-prototypes". +++CFLAGS = @CFLAGS@ +++CXXFLAGS = @CXXFLAGS@ +++CPPFLAGS = @CPPFLAGS@ +++ +++# Set by configure, for e.g. expat. Python installations are such that +++# C headers are included using their basename (for example, we #include +++# rather than, say, ). Since the file names +++# are sometimes a little generic, we think that the risk of collision +++# with other header files is high. If that happens, we try to mitigate +++# a bit the consequences by putting the Python includes last in the list. +++INTERNAL_CPPFLAGS = $(CPPFLAGS) @GUILE_CPPFLAGS@ @PYTHON_CPPFLAGS@ \ +++ @LARGEFILE_CPPFLAGS@ +++ +++# INTERNAL_CFLAGS is the aggregate of all other *CFLAGS macros. +++INTERNAL_CFLAGS_BASE = \ +++ $(CXXFLAGS) $(GLOBAL_CFLAGS) $(PROFILE_CFLAGS) \ +++ $(GDB_CFLAGS) $(OPCODES_CFLAGS) $(READLINE_CFLAGS) $(ZLIBINC) \ +++ $(BFD_CFLAGS) $(INCLUDE_CFLAGS) $(LIBDECNUMBER_CFLAGS) \ +++ $(INTL_CFLAGS) $(INCGNU) $(INCSUPPORT) $(ENABLE_CFLAGS) \ +++ $(INTERNAL_CPPFLAGS) $(SRCHIGH_CFLAGS) $(TOP_CFLAGS) $(PTHREAD_CFLAGS) \ +++ $(DEBUGINFOD_CFLAGS) +++INTERNAL_WARN_CFLAGS = $(INTERNAL_CFLAGS_BASE) $(GDB_WARN_CFLAGS) +++INTERNAL_CFLAGS = $(INTERNAL_WARN_CFLAGS) $(GDB_WERROR_CFLAGS) +++ +++# LDFLAGS is specifically reserved for setting from the command line +++# when running make. +++LDFLAGS = @LDFLAGS@ +++ +++# Profiling options need to go here to work. +++# I think it's perfectly reasonable for a user to set -pg in CFLAGS +++# and have it work; that's why CFLAGS is here. +++# PROFILE_CFLAGS is _not_ included, however, because we use monstartup. +++INTERNAL_LDFLAGS = \ +++ $(CXXFLAGS) $(GLOBAL_CFLAGS) $(MH_LDFLAGS) \ +++ $(LDFLAGS) $(CONFIG_LDFLAGS) $(PTHREAD_CFLAGS) +++ +++# Libraries and corresponding dependencies for compiling gdb. +++# XM_CLIBS, defined in *config files, have host-dependent libs. +++# LIBIBERTY appears twice on purpose. +++CLIBS = $(SIM) $(READLINE) $(OPCODES) $(LIBCTF) $(BFD) $(ZLIB) \ +++ $(LIBSUPPORT) $(INTL) $(LIBIBERTY) $(LIBDECNUMBER) \ +++ $(XM_CLIBS) $(GDBTKLIBS) \ +++ @LIBS@ @GUILE_LIBS@ @PYTHON_LIBS@ \ +++ $(LIBEXPAT) $(LIBLZMA) $(LIBBABELTRACE) $(LIBIPT) \ +++ $(WIN32LIBS) $(LIBGNU) $(LIBICONV) \ +++ $(LIBMPFR) $(SRCHIGH_LIBS) $(LIBXXHASH) $(PTHREAD_LIBS) \ +++ $(DEBUGINFOD_LIBS) +++CDEPS = $(NAT_CDEPS) $(SIM) $(BFD) $(READLINE_DEPS) $(CTF_DEPS) \ +++ $(OPCODES) $(INTL_DEPS) $(LIBIBERTY) $(CONFIG_DEPS) $(LIBGNU) \ +++ $(LIBSUPPORT) +++ +++DIST = gdb +++ +++RUNTEST = runtest +++RUNTESTFLAGS = +++ +++# XML files to build in to GDB. +++XMLFILES = \ +++ $(srcdir)/features/btrace.dtd \ +++ $(srcdir)/features/btrace-conf.dtd \ +++ $(srcdir)/features/gdb-target.dtd \ +++ $(srcdir)/features/library-list.dtd \ +++ $(srcdir)/features/library-list-aix.dtd \ +++ $(srcdir)/features/library-list-svr4.dtd \ +++ $(srcdir)/features/osdata.dtd \ +++ $(srcdir)/features/threads.dtd \ +++ $(srcdir)/features/traceframe-info.dtd \ +++ $(srcdir)/features/xinclude.dtd +++ +++# Build the ser-*.o files the host supports. This includes ser-unix.o +++# for any system that supports a POSIX interface to the serial port. +++# See configure.ac. +++SER_HARDWIRE = @SER_HARDWIRE@ +++ +++# This is remote-sim.o if a simulator is to be linked in. +++SIM_OBS = @SIM_OBS@ +++ +++# Target-dependent object files. +++TARGET_OBS = @TARGET_OBS@ +++ +++# All target-dependent objects files that require 64-bit CORE_ADDR +++# (used with --enable-targets=all --enable-64-bit-bfd). +++ALL_64_TARGET_OBS = \ +++ aarch64-fbsd-tdep.o \ +++ aarch64-linux-tdep.o \ +++ aarch64-newlib-tdep.o \ +++ aarch64-ravenscar-thread.o \ +++ aarch64-tdep.o \ +++ alpha-bsd-tdep.o \ +++ alpha-linux-tdep.o \ +++ alpha-mdebug-tdep.o \ +++ alpha-nbsd-tdep.o \ +++ alpha-obsd-tdep.o \ +++ alpha-tdep.o \ +++ amd64-darwin-tdep.o \ +++ amd64-dicos-tdep.o \ +++ amd64-fbsd-tdep.o \ +++ amd64-linux-tdep.o \ +++ amd64-nbsd-tdep.o \ +++ amd64-obsd-tdep.o \ +++ amd64-sol2-tdep.o \ +++ amd64-tdep.o \ +++ amd64-windows-tdep.o \ +++ arch/aarch64.o \ +++ arch/aarch64-insn.o \ +++ arch/amd64.o \ +++ ia64-linux-tdep.o \ +++ ia64-tdep.o \ +++ ia64-vms-tdep.o \ +++ mips64-obsd-tdep.o \ +++ sparc64-fbsd-tdep.o \ +++ sparc64-linux-tdep.o \ +++ sparc64-nbsd-tdep.o \ +++ sparc64-obsd-tdep.o \ +++ sparc64-sol2-tdep.o \ +++ sparc64-tdep.o +++ +++# All other target-dependent objects files (used with --enable-targets=all). +++ALL_TARGET_OBS = \ +++ aarch32-tdep.o \ +++ arc-linux-tdep.o \ +++ arc-tdep.o \ +++ arch/aarch32.o \ +++ arch/arc.o \ +++ arch/arm.o \ +++ arch/arm-get-next-pcs.o \ +++ arch/arm-linux.o \ +++ arch/i386.o \ +++ arch/ppc-linux-common.o \ +++ arch/riscv.o \ +++ arm-bsd-tdep.o \ +++ arm-fbsd-tdep.o \ +++ arm-linux-tdep.o \ +++ arm-nbsd-tdep.o \ +++ arm-obsd-tdep.o \ +++ arm-pikeos-tdep.o \ +++ arm-symbian-tdep.o \ +++ arm-tdep.o \ +++ arm-wince-tdep.o \ +++ avr-tdep.o \ +++ bfin-linux-tdep.o \ +++ bfin-tdep.o \ +++ bpf-tdep.o \ +++ bsd-uthread.o \ +++ cris-linux-tdep.o \ +++ cris-tdep.o \ +++ csky-linux-tdep.o \ +++ csky-tdep.o \ +++ dicos-tdep.o \ +++ fbsd-tdep.o \ +++ frv-linux-tdep.o \ +++ frv-tdep.o \ +++ ft32-tdep.o \ +++ glibc-tdep.o \ +++ h8300-tdep.o \ +++ hppa-bsd-tdep.o \ +++ hppa-linux-tdep.o \ +++ hppa-nbsd-tdep.o \ +++ hppa-obsd-tdep.o \ +++ hppa-tdep.o \ +++ i386-bsd-tdep.o \ +++ i386-darwin-tdep.o \ +++ i386-dicos-tdep.o \ +++ i386-fbsd-tdep.o \ +++ i386-gnu-tdep.o \ +++ i386-go32-tdep.o \ +++ i386-linux-tdep.o \ +++ i386-nbsd-tdep.o \ +++ i386-nto-tdep.o \ +++ i386-obsd-tdep.o \ +++ i386-sol2-tdep.o \ +++ i386-tdep.o \ +++ i386-windows-tdep.o \ +++ i387-tdep.o \ +++ iq2000-tdep.o \ +++ linux-record.o \ +++ linux-tdep.o \ +++ lm32-tdep.o \ +++ m32c-tdep.o \ +++ m32r-linux-tdep.o \ +++ m32r-tdep.o \ +++ m68hc11-tdep.o \ +++ m68k-bsd-tdep.o \ +++ m68k-linux-tdep.o \ +++ m68k-tdep.o \ +++ mep-tdep.o \ +++ microblaze-linux-tdep.o \ +++ microblaze-tdep.o \ +++ mips-fbsd-tdep.o \ +++ mips-linux-tdep.o \ +++ mips-nbsd-tdep.o \ +++ mips-sde-tdep.o \ +++ mips-tdep.o \ +++ mn10300-linux-tdep.o \ +++ mn10300-tdep.o \ +++ moxie-tdep.o \ +++ msp430-tdep.o \ +++ nbsd-tdep.o \ +++ nds32-tdep.o \ +++ nios2-linux-tdep.o \ +++ nios2-tdep.o \ +++ nto-tdep.o \ +++ obsd-tdep.o \ +++ or1k-linux-tdep.o \ +++ or1k-tdep.o \ +++ ppc-fbsd-tdep.o \ +++ ppc-linux-tdep.o \ +++ ppc-nbsd-tdep.o \ +++ ppc-obsd-tdep.o \ +++ ppc-ravenscar-thread.o \ +++ ppc-sysv-tdep.o \ +++ ppc64-tdep.o \ +++ ravenscar-thread.o \ +++ riscv-fbsd-tdep.o \ +++ riscv-linux-tdep.o \ +++ riscv-ravenscar-thread.o \ +++ riscv-tdep.o \ +++ rl78-tdep.o \ +++ rs6000-aix-tdep.o \ +++ rs6000-lynx178-tdep.o \ +++ rs6000-tdep.o \ +++ rx-tdep.o \ +++ s12z-tdep.o \ +++ s390-linux-tdep.o \ +++ s390-tdep.o \ +++ score-tdep.o \ +++ sh-linux-tdep.o \ +++ sh-nbsd-tdep.o \ +++ sh-tdep.o \ +++ sol2-tdep.o \ +++ solib-aix.o \ +++ solib-darwin.o \ +++ solib-dsbt.o \ +++ solib-frv.o \ +++ solib-svr4.o \ +++ sparc-linux-tdep.o \ +++ sparc-nbsd-tdep.o \ +++ sparc-obsd-tdep.o \ +++ sparc-ravenscar-thread.o \ +++ sparc-sol2-tdep.o \ +++ sparc-tdep.o \ +++ symfile-mem.o \ +++ tic6x-linux-tdep.o \ +++ tic6x-tdep.o \ +++ tilegx-linux-tdep.o \ +++ tilegx-tdep.o \ +++ v850-tdep.o \ +++ vax-nbsd-tdep.o \ +++ vax-tdep.o \ +++ windows-tdep.o \ +++ x86-tdep.o \ +++ xcoffread.o \ +++ xstormy16-tdep.o \ +++ xtensa-config.o \ +++ xtensa-linux-tdep.o \ +++ xtensa-tdep.o +++ +++# The following native-target dependent variables are defined on +++# configure.nat. +++NAT_FILE = @NAT_FILE@ +++NATDEPFILES = @NATDEPFILES@ +++NAT_CDEPS = @NAT_CDEPS@ +++LOADLIBES = @LOADLIBES@ +++MH_CFLAGS = @MH_CFLAGS@ +++XM_CLIBS = @XM_CLIBS@ +++NAT_GENERATED_FILES = @NAT_GENERATED_FILES@ +++NM_H = @NM_H@ +++HAVE_NATIVE_GCORE_HOST = @HAVE_NATIVE_GCORE_HOST@ +++ +++# Native-target dependent makefile fragment comes in here. +++@nat_makefile_frag@ +++ +++# End of native-target dependent variables. +++ +++FLAGS_TO_PASS = \ +++ "prefix=$(prefix)" \ +++ "exec_prefix=$(exec_prefix)" \ +++ "infodir=$(infodir)" \ +++ "datarootdir=$(datarootdir)" \ +++ "docdir=$(docdir)" \ +++ "htmldir=$(htmldir)" \ +++ "pdfdir=$(pdfdir)" \ +++ "libdir=$(libdir)" \ +++ "mandir=$(mandir)" \ +++ "datadir=$(datadir)" \ +++ "includedir=$(includedir)" \ +++ "against=$(against)" \ +++ "DESTDIR=$(DESTDIR)" \ +++ "AR=$(AR)" \ +++ "AR_FLAGS=$(AR_FLAGS)" \ +++ "CC=$(CC)" \ +++ "CFLAGS=$(CFLAGS)" \ +++ "CXX=$(CXX)" \ +++ "CXX_DIALECT=$(CXX_DIALECT)" \ +++ "CXXFLAGS=$(CXXFLAGS)" \ +++ "DLLTOOL=$(DLLTOOL)" \ +++ "LDFLAGS=$(LDFLAGS)" \ +++ "RANLIB=$(RANLIB)" \ +++ "MAKEINFO=$(MAKEINFO)" \ +++ "MAKEINFOFLAGS=$(MAKEINFOFLAGS)" \ +++ "MAKEINFO_EXTRA_FLAGS=$(MAKEINFO_EXTRA_FLAGS)" \ +++ "MAKEHTML=$(MAKEHTML)" \ +++ "MAKEHTMLFLAGS=$(MAKEHTMLFLAGS)" \ +++ "INSTALL=$(INSTALL)" \ +++ "INSTALL_PROGRAM=$(INSTALL_PROGRAM)" \ +++ "INSTALL_SCRIPT=$(INSTALL_SCRIPT)" \ +++ "INSTALL_DATA=$(INSTALL_DATA)" \ +++ "RUNTEST=$(RUNTEST)" \ +++ "RUNTESTFLAGS=$(RUNTESTFLAGS)" +++ +++# Flags that we pass when building the testsuite. +++ +++# empty for native, $(target_alias)/ for cross +++target_subdir = @target_subdir@ +++ +++CC_FOR_TARGET = ` \ +++ if [ -f $${rootme}/../gcc/xgcc ] ; then \ +++ if [ -f $${rootme}/../$(target_subdir)newlib/Makefile ] ; then \ +++ echo $${rootme}/../gcc/xgcc -B$${rootme}/../gcc/ -idirafter $${rootme}/$(target_subdir)newlib/targ-include -idirafter $${rootsrc}/../$(target_subdir)newlib/libc/include -nostdinc -B$${rootme}/../$(target_subdir)newlib/; \ +++ else \ +++ echo $${rootme}/../gcc/xgcc -B$${rootme}/../gcc/; \ +++ fi; \ +++ else \ +++ if [ "$(host_canonical)" = "$(target_canonical)" ] ; then \ +++ echo $(CC); \ +++ else \ +++ t='$(program_transform_name)'; echo gcc | sed -e '' $$t; \ +++ fi; \ +++ fi` +++ +++CXX_FOR_TARGET = ` \ +++ if [ -f $${rootme}/../gcc/xg++ ] ; then \ +++ if [ -f $${rootme}/../$(target_subdir)newlib/Makefile ] ; then \ +++ echo $${rootme}/../gcc/xg++ -B$${rootme}/../gcc/ -idirafter $${rootme}/$(target_subdir)newlib/targ-include -idirafter $${rootsrc}/../$(target_subdir)newlib/libc/include -nostdinc -B$${rootme}/../$(target_subdir)newlib/; \ +++ else \ +++ echo $${rootme}/../gcc/xg++ -B$${rootme}/../gcc/; \ +++ fi; \ +++ else \ +++ if [ "$(host_canonical)" = "$(target_canonical)" ] ; then \ +++ echo $(CXX); \ +++ else \ +++ t='$(program_transform_name)'; echo g++ | sed -e '' $$t; \ +++ fi; \ +++ fi` +++ +++# The use of $$(x_FOR_TARGET) reduces the command line length by not +++# duplicating the lengthy definition. +++TARGET_FLAGS_TO_PASS = \ +++ "prefix=$(prefix)" \ +++ "exec_prefix=$(exec_prefix)" \ +++ "against=$(against)" \ +++ 'CC=$$(CC_FOR_TARGET)' \ +++ "CC_FOR_TARGET=$(CC_FOR_TARGET)" \ +++ "CFLAGS=$(CFLAGS)" \ +++ 'CXX=$$(CXX_FOR_TARGET)' \ +++ "CXX_FOR_TARGET=$(CXX_FOR_TARGET)" \ +++ "CXXFLAGS=$(CXXFLAGS)" \ +++ "INSTALL=$(INSTALL)" \ +++ "INSTALL_PROGRAM=$(INSTALL_PROGRAM)" \ +++ "INSTALL_DATA=$(INSTALL_DATA)" \ +++ "MAKEINFO=$(MAKEINFO)" \ +++ "MAKEHTML=$(MAKEHTML)" \ +++ "RUNTEST=$(RUNTEST)" \ +++ "RUNTESTFLAGS=$(RUNTESTFLAGS)" \ +++ "FORCE_PARALLEL=$(FORCE_PARALLEL)" \ +++ "TESTS=$(TESTS)" +++ +++# All source files that go into linking GDB. +++ +++# Files that should wind up in SFILES and whose corresponding .o +++# should be in COMMON_OBS. +++COMMON_SFILES = \ +++ ada-lang.c \ +++ ada-tasks.c \ +++ ada-typeprint.c \ +++ ada-valprint.c \ +++ ada-varobj.c \ +++ addrmap.c \ +++ agent.c \ +++ alloc.c \ +++ annotate.c \ +++ arch-utils.c \ +++ async-event.c \ +++ auto-load.c \ +++ auxv.c \ +++ ax-gdb.c \ +++ ax-general.c \ +++ bcache.c \ +++ bfd-target.c \ +++ block.c \ +++ blockframe.c \ +++ break-catch-sig.c \ +++ break-catch-syscall.c \ +++ break-catch-throw.c \ +++ breakpoint.c \ +++ btrace.c \ +++ build-id.c \ +++ buildsym-legacy.c \ +++ buildsym.c \ +++ c-lang.c \ +++ c-typeprint.c \ +++ c-valprint.c \ +++ c-varobj.c \ +++ charset.c \ +++ cli-out.c \ +++ coff-pe-read.c \ +++ coffread.c \ +++ complaints.c \ +++ completer.c \ +++ continuations.c \ +++ copying.c \ +++ corefile.c \ +++ corelow.c \ +++ cp-abi.c \ +++ cp-namespace.c \ +++ cp-support.c \ +++ cp-valprint.c \ +++ ctfread.c \ +++ d-lang.c \ +++ d-namespace.c \ +++ d-valprint.c \ +++ dbxread.c \ +++ dcache.c \ +++ debug.c \ +++ debuginfod-support.c \ +++ dictionary.c \ +++ disasm.c \ +++ dummy-frame.c \ +++ dwarf2/abbrev.c \ +++ dwarf2/attribute.c \ +++ dwarf2/comp-unit.c \ +++ dwarf2/dwz.c \ +++ dwarf2/expr.c \ +++ dwarf2/frame-tailcall.c \ +++ dwarf2/frame.c \ +++ dwarf2/index-cache.c \ +++ dwarf2/index-common.c \ +++ dwarf2/index-write.c \ +++ dwarf2/leb.c \ +++ dwarf2/line-header.c \ +++ dwarf2/loc.c \ +++ dwarf2/macro.c \ +++ dwarf2/read.c \ +++ dwarf2/section.c \ +++ dwarf2/stringify.c \ +++ eval.c \ +++ event-top.c \ +++ exceptions.c \ +++ exec.c \ +++ expprint.c \ +++ extension.c \ +++ f-lang.c \ +++ f-typeprint.c \ +++ f-valprint.c \ +++ filename-seen-cache.c \ +++ filesystem.c \ +++ findcmd.c \ +++ findvar.c \ +++ frame.c \ +++ frame-base.c \ +++ frame-unwind.c \ +++ gcore.c \ +++ gdb-demangle.c \ +++ gdb_bfd.c \ +++ gdb_obstack.c \ +++ gdb_regex.c \ +++ gdbarch.c \ +++ gdbtypes.c \ +++ gnu-v2-abi.c \ +++ gnu-v3-abi.c \ +++ go-lang.c \ +++ go-typeprint.c \ +++ go-valprint.c \ +++ inf-child.c \ +++ inf-loop.c \ +++ infcall.c \ +++ infcmd.c \ +++ inferior.c \ +++ inflow.c \ +++ infrun.c \ +++ inline-frame.c \ +++ interps.c \ +++ jit.c \ +++ language.c \ +++ linespec.c \ +++ location.c \ +++ m2-lang.c \ +++ m2-typeprint.c \ +++ m2-valprint.c \ +++ macrocmd.c \ +++ macroexp.c \ +++ macroscope.c \ +++ macrotab.c \ +++ main.c \ +++ maint.c \ +++ maint-test-options.c \ +++ maint-test-settings.c \ +++ mdebugread.c \ +++ mem-break.c \ +++ memattr.c \ +++ memory-map.c \ +++ memrange.c \ +++ minidebug.c \ +++ minsyms.c \ +++ mipsread.c \ +++ namespace.c \ +++ objc-lang.c \ +++ objfiles.c \ +++ observable.c \ +++ opencl-lang.c \ +++ osabi.c \ +++ osdata.c \ +++ p-lang.c \ +++ p-typeprint.c \ +++ p-valprint.c \ +++ parse.c \ +++ printcmd.c \ +++ probe.c \ +++ process-stratum-target.c \ +++ producer.c \ +++ progspace.c \ +++ progspace-and-thread.c \ +++ prologue-value.c \ +++ psymtab.c \ +++ record.c \ +++ record-btrace.c \ +++ record-full.c \ +++ regcache.c \ +++ regcache-dump.c \ +++ reggroups.c \ +++ registry.c \ +++ remote.c \ +++ remote-fileio.c \ +++ remote-notif.c \ +++ reverse.c \ +++ run-on-main-thread.c \ +++ rust-lang.c \ +++ sentinel-frame.c \ +++ ser-event.c \ +++ serial.c \ +++ skip.c \ +++ solib.c \ +++ solib-target.c \ +++ source.c \ +++ source-cache.c \ +++ stabsread.c \ +++ stack.c \ +++ std-regs.c \ +++ symfile.c \ +++ symfile-debug.c \ +++ symmisc.c \ +++ symtab.c \ +++ target.c \ +++ ../../crash_target.c \ +++ target-connection.c \ +++ target-dcache.c \ +++ target-descriptions.c \ +++ target-memory.c \ +++ test-target.c \ +++ thread.c \ +++ thread-iter.c \ +++ tid-parse.c \ +++ top.c \ +++ tracectf.c \ +++ tracefile.c \ +++ tracefile-tfile.c \ +++ tracepoint.c \ +++ trad-frame.c \ +++ tramp-frame.c \ +++ target-float.c \ +++ type-stack.c \ +++ typeprint.c \ +++ ui-file.c \ +++ ui-out.c \ +++ ui-style.c \ +++ user-regs.c \ +++ utils.c \ +++ valarith.c \ +++ valops.c \ +++ valprint.c \ +++ value.c \ +++ varobj.c \ +++ xml-support.c \ +++ xml-syscall.c \ +++ xml-tdesc.c +++ +++# Links made at configuration time should not be specified here, since +++# SFILES is used in building the distribution archive. +++SFILES = \ +++ ada-exp.y \ +++ arch/i386.c \ +++ c-exp.y \ +++ cp-name-parser.y \ +++ d-exp.y \ +++ dtrace-probe.c \ +++ elfread.c \ +++ f-exp.y \ +++ gdb.c \ +++ go-exp.y \ +++ m2-exp.y \ +++ p-exp.y \ +++ proc-service.list \ +++ rust-exp.y \ +++ ser-base.c \ +++ ser-unix.c \ +++ sol-thread.c \ +++ stap-probe.c \ +++ stub-termcap.c \ +++ symfile-mem.c \ +++ ui-file.h \ +++ mi/mi-common.c \ +++ $(SUBDIR_CLI_SRCS) \ +++ $(SUBDIR_TARGET_SRCS) \ +++ $(COMMON_SFILES) \ +++ $(SUBDIR_GCC_COMPILE_SRCS) +++ +++# Header files that need to have srcdir added. Note that in the cases +++# where we use a macro like $(gdbcmd_h), things are carefully arranged +++# so that each .h file is listed exactly once (M-x tags-search works +++# wrong if TAGS has files twice). Because this is tricky to get +++# right, it is probably easiest just to list .h files here directly. +++ +++HFILES_NO_SRCDIR = \ +++ aarch32-tdep.h \ +++ aarch64-ravenscar-thread.h \ +++ aarch64-tdep.h \ +++ ada-lang.h \ +++ addrmap.h \ +++ alpha-bsd-tdep.h \ +++ alpha-tdep.h \ +++ amd64-darwin-tdep.h \ +++ amd64-linux-tdep.h \ +++ amd64-nat.h \ +++ amd64-tdep.h \ +++ annotate.h \ +++ arc-tdep.h \ +++ arch-utils.h \ +++ arm-linux-tdep.h \ +++ arm-nbsd-tdep.h \ +++ arm-tdep.h \ +++ async-event.h \ +++ auto-load.h \ +++ auxv.h \ +++ ax.h \ +++ ax-gdb.h \ +++ bcache.h \ +++ bfd-target.h \ +++ bfin-tdep.h \ +++ block.h \ +++ breakpoint.h \ +++ bsd-kvm.h \ +++ bsd-uthread.h \ +++ build-id.h \ +++ buildsym-legacy.h \ +++ buildsym.h \ +++ c-lang.h \ +++ charset.h \ +++ charset-list.h \ +++ cli-out.h \ +++ coff-pe-read.h \ +++ command.h \ +++ complaints.h \ +++ completer.h \ +++ cp-abi.h \ +++ cp-support.h \ +++ csky-tdep.h \ +++ d-lang.h \ +++ darwin-nat.h \ +++ dcache.h \ +++ defs.h \ +++ dicos-tdep.h \ +++ dictionary.h \ +++ disasm.h \ +++ dummy-frame.h \ +++ dwarf2/frame-tailcall.h \ +++ dwarf2/frame.h \ +++ dwarf2/expr.h \ +++ dwarf2/index-cache.h \ +++ dwarf2/index-common.h \ +++ dwarf2/loc.h \ +++ dwarf2/read.h \ +++ event-top.h \ +++ exceptions.h \ +++ exec.h \ +++ expression.h \ +++ extension.h \ +++ extension-priv.h \ +++ f-lang.h \ +++ fbsd-nat.h \ +++ fbsd-tdep.h \ +++ filesystem.h \ +++ frame.h \ +++ frame-base.h \ +++ frame-unwind.h \ +++ frv-tdep.h \ +++ ft32-tdep.h \ +++ gcore.h \ +++ gdb_bfd.h \ +++ gdb_curses.h \ +++ gdb_expat.h \ +++ gdb_obstack.h \ +++ gdb_proc_service.h \ +++ gdb_regex.h \ +++ gdb_select.h \ +++ gdb-stabs.h \ +++ gdb_vfork.h \ +++ gdb_wchar.h \ +++ gdbarch.h \ +++ gdbcmd.h \ +++ gdbcore.h \ +++ gdbthread.h \ +++ gdbtypes.h \ +++ glibc-tdep.h \ +++ gnu-nat.h \ +++ go-lang.h \ +++ gregset.h \ +++ hppa-bsd-tdep.h \ +++ hppa-linux-offsets.h \ +++ hppa-tdep.h \ +++ i386-bsd-nat.h \ +++ i386-darwin-tdep.h \ +++ i386-linux-nat.h \ +++ i386-linux-tdep.h \ +++ i386-tdep.h \ +++ i387-tdep.h \ +++ ia64-libunwind-tdep.h \ +++ ia64-tdep.h \ +++ inf-child.h \ +++ inf-loop.h \ +++ inf-ptrace.h \ +++ infcall.h \ +++ inferior.h \ +++ inflow.h \ +++ inline-frame.h \ +++ interps.h \ +++ jit.h \ +++ language.h \ +++ linespec.h \ +++ linux-fork.h \ +++ linux-nat.h \ +++ linux-record.h \ +++ linux-tdep.h \ +++ location.h \ +++ m2-lang.h \ +++ m32r-tdep.h \ +++ m68k-tdep.h \ +++ macroexp.h \ +++ macroscope.h \ +++ macrotab.h \ +++ main.h \ +++ mdebugread.h \ +++ memattr.h \ +++ memory-map.h \ +++ memrange.h \ +++ microblaze-tdep.h \ +++ mips-linux-tdep.h \ +++ mips-nbsd-tdep.h \ +++ mips-tdep.h \ +++ mn10300-tdep.h \ +++ moxie-tdep.h \ +++ nbsd-nat.h \ +++ nbsd-tdep.h \ +++ nds32-tdep.h \ +++ nios2-tdep.h \ +++ nto-tdep.h \ +++ objc-lang.h \ +++ objfiles.h \ +++ obsd-nat.h \ +++ obsd-tdep.h \ +++ osabi.h \ +++ osdata.h \ +++ p-lang.h \ +++ parser-defs.h \ +++ ppc-fbsd-tdep.h \ +++ ppc-linux-tdep.h \ +++ ppc-nbsd-tdep.h \ +++ ppc-obsd-tdep.h \ +++ ppc-ravenscar-thread.h \ +++ ppc-tdep.h \ +++ ppc64-tdep.h \ +++ probe.h \ +++ proc-utils.h \ +++ procfs.h \ +++ progspace.h \ +++ progspace-and-thread.h \ +++ prologue-value.h \ +++ psympriv.h \ +++ psymtab.h \ +++ ravenscar-thread.h \ +++ record.h \ +++ record-full.h \ +++ regcache.h \ +++ reggroups.h \ +++ regset.h \ +++ remote.h \ +++ remote-fileio.h \ +++ remote-notif.h \ +++ riscv-fbsd-tdep.h \ +++ riscv-ravenscar-thread.h \ +++ riscv-tdep.h \ +++ rs6000-aix-tdep.h \ +++ rs6000-tdep.h \ +++ run-on-main-thread.h \ +++ s390-linux-tdep.h \ +++ s390-tdep.h \ +++ score-tdep.h \ +++ selftest-arch.h \ +++ sentinel-frame.h \ +++ ser-base.h \ +++ ser-event.h \ +++ ser-tcp.h \ +++ ser-unix.h \ +++ serial.h \ +++ sh-tdep.h \ +++ sim-regno.h \ +++ skip.h \ +++ sol2-tdep.h \ +++ solib.h \ +++ solib-aix.h \ +++ solib-darwin.h \ +++ solib-svr4.h \ +++ solib-target.h \ +++ solist.h \ +++ source.h \ +++ source-cache.h \ +++ sparc-nat.h \ +++ sparc-ravenscar-thread.h \ +++ sparc-tdep.h \ +++ sparc64-tdep.h \ +++ stabsread.h \ +++ stack.h \ +++ stap-probe.h \ +++ symfile.h \ +++ symtab.h \ +++ target.h \ +++ target-dcache.h \ +++ target-descriptions.h \ +++ terminal.h \ +++ tid-parse.h \ +++ top.h \ +++ tracectf.h \ +++ tracefile.h \ +++ tracepoint.h \ +++ trad-frame.h \ +++ target-float.h \ +++ tramp-frame.h \ +++ type-stack.h \ +++ typeprint.h \ +++ ui-file.h \ +++ ui-out.h \ +++ ui-style.h \ +++ user-regs.h \ +++ utils.h \ +++ valprint.h \ +++ value.h \ +++ varobj.h \ +++ varobj-iter.h \ +++ vax-tdep.h \ +++ windows-nat.h \ +++ windows-tdep.h \ +++ x86-bsd-nat.h \ +++ x86-linux-nat.h \ +++ x86-nat.h \ +++ xcoffread.h \ +++ xml-builtin.h \ +++ xml-support.h \ +++ xml-syscall.h \ +++ xml-tdesc.h \ +++ xtensa-tdep.h \ +++ arch/aarch32.h \ +++ arch/aarch64.h \ +++ arch/aarch64-insn.h \ +++ arch/arc.h \ +++ arch/arm.h \ +++ arch/i386.h \ +++ arch/ppc-linux-common.h \ +++ arch/ppc-linux-tdesc.h \ +++ arch/riscv.h \ +++ cli/cli-cmds.h \ +++ cli/cli-decode.h \ +++ cli/cli-script.h \ +++ cli/cli-setshow.h \ +++ cli/cli-style.h \ +++ cli/cli-utils.h \ +++ compile/compile.h \ +++ compile/compile-c.h \ +++ compile/compile-cplus.h \ +++ compile/compile-internal.h \ +++ compile/compile-object-load.h \ +++ compile/compile-object-run.h \ +++ compile/gcc-c-plugin.h \ +++ compile/gcc-cp-plugin.h \ +++ config/nm-linux.h \ +++ config/nm-nto.h \ +++ config/djgpp/langinfo.h \ +++ config/djgpp/nl_types.h \ +++ config/i386/nm-i386gnu.h \ +++ config/sparc/nm-sol2.h \ +++ mi/mi-cmds.h \ +++ mi/mi-common.h \ +++ mi/mi-console.h \ +++ mi/mi-getopt.h \ +++ mi/mi-main.h \ +++ mi/mi-out.h \ +++ mi/mi-parse.h \ +++ nat/aarch64-linux.h \ +++ nat/aarch64-linux-hw-point.h \ +++ nat/aarch64-sve-linux-ptrace.h \ +++ nat/amd64-linux-siginfo.h \ +++ nat/gdb_ptrace.h \ +++ nat/gdb_thread_db.h \ +++ nat/fork-inferior.h \ +++ nat/linux-btrace.h \ +++ nat/linux-namespaces.h \ +++ nat/linux-nat.h \ +++ nat/linux-osdata.h \ +++ nat/linux-personality.h \ +++ nat/linux-ptrace.h \ +++ nat/linux-waitpid.h \ +++ nat/mips-linux-watch.h \ +++ nat/ppc-linux.h \ +++ nat/x86-cpuid.h \ +++ nat/x86-dregs.h \ +++ nat/x86-gcc-cpuid.h \ +++ nat/x86-linux.h \ +++ nat/x86-linux-dregs.h \ +++ python/py-event.h \ +++ python/py-events.h \ +++ python/py-stopevent.h \ +++ python/python.h \ +++ python/python-internal.h \ +++ regformats/regdef.h \ +++ target/resume.h \ +++ target/target.h \ +++ target/wait.h \ +++ target/waitstatus.h \ +++ tui/tui.h \ +++ tui/tui-command.h \ +++ tui/tui-data.h \ +++ tui/tui-disasm.h \ +++ tui/tui-file.h \ +++ tui/tui-hooks.h \ +++ tui/tui-io.h \ +++ tui/tui-layout.h \ +++ tui/tui-regs.h \ +++ tui/tui-source.h \ +++ tui/tui-stack.h \ +++ tui/tui-win.h \ +++ tui/tui-windata.h \ +++ tui/tui-wingeneral.h \ +++ tui/tui-winsource.h \ +++ x86-tdep.h +++ +++# Header files that already have srcdir in them, or which are in objdir. +++ +++HFILES_WITH_SRCDIR = \ +++ ../bfd/bfd.h \ +++ jit-reader.h +++ +++# {X,T,NAT}DEPFILES are something of a pain in that it's hard to +++# default their values the way we do for SER_HARDWIRE; in the future +++# maybe much of the stuff now in {X,T,NAT}DEPFILES will go into other +++# variables analogous to SER_HARDWIRE which get defaulted in this +++# Makefile.in +++ +++DEPFILES = $(TARGET_OBS) $(SER_HARDWIRE) $(NATDEPFILES) $(SIM_OBS) +++ +++SOURCES = $(SFILES) $(ALLDEPFILES) $(YYFILES) $(CONFIG_SRCS) +++# Don't include YYFILES (*.c) because we already include *.y in SFILES, +++# and it's more useful to see it in the .y file. +++TAGFILES_NO_SRCDIR = $(SFILES) $(HFILES_NO_SRCDIR) $(ALLDEPFILES) \ +++ $(CONFIG_SRCS) +++TAGFILES_WITH_SRCDIR = $(HFILES_WITH_SRCDIR) +++ +++COMMON_OBS = $(DEPFILES) $(CONFIG_OBS) $(YYOBJ) \ +++ mi/mi-common.o \ +++ version.o \ +++ xml-builtin.o \ +++ $(patsubst %.c,%.o,$(COMMON_SFILES)) \ +++ $(SUBDIR_CLI_OBS) \ +++ $(SUBDIR_TARGET_OBS) \ +++ $(SUBDIR_GCC_COMPILE_OBS) +++ +++SUBDIRS = build_no_subdirs +++CLEANDIRS = $(SUBDIRS) +++ +++# List of subdirectories in the build tree that must exist. +++# This is used to force build failures in existing trees when +++# a new directory is added. +++# The format here is for the `case' shell command. +++REQUIRED_SUBDIRS = doc | testsuite | data-directory +++ +++# Parser intermediate files. +++YYFILES = \ +++ ada-exp.c \ +++ ada-lex.c \ +++ c-exp.c \ +++ cp-name-parser.c \ +++ d-exp.c \ +++ f-exp.c \ +++ go-exp.c \ +++ m2-exp.c \ +++ p-exp.c \ +++ rust-exp.c +++ +++# ada-lex.c is included by another file, so it shouldn't wind up as a +++# .o itself. +++YYOBJ = $(filter-out ada-lex.o,$(patsubst %.c,%.o,$(YYFILES))) +++ +++# Things which need to be built when making a distribution. +++ +++DISTSTUFF = $(YYFILES) +++ +++ +++# All generated files which can be included by another file. +++generated_files = \ +++ ada-lex.c \ +++ config.h \ +++ jit-reader.h \ +++ $(NAT_GENERATED_FILES) \ +++ $(NM_H) +++ +++# Flags needed to compile Python code +++PYTHON_CFLAGS = @PYTHON_CFLAGS@ +++ +++all: gdb$(EXEEXT) gdb-gdb.py gdb-gdb.gdb +++ @$(MAKE) -s $(FLAGS_TO_PASS) DO=all "DODIRS=`echo $(SUBDIRS) | sed 's/testsuite//'`" subdir_do +++ +++# Rule for compiling .c files in the top-level gdb directory. +++# The order-only dependencies ensure that we create the build subdirectories. +++%.o: %.c | $(CONFIG_DEP_SUBDIR) +++ $(COMPILE) $< +++ $(POSTCOMPILE) +++ +++$(CONFIG_DEP_SUBDIR): +++ $(SHELL) $(srcdir)/../mkinstalldirs $@ +++ +++# Python files need special flags. +++python/%.o: INTERNAL_CFLAGS += $(PYTHON_CFLAGS) +++ +++# Rules for compiling .c files in the various source subdirectories. +++%.o: $(srcdir)/gdbtk/generic/%.c +++ $(COMPILE) $(all_gdbtk_cflags) $< +++ $(POSTCOMPILE) +++ +++installcheck: +++ +++# The check target can not use subdir_do, because subdir_do does not +++# use TARGET_FLAGS_TO_PASS. +++check: force +++ @if [ -f testsuite/Makefile ]; then \ +++ rootme=`pwd`; export rootme; \ +++ rootsrc=`cd $(srcdir); pwd`; export rootsrc; \ +++ cd testsuite; \ +++ $(MAKE) $(TARGET_FLAGS_TO_PASS) check; \ +++ else true; fi +++ +++check-perf: force +++ @if [ -f testsuite/Makefile ]; then \ +++ rootme=`pwd`; export rootme; \ +++ rootsrc=`cd $(srcdir); pwd`; export rootsrc; \ +++ cd testsuite; \ +++ $(MAKE) $(TARGET_FLAGS_TO_PASS) check-perf; \ +++ else true; fi +++ +++check-read1: force +++ @if [ -f testsuite/Makefile ]; then \ +++ rootme=`pwd`; export rootme; \ +++ rootsrc=`cd $(srcdir); pwd`; export rootsrc; \ +++ cd testsuite; \ +++ $(MAKE) $(TARGET_FLAGS_TO_PASS) check-read1; \ +++ else true; fi +++ +++check-parallel: force +++ @if [ -f testsuite/Makefile ]; then \ +++ rootme=`pwd`; export rootme; \ +++ rootsrc=`cd $(srcdir); pwd`; export rootsrc; \ +++ cd testsuite; \ +++ $(MAKE) $(TARGET_FLAGS_TO_PASS) check-parallel; \ +++ else true; fi +++ +++# The idea is to parallelize testing of multilibs, for example: +++# make -j3 check//sh-hms-sim/{-m1,-m2,-m3,-m3e,-m4}/{,-nofpu} +++# will run 3 concurrent sessions of check, eventually testing all 10 +++# combinations. GNU make is required for the % pattern to work, as is +++# a shell that expands alternations within braces. If GNU make is not +++# used, this rule will harmlessly fail to match. Used FORCE_PARALLEL to +++# prevent serialized checking due to the passed RUNTESTFLAGS. +++# FIXME: use config.status --config not --version, when available. +++check//%: force +++ @if [ -f testsuite/config.status ]; then \ +++ rootme=`pwd`; export rootme; \ +++ rootsrc=`cd $(srcdir); pwd`; export rootsrc; \ +++ target=`echo "$@" | sed 's,//.*,,'`; \ +++ variant=`echo "$@" | sed 's,^[^/]*//,,'`; \ +++ vardots=`echo "$$variant" | sed 's,/,.,g'`; \ +++ testdir=testsuite.$$vardots; \ +++ if [ ! -f $$testdir/Makefile ] && [ -f testsuite/config.status ]; then \ +++ configargs=`cd testsuite && ./config.status --version | \ +++ sed -n -e 's,"$$,,' -e 's,^ *with options ",,p'`; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $$testdir && \ +++ (cd $$testdir && \ +++ eval $(SHELL) "\"\$$rootsrc/testsuite/configure\" $$configargs" \ +++ "\"--srcdir=\$$rootsrc/testsuite\"" \ +++ ); \ +++ else :; fi && cd $$testdir && \ +++ $(MAKE) $(TARGET_FLAGS_TO_PASS) \ +++ RUNTESTFLAGS="--target_board=$$variant $(RUNTESTFLAGS)" \ +++ FORCE_PARALLEL=$(if $(FORCE_PARALLEL),1,$(if $(RUNTESTFLAGS),,1)) \ +++ "$$target"; \ +++ else true; fi +++ +++# The set of headers checked by 'check-headers' by default. +++CHECK_HEADERS = $(HFILES_NO_SRCDIR) +++ +++# Try to compile each header in isolation, thus ensuring headers are +++# self-contained. +++# +++# Defaults to checking all $HFILES_NO_SRCDIR headers. +++# +++# Do: +++# +++# make check-headers CHECK_HEADERS="header.h list.h" +++# +++# to check specific headers. +++# +++check-headers: +++ @echo Checking headers. +++ for i in $(CHECK_HEADERS) ; do \ +++ $(CXX) $(CXX_DIALECT) -x c++-header -c -fsyntax-only \ +++ $(INTERNAL_CFLAGS) -include defs.h $(srcdir)/$$i ; \ +++ done +++.PHONY: check-headers +++ +++info install-info clean-info dvi pdf install-pdf html install-html: force +++ @$(MAKE) $(FLAGS_TO_PASS) DO=$@ "DODIRS=$(SUBDIRS)" subdir_do +++ +++# Traditionally "install" depends on "all". But it may be useful +++# not to; for example, if the user has made some trivial change to a +++# source file and doesn't care about rebuilding or just wants to save the +++# time it takes for make to check that all is up to date. +++# install-only is intended to address that need. +++install: all +++ @$(MAKE) $(FLAGS_TO_PASS) install-only +++ +++install-only: $(CONFIG_INSTALL) +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo gdb | sed -e "$$t"` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=gdb ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(bindir) ; \ +++ $(INSTALL_PROGRAM_ENV) $(INSTALL_PROGRAM) gdb$(EXEEXT) \ +++ $(DESTDIR)$(bindir)/$$transformed_name$(EXEEXT) ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(includedir)/gdb ; \ +++ $(INSTALL_DATA) jit-reader.h $(DESTDIR)$(includedir)/gdb/jit-reader.h +++ if test "x$(HAVE_NATIVE_GCORE_TARGET)$(HAVE_NATIVE_GCORE_HOST)" != x; \ +++ then \ +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo gcore | sed -e "$$t"` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=gcore ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(bindir) ; \ +++ $(INSTALL_SCRIPT) gcore \ +++ $(DESTDIR)$(bindir)/$$transformed_name; \ +++ fi +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo gdb-add-index | sed -e "$$t"` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=gdb-add-index ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ $(INSTALL_SCRIPT) $(srcdir)/contrib/gdb-add-index.sh \ +++ $(DESTDIR)$(bindir)/$$transformed_name +++ @$(MAKE) DO=install "DODIRS=$(SUBDIRS)" $(FLAGS_TO_PASS) subdir_do +++ +++install-strip: +++ $(MAKE) $(FLAGS_TO_PASS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ +++ install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ +++ `test -z '$(STRIP)' || \ +++ echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install-only +++ +++install-guile: +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(GDB_DATADIR)/guile/gdb +++ +++install-python: +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(GDB_DATADIR)/python/gdb +++ +++uninstall: force $(CONFIG_UNINSTALL) +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo gdb | sed -e $$t` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=gdb ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ rm -f $(DESTDIR)$(bindir)/$$transformed_name$(EXEEXT) \ +++ $(DESTDIR)$(man1dir)/$$transformed_name.1 +++ if test "x$(HAVE_NATIVE_GCORE_TARGET)$(HAVE_NATIVE_GCORE_HOST)" != x; \ +++ then \ +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo gcore | sed -e "$$t"` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=gcore ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ rm -f $(DESTDIR)$(bindir)/$$transformed_name; \ +++ fi +++ @$(MAKE) DO=uninstall "DODIRS=$(SUBDIRS)" $(FLAGS_TO_PASS) subdir_do +++ +++# The C++ name parser can be built standalone for testing. +++test-cp-name-parser.o: cp-name-parser.c +++ $(COMPILE) -DTEST_CPNAMES cp-name-parser.c +++ $(POSTCOMPILE) +++ +++test-cp-name-parser$(EXEEXT): test-cp-name-parser.o $(LIBIBERTY) +++ $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) \ +++ -o test-cp-name-parser$(EXEEXT) test-cp-name-parser.o \ +++ $(LIBIBERTY) +++ +++# We do this by grepping through sources. If that turns out to be too slow, +++# maybe we could just require every .o file to have an initialization routine +++# of a given name (top.o -> _initialize_top, etc.). +++# +++# Formatting conventions: The name of the _initialize_* routines must start +++# in column zero, and must not be inside #if. +++# +++# Note that the set of files with init functions might change, or the names +++# of the functions might change, so this files needs to depend on all the +++# source files that will be linked into gdb. However, due to the way +++# this Makefile has generally been written, we do this indirectly, by +++# computing the list of source files from the list of object files. +++ +++INIT_FILES = \ +++ $(patsubst %.o,%.c, \ +++ $(patsubst %-exp.o,%-exp.y, \ +++ $(filter-out init.o version.o %_S.o %_U.o,\ +++ $(COMMON_OBS)))) +++ +++init.c: stamp-init; @true +++stamp-init: $(INIT_FILES) +++ @$(ECHO_INIT_C) echo "Making init.c" +++ @rm -f init.c-tmp init.l-tmp +++ @touch init.c-tmp +++ @-for f in $(INIT_FILES); do \ +++ sed -n -e 's/^_initialize_\([a-z_0-9A-Z]*\).*/\1/p' \ +++ $(srcdir)/$$f 2>/dev/null; \ +++ done > init.l-tmp +++ @echo '/* Do not modify this file. */' >>init.c-tmp +++ @echo '/* It is created automatically by the Makefile. */'>>init.c-tmp +++ @echo '#include "defs.h" /* For initialize_file_ftype. */' >>init.c-tmp +++ @echo 'extern void initialize_all_files(void);' >>init.c-tmp +++ @sed -e 's/\(.*\)/extern initialize_file_ftype _initialize_\1;/' >init.c-tmp +++ @echo 'void' >>init.c-tmp +++ @echo 'initialize_all_files (void)' >>init.c-tmp +++ @echo '{' >>init.c-tmp +++ @sed -e 's/\(.*\)/ _initialize_\1 ();/' >init.c-tmp +++ @echo '}' >>init.c-tmp +++ @$(SHELL) $(srcdir)/../move-if-change init.c-tmp init.c +++ @echo stamp > stamp-init +++ +++.PRECIOUS: init.c +++ +++# Create a library of the gdb object files and build GDB by linking +++# against that. +++# +++# init.o is very important. It pulls in the rest of GDB. +++LIBGDB_OBS = $(sort $(COMMON_OBS)) init.o +++libgdb.a: $(LIBGDB_OBS) +++ -rm -f libgdb.a +++ $(AR) q libgdb.a $(LIBGDB_OBS) +++ $(RANLIB) libgdb.a +++ +++# Removing the old gdb first works better if it is running, at least on SunOS. +++gdb$(EXEEXT): gdb.o $(LIBGDB_OBS) $(CDEPS) $(TDEPLIBS) +++ $(SILENCE) rm -f gdb$(EXEEXT) +++ @$(MAKE) -C ../.. GDB_FLAGS=-DGDB_10_2 library +++ $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) $(WIN32LDAPP) \ +++ -o $(shell /bin/cat mergeobj) $(LIBGDB_OBS) \ +++ $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) $(shell /bin/cat mergelibs) +++ifneq ($(CODESIGN_CERT),) +++ $(ECHO_SIGN) $(CODESIGN) -s $(CODESIGN_CERT) gdb$(EXEEXT) +++endif +++ +++# Convenience rule to handle recursion. +++.PHONY: all-data-directory +++all-data-directory: data-directory/Makefile +++ @$(MAKE) $(FLAGS_TO_PASS) DO=all DODIRS=data-directory subdir_do +++ +++# This is useful when debugging GDB, because some Unix's don't let you run GDB +++# on itself without copying the executable. So "make gdb1" will make +++# gdb and put a copy in gdb1, and you can run it with "gdb gdb1". +++# Removing gdb1 before the copy is the right thing if gdb1 is open +++# in another process. +++gdb1$(EXEEXT): gdb$(EXEEXT) +++ rm -f gdb1$(EXEEXT) +++ cp gdb$(EXEEXT) gdb1$(EXEEXT) +++ +++# Put the proper machine-specific files first, so M-. on a machine +++# specific routine gets the one for the correct machine. (FIXME: those +++# files go in twice; we should be removing them from the main list). +++ +++# TAGS depends on all the files that go into it so you can rebuild TAGS +++# with `make TAGS' and not have to say `rm TAGS' first. +++ +++GDB_NM_FILE = @GDB_NM_FILE@ +++TAGS: $(TAGFILES_NO_SRCDIR) $(TAGFILES_WITH_SRCDIR) +++ @echo Making TAGS +++ etags `(test -n "$(GDB_NM_FILE)" && echo "$(srcdir)/$(GDB_NM_FILE)")` \ +++ `(for i in $(DEPFILES) $(TAGFILES_NO_SRCDIR); do \ +++ echo $(srcdir)/$$i ; \ +++ done ; for i in $(TAGFILES_WITH_SRCDIR); do \ +++ echo $$i ; \ +++ done) | sed -e 's/\.o$$/\.c/'` \ +++ `find $(srcdir)/config -name '*.h' -print` +++ +++tags: TAGS +++ +++clean mostlyclean: $(CONFIG_CLEAN) +++ @$(MAKE) $(FLAGS_TO_PASS) DO=clean "DODIRS=$(CLEANDIRS)" subdir_do +++ rm -f *.o *.a *~ init.c-tmp init.l-tmp version.c-tmp +++ rm -f init.c stamp-init version.c stamp-version +++ rm -f gdb$(EXEEXT) core make.log +++ rm -f gdb[0-9]$(EXEEXT) +++ rm -f test-cp-name-parser$(EXEEXT) +++ rm -f xml-builtin.c stamp-xml +++ rm -f $(DEPDIR)/* +++ for i in $(CONFIG_SRC_SUBDIR); do \ +++ rm -f $$i/*.o; \ +++ rm -f $$i/$(DEPDIR)/*; \ +++ done +++ +++# This used to depend on c-exp.c m2-exp.c TAGS +++# I believe this is wrong; the makefile standards for distclean just +++# describe removing files; the only sort of "re-create a distribution" +++# functionality described is if the distributed files are unmodified. +++distclean: clean +++ @$(MAKE) $(FLAGS_TO_PASS) DO=distclean "DODIRS=$(CLEANDIRS)" subdir_do +++ rm -f nm.h config.status config.h stamp-h b jit-reader.h +++ rm -f gdb-gdb.py gdb-gdb.gdb +++ rm -f y.output yacc.acts yacc.tmp y.tab.h +++ rm -f config.log config.cache +++ rm -f Makefile +++ rm -rf $(DEPDIR) +++ for i in $(CONFIG_SRC_SUBDIR); do \ +++ if test -d $$i/$(DEPDIR); then rmdir $$i/$(DEPDIR); fi \ +++ done +++ +++maintainer-clean: local-maintainer-clean do-maintainer-clean distclean +++realclean: maintainer-clean +++ +++local-maintainer-clean: +++ @echo "This command is intended for maintainers to use;" +++ @echo "it deletes files that may require special tools to rebuild." +++ rm -f c-exp.c \ +++ cp-name-parser.c \ +++ ada-lex.c ada-exp.c \ +++ d-exp.c f-exp.c go-exp.c m2-exp.c p-exp.c rust-exp.c +++ rm -f TAGS +++ rm -f $(YYFILES) +++ rm -f nm.h config.status +++ +++do-maintainer-clean: +++ @$(MAKE) $(FLAGS_TO_PASS) DO=maintainer-clean "DODIRS=$(CLEANDIRS)" \ +++ subdir_do +++ +++diststuff: $(DISTSTUFF) $(PACKAGE).pot $(CATALOGS) +++ cd doc; $(MAKE) $(MFLAGS) diststuff +++ +++subdir_do: force +++ @for i in $(DODIRS); do \ +++ case $$i in \ +++ $(REQUIRED_SUBDIRS)) \ +++ if [ ! -f ./$$i/Makefile ] ; then \ +++ echo "Missing $$i/Makefile" >&2 ; \ +++ exit 1 ; \ +++ fi ;; \ +++ esac ; \ +++ if [ -f ./$$i/Makefile ] ; then \ +++ if (cd ./$$i; \ +++ $(MAKE) $(FLAGS_TO_PASS) $(DO)) ; then true ; \ +++ else exit 1 ; fi ; \ +++ else true ; fi ; \ +++ done +++ +++Makefile: Makefile.in config.status +++ $(SHELL) config.status $@ +++ +++data-directory/Makefile: data-directory/Makefile.in config.status +++ $(SHELL) config.status $@ +++ +++.PHONY: run +++run: Makefile +++ ./gdb$(EXEEXT) --data-directory=`pwd`/data-directory $(GDBFLAGS) +++ +++jit-reader.h: $(srcdir)/jit-reader.in +++ $(SHELL) config.status $@ +++ +++gcore: $(srcdir)/gcore.in +++ $(SHELL) config.status $@ +++ +++gdb-gdb.py: $(srcdir)/gdb-gdb.py.in +++ $(SHELL) config.status $@ +++ +++gdb-gdb.gdb: $(srcdir)/gdb-gdb.gdb.in +++ $(SHELL) config.status $@ +++ +++config.h: stamp-h ; @true +++stamp-h: $(srcdir)/config.in config.status +++ $(SHELL) config.status config.h +++ +++nm.h: stamp-nmh ; @true +++stamp-nmh: config.status +++ $(SHELL) config.status nm.h +++ +++config.status: $(srcdir)/configure configure.nat configure.tgt configure.host ../bfd/development.sh +++ $(SHELL) config.status --recheck +++ +++ACLOCAL = aclocal +++ACLOCAL_AMFLAGS = -I ../config +++ +++# Keep these in sync with the includes in acinclude.m4. +++aclocal_m4_deps = \ +++ configure.ac \ +++ acx_configure_dir.m4 \ +++ transform.m4 \ +++ ../bfd/bfd.m4 \ +++ ../config/acinclude.m4 \ +++ ../config/enable.m4 \ +++ ../config/plugins.m4 \ +++ ../config/lead-dot.m4 \ +++ ../config/override.m4 \ +++ ../config/largefile.m4 \ +++ ../config/gettext-sister.m4 \ +++ ../config/lib-ld.m4 \ +++ ../config/lib-prefix.m4 \ +++ ../config/lib-link.m4 \ +++ ../config/acx.m4 \ +++ ../config/tcl.m4 \ +++ ../config/depstand.m4 \ +++ ../config/lcmessage.m4 \ +++ ../config/codeset.m4 \ +++ ../config/zlib.m4 \ +++ ../config/ax_pthread.m4 +++ +++$(srcdir)/aclocal.m4: @MAINTAINER_MODE_TRUE@ $(aclocal_m4_deps) +++ cd $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS) +++ +++AUTOCONF = autoconf +++configure_deps = $(srcdir)/configure.ac $(srcdir)/aclocal.m4 +++$(srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(configure_deps) +++ cd $(srcdir) && $(AUTOCONF) +++ +++AUTOHEADER = autoheader +++$(srcdir)/config.in: @MAINTAINER_MODE_TRUE@ $(configure_deps) +++ cd $(srcdir) && $(AUTOHEADER) +++ rm -f stamp-h +++ touch $@ +++ +++# automatic rebuilding in automake-generated Makefiles requires +++# this rule in the toplevel Makefile, which, with GNU make, causes +++# the desired updates through the implicit regeneration of the Makefile +++# and all of its prerequisites. +++am--refresh: +++ @: +++ +++force: +++ +++# Documentation! +++# GDB QUICK REFERENCE (TeX dvi file, CM fonts) +++doc/refcard.dvi: +++ cd doc; $(MAKE) refcard.dvi $(FLAGS_TO_PASS) +++ +++# GDB QUICK REFERENCE (PostScript output, common PS fonts) +++doc/refcard.ps: +++ cd doc; $(MAKE) refcard.ps $(FLAGS_TO_PASS) +++ +++# GDB MANUAL: TeX dvi file +++doc/gdb.dvi: +++ cd doc; $(MAKE) gdb.dvi $(FLAGS_TO_PASS) +++ +++# GDB MANUAL: info file +++doc/gdb.info: +++ cd doc; $(MAKE) gdb.info $(FLAGS_TO_PASS) +++ +++# Make copying.c from COPYING +++$(srcdir)/copying.c: @MAINTAINER_MODE_TRUE@ $(srcdir)/../COPYING3 $(srcdir)/copying.awk +++ awk -f $(srcdir)/copying.awk \ +++ < $(srcdir)/../COPYING3 > $(srcdir)/copying.tmp +++ mv $(srcdir)/copying.tmp $(srcdir)/copying.c +++ +++version.c: stamp-version; @true +++# Note that the obvious names for the temp file are taken by +++# create-version.sh. +++stamp-version: Makefile version.in $(srcdir)/../bfd/version.h $(srcdir)/../gdbsupport/create-version.sh +++ $(ECHO_GEN) $(SHELL) $(srcdir)/../gdbsupport/create-version.sh $(srcdir) \ +++ $(host_alias) $(target_alias) version-t.t +++ @$(SHELL) $(srcdir)/../move-if-change version-t.t version.c +++ @echo stamp > stamp-version +++ +++ +++gdb.cxref: $(SFILES) +++ cxref -I. $(SFILES) >gdb.cxref +++ +++force_update: +++ +++# GNU Make has an annoying habit of putting *all* the Makefile variables +++# into the environment, unless you include this target as a circumvention. +++# Rumor is that this will be fixed (and this target can be removed) +++# in GNU Make 4.0. +++.NOEXPORT: +++ +++# GNU Make 3.63 has a different problem: it keeps tacking command line +++# overrides onto the definition of $(MAKE). This variable setting +++# will remove them. +++MAKEOVERRIDES = +++ +++ALLDEPFILES = \ +++ aarch32-tdep.c \ +++ aarch64-fbsd-nat.c \ +++ aarch64-fbsd-tdep.c \ +++ aarch64-linux-nat.c \ +++ aarch64-linux-tdep.c \ +++ aarch64-newlib-tdep.c \ +++ aarch64-ravenscar-thread.c \ +++ aarch64-tdep.c \ +++ aix-thread.c \ +++ alpha-bsd-nat.c \ +++ alpha-bsd-tdep.c \ +++ alpha-linux-nat.c \ +++ alpha-linux-tdep.c \ +++ alpha-mdebug-tdep.c \ +++ alpha-nbsd-tdep.c \ +++ alpha-obsd-tdep.c \ +++ alpha-tdep.c \ +++ amd64-bsd-nat.c \ +++ amd64-darwin-tdep.c \ +++ amd64-dicos-tdep.c \ +++ amd64-fbsd-nat.c \ +++ amd64-fbsd-tdep.c \ +++ amd64-linux-nat.c \ +++ amd64-linux-tdep.c \ +++ amd64-nat.c \ +++ amd64-nbsd-nat.c \ +++ amd64-nbsd-tdep.c \ +++ amd64-obsd-nat.c \ +++ amd64-obsd-tdep.c \ +++ amd64-sol2-tdep.c \ +++ amd64-tdep.c \ +++ arc-tdep.c \ +++ arm.c \ +++ arm-bsd-tdep.c \ +++ arm-fbsd-nat.c \ +++ arm-fbsd-tdep.c \ +++ arm-get-next-pcs.c \ +++ arm-linux.c \ +++ arm-linux-nat.c \ +++ arm-linux-tdep.c \ +++ arm-nbsd-nat.c \ +++ arm-nbsd-tdep.c \ +++ arm-obsd-tdep.c \ +++ arm-symbian-tdep.c \ +++ arm-tdep.c \ +++ avr-tdep.c \ +++ bfin-linux-tdep.c \ +++ bfin-tdep.c \ +++ bpf-tdep.c \ +++ bsd-kvm.c \ +++ bsd-uthread.c \ +++ csky-linux-tdep.c \ +++ csky-tdep.c \ +++ darwin-nat.c \ +++ dicos-tdep.c \ +++ fbsd-nat.c \ +++ fbsd-tdep.c \ +++ fork-child.c \ +++ ft32-tdep.c \ +++ glibc-tdep.c \ +++ go32-nat.c \ +++ h8300-tdep.c \ +++ hppa-bsd-tdep.c \ +++ hppa-linux-nat.c \ +++ hppa-linux-tdep.c \ +++ hppa-nbsd-nat.c \ +++ hppa-nbsd-tdep.c \ +++ hppa-obsd-nat.c \ +++ hppa-obsd-tdep.c \ +++ hppa-tdep.c \ +++ i386-bsd-nat.c \ +++ i386-bsd-tdep.c \ +++ i386-darwin-nat.c \ +++ i386-darwin-tdep.c \ +++ i386-dicos-tdep.c \ +++ i386-fbsd-nat.c \ +++ i386-fbsd-tdep.c \ +++ i386-gnu-nat.c \ +++ i386-gnu-tdep.c \ +++ i386-linux-nat.c \ +++ i386-linux-tdep.c \ +++ i386-nbsd-nat.c \ +++ i386-nbsd-tdep.c \ +++ i386-obsd-nat.c \ +++ i386-obsd-tdep.c \ +++ i386-sol2-nat.c \ +++ i386-sol2-tdep.c \ +++ i386-tdep.c \ +++ i386-windows-tdep.c \ +++ i387-tdep.c \ +++ ia64-libunwind-tdep.c \ +++ ia64-linux-nat.c \ +++ ia64-linux-tdep.c \ +++ ia64-tdep.c \ +++ ia64-vms-tdep.c \ +++ inf-ptrace.c \ +++ linux-fork.c \ +++ linux-record.c \ +++ linux-tdep.c \ +++ lm32-tdep.c \ +++ m32r-linux-nat.c \ +++ m32r-linux-tdep.c \ +++ m32r-tdep.c \ +++ m68hc11-tdep.c \ +++ m68k-bsd-nat.c \ +++ m68k-bsd-tdep.c \ +++ m68k-linux-nat.c \ +++ m68k-linux-tdep.c \ +++ m68k-tdep.c \ +++ microblaze-linux-tdep.c \ +++ microblaze-tdep.c \ +++ mingw-hdep.c \ +++ mips-fbsd-nat.c \ +++ mips-fbsd-tdep.c \ +++ mips-linux-nat.c \ +++ mips-linux-tdep.c \ +++ mips-nbsd-nat.c \ +++ mips-nbsd-tdep.c \ +++ mips-sde-tdep.c \ +++ mips-tdep.c \ +++ mips64-obsd-nat.c \ +++ mips64-obsd-tdep.c \ +++ msp430-tdep.c \ +++ nbsd-nat.c \ +++ nbsd-tdep.c \ +++ nds32-tdep.c \ +++ nios2-linux-tdep.c \ +++ nios2-tdep.c \ +++ obsd-nat.c \ +++ obsd-tdep.c \ +++ posix-hdep.c \ +++ ppc-fbsd-nat.c \ +++ ppc-fbsd-tdep.c \ +++ ppc-linux-nat.c \ +++ ppc-linux-tdep.c \ +++ ppc-nbsd-nat.c \ +++ ppc-nbsd-tdep.c \ +++ ppc-obsd-nat.c \ +++ ppc-obsd-tdep.c \ +++ ppc-ravenscar-thread.c \ +++ ppc-sysv-tdep.c \ +++ ppc64-tdep.c \ +++ procfs.c \ +++ ravenscar-thread.c \ +++ remote-sim.c \ +++ riscv-fbsd-nat.c \ +++ riscv-fbsd-tdep.c \ +++ riscv-linux-nat.c \ +++ riscv-linux-tdep.c \ +++ riscv-ravenscar-thread.c \ +++ riscv-tdep.c \ +++ rl78-tdep.c \ +++ rs6000-lynx178-tdep.c \ +++ rs6000-nat.c \ +++ rs6000-tdep.c \ +++ rx-tdep.c \ +++ s390-linux-nat.c \ +++ s390-linux-tdep.c \ +++ s390-tdep.c \ +++ score-tdep.c \ +++ ser-go32.c \ +++ ser-mingw.c \ +++ ser-pipe.c \ +++ ser-tcp.c \ +++ ser-uds.c \ +++ sh-nbsd-nat.c \ +++ sh-nbsd-tdep.c \ +++ sh-tdep.c \ +++ sol2-tdep.c \ +++ solib-aix.c \ +++ solib-svr4.c \ +++ sparc-linux-nat.c \ +++ sparc-linux-tdep.c \ +++ sparc-nat.c \ +++ sparc-nbsd-nat.c \ +++ sparc-nbsd-tdep.c \ +++ sparc-obsd-tdep.c \ +++ sparc-ravenscar-thread.c \ +++ sparc-sol2-nat.c \ +++ sparc-sol2-tdep.c \ +++ sparc-tdep.c \ +++ sparc64-fbsd-nat.c \ +++ sparc64-fbsd-tdep.c \ +++ sparc64-linux-nat.c \ +++ sparc64-linux-tdep.c \ +++ sparc64-nat.c \ +++ sparc64-nbsd-nat.c \ +++ sparc64-nbsd-tdep.c \ +++ sparc64-obsd-nat.c \ +++ sparc64-obsd-tdep.c \ +++ sparc64-sol2-tdep.c \ +++ sparc64-tdep.c \ +++ tilegx-linux-nat.c \ +++ tilegx-linux-tdep.c \ +++ tilegx-tdep.c \ +++ v850-tdep.c \ +++ vax-bsd-nat.c \ +++ vax-nbsd-tdep.c \ +++ vax-tdep.c \ +++ windows-nat.c \ +++ windows-tdep.c \ +++ x86-nat.c \ +++ x86-tdep.c \ +++ xcoffread.c \ +++ xstormy16-tdep.c \ +++ xtensa-config.c \ +++ xtensa-linux-nat.c \ +++ xtensa-linux-tdep.c \ +++ xtensa-tdep.c \ +++ xtensa-xtregs.c +++ +++# Some files need explicit build rules (due to -Werror problems) or due +++# to sub-directory fun 'n' games. +++ +++# ada-exp.c can appear in srcdir, for releases; or in ., for +++# development builds. +++ADA_EXP_C = `if test -f ada-exp.c; then echo ada-exp.c; else echo $(srcdir)/ada-exp.c; fi` +++ +++ada-exp.o: ada-exp.c +++ $(COMPILE) $(ADA_EXP_C) +++ $(POSTCOMPILE) +++ +++# Message files. Based on code in gcc/Makefile.in. +++ +++# Rules for generating translated message descriptions. Disabled by +++# autoconf if the tools are not available. +++ +++.PHONY: all-po install-po uninstall-po clean-po update-po $(PACKAGE).pot +++ +++all-po: $(CATALOGS) +++ +++# This notation should be acceptable to all Make implementations used +++# by people who are interested in updating .po files. +++update-po: $(CATALOGS:.gmo=.pox) +++ +++# N.B. We do not attempt to copy these into $(srcdir). The snapshot +++# script does that. +++%.gmo: %.po +++ -test -d po || mkdir po +++ $(GMSGFMT) --statistics -o $@ $< +++ +++# The new .po has to be gone over by hand, so we deposit it into +++# build/po with a different extension. If build/po/$(PACKAGE).pot +++# exists, use it (it was just created), else use the one in srcdir. +++%.pox: %.po +++ -test -d po || mkdir po +++ $(MSGMERGE) $< `if test -f po/$(PACKAGE).pot; \ +++ then echo po/$(PACKAGE).pot; \ +++ else echo $(srcdir)/po/$(PACKAGE).pot; fi` -o $@ +++ +++# This rule has to look for .gmo modules in both srcdir and the cwd, +++# and has to check that we actually have a catalog for each language, +++# in case they weren't built or included with the distribution. +++install-po: +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(datadir) +++ cats="$(CATALOGS)"; for cat in $$cats; do \ +++ lang=`basename $$cat | sed 's/\.gmo$$//'`; \ +++ if [ -f $$cat ]; then :; \ +++ elif [ -f $(srcdir)/$$cat ]; then cat=$(srcdir)/$$cat; \ +++ else continue; \ +++ fi; \ +++ dir=$(localedir)/$$lang/LC_MESSAGES; \ +++ echo $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$$dir; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$$dir || exit 1; \ +++ echo $(INSTALL_DATA) $$cat $(DESTDIR)$$dir/$(PACKAGE).mo; \ +++ $(INSTALL_DATA) $$cat $(DESTDIR)$$dir/$(PACKAGE).mo; \ +++ done +++uninstall-po: +++ cats="$(CATALOGS)"; for cat in $$cats; do \ +++ lang=`basename $$cat | sed 's/\.gmo$$//'`; \ +++ if [ -f $$cat ]; then :; \ +++ elif [ -f $(srcdir)/$$cat ]; then cat=$(srcdir)/$$cat; \ +++ else continue; \ +++ fi; \ +++ dir=$(localedir)/$$lang/LC_MESSAGES; \ +++ rm -f $(DESTDIR)$$dir/$(PACKAGE).mo; \ +++ done +++# Delete po/*.gmo only if we are not building in the source directory. +++clean-po: +++ -if [ ! -f Makefile.in ]; then rm -f po/*.gmo; fi +++ +++# Rule for regenerating the message template (gdb.pot). Instead of +++# forcing everyone to edit POTFILES.in, which proved impractical, this +++# rule has no dependencies and always regenerates gdb.pot. This is +++# relatively harmless since the .po files do not directly depend on +++# it. The .pot file is left in the build directory. Since GDB's +++# Makefile lacks a cannonical list of sources (missing xm, tm and nm +++# files) force this rule. +++$(PACKAGE).pot: po/$(PACKAGE).pot +++po/$(PACKAGE).pot: force +++ -test -d po || mkdir po +++ sh -e $(srcdir)/po/gdbtext $(XGETTEXT) $(PACKAGE) . $(srcdir) +++ +++ +++# +++# YACC/LEX dependencies +++# +++# LANG-exp.c is generated in objdir from LANG-exp.y if it doesn't +++# exist in srcdir, then compiled in objdir to LANG-exp.o. If we +++# said LANG-exp.c rather than ./c-exp.c some makes would +++# sometimes re-write it into $(srcdir)/c-exp.c. Remove bogus +++# decls for malloc/realloc/free which conflict with everything else. +++# Strictly speaking c-exp.c should therefore depend on +++# Makefile.in, but that was a pretty big annoyance. +++ +++%.c: %.y +++ $(ECHO_YACC) $(SHELL) $(YLWRAP) $< y.tab.c $@.tmp -- \ +++ $(YACC) $(YFLAGS) || (rm -f $@.tmp; false) +++ @sed -e '/extern.*malloc/d' \ +++ -e '/extern.*realloc/d' \ +++ -e '/extern.*free/d' \ +++ -e '/include.*malloc.h/d' \ +++ -e 's/\([^x]\)malloc/\1xmalloc/g' \ +++ -e 's/\([^x]\)realloc/\1xrealloc/g' \ +++ -e 's/\([ \t;,(]\)free\([ \t]*[&(),]\)/\1xfree\2/g' \ +++ -e 's/\([ \t;,(]\)free$$/\1xfree/g' \ +++ -e '/^#line.*y.tab.c/d' \ +++ -e 's/YY_NULL/YY_NULLPTR/g' \ +++ < $@.tmp > $@.new && \ +++ rm -f $@.tmp && \ +++ mv $@.new $@ +++%.c: %.l +++ $(ECHO_LEX) $(FLEX) -t $< \ +++ | sed -e '/extern.*malloc/d' \ +++ -e '/extern.*realloc/d' \ +++ -e '/extern.*free/d' \ +++ -e '/include.*malloc.h/d' \ +++ -e 's/\([^x]\)malloc/\1xmalloc/g' \ +++ -e 's/\([^x]\)realloc/\1xrealloc/g' \ +++ -e 's/\([ \t;,(]\)free\([ \t]*[&(),]\)/\1xfree\2/g' \ +++ -e 's/\([ \t;,(]\)free$$/\1xfree/g' \ +++ -e 's/yy_flex_xrealloc/yyxrealloc/g' \ +++ > $@.new && \ +++ mv $@.new $@ +++ +++.PRECIOUS: ada-lex.c +++ +++# XML rules +++ +++xml-builtin.c: stamp-xml; @true +++stamp-xml: $(srcdir)/features/feature_to_c.sh Makefile $(XMLFILES) +++ $(SILENCE) rm -f xml-builtin.tmp +++ $(ECHO_GEN_XML_BUILTIN) AWK="$(AWK)" \ +++ $(SHELL) $(srcdir)/features/feature_to_c.sh \ +++ xml-builtin.tmp $(XMLFILES) +++ $(SILENCE) $(SHELL) $(srcdir)/../move-if-change xml-builtin.tmp xml-builtin.c +++ $(SILENCE) echo stamp > stamp-xml +++ +++.PRECIOUS: xml-builtin.c +++ +++# +++# GDBTK sub-directory +++# +++ +++all-gdbtk: insight$(EXEEXT) +++ +++install-gdbtk: +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo insight | sed -e $$t` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=insight ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs $(DESTDIR)$(bindir); \ +++ $(INSTALL_PROGRAM_ENV) $(INSTALL_PROGRAM) insight$(EXEEXT) \ +++ $(DESTDIR)$(bindir)/$$transformed_name$(EXEEXT) ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs \ +++ $(DESTDIR)$(GDBTK_LIBRARY) ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs \ +++ $(DESTDIR)$(libdir)/insight$(GDBTK_VERSION) ; \ +++ $(INSTALL_DATA) $(srcdir)/gdbtk/plugins/plugins.tcl \ +++ $(DESTDIR)$(libdir)/insight$(GDBTK_VERSION)/plugins.tcl ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs \ +++ $(DESTDIR)$(GDBTK_LIBRARY)/images \ +++ $(DESTDIR)$(GDBTK_LIBRARY)/images2 ; \ +++ $(SHELL) $(srcdir)/../mkinstalldirs \ +++ $(DESTDIR)$(GDBTK_LIBRARY)/help \ +++ $(DESTDIR)$(GDBTK_LIBRARY)/help/images \ +++ $(DESTDIR)$(GDBTK_LIBRARY)/help/trace ; \ +++ cd $(srcdir)/gdbtk/library ; \ +++ for i in *.tcl *.itcl *.ith *.itb images/*.gif images2/*.gif images/icons.txt images2/icons.txt tclIndex help/*.html help/trace/*.html help/trace/index.toc help/images/*.gif help/images/*.png; \ +++ do \ +++ $(INSTALL_DATA) $$i $(DESTDIR)$(GDBTK_LIBRARY)/$$i ; \ +++ done ; +++ +++uninstall-gdbtk: +++ transformed_name=`t='$(program_transform_name)'; \ +++ echo insight | sed -e $$t` ; \ +++ if test "x$$transformed_name" = x; then \ +++ transformed_name=insight ; \ +++ else \ +++ true ; \ +++ fi ; \ +++ rm -f $(DESTDIR)$(bindir)/$$transformed_name$(EXEEXT) ; \ +++ rm -rf $(DESTDIR)$(GDBTK_LIBRARY) +++ +++clean-gdbtk: +++ rm -f insight$(EXEEXT) +++ +++# Removing the old gdb first works better if it is running, at least on SunOS. +++insight$(EXEEXT): gdbtk-main.o libgdb.a $(CDEPS) $(TDEPLIBS) +++ rm -f insight$(EXEEXT) +++ $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) $(WIN32LDAPP) \ +++ -o insight$(EXEEXT) gdbtk-main.o libgdb.a \ +++ $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) +++ +++gdbres.o: $(srcdir)/gdbtk/gdb.rc $(srcdir)/gdbtk/gdbtool.ico +++ $(WINDRES) --include $(srcdir)/gdbtk $(srcdir)/gdbtk/gdb.rc gdbres.o +++ +++all_gdbtk_cflags = $(IDE_CFLAGS) $(ITCL_CFLAGS) \ +++ $(ITK_CFLAGS) $(TCL_CFLAGS) $(TK_CFLAGS) $(X11_CFLAGS) \ +++ $(GDBTK_CFLAGS) \ +++ -DGDBTK_LIBRARY=\"$(GDBTK_LIBRARY)\" \ +++ -DSRC_DIR=\"$(GDBTK_SRC_DIR)\" +++ +++# +++# Dependency tracking. +++# +++ +++ifeq ($(DEPMODE),depmode=gcc3) +++# Note that we put the dependencies into a .Tpo file, then move them +++# into place if the compile succeeds. We need this because gcc does +++# not atomically write the dependency output file. +++override COMPILE.post = -c -o $@ -MT $@ -MMD -MP \ +++ -MF $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo +++override POSTCOMPILE = @mv $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Tpo \ +++ $(subst ../..,.,$(@D))/$(DEPDIR)/$(basename $(@F)).Po +++else +++override COMPILE.pre = source='$<' object='$@' libtool=no \ +++ DEPDIR=$(DEPDIR) $(DEPMODE) $(depcomp) \ +++ $(CXX) -x c++ $(CXX_DIALECT) +++# depcomp handles atomicity for us, so we don't need a postcompile +++# step. +++override POSTCOMPILE = +++endif +++ +++# A list of all the objects we might care about in this build, for +++# dependency tracking. +++all_object_files = gdb.o $(LIBGDB_OBS) gdbtk-main.o \ +++ test-cp-name-parser.o +++ +++# All the .deps files to include. +++all_deps_files = $(foreach dep,$(patsubst %.o,%.Po,$(all_object_files)),\ +++ $(dir $(dep))/$(DEPDIR)/$(notdir $(dep))) +++ +++# Ensure that generated files are created early. Use order-only +++# dependencies if available. They require GNU make 3.80 or newer, +++# and the .VARIABLES variable was introduced at the same time. +++ifdef .VARIABLES +++$(all_object_files): | $(generated_files) +++else +++$(all_object_files) : $(generated_files) +++endif +++ +++# Dependencies. +++-include $(all_deps_files) +++ +++# Disable implicit make rules. +++include $(srcdir)/disable-implicit-rules.mk +++ +++### end of the gdb Makefile.in. ++diff -Nuar gdb-10.2/gdb/nat/linux-waitpid.h gdb-10.2/gdb/nat/linux-waitpid.h ++--- gdb-10.2/gdb/nat/linux-waitpid.h 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdb/nat/linux-waitpid.h 2025-04-16 17:06:51.972086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Wrapper for waitpid for GNU/Linux (LWP layer). ++ ++- Copyright (C) 2000-2021 Free Software Foundation, Inc. +++ Copyright (C) 2000-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -20,6 +20,7 @@ ++ #ifndef NAT_LINUX_WAITPID_H ++ #define NAT_LINUX_WAITPID_H ++ +++#define MAXCGS 4//sw_64-linux-watch.c ++ /* Wrapper function for waitpid which handles EINTR. */ ++ extern int my_waitpid (int pid, int *status, int flags); ++ ++diff -Nuar gdb-10.2/gdb/nat/sw_64-linux-watch.c gdb-10.2/gdb/nat/sw_64-linux-watch.c ++--- gdb-10.2/gdb/nat/sw_64-linux-watch.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/nat/sw_64-linux-watch.c 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,224 @@ +++/* Copyright (C) 2009-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "gdbsupport/common-defs.h" +++#include "nat/gdb_ptrace.h" +++#include "nat/linux-ptrace.h" +++#include "sw_64-linux-watch.h" +++#include +++#include +++#include +++#include +++#include +++ +++unsigned long cgmap, spemap[MAXCGS]; +++ +++/* It's decided by NINSERTS_INIT and entry__init. +++ * NINSERTS_INIT defined in nat/sw_64-linux-watch.h and filled in alpha-tdep.c. +++ * The number of NINSERTS_INIT must be fully filled at entry__init and equal to the inserted instructions +++ **/ +++//extern long slave_Ax_hwbpt; +++ +++//slave_state_t slave_state[MAXCGS]; +++ +++#ifdef GDBSERVER +++extern int debug_threads; +++#define debug(format, ... ) do { \ +++ if (debug_threads) {\ +++ fprintf(stdout, "%s,%d:%s:", __FILE__, __LINE__,__func__); \ +++ fprintf(stdout, format, ##__VA_ARGS__); \ +++ fprintf(stdout, "\n"); \ +++ fflush(stdout); \ +++ } \ +++ } while (0) +++extern int delete_gdb_breakpoint (char z_type, CORE_ADDR addr, int kind); +++#else +++extern int debug_infrun; +++#define debug(format, ... ) do { \ +++ if (debug_infrun){ \ +++ fprintf(stdout, "%s,%d:%s:", __FILE__, __LINE__,__func__); \ +++ fprintf(stdout, format, ##__VA_ARGS__); \ +++ fprintf(stdout, "\n"); \ +++ fflush(stdout); \ +++ } \ +++ } while (0) +++#endif +++ +++int read_debug_register (pid_t pid, int regno, long *val) +++{ +++ int ret; +++ errno = 0; +++ +++ if (SPE_LWP(pid)) +++ ret = ptrace (PT_READ_U, pid, (PTRACE_TYPE_ARG3) regno, val); +++ else +++ *val = ptrace (PT_READ_U, pid, (PTRACE_TYPE_ARG3) regno, 0); +++ +++ if ( ret < 0 || errno != 0) +++ { +++ warning("lwp %x write $%d failed \n", pid, regno); +++ return 0; +++ } +++ return 1; +++} +++ +++int store_debug_register (pid_t pid, int regno, long val) +++{ +++ int ret; +++ debug("store tid %x CSR %d, val = %#lx", pid, regno, val); +++ errno = 0; +++ ret = ptrace (PT_WRITE_U, pid, (PTRACE_TYPE_ARG3) regno, val); +++ errno = 0; +++ errno = 0; +++ ret = ptrace (PT_WRITE_U, pid, (PTRACE_TYPE_ARG3) regno, val); +++ if ( ret < 0 || errno != 0) +++ { +++ warning("lwp %x write $%d failed \n", pid, regno); +++ return 0; +++ } +++ return 1; +++} +++ +++int is_power_of_2 (int val) +++{ +++ int i, onecount; +++ +++ onecount = 0; +++ for (i = 0; i < 8 * sizeof (val); i++) +++ if (val & (1 << i)) +++ onecount++; +++ +++ return onecount <= 1; +++} +++ +++int sw_64_read_insn(pid_t pid, ulong pc) +++{ +++ int insn; +++ long tmp, data; +++ +++ tmp = pc & ~0x7; +++ data = ptrace(PTRACE_PEEKTEXT, pid, tmp, 0); +++ if ( pc & 0x7) +++ insn = (int)(data>>32); +++ else +++ insn = (int)data; +++ return insn; +++} +++ +++int sw_64_linux_try_one_watch (pid_t lwpid, struct arch_lwp_info *info, +++ enum sw_64_hw_bp_type wpt_type, long addr, int len) +++{ +++ long data; +++ int found = 0; +++ struct pt_watch_regs *wpt = info->wpt; +++ +++ if (!addr || !is_power_of_2 (len)) +++ return 0; +++ if ( wpt_type == sw_64_vstore) +++ { +++ debug("insert master wp %lx, dv_match len = %d", (long)addr, len); +++ +++ info->value_address = addr; //saved +++ wpt[1].match = ptrace(PTRACE_PEEKDATA, lwpid, addr, 0); //dv_match +++ wpt[1].mask = (len &0x8)?0xffffffffffffffffUL:0xffffffffUL; //dv_mask +++ wpt[1].match &= wpt[1].mask; +++ wpt[1].valid = 1; +++ +++ if (wpt[0].valid) +++ { +++ data = wpt[0].match & ((1L<<53)-1); +++ +++ wpt[0].match = sw_64_write; +++ wpt->match <<= 53; +++ wpt->match |= data; +++ /* wpt->mask not changed */ +++ } +++ } +++ else +++ { +++ debug("insert master wp %lx, da_match len = %d", (long)addr, len); +++ wpt->match = wpt_type&0x3; +++ wpt->match <<= 53; +++ wpt->match |= addr & ((1L<<53)-1); +++ data = len -1; +++ wpt->mask = ~data & ((1L<<53)-1); +++ wpt->valid = 1; +++ } +++ +++ found = 1; +++ +++ if (!found) +++ error("hardware wpt resource empty\n"); +++ return 1; +++} +++ +++ +++int sw_64_linux_del_one_watch (pid_t lwpid, struct arch_lwp_info *info, +++ enum sw_64_hw_bp_type wpt_type, long addr, int len) +++{ +++ int deleted_one = 0; +++ long match; +++ struct pt_watch_regs *wpt = info->wpt; +++ +++ if ( wpt_type == sw_64_vstore ) +++ { +++ wpt[1].valid = 0; +++ wpt[0].valid = 0; +++ debug("to remove master wp %#lx, dv_match", (long)addr); +++ info->value_address = 0L; //clr the saved +++ return 1; +++ } +++ match = wpt_type&0x3; +++ match <<= 53; +++ match |= addr&((1L<<53)-1); +++ +++ if ( wpt->valid && (match == wpt->match )) +++ { +++ wpt->match &= ~(0x3L<<53); +++ wpt->valid = 0; +++ // deleted_one ++; +++ debug("to remove master wp %#lx, da_match", (long)addr); +++ return 1; +++ } +++ +++ return deleted_one>0; +++} +++ +++/* gdb712 has this function, but gdb821 deleted the interface of ptid_get_pid */ +++//int sw_64_linux_enable_sdebug(ptid_t master) +++//{ +++// int i; +++// pid_t pid; +++// +++// /* sw7run calloc score!!!! */ +++// //pid = ptid_get_pid(master); +++// pid = master.pid (); +++// /* Maybe master-only, maybe slave unspawned */ +++// if ( !cgmap) +++// return 1; +++// +++// ALLCGS(cgmap, i) +++// { +++// //debug("set debugging flag for scores %#lx", spemap[i]); +++// if ( ptrace(PTRACE_TRACESPE, 1<<31|i<<6, spemap[i], 0) < 0) +++// { +++// warning("PTRACE_TRACESPE: CG<%d>SPE<%lx> ...", i, spemap[i]); +++// return 0; +++// } +++// } +++// return 1; +++//} ++diff -Nuar gdb-10.2/gdb/nat/sw_64-linux-watch.h gdb-10.2/gdb/nat/sw_64-linux-watch.h ++--- gdb-10.2/gdb/nat/sw_64-linux-watch.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/nat/sw_64-linux-watch.h 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,178 @@ +++/* Copyright (C) 2009-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#ifndef NAT_SW_64_LINUX_WATCH_H +++#define NAT_SW_64_LINUX_WATCH_H 1 +++ +++#include +++#include "gdbsupport/break-common.h" +++#include "linux-waitpid.h" // include defs of MAXCGS +++ +++#define MAXSPE 64 +++#define SW7AOP 28 +++#define SW7ARA 22 +++#define SW7ARB 16 +++#define SW7ARC 6 +++#define MAXDISPI 10 +++#define NINSERTS_INIT 68 //must be actual number of inserted +++#define OFFSET22b 0x3fffff +++ +++/* master watchpoint si_code == __SI_FAULT|M_DA_MATCH_TRAP */ +++#define __SI_FAULT (3 << 16) +++#define M_DA_MATCH_TRAP 4 +++ +++#ifndef ALPHA_INSN_SIZE +++#define ALPHA_INSN_SIZE 4 +++#endif +++#define SPE_COREID(pid) (pid & 0x3fUL) +++#define SPE_CGID(pid) (0x7&(pid>>6)) +++#define SPE_TID(cg,core) (unsigned long)(SPE_COREID(core) | 1UL<<31 | (cg)<<6) +++#define SPE_LWP(pid) (pid&(1<<31)) +++ +++enum ptrace_extend_request { +++ PTRACE_TRACESPE = 10, +++ PTRACE_GET_SCORE = 20, +++}; +++ +++enum { +++ REG_R0 = 0, +++ REG_SP = 30, +++ REG_F0 = 32, +++ REG_FPCR = 63, +++ REG_PC = 64, +++ UNIQUE_ADDR =65, +++ REG_V0F1 = 67, +++ SPE_V0 = 70, +++ REG_V0F2 = 99, +++ REG_V0F3 = 131, +++ M_DA_MATCH = 163 , +++ M_DA_MASK, +++ M_DV_MATCH = 165 , +++ M_DV_MASK, +++}; +++ +++enum { +++ S_DA_MATCH0 = 65, +++ S_DA_MATCH1, +++ S_DA_MASK0, +++ S_DA_MASK1, +++}; +++ +++ +++enum sw_64_hw_bp_type +++{ +++ sw_64_none = 0, /* not match, or Execute HW breakpoint */ +++ sw_64_read = 1, /* Read HW watchpoint */ +++ sw_64_write = 2, /* Common HW watchpoint */ +++ sw_64_access = 3, /* Access HW watchpoint */ +++ sw_64_vstore = 4, +++}; +++ +++typedef unsigned long ulong; +++ +++#define ALLCGS(bitmap, cg) \ +++ for (cg=0; cg>32)) +++#define IBXBPT_L_SET(ibx, addr) {\ +++ ibx &= ~0x0ffffffffUL;\ +++ ibx |= SPCMASK(addr);\ +++ ibx |= (1UL<<31); \ +++} +++ +++#define IBXBPT_H_SET(ibx, addr) {\ +++ ibx &= ~(0xffffffffL<<32); \ +++ ibx |= (1UL<<63)|(SPCMASK(addr)<<32); \ +++} +++ +++ +++#define STOPPED_SPC(cg,core) slave_state[cg].pc[core] +++ +++extern unsigned long entry__init; +++extern unsigned int size__init; +++extern unsigned long cgmap, spemap[]; +++ +++/* A value of zero in a watchlo indicates that it is available. */ +++ +++struct pt_watch_regs +++{ +++ uint64_t match; +++ uint64_t mask; +++ int valid; +++} __attribute__ ((aligned (8))); +++ +++ +++/* Per-thread arch-specific data we want to keep. */ +++#define MAX_BPTS 1 +++#define MAX_WPTS 2 +++ +++#define MAX_DA_MATECH 2 +++struct arch_lwp_info +++{ +++ /* Non-zero if our copy differs from what's recorded in the thread. */ +++ int watch_registers_changed; +++ int watch_matched; +++ +++ struct pt_watch_regs wpt[MAX_DA_MATECH]; +++ +++ /* Cached stopped data address. */ +++ CORE_ADDR stopped_data_address; +++ CORE_ADDR value_address; +++ /* tls cs */ +++ long ebxio_def0; +++#ifndef LHX20201112 +++ char matched; +++ /* Non-zero if our copy differs from what's recorded in the thread. */ +++ char bpts_changed[MAX_BPTS]; +++ char wpts_changed[MAX_WPTS]; +++#endif +++ +++}; +++ +++ +++#define IRW_MASK 0xffffffffffffUL +++ +++/* We keep list of all watchpoints we should install and calculate the +++ watch register values each time the list changes. This allows for +++ easy sharing of watch registers for more than one watchpoint. */ +++ +++struct sw_64_watchpoint +++{ +++ CORE_ADDR addr; +++ int len; +++ enum target_hw_bp_type type; +++ struct sw_64_watchpoint *next; +++}; +++ +++ +++int is_power_of_2 (int val); +++int sw_64_linux_try_one_watch (pid_t , struct arch_lwp_info *, enum sw_64_hw_bp_type , long , int ); +++int sw_64_linux_del_one_watch (pid_t , struct arch_lwp_info *, enum sw_64_hw_bp_type , long , int ); +++int read_debug_register (pid_t pid, int regno, long *val); +++int store_debug_register (pid_t pid, int regno, long val); +++int expt_thr_handler(ptid_t ptid/* master */, int cg, int core, struct expt_inf *inf); +++ +++#endif /* NAT_SW_64_LINUX_WATCH_H */ ++diff -Nuar gdb-10.2/gdb/objfiles.h gdb-10.2/gdb/objfiles.h ++--- gdb-10.2/gdb/objfiles.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/objfiles.h 2025-04-16 17:06:41.902086800 +0800 ++@@ -747,9 +747,9 @@ ++ ++ extern int objfile_has_symbols (struct objfile *objfile); ++ ++-extern int have_partial_symbols (void); +++extern "C" int have_partial_symbols (void); ++ ++-extern int have_full_symbols (void); +++extern "C" int have_full_symbols (void); ++ ++ extern void objfile_set_sym_fns (struct objfile *objfile, ++ const struct sym_fns *sf); ++diff -Nuar gdb-10.2/gdb/printcmd.c gdb-10.2/gdb/printcmd.c ++--- gdb-10.2/gdb/printcmd.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/printcmd.c 2025-04-16 17:06:41.922086800 +0800 ++@@ -524,6 +524,9 @@ ++ form. However note that DO_DEMANGLE can be overridden by the specific ++ settings of the demangle and asm_demangle variables. Returns ++ non-zero if anything was printed; zero otherwise. */ +++#ifdef CRASH_MERGE +++extern "C" int gdb_print_callback(unsigned long); +++#endif ++ ++ int ++ print_address_symbolic (struct gdbarch *gdbarch, CORE_ADDR addr, ++@@ -535,6 +538,12 @@ ++ int offset = 0; ++ int line = 0; ++ +++#ifdef CRASH_MERGE +++ if (!gdb_print_callback(addr)) { +++ return 0; +++ } +++#endif +++ ++ if (build_address_symbolic (gdbarch, addr, do_demangle, false, &name, ++ &offset, &filename, &line, &unmapped)) ++ return 0; ++@@ -567,6 +576,10 @@ ++ ++ /* See valprint.h. */ ++ +++#ifdef CRASH_MERGE +++extern "C" char *gdb_lookup_module_symbol(unsigned long, unsigned long *); +++#endif +++ ++ int ++ build_address_symbolic (struct gdbarch *gdbarch, ++ CORE_ADDR addr, /* IN */ ++@@ -673,7 +686,19 @@ ++ } ++ } ++ if (symbol == NULL && msymbol.minsym == NULL) +++#ifdef CRASH_MERGE +++ { +++ char *name_ptr = gdb_lookup_module_symbol(addr, (unsigned long *)offset); +++ if (name_ptr) { +++ *name = name_ptr; +++ return 0; +++ } else { +++ return 1; +++ } +++ } +++#else ++ return 1; +++#endif ++ ++ /* If the nearest symbol is too far away, don't print anything symbolic. */ ++ ++@@ -1221,6 +1246,43 @@ ++ print_value (val, print_opts); ++ } ++ +++static void +++print_command_2 (const char *args, int voidprint) +++{ +++ struct value *val; +++ value_print_options print_opts; +++ +++ get_user_print_options (&print_opts); +++ /* Override global settings with explicit options, if any. */ +++ auto group = make_value_print_options_def_group (&print_opts); +++ gdb::option::process_options +++ (&args, gdb::option::PROCESS_OPTIONS_REQUIRE_DELIMITER, group); +++ +++ print_command_parse_format (&args, "print", &print_opts); +++ +++ const char *exp = args; +++ +++ if (exp != nullptr && *exp) +++ { +++ expression_up expr = parse_expression (exp); +++ val = evaluate_expression (expr.get ()); +++ } +++ else +++ val = access_value_history (0); +++ +++ printf_filtered ("%d %d %ld %ld %ld %ld\n", +++ check_typedef(value_type (val))->code(), +++ TYPE_UNSIGNED (check_typedef(value_type (val))), +++ TYPE_LENGTH (check_typedef(value_type(val))), +++ value_offset (val), value_bitpos (val), value_bitsize(val)); +++} +++ +++static void +++printm_command (const char *exp, int from_tty) +++{ +++ print_command_2 (exp, 1); +++} +++ ++ /* See valprint.h. */ ++ ++ void ++@@ -2855,6 +2917,12 @@ ++ c = add_com ("print", class_vars, print_command, print_help.c_str ()); ++ set_cmd_completer_handle_brkchars (c, print_command_completer); ++ add_com_alias ("p", "print", class_vars, 1); +++ +++ c = add_com ("printm", class_vars, printm_command, _("\ +++Similar to \"print\" command, but it used to print the type, size, offset,\n\ +++bitpos and bitsize of the expression EXP.")); +++ set_cmd_completer (c, expression_completer); +++ ++ add_com_alias ("inspect", "print", class_vars, 1); ++ ++ add_setshow_uinteger_cmd ("max-symbolic-offset", no_class, ++diff -Nuar gdb-10.2/gdb/psymtab.c gdb-10.2/gdb/psymtab.c ++--- gdb-10.2/gdb/psymtab.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/psymtab.c 2025-04-16 17:06:41.902086800 +0800 ++@@ -283,6 +283,9 @@ ++ return best_pst; ++ } ++ +++#ifdef CRASH_MERGE +++ extern "C" int gdb_line_number_callback(unsigned long, unsigned long, unsigned long); +++#endif ++ /* Find which partial symtab contains PC and SECTION. Return NULL if ++ none. We return the psymtab that contains a symbol whose address ++ exactly matches PC, or, if we cannot find an exact match, the ++@@ -363,7 +366,12 @@ ++ ++ best_pst = find_pc_sect_psymtab_closer (objfile, pc, section, pst, ++ msymbol); +++#ifdef CRASH_MERGE +++ if ((best_pst != NULL) && +++ gdb_line_number_callback(pc, pst->text_low (objfile), pst->text_high (objfile))) +++#else ++ if (best_pst != NULL) +++#endif ++ return best_pst; ++ } ++ ++diff -Nuar gdb-10.2/gdb/regcache.c gdb-10.2/gdb/regcache.c ++--- gdb-10.2/gdb/regcache.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/regcache.c 2025-04-16 17:06:51.972086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Cache and manage the values of registers for GDB, the GNU debugger. ++ ++- Copyright (C) 1986-2021 Free Software Foundation, Inc. +++ Copyright (C) 1986-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -222,13 +222,23 @@ ++ } ++ ++ /* Return a pointer to register REGNUM's buffer cache. */ ++- ++ gdb_byte * ++ reg_buffer::register_buffer (int regnum) const ++ { ++ return m_registers.get () + m_descr->register_offset[regnum]; ++ } ++ +++/*gdb_byte * +++reg_buffer::register_buffer0 (int regnum) const +++{ +++ //return m_registers.get () + m_descr->register_offset[regnum]; +++ gdb_byte *pR0; +++ asm("mov $0,%0" +++ :"=r"(pR0)); +++ +++ return pR0 ; +++}*/ +++ ++ void ++ reg_buffer::save (register_read_ftype cooked_read) ++ { ++@@ -598,10 +608,12 @@ ++ ++ if (m_register_status[regnum] != REG_VALID) ++ memset (buf, 0, m_descr->sizeof_register[regnum]); ++- else +++ /*else if(regnum == 0) +++ memcpy (buf, register_buffer0 (regnum), +++ m_descr->sizeof_register[regnum]);*/ +++ else ++ memcpy (buf, register_buffer (regnum), ++- m_descr->sizeof_register[regnum]); ++- +++ m_descr->sizeof_register[regnum]); ++ return m_register_status[regnum]; ++ } ++ ++@@ -1856,6 +1868,7 @@ ++ if (bfd_arch == bfd_arch_frv || bfd_arch == bfd_arch_h8300 ++ || bfd_arch == bfd_arch_m32c || bfd_arch == bfd_arch_sh ++ || bfd_arch == bfd_arch_alpha || bfd_arch == bfd_arch_v850 +++ || bfd_arch == bfd_arch_sw_64 ++ || bfd_arch == bfd_arch_msp430 || bfd_arch == bfd_arch_mep ++ || bfd_arch == bfd_arch_mips || bfd_arch == bfd_arch_v850_rh850 ++ || bfd_arch == bfd_arch_tic6x || bfd_arch == bfd_arch_mn10300 ++diff -Nuar gdb-10.2/gdb/regcache.h gdb-10.2/gdb/regcache.h ++--- gdb-10.2/gdb/regcache.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/regcache.h 2025-04-16 17:06:51.972086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Cache and manage the values of registers for GDB, the GNU debugger. ++ ++- Copyright (C) 1986-2021 Free Software Foundation, Inc. +++ Copyright (C) 1986-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -242,6 +242,7 @@ ++ int num_raw_registers () const; ++ ++ gdb_byte *register_buffer (int regnum) const; +++ gdb_byte *register_buffer0 (int regnum) const; ++ ++ /* Save a register cache. The set of registers saved into the ++ regcache determined by the save_reggroup. COOKED_READ returns ++diff -Nuar gdb-10.2/gdb/regformats/sw_64-linux.dat gdb-10.2/gdb/regformats/sw_64-linux.dat ++--- gdb-10.2/gdb/regformats/sw_64-linux.dat 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/regformats/sw_64-linux.dat 2025-04-16 17:06:51.972086800 +0800 ++@@ -0,0 +1,168 @@ +++# THIS FILE IS GENERATED. -*- buffer-read-only: t -*- vi :set ro: +++# Generated from: sw64-linux.xml +++name:sw_64_linux +++xmltarget:sw_64-linux.xml +++expedite:fp,sp,pc +++64:v0 +++64:t0 +++64:t1 +++64:t2 +++64:t3 +++64:t4 +++64:t5 +++64:t6 +++64:t7 +++64:s0 +++64:s1 +++64:s2 +++64:s3 +++64:s4 +++64:s5 +++64:fp +++64:a0 +++64:a1 +++64:a2 +++64:a3 +++64:a4 +++64:a5 +++64:t8 +++64:t9 +++64:t10 +++64:t11 +++64:ra +++64:t12 +++64:at +++64:gp +++64:sp +++64:zero +++64:f0 +++64:f1 +++64:f2 +++64:f3 +++64:f4 +++64:f5 +++64:f6 +++64:f7 +++64:f8 +++64:f9 +++64:f10 +++64:f11 +++64:f12 +++64:f13 +++64:f14 +++64:f15 +++64:f16 +++64:f17 +++64:f18 +++64:f19 +++64:f20 +++64:f21 +++64:f22 +++64:f23 +++64:f24 +++64:f25 +++64:f26 +++64:f27 +++64:f28 +++64:f29 +++64:f30 +++64:fcsr +++64:pc +++64: +++64:unique +++64:ef0 +++64:ef1 +++64:ef2 +++64:ef3 +++64:ef4 +++64:ef5 +++64:ef6 +++64:ef7 +++64:ef8 +++64:ef9 +++64:ef10 +++64:ef11 +++64:ef12 +++64:ef13 +++64:ef14 +++64:ef15 +++64:ef16 +++64:ef17 +++64:ef18 +++64:ef19 +++64:ef20 +++64:ef21 +++64:ef22 +++64:ef23 +++64:ef24 +++64:ef25 +++64:ef26 +++64:ef27 +++64:ef28 +++64:ef29 +++64:ef30 +++64:ef31 +++64:ef0 +++64:ef1 +++64:ef2 +++64:ef3 +++64:ef4 +++64:ef5 +++64:ef6 +++64:ef7 +++64:ef8 +++64:ef9 +++64:ef10 +++64:ef11 +++64:ef12 +++64:ef13 +++64:ef14 +++64:ef15 +++64:ef16 +++64:ef17 +++64:ef18 +++64:ef19 +++64:ef20 +++64:ef21 +++64:ef22 +++64:ef23 +++64:ef24 +++64:ef25 +++64:ef26 +++64:ef27 +++64:ef28 +++64:ef29 +++64:ef30 +++64:ef31 +++64:ef0 +++64:ef1 +++64:ef2 +++64:ef3 +++64:ef4 +++64:ef5 +++64:ef6 +++64:ef7 +++64:ef8 +++64:ef9 +++64:ef10 +++64:ef11 +++64:ef12 +++64:ef13 +++64:ef14 +++64:ef15 +++64:ef16 +++64:ef17 +++64:ef18 +++64:ef19 +++64:ef20 +++64:ef21 +++64:ef22 +++64:ef23 +++64:ef24 +++64:ef25 +++64:ef26 +++64:ef27 +++64:ef28 +++64:ef29 +++64:ef30 +++64:ef31 ++diff -Nuar gdb-10.2/gdb/remote.c gdb-10.2/gdb/remote.c ++--- gdb-10.2/gdb/remote.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/remote.c 2025-04-16 17:06:51.982086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Remote target communications for serial-line targets in custom GDB protocol ++ ++- Copyright (C) 1988-2021 Free Software Foundation, Inc. +++ Copyright (C) 1988-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -2171,6 +2171,9 @@ ++ Z_PACKET_WRITE_WP, ++ Z_PACKET_READ_WP, ++ Z_PACKET_ACCESS_WP, +++#ifndef XWB20200308 +++ Z_PACKET_DV_WP, +++#endif ++ NR_Z_PACKET_TYPES ++ }; ++ ++@@ -10401,6 +10404,11 @@ ++ case hw_access: ++ return Z_PACKET_ACCESS_WP; ++ break; +++#ifndef XWB20200308 +++ case hw_vstore: +++ return Z_PACKET_DV_WP; +++ break; +++#endif ++ default: ++ internal_error (__FILE__, __LINE__, ++ _("hw_bp_to_z: bad watchpoint type %d"), type); ++@@ -14163,13 +14171,9 @@ ++ static void ++ remote_async_inferior_event_handler (gdb_client_data data) ++ { ++- remote_target *remote = (remote_target *) data; ++- /* Hold a strong reference to the remote target while handling an ++- event, since that could result in closing the connection. */ ++- auto remote_ref = target_ops_ref::new_reference (remote); ++- ++ inferior_event_handler (INF_REG_EVENT); ++ +++ remote_target *remote = (remote_target *) data; ++ remote_state *rs = remote->get_remote_state (); ++ ++ /* inferior_event_handler may have consumed an event pending on the ++diff -Nuar gdb-10.2/gdb/sw_64-bsd-nat.c gdb-10.2/gdb/sw_64-bsd-nat.c ++--- gdb-10.2/gdb/sw_64-bsd-nat.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-bsd-nat.c 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,202 @@ +++/* Native-dependent code for SW_64 BSD's. +++ +++ Copyright (C) 2000-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "defs.h" +++#include "inferior.h" +++#include "regcache.h" +++ +++#include "sw_64-tdep.h" +++#include "sw_64-bsd-tdep.h" +++#include "inf-ptrace.h" +++ +++#include +++#include +++#include +++ +++#ifdef HAVE_SYS_PROCFS_H +++#include +++#endif +++ +++#ifndef HAVE_GREGSET_T +++typedef struct reg gregset_t; +++#endif +++ +++#ifndef HAVE_FPREGSET_T +++typedef struct fpreg fpregset_t; +++#endif +++ +++#include "gregset.h" +++ +++struct sw_64_bsd_nat_target final : public inf_ptrace_target +++{ +++ void fetch_registers (struct regcache *, int) override; +++ void store_registers (struct regcache *, int) override; +++}; +++ +++static sw_64_bsd_nat_target the_sw_64_bsd_nat_target; +++ +++/* Provide *regset() wrappers around the generic SW_64 BSD register +++ supply/fill routines. */ +++ +++void +++supply_gregset (struct regcache *regcache, const gregset_t *gregsetp) +++{ +++ sw_64bsd_supply_reg (regcache, (const char *) gregsetp, -1); +++} +++ +++void +++fill_gregset (const struct regcache *regcache, gregset_t *gregsetp, int regno) +++{ +++ sw_64bsd_fill_reg (regcache, (char *) gregsetp, regno); +++} +++ +++void +++supply_fpregset (struct regcache *regcache, const fpregset_t *fpregsetp) +++{ +++ sw_64bsd_supply_fpreg (regcache, (const char *) fpregsetp, -1); +++} +++ +++void +++fill_fpregset (const struct regcache *regcache, +++ fpregset_t *fpregsetp, int regno) +++{ +++ sw_64bsd_fill_fpreg (regcache, (char *) fpregsetp, regno); +++} +++ +++/* Determine if PT_GETREGS fetches this register. */ +++ +++static int +++getregs_supplies (int regno) +++{ +++ return ((regno >= SW_64_V0_REGNUM && regno <= SW_64_ZERO_REGNUM) +++ || regno >= SW_64_PC_REGNUM); +++} +++ +++/* Fetch register REGNO from the inferior. If REGNO is -1, do this +++ for all registers (including the floating point registers). */ +++ +++void +++sw_64_bsd_nat_target::fetch_registers (struct regcache *regcache, int regno) +++{ +++ if (regno == -1 || getregs_supplies (regno)) +++ { +++ struct reg gregs; +++ +++ if (ptrace (PT_GETREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &gregs, 0) == -1) +++ perror_with_name (_("Couldn't get registers")); +++ +++ sw_64bsd_supply_reg (regcache, (char *) &gregs, regno); +++ if (regno != -1) +++ return; +++ } +++ +++ if (regno == -1 +++ || regno >= gdbarch_fp0_regnum (regcache->arch ())) +++ { +++ struct fpreg fpregs; +++ +++ if (ptrace (PT_GETFPREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) +++ perror_with_name (_("Couldn't get floating point status")); +++ +++ sw_64bsd_supply_fpreg (regcache, (char *) &fpregs, regno); +++ } +++} +++ +++/* Store register REGNO back into the inferior. If REGNO is -1, do +++ this for all registers (including the floating point registers). */ +++ +++void +++sw_64_bsd_nat_target::store_registers (struct regcache *regcache, int regno) +++{ +++ if (regno == -1 || getregs_supplies (regno)) +++ { +++ struct reg gregs; +++ if (ptrace (PT_GETREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &gregs, 0) == -1) +++ perror_with_name (_("Couldn't get registers")); +++ +++ sw_64bsd_fill_reg (regcache, (char *) &gregs, regno); +++ +++ if (ptrace (PT_SETREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &gregs, 0) == -1) +++ perror_with_name (_("Couldn't write registers")); +++ +++ if (regno != -1) +++ return; +++ } +++ +++ if (regno == -1 +++ || regno >= gdbarch_fp0_regnum (regcache->arch ())) +++ { +++ struct fpreg fpregs; +++ +++ if (ptrace (PT_GETFPREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) +++ perror_with_name (_("Couldn't get floating point status")); +++ +++ sw_64bsd_fill_fpreg (regcache, (char *) &fpregs, regno); +++ +++ if (ptrace (PT_SETFPREGS, regcache->ptid ().pid (), +++ (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) +++ perror_with_name (_("Couldn't write floating point status")); +++ } +++} +++ +++ +++/* Support for debugging kernel virtual memory images. */ +++ +++#include +++#include +++ +++#include "bsd-kvm.h" +++ +++static int +++sw_64bsd_supply_pcb (struct regcache *regcache, struct pcb *pcb) +++{ +++ int regnum; +++ +++ /* The following is true for OpenBSD 3.9: +++ +++ The pcb contains the register state at the context switch inside +++ cpu_switch(). */ +++ +++ /* The stack pointer shouldn't be zero. */ +++ if (pcb->pcb_hw.apcb_ksp == 0) +++ return 0; +++ +++ regcache->raw_supply (SW_64_SP_REGNUM, &pcb->pcb_hw.apcb_ksp); +++ +++ for (regnum = SW_64_S0_REGNUM; regnum < SW_64_A0_REGNUM; regnum++) +++ regcache->raw_supply (regnum, &pcb->pcb_context[regnum - SW_64_S0_REGNUM]); +++ regcache->raw_supply (SW_64_RA_REGNUM, &pcb->pcb_context[7]); +++ +++ return 1; +++} +++ +++ +++void +++_initialize_sw_64bsd_nat (void) +++{ +++ add_inf_child_target (&the_sw_64_bsd_nat_target); +++ +++ /* Support debugging kernel virtual memory images. */ +++ bsd_kvm_add_target (sw_64bsd_supply_pcb); +++} ++diff -Nuar gdb-10.2/gdb/sw_64-cpu.xml gdb-10.2/gdb/sw_64-cpu.xml ++--- gdb-10.2/gdb/sw_64-cpu.xml 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-cpu.xml 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,43 @@ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/sw_64-efu.xml gdb-10.2/gdb/sw_64-efu.xml ++--- gdb-10.2/gdb/sw_64-efu.xml 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-efu.xml 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,106 @@ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/sw_64-fpu.xml gdb-10.2/gdb/sw_64-fpu.xml ++--- gdb-10.2/gdb/sw_64-fpu.xml 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-fpu.xml 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,42 @@ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/sw_64-linux-nat.c gdb-10.2/gdb/sw_64-linux-nat.c ++--- gdb-10.2/gdb/sw_64-linux-nat.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-linux-nat.c 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,365 @@ +++/* Low level SW_64 GNU/Linux interface, for GDB when running native. +++ Copyright (C) 2005-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "defs.h" +++#include "target.h" +++#include "regcache.h" +++#include "linux-nat-trad.h" +++ +++#include "sw_64-tdep.h" +++#include "gdbarch.h" +++ +++#include "nat/gdb_ptrace.h" +++#include "nat/sw_64-linux-watch.h" +++#include +++ +++#include +++#include "gregset.h" +++#include "inferior.h" +++ +++/* The address of UNIQUE for ptrace. */ +++#define SW_UNIQUE_PTRACE_ADDR 65 +++ +++/* -1 if the kernel and/or CPU do not support watch registers. +++ * 1 if watch_readback is valid and we can read style, num_valid +++ * and the masks. +++ * 0 if we need to read the watch_readback. */ +++ +++static int watch_readback_valid; +++ +++/* Cached watch register read values. */ +++ +++static struct arch_lwp_info watch_readback; +++//static struct pt_watch_regs watch_readback; +++ +++ +++class sw_64_linux_nat_target final : public linux_nat_trad_target +++{ +++public: +++ void close () override; +++ +++#ifdef LHX20201012 +++ int can_use_hw_breakpoint (enum bptype, int, int) override; +++ +++ int remove_watchpoint (CORE_ADDR, int, enum target_hw_bp_type, +++ struct expression *) override; +++ +++ int insert_watchpoint (CORE_ADDR, int, enum target_hw_bp_type, +++ struct expression *) override; +++ +++ bool stopped_by_watchpoint () override; +++ +++ bool stopped_data_address (CORE_ADDR *) override; +++#endif +++ +++ int region_ok_for_hw_watchpoint (CORE_ADDR, int) override; +++ +++ void low_prepare_to_resume (struct lwp_info *lp) override; +++ +++protected: +++ /* Override linux_nat_trad_target methods. */ +++ CORE_ADDR register_u_offset (struct gdbarch *gdbarch, +++ int regno, int store_p) override; +++ +++ +++private: +++}; +++ +++static sw_64_linux_nat_target the_sw_64_linux_nat_target; +++ +++/* See the comment in m68k-tdep.c regarding the utility of these +++ functions. */ +++ +++void +++supply_gregset (struct regcache *regcache, const gdb_gregset_t *gregsetp) +++{ +++ const long *regp = (const long *)gregsetp; +++ +++ /* PC is in slot 32, UNIQUE is in slot 33. */ +++ sw_64_supply_int_regs (regcache, -1, regp, regp + 31, regp + 32); +++} +++ +++void +++fill_gregset (const struct regcache *regcache, +++ gdb_gregset_t *gregsetp, int regno) +++{ +++ long *regp = (long *)gregsetp; +++ +++ /* PC is in slot 32, UNIQUE is in slot 33. */ +++ sw_64_fill_int_regs (regcache, regno, regp, regp + 31, regp + 32); +++} +++ +++/* Now we do the same thing for floating-point registers. +++ Again, see the comments in m68k-tdep.c. */ +++ +++void +++supply_fpregset (struct regcache *regcache, const gdb_fpregset_t *fpregsetp) +++{ +++ const long *regp = (const long *)fpregsetp; +++ +++ /* FPCR is in slot 32. */ +++ sw_64_supply_fp_regs (regcache, -1, regp, regp + 31); +++} +++ +++void +++fill_fpregset (const struct regcache *regcache, +++ gdb_fpregset_t *fpregsetp, int regno) +++{ +++ long *regp = (long *)fpregsetp; +++ +++ /* FPCR is in slot 32. */ +++ sw_64_fill_fp_regs (regcache, regno, regp, regp + 31); +++} +++ +++CORE_ADDR +++sw_64_linux_nat_target::register_u_offset (struct gdbarch *gdbarch, +++ int regno, int store_p) +++{ +++ if (regno == gdbarch_pc_regnum (gdbarch)) +++ return PC; +++ if (regno == SW_UNIQUE_REGNUM) +++ return SW_UNIQUE_PTRACE_ADDR; +++ if (regno < gdbarch_fp0_regnum (gdbarch)) +++ return GPR_BASE + regno; +++ else +++ return FPR_BASE + regno - gdbarch_fp0_regnum (gdbarch); +++} +++ +++#ifdef LHX20201012 +++/* Target to_can_use_hw_breakpoint implementation. Return 1 if we can +++ handle the specified watch type. */ +++ +++int +++sw_64_linux_nat_target::can_use_hw_breakpoint (enum bptype type, +++ int cnt, int ot) +++{ +++ debug("type:%d,cnt:%d,ot:%d", type,cnt,ot); +++ +++ if (type == bp_hardware_watchpoint || type == bp_read_watchpoint +++ || type == bp_access_watchpoint || type == bp_watchpoint) +++ return !(watch_readback.wpt[0].valid); +++ +++ if (type == bp_value_watchpoint) +++ return !watch_readback.wpt[1].valid; +++ +++ return (cnt == 0) ? 1 : 0; +++} +++ +++/* Target to_stopped_by_watchpoint implementation. Return 1 if +++ stopped by watchpoint. The watchhi R and W bits indicate the watch +++ register triggered. */ +++ +++bool +++sw_64_linux_nat_target::stopped_by_watchpoint () +++{ +++ siginfo_t siginfo; +++ pid_t lwpid = inferior_ptid.lwp(); +++ +++ /* Retrieve siginfo. */ +++ errno = 0; +++ ptrace (PTRACE_GETSIGINFO, lwpid, 0, &siginfo); +++ if (errno != 0) +++ { +++ warning("%s:%d GETSIGINFO return %d\n", __FILE__, __LINE__, errno); +++ return false; +++ } +++ /* This must be a hardware breakpoint. */ +++ if (siginfo.si_signo != SIGTRAP +++ || (siginfo.si_code & 0xffff) != M_DA_MATCH_TRAP/* TRAP_HWBKPT */) +++ return false; +++ +++ debug("si_code=%#x si_signo=%d si_errno = %x pc=%#lx, data_address %#lx", +++ siginfo.si_code, siginfo.si_signo,siginfo.si_errno,(long)siginfo.si_value.sival_ptr, (long)siginfo.si_addr); +++ /* siginfo should return the accessed data address, not pc */ +++ switch (siginfo.si_errno){ +++ case 1: //si_errno[0]: +++ case 4: +++ case 7: //si_errno[2]: +++ watch_readback.stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (watch_readback.wpt[0].match & ((1L<<53)-1)); +++ watch_readback.matched = 1; +++ break; +++ case 2: //si_errno[`] +++ watch_readback.stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (watch_readback.value_address); // get the saved +++ watch_readback.matched = 1; +++ break; +++ default: +++ ;; +++ } +++ return true; +++} +++ +++/* Target to_stopped_data_address implementation. Set the address +++ where the watch triggered (if known). Return 1 if the address was +++ known. */ +++ +++bool +++sw_64_linux_nat_target::stopped_data_address (CORE_ADDR *paddr) +++{ +++ if (watch_readback.matched) +++ { +++ *paddr = watch_readback.stopped_data_address; +++ return true; +++ } +++ return false; +++} +++#endif +++ +++/* Target to_region_ok_for_hw_watchpoint implementation. Return 1 if +++ the specified region can be covered by the watch registers. */ +++ +++int +++sw_64_linux_nat_target::region_ok_for_hw_watchpoint (CORE_ADDR addr, int len) +++{ +++ /* Can not set watchpoints for zero or negative lengths. */ +++ if (len <= 0) +++ return 0; +++ +++ /* The current ptrace interface can only handle watchpoints that are a +++ * power of 2. */ +++ if ((len & (len - 1)) != 0) +++ return 0; +++ +++ /* All tests passed so we must be able to set a watchpoint. */ +++ return 1; +++} +++ +++enum sw_64_hw_bp_type +++sw_64_hw_bp_type_from_target_hw_bp_type (enum target_hw_bp_type raw_type) +++{ +++ switch (raw_type) +++ { +++ case hw_execute: +++ /* permit r/w */ +++ return sw_64_none; +++ case hw_write: +++ return sw_64_write; +++ case hw_read: +++ return sw_64_read; +++ case hw_access: +++ return sw_64_access; +++ case hw_vstore: +++ return sw_64_vstore; +++ default: +++ error ( "bad raw breakpoint type %d", (int) raw_type); +++ } +++} +++ +++#ifdef LHX20201012 +++/* Target to_insert_watchpoint implementation. Try to insert a new +++ watch. Return zero on success. */ +++ +++int +++sw_64_linux_nat_target::insert_watchpoint (CORE_ADDR addr, int len, +++ enum target_hw_bp_type type, +++ struct expression *cond) +++{ +++ enum sw_64_hw_bp_type watch_type; +++ +++ debug("%s insert wpt at %#lx type %d", target_pid_to_str(inferior_ptid), +++ addr, type); +++ +++ +++ watch_type = sw_64_hw_bp_type_from_target_hw_bp_type(type); +++ +++ if (sw_64_linux_try_one_watch(inferior_ptid.lwp(), &watch_readback, watch_type,addr,len)) +++ return 0; +++ return -1; +++} +++ +++/* Target to_remove_watchpoint implementation. Try to remove a watch. +++ Return zero on success. */ +++ +++int +++sw_64_linux_nat_target::remove_watchpoint (CORE_ADDR addr, int len, +++ enum target_hw_bp_type type, +++ struct expression *cond) +++{ +++ enum sw_64_hw_bp_type watch_type; +++ +++ watch_type = sw_64_hw_bp_type_from_target_hw_bp_type(type); +++ if (sw_64_linux_del_one_watch(&watch_readback, watch_type,addr,len)) +++ return 0; +++ return -1; +++} +++#endif +++ +++/* Target to_close implementation. Free any watches and call the +++ super implementation. */ +++ +++void +++sw_64_linux_nat_target::close () +++{ +++ linux_nat_trad_target::close (); +++} +++ +++/* Called when resuming a thread. +++ The hardware debug registers are updated when there is any change. */ +++ +++void +++sw_64_linux_nat_target::low_prepare_to_resume (struct lwp_info *lwp) +++{ +++ int i,ctl; +++ int lwpid = lwp->ptid.lwp(); +++ int regno[2]= {M_DA_MATCH,M_DV_MATCH}; +++ struct pt_watch_regs *wpt = watch_readback.wpt; +++ +++ /* NULL means this is the main thread still going through the shell, +++ or, no watchpoint has been set yet. In that case, there's +++ nothing to do. */ +++ +++ for (i = 0, ctl=0; i < MAX_WPTS; i++) +++ if (watch_readback.wpts_changed[i]) +++ { +++ //debug("write master da/dv_match %#lx, mask %#lx", wpt[i].match, wpt[i].mask); +++ store_debug_register (lwpid, regno[i], wpt[i].match); +++ store_debug_register (lwpid, regno[i]+1, wpt[i].mask); +++ //perror_with_name (_("Unexpected error setting watchpoint")); +++ ctl |= watch_readback.wpts_changed[i] <. */ +++#include "defs.h" +++#include "frame.h" +++#include "osabi.h" +++#include "solib-svr4.h" +++#include "symtab.h" +++#include "regset.h" +++#include "regcache.h" +++#include "linux-tdep.h" +++#include "sw_64-tdep.h" +++#include "gdbarch.h" +++#ifndef LHX20210326 +++#include "xml-syscall.h" +++#endif +++ +++ +++//sw_64-linux-tdep.c +++ +++ +++#include "glibc-tdep.h" +++#include "sw_64-linux-tdep.h" +++#include "tramp-frame.h" +++#include "trad-frame.h" +++#include "target/target.h" +++ +++ +++#include "stap-probe.h" +++#include "parser-defs.h" +++#include "user-regs.h" +++#include +++ +++#include "record-full.h" +++#include "linux-record.h" +++/* This enum represents the signals' numbers on the Alpha +++ architecture. It just contains the signal definitions which are +++ different from the generic implementation. +++ +++ It is derived from the file , +++ from the Linux kernel tree. */ +++ +++enum +++ { +++ /* SIGABRT is the same as in the generic implementation, but is +++ defined here because SIGIOT depends on it. */ +++ SW_LINUX_SIGABRT = 6, +++ SW_LINUX_SIGEMT = 7, +++ SW_LINUX_SIGBUS = 10, +++ SW_LINUX_SIGSYS = 12, +++ SW_LINUX_SIGURG = 16, +++ SW_LINUX_SIGSTOP = 17, +++ SW_LINUX_SIGTSTP = 18, +++ SW_LINUX_SIGCONT = 19, +++ SW_LINUX_SIGCHLD = 20, +++ SW_LINUX_SIGIO = 23, +++ SW_LINUX_SIGINFO = 29, +++ SW_LINUX_SIGUSR1 = 30, +++ SW_LINUX_SIGUSR2 = 31, +++ SW_LINUX_SIGPOLL = SW_LINUX_SIGIO, +++ SW_LINUX_SIGPWR = SW_LINUX_SIGINFO, +++ SW_LINUX_SIGIOT = SW_LINUX_SIGABRT, +++ }; +++ +++/* Under GNU/Linux, signal handler invocations can be identified by +++ the designated code sequence that is used to return from a signal +++ handler. In particular, the return address of a signal handler +++ points to a sequence that copies $sp to $16, loads $0 with the +++ appropriate syscall number, and finally enters the kernel. +++ +++ This is somewhat complicated in that: +++ (1) the expansion of the "mov" assembler macro has changed over +++ time, from "bis src,src,dst" to "bis zero,src,dst", +++ (2) the kernel has changed from using "addq" to "lda" to load the +++ syscall number, +++ (3) there is a "normal" sigreturn and an "rt" sigreturn which +++ has a different stack layout. */ +++ +++static long +++sw_64_linux_sigtramp_offset_1 (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ switch (sw_64_read_insn (gdbarch, pc)) +++ { +++ case 0x47de0410: /* bis $30,$30,$16 */ +++ case 0x47fe0410: /* bis $31,$30,$16 */ +++ return 0; +++ +++ case 0x43ecf400: /* addq $31,103,$0 */ +++#if 0 +++ case 0x201f0067: /* lda $0,103($31) */ +++ case 0x201f015f: /* lda $0,351($31) */ +++#else +++ case 0xf81f0067U: +++ case 0xf81f015fU: +++#endif +++ return 4; +++ +++ case 0x00000083: /* call_pal callsys */ +++ return 8; +++ +++ default: +++ return -1; +++ } +++} +++ +++static LONGEST +++sw_64_linux_sigtramp_offset (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ long i, off; +++ +++ if (pc & 3) +++ return -1; +++ +++ /* Guess where we might be in the sequence. */ +++ off = sw_64_linux_sigtramp_offset_1 (gdbarch, pc); +++ if (off < 0) +++ return -1; +++ +++ /* Verify that the other two insns of the sequence are as we expect. */ +++ pc -= off; +++ for (i = 0; i < 12; i += 4) +++ { +++ if (i == off) +++ continue; +++ if (sw_64_linux_sigtramp_offset_1 (gdbarch, pc + i) != i) +++ return -1; +++ } +++ +++ return off; +++} +++ +++static int +++sw_64_linux_pc_in_sigtramp (struct gdbarch *gdbarch, +++ CORE_ADDR pc, const char *func_name) +++{ +++ return sw_64_linux_sigtramp_offset (gdbarch, pc) >= 0; +++} +++ +++static CORE_ADDR +++sw_64_linux_sigcontext_addr (struct frame_info *this_frame) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (this_frame); +++ CORE_ADDR pc; +++ ULONGEST sp; +++ long off; +++ +++ pc = get_frame_pc (this_frame); +++ sp = get_frame_register_unsigned (this_frame, SW_SP_REGNUM); +++ +++ off = sw_64_linux_sigtramp_offset (gdbarch, pc); +++ gdb_assert (off >= 0); +++ +++ /* __NR_rt_sigreturn has a couple of structures on the stack. This is: +++ +++ struct rt_sigframe { +++ struct siginfo info; +++ struct ucontext uc; +++ }; +++ +++ offsetof (struct rt_sigframe, uc.uc_mcontext); */ +++ +++ if (sw_64_read_insn (gdbarch, pc - off + 4) == 0xf81f015fU) +++ return sp + 176; +++ +++ /* __NR_sigreturn has the sigcontext structure at the top of the stack. */ +++ return sp; +++} +++ +++/* Supply register REGNUM from the buffer specified by GREGS and LEN +++ in the general-purpose register set REGSET to register cache +++ REGCACHE. If REGNUM is -1, do this for all registers in REGSET. */ +++ +++static void +++sw_64_linux_supply_gregset (const struct regset *regset, +++ struct regcache *regcache, +++ int regnum, const void *gregs, size_t len) +++{ +++ const gdb_byte *regs = (const gdb_byte *) gregs; +++ +++ gdb_assert (len >= 32 * 8); +++ sw_64_supply_int_regs (regcache, regnum, regs, regs + 31 * 8, +++ len >= 33 * 8 ? regs + 32 * 8 : NULL); +++} +++ +++/* Collect register REGNUM from the register cache REGCACHE and store +++ it in the buffer specified by GREGS and LEN as described by the +++ general-purpose register set REGSET. If REGNUM is -1, do this for +++ all registers in REGSET. */ +++ +++static void +++sw_64_linux_collect_gregset (const struct regset *regset, +++ const struct regcache *regcache, +++ int regnum, void *gregs, size_t len) +++{ +++ gdb_byte *regs = (gdb_byte *) gregs; +++ +++ gdb_assert (len >= 32 * 8); +++ sw_64_fill_int_regs (regcache, regnum, regs, regs + 31 * 8, +++ len >= 33 * 8 ? regs + 32 * 8 : NULL); +++} +++ +++/* Supply register REGNUM from the buffer specified by FPREGS and LEN +++ in the floating-point register set REGSET to register cache +++ REGCACHE. If REGNUM is -1, do this for all registers in REGSET. */ +++ +++static void +++sw_64_linux_supply_fpregset (const struct regset *regset, +++ struct regcache *regcache, +++ int regnum, const void *fpregs, size_t len) +++{ +++ const gdb_byte *regs = (const gdb_byte *) fpregs; +++ +++ gdb_assert (len >= 32 * 8); +++ sw_64_supply_fp_regs (regcache, regnum, regs, regs + 31 * 8); +++} +++ +++/* Collect register REGNUM from the register cache REGCACHE and store +++ it in the buffer specified by FPREGS and LEN as described by the +++ general-purpose register set REGSET. If REGNUM is -1, do this for +++ all registers in REGSET. */ +++ +++static void +++sw_64_linux_collect_fpregset (const struct regset *regset, +++ const struct regcache *regcache, +++ int regnum, void *fpregs, size_t len) +++{ +++ gdb_byte *regs = (gdb_byte *) fpregs; +++ +++ gdb_assert (len >= 32 * 8); +++ sw_64_fill_fp_regs (regcache, regnum, regs, regs + 31 * 8); +++} +++ +++static const struct regset sw_64_linux_gregset = +++{ +++ NULL, +++ sw_64_linux_supply_gregset, sw_64_linux_collect_gregset +++}; +++ +++static const struct regset sw_64_linux_fpregset = +++{ +++ NULL, +++ sw_64_linux_supply_fpregset, sw_64_linux_collect_fpregset +++}; +++ +++/* Iterate over core file register note sections. */ +++ +++static void +++sw_64_linux_iterate_over_regset_sections (struct gdbarch *gdbarch, +++ iterate_over_regset_sections_cb *cb, +++ void *cb_data, +++ const struct regcache *regcache) +++{ +++ cb (".reg", 32 * 8, 32 * 8, &sw_64_linux_gregset, NULL, cb_data); +++ cb (".reg2", 32 * 8, 32 * 8, &sw_64_linux_fpregset, NULL, cb_data); +++} +++ +++/* Implementation of `gdbarch_gdb_signal_from_target', as defined in +++ gdbarch.h. */ +++ +++static enum gdb_signal +++sw_64_linux_gdb_signal_from_target (struct gdbarch *gdbarch, +++ int signal) +++{ +++ switch (signal) +++ { +++ case SW_LINUX_SIGEMT: +++ return GDB_SIGNAL_EMT; +++ +++ case SW_LINUX_SIGBUS: +++ return GDB_SIGNAL_BUS; +++ +++ case SW_LINUX_SIGSYS: +++ return GDB_SIGNAL_SYS; +++ +++ case SW_LINUX_SIGURG: +++ return GDB_SIGNAL_URG; +++ +++ case SW_LINUX_SIGSTOP: +++ return GDB_SIGNAL_STOP; +++ +++ case SW_LINUX_SIGTSTP: +++ return GDB_SIGNAL_TSTP; +++ +++ case SW_LINUX_SIGCONT: +++ return GDB_SIGNAL_CONT; +++ +++ case SW_LINUX_SIGCHLD: +++ return GDB_SIGNAL_CHLD; +++ +++ /* No way to differentiate between SIGIO and SIGPOLL. +++ Therefore, we just handle the first one. */ +++ case SW_LINUX_SIGIO: +++ return GDB_SIGNAL_IO; +++ +++ /* No way to differentiate between SIGINFO and SIGPWR. +++ Therefore, we just handle the first one. */ +++ case SW_LINUX_SIGINFO: +++ return GDB_SIGNAL_INFO; +++ +++ case SW_LINUX_SIGUSR1: +++ return GDB_SIGNAL_USR1; +++ +++ case SW_LINUX_SIGUSR2: +++ return GDB_SIGNAL_USR2; +++ } +++ +++ return linux_gdb_signal_from_target (gdbarch, signal); +++} +++ +++/* Implementation of `gdbarch_gdb_signal_to_target', as defined in +++ gdbarch.h. */ +++ +++static int +++sw_64_linux_gdb_signal_to_target (struct gdbarch *gdbarch, +++ enum gdb_signal signal) +++{ +++ switch (signal) +++ { +++ case GDB_SIGNAL_EMT: +++ return SW_LINUX_SIGEMT; +++ +++ case GDB_SIGNAL_BUS: +++ return SW_LINUX_SIGBUS; +++ +++ case GDB_SIGNAL_SYS: +++ return SW_LINUX_SIGSYS; +++ +++ case GDB_SIGNAL_URG: +++ return SW_LINUX_SIGURG; +++ +++ case GDB_SIGNAL_STOP: +++ return SW_LINUX_SIGSTOP; +++ +++ case GDB_SIGNAL_TSTP: +++ return SW_LINUX_SIGTSTP; +++ +++ case GDB_SIGNAL_CONT: +++ return SW_LINUX_SIGCONT; +++ +++ case GDB_SIGNAL_CHLD: +++ return SW_LINUX_SIGCHLD; +++ +++ case GDB_SIGNAL_IO: +++ return SW_LINUX_SIGIO; +++ +++ case GDB_SIGNAL_INFO: +++ return SW_LINUX_SIGINFO; +++ +++ case GDB_SIGNAL_USR1: +++ return SW_LINUX_SIGUSR1; +++ +++ case GDB_SIGNAL_USR2: +++ return SW_LINUX_SIGUSR2; +++ +++ case GDB_SIGNAL_POLL: +++ return SW_LINUX_SIGPOLL; +++ +++ case GDB_SIGNAL_PWR: +++ return SW_LINUX_SIGPWR; +++ } +++ +++ return linux_gdb_signal_to_target (gdbarch, signal); +++} +++ +++#ifndef LHX20210326 +++/* Return the current system call's number present in the +++ v0 register. When the function fails, it returns -1. */ +++ +++static LONGEST +++sw_64_linux_get_syscall_number (struct gdbarch *gdbarch, +++ thread_info *thread) +++{ +++ struct regcache *regcache = get_thread_regcache (thread); +++ //struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ int regsize = register_size (gdbarch, SW_V0_REGNUM); +++ /* The content of a register */ +++ gdb_byte buf[8]; +++ /* The result */ +++ LONGEST ret; +++ +++// /* Make sure we're in a known ABI */ +++// gdb_assert (tdep->mips_abi == MIPS_ABI_O32 +++// || tdep->mips_abi == MIPS_ABI_N32 +++// || tdep->mips_abi == MIPS_ABI_N64); +++// +++// gdb_assert (regsize <= sizeof (buf)); +++ +++ /* Getting the system call number from the register. +++ syscall number is in v0 or $0. */ +++ regcache->cooked_read (SW_V0_REGNUM, buf); +++ +++ ret = extract_signed_integer (buf, regsize, byte_order); +++ +++ return ret; +++} +++#endif +++ +++/* Initialize linux_record_tdep if not initialized yet. +++ WORDSIZE is 4 or 8 for 32- or 64-bit PowerPC Linux respectively. +++ Sizes of data structures are initialized accordingly. */ +++ +++static void +++sw_64_init_linux_record_tdep (struct linux_record_tdep *record_tdep, +++ int wordsize) +++ +++{ +++ /* Simply return if it had been initialized. */ +++ if (record_tdep->size_pointer != 0) +++ return; +++ +++ /* These values are the size of the type that will be used in a system +++ call. They are obtained from Linux Kernel source. */ +++ +++ if (wordsize == 8) +++ { +++ record_tdep->size_pointer = 8; +++ record_tdep->size__old_kernel_stat = 32; +++ record_tdep->size_tms = 32; +++ record_tdep->size_loff_t = 8; +++ record_tdep->size_flock = 32; +++ record_tdep->size_oldold_utsname = 45; +++ record_tdep->size_ustat = 32; +++ record_tdep->size_old_sigaction = 32; +++ record_tdep->size_old_sigset_t = 8; +++ record_tdep->size_rlimit = 16; +++ record_tdep->size_rusage = 144; +++ record_tdep->size_timeval = 16; +++ record_tdep->size_timezone = 8; +++ record_tdep->size_old_gid_t = 4; +++ record_tdep->size_old_uid_t = 4; +++ record_tdep->size_fd_set = 128; +++ record_tdep->size_old_dirent = 280; +++ record_tdep->size_statfs = 120; +++ record_tdep->size_statfs64 = 120; +++ record_tdep->size_sockaddr = 16; +++ record_tdep->size_int = 4; +++ record_tdep->size_long = 8; +++ record_tdep->size_ulong = 8; +++ record_tdep->size_msghdr = 56; +++ record_tdep->size_itimerval = 32; +++ record_tdep->size_stat = 144; +++ record_tdep->size_old_utsname = 325; +++ record_tdep->size_sysinfo = 112; +++ record_tdep->size_msqid_ds = 120; +++ record_tdep->size_shmid_ds = 112; +++ record_tdep->size_new_utsname = 390; +++ record_tdep->size_timex = 208; +++ record_tdep->size_mem_dqinfo = 24; +++ record_tdep->size_if_dqblk = 72; +++ record_tdep->size_fs_quota_stat = 80; +++ record_tdep->size_timespec = 16; +++ record_tdep->size_pollfd = 8; +++ record_tdep->size_NFS_FHSIZE = 32; +++ record_tdep->size_knfsd_fh = 132; +++ record_tdep->size_TASK_COMM_LEN = 16; +++ record_tdep->size_sigaction = 32; +++ record_tdep->size_sigset_t = 8; +++ record_tdep->size_siginfo_t = 128; +++ record_tdep->size_cap_user_data_t = 8; +++ record_tdep->size_stack_t = 24; +++ record_tdep->size_off_t = 8; +++ record_tdep->size_stat64 = 104; +++ record_tdep->size_gid_t = 4; +++ record_tdep->size_uid_t = 4; +++ record_tdep->size_PAGE_SIZE = 0x10000; /* 64KB */ +++ record_tdep->size_flock64 = 32; +++ record_tdep->size_io_event = 32; +++ record_tdep->size_iocb = 64; +++ record_tdep->size_epoll_event = 16; +++ record_tdep->size_itimerspec = 32; +++ record_tdep->size_mq_attr = 64; +++ record_tdep->size_termios = 44; +++ record_tdep->size_pid_t = 4; +++ record_tdep->size_winsize = 8; +++ record_tdep->size_serial_struct = 72; +++ record_tdep->size_serial_icounter_struct = 80; +++ record_tdep->size_size_t = 8; +++ record_tdep->size_iovec = 16; +++ record_tdep->size_time_t = 8; +++ } +++ else if (wordsize == 4) +++ { +++ record_tdep->size_pointer = 4; +++ record_tdep->size__old_kernel_stat = 32; +++ record_tdep->size_tms = 16; +++ record_tdep->size_loff_t = 8; +++ record_tdep->size_flock = 16; +++ record_tdep->size_oldold_utsname = 45; +++ record_tdep->size_ustat = 20; +++ record_tdep->size_old_sigaction = 16; +++ record_tdep->size_old_sigset_t = 4; +++ record_tdep->size_rlimit = 8; +++ record_tdep->size_rusage = 72; +++ record_tdep->size_timeval = 8; +++ record_tdep->size_timezone = 8; +++ record_tdep->size_old_gid_t = 4; +++ record_tdep->size_old_uid_t = 4; +++ record_tdep->size_fd_set = 128; +++ record_tdep->size_old_dirent = 268; +++ record_tdep->size_statfs = 64; +++ record_tdep->size_statfs64 = 88; +++ record_tdep->size_sockaddr = 16; +++ record_tdep->size_int = 4; +++ record_tdep->size_long = 4; +++ record_tdep->size_ulong = 4; +++ record_tdep->size_msghdr = 28; +++ record_tdep->size_itimerval = 16; +++ record_tdep->size_stat = 88; +++ record_tdep->size_old_utsname = 325; +++ record_tdep->size_sysinfo = 64; +++ record_tdep->size_msqid_ds = 68; +++ record_tdep->size_shmid_ds = 60; +++ record_tdep->size_new_utsname = 390; +++ record_tdep->size_timex = 128; +++ record_tdep->size_mem_dqinfo = 24; +++ record_tdep->size_if_dqblk = 72; +++ record_tdep->size_fs_quota_stat = 80; +++ record_tdep->size_timespec = 8; +++ record_tdep->size_pollfd = 8; +++ record_tdep->size_NFS_FHSIZE = 32; +++ record_tdep->size_knfsd_fh = 132; +++ record_tdep->size_TASK_COMM_LEN = 16; +++ record_tdep->size_sigaction = 20; +++ record_tdep->size_sigset_t = 8; +++ record_tdep->size_siginfo_t = 128; +++ record_tdep->size_cap_user_data_t = 4; +++ record_tdep->size_stack_t = 12; +++ record_tdep->size_off_t = 4; +++ record_tdep->size_stat64 = 104; +++ record_tdep->size_gid_t = 4; +++ record_tdep->size_uid_t = 4; +++ record_tdep->size_PAGE_SIZE = 0x10000; /* 64KB */ +++ record_tdep->size_flock64 = 32; +++ record_tdep->size_io_event = 32; +++ record_tdep->size_iocb = 64; +++ record_tdep->size_epoll_event = 16; +++ record_tdep->size_itimerspec = 16; +++ record_tdep->size_mq_attr = 32; +++ record_tdep->size_termios = 44; +++ record_tdep->size_pid_t = 4; +++ record_tdep->size_winsize = 8; +++ record_tdep->size_serial_struct = 60; +++ record_tdep->size_serial_icounter_struct = 80; +++ record_tdep->size_size_t = 4; +++ record_tdep->size_iovec = 8; +++ record_tdep->size_time_t = 4; +++ } +++ else +++ internal_error (__FILE__, __LINE__, _("unexpected wordsize")); +++ +++ /* These values are the second argument of system call "sys_fcntl" +++ and "sys_fcntl64". They are obtained from Linux Kernel source. */ +++ record_tdep->fcntl_F_GETLK = 5; +++ record_tdep->fcntl_F_GETLK64 = 12; +++ record_tdep->fcntl_F_SETLK64 = 13; +++ record_tdep->fcntl_F_SETLKW64 = 14; +++ +++ record_tdep->arg1 = SW_A0_REGNUM + 0; +++ record_tdep->arg2 = SW_A0_REGNUM + 1; +++ record_tdep->arg3 = SW_A0_REGNUM + 2; +++ record_tdep->arg4 = SW_A0_REGNUM + 3; +++ record_tdep->arg5 = SW_A0_REGNUM + 4; +++ record_tdep->arg6 = SW_A0_REGNUM + 5; +++ +++ /* These values are the second argument of system call "sys_ioctl". +++ They are obtained from Linux Kernel source. +++ See arch/powerpc/include/uapi/asm/ioctls.h. */ +++ record_tdep->ioctl_TCGETS = 0x403c7413;//402c7413 +++ record_tdep->ioctl_TCSETS = 0x802c7414;//802c7414 +++ record_tdep->ioctl_TCSETSW = 0x802c7415;//802c7415 +++ record_tdep->ioctl_TCSETSF = 0x802c7416;//802c7416 +++ record_tdep->ioctl_TCGETA = 0x40127417;//40127417 +++ record_tdep->ioctl_TCSETA = 0x80127418;//80127418 +++ record_tdep->ioctl_TCSETAW = 0x80127419;//80127419 +++ record_tdep->ioctl_TCSETAF = 0x8012741c;//8012741c +++ record_tdep->ioctl_TCSBRK = 0x2000741d;//2000741d +++ record_tdep->ioctl_TCXONC = 0x2000741e;//2000741e +++ record_tdep->ioctl_TCFLSH = 0x2000741f;//2000741f +++ record_tdep->ioctl_TIOCEXCL = 0x540c;// +++ record_tdep->ioctl_TIOCNXCL = 0x540d;// +++ record_tdep->ioctl_TIOCSCTTY = 0x540e;// +++ record_tdep->ioctl_TIOCGPGRP = 0x40047477;//40047477 +++ record_tdep->ioctl_TIOCSPGRP = 0x80047476;//80047476 +++ record_tdep->ioctl_TIOCOUTQ = 0x40047473;//40047473 +++ record_tdep->ioctl_TIOCSTI = 0x5412;//5412 +++ record_tdep->ioctl_TIOCGWINSZ = 0x40087468;//40087468 +++ record_tdep->ioctl_TIOCSWINSZ = 0x80087467;//80087467 +++ record_tdep->ioctl_TIOCMGET = 0x5415;// +++ record_tdep->ioctl_TIOCMBIS = 0x5416;// +++ record_tdep->ioctl_TIOCMBIC = 0x5417;// +++ record_tdep->ioctl_TIOCMSET = 0x5418;// +++ record_tdep->ioctl_TIOCGSOFTCAR = 0x5419;// +++ record_tdep->ioctl_TIOCSSOFTCAR = 0x541a;// +++ record_tdep->ioctl_FIONREAD = 0x4004667f;//4004667f +++ record_tdep->ioctl_TIOCINQ = 0x4004667f;//4004667f +++ record_tdep->ioctl_TIOCLINUX = 0x541c;// +++ record_tdep->ioctl_TIOCCONS = 0x541d;// +++ record_tdep->ioctl_TIOCGSERIAL = 0x541e;// +++ record_tdep->ioctl_TIOCSSERIAL = 0x541f;// +++ record_tdep->ioctl_TIOCPKT = 0x5420;// +++ record_tdep->ioctl_FIONBIO = 0x8004667e;//8004667e +++ record_tdep->ioctl_TIOCNOTTY = 0x5422;// +++ record_tdep->ioctl_TIOCSETD = 0x5423;// +++ record_tdep->ioctl_TIOCGETD = 0x5424;// +++ record_tdep->ioctl_TCSBRKP = 0x5425;// +++ record_tdep->ioctl_TIOCSBRK = 0x5427; +++ record_tdep->ioctl_TIOCCBRK = 0x5428; +++ record_tdep->ioctl_TIOCGSID = 0x5429; +++ record_tdep->ioctl_TIOCGPTN = 0x40045430;//40045430 +++ record_tdep->ioctl_TIOCSPTLCK = 0x80045431;//80045431 +++ record_tdep->ioctl_FIONCLEX = 0x20006602;//20006602 +++ record_tdep->ioctl_FIOCLEX = 0x20006601;//20006601 +++ record_tdep->ioctl_FIOASYNC = 0x8004667d;//8004667d +++ record_tdep->ioctl_TIOCSERCONFIG = 0x5453;// +++ record_tdep->ioctl_TIOCSERGWILD = 0x5454; +++ record_tdep->ioctl_TIOCSERSWILD = 0x5455; +++ record_tdep->ioctl_TIOCGLCKTRMIOS = 0x5456; +++ record_tdep->ioctl_TIOCSLCKTRMIOS = 0x5457; +++ record_tdep->ioctl_TIOCSERGSTRUCT = 0x5458; +++ record_tdep->ioctl_TIOCSERGETLSR = 0x5459; +++ record_tdep->ioctl_TIOCSERGETMULTI = 0x545a; +++ record_tdep->ioctl_TIOCSERSETMULTI = 0x545b; +++ record_tdep->ioctl_TIOCMIWAIT = 0x545c; +++ record_tdep->ioctl_TIOCGICOUNT = 0x545d; +++ record_tdep->ioctl_FIOQSIZE = 0x40086680;// +++} +++ +++/* Implementation of `gdbarch_stap_is_single_operand', as defined in +++ gdbarch.h. */ +++ +++//static int +++//sw_64_stap_is_single_operand (struct gdbarch *gdbarch, const char *s) +++//{ +++// return (*s == 'i' /* Literal number. */ +++ // || (isdigit (*s) && s[1] == '(' +++ // && isdigit (s[2])) /* Displacement. */ +++ // || (*s == '(' && isdigit (s[1])) /* Register indirection. */ +++ // || isdigit (*s)); /* Register value. */ +++//} +++ +++ +++ +++/* Target-dependent code for GNU/Linux AArch64. +++ +++ Copyright (C) 2009-2020 Free Software Foundation, Inc. +++ Contributed by ARM Ltd. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++/* Signal frame handling. +++ +++ +------------+ ^ +++ | saved lr | | +++ +->| saved fp |--+ +++ | | | +++ | | | +++ | +------------+ +++ | | saved lr | +++ +--| saved fp | +++ ^ | | +++ | | | +++ | +------------+ +++ ^ | | +++ | | signal | +++ | | | SIGTRAMP_FRAME (struct rt_sigframe) +++ | | saved regs | +++ +--| saved sp |--> interrupted_sp +++ | | saved pc |--> interrupted_pc +++ | | | +++ | +------------+ +++ | | saved lr |--> default_restorer (movz x8, NR_sys_rt_sigreturn; svc 0) +++ +--| saved fp |<- FP +++ | | NORMAL_FRAME +++ | |<- SP +++ +------------+ +++ +++ On signal delivery, the kernel will create a signal handler stack +++ frame and setup the return address in LR to point at restorer stub. +++ The signal stack frame is defined by: +++ +++ struct rt_sigframe +++ { +++ siginfo_t info; +++ struct ucontext uc; +++ }; +++ +++ The ucontext has the following form: +++ struct ucontext +++ { +++ unsigned long uc_flags; +++ struct ucontext *uc_link; +++ stack_t uc_stack; +++ sigset_t uc_sigmask; +++ struct sigcontext uc_mcontext; +++ }; +++ +++ struct sigcontext +++ { +++ unsigned long fault_address; +++ unsigned long regs[31]; +++ unsigned long sp; / * 31 * / +++ unsigned long pc; / * 32 * / +++ unsigned long pstate; / * 33 * / +++ __u8 __reserved[4096] +++ }; +++ +++ The reserved space in sigcontext contains additional structures, each starting +++ with a sw_64_ctx, which specifies a unique identifier and the total size of +++ the structure. The final structure in reserved will start will a null +++ sw_64_ctx. The penultimate entry in reserved may be a extra_context which +++ then points to a further block of reserved space. +++ +++ struct sw_64_ctx { +++ u32 magic; +++ u32 size; +++ }; +++ +++ The restorer stub will always have the form: +++ +++ d28015a8 movz x8, #0xad +++ d4000001 svc #0x0 +++ +++ This is a system call sys_rt_sigreturn. +++ +++ We detect signal frames by snooping the return code for the restorer +++ instruction sequence. +++ +++ The handler then needs to recover the saved register set from +++ ucontext.uc_mcontext. */ +++ +++/* These magic numbers need to reflect the layout of the kernel +++ defined struct rt_sigframe and ucontext. */ +++#define SW_SIGCONTEXT_REG_SIZE 8 +++#define SW_RT_SIGFRAME_UCONTEXT_OFFSET 128 +++#define SW_UCONTEXT_SIGCONTEXT_OFFSET 176 +++#define SW_SIGCONTEXT_XO_OFFSET 8 +++#define SW_SIGCONTEXT_RESERVED_OFFSET 288 +++ +++#define SW_SIGCONTEXT_RESERVED_SIZE 4096 +++ +++/* Unique identifiers that may be used for sw_64_ctx.magic. */ +++#define SW_EXTRA_MAGIC 0x45585401 +++#define SW_FPSIMD_MAGIC 0x46508001 +++#define SW_SVE_MAGIC 0x53564501 +++ +++/* Defines for the extra_context that follows an SW_EXTRA_MAGIC. */ +++#define SW_EXTRA_DATAP_OFFSET 8 +++ +++/* Defines for the fpsimd that follows an SW_FPSIMD_MAGIC. */ +++#define SW_FPSIMD_FPSR_OFFSET 8 +++#define SW_FPSIMD_FPCR_OFFSET 12 +++#define SW_FPSIMD_V0_OFFSET 16 +++#define SW_FPSIMD_VREG_SIZE 16 +++ +++/* Defines for the sve structure that follows an SW_SVE_MAGIC. */ +++#define SW_SVE_CONTEXT_VL_OFFSET 8 +++#define SW_SVE_CONTEXT_REGS_OFFSET 16 +++#define SW_SVE_CONTEXT_P_REGS_OFFSET(vq) (32 * vq * 16) +++#define SW_SVE_CONTEXT_FFR_OFFSET(vq) \ +++ (SW_SVE_CONTEXT_P_REGS_OFFSET (vq) + (16 * vq * 2)) +++#define SW_SVE_CONTEXT_SIZE(vq) \ +++ (SW_SVE_CONTEXT_FFR_OFFSET (vq) + (vq * 2)) +++ +++ +++/* Read an sw_64_ctx, returning the magic value, and setting *SIZE to the +++ size, or return 0 on error. */ +++ +++static uint32_t +++read_sw_64_ctx (CORE_ADDR ctx_addr, enum bfd_endian byte_order, +++ uint32_t *size) +++{ +++ uint32_t magic = 0; +++ gdb_byte buf[4]; +++ +++ if (target_read_memory (ctx_addr, buf, 4) != 0) +++ return 0; +++ magic = extract_unsigned_integer (buf, 4, byte_order); +++ +++ if (target_read_memory (ctx_addr + 4, buf, 4) != 0) +++ return 0; +++ *size = extract_unsigned_integer (buf, 4, byte_order); +++ +++ return magic; +++} +++ +++/* Implement the "init" method of struct tramp_frame. */ +++ +++/*static void +++sw_64_linux_sigframe_init (const struct tramp_frame *self, +++ struct frame_info *this_frame, +++ struct trad_frame_cache *this_cache, +++ CORE_ADDR func) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (this_frame); +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ CORE_ADDR sp = get_frame_register_unsigned (this_frame, SW_SP_REGNUM); +++ CORE_ADDR sigcontext_addr = (sp + SW_RT_SIGFRAME_UCONTEXT_OFFSET +++ + SW_UCONTEXT_SIGCONTEXT_OFFSET ); +++ CORE_ADDR section = sigcontext_addr + SW_SIGCONTEXT_RESERVED_OFFSET; +++ CORE_ADDR section_end = section + SW_SIGCONTEXT_RESERVED_SIZE; +++ CORE_ADDR fpsimd = 0; +++ CORE_ADDR sve_regs = 0; +++ uint32_t size, magic; +++ bool extra_found = false; +++ int num_regs = gdbarch_num_regs (gdbarch); +++ +++ // Read in the integer registers. +++ +++ for (int i = 0; i < 31; i++) +++ { +++ trad_frame_set_reg_addr (this_cache, +++ SW_A0_REGNUM + i, +++ sigcontext_addr + SW_SIGCONTEXT_XO_OFFSET +++ + i * SW_SIGCONTEXT_REG_SIZE); +++ } +++ trad_frame_set_reg_addr (this_cache, SW_SP_REGNUM, +++ sigcontext_addr + SW_SIGCONTEXT_XO_OFFSET +++ + 31 * SW_SIGCONTEXT_REG_SIZE); +++ trad_frame_set_reg_addr (this_cache, SW_PC_REGNUM, +++ sigcontext_addr + SW_SIGCONTEXT_XO_OFFSET +++ + 32 * SW_SIGCONTEXT_REG_SIZE); +++ +++ // Search for the FP and SVE sections, stopping at null. +++ while ((magic = read_sw_64_ctx (section, byte_order, &size)) != 0 +++ && size != 0) +++ { +++ switch (magic) +++ { +++ case SW_FPSIMD_MAGIC: +++ fpsimd = section; +++ section += size; +++ break; +++ +++ case SW_SVE_MAGIC: +++ { +++ // Check if the section is followed by a full SVE dump, and set +++ // sve_regs if it is. +++ gdb_byte buf[4]; +++ uint16_t vq; +++ +++ if (!tdep->has_sve ()) +++ break; +++ +++ if (target_read_memory (section + SW_SVE_CONTEXT_VL_OFFSET, +++ buf, 2) != 0) +++ { +++ section += size; +++ break; +++ } +++ vq = sve_vq_from_vl (extract_unsigned_integer (buf, 2, byte_order)); +++ +++ if (vq != tdep->vq) +++ error (_("Invalid vector length in signal frame %d vs %s."), vq, +++ pulongest (tdep->vq)); +++ +++ if (size >= SW_SVE_CONTEXT_SIZE (vq)) +++ sve_regs = section + SW_SVE_CONTEXT_REGS_OFFSET; +++ +++ section += size; +++ break; +++ } +++ +++ case SW_EXTRA_MAGIC: +++ { +++ // Extra is always the last valid section in reserved and points to +++ // an additional block of memory filled with more sections. Reset +++ // the address to the extra section and continue looking for more +++ // structures. +++ gdb_byte buf[8]; +++ +++ if (target_read_memory (section + SW_EXTRA_DATAP_OFFSET, +++ buf, 8) != 0) +++ { +++ section += size; +++ break; +++ } +++ +++ section = extract_unsigned_integer (buf, 8, byte_order); +++ extra_found = true; +++ break; +++ } +++ +++ default: +++ section += size; +++ break; +++ } +++ +++ // Prevent searching past the end of the reserved section. The extra +++ section does not have a hard coded limit - we have to rely on it ending +++ with nulls. +++ if (!extra_found && section > section_end) +++ break; +++ } +++ +++ if (sve_regs != 0) +++ { +++ CORE_ADDR offset; +++ +++ for (int i = 0; i < 32; i++) +++ { +++ offset = sve_regs + (i * tdep->vq * 16); +++ trad_frame_set_reg_addr (this_cache, SW_SVE_Z0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_SVE_V0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, num_regs + SW_Q0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, num_regs + SW_D0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, num_regs + SW_S0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, num_regs + SW_H0_REGNUM + i, +++ offset); +++ trad_frame_set_reg_addr (this_cache, num_regs + SW_B0_REGNUM + i, +++ offset); +++ } +++ +++ offset = sve_regs + SW_SVE_CONTEXT_P_REGS_OFFSET (tdep->vq); +++ for (int i = 0; i < 16; i++) +++ trad_frame_set_reg_addr (this_cache, SW_SVE_P0_REGNUM + i, +++ offset + (i * tdep->vq * 2)); +++ +++ offset = sve_regs + SW_SVE_CONTEXT_FFR_OFFSET (tdep->vq); +++ trad_frame_set_reg_addr (this_cache, SW_SVE_FFR_REGNUM, offset); +++ } +++ +++ if (fpsimd != 0) +++ { +++ trad_frame_set_reg_addr (this_cache, SW_FPSR_REGNUM, +++ fpsimd + SW_FPSIMD_FPSR_OFFSET); +++ trad_frame_set_reg_addr (this_cache, SW_FPCR_REGNUM, +++ fpsimd + SW_FPSIMD_FPCR_OFFSET); +++ +++ // If there was no SVE section then set up the V registers. +++ if (sve_regs == 0) +++ for (int i = 0; i < 32; i++) +++ { +++ CORE_ADDR offset = (fpsimd + SW_FPSIMD_V0_OFFSET +++ + (i * SW_FPSIMD_VREG_SIZE)); +++ +++ trad_frame_set_reg_addr (this_cache, SW_V0_REGNUM + i, offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_Q0_REGNUM + i, offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_D0_REGNUM + i, offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_S0_REGNUM + i, offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_H0_REGNUM + i, offset); +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_B0_REGNUM + i, offset); +++ if (tdep->has_sve ()) +++ trad_frame_set_reg_addr (this_cache, +++ num_regs + SW_SVE_V0_REGNUM + i, +++ offset); +++ } +++ } +++ +++ trad_frame_set_id (this_cache, frame_id_build (sp, func)); +++} */ +++//rewrite +++/*static const struct tramp_frame sw_64_linux_rt_sigframe = +++{ +++ SIGTRAMP_FRAME, +++ 4, +++ { +++ // / movz x8, 0x8b (S=1,o=10,h=0,i=0x8b,r=8) +++ Soo1 0010 1hhi iiii iiii iiii iiir rrrr +++ {0xd2801168, ULONGEST_MAX}, +++ +++ svc 0x0 (o=0, l=1) +++ // 1101 0100 oooi iiii iiii iiii iii0 00ll +++ {0xd4000001, ULONGEST_MAX}, +++ {TRAMP_SENTINEL_INSN, ULONGEST_MAX} +++ }, +++ sw_64_linux_sigframe_init +++}; +++ +++ Register maps. +++ +++sve_vq_from_vl (vl); +++ +++ if (vq > SW_MAX_SVE_VQ) +++ { +++ warning (_("SVE Vector length in core file not supported by this version" +++ " of GDB. (VQ=%s)"), pulongest (vq)); +++ return 0; +++ } +++ else if (vq == 0) +++ { +++ warning (_("SVE Vector length in core file is invalid. (VQ=%s"), +++ pulongest (vq)); +++ return 0; +++ } +++ +++ return vq; +++}*/ +++ +++/* Supply register REGNUM from BUF to REGCACHE, using the register map +++ in REGSET. If REGNUM is -1, do this for all registers in REGSET. +++ If BUF is NULL, set the registers to "unavailable" status. */ +++ +++ +++/* Collect register REGNUM from REGCACHE to BUF, using the register +++ map in REGSET. If REGNUM is -1, do this for all registers in +++ REGSET. */ +++ +++ +++ +++/* Implement the "core_read_description" gdbarch method. */ +++ +++/*static const struct target_desc * +++sw_64_linux_core_read_description (struct gdbarch *gdbarch, +++ struct target_ops *target, bfd *abfd) +++{ +++ CORE_ADDR hwcap = linux_get_hwcap (target); +++ +++ return sw_64_read_description (sw_64_linux_core_read_vq (gdbarch, abfd), +++ hwcap & SW_64_HWCAP_PACA); +++}*/ +++ +++ +++ +++/* This routine is used to parse a special token in AArch64's assembly. +++ +++ The special tokens parsed by it are: +++ +++ - Register displacement (e.g, [fp, #-8]) +++ +++ It returns one if the special token has been parsed successfully, +++ or zero if the current token is not considered special. */ +++ +++/*static int +++sw_64_stap_parse_special_token (struct gdbarch *gdbarch, +++ struct stap_parse_info *p) +++{ +++ if (*p->arg == '[') +++ { +++ // / Temporary holder for lookahead. / +++ const char *tmp = p->arg; +++ char *endp; +++ // Used to save the register name. / +++ const char *start; +++ char *regname; +++ int len; +++ int got_minus = 0; +++ long displacement; +++ struct stoken str; +++ +++ ++tmp; +++ start = tmp; +++ +++ / Register name. / +++ while (isalnum (*tmp)) +++ ++tmp; +++ +++ if (*tmp != ',') +++ return 0; +++ +++ len = tmp - start; +++ regname = (char *) alloca (len + 2); +++ +++ strncpy (regname, start, len); +++ regname[len] = '\0'; +++ +++ if (user_reg_map_name_to_regnum (gdbarch, regname, len) == -1) +++ error (_("Invalid register name `%s' on expression `%s'."), +++ regname, p->saved_arg); +++ +++ ++tmp; +++ tmp = skip_spaces (tmp); +++ /* Now we expect a number. It can begin with '#' or simply +++ a digit. / +++ if (*tmp == '#') +++ ++tmp; +++ +++ if (*tmp == '-') +++ { +++ ++tmp; +++ got_minus = 1; +++ } +++ else if (*tmp == '+') +++ ++tmp; +++ +++ if (!isdigit (*tmp)) +++ return 0; +++ +++ displacement = strtol (tmp, &endp, 10); +++ tmp = endp; +++ +++ /* Skipping last `]'. / +++ if (*tmp++ != ']') +++ return 0; +++ +++ /* The displacement. / +++ write_exp_elt_opcode (&p->pstate, OP_LONG); +++ write_exp_elt_type (&p->pstate, builtin_type (gdbarch)->builtin_long); +++ write_exp_elt_longcst (&p->pstate, displacement); +++ write_exp_elt_opcode (&p->pstate, OP_LONG); +++ if (got_minus) +++ write_exp_elt_opcode (&p->pstate, UNOP_NEG); +++ +++ /* The register name. / +++ write_exp_elt_opcode (&p->pstate, OP_REGISTER); +++ str.ptr = regname; +++ str.length = len; +++ write_exp_string (&p->pstate, str); +++ write_exp_elt_opcode (&p->pstate, OP_REGISTER); +++ +++ write_exp_elt_opcode (&p->pstate, BINOP_ADD); +++ +++ /* Casting to the expected type. / +++ write_exp_elt_opcode (&p->pstate, UNOP_CAST); +++ write_exp_elt_type (&p->pstate, lookup_pointer_type (p->arg_type)); +++ write_exp_elt_opcode (&p->pstate, UNOP_CAST); +++ +++ write_exp_elt_opcode (&p->pstate, UNOP_IND); +++ +++ p->arg = tmp; +++ } +++ else +++ return 0; +++ +++ return 1; +++}*/ +++ +++/* AArch64 process record-replay constructs: syscall, signal etc. */ +++ +++struct linux_record_tdep sw_64_linux_record_tdep; +++ +++/* Enum that defines the AArch64 linux specific syscall identifiers used for +++ process record/replay. */ +++//rewrite +++/* +++enum sw_64_syscall{ +++ +++sw_64_sys_exit =1, +++sw_64_sys_fork =2, +++sw_64_sys_read =3, +++sw_64_sys_write =4, +++sw_64_sys_close =6, +++sw_64_sys_osf_wait4 =7, +++sw_64_sys_link =9, +++sw_64_sys_unlink =10, +++sw_64_sys_chdir =12, +++sw_64_sys_fchdir =13, +++sw_64_sys_mknod =14, +++sw_64_sys_chmod =15, +++sw_64_sys_chown =16, +++sw_64_sys_brk =17, +++sw_64_sys_lseek =19, +++sw_64_sys_getxpid =20, +++sw_64_sys_osf_mount =21, +++sw_64_sys_umount2 =22, +++sw_64_sys_setuid =23, +++sw_64_sys_getxuid =24, +++sw_64_sys_ptrace =26, +++sw_64_sys_access =33, +++sw_64_sys_sync =36, +++sw_64_sys_kill =37, +++sw_64_sys_setpgid =39, +++sw_64_sys_dup =41, +++sw_64_sys_pipe =42, +++sw_64_sys_osf_set_program_attributes =43, +++sw_64_sys_open =45, +++sw_64_sys_getxgid =47, +++sw_64_sys_osf_sigprocmask =48, +++sw_64_sys_acct =51, +++sw_64_sys_sigpending =52, +++sw_64_sys_ioctl =54, +++sw_64_sys_symlink =57, +++sw_64_sys_readlink =58, +++sw_64_sys_execve =59, +++sw_64_sys_umask =60, +++sw_64_sys_chroot =61, +++sw_64_sys_getpgrp =63, +++sw_64_sys_getpagesize =64, +++sw_64_sys_vfork =66, +++sw_64_sys_stat =67, +++sw_64_sys_lstat =68, +++sw_64_sys_mmap =71, +++sw_64_sys_munmap =73, +++sw_64_sys_mprotect =74, +++sw_64_sys_madvise =75, +++sw_64_sys_vhangup =76, +++sw_64_sys_getgroups =79, +++sw_64_sys_setgroups =80, +++sw_64_sys_setpgrp =82, +++sw_64_sys_osf_setitimer =83, +++sw_64_sys_osf_getitimer =86, +++sw_64_sys_gethostname =87, +++sw_64_sys_sethostname =88, +++sw_64_sys_getdtablesize =89, +++sw_64_sys_dup2 =90, +++sw_64_sys_fstat =91, +++sw_64_sys_fcntl =92, +++sw_64_sys_osf_select =93, +++sw_64_sys_poll =94, +++sw_64_sys_fsync =95, +++sw_64_sys_setpriority =96, +++sw_64_sys_socket =97, +++sw_64_sys_connect =98, +++sw_64_sys_accept =99, +++sw_64_sys_getpriority =100, +++sw_64_sys_send =101, +++sw_64_sys_recv =102, +++sw_64_sys_sigreturn =103, +++sw_64_sys_bind =104, +++sw_64_sys_setsockopt =105, +++sw_64_sys_listen =106, +++sw_64_sys_sigsuspend =111, +++sw_64_sys_osf_sigstack =112, +++sw_64_sys_recvmsg =113, +++sw_64_sys_sendmsg =114, +++sw_64_sys_osf_gettimeofday =116, +++sw_64_sys_osf_getrusage =117, +++sw_64_sys_getsockopt =118, +++sw_64_sys_socketcall =119, +++sw_64_sys_readv =120, +++sw_64_sys_writev =121, +++sw_64_sys_osf_settimeofday =122, +++sw_64_sys_fchown =123, +++sw_64_sys_fchmod =124, +++sw_64_sys_recvfrom =125, +++sw_64_sys_setreuid =126, +++sw_64_sys_setregid =127, +++sw_64_sys_rename =128, +++sw_64_sys_truncate =129, +++sw_64_sys_ftruncate =130, +++sw_64_sys_flock =131, +++sw_64_sys_setgid =132, +++sw_64_sys_sendto =133, +++sw_64_sys_shutdown =134, +++sw_64_sys_socketpair =135, +++sw_64_sys_mkdir =136, +++sw_64_sys_rmdir =137, +++sw_64_sys_osf_utimes =138, +++sw_64_sys_getpeername =141, +++sw_64_sys_getrlimit =144, +++sw_64_sys_setrlimit =145, +++sw_64_sys_setsid =147, +++sw_64_sys_quotactl =148, +++sw_64_sys_getsockname =150, +++sw_64_sys_sigaction =156, +++sw_64_sys_osf_getdirentries =159, +++sw_64_sys_osf_statfs =160, +++sw_64_sys_osf_fstatfs =161, +++sw_64_sys_osf_getdomainname =165, +++sw_64_sys_setdomainname =166, +++sw_64_sys_bpf =170, +++sw_64_sys_userfaultfd =171, +++sw_64_sys_membarrier =172, +++sw_64_sys_mlock2 =173, +++sw_64_sys_getpid =174, +++sw_64_sys_getppid =175, +++sw_64_sys_getuid =176, +++sw_64_sys_geteuid =177, +++sw_64_sys_getgid =178, +++sw_64_sys_getegid =179, +++sw_64_sys_osf_swapon =199, +++sw_64_sys_msgctl =200, +++sw_64_sys_msgget =201, +++sw_64_sys_msgrcv =202, +++sw_64_sys_msgsnd =203, +++sw_64_sys_semctl =204, +++sw_64_sys_semget =205, +++sw_64_sys_semop =206, +++sw_64_sys_osf_utsname =207, +++sw_64_sys_lchown =208, +++sw_64_sys_shmat =209, +++sw_64_sys_shmctl =210, +++sw_64_sys_shmdt =211, +++sw_64_sys_shmget =212, +++sw_64_sys_msync =217, +++sw_64_sys_osf_stat =224, +++sw_64_sys_osf_lstat =225, +++sw_64_sys_osf_fstat =226, +++sw_64_sys_osf_statfs64 =227, +++sw_64_sys_osf_fstatfs64 =228, +++sw_64_sys_statfs64 =229, +++sw_64_sys_fstatfs64 =230, +++sw_64_sys_getpgid =233, +++sw_64_sys_getsid =234, +++sw_64_sys_sigaltstack =235, +++sw_64_sys_osf_sysinfo =241, +++sw_64_sys_osf_proplist_syscall =244, +++sw_64_sys_osf_usleep_thread =251, +++sw_64_sys_sysfs =254, +++sw_64_sys_osf_getsysinfo =256, +++sw_64_sys_osf_setsysinfo =257, +++sw_64_sys_bdflush =300, +++sw_64_sys_sethae =301, +++sw_64_sys_mount =302, +++sw_64_sys_old_adjtimex =303, +++sw_64_sys_swapoff =304, +++sw_64_sys_getdents =305, +++sw_64_sys_create_module =306, +++sw_64_sys_init_module =307, +++sw_64_sys_delete_module =308, +++sw_64_sys_get_kernel_syms =309, +++sw_64_sys_syslog =310, +++sw_64_sys_reboot =311, +++sw_64_sys_clone =312, +++sw_64_sys_uselib =313, +++sw_64_sys_mlock =314, +++sw_64_sys_munlock =315, +++sw_64_sys_mlockall =316, +++sw_64_sys_munlockall =317, +++sw_64_sys_sysinfo =318, +++sw_64_sys__sysctl =319, +++sw_64_sys_oldumount =321, +++sw_64_sys_swapon =322, +++sw_64_sys_times =323, +++sw_64_sys_personality =324, +++sw_64_sys_setfsuid =325, +++sw_64_sys_setfsgid =326, +++sw_64_sys_ustat =327, +++sw_64_sys_statfs =328, +++sw_64_sys_fstatfs =329, +++sw_64_sys_sched_setparam =330, +++sw_64_sys_sched_getparam =331, +++sw_64_sys_sched_setscheduler =332, +++sw_64_sys_sched_getscheduler =333, +++sw_64_sys_sched_yield =334, +++sw_64_sys_sched_get_priority_max =335, +++sw_64_sys_sched_get_priority_min =336, +++sw_64_sys_sched_rr_get_interval =337, +++sw_64_sys_afs_syscall =338, +++sw_64_sys_uname =339, +++sw_64_sys_nanosleep =340, +++sw_64_sys_mremap =341, +++sw_64_sys_nfsservctl =342, +++sw_64_sys_setresuid =343, +++sw_64_sys_getresuid =344, +++sw_64_sys_pciconfig_read =345, +++sw_64_sys_pciconfig_write =346, +++sw_64_sys_query_module =347, +++sw_64_sys_prctl =348, +++sw_64_sys_pread64 =349, +++sw_64_sys_pwrite64 =350, +++sw_64_sys_rt_sigreturn =351, +++sw_64_sys_rt_sigaction =352, +++sw_64_sys_rt_sigprocmask =353, +++sw_64_sys_rt_sigpending =354, +++sw_64_sys_rt_sigtimedwait =355, +++sw_64_sys_rt_sigqueueinfo =356, +++sw_64_sys_rt_sigsuspend =357, +++sw_64_sys_select =358, +++sw_64_sys_gettimeofday =359, +++sw_64_sys_settimeofday =360, +++sw_64_sys_getitimer =361, +++sw_64_sys_setitimer =362, +++sw_64_sys_utimes =363, +++sw_64_sys_getrusage =364, +++sw_64_sys_wait4 =365, +++sw_64_sys_adjtimex =366, +++sw_64_sys_getcwd =367, +++sw_64_sys_capget =368, +++sw_64_sys_capset =369, +++sw_64_sys_sendfile =370, +++sw_64_sys_setresgid =371, +++sw_64_sys_getresgid =372, +++sw_64_sys_dipc =373, +++sw_64_sys_pivot_root =374, +++sw_64_sys_mincore =375, +++sw_64_sys_pciconfig_iobase =376, +++sw_64_sys_getdents64 =377, +++sw_64_sys_gettid =378, +++sw_64_sys_readahead =379, +++sw_64_sys_tkill =381, +++sw_64_sys_setxattr =382, +++sw_64_sys_lsetxattr =383, +++sw_64_sys_fsetxattr =384, +++sw_64_sys_getxattr =385, +++sw_64_sys_lgetxattr =386, +++sw_64_sys_fgetxattr =387, +++sw_64_sys_listxattr =388, +++sw_64_sys_llistxattr =389, +++sw_64_sys_flistxattr =390, +++sw_64_sys_removexattr =391, +++sw_64_sys_lremovexattr =392, +++sw_64_sys_fremovexattr =393, +++sw_64_sys_futex =394, +++sw_64_sys_sched_setaffinity =395, +++sw_64_sys_sched_getaffinity =396, +++sw_64_sys_tuxcall =397, +++sw_64_sys_io_setup =398, +++sw_64_sys_io_destroy =399, +++sw_64_sys_io_getevents =400, +++sw_64_sys_io_submit =401, +++sw_64_sys_io_cancel =402, +++sw_64_sys_io_pgetevents =403, +++sw_64_sys_rseq =404, +++sw_64_sys_exit_group =405, +++sw_64_sys_lookup_dcookie =406, +++sw_64_sys_epoll_create =407, +++sw_64_sys_epoll_ctl =408, +++sw_64_sys_epoll_wait =409, +++sw_64_sys_remap_file_pages =410, +++sw_64_sys_set_tid_address =411, +++sw_64_sys_restart_syscall =412, +++sw_64_sys_fadvise64 =413, +++sw_64_sys_timer_create =414, +++sw_64_sys_timer_settime =415, +++sw_64_sys_timer_gettime =416, +++sw_64_sys_timer_getoverrun =417, +++sw_64_sys_timer_delete =418, +++sw_64_sys_clock_settime =419, +++sw_64_sys_clock_gettime =420, +++sw_64_sys_clock_getres =421, +++sw_64_sys_clock_nanosleep =422, +++sw_64_sys_semtimedop =423, +++sw_64_sys_tgkill =424, +++sw_64_sys_stat64 =425, +++sw_64_sys_lstat64 =426, +++sw_64_sys_fstat64 =427, +++sw_64_sys_vserver =428, +++sw_64_sys_mbind =429, +++sw_64_sys_get_mempolicy =430, +++sw_64_sys_set_mempolicy =431, +++sw_64_sys_mq_open =432, +++sw_64_sys_mq_unlink =433, +++sw_64_sys_mq_timedsend =434, +++sw_64_sys_mq_timedreceive =435, +++sw_64_sys_mq_notify =436, +++sw_64_sys_mq_getsetattr =437, +++sw_64_sys_waitid =438, +++sw_64_sys_add_key =439, +++sw_64_sys_request_key =440, +++sw_64_sys_keyctl =441, +++sw_64_sys_ioprio_set =442, +++sw_64_sys_ioprio_get =443, +++sw_64_sys_inotify_init =444, +++sw_64_sys_inotify_add_watch =445, +++sw_64_sys_inotify_rm_watch =446, +++sw_64_sys_fdatasync =447, +++sw_64_sys_kexec_load =448, +++sw_64_sys_migrate_pages =449, +++sw_64_sys_openat =450, +++sw_64_sys_mkdirat =451, +++sw_64_sys_mknodat =452, +++sw_64_sys_fchownat =453, +++sw_64_sys_futimesat =454, +++sw_64_sys_fstatat64 =455, +++sw_64_sys_unlinkat =456, +++sw_64_sys_renameat =457, +++sw_64_sys_linkat =458, +++sw_64_sys_symlinkat =459, +++sw_64_sys_readlinkat =460, +++sw_64_sys_fchmodat =461, +++sw_64_sys_faccessat =462, +++sw_64_sys_pselect6 =463, +++sw_64_sys_ppoll =464, +++sw_64_sys_unshare =465, +++sw_64_sys_set_robust_list =466, +++sw_64_sys_get_robust_list =467, +++sw_64_sys_splice =468, +++sw_64_sys_sync_file_range =469, +++sw_64_sys_tee =470, +++sw_64_sys_vmsplice =471, +++sw_64_sys_move_pages =472, +++sw_64_sys_getcpu =473, +++sw_64_sys_epoll_pwait =474, +++sw_64_sys_utimensat =475, +++sw_64_sys_signalfd =476, +++sw_64_sys_timerfd =477, +++sw_64_sys_eventfd =478, +++sw_64_sys_recvmmsg =479, +++sw_64_sys_fallocate =480, +++sw_64_sys_timerfd_create =481, +++sw_64_sys_timerfd_settime =482, +++sw_64_sys_timerfd_gettime =483, +++sw_64_sys_signalfd4 =484, +++sw_64_sys_eventfd2 =485, +++sw_64_sys_epoll_create1 =486, +++sw_64_sys_dup3 =487, +++sw_64_sys_pipe2 =488, +++sw_64_sys_inotify_init1 =489, +++sw_64_sys_preadv =490, +++sw_64_sys_pwritev =491, +++sw_64_sys_rt_tgsigqueueinfo =492, +++sw_64_sys_perf_event_open =493, +++sw_64_sys_fanotify_init =494, +++sw_64_sys_fanotify_mark =495, +++sw_64_sys_prlimit64 =496, +++sw_64_sys_name_to_handle_at =497, +++sw_64_sys_open_by_handle_at =498, +++sw_64_sys_clock_adjtime =499, +++sw_64_sys_syncfs =500, +++sw_64_sys_setns =501, +++sw_64_sys_accept4 =502, +++sw_64_sys_sendmmsg =503, +++sw_64_sys_process_vm_readv =504, +++sw_64_sys_process_vm_writev 505, +++sw_64_sys_kcmp =506, +++sw_64_sys_finit_module =507, +++sw_64_sys_sched_setattr =508, +++sw_64_sys_sched_getattr =509, +++sw_64_sys_renameat2 =510, +++sw_64_sys_getrandom =511, +++sw_64_sys_memfd_create =512, +++sw_64_sys_execveat =513, +++sw_64_sys_seccomp =514, +++sw_64_sys_copy_file_range =515, +++sw_64_sys_preadv2 =516, +++sw_64_sys_pwritev2 =517, +++sw_64_sys_statx = 518, +++};*/ +++enum sw_64_syscall{ +++ +++sw_64_sys_exit =1, +++sw_64_sys_fork =2, +++sw_64_sys_read =3, +++sw_64_sys_write =4, +++sw_64_sys_close =6, +++sw_64_sys_wait4 =7, +++sw_64_sys_link =9, +++sw_64_sys_unlink =10, +++sw_64_sys_chdir =12, +++sw_64_sys_fchdir =13, +++sw_64_sys_mknod =14, +++sw_64_sys_chmod =15, +++sw_64_sys_chown =16, +++sw_64_sys_brk =17, +++sw_64_sys_lseek =19, +++sw_64_sys_getpid =20,//getxpid +++sw_64_sys_mount =21, +++sw_64_sys_umount2 =22, +++sw_64_sys_setuid =23, +++sw_64_sys_getuid =24,//getxuid +++sw_64_sys_ptrace =26, +++sw_64_sys_access =33, +++sw_64_sys_sync =36, +++sw_64_sys_kill =37, +++sw_64_sys_setpgid =39, +++sw_64_sys_dup =41, +++sw_64_sys_pipe =42, +++sw_64_sys_set_program_attributes =43, +++sw_64_sys_open =45, +++sw_64_sys_getgid =47,//getxgid +++sw_64_sys_sigprocmask =48, +++sw_64_sys_acct =51, +++sw_64_sys_sigpending =52, +++sw_64_sys_ioctl =54, +++sw_64_sys_symlink =57, +++sw_64_sys_readlink =58, +++sw_64_sys_execve =59, +++sw_64_sys_umask =60, +++sw_64_sys_chroot =61, +++sw_64_sys_getpgrp =63, +++sw_64_sys_getpagesize =64, +++sw_64_sys_vfork =66, +++sw_64_sys_stat =67, +++sw_64_sys_lstat =68, +++sw_64_sys_mmap =71, +++sw_64_sys_munmap =73, +++sw_64_sys_mprotect =74, +++sw_64_sys_madvise =75, +++sw_64_sys_vhangup =76, +++sw_64_sys_getgroups =79, +++sw_64_sys_setgroups =80, +++sw_64_sys_setpgrp =82, +++sw_64_sys_setitimer =83, +++sw_64_sys_getitimer =86, +++sw_64_sys_gethostname =87, +++sw_64_sys_sethostname =88, +++sw_64_sys_getdtablesize =89, +++sw_64_sys_dup2 =90, +++sw_64_sys_fstat =91, +++sw_64_sys_fcntl =92, +++sw_64_sys_select =93, +++sw_64_sys_poll =94, +++sw_64_sys_fsync =95, +++sw_64_sys_setpriority =96, +++sw_64_sys_socket =97, +++sw_64_sys_connect =98, +++sw_64_sys_accept =99, +++sw_64_sys_getpriority =100, +++sw_64_sys_send =101, +++sw_64_sys_recv =102, +++sw_64_sys_sigreturn =103, +++sw_64_sys_bind =104, +++sw_64_sys_setsockopt =105, +++sw_64_sys_listen =106, +++sw_64_sys_sigsuspend =111, +++sw_64_sysi_sigstack =112, +++sw_64_sys_recvmsg =113, +++sw_64_sys_sendmsg =114, +++sw_64_sys_gettimeofday =116, +++sw_64_sys_getrusage =117, +++sw_64_sys_getsockopt =118, +++sw_64_sys_socketcall =119, +++sw_64_sys_readv =120, +++sw_64_sys_writev =121, +++sw_64_sys_settimeofday =122, +++sw_64_sys_fchown =123, +++sw_64_sys_fchmod =124, +++sw_64_sys_recvfrom =125, +++sw_64_sys_setreuid =126, +++sw_64_sys_setregid =127, +++sw_64_sys_rename =128, +++sw_64_sys_truncate =129, +++sw_64_sys_ftruncate =130, +++sw_64_sys_flock =131, +++sw_64_sys_setgid =132, +++sw_64_sys_sendto =133, +++sw_64_sys_shutdown =134, +++sw_64_sys_socketpair =135, +++sw_64_sys_mkdir =136, +++sw_64_sys_rmdir =137, +++sw_64_sys_utimes =138, +++sw_64_sys_getpeername =141, +++sw_64_sys_getrlimit =144, +++sw_64_sys_setrlimit =145, +++sw_64_sys_setsid =147, +++sw_64_sys_quotactl =148, +++sw_64_sys_getsockname =150, +++sw_64_sys_sigaction =156, +++sw_64_sys_getdirentries =159, +++sw_64_sys_statfs =160, +++sw_64_sys_fstatfs =161, +++sw_64_sys_getdomainname =165, +++sw_64_sys_setdomainname =166, +++sw_64_sys_bpf =170, +++sw_64_sys_userfaultfd =171, +++sw_64_sys_membarrier =172, +++sw_64_sys_mlock2 =173, +++//sw_64_sys_getpid =174,//REPITATION +++sw_64_sys_getppid =175, +++//sw_64_sys_getuid =176,//REPITATION +++sw_64_sys_geteuid =177, +++//sw_64_sys_getgid =178,//REPITATION +++sw_64_sys_getegid =179, +++sw_64_sys_swapon =199, +++sw_64_sys_msgctl =200, +++sw_64_sys_msgget =201, +++sw_64_sys_msgrcv =202, +++sw_64_sys_msgsnd =203, +++sw_64_sys_semctl =204, +++sw_64_sys_semget =205, +++sw_64_sys_semop =206, +++sw_64_sys_utsname =207, +++sw_64_sys_lchown =208, +++sw_64_sys_shmat =209, +++sw_64_sys_shmctl =210, +++sw_64_sys_shmdt =211, +++sw_64_sys_shmget =212, +++sw_64_sys_msync =217, +++sw_64_sysi_stat =224, +++sw_64_sys_statfs64 =227, +++sw_64_sys_fstatfs64 =230, +++sw_64_sys_getpgid =233, +++sw_64_sys_getsid =234, +++sw_64_sys_sigaltstack =235, +++//sw_64_sys_osf_sysinfo =241,// +++sw_64_sys_proplist_syscall =244, +++sw_64_sys_usleep_thread =251, +++sw_64_sys_sysfs =254, +++sw_64_sys_getsysinfo =256, +++sw_64_sys_setsysinfo =257, +++sw_64_sys_bdflush =300, +++sw_64_sys_sethae =301, +++sw_64_sys_old_adjtimex =303, +++sw_64_sys_swapoff =304, +++sw_64_sys_getdents =305, +++sw_64_sys_create_module =306, +++sw_64_sys_init_module =307, +++sw_64_sys_delete_module =308, +++sw_64_sys_get_kernel_syms =309, +++sw_64_sys_syslog =310, +++sw_64_sys_reboot =311, +++sw_64_sys_clone =312, +++sw_64_sys_uselib =313, +++sw_64_sys_mlock =314, +++sw_64_sys_munlock =315, +++sw_64_sys_mlockall =316, +++sw_64_sys_munlockall =317, +++sw_64_sys_sysinfo =318, +++sw_64_sys_sysctl =319, +++sw_64_sys_oldumount =321, +++sw_64_sys_times =323, +++sw_64_sys_personality =324, +++sw_64_sys_setfsuid =325, +++sw_64_sys_setfsgid =326, +++sw_64_sys_ustat =327, +++sw_64_sys_sched_setparam =330, +++sw_64_sys_sched_getparam =331, +++sw_64_sys_sched_setscheduler =332, +++sw_64_sys_sched_getscheduler =333, +++sw_64_sys_sched_yield =334, +++sw_64_sys_sched_get_priority_max =335, +++sw_64_sys_sched_get_priority_min =336, +++sw_64_sys_sched_rr_get_interval =337, +++sw_64_sys_afs_syscall =338, +++sw_64_sys_uname =339, +++sw_64_sys_nanosleep =340, +++sw_64_sys_mremap =341, +++sw_64_sys_nfsservctl =342, +++sw_64_sys_setresuid =343, +++sw_64_sys_getresuid =344, +++sw_64_sys_pciconfig_read =345, +++sw_64_sys_pciconfig_write =346, +++sw_64_sys_query_module =347, +++sw_64_sys_prctl =348, +++sw_64_sys_pread64 =349, +++sw_64_sys_pwrite64 =350, +++sw_64_sys_rt_sigreturn =351, +++sw_64_sys_rt_sigaction =352, +++sw_64_sys_rt_sigprocmask =353, +++sw_64_sys_rt_sigpending =354, +++sw_64_sys_rt_sigtimedwait =355, +++sw_64_sys_rt_sigqueueinfo =356, +++sw_64_sys_rt_sigsuspend =357, +++sw_64_sys_adjtimex =366, +++sw_64_sys_getcwd =367, +++sw_64_sys_capget =368, +++sw_64_sys_capset =369, +++sw_64_sys_sendfile =370, +++sw_64_sys_setresgid =371, +++sw_64_sys_getresgid =372, +++sw_64_sys_dipc =373, +++sw_64_sys_pivot_root =374, +++sw_64_sys_mincore =375, +++sw_64_sys_pciconfig_iobase =376, +++sw_64_sys_getdents64 =377, +++sw_64_sys_gettid =378, +++sw_64_sys_readahead =379, +++sw_64_sys_tkill =381, +++sw_64_sys_setxattr =382, +++sw_64_sys_lsetxattr =383, +++sw_64_sys_fsetxattr =384, +++sw_64_sys_getxattr =385, +++sw_64_sys_lgetxattr =386, +++sw_64_sys_fgetxattr =387, +++sw_64_sys_listxattr =388, +++sw_64_sys_llistxattr =389, +++sw_64_sys_flistxattr =390, +++sw_64_sys_removexattr =391, +++sw_64_sys_lremovexattr =392, +++sw_64_sys_fremovexattr =393, +++sw_64_sys_futex =394, +++sw_64_sys_sched_setaffinity =395, +++sw_64_sys_sched_getaffinity =396, +++sw_64_sys_tuxcall =397, +++sw_64_sys_io_setup =398, +++sw_64_sys_io_destroy =399, +++sw_64_sys_io_getevents =400, +++sw_64_sys_io_submit =401, +++sw_64_sys_io_cancel =402, +++sw_64_sys_io_pgetevents =403, +++sw_64_sys_rseq =404, +++sw_64_sys_exit_group =405, +++sw_64_sys_lookup_dcookie =406, +++sw_64_sys_epoll_create =407, +++sw_64_sys_epoll_ctl =408, +++sw_64_sys_epoll_wait =409, +++sw_64_sys_remap_file_pages =410, +++sw_64_sys_set_tid_address =411, +++sw_64_sys_restart_syscall =412, +++sw_64_sys_fadvise64 =413, +++sw_64_sys_timer_create =414, +++sw_64_sys_timer_settime =415, +++sw_64_sys_timer_gettime =416, +++sw_64_sys_timer_getoverrun =417, +++sw_64_sys_timer_delete =418, +++sw_64_sys_clock_settime =419, +++sw_64_sys_clock_gettime =420, +++sw_64_sys_clock_getres =421, +++sw_64_sys_clock_nanosleep =422, +++sw_64_sys_semtimedop =423, +++sw_64_sys_tgkill =424, +++sw_64_sys_stat64 =425, +++sw_64_sys_lstat64 =426, +++sw_64_sys_fstat64 =427, +++sw_64_sys_vserver =428, +++sw_64_sys_mbind =429, +++sw_64_sys_get_mempolicy =430, +++sw_64_sys_set_mempolicy =431, +++sw_64_sys_mq_open =432, +++sw_64_sys_mq_unlink =433, +++sw_64_sys_mq_timedsend =434, +++sw_64_sys_mq_timedreceive =435, +++sw_64_sys_mq_notify =436, +++sw_64_sys_mq_getsetattr =437, +++sw_64_sys_waitid =438, +++sw_64_sys_add_key =439, +++sw_64_sys_request_key =440, +++sw_64_sys_keyctl =441, +++sw_64_sys_ioprio_set =442, +++sw_64_sys_ioprio_get =443, +++sw_64_sys_inotify_init =444, +++sw_64_sys_inotify_add_watch =445, +++sw_64_sys_inotify_rm_watch =446, +++sw_64_sys_fdatasync =447, +++sw_64_sys_kexec_load =448, +++sw_64_sys_migrate_pages =449, +++sw_64_sys_openat =450, +++sw_64_sys_mkdirat =451, +++sw_64_sys_mknodat =452, +++sw_64_sys_fchownat =453, +++sw_64_sys_futimesat =454, +++sw_64_sys_fstatat64 =455, +++sw_64_sys_unlinkat =456, +++sw_64_sys_renameat =457, +++sw_64_sys_linkat =458, +++sw_64_sys_symlinkat =459, +++sw_64_sys_readlinkat =460, +++sw_64_sys_fchmodat =461, +++sw_64_sys_faccessat =462, +++sw_64_sys_pselect6 =463, +++sw_64_sys_ppoll =464, +++sw_64_sys_unshare =465, +++sw_64_sys_set_robust_list =466, +++sw_64_sys_get_robust_list =467, +++sw_64_sys_splice =468, +++sw_64_sys_sync_file_range =469, +++sw_64_sys_tee =470, +++sw_64_sys_vmsplice =471, +++sw_64_sys_move_pages =472, +++sw_64_sys_getcpu =473, +++sw_64_sys_epoll_pwait =474, +++sw_64_sys_utimensat =475, +++sw_64_sys_signalfd =476, +++sw_64_sys_timerfd =477, +++sw_64_sys_eventfd =478, +++sw_64_sys_recvmmsg =479, +++sw_64_sys_fallocate =480, +++sw_64_sys_timerfd_create =481, +++sw_64_sys_timerfd_settime =482, +++sw_64_sys_timerfd_gettime =483, +++sw_64_sys_signalfd4 =484, +++sw_64_sys_eventfd2 =485, +++sw_64_sys_epoll_create1 =486, +++sw_64_sys_dup3 =487, +++sw_64_sys_pipe2 =488, +++sw_64_sys_inotify_init1 =489, +++sw_64_sys_preadv =490, +++sw_64_sys_pwritev =491, +++sw_64_sys_rt_tgsigqueueinfo =492, +++sw_64_sys_perf_event_open =493, +++sw_64_sys_fanotify_init =494, +++sw_64_sys_fanotify_mark =495, +++sw_64_sys_prlimit64 =496, +++sw_64_sys_name_to_handle_at =497, +++sw_64_sys_open_by_handle_at =498, +++sw_64_sys_clock_adjtime =499, +++sw_64_sys_syncfs =500, +++sw_64_sys_setns =501, +++sw_64_sys_accept4 =502, +++sw_64_sys_sendmmsg =503, +++sw_64_sys_process_vm_readv =504, +++sw_64_sys_process_vm_writev= 505, +++sw_64_sys_kcmp =506, +++sw_64_sys_finit_module =507, +++sw_64_sys_sched_setattr =508, +++sw_64_sys_sched_getattr =509, +++sw_64_sys_renameat2 =510, +++sw_64_sys_getrandom =511, +++sw_64_sys_memfd_create =512, +++sw_64_sys_execveat =513, +++sw_64_sys_seccomp =514, +++sw_64_sys_copy_file_range =515, +++sw_64_sys_preadv2 =516, +++sw_64_sys_pwritev2 =517, +++sw_64_sys_statx = 518, +++}; +++/*enum sw_64_syscall{ +++ sw_64_sys_osf_syscall =0, +++ sw_64_sys_exit =1, +++ sw_64_sys_fork =2, +++ sw_64_sys_read =3, +++ sw_64_sys_write =4, +++ sw_64_sys_osf_old_open =5, +++ sw_64_sys_close =6, +++ sw_64_sys_osf_wait4 =7, +++ sw_64_sys_osf_old_creat =8, +++ sw_64_sys_link =9, +++ sw_64_sys_unlink =10, +++ sw_64_sys_osf_execve =11, +++ sw_64_sys_chdir =12, +++ sw_64_sys_fchdir =13, +++ sw_64_sys_mknod =14, +++ sw_64_sys_chmod =15, +++ sw_64_sys_chown =16, +++ sw_64_sys_brk =17, +++ sw_64_sys_osf_getfsstat =18, +++ sw_64_sys_lseek =19, +++ sw_64_sys_getxpid =20, +++ sw_64_sys_osf_mount =21, +++ sw_64_sys_umount =22, +++ sw_64_sys_setuid =23, +++ sw_64_sys_getxuid =24, +++ sw_64_sys_exec_with_loader =25, +++ sw_64_sys_ptrace =26, +++ sw_64_sys_osf_nrecvmsg =27, +++ sw_64_sys_osf_nsendmsg =28, +++ sw_64_sys_osf_nrecvfrom =29, +++ sw_64_sys_osf_naccept =30, +++ sw_64_sys_osf_ngetpeername =31, +++ sw_64_sys_osf_ngetsockname =32, +++ sw_64_sys_access =33, +++ sw_64_sys_osf_chflags =34, +++ sw_64_sys_osf_fchflags =35, +++ sw_64_sys_sync =36, +++ sw_64_sys_kill =37, +++ sw_64_sys_osf_old_stat =38, +++ sw_64_sys_setpgid =39, +++ sw_64_sys_osf_old_lstat =40, +++ sw_64_sys_dup =41, +++ sw_64_sys_pipe =42, +++ sw_64_sys_osf_set_program_attributes =43, +++ sw_64_sys_osf_profil =44, +++ sw_64_sys_open =45, +++ sw_64_sys_osf_old_sigaction =46, +++ sw_64_sys_getxgid =47, +++ sw_64_sys_osf_sigprocmask =48, +++ sw_64_sys_osf_getlogin =49, +++ sw_64_sys_osf_setlogin =50, +++ sw_64_sys_acct =51, +++ sw_64_sys_sigpending =52, +++ +++ sw_64_sys_ioctl =54, +++ sw_64_sys_osf_reboot =55, +++ sw_64_sys_osf_revoke =56, +++ sw_64_sys_symlink =57, +++ sw_64_sys_readlink =58, +++ sw_64_sys_execve =59, +++ sw_64_sys_umask =60, +++ sw_64_sys_chroot =61, +++ sw_64_sys_osf_old_fstat =62, +++ sw_64_sys_getpgrp =63, +++ sw_64_sys_getpagesize =64, +++ sw_64_sys_osf_mremap =65, +++ sw_64_sys_vfork =66, +++ sw_64_sys_stat =67, +++ sw_64_sys_lstat =68, +++ sw_64_sys_osf_sbrk =69, +++ sw_64_sys_osf_sstk =70, +++ sw_64_sys_mmap =71, +++ sw_64_sys_osf_old_vadvise =72, +++ sw_64_sys_munmap =73, +++ sw_64_sys_mprotect =74, +++ sw_64_sys_madvise =75, +++ sw_64_sys_vhangup =76, +++ sw_64_sys_osf_kmodcall =77, +++ sw_64_sys_osf_mincore =78, +++ sw_64_sys_getgroups =79, +++ sw_64_sys_setgroups =80, +++ sw_64_sys_osf_old_getpgrp =81, +++ sw_64_sys_setpgrp =82, +++ sw_64_sys_osf_setitimer =83, +++ sw_64_sys_osf_old_wait =84, +++ sw_64_sys_osf_table =85, +++ sw_64_sys_osf_getitimer =86, +++ sw_64_sys_gethostname =87, +++ sw_64_sys_sethostname =88, +++ sw_64_sys_getdtablesize =89, +++ sw_64_sys_dup2 =90, +++ sw_64_sys_fstat =91, +++ sw_64_sys_fcntl =92, +++ sw_64_sys_osf_select =93, +++ sw_64_sys_poll =94, +++ sw_64_sys_fsync =95, +++ sw_64_sys_setpriority =96, +++ sw_64_sys_socket =97, +++ sw_64_sys_connect =98, +++ sw_64_sys_accept =99, +++ sw_64_sys_getpriority =100, +++ sw_64_sys_send =101, +++ sw_64_sys_recv =102, +++ sw_64_sys_sigreturn =103, +++ sw_64_sys_bind =104, +++ sw_64_sys_setsockopt =105, +++ sw_64_sys_listen =106, +++ sw_64_sys_osf_plock =107, +++ sw_64_sys_osf_old_sigvec =108, +++ sw_64_sys_osf_old_sigblock =109, +++ sw_64_sys_osf_old_sigsetmask =110, +++ sw_64_sys_sigsuspend =111, +++ sw_64_sys_osf_sigstack =112, +++ sw_64_sys_recvmsg =113, +++ sw_64_sys_sendmsg =114, +++ sw_64_sys_osf_old_vtrace =115, +++ sw_64_sys_osf_gettimeofday =116, +++ sw_64_sys_osf_getrusage =117, +++ sw_64_sys_getsockopt =118, +++ sw_64_sys_socketcall =119, +++ sw_64_sys_readv =120, +++ sw_64_sys_writev =121, +++ sw_64_sys_osf_settimeofday =122, +++ sw_64_sys_fchown =123, +++ sw_64_sys_fchmod =124, +++ sw_64_sys_recvfrom =125, +++ sw_64_sys_setreuid =126, +++ sw_64_sys_setregid =127, +++ sw_64_sys_rename =128, +++ sw_64_sys_truncate =129, +++ sw_64_sys_ftruncate =130, +++ sw_64_sys_flock =131, +++ sw_64_sys_setgid =132, +++ sw_64_sys_sendto =133, +++ sw_64_sys_shutdown =134, +++ sw_64_sys_socketpair =135, +++ sw_64_sys_mkdir =136, +++ sw_64_sys_rmdir =137, +++ sw_64_sys_osf_utimes =138, +++ sw_64_sys_osf_old_sigreturn =139, +++ sw_64_sys_osf_adjtime =140, +++ sw_64_sys_getpeername =141, +++ sw_64_sys_osf_gethostid =142, +++ sw_64_sys_osf_sethostid =143, +++ sw_64_sys_getrlimit =144, +++ sw_64_sys_setrlimit =145, +++ sw_64_sys_osf_old_killpg =146, +++ sw_64_sys_setsid =147, +++ sw_64_sys_quotactl =148, +++ sw_64_sys_osf_oldquota =149, +++ sw_64_sys_getsockname =150, +++ +++ sw_64_sys_osf_pid_block =153, +++ sw_64_sys_osf_pid_unblock =154, +++ +++ sw_64_sys_sigaction =156, +++ sw_64_sys_osf_sigwaitprim =157, +++ sw_64_sys_osf_nfssvc =158, +++ sw_64_sys_osf_getdirentries =159, +++ sw_64_sys_osf_statfs =160, +++ sw_64_sys_osf_fstatfs =161, +++ +++ sw_64_sys_osf_asynch_daemon =163, +++ sw_64_sys_osf_getfh =164, +++ sw_64_sys_osf_getdomainname =165, +++ sw_64_sys_setdomainname =166, +++ +++ sw_64_sys_osf_exportfs =169, +++ sw_64_sys_bpf =170, +++ sw_64_sys_userfaultfd =171, +++ sw_64_sys_membarrier =172, +++ sw_64_sys_mlock2 =173, +++ sw_64_sys_getpid=174, +++ sw_64_sys_getppid=175, +++ sw_64_sys_getuid=176, +++ sw_64_sys_geteuid=177, +++ sw_64_sys_getgid=178, +++ sw_64_sys_getegid=179, +++ sw_64_sys_osf_alt_plock =181, +++ +++ sw_64_sys_osf_getmnt =184, +++ +++ sw_64_sys_osf_alt_sigpending =187, +++ sw_64_sys_osf_alt_setsid =188, +++ +++ sw_64_sys_osf_swapon =199, +++ sw_64_sys_msgctl =200, +++ sw_64_sys_msgget =201, +++ sw_64_sys_msgrcv =202, +++ sw_64_sys_msgsnd =203, +++ sw_64_sys_semctl =204, +++ sw_64_sys_semget =205, +++ sw_64_sys_semop =206, +++ sw_64_sys_osf_utsname =207, +++ sw_64_sys_lchown =208, +++ sw_64_sys_osf_shmat =209, +++ sw_64_sys_shmctl =210, +++ sw_64_sys_shmdt =211, +++ sw_64_sys_shmget =212, +++ sw_64_sys_osf_mvalid =213, +++ sw_64_sys_osf_getaddressconf =214, +++ sw_64_sys_osf_msleep =215, +++ sw_64_sys_osf_mwakeup =216, +++ sw_64_sys_msync =217, +++ sw_64_sys_osf_signal =218, +++ sw_64_sys_osf_utc_gettime =219, +++ sw_64_sys_osf_utc_adjtime =220, +++ +++ sw_64_sys_osf_security =222, +++ sw_64_sys_osf_kloadcall =223, +++ sw_64_sys_osf_stat =224, +++ sw_64_sys_osf_lstat =225, +++ sw_64_sys_osf_fstat =226, +++ sw_64_sys_osf_statfs64 =227, +++ sw_64_sys_osf_fstatfs64 =228, +++ +++ sw_64_sys_getpgid =233, +++ sw_64_sys_getsid =234, +++ sw_64_sys_sigaltstack =235, +++ sw_64_sys_osf_waitid =236, +++ sw_64_sys_osf_priocntlset =237, +++ sw_64_sys_osf_sigsendset =238, +++ sw_64_sys_osf_set_speculative =239, +++ sw_64_sys_osf_msfs_syscall =240, +++ sw_64_sys_osf_sysinfo =241, +++ sw_64_sys_osf_uadmin =242, +++ sw_64_sys_osf_fuser =243, +++ sw_64_sys_osf_proplist_syscall =244, +++ sw_64_sys_osf_ntp_adjtime =245, +++ sw_64_sys_osf_ntp_gettime =246, +++ sw_64_sys_osf_pathconf =247, +++ sw_64_sys_osf_fpathconf =248, +++ +++ sw_64_sys_osf_uswitch =250, +++ sw_64_sys_osf_usleep_thread =251, +++ sw_64_sys_osf_audcntl =252, +++ sw_64_sys_osf_audgen =253, +++ sw_64_sys_sysfs =254, +++ sw_64_sys_osf_subsys_info =255, +++ sw_64_sys_osf_getsysinfo =256, +++ sw_64_sys_osf_setsysinfo =257, +++ sw_64_sys_osf_afs_syscall =258, +++ sw_64_sys_osf_swapctl =259, +++ sw_64_sys_osf_memcntl =260, +++ sw_64_sys_osf_fdatasync =261, +++ +++ sw_64_sys_bdflush =300, +++ sw_64_sys_sethae =301, +++ sw_64_sys_mount =302, +++ sw_64_sys_old_adjtimex =303, +++ sw_64_sys_swapoff =304, +++ sw_64_sys_getdents =305, +++ sw_64_sys_create_module =306, +++ sw_64_sys_init_module =307, +++ sw_64_sys_delete_module =308, +++ sw_64_sys_get_kernel_syms =309, +++ sw_64_sys_syslog =310, +++ sw_64_sys_reboot =311, +++ sw_64_sys_clone =312, +++ sw_64_sys_uselib =313, +++ sw_64_sys_mlock =314, +++ sw_64_sys_munlock =315, +++ sw_64_sys_mlockall =316, +++ sw_64_sys_munlockall =317, +++ sw_64_sys_sysinfo =318, +++ sw_64_sys__sysctl =319, +++ +++ sw_64_sys_oldumount =321, +++ sw_64_sys_swapon =322, +++ sw_64_sys_times =323, +++ sw_64_sys_personality =324, +++ sw_64_sys_setfsuid =325, +++ sw_64_sys_setfsgid =326, +++ sw_64_sys_ustat =327, +++ sw_64_sys_statfs =328, +++ sw_64_sys_fstatfs =329, +++ sw_64_sys_sched_setparam =330, +++ sw_64_sys_sched_getparam =331, +++ sw_64_sys_sched_setscheduler =332, +++ sw_64_sys_sched_getscheduler =333, +++ sw_64_sys_sched_yield =334, +++ sw_64_sys_sched_get_priority_max =335, +++ sw_64_sys_sched_get_priority_min =336, +++ sw_64_sys_sched_rr_get_interval =337, +++ sw_64_sys_afs_syscall =338, +++ sw_64_sys_uname =339, +++ sw_64_sys_nanosleep =340, +++ sw_64_sys_mremap =341, +++ sw_64_sys_nfsservctl =342, +++ sw_64_sys_setresuid =343, +++ sw_64_sys_getresuid =344, +++ sw_64_sys_pciconfig_read =345, +++ sw_64_sys_pciconfig_write =346, +++ sw_64_sys_query_module =347, +++ sw_64_sys_prctl =348, +++ sw_64_sys_pread64 =349, +++ sw_64_sys_pwrite64 =350, +++ sw_64_sys_rt_sigreturn =351, +++ sw_64_sys_rt_sigaction =352, +++ sw_64_sys_rt_sigprocmask =353, +++ sw_64_sys_rt_sigpending =354, +++ sw_64_sys_rt_sigtimedwait =355, +++ sw_64_sys_rt_sigqueueinfo =356, +++ sw_64_sys_rt_sigsuspend =357, +++ sw_64_sys_select =358, +++ sw_64_sys_gettimeofday =359, +++ sw_64_sys_settimeofday =360, +++ sw_64_sys_getitimer =361, +++ sw_64_sys_setitimer =362, +++ sw_64_sys_utimes =363, +++ sw_64_sys_getrusage =364, +++ sw_64_sys_wait4 =365, +++ sw_64_sys_adjtimex =366, +++ sw_64_sys_getcwd =367, +++ sw_64_sys_capget =368, +++ sw_64_sys_capset =369, +++ sw_64_sys_sendfile =370, +++ sw_64_sys_setresgid =371, +++ sw_64_sys_getresgid =372, +++ sw_64_sys_dipc =373, +++ sw_64_sys_pivot_root =374, +++ sw_64_sys_mincore =375, +++ sw_64_sys_pciconfig_iobase =376, +++ sw_64_sys_getdents64 =377, +++ sw_64_sys_gettid =378, +++ sw_64_sys_readahead =379, +++ +++ sw_64_sys_tkill =381, +++ sw_64_sys_setxattr =382, +++ sw_64_sys_lsetxattr =383, +++ sw_64_sys_fsetxattr =384, +++ sw_64_sys_getxattr =385, +++ sw_64_sys_lgetxattr =386, +++ sw_64_sys_fgetxattr =387, +++ sw_64_sys_listxattr =388, +++ sw_64_sys_llistxattr =389, +++ sw_64_sys_flistxattr =390, +++ sw_64_sys_removexattr =391, +++ sw_64_sys_lremovexattr =392, +++ sw_64_sys_fremovexattr =393, +++ sw_64_sys_futex =394, +++ sw_64_sys_sched_setaffinity =395, +++ sw_64_sys_sched_getaffinity =396, +++ sw_64_sys_tuxcall =397, +++ sw_64_sys_io_setup =398, +++ sw_64_sys_io_destroy =399, +++ sw_64_sys_io_getevents =400, +++ +++ sw_64_sys_io_submit =401, +++ sw_64_sys_io_cancel =402, +++ +++ sw_64_sys_exit_group =405, +++ sw_64_sys_lookup_dcookie =406, +++ sw_64_sys_epoll_create =407, +++ sw_64_sys_epoll_ctl =408, +++ sw_64_sys_epoll_wait =409, +++ +++ sw_64_sys_remap_file_pages =410, +++ sw_64_sys_set_tid_address =411, +++ sw_64_sys_restart_syscall =412, +++ sw_64_sys_fadvise64 =413, +++ sw_64_sys_timer_create =414, +++ sw_64_sys_timer_settime =415, +++ sw_64_sys_timer_gettime =416, +++ sw_64_sys_timer_getoverrun =417, +++ sw_64_sys_timer_delete =418, +++ sw_64_sys_clock_settime =419, +++ sw_64_sys_clock_gettime =420, +++ sw_64_sys_clock_getres =421, +++ sw_64_sys_clock_nanosleep =422, +++ sw_64_sys_semtimedop =423, +++ sw_64_sys_tgkill =424, +++ sw_64_sys_stat64 =425, +++ sw_64_sys_lstat64 =426, +++ sw_64_sys_fstat64 =427, +++ sw_64_sys_vserver =428, +++ sw_64_sys_mbind =429, +++ sw_64_sys_get_mempolicy =430, +++ sw_64_sys_set_mempolicy =431, +++ sw_64_sys_mq_open =432, +++ sw_64_sys_mq_unlink =433, +++ sw_64_sys_mq_timedsend =434, +++ sw_64_sys_mq_timedreceive =435, +++ sw_64_sys_mq_notify =436, +++ sw_64_sys_mq_getsetattr =437, +++ sw_64_sys_waitid =438, +++ sw_64_sys_add_key =439, +++ sw_64_sys_request_key =440, +++ sw_64_sys_keyctl =441, +++ sw_64_sys_ioprio_set =442, +++ sw_64_sys_ioprio_get =443, +++ sw_64_sys_inotify_init =444, +++ sw_64_sys_inotify_add_watch =445, +++ sw_64_sys_inotify_rm_watch =446, +++ sw_64_sys_fdatasync =447, +++ sw_64_sys_kexec_load =448, +++ sw_64_sys_migrate_pages =449, +++ sw_64_sys_openat =450, +++ sw_64_sys_mkdirat =451, +++ sw_64_sys_mknodat =452, +++ sw_64_sys_fchownat =453, +++ sw_64_sys_futimesat =454, +++ sw_64_sys_fstatat64 =455, +++ sw_64_sys_unlinkat =456, +++ sw_64_sys_renameat =457, +++ sw_64_sys_linkat =458, +++ sw_64_sys_symlinkat =459, +++ sw_64_sys_readlinkat =460, +++ sw_64_sys_fchmodat =461, +++ sw_64_sys_faccessat =462, +++ sw_64_sys_pselect6 =463, +++ sw_64_sys_ppoll =464, +++ sw_64_sys_unshare =465, +++ sw_64_sys_set_robust_list =466, +++ sw_64_sys_get_robust_list =467, +++ sw_64_sys_splice =468, +++ sw_64_sys_sync_file_range =469, +++ sw_64_sys_tee =470, +++ sw_64_sys_vmsplice =471, +++ sw_64_sys_move_pages =472, +++ sw_64_sys_getcpu =473, +++ sw_64_sys_epoll_pwait =474, +++ //sw_64_sys_utimensat =475, +++ //sw_64_sys_signalfd =476, +++ //sw_64_sys_timerfd =477, +++ sw_64_sys_eventfd =478, +++ sw_64_sys_recvmmsg =479,// +++ sw_64_sys_fallocate =480, +++ sw_64_sys_timerfd_create =481, +++ sw_64_sys_timerfd_settime =482, +++ sw_64_sys_timerfd_gettime =483, +++ sw_64_sys_signalfd4 =484, +++ sw_64_sys_eventfd2 =485, +++ sw_64_sys_epoll_create1 =486, +++ sw_64_sys_dup3 =487, +++ sw_64_sys_pipe2 =488, +++ sw_64_sys_inotify_init1 =489, +++ sw_64_sys_preadv =490,// +++ //sw_64_sys_pwritev =491, +++ sw_64_sys_rt_tgsigqueueinfo =492,//unsupport +++ sw_64_sys_perf_event_open =493,//unsupport +++ sw_64_sys_fanotify_init =494,// +++ sw_64_sys_fanotify_mark =495,// +++ sw_64_sys_prlimit64 =496,/// +++ sw_64_sys_name_to_handle_at =497,// +++ sw_64_sys_open_by_handle_at =498,// +++ sw_64_sys_clock_adjtime =499,// +++ sw_64_sys_syncfs =500,// +++ sw_64_sys_setns =501,// +++ sw_64_sys_accept4 =502,//unsupport +++ sw_64_sys_sendmmsg =503,// +++ sw_64_sys_process_vm_readv =504,// +++ sw_64_sys_process_vm_writev =505,// +++ sw_64_sys_kcmp =506,// +++ sw_64_sys_finit_module =507,// +++ sw_64_sys_sched_setattr =508,// +++ sw_64_sys_sched_getattr =509,// +++ //sw_64_sys_renameat2 =510, +++ //sw_64_sys_getrandom =511, +++ //sw_64_sys_memfd_create =512, +++ //sw_64_sys_execveat =513, +++ //sw_64_sys_seccomp =514, +++ //sw_64_sys_copy_file_range =515, +++ //sw_64_sys_preadv2 =516, +++ //sw_64_sys_pwritev2 =517, +++ //sw_64_sys_statx =518, +++ +++};*/ +++ +++/* sw_64_canonicalize_syscall maps syscall ids from the native AArch64 +++ linux set of syscall ids into a canonical set of syscall ids used by +++ process record. */ +++ +++static enum gdb_syscall +++sw_64_canonicalize_syscall (enum sw_64_syscall syscall_number) +++{ +++#define SYSCALL_MAP(SYSCALL) case sw_64_sys_##SYSCALL: \ +++ return gdb_sys_##SYSCALL +++ +++#define UNSUPPORTED_SYSCALL_MAP(SYSCALL) case sw_64_sys_##SYSCALL: \ +++ return gdb_sys_no_syscall +++ +++ switch (syscall_number) +++ { +++ //sw syscall +++ //UNSUPPORTED_SYSCALL_MAP(SYSCALL) (execveat); +++ //UNSUPPORTED_SYSCALL_MAP (userfaultfd); +++ //UNSUPPORTED_SYSCALL_MAP (mlock2); +++ //UNSUPPORTED_SYSCALL_MAP (copy_file_range); +++ //UNSUPPORTED_SYSCALL_MAP (preadv2); +++ //UNSUPPORTED_SYSCALL_MAP (pwritev2); +++ //UNSUPPORTED_SYSCALL_MAP (renameat2); +++ //UNSUPPORTED_SYSCALL_MAP (seccomp); +++ //UNSUPPORTED_SYSCALL_MAP (getrandom); +++ //UNSUPPORTED_SYSCALL_MAP (memfd_create); +++ //UNSUPPORTED_SYSCALL_MAP (bpf); +++ //UNSUPPORTED_SYSCALL_MAP(syscalls); +++ // arm syscall +++ SYSCALL_MAP (fstatat64); +++ SYSCALL_MAP (io_setup); +++ SYSCALL_MAP (io_destroy); +++ SYSCALL_MAP (io_submit); +++ SYSCALL_MAP (io_cancel); +++ SYSCALL_MAP (io_getevents); +++ +++ SYSCALL_MAP (setxattr); +++ SYSCALL_MAP (lsetxattr); +++ SYSCALL_MAP (fsetxattr); +++ SYSCALL_MAP (getxattr); +++ SYSCALL_MAP (lgetxattr); +++ SYSCALL_MAP (fgetxattr); +++ SYSCALL_MAP (listxattr); +++ SYSCALL_MAP (llistxattr); +++ SYSCALL_MAP (flistxattr); +++ SYSCALL_MAP (removexattr); +++ SYSCALL_MAP (lremovexattr); +++ SYSCALL_MAP (fremovexattr); +++ SYSCALL_MAP (getcwd); +++ SYSCALL_MAP (lookup_dcookie); +++ SYSCALL_MAP (eventfd2); +++ SYSCALL_MAP (epoll_create1); +++ SYSCALL_MAP (epoll_ctl); +++ SYSCALL_MAP (epoll_pwait); +++ SYSCALL_MAP (dup); +++ SYSCALL_MAP (dup3); +++ SYSCALL_MAP (fcntl); +++ SYSCALL_MAP (inotify_init1); +++ SYSCALL_MAP (inotify_add_watch); +++ SYSCALL_MAP (inotify_rm_watch); +++ SYSCALL_MAP (ioctl); +++ SYSCALL_MAP (ioprio_set); +++ SYSCALL_MAP (ioprio_get); +++ SYSCALL_MAP (flock); +++ SYSCALL_MAP (mknodat); +++ SYSCALL_MAP (mkdirat); +++ SYSCALL_MAP (unlinkat); +++ SYSCALL_MAP (symlinkat); +++ SYSCALL_MAP (linkat); +++ SYSCALL_MAP (renameat); +++ UNSUPPORTED_SYSCALL_MAP (umount2); +++ SYSCALL_MAP (mount); +++ SYSCALL_MAP (pivot_root); +++ SYSCALL_MAP (nfsservctl); +++ SYSCALL_MAP (statfs); +++ SYSCALL_MAP (truncate); +++ SYSCALL_MAP (ftruncate); +++ SYSCALL_MAP (fallocate); +++ SYSCALL_MAP (faccessat); +++ SYSCALL_MAP (fchdir); +++ SYSCALL_MAP (chroot); +++ SYSCALL_MAP (fchmod); +++ SYSCALL_MAP (fchmodat); +++ SYSCALL_MAP (fchownat); +++ SYSCALL_MAP (fchown); +++ SYSCALL_MAP (openat); +++ SYSCALL_MAP (close); +++ SYSCALL_MAP (vhangup); +++ SYSCALL_MAP (pipe); +++ SYSCALL_MAP (pipe2); +++ SYSCALL_MAP (quotactl); +++ SYSCALL_MAP (getdents64); +++ SYSCALL_MAP (lseek); +++ SYSCALL_MAP (read); +++ SYSCALL_MAP (write); +++ SYSCALL_MAP (readv); +++ SYSCALL_MAP (writev); +++ SYSCALL_MAP (pread64); +++ SYSCALL_MAP (pwrite64); +++ UNSUPPORTED_SYSCALL_MAP (preadv); +++ UNSUPPORTED_SYSCALL_MAP (pwritev); +++ SYSCALL_MAP (sendfile); +++ SYSCALL_MAP (pselect6); +++ SYSCALL_MAP (ppoll); +++ UNSUPPORTED_SYSCALL_MAP (signalfd4); +++ SYSCALL_MAP (vmsplice); +++ SYSCALL_MAP (splice); +++ SYSCALL_MAP (tee); +++ SYSCALL_MAP (readlinkat); +++ //SYSCALL_MAP (newfstatat); +++ +++ SYSCALL_MAP (fstat); +++ SYSCALL_MAP (sync); +++ SYSCALL_MAP (fsync); +++ SYSCALL_MAP (fdatasync); +++ SYSCALL_MAP (sync_file_range); +++ UNSUPPORTED_SYSCALL_MAP (timerfd_create); +++ UNSUPPORTED_SYSCALL_MAP (timerfd_settime); +++ UNSUPPORTED_SYSCALL_MAP (timerfd_gettime); +++ UNSUPPORTED_SYSCALL_MAP (utimensat); +++ SYSCALL_MAP (acct); +++ SYSCALL_MAP (capget); +++ SYSCALL_MAP (capset); +++ SYSCALL_MAP (personality); +++ SYSCALL_MAP (exit); +++ SYSCALL_MAP (exit_group); +++ SYSCALL_MAP (waitid); +++ SYSCALL_MAP (set_tid_address); +++ SYSCALL_MAP (unshare); +++ SYSCALL_MAP (futex); +++ SYSCALL_MAP (set_robust_list); +++ SYSCALL_MAP (get_robust_list); +++ SYSCALL_MAP (nanosleep); +++ +++ SYSCALL_MAP (getitimer); +++ SYSCALL_MAP (setitimer); +++ SYSCALL_MAP (kexec_load); +++ SYSCALL_MAP (init_module); +++ SYSCALL_MAP (delete_module); +++ SYSCALL_MAP (timer_create); +++ SYSCALL_MAP (timer_settime); +++ SYSCALL_MAP (timer_gettime); +++ SYSCALL_MAP (timer_getoverrun); +++ SYSCALL_MAP (timer_delete); +++ SYSCALL_MAP (clock_settime); +++ SYSCALL_MAP (clock_gettime); +++ SYSCALL_MAP (clock_getres); +++ SYSCALL_MAP (clock_nanosleep); +++ SYSCALL_MAP (syslog); +++ SYSCALL_MAP (ptrace); +++ SYSCALL_MAP (sched_setparam); +++ SYSCALL_MAP (sched_setscheduler); +++ SYSCALL_MAP (sched_getscheduler); +++ SYSCALL_MAP (sched_getparam); +++ SYSCALL_MAP (sched_setaffinity); +++ SYSCALL_MAP (sched_getaffinity); +++ SYSCALL_MAP (sched_yield); +++ SYSCALL_MAP (sched_get_priority_max); +++ SYSCALL_MAP (sched_get_priority_min); +++ SYSCALL_MAP (sched_rr_get_interval); +++ SYSCALL_MAP (kill); +++ SYSCALL_MAP (tkill); +++ SYSCALL_MAP (tgkill); +++ SYSCALL_MAP (sigaltstack); +++ SYSCALL_MAP (rt_sigsuspend); +++ SYSCALL_MAP (rt_sigaction); +++ SYSCALL_MAP (sigprocmask); +++ SYSCALL_MAP (rt_sigprocmask); +++ SYSCALL_MAP (rt_sigpending); +++ SYSCALL_MAP (rt_sigtimedwait); +++ SYSCALL_MAP (rt_sigqueueinfo); +++ SYSCALL_MAP (sigreturn); +++ SYSCALL_MAP (rt_sigreturn); +++ SYSCALL_MAP (setpriority); +++ SYSCALL_MAP (getpriority); +++ SYSCALL_MAP (reboot); +++ SYSCALL_MAP (setregid); +++ SYSCALL_MAP (setgid); +++ SYSCALL_MAP (setreuid); +++ SYSCALL_MAP (setuid); +++ SYSCALL_MAP (setresuid); +++ SYSCALL_MAP (getresuid); +++ SYSCALL_MAP (setresgid); +++ SYSCALL_MAP (getresgid); +++ SYSCALL_MAP (setfsuid); +++ SYSCALL_MAP (setfsgid); +++ SYSCALL_MAP (times); +++ SYSCALL_MAP (setpgid); +++ SYSCALL_MAP (getpgid); +++ SYSCALL_MAP (getsid); +++ SYSCALL_MAP (setsid); +++ SYSCALL_MAP (getgroups); +++ SYSCALL_MAP (setgroups); +++ SYSCALL_MAP (uname); +++ SYSCALL_MAP (sethostname); +++ SYSCALL_MAP (setdomainname); +++ SYSCALL_MAP (getrlimit); +++ SYSCALL_MAP (setrlimit); +++ SYSCALL_MAP (getrusage); +++ SYSCALL_MAP (umask); +++ SYSCALL_MAP (prctl); +++ SYSCALL_MAP (getcpu); +++ SYSCALL_MAP (gettimeofday); +++ SYSCALL_MAP (settimeofday); +++ SYSCALL_MAP (adjtimex); +++ SYSCALL_MAP (getpid); +++ SYSCALL_MAP (getppid); +++ SYSCALL_MAP (getuid); +++ SYSCALL_MAP (geteuid); +++ SYSCALL_MAP (getgid); +++ SYSCALL_MAP (getegid); +++ SYSCALL_MAP (gettid); +++ SYSCALL_MAP (sysinfo); +++ SYSCALL_MAP (mq_open); +++ SYSCALL_MAP (mq_unlink); +++ SYSCALL_MAP (mq_timedsend); +++ SYSCALL_MAP (mq_timedreceive); +++ SYSCALL_MAP (mq_notify); +++ SYSCALL_MAP (mq_getsetattr); +++ SYSCALL_MAP (msgget); +++ SYSCALL_MAP (msgctl); +++ SYSCALL_MAP (msgrcv); +++ SYSCALL_MAP (msgsnd); +++ SYSCALL_MAP (semget); +++ SYSCALL_MAP (semctl); +++ SYSCALL_MAP (semtimedop); +++ SYSCALL_MAP (semop); +++ SYSCALL_MAP (shmget); +++ SYSCALL_MAP (shmctl); +++ SYSCALL_MAP (shmat); +++ SYSCALL_MAP (shmdt); +++ SYSCALL_MAP (socket); +++ SYSCALL_MAP (socketpair); +++ SYSCALL_MAP (bind); +++ SYSCALL_MAP (listen); +++ SYSCALL_MAP (accept); +++ SYSCALL_MAP (connect); +++ SYSCALL_MAP (getsockname); +++ SYSCALL_MAP (getpeername); +++ SYSCALL_MAP (sendto); +++ SYSCALL_MAP (recvfrom); +++ SYSCALL_MAP (setsockopt); +++ SYSCALL_MAP (getsockopt); +++ SYSCALL_MAP (shutdown); +++ SYSCALL_MAP (sendmsg); +++ SYSCALL_MAP (recvmsg); +++ SYSCALL_MAP (readahead); +++ SYSCALL_MAP (brk); +++ SYSCALL_MAP (munmap); +++ SYSCALL_MAP (mremap); +++ SYSCALL_MAP (add_key); +++ SYSCALL_MAP (request_key); +++ SYSCALL_MAP (keyctl); +++ SYSCALL_MAP (clone); +++ SYSCALL_MAP (execve); +++ +++ case sw_64_sys_mmap: +++ return gdb_sys_mmap2; +++ +++ SYSCALL_MAP (fadvise64); +++ SYSCALL_MAP (swapon); +++ SYSCALL_MAP (swapoff); +++ SYSCALL_MAP (mprotect); +++ SYSCALL_MAP (msync); +++ SYSCALL_MAP (mlock); +++ SYSCALL_MAP (munlock); +++ SYSCALL_MAP (mlockall); +++ SYSCALL_MAP (munlockall); +++ SYSCALL_MAP (mincore); +++ SYSCALL_MAP (madvise); +++ SYSCALL_MAP (remap_file_pages); +++ SYSCALL_MAP (mbind); +++ SYSCALL_MAP (get_mempolicy); +++ SYSCALL_MAP (set_mempolicy); +++ SYSCALL_MAP (migrate_pages); +++ SYSCALL_MAP (move_pages); +++ UNSUPPORTED_SYSCALL_MAP (rt_tgsigqueueinfo); +++ UNSUPPORTED_SYSCALL_MAP (perf_event_open); +++ UNSUPPORTED_SYSCALL_MAP (accept4); +++ UNSUPPORTED_SYSCALL_MAP (recvmmsg); +++ +++ SYSCALL_MAP (wait4); +++ +++ UNSUPPORTED_SYSCALL_MAP (prlimit64); +++ UNSUPPORTED_SYSCALL_MAP (fanotify_init); +++ UNSUPPORTED_SYSCALL_MAP (fanotify_mark); +++ UNSUPPORTED_SYSCALL_MAP (name_to_handle_at); +++ UNSUPPORTED_SYSCALL_MAP (open_by_handle_at); +++ UNSUPPORTED_SYSCALL_MAP (clock_adjtime); +++ UNSUPPORTED_SYSCALL_MAP (syncfs); +++ UNSUPPORTED_SYSCALL_MAP (setns); +++ UNSUPPORTED_SYSCALL_MAP (sendmmsg); +++ UNSUPPORTED_SYSCALL_MAP (process_vm_readv); +++ UNSUPPORTED_SYSCALL_MAP (process_vm_writev); +++ UNSUPPORTED_SYSCALL_MAP (kcmp); +++ UNSUPPORTED_SYSCALL_MAP (finit_module); +++ UNSUPPORTED_SYSCALL_MAP (sched_setattr); +++ UNSUPPORTED_SYSCALL_MAP (sched_getattr); +++ default: +++ return gdb_sys_no_syscall; +++ } +++} +++ +++/* Record all registers but PC register for process-record. */ +++ +++static int +++sw_64_all_but_pc_registers_record (struct regcache *regcache) +++{ +++ int i; +++ +++ for (i = SW_A0_REGNUM; i < SW_PC_REGNUM; i++) +++ if (record_full_arch_list_add_reg (regcache, i)) +++ return -1; +++ +++ if (record_full_arch_list_add_reg (regcache, SW_CSR_REGNUM)) +++ return -1; +++ +++ return 0; +++} +++ +++/* Handler for sw_64 system call instruction recording. */ +++ +++static int +++sw_64_linux_syscall_record (struct regcache *regcache) +++{ +++ int ret = 0; +++ enum gdb_syscall syscall_gdb; +++ ULONGEST svc_number; +++ regcache_raw_read_unsigned (regcache, SW_V0_REGNUM, &svc_number);//_ASM_ get regbuf +++ syscall_gdb = +++ sw_64_canonicalize_syscall ((enum sw_64_syscall) svc_number); +++ +++ if (syscall_gdb < 0) +++ { +++ printf_unfiltered (_("Process record and replay target doesn't " +++ "support syscall number %s\n"), +++ plongest (svc_number)); +++ return -1; +++ } +++ +++ if (syscall_gdb == gdb_sys_sigreturn +++ || syscall_gdb == gdb_sys_rt_sigreturn) +++ { +++ if (sw_64_all_but_pc_registers_record (regcache)) +++ return -1; +++ return 0; +++ } +++ +++ ret = record_linux_system_call (syscall_gdb, regcache, &sw_64_linux_record_tdep); +++ +++ if (ret != 0) +++ return ret; +++ +++ /* Record the return value of the system call. */ +++ if (record_full_arch_list_add_reg (regcache, SW_V0_REGNUM)) +++ return -1; +++ +++ return 0; +++} +++ +++/* Implement the "gcc_target_options" gdbarch method. */ +++ +++static std::string +++sw_64_linux_gcc_target_options (struct gdbarch *gdbarch) +++{ +++ /* GCC doesn't know "-m64". */ +++ return {}; +++} +++ +++static void +++sw_64_linux_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ +++ static const char *const stap_integer_prefixes[] = { "i", NULL }; +++ static const char *const stap_register_indirection_prefixes[] = { "(", +++ NULL }; +++ static const char *const stap_register_indirection_suffixes[] = { ")", +++ NULL }; +++ +++ linux_init_abi (info, gdbarch); +++ +++#ifndef LHX20210326 +++ //set_xml_syscall_file_name (gdbarch, "syscalls/sw_64-linux.xml"); +++ /* Get the syscall number from the arch's register. */ +++ //set_gdbarch_get_syscall_number (gdbarch, sw_64_linux_get_syscall_number); +++#endif +++ +++ /* Hook into the DWARF CFI frame unwinder. */ +++ sw_64_dwarf2_init_abi (info, gdbarch); +++ +++ /* Hook into the MDEBUG frame unwinder. */ +++ sw_64_mdebug_init_abi (info, gdbarch); +++ +++ tdep->dynamic_sigtramp_offset = sw_64_linux_sigtramp_offset; +++ tdep->sigcontext_addr = sw_64_linux_sigcontext_addr; +++ tdep->pc_in_sigtramp = sw_64_linux_pc_in_sigtramp; +++ tdep->jb_pc = 2; +++ tdep->jb_elt_size = 8; +++ +++ set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target); +++ +++ set_solib_svr4_fetch_link_map_offsets +++ (gdbarch, svr4_lp64_fetch_link_map_offsets); +++ //set_gdbarch_core_read_description (gdbarch, ppc_linux_core_read_description); +++ // set_gdbarch_iterate_over_regset_sections (gdbarch, +++ // ppc_linux_iterate_over_regset_sections); +++ +++ /* Enable TLS support. */ +++ set_gdbarch_fetch_tls_load_module_address (gdbarch, +++ svr4_fetch_objfile_link_map); +++ +++ set_gdbarch_iterate_over_regset_sections +++ (gdbarch, sw_64_linux_iterate_over_regset_sections); +++ +++ set_gdbarch_gdb_signal_from_target (gdbarch, +++ sw_64_linux_gdb_signal_from_target); +++ set_gdbarch_gdb_signal_to_target (gdbarch, +++ sw_64_linux_gdb_signal_to_target); +++ /* SystemTap functions. */ +++ set_gdbarch_stap_integer_prefixes (gdbarch, stap_integer_prefixes); +++ set_gdbarch_stap_register_indirection_prefixes (gdbarch, +++ stap_register_indirection_prefixes); +++ set_gdbarch_stap_register_indirection_suffixes (gdbarch, +++ stap_register_indirection_suffixes); +++ set_gdbarch_stap_gdb_register_prefix (gdbarch, "r"); +++ //set_gdbarch_stap_is_single_operand (gdbarch, sw_64_stap_is_single_operand); +++ //set_gdbarch_stap_parse_special_token (gdbarch, +++ // sw_64_stap_parse_special_token); +++ /* Shared library handling. */ +++ // set_gdbarch_skip_trampoline_code (gdbarch, sw_64_skip_trampoline_code); +++ set_solib_svr4_fetch_link_map_offsets +++ (gdbarch, svr4_lp64_fetch_link_map_offsets); +++ /* Reversible debugging, process record. */ +++ set_gdbarch_process_record (gdbarch, sw_64_process_record); +++ /* Syscall record. */ +++ tdep->sw_64_syscall_record = sw_64_linux_syscall_record; +++ /* Displaced stepping. */ +++ //set_gdbarch_displaced_step_location (gdbarch, +++ // linux_displaced_step_location); +++ sw_64_init_linux_record_tdep (&sw_64_linux_record_tdep, 8); +++ +++} +++ +++void _initialize_aarch64_linux_tdep (); +++void +++_initialize_sw_64_linux_tdep (void) +++{ +++ gdbarch_register_osabi (bfd_arch_sw_64, 0, GDB_OSABI_LINUX, +++ sw_64_linux_init_abi); +++} ++diff -Nuar gdb-10.2/gdb/sw_64-linux-tdep.h gdb-10.2/gdb/sw_64-linux-tdep.h ++--- gdb-10.2/gdb/sw_64-linux-tdep.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-linux-tdep.h 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,43 @@ +++/* GNU/Linux on SW_64 target support, prototypes. +++ +++ Copyright (C) 2012-2020 Free Software Foundation, Inc. +++ Contributed by ARM Ltd. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#ifndef SW_64_LINUX_TDEP_H +++#define SW_64_LINUX_TDEP_H +++ +++#include "regset.h" +++ +++/* The general-purpose regset consists of 31 X registers, plus SP, PC, +++ and PSTATE registers, as defined in the SW_64 port of the Linux +++ kernel. */ +++#define SW_64_LINUX_SIZEOF_GREGSET (34 * X_REGISTER_SIZE) +++ +++/* The fp regset consists of 32 V registers, plus FPCR and FPSR which +++ are 4 bytes wide each, and the whole structure is padded to 128 bit +++ alignment. */ +++#define SW_64_LINUX_SIZEOF_FPREGSET (33 * V_REGISTER_SIZE) +++ +++/* The pauth regset consists of 2 X sized registers. */ +++#define SW_64_LINUX_SIZEOF_PAUTH (2 * X_REGISTER_SIZE) +++ +++ +++/* Matches HWCAP_PACA in kernel header arch/arm64/include/uapi/asm/hwcap.h. */ +++#define SW_64_HWCAP_PACA (1 << 30) +++ +++#endif /* SW_64_LINUX_TDEP_H */ ++diff -Nuar gdb-10.2/gdb/sw_64-linux.xml gdb-10.2/gdb/sw_64-linux.xml ++--- gdb-10.2/gdb/sw_64-linux.xml 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-linux.xml 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,18 @@ +++ +++ +++ +++ +++ +++ sw_64 +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/sw_64-mdebug-tdep.c gdb-10.2/gdb/sw_64-mdebug-tdep.c ++--- gdb-10.2/gdb/sw_64-mdebug-tdep.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-mdebug-tdep.c 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,408 @@ +++/* Target-dependent mdebug code for the SW_64 architecture. +++ Copyright (C) 1993-2018 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "defs.h" +++#include "frame.h" +++#include "frame-unwind.h" +++#include "frame-base.h" +++#include "symtab.h" +++#include "gdbcore.h" +++#include "block.h" +++#include "trad-frame.h" +++ +++#include "sw_64-tdep.h" +++#include "mdebugread.h" +++#include "gdbarch.h" +++ +++/* FIXME: Some of this code should perhaps be merged with mips. */ +++ +++/* *INDENT-OFF* */ +++/* Layout of a stack frame on the alpha: +++ +++ | | +++ pdr members: | 7th ... nth arg, | +++ | `pushed' by caller. | +++ | | +++----------------|-------------------------------|<-- old_sp == vfp +++ ^ ^ ^ ^ | | +++ | | | | | | +++ | |localoff | Copies of 1st .. 6th | +++ | | | | | argument if necessary. | +++ | | | v | | +++ | | | --- |-------------------------------|<-- LOCALS_ADDRESS +++ | | | | | +++ | | | | Locals and temporaries. | +++ | | | | | +++ | | | |-------------------------------| +++ | | | | | +++ |-fregoffset | Saved float registers. | +++ | | | | F9 | +++ | | | | . | +++ | | | | . | +++ | | | | F2 | +++ | | v | | +++ | | -------|-------------------------------| +++ | | | | +++ | | | Saved registers. | +++ | | | S6 | +++ |-regoffset | . | +++ | | | . | +++ | | | S0 | +++ | | | pdr.pcreg | +++ | v | | +++ | ----------|-------------------------------| +++ | | | +++ frameoffset | Argument build area, gets | +++ | | 7th ... nth arg for any | +++ | | called procedure. | +++ v | | +++ -------------|-------------------------------|<-- sp +++ | | +++*/ +++/* *INDENT-ON* */ +++ +++#define PROC_LOW_ADDR(proc) ((proc)->pdr.adr) +++#define PROC_FRAME_OFFSET(proc) ((proc)->pdr.frameoffset) +++#define PROC_FRAME_REG(proc) ((proc)->pdr.framereg) +++#define PROC_REG_MASK(proc) ((proc)->pdr.regmask) +++#define PROC_FREG_MASK(proc) ((proc)->pdr.fregmask) +++#define PROC_REG_OFFSET(proc) ((proc)->pdr.regoffset) +++#define PROC_FREG_OFFSET(proc) ((proc)->pdr.fregoffset) +++#define PROC_PC_REG(proc) ((proc)->pdr.pcreg) +++#define PROC_LOCALOFF(proc) ((proc)->pdr.localoff) +++ +++/* Locate the mdebug PDR for the given PC. Return null if one can't +++ be found; you'll have to fall back to other methods in that case. */ +++ +++static struct mdebug_extra_func_info * +++find_proc_desc (CORE_ADDR pc) +++{ +++ const struct block *b = block_for_pc (pc); +++ struct mdebug_extra_func_info *proc_desc = NULL; +++ struct symbol *sym = NULL; +++ const char *sh_name = NULL; +++ +++ if (b) +++ { +++ CORE_ADDR startaddr; +++ find_pc_partial_function (pc, &sh_name, &startaddr, NULL); +++ +++ if (startaddr > BLOCK_START (b)) +++ /* This is the "pathological" case referred to in a comment in +++ print_frame_info. It might be better to move this check into +++ symbol reading. */ +++ sym = NULL; +++ else +++ sym = lookup_symbol (MDEBUG_EFI_SYMBOL_NAME, b, LABEL_DOMAIN, +++ 0).symbol; +++ } +++ +++ if (sym) +++ { +++ proc_desc = (struct mdebug_extra_func_info *) SYMBOL_VALUE_BYTES (sym); +++ +++ /* Correct incorrect setjmp procedure descriptor from the library +++ to make backtrace through setjmp work. */ +++ if (proc_desc->pdr.pcreg == 0 +++ && strcmp (sh_name, "setjmp") == 0) +++ { +++ proc_desc->pdr.pcreg = SW_RA_REGNUM; +++ proc_desc->pdr.regmask = 0x80000000; +++ proc_desc->pdr.regoffset = -4; +++ } +++ +++ /* If we never found a PDR for this function in symbol reading, +++ then examine prologues to find the information. */ +++ if (proc_desc->pdr.framereg == -1) +++ proc_desc = NULL; +++ } +++ +++ return proc_desc; +++} +++ +++/* Return a non-zero result if the function is frameless; zero otherwise. */ +++ +++static int +++sw_64_mdebug_frameless (struct mdebug_extra_func_info *proc_desc) +++{ +++ return (PROC_FRAME_REG (proc_desc) == SW_SP_REGNUM +++ && PROC_FRAME_OFFSET (proc_desc) == 0); +++} +++ +++/* This returns the PC of the first inst after the prologue. If we can't +++ find the prologue, then return 0. */ +++ +++static CORE_ADDR +++sw_64_mdebug_after_prologue (CORE_ADDR pc, +++ struct mdebug_extra_func_info *proc_desc) +++{ +++ if (proc_desc) +++ { +++ /* If function is frameless, then we need to do it the hard way. I +++ strongly suspect that frameless always means prologueless... */ +++ if (sw_64_mdebug_frameless (proc_desc)) +++ return 0; +++ } +++ +++ return sw_64_after_prologue (pc); +++} +++ +++/* Return non-zero if we *might* be in a function prologue. Return zero +++ if we are definitively *not* in a function prologue. */ +++ +++static int +++sw_64_mdebug_in_prologue (CORE_ADDR pc, +++ struct mdebug_extra_func_info *proc_desc) +++{ +++ CORE_ADDR after_prologue_pc = sw_64_mdebug_after_prologue (pc, proc_desc); +++ return (after_prologue_pc == 0 || pc < after_prologue_pc); +++} +++ +++ +++/* Frame unwinder that reads mdebug PDRs. */ +++ +++struct sw_64_mdebug_unwind_cache +++{ +++ struct mdebug_extra_func_info *proc_desc; +++ CORE_ADDR vfp; +++ struct trad_frame_saved_reg *saved_regs; +++}; +++ +++/* Extract all of the information about the frame from PROC_DESC +++ and store the resulting register save locations in the structure. */ +++ +++static struct sw_64_mdebug_unwind_cache * +++sw_64_mdebug_frame_unwind_cache (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_mdebug_unwind_cache *info; +++ struct mdebug_extra_func_info *proc_desc; +++ ULONGEST vfp; +++ CORE_ADDR pc, reg_position; +++ unsigned long mask; +++ int ireg, returnreg; +++ +++ if (*this_prologue_cache) +++ return (struct sw_64_mdebug_unwind_cache *) *this_prologue_cache; +++ +++ info = FRAME_OBSTACK_ZALLOC (struct sw_64_mdebug_unwind_cache); +++ *this_prologue_cache = info; +++ pc = get_frame_address_in_block (this_frame); +++ +++ /* ??? We don't seem to be able to cache the lookup of the PDR +++ from sw_64_mdebug_frame_p. It'd be nice if we could change +++ the arguments to that function. Oh well. */ +++ proc_desc = find_proc_desc (pc); +++ info->proc_desc = proc_desc; +++ gdb_assert (proc_desc != NULL); +++ +++ info->saved_regs = trad_frame_alloc_saved_regs (this_frame); +++ +++ /* The VFP of the frame is at FRAME_REG+FRAME_OFFSET. */ +++ vfp = get_frame_register_unsigned (this_frame, PROC_FRAME_REG (proc_desc)); +++ vfp += PROC_FRAME_OFFSET (info->proc_desc); +++ info->vfp = vfp; +++ +++ /* Fill in the offsets for the registers which gen_mask says were saved. */ +++ +++ reg_position = vfp + PROC_REG_OFFSET (proc_desc); +++ mask = PROC_REG_MASK (proc_desc); +++ returnreg = PROC_PC_REG (proc_desc); +++ +++ /* Note that RA is always saved first, regardless of its actual +++ register number. */ +++ if (mask & (1 << returnreg)) +++ { +++ /* Clear bit for RA so we don't save it again later. */ +++ mask &= ~(1 << returnreg); +++ +++ info->saved_regs[returnreg].addr = reg_position; +++ reg_position += 8; +++ } +++ +++ for (ireg = 0; ireg <= 31; ++ireg) +++ if (mask & (1 << ireg)) +++ { +++ info->saved_regs[ireg].addr = reg_position; +++ reg_position += 8; +++ } +++ +++ reg_position = vfp + PROC_FREG_OFFSET (proc_desc); +++ mask = PROC_FREG_MASK (proc_desc); +++ +++ for (ireg = 0; ireg <= 31; ++ireg) +++ if (mask & (1 << ireg)) +++ { +++ info->saved_regs[SW_FP0_REGNUM + ireg].addr = reg_position; +++ reg_position += 8; +++ } +++ +++ /* The stack pointer of the previous frame is computed by popping +++ the current stack frame. */ +++ if (!trad_frame_addr_p (info->saved_regs, SW_SP_REGNUM)) +++ trad_frame_set_value (info->saved_regs, SW_SP_REGNUM, vfp); +++ +++ return info; +++} +++ +++/* Given a GDB frame, determine the address of the calling function's +++ frame. This will be used to create a new GDB frame struct. */ +++ +++static void +++sw_64_mdebug_frame_this_id (struct frame_info *this_frame, +++ void **this_prologue_cache, +++ struct frame_id *this_id) +++{ +++ struct sw_64_mdebug_unwind_cache *info +++ = sw_64_mdebug_frame_unwind_cache (this_frame, this_prologue_cache); +++ +++ *this_id = frame_id_build (info->vfp, get_frame_func (this_frame)); +++} +++ +++/* Retrieve the value of REGNUM in FRAME. Don't give up! */ +++ +++static struct value * +++sw_64_mdebug_frame_prev_register (struct frame_info *this_frame, +++ void **this_prologue_cache, int regnum) +++{ +++ struct sw_64_mdebug_unwind_cache *info +++ = sw_64_mdebug_frame_unwind_cache (this_frame, this_prologue_cache); +++ +++ /* The PC of the previous frame is stored in the link register of +++ the current frame. Frob regnum so that we pull the value from +++ the correct place. */ +++ if (regnum == SW_PC_REGNUM) +++ regnum = PROC_PC_REG (info->proc_desc); +++ +++ return trad_frame_get_prev_register (this_frame, info->saved_regs, regnum); +++} +++ +++/* Return a non-zero result if the size of the stack frame exceeds the +++ maximum debuggable frame size (512 Kbytes); zero otherwise. */ +++ +++static int +++sw_64_mdebug_max_frame_size_exceeded (struct mdebug_extra_func_info *proc_desc) +++{ +++ /* If frame offset is null, we can be in two cases: either the +++ function is frameless (the stack frame is null) or its +++ frame exceeds the maximum debuggable frame size (512 Kbytes). */ +++ +++ return (PROC_FRAME_OFFSET (proc_desc) == 0 +++ && !sw_64_mdebug_frameless (proc_desc)); +++} +++ +++static int +++sw_64_mdebug_frame_sniffer (const struct frame_unwind *self, +++ struct frame_info *this_frame, +++ void **this_cache) +++{ +++ CORE_ADDR pc = get_frame_address_in_block (this_frame); +++ struct mdebug_extra_func_info *proc_desc; +++ +++ /* If this PC does not map to a PDR, then clearly this isn't an +++ mdebug frame. */ +++ proc_desc = find_proc_desc (pc); +++ if (proc_desc == NULL) +++ return 0; +++ +++ /* If we're in the prologue, the PDR for this frame is not yet valid. +++ Say no here and we'll fall back on the heuristic unwinder. */ +++ if (sw_64_mdebug_in_prologue (pc, proc_desc)) +++ return 0; +++ +++ /* If the maximum debuggable frame size has been exceeded, the +++ proc desc is bogus. Fall back on the heuristic unwinder. */ +++ if (sw_64_mdebug_max_frame_size_exceeded (proc_desc)) +++ return 0; +++ +++ return 1; +++} +++ +++static const struct frame_unwind sw_64_mdebug_frame_unwind = { +++ NORMAL_FRAME, +++ default_frame_unwind_stop_reason, +++ sw_64_mdebug_frame_this_id, +++ sw_64_mdebug_frame_prev_register, +++ NULL, +++ sw_64_mdebug_frame_sniffer +++}; +++ +++static CORE_ADDR +++sw_64_mdebug_frame_base_address (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_mdebug_unwind_cache *info +++ = sw_64_mdebug_frame_unwind_cache (this_frame, this_prologue_cache); +++ +++ return info->vfp; +++} +++ +++static CORE_ADDR +++sw_64_mdebug_frame_locals_address (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_mdebug_unwind_cache *info +++ = sw_64_mdebug_frame_unwind_cache (this_frame, this_prologue_cache); +++ +++ return info->vfp - PROC_LOCALOFF (info->proc_desc); +++} +++ +++static CORE_ADDR +++sw_64_mdebug_frame_args_address (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_mdebug_unwind_cache *info +++ = sw_64_mdebug_frame_unwind_cache (this_frame, this_prologue_cache); +++ +++ return info->vfp - SW_NUM_ARG_REGS * 8; +++} +++ +++static const struct frame_base sw_64_mdebug_frame_base = { +++ &sw_64_mdebug_frame_unwind, +++ sw_64_mdebug_frame_base_address, +++ sw_64_mdebug_frame_locals_address, +++ sw_64_mdebug_frame_args_address +++}; +++ +++static const struct frame_base * +++sw_64_mdebug_frame_base_sniffer (struct frame_info *this_frame) +++{ +++ CORE_ADDR pc = get_frame_address_in_block (this_frame); +++ struct mdebug_extra_func_info *proc_desc; +++ +++ /* If this PC does not map to a PDR, then clearly this isn't an +++ mdebug frame. */ +++ proc_desc = find_proc_desc (pc); +++ if (proc_desc == NULL) +++ return NULL; +++ +++ /* If the maximum debuggable frame size has been exceeded, the +++ proc desc is bogus. Fall back on the heuristic unwinder. */ +++ if (sw_64_mdebug_max_frame_size_exceeded (proc_desc)) +++ return 0; +++ +++ return &sw_64_mdebug_frame_base; +++} +++ +++ +++void +++sw_64_mdebug_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch) +++{ +++ frame_unwind_append_unwinder (gdbarch, &sw_64_mdebug_frame_unwind); +++ frame_base_append_sniffer (gdbarch, sw_64_mdebug_frame_base_sniffer); +++} ++diff -Nuar gdb-10.2/gdb/sw_64-tdep.c gdb-10.2/gdb/sw_64-tdep.c ++--- gdb-10.2/gdb/sw_64-tdep.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-tdep.c 2025-04-16 17:06:52.012086800 +0800 ++@@ -0,0 +1,2739 @@ +++/* Target-dependent code for the SW_64 architecture, for GDB, the GNU Debugger. +++ +++ Copyright (C) 1993-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "defs.h" +++#include "frame.h" +++#include "frame-unwind.h" +++#include "frame-base.h" +++#include "dwarf2/frame.h" +++#include "inferior.h" +++#include "symtab.h" +++#include "value.h" +++#include "gdbcmd.h" +++#include "gdbcore.h" +++#include "dis-asm.h" +++#include "symfile.h" +++#include "objfiles.h" +++#include "linespec.h" +++#include "regcache.h" +++#include "reggroups.h" +++#include "arch-utils.h" +++#include "osabi.h" +++#include "block.h" +++#include "infcall.h" +++#include "trad-frame.h" +++#include +++#include "elf-bfd.h" +++ +++#include "sw_64-tdep.h" +++#include +++#include "record.h" +++#include "record-full.h" +++ +++/* Instruction decoding. The notations for registers, immediates and +++ opcodes are the same as the one used in Compaq's SW_64 architecture +++ handbook. */ +++#define submask(x) ((1L << ((x) + 1)) - 1) +++#define bits(obj,st,fn) (((obj) >> (st)) & submask ((fn) - (st))) +++#define INSN_OPCODE(insn) ((insn & 0xfc000000) >> 26) +++#define bit(obj,st) (((obj) >> (st)) & 1) +++#define rigg(obj,st) ((obj) >> (st)) +++enum sw_64_record_result +++{ +++ SW_64_RECORD_SUCCESS, +++ SW_64_RECORD_UNSUPPORTED, +++ SW_64_RECORD_UNKNOWN +++}; +++ +++/* Memory instruction format */ +++#define MEM_RA(insn) ((insn & 0x03e00000) >> 21) +++#define MEM_RB(insn) ((insn & 0x001f0000) >> 16) +++#define MEM_DISP(insn) \ +++ (((insn & 0x8000) == 0) ? (insn & 0xffff) : -((-insn) & 0xffff)) +++ +++#ifdef LHX20201102 +++static const int lda_opcode = 0x08; +++static const int stq_opcode = 0x2d; +++#else +++ +++static const int lda_opcode = 0x3e; +++static const int stq_opcode = 0x2d; +++#endif +++ +++/* Branch instruction format */ +++#define BR_RA(insn) MEM_RA(insn) +++ +++static const int br_opcode = 0x30; +++static const int bne_opcode = 0x3d; +++ +++/* Operate instruction format */ +++#define OPR_FUNCTION(insn) ((insn & 0xfe0) >> 5) +++#define OPR_HAS_IMMEDIATE(insn) ((insn & 0x1000) == 0x1000) +++#define OPR_RA(insn) MEM_RA(insn) +++#define OPR_RC(insn) ((insn & 0x1f)) +++#define OPR_LIT(insn) ((insn & 0x1fe000) >> 13) +++ +++static const int subq_opcode = 0x10; +++static const int subq_function = 0x29; +++ +++extern int pc_in_section (CORE_ADDR , char *); +++ +++ +++/* Return the name of the REGNO register. +++ +++ An empty name corresponds to a register number that used to +++ be used for a virtual register. That virtual register has +++ been removed, but the index is still reserved to maintain +++ compatibility with existing remote sw_64 targets. */ +++ +++static const char * +++sw_64_register_name (struct gdbarch *gdbarch, int regno) +++{ +++ static const char * const register_names[] = +++ { +++#ifndef LHX20201026 +++ "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", +++ "r8", "r9", "r10", "r11", "r12", "r13", "r14", "fp", +++ "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23", +++ "r24", "r25", "ra", "r27", "r28", "r29", "sp", "r31", +++#else +++ "v0", "t0", "t1", "t2", "t3", "t4", "t5", "t6", +++ "t7", "s0", "s1", "s2", "s3", "s4", "s5", "fp", +++ "a0", "a1", "a2", "a3", "a4", "a5", "t8", "t9", +++ "t10", "t11", "ra", "t12", "at", "gp", "sp", "zero", +++#endif +++ "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7", +++ "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15", +++ "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23", +++ "f24", "f25", "f26", "f27", "f28", "f29", "f30", "fpcr", +++ "pc", "", "unique", +++ "ef0", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef1", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef2", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef3", "ef", "ef", "ef", "ef", "ef", "ef", "ef", /* ef0 */ +++ "ef4", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef5", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef6", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef7", "ef", "ef", "ef", "ef", "ef", "ef", "ef", /* ef1 */ +++ "ef8", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef9", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef10", "ef", "ef", "ef", "ef", "ef", "ef", "ef", +++ "ef11", "ef", "ef", "ef", "ef", "ef", "ef", "ef", /* ef2 */ +++ "", "", "", "", /*"DA_MATCH", "DA_MASK", "DV__MATCH", "DV_MASK",*/ +++ "V0", "V1", "V2", "V3", "V4", "V5", "V6", "V7", +++ "V8", "V9", "V10", "V11", "V12", "V13", "V14", "V15", +++ "V16", "V17", "V18", "V19", "V20", "V21", "V22", "V23", +++ "V24", "V25", "V26", "V27", "V28", "V29", "V30", "V31", +++ "" +++ }; +++ +++ if (regno < 0) +++ return NULL; +++ if (regno >= ARRAY_SIZE(register_names)) +++ return NULL; +++ return register_names[regno]; +++} +++ +++static int +++sw_64_cannot_fetch_register (struct gdbarch *gdbarch, int regno) +++{ +++ return (strlen (sw_64_register_name (gdbarch, regno)) == 0); +++} +++ +++static int +++sw_64_cannot_store_register (struct gdbarch *gdbarch, int regno) +++{ +++ return (regno == SW_ZERO_REGNUM +++ || strlen (sw_64_register_name (gdbarch, regno)) == 0); +++} +++/* Construct vector type for ext registers. */ +++static struct type * +++sw_64_vec_type (struct gdbarch *gdbarch) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ +++ if (!tdep->sw_64_vec_type) +++ { +++ struct type *t,*elem; +++ +++ t = arch_composite_type(gdbarch, "__gdb_builtin_type_vec256", TYPE_CODE_UNION); +++ +++ elem = builtin_type (gdbarch)->builtin_long_long; +++ append_composite_type_field (t, "v4_int64", +++ init_vector_type (elem, 4)); +++ elem = builtin_type (gdbarch)->builtin_double; +++ append_composite_type_field (t, "v4_double", +++ init_vector_type (elem, 4)); +++ +++ TYPE_VECTOR(t) = 1; +++ const char a[20]="builtin_type_vec256"; +++ t->set_name (&a[0]);//SBW +++ tdep->sw_64_vec_type = t; +++ } +++ +++ return tdep->sw_64_vec_type; +++} +++static struct type * +++sw_64_register_type (struct gdbarch *gdbarch, int regno) +++{ +++ if (regno == SW_SP_REGNUM || regno == SW_GP_REGNUM) +++ return builtin_type (gdbarch)->builtin_data_ptr; +++ if (regno == SW_PC_REGNUM) +++ return builtin_type (gdbarch)->builtin_func_ptr; +++ +++ /* Don't need to worry about little vs big endian until +++ some jerk tries to port to sw_64-unicosmk. */ +++ if (regno >= SW_FP0_REGNUM && regno < SW_FP0_REGNUM + NFP_REGS - 1) +++ return builtin_type (gdbarch)->builtin_double; +++ +++if (regno >= SW64_VEC0 && regno < SW64_VEC0 + NVEC_REGS - 1 ) +++ return sw_64_vec_type(gdbarch); +++#ifndef LHX20201102 +++ if (regno >= 67 && regno <= 131 + 31) +++ return builtin_type (gdbarch)->builtin_double; +++#endif +++ +++ return builtin_type (gdbarch)->builtin_int64; +++} +++ +++/* Is REGNUM a member of REGGROUP? */ +++ +++static int +++sw_64_register_reggroup_p (struct gdbarch *gdbarch, int regnum, +++ struct reggroup *group) +++{ +++ /* Filter out any registers eliminated, but whose regnum is +++ reserved for backward compatibility, e.g. the vfp. */ +++ if (gdbarch_register_name (gdbarch, regnum) == NULL +++ || *gdbarch_register_name (gdbarch, regnum) == '\0') +++ return 0; +++ +++ if (group == all_reggroup) +++ return 1; +++ +++ /* Zero should not be saved or restored. Technically it is a general +++ register (just as $f31 would be a float if we represented it), but +++ there's no point displaying it during "info regs", so leave it out +++ of all groups except for "all". */ +++ if (regnum == SW_ZERO_REGNUM) +++ return 0; +++ +++ /* All other registers are saved and restored. */ +++ if (group == save_reggroup || group == restore_reggroup) +++ return 1; +++ +++ /* All other groups are non-overlapping. */ +++ +++ /* Since this is really a PALcode memory slot... */ +++ if (regnum == SW_UNIQUE_REGNUM) +++ return group == system_reggroup; +++ +++ /* Force the FPCR to be considered part of the floating point state. */ +++ if (regnum == SW_FPCR_REGNUM) +++ return group == float_reggroup; +++ +++#ifndef LHX20201102 +++ if (regnum >= SW_FP0_REGNUM && regnum < SW_FP0_REGNUM + NFP_REGS - 1) +++ return group == float_reggroup; +++ if (regnum >= SW64_VEC0 && regnum < SW64_VEC0 + NVEC_REGS - 1) +++ return group == vector_reggroup; +++#endif +++ if (regnum < SW_ZERO_REGNUM ) +++ return group == general_reggroup; +++ else +++ return 0; +++} +++ +++static enum register_status +++sw_64_vec_register_read (struct gdbarch *gdbarch, readable_regcache *regcache, +++ int regnum, gdb_byte *buf) +++{ +++#ifndef LHX20201102 +++//printf("[sw_64_vec_register_read] REG: read $V%d\n", regnum); +++#endif +++#ifndef LHX20201102 +++ int i,fpnum; +++ enum register_status status; +++ // ULONGEST addr; +++ gdb_byte fp_buf[SW_REGISTER_SIZE]; +++ if (regnum >= SW2_V0_REGNUM && regnum < SW2_V0_REGNUM + 31) +++ { +++ fpnum = regnum - SW2_V0_REGNUM + SW_FP0_REGNUM; +++ //status = regcache->raw_read(fpnum, &addr); +++ status = regcache->raw_read(fpnum, fp_buf); +++ if (status != REG_VALID) +++ return status; +++ //read_memory (addr, buf+24, SW_REGISTER_SIZE); +++ memcpy (buf+24, fp_buf, SW_REGISTER_SIZE); +++ fpnum = regnum - SW2_V0_REGNUM + SW2_V0F3_REGNUM; +++ for (i=0; i<3; +++ i++, fpnum -= 32 ) { +++ //status = regcache->raw_read(fpnum, &addr); +++ status = regcache->raw_read(fpnum, fp_buf); +++ if (status != REG_VALID) +++ return status; +++ //read_memory(addr, buf+(i<<3), SW_REGISTER_SIZE); +++ memcpy (buf+(i<<3), fp_buf, SW_REGISTER_SIZE); +++ +++ } +++ } +++ return REG_VALID; +++#else +++ int i,fpnum; +++ enum register_status status; +++ ULONGEST addr; +++ +++ if ( regnum < SW64_VEC0 || regnum >= SW64_VEC0 + NVEC_REGS) { +++ warning("REG: read $V%d\n", regnum); +++ return REG_VALID; +++ } +++ fpnum = regnum - SW64_VEC0 + SW_FP0_REGNUM; +++ status = regcache->raw_read(fpnum, &addr); +++ read_memory (addr, buf+24, SW_REGISTER_SIZE); +++ +++ fpnum += NVEC_REGS*3; +++ for (i=0; i<3; i++, fpnum -= NVEC_REGS) +++ { +++ status = regcache->raw_read(fpnum, &addr); +++ read_memory(addr, buf+(i<<3), SW_REGISTER_SIZE); +++ } +++ return status; +++#endif +++} +++ +++static void +++sw_64_vec_register_write (struct gdbarch *gdbarch, struct regcache *regcache, +++ int regnum, const gdb_byte *buf) +++{ +++#ifndef LHX20201102 +++//printf("[sw_64_vec_register_write] REG: write $V%d\n", regnum); +++#endif +++#ifndef LHX20201102 +++ if (regnum >= SW2_V0_REGNUM && regnum < SW2_V0_REGNUM + 31) { +++ int i,fpnum; +++ +++ fpnum = regnum - SW2_V0_REGNUM + SW_FP0_REGNUM; +++ regcache->raw_write (fpnum, buf+24); +++ +++ fpnum = regnum - SW2_V0_REGNUM + SW2_V0F3_REGNUM; +++ for (i=0; i<3; +++ i++, fpnum -= 32 ) { +++ regcache->raw_write (fpnum, buf+(i<<3)); +++ } +++ } +++#else +++ int i,fpnum; +++ enum register_status status; +++ if ( regnum < SW64_VEC0 || regnum >= SW64_VEC0 + NVEC_REGS) +++ { +++ warning("REG: write $V%d\n", regnum); +++ return ; +++ } +++ +++ fpnum = regnum - SW64_VEC0 + SW_FP0_REGNUM; +++ //regcache_raw_write (regcache, fpnum, buf+24); +++ regcache->raw_write (fpnum, buf+24); +++ +++ fpnum += NVEC_REGS*3; +++ for (i=0; i<3; i++, fpnum -= NVEC_REGS ) +++ //regcache_raw_write (regcache, fpnum, buf+(i<<3)); +++ regcache->raw_write (fpnum, buf+(i<<3)); +++#endif +++} +++#ifndef LHX20201026 +++/* Read an instruction from memory at PC, looking through breakpoints. */ +++/* n is power of 2, over 0 */ +++ +++unsigned int* +++sw_64_read_insns (struct gdbarch *gdbarch, CORE_ADDR pc, int n) +++{ +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ +++ /* alloc from stack frame, freed on return */ +++ gdb_byte *buf = (gdb_byte *)XALLOCAVEC(int, n); +++ unsigned int *ibuf = XCNEWVEC(unsigned int, n); +++ gdb_byte *p; +++ int res, i; +++ +++ +++ res = target_read_memory (pc, buf, sizeof (int)*n); +++ if (res != 0) +++ memory_error (TARGET_XFER_E_IO, pc); +++ +++ n >>= 1; +++ for (i=0, p=buf; i> 0) & 0x7fffff; +++ ULONGEST sign = (mem >> 31) & 1; +++ ULONGEST exp_msb = (mem >> 30) & 1; +++ ULONGEST exp_low = (mem >> 23) & 0x7f; +++ ULONGEST exp, reg; +++ +++ exp = (exp_msb << 10) | exp_low; +++ if (exp_msb) +++ { +++ if (exp_low == 0x7f) +++ exp = 0x7ff; +++ } +++ else +++ { +++ if (exp_low != 0x00) +++ exp |= 0x380; +++ } +++ +++ reg = (sign << 63) | (exp << 52) | (frac << 29); +++ store_unsigned_integer ((gdb_byte *) out, 8, byte_order, reg); +++} +++ +++/* Similarly, this represents exactly the conversion performed by +++ the STS instruction. */ +++ +++static void +++sw_64_sts (struct gdbarch *gdbarch, void *out, const void *in) +++{ +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ ULONGEST reg, mem; +++ +++ reg = extract_unsigned_integer ((const gdb_byte *) in, 8, byte_order); +++ mem = ((reg >> 32) & 0xc0000000) | ((reg >> 29) & 0x3fffffff); +++ store_unsigned_integer ((gdb_byte *) out, 4, byte_order, mem); +++} +++ +++/* The sw_64 needs a conversion between register and memory format if the +++ register is a floating point register and memory format is float, as the +++ register format must be double or memory format is an integer with 4 +++ bytes, as the representation of integers in floating point +++ registers is different. */ +++ +++static int +++sw_64_convert_register_p (struct gdbarch *gdbarch, int regno, +++ struct type *type) +++{ +++ return (regno >= SW_FP0_REGNUM && regno < SW_FP0_REGNUM + 31 +++ && TYPE_LENGTH (type) == 4); +++} +++ +++static int +++sw_64_register_to_value (struct frame_info *frame, int regnum, +++ struct type *valtype, gdb_byte *out, +++ int *optimizedp, int *unavailablep) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (frame); +++ struct value *value = get_frame_register_value (frame, regnum); +++ +++ gdb_assert (value != NULL); +++ *optimizedp = value_optimized_out (value); +++ *unavailablep = !value_entirely_available (value); +++ +++ if (*optimizedp || *unavailablep) +++ { +++ release_value (value); +++ return 0; +++ } +++ +++ /* Convert to VALTYPE. */ +++ +++ gdb_assert (TYPE_LENGTH (valtype) == 4); +++ sw_64_sts (gdbarch, out, value_contents_all (value)); +++ +++ release_value (value); +++ return 1; +++} +++ +++static void +++sw_64_value_to_register (struct frame_info *frame, int regnum, +++ struct type *valtype, const gdb_byte *in) +++{ +++ gdb_byte out[SW_REGISTER_SIZE]; +++ +++ gdb_assert (TYPE_LENGTH (valtype) == 4); +++ gdb_assert (register_size (get_frame_arch (frame), regnum) +++ <= SW_REGISTER_SIZE); +++ sw_64_lds (get_frame_arch (frame), out, in); +++ +++ put_frame_register (frame, regnum, out); +++} +++ +++ +++/* The sw_64 passes the first six arguments in the registers, the rest on +++ the stack. The register arguments are stored in ARG_REG_BUFFER, and +++ then moved into the register file; this simplifies the passing of a +++ large struct which extends from the registers to the stack, plus avoids +++ three ptrace invocations per word. +++ +++ We don't bother tracking which register values should go in integer +++ regs or fp regs; we load the same values into both. +++ +++ If the called function is returning a structure, the address of the +++ structure to be returned is passed as a hidden first argument. */ +++ +++static CORE_ADDR +++sw_64_push_dummy_call (struct gdbarch *gdbarch, struct value *function, +++ struct regcache *regcache, CORE_ADDR bp_addr, +++ int nargs, struct value **args, CORE_ADDR sp, +++ function_call_return_method return_method, +++ CORE_ADDR struct_addr) +++{ +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ int i; +++ int accumulate_size = (return_method == return_method_struct) ? 8 : 0; +++ struct sw_64_arg +++ { +++ const gdb_byte *contents; +++ int len; +++ int offset; +++ }; +++ struct sw_64_arg *sw_64_args = XALLOCAVEC (struct sw_64_arg, nargs); +++ struct sw_64_arg *m_arg; +++ gdb_byte arg_reg_buffer[SW_REGISTER_SIZE * SW_NUM_ARG_REGS]; +++ int required_arg_regs; +++ CORE_ADDR func_addr = find_function_addr (function, NULL); +++ +++ /* The ABI places the address of the called function in T12. */ +++ regcache_cooked_write_signed (regcache, SW_T12_REGNUM, func_addr); +++ +++ /* Set the return address register to point to the entry point +++ of the program, where a breakpoint lies in wait. */ +++ regcache_cooked_write_signed (regcache, SW_RA_REGNUM, bp_addr); +++ +++ /* Lay out the arguments in memory. */ +++ for (i = 0, m_arg = sw_64_args; i < nargs; i++, m_arg++) +++ { +++ struct value *arg = args[i]; +++ struct type *arg_type = check_typedef (value_type (arg)); +++ +++ /* Cast argument to long if necessary as the compiler does it too. */ +++ switch (arg_type->code ()) +++ { +++ case TYPE_CODE_INT: +++ case TYPE_CODE_BOOL: +++ case TYPE_CODE_CHAR: +++ case TYPE_CODE_RANGE: +++ case TYPE_CODE_ENUM: +++ if (TYPE_LENGTH (arg_type) == 4) +++ { +++ /* 32-bit values must be sign-extended to 64 bits +++ even if the base data type is unsigned. */ +++ arg_type = builtin_type (gdbarch)->builtin_int32; +++ arg = value_cast (arg_type, arg); +++ } +++ if (TYPE_LENGTH (arg_type) < SW_REGISTER_SIZE) +++ { +++ arg_type = builtin_type (gdbarch)->builtin_int64; +++ arg = value_cast (arg_type, arg); +++ } +++ break; +++ +++ case TYPE_CODE_FLT: +++ /* "float" arguments loaded in registers must be passed in +++ register format, aka "double". */ +++ if (accumulate_size < sizeof (arg_reg_buffer) +++ && TYPE_LENGTH (arg_type) == 4) +++ { +++ arg_type = builtin_type (gdbarch)->builtin_double; +++ arg = value_cast (arg_type, arg); +++ } +++ /* Tru64 5.1 has a 128-bit long double, and passes this by +++ invisible reference. No one else uses this data type. */ +++ else if (TYPE_LENGTH (arg_type) == 16) +++ { +++ /* Allocate aligned storage. */ +++ sp = (sp & -16) - 16; +++ +++ /* Write the real data into the stack. */ +++ write_memory (sp, value_contents (arg), 16); +++ +++ /* Construct the indirection. */ +++ arg_type = lookup_pointer_type (arg_type); +++ arg = value_from_pointer (arg_type, sp); +++ } +++ break; +++ +++ case TYPE_CODE_COMPLEX: +++ /* ??? The ABI says that complex values are passed as two +++ separate scalar values. This distinction only matters +++ for complex float. However, GCC does not implement this. */ +++ +++ /* Tru64 5.1 has a 128-bit long double, and passes this by +++ invisible reference. */ +++ if (TYPE_LENGTH (arg_type) == 32) +++ { +++ /* Allocate aligned storage. */ +++ sp = (sp & -16) - 16; +++ +++ /* Write the real data into the stack. */ +++ write_memory (sp, value_contents (arg), 32); +++ +++ /* Construct the indirection. */ +++ arg_type = lookup_pointer_type (arg_type); +++ arg = value_from_pointer (arg_type, sp); +++ } +++ break; +++ +++ default: +++ break; +++ } +++ m_arg->len = TYPE_LENGTH (arg_type); +++ m_arg->offset = accumulate_size; +++ accumulate_size = (accumulate_size + m_arg->len + 7) & ~7; +++ m_arg->contents = value_contents (arg); +++ } +++ +++ /* Determine required argument register loads, loading an argument register +++ is expensive as it uses three ptrace calls. */ +++ required_arg_regs = accumulate_size / 8; +++ if (required_arg_regs > SW_NUM_ARG_REGS) +++ required_arg_regs = SW_NUM_ARG_REGS; +++ +++ /* Make room for the arguments on the stack. */ +++ if (accumulate_size < sizeof(arg_reg_buffer)) +++ accumulate_size = 0; +++ else +++ accumulate_size -= sizeof(arg_reg_buffer); +++ sp -= accumulate_size; +++ +++ /* Keep sp aligned to a multiple of 16 as the ABI requires. */ +++ sp &= ~15; +++ +++ /* `Push' arguments on the stack. */ +++ for (i = nargs; m_arg--, --i >= 0;) +++ { +++ const gdb_byte *contents = m_arg->contents; +++ int offset = m_arg->offset; +++ int len = m_arg->len; +++ +++ /* Copy the bytes destined for registers into arg_reg_buffer. */ +++ if (offset < sizeof(arg_reg_buffer)) +++ { +++ if (offset + len <= sizeof(arg_reg_buffer)) +++ { +++ memcpy (arg_reg_buffer + offset, contents, len); +++ continue; +++ } +++ else +++ { +++ int tlen = sizeof(arg_reg_buffer) - offset; +++ memcpy (arg_reg_buffer + offset, contents, tlen); +++ offset += tlen; +++ contents += tlen; +++ len -= tlen; +++ } +++ } +++ +++ /* Everything else goes to the stack. */ +++ write_memory (sp + offset - sizeof(arg_reg_buffer), contents, len); +++ } +++ if (return_method == return_method_struct) +++ store_unsigned_integer (arg_reg_buffer, SW_REGISTER_SIZE, +++ byte_order, struct_addr); +++ +++ /* Load the argument registers. */ +++ for (i = 0; i < required_arg_regs; i++) +++ { +++ regcache->cooked_write (SW_A0_REGNUM + i, +++ arg_reg_buffer + i * SW_REGISTER_SIZE); +++ regcache->cooked_write (SW_FPA0_REGNUM + i, +++ arg_reg_buffer + i * SW_REGISTER_SIZE); +++ } +++ +++ /* Finally, update the stack pointer. */ +++ regcache_cooked_write_signed (regcache, SW_SP_REGNUM, sp); +++ +++ return sp; +++} +++ +++/* Extract from REGCACHE the value about to be returned from a function +++ and copy it into VALBUF. */ +++ +++static void +++sw_64_extract_return_value (struct type *valtype, struct regcache *regcache, +++ gdb_byte *valbuf) +++{ +++ struct gdbarch *gdbarch = regcache->arch (); +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ gdb_byte raw_buffer[SW_REGISTER_SIZE]; +++ ULONGEST l; +++ +++ switch (valtype->code ()) +++ { +++ case TYPE_CODE_FLT: +++ switch (TYPE_LENGTH (valtype)) +++ { +++ case 4: +++ regcache->cooked_read (SW_FP0_REGNUM, raw_buffer); +++ sw_64_sts (gdbarch, valbuf, raw_buffer); +++ break; +++ +++ case 8: +++ regcache->cooked_read (SW_FP0_REGNUM, valbuf); +++ break; +++ +++ case 16: +++ regcache_cooked_read_unsigned (regcache, SW_V0_REGNUM, &l); +++ read_memory (l, valbuf, 16); +++ break; +++ +++ default: +++ internal_error (__FILE__, __LINE__, +++ _("unknown floating point width")); +++ } +++ break; +++ +++ case TYPE_CODE_COMPLEX: +++ switch (TYPE_LENGTH (valtype)) +++ { +++ case 8: +++ /* ??? This isn't correct wrt the ABI, but it's what GCC does. */ +++ regcache->cooked_read (SW_FP0_REGNUM, valbuf); +++ break; +++ +++ case 16: +++ regcache->cooked_read (SW_FP0_REGNUM, valbuf); +++ regcache->cooked_read (SW_FP0_REGNUM + 1, valbuf + 8); +++ break; +++ +++ case 32: +++ regcache_cooked_read_unsigned (regcache, SW_V0_REGNUM, &l); +++ read_memory (l, valbuf, 32); +++ break; +++ +++ default: +++ internal_error (__FILE__, __LINE__, +++ _("unknown floating point width")); +++ } +++ break; +++ +++ default: +++ /* Assume everything else degenerates to an integer. */ +++ regcache_cooked_read_unsigned (regcache, SW_V0_REGNUM, &l); +++ store_unsigned_integer (valbuf, TYPE_LENGTH (valtype), byte_order, l); +++ break; +++ } +++} +++ +++/* Insert the given value into REGCACHE as if it was being +++ returned by a function. */ +++ +++static void +++sw_64_store_return_value (struct type *valtype, struct regcache *regcache, +++ const gdb_byte *valbuf) +++{ +++ struct gdbarch *gdbarch = regcache->arch (); +++ gdb_byte raw_buffer[SW_REGISTER_SIZE]; +++ ULONGEST l; +++ +++ switch (valtype->code ()) +++ { +++ case TYPE_CODE_FLT: +++ switch (TYPE_LENGTH (valtype)) +++ { +++ case 4: +++ sw_64_lds (gdbarch, raw_buffer, valbuf); +++ regcache->cooked_write (SW_FP0_REGNUM, raw_buffer); +++ break; +++ +++ case 8: +++ regcache->cooked_write (SW_FP0_REGNUM, valbuf); +++ break; +++ +++ case 16: +++ /* FIXME: 128-bit long doubles are returned like structures: +++ by writing into indirect storage provided by the caller +++ as the first argument. */ +++ error (_("Cannot set a 128-bit long double return value.")); +++ +++ default: +++ internal_error (__FILE__, __LINE__, +++ _("unknown floating point width")); +++ } +++ break; +++ +++ case TYPE_CODE_COMPLEX: +++ switch (TYPE_LENGTH (valtype)) +++ { +++ case 8: +++ /* ??? This isn't correct wrt the ABI, but it's what GCC does. */ +++ regcache->cooked_write (SW_FP0_REGNUM, valbuf); +++ break; +++ +++ case 16: +++ regcache->cooked_write (SW_FP0_REGNUM, valbuf); +++ regcache->cooked_write (SW_FP0_REGNUM + 1, valbuf + 8); +++ break; +++ +++ case 32: +++ /* FIXME: 128-bit long doubles are returned like structures: +++ by writing into indirect storage provided by the caller +++ as the first argument. */ +++ error (_("Cannot set a 128-bit long double return value.")); +++ +++ default: +++ internal_error (__FILE__, __LINE__, +++ _("unknown floating point width")); +++ } +++ break; +++ +++ default: +++ /* Assume everything else degenerates to an integer. */ +++ /* 32-bit values must be sign-extended to 64 bits +++ even if the base data type is unsigned. */ +++ if (TYPE_LENGTH (valtype) == 4) +++ valtype = builtin_type (gdbarch)->builtin_int32; +++ l = unpack_long (valtype, valbuf); +++ regcache_cooked_write_unsigned (regcache, SW_V0_REGNUM, l); +++ break; +++ } +++} +++ +++static enum return_value_convention +++sw_64_return_value (struct gdbarch *gdbarch, struct value *function, +++ struct type *type, struct regcache *regcache, +++ gdb_byte *readbuf, const gdb_byte *writebuf) +++{ +++ enum type_code code = type->code (); +++ +++ if ((code == TYPE_CODE_STRUCT +++ || code == TYPE_CODE_UNION +++ || code == TYPE_CODE_ARRAY) +++ && gdbarch_tdep (gdbarch)->return_in_memory (type)) +++ { +++ if (readbuf) +++ { +++ ULONGEST addr; +++ regcache_raw_read_unsigned (regcache, SW_V0_REGNUM, &addr); +++ read_memory (addr, readbuf, TYPE_LENGTH (type)); +++ } +++ +++ return RETURN_VALUE_ABI_RETURNS_ADDRESS; +++ } +++ +++ if (readbuf) +++ sw_64_extract_return_value (type, regcache, readbuf); +++ if (writebuf) +++ sw_64_store_return_value (type, regcache, writebuf); +++ +++ return RETURN_VALUE_REGISTER_CONVENTION; +++} +++ +++static int +++sw_64_return_in_memory_always (struct type *type) +++{ +++ return 1; +++} +++ +++ +++constexpr gdb_byte sw_64_break_insn[] = { 0x80, 0, 0, 0 }; /* call_pal bpt */ +++ +++typedef BP_MANIPULATION (sw_64_break_insn) sw_64_breakpoint; +++ +++ +++/* This returns the PC of the first insn after the prologue. +++ If we can't find the prologue, then return 0. */ +++ +++CORE_ADDR +++sw_64_after_prologue (CORE_ADDR pc) +++{ +++ struct symtab_and_line sal; +++ CORE_ADDR func_addr, func_end; +++ +++ if (!find_pc_partial_function (pc, NULL, &func_addr, &func_end)) +++ return 0; +++ +++ sal = find_pc_line (func_addr, 0); +++ if (sal.end < func_end) +++ return sal.end; +++ +++ /* The line after the prologue is after the end of the function. In this +++ case, tell the caller to find the prologue the hard way. */ +++ return 0; +++} +++ +++/* Read an instruction from memory at PC, looking through breakpoints. */ +++ +++unsigned int +++sw_64_read_insn (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ gdb_byte buf[SW_INSN_SIZE]; +++ int res; +++ +++ res = target_read_memory (pc, buf, sizeof (buf)); +++ if (res != 0) +++ memory_error (TARGET_XFER_E_IO, pc); +++ return extract_unsigned_integer (buf, sizeof (buf), byte_order); +++} +++ +++/* To skip prologues, I use this predicate. Returns either PC itself +++ if the code at PC does not look like a function prologue; otherwise +++ returns an address that (if we're lucky) follows the prologue. If +++ LENIENT, then we must skip everything which is involved in setting +++ up the frame (it's OK to skip more, just so long as we don't skip +++ anything which might clobber the registers which are being saved. */ +++ +++static CORE_ADDR +++sw_64_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ unsigned long inst; +++ int offset; +++ CORE_ADDR post_prologue_pc; +++ gdb_byte buf[SW_INSN_SIZE]; +++ +++ /* Silently return the unaltered pc upon memory errors. +++ This could happen on OSF/1 if decode_line_1 tries to skip the +++ prologue for quickstarted shared library functions when the +++ shared library is not yet mapped in. +++ Reading target memory is slow over serial lines, so we perform +++ this check only if the target has shared libraries (which all +++ SW_64 targets do). */ +++ if (target_read_memory (pc, buf, sizeof (buf))) +++ return pc; +++ +++ /* See if we can determine the end of the prologue via the symbol table. +++ If so, then return either PC, or the PC after the prologue, whichever +++ is greater. */ +++ +++ post_prologue_pc = sw_64_after_prologue (pc); +++ if (post_prologue_pc != 0) +++ return std::max (pc, post_prologue_pc); +++ +++ /* Can't determine prologue from the symbol table, need to examine +++ instructions. */ +++ +++ /* Skip the typical prologue instructions. These are the stack adjustment +++ instruction and the instructions that save registers on the stack +++ or in the gcc frame. */ +++ for (offset = 0; offset < 100; offset += SW_INSN_SIZE) +++ { +++ inst = sw_64_read_insn (gdbarch, pc + offset); +++ +++ if ((inst & 0xffff0000) == 0xffbb0000) /* ldah $gp,n($t12) */ +++ continue; +++ if ((inst & 0xffff0000) == 0xfbbd0000) /* lda $gp,n($gp) */ +++ continue; +++ if ((inst & 0xffff0000) == 0x8f7d0000) /* lda $sp,n($sp) */ +++ continue; +++ if ((inst & 0xfffff000) == 0xfbde8000) /* subq $sp,n,$sp */ +++ continue; +++ +++ if ((inst & 0xffe01fff) == 0x43c0153e) /* stq reg,n($sp) */ +++ continue; +++ if ((inst & 0xfc1f0000) == 0xac1e0000) /* stl reg,n($sp) */ +++ continue; +++ +++ if (inst == 0x43de074f) /* bis sp,sp,fp */ +++ continue; +++ if (inst == 0x43fe074f) /* bis zero,sp,fp */ +++ continue; +++ +++ break; +++ } +++ return pc + offset; +++} +++ +++ +++#ifdef LHX20201026 +++static const int ldl_l_opcode = 0x2a; +++static const int ldq_l_opcode = 0x2b; +++static const int stl_c_opcode = 0x2e; +++static const int stq_c_opcode = 0x2f; +++#else +++static const int ldq_l_opcode = 0x23; //ldi +++static const int ldl_l_opcode = 0x3e; // ldl +++static const int stl_c_opcode = 0x2b; +++static const int stq_c_opcode = 0x2b; // stl +++#endif +++ +++/* Checks for an atomic sequence of instructions beginning with a LDL_L/LDQ_L +++ instruction and ending with a STL_C/STQ_C instruction. If such a sequence +++ is found, attempt to step through it. A breakpoint is placed at the end of +++ the sequence. */ +++ +++static std::vector +++sw_64_deal_with_atomic_sequence (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ CORE_ADDR breaks[2] = {CORE_ADDR_MAX, CORE_ADDR_MAX}; +++ CORE_ADDR loc = pc; +++ CORE_ADDR closing_insn; /* Instruction that closes the atomic sequence. */ +++ unsigned int insn = sw_64_read_insn (gdbarch, loc); +++ int insn_count; +++ int index; +++ int last_breakpoint = 0; /* Defaults to 0 (no breakpoints placed). */ +++ const int atomic_sequence_length = 16; /* Instruction sequence length. */ +++ int bc_insn_count = 0; /* Conditional branch instruction count. */ +++ unsigned int func_opcode = (insn>>12)&0xf; +++ /* Assume all atomic sequences start with a LDL_L/LDQ_L instruction. */ +++ if (!((INSN_OPCODE (insn) == 0x8 ) && +++ (func_opcode == 0 || func_opcode == 1))) +++ return {}; +++ +++ /* Assume that no atomic sequence is longer than "atomic_sequence_length" +++ instructions. */ +++ for (insn_count = 0; insn_count < atomic_sequence_length; ++insn_count) +++ { +++ loc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, loc); +++ +++ /* Assume that there is at most one branch in the atomic +++ sequence. If a branch is found, put a breakpoint in +++ its destination address. */ +++ if (INSN_OPCODE (insn) >= 0x30 && +++ INSN_OPCODE (insn) <= 0x3d) +++ { +++ int immediate = (insn & 0x001fffff) << 2; +++ +++ immediate = (immediate ^ 0x400000) - 0x400000; +++ +++ if (bc_insn_count >= 1) +++ return {}; /* More than one branch found, fallback +++ to the standard single-step code. */ +++ +++ breaks[1] = loc + SW_INSN_SIZE + immediate; +++ +++ bc_insn_count++; +++ last_breakpoint++; +++ } +++ +++ if (INSN_OPCODE (insn) >= 0x20 && INSN_OPCODE (insn) <= 0x2c) +++ { +++ loc -= SW_INSN_SIZE; +++ break; +++ } +++ func_opcode = (insn>>12)&0xf; +++ if (INSN_OPCODE (insn) == 0x6 && +++ func_opcode == 0) +++ break; +++ } +++#if 0 +++ /* Assume that the atomic sequence ends with a STL_C/STQ_C instruction. */ +++ if (INSN_OPCODE (insn) != stl_c_opcode +++ && INSN_OPCODE (insn) != stq_c_opcode) +++ return {}; +++#endif +++ closing_insn = loc; +++ loc += SW_INSN_SIZE; +++ +++ /* Insert a breakpoint right after the end of the atomic sequence. */ +++ breaks[0] = loc; +++ +++ /* Check for duplicated breakpoints. Check also for a breakpoint +++ placed (branch instruction's destination) anywhere in sequence. */ +++ if (last_breakpoint +++ && (breaks[1] == breaks[0] +++ || (breaks[1] >= pc && breaks[1] <= closing_insn))) +++ last_breakpoint = 0; +++ +++ std::vector next_pcs; +++ +++ for (index = 0; index <= last_breakpoint; index++) +++ next_pcs.push_back (breaks[index]); +++ +++ return next_pcs; +++} +++ +++#ifndef XWB20200903 +++static void +++sw_64_skip_permanent_breakpoint (struct regcache *regcache) +++{ +++ CORE_ADDR current_pc = regcache_read_pc (regcache); +++ +++ current_pc += 4; +++ regcache_write_pc (regcache, current_pc); } +++#endif +++ +++ +++/* Figure out where the longjmp will land. +++ We expect the first arg to be a pointer to the jmp_buf structure from +++ which we extract the PC (JB_PC) that we will land at. The PC is copied +++ into the "pc". This routine returns true on success. */ +++ +++static int +++sw_64_get_longjmp_target (struct frame_info *frame, CORE_ADDR *pc) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (frame); +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); +++ CORE_ADDR jb_addr; +++ gdb_byte raw_buffer[SW_REGISTER_SIZE]; +++ +++ jb_addr = get_frame_register_unsigned (frame, SW_A0_REGNUM); +++ +++ if (target_read_memory (jb_addr + (tdep->jb_pc * tdep->jb_elt_size), +++ raw_buffer, tdep->jb_elt_size)) +++ return 0; +++ +++ *pc = extract_unsigned_integer (raw_buffer, tdep->jb_elt_size, byte_order); +++ return 1; +++} +++ +++ +++/* Frame unwinder for signal trampolines. We use sw_64 tdep bits that +++ describe the location and shape of the sigcontext structure. After +++ that, all registers are in memory, so it's easy. */ +++/* ??? Shouldn't we be able to do this generically, rather than with +++ OSABI data specific to SW_64? */ +++ +++struct sw_64_sigtramp_unwind_cache +++{ +++ CORE_ADDR sigcontext_addr; +++}; +++ +++static struct sw_64_sigtramp_unwind_cache * +++sw_64_sigtramp_frame_unwind_cache (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_sigtramp_unwind_cache *info; +++ struct gdbarch_tdep *tdep; +++ +++ if (*this_prologue_cache) +++ return (struct sw_64_sigtramp_unwind_cache *) *this_prologue_cache; +++ +++ info = FRAME_OBSTACK_ZALLOC (struct sw_64_sigtramp_unwind_cache); +++ *this_prologue_cache = info; +++ +++ tdep = gdbarch_tdep (get_frame_arch (this_frame)); +++ info->sigcontext_addr = tdep->sigcontext_addr (this_frame); +++ +++ return info; +++} +++ +++/* Return the address of REGNUM in a sigtramp frame. Since this is +++ all arithmetic, it doesn't seem worthwhile to cache it. */ +++ +++static CORE_ADDR +++sw_64_sigtramp_register_address (struct gdbarch *gdbarch, +++ CORE_ADDR sigcontext_addr, int regnum) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ +++ if (regnum >= 0 && regnum < 32) +++ return sigcontext_addr + tdep->sc_regs_offset + regnum * 8; +++ else if (regnum >= SW_FP0_REGNUM && regnum < SW_FP0_REGNUM + 32) +++ return sigcontext_addr + tdep->sc_fpregs_offset + regnum * 8; +++ else if (regnum == SW_PC_REGNUM) +++ return sigcontext_addr + tdep->sc_pc_offset; +++ +++ return 0; +++} +++ +++/* Given a GDB frame, determine the address of the calling function's +++ frame. This will be used to create a new GDB frame struct. */ +++ +++static void +++sw_64_sigtramp_frame_this_id (struct frame_info *this_frame, +++ void **this_prologue_cache, +++ struct frame_id *this_id) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (this_frame); +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ struct sw_64_sigtramp_unwind_cache *info +++ = sw_64_sigtramp_frame_unwind_cache (this_frame, this_prologue_cache); +++ CORE_ADDR stack_addr, code_addr; +++ +++ /* If the OSABI couldn't locate the sigcontext, give up. */ +++ if (info->sigcontext_addr == 0) +++ return; +++ +++ /* If we have dynamic signal trampolines, find their start. +++ If we do not, then we must assume there is a symbol record +++ that can provide the start address. */ +++ if (tdep->dynamic_sigtramp_offset) +++ { +++ int offset; +++ code_addr = get_frame_pc (this_frame); +++ offset = tdep->dynamic_sigtramp_offset (gdbarch, code_addr); +++ if (offset >= 0) +++ code_addr -= offset; +++ else +++ code_addr = 0; +++ } +++ else +++ code_addr = get_frame_func (this_frame); +++ +++ /* The stack address is trivially read from the sigcontext. */ +++ stack_addr = sw_64_sigtramp_register_address (gdbarch, info->sigcontext_addr, +++ SW_SP_REGNUM); +++ stack_addr = get_frame_memory_unsigned (this_frame, stack_addr, +++ SW_REGISTER_SIZE); +++ +++ *this_id = frame_id_build (stack_addr, code_addr); +++} +++ +++/* Retrieve the value of REGNUM in FRAME. Don't give up! */ +++ +++static struct value * +++sw_64_sigtramp_frame_prev_register (struct frame_info *this_frame, +++ void **this_prologue_cache, int regnum) +++{ +++ struct sw_64_sigtramp_unwind_cache *info +++ = sw_64_sigtramp_frame_unwind_cache (this_frame, this_prologue_cache); +++ CORE_ADDR addr; +++ +++ if (info->sigcontext_addr != 0) +++ { +++ /* All integer and fp registers are stored in memory. */ +++ addr = sw_64_sigtramp_register_address (get_frame_arch (this_frame), +++ info->sigcontext_addr, regnum); +++ if (addr != 0) +++ return frame_unwind_got_memory (this_frame, regnum, addr); +++ } +++ +++ /* This extra register may actually be in the sigcontext, but our +++ current description of it in sw_64_sigtramp_frame_unwind_cache +++ doesn't include it. Too bad. Fall back on whatever's in the +++ outer frame. */ +++ return frame_unwind_got_register (this_frame, regnum, regnum); +++} +++ +++static int +++sw_64_sigtramp_frame_sniffer (const struct frame_unwind *self, +++ struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (this_frame); +++ CORE_ADDR pc = get_frame_pc (this_frame); +++ const char *name; +++ +++ /* NOTE: cagney/2004-04-30: Do not copy/clone this code. Instead +++ look at tramp-frame.h and other simpler per-architecture +++ sigtramp unwinders. */ +++ +++ /* We shouldn't even bother to try if the OSABI didn't register a +++ sigcontext_addr handler or pc_in_sigtramp handler. */ +++ if (gdbarch_tdep (gdbarch)->sigcontext_addr == NULL) +++ return 0; +++ if (gdbarch_tdep (gdbarch)->pc_in_sigtramp == NULL) +++ return 0; +++ +++ /* Otherwise we should be in a signal frame. */ +++ find_pc_partial_function (pc, &name, NULL, NULL); +++ if (gdbarch_tdep (gdbarch)->pc_in_sigtramp (gdbarch, pc, name)) +++ return 1; +++ +++ return 0; +++} +++ +++static const struct frame_unwind sw_64_sigtramp_frame_unwind = { +++ SIGTRAMP_FRAME, +++ default_frame_unwind_stop_reason, +++ sw_64_sigtramp_frame_this_id, +++ sw_64_sigtramp_frame_prev_register, +++ NULL, +++ sw_64_sigtramp_frame_sniffer +++}; +++ +++ +++ +++/* Heuristic_proc_start may hunt through the text section for a long +++ time across a 2400 baud serial line. Allows the user to limit this +++ search. */ +++#ifndef _SW64_ +++static int heuristic_fence_post = 40; +++#else +++static int heuristic_fence_post = 0; +++#endif +++/* Attempt to locate the start of the function containing PC. We assume that +++ the previous function ends with an about_to_return insn. Not foolproof by +++ any means, since gcc is happy to put the epilogue in the middle of a +++ function. But we're guessing anyway... */ +++ +++static CORE_ADDR +++sw_64_heuristic_proc_start (struct gdbarch *gdbarch, CORE_ADDR pc) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); +++ CORE_ADDR last_non_nop = pc; +++ CORE_ADDR fence = pc - heuristic_fence_post; +++ CORE_ADDR orig_pc = pc; +++ CORE_ADDR func; +++ struct inferior *inf; +++ +++ if (pc == 0) +++ return 0; +++ +++ /* First see if we can find the start of the function from minimal +++ symbol information. This can succeed with a binary that doesn't +++ have debug info, but hasn't been stripped. */ +++ func = get_pc_function_start (pc); +++ if (func) +++ return func; +++ +++ if (heuristic_fence_post == -1 +++ || fence < tdep->vm_min_address) +++ fence = tdep->vm_min_address; +++ +++ /* Search back for previous return; also stop at a 0, which might be +++ seen for instance before the start of a code section. Don't include +++ nops, since this usually indicates padding between functions. */ +++#ifdef LHX20201102 +++ i = 0; +++ insns = sw_64_read_insns (gdbarch, pc, heuristic_fence_post>>2) +++ for (pc -= SW_INSN_SIZE; pc >= fence; i++, pc -= SW_INSN_SIZE) +++ { +++ unsigned int insn = insns[i]; +++ /* The above is unreliable, sometime other unexpacted insn ex ist. */ +++ /* ldih gp,17(t12) ;0xffbb0011 +++ * ldi gp,18728(gp) ;0xfbbd4928 */ +++ /* swxrun */ +++ if ((insn & 0xffff0000) == 0xfbbd0000) +++ flag = 1; +++ else +++ if ((insn & 0xffff0000) == 0xffbb0000) +++ { +++ if ((flag == 1) && +++ ((last_non_nop-SW_INSN_SIZE) == pc)) +++ return pc; +++ } +++ switch (insn) +++ { +++ case 0: /* invalid insn */ +++// case 0x6bfa8001: /* ret $31,($26),1 */ +++ case 0x07da6001: /* slave ret */ +++ case 0x0bfa0001: /* mater ret */ +++ //debug("ret before proc_start"); +++ return last_non_nop; +++ +++ case 0x2ffe0000: /* unop: ldq_u $31,0($30) */ +++ case 0x47ff041f: /* nop: bis $31,$31,$31 */ +++ break; +++ +++ default: +++ last_non_nop = pc; +++ break; +++ } +++ } +++ XDELETEVEC(insns); +++#else +++ for (pc -= SW_INSN_SIZE; pc >= fence; pc -= SW_INSN_SIZE) +++ { +++ unsigned int insn = sw_64_read_insn (gdbarch, pc); +++ +++ switch (insn) +++ { +++ case 0: /* invalid insn */ +++ case 0x6bfa8001: /* ret $31,($26),1 */ +++ case 0x0bfa0001: /* mater ret */ +++ return last_non_nop; +++ +++ case 0x2ffe0000: /* unop: ldq_u $31,0($30) */ +++ case 0x47ff041f: /* nop: bis $31,$31,$31 */ +++ break; +++ +++ default: +++ last_non_nop = pc; +++ break; +++ } +++ } +++#endif +++ inf = current_inferior (); +++ +++ /* It's not clear to me why we reach this point when stopping quietly, +++ but with this test, at least we don't print out warnings for every +++ child forked (eg, on decstation). 22apr93 rich@cygnus.com. */ +++ if (inf->control.stop_soon == NO_STOP_QUIETLY) +++ { +++ static int blurb_printed = 0; +++ +++ if (fence == tdep->vm_min_address) +++ warning (_("Hit beginning of text section without finding \ +++enclosing function for address %s"), paddress (gdbarch, orig_pc)); +++ else +++ warning (_("Hit heuristic-fence-post without finding \ +++enclosing function for address %s"), paddress (gdbarch, orig_pc)); +++ +++ if (!blurb_printed) +++ { +++ printf_filtered (_("\ +++This warning occurs if you are debugging a function without any symbols\n\ +++(for example, in a stripped executable). In that case, you may wish to\n\ +++increase the size of the search with the `set heuristic-fence-post' command.\n\ +++\n\ +++Otherwise, you told GDB there was a function where there isn't one, or\n\ +++(more likely) you have encountered a bug in GDB.\n")); +++ blurb_printed = 1; +++ } +++ } +++ +++ return 0; +++} +++ +++ +++/* Fallback sw_64 frame unwinder. Uses instruction scanning and knows +++ something about the traditional layout of sw_64 stack frames. */ +++ +++struct sw_64_heuristic_unwind_cache +++{ +++ CORE_ADDR vfp; +++ CORE_ADDR start_pc; +++ struct trad_frame_saved_reg *saved_regs; +++ int return_reg; +++}; +++ +++/* If a probing loop sequence starts at PC, simulate it and compute +++ FRAME_SIZE and PC after its execution. Otherwise, return with PC and +++ FRAME_SIZE unchanged. */ +++ +++static void +++sw_64_heuristic_analyze_probing_loop (struct gdbarch *gdbarch, CORE_ADDR *pc, +++ int *frame_size) +++{ +++ CORE_ADDR cur_pc = *pc; +++ int cur_frame_size = *frame_size; +++ int nb_of_iterations, reg_index, reg_probe; +++ unsigned int insn; +++ +++ /* The following pattern is recognized as a probing loop: +++ +++ lda REG_INDEX,NB_OF_ITERATIONS +++ lda REG_PROBE,(sp) +++ +++ LOOP_START: +++ stq zero,(REG_PROBE) +++ subq REG_INDEX,0x1,REG_INDEX +++ lda REG_PROBE,(REG_PROBE) +++ bne REG_INDEX, LOOP_START +++ +++ lda sp,(REG_PROBE) +++ +++ If anything different is found, the function returns without +++ changing PC and FRAME_SIZE. Otherwise, PC will point immediately +++ after this sequence, and FRAME_SIZE will be updated. */ +++ +++ /* lda REG_INDEX,NB_OF_ITERATIONS */ +++ +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != lda_opcode) +++ return; +++ reg_index = MEM_RA (insn); +++ nb_of_iterations = MEM_DISP (insn); +++ +++ /* lda REG_PROBE,(sp) */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != lda_opcode +++ || MEM_RB (insn) != SW_SP_REGNUM) +++ return; +++ reg_probe = MEM_RA (insn); +++ cur_frame_size -= MEM_DISP (insn); +++ +++ /* stq zero,(REG_PROBE) */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != stq_opcode +++ || MEM_RA (insn) != 0x1f +++ || MEM_RB (insn) != reg_probe) +++ return; +++ +++ /* subq REG_INDEX,0x1,REG_INDEX */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != subq_opcode +++ || !OPR_HAS_IMMEDIATE (insn) +++ || OPR_FUNCTION (insn) != subq_function +++ || OPR_LIT(insn) != 1 +++ || OPR_RA (insn) != reg_index +++ || OPR_RC (insn) != reg_index) +++ return; +++ +++ /* lda REG_PROBE,(REG_PROBE) */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != lda_opcode +++ || MEM_RA (insn) != reg_probe +++ || MEM_RB (insn) != reg_probe) +++ return; +++ cur_frame_size -= MEM_DISP (insn) * nb_of_iterations; +++ +++ /* bne REG_INDEX, LOOP_START */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != bne_opcode +++ || MEM_RA (insn) != reg_index) +++ return; +++ +++ /* lda sp,(REG_PROBE) */ +++ +++ cur_pc += SW_INSN_SIZE; +++ insn = sw_64_read_insn (gdbarch, cur_pc); +++ if (INSN_OPCODE (insn) != lda_opcode +++ || MEM_RA (insn) != SW_SP_REGNUM +++ || MEM_RB (insn) != reg_probe) +++ return; +++ cur_frame_size -= MEM_DISP (insn); +++ +++ *pc = cur_pc; +++ *frame_size = cur_frame_size; +++} +++ +++static struct sw_64_heuristic_unwind_cache * +++sw_64_heuristic_frame_unwind_cache (struct frame_info *this_frame, +++ void **this_prologue_cache, +++ CORE_ADDR start_pc) +++{ +++ struct gdbarch *gdbarch = get_frame_arch (this_frame); +++ struct sw_64_heuristic_unwind_cache *info; +++ ULONGEST val; +++ CORE_ADDR limit_pc, cur_pc; +++ int frame_reg, frame_size, return_reg, reg; +++ +++ if (*this_prologue_cache) +++ return (struct sw_64_heuristic_unwind_cache *) *this_prologue_cache; +++ +++ info = FRAME_OBSTACK_ZALLOC (struct sw_64_heuristic_unwind_cache); +++ *this_prologue_cache = info; +++ info->saved_regs = trad_frame_alloc_saved_regs (this_frame); +++ +++ limit_pc = get_frame_pc (this_frame); +++ if (start_pc == 0) +++ start_pc = sw_64_heuristic_proc_start (gdbarch, limit_pc); +++ info->start_pc = start_pc; +++ +++ frame_reg = SW_SP_REGNUM; +++ frame_size = 0; +++ return_reg = -1; +++ +++ /* If we've identified a likely place to start, do code scanning. */ +++ if (start_pc != 0) +++ { +++ /* Limit the forward search to 50 instructions. */ +++ if (start_pc + 200 < limit_pc) +++ limit_pc = start_pc + 200; +++ +++ for (cur_pc = start_pc; cur_pc < limit_pc; cur_pc += SW_INSN_SIZE) +++ { +++ unsigned int word = sw_64_read_insn (gdbarch, cur_pc); +++ +++ if ((word & 0xffff8000) == 0xfbde8000) /* lda $sp,n($sp) */ +++ { +++ if (word & 0x8000) +++ { +++ /* Consider only the first stack allocation instruction +++ to contain the static size of the frame. */ +++ if (frame_size == 0) +++ frame_size = (-word) & 0xffff; +++ } +++ else +++ { +++ /* Exit loop if a positive stack adjustment is found, which +++ usually means that the stack cleanup code in the function +++ epilogue is reached. */ +++ break; +++ } +++ } +++ else if ((word & 0xfc1f8000) == 0xac1e0000 || (word & 0xfc1f8000) ==0xac0f0000 ) /* stq reg,n($sp) */ +++ { +++ reg = (word & 0x03e00000) >> 21; +++ +++ /* Ignore this instruction if we have already encountered +++ an instruction saving the same register earlier in the +++ function code. The current instruction does not tell +++ us where the original value upon function entry is saved. +++ All it says is that the function we are scanning reused +++ that register for some computation of its own, and is now +++ saving its result. */ +++ if (trad_frame_addr_p(info->saved_regs, reg)) +++ continue; +++ +++ if (reg == 31) +++ continue; +++ +++ /* Do not compute the address where the register was saved yet, +++ because we don't know yet if the offset will need to be +++ relative to $sp or $fp (we can not compute the address +++ relative to $sp if $sp is updated during the execution of +++ the current subroutine, for instance when doing some alloca). +++ So just store the offset for the moment, and compute the +++ address later when we know whether this frame has a frame +++ pointer or not. */ +++ /* Hack: temporarily add one, so that the offset is non-zero +++ and we can tell which registers have save offsets below. */ +++ info->saved_regs[reg].addr = (word & 0xffff) + 1; +++ +++ /* Starting with OSF/1-3.2C, the system libraries are shipped +++ without local symbols, but they still contain procedure +++ descriptors without a symbol reference. GDB is currently +++ unable to find these procedure descriptors and uses +++ heuristic_proc_desc instead. +++ As some low level compiler support routines (__div*, __add*) +++ use a non-standard return address register, we have to +++ add some heuristics to determine the return address register, +++ or stepping over these routines will fail. +++ Usually the return address register is the first register +++ saved on the stack, but assembler optimization might +++ rearrange the register saves. +++ So we recognize only a few registers (t7, t9, ra) within +++ the procedure prologue as valid return address registers. +++ If we encounter a return instruction, we extract the +++ return address register from it. +++ +++ FIXME: Rewriting GDB to access the procedure descriptors, +++ e.g. via the minimal symbol table, might obviate this +++ hack. */ +++ if (return_reg == -1 +++ && cur_pc < (start_pc + 80) +++ && (reg == SW_T7_REGNUM +++ || reg == SW_T9_REGNUM +++ || reg == SW_RA_REGNUM)) +++ return_reg = reg; +++ } +++ else if ((word & 0xffe0ffff) == 0x6be08001) /* ret zero,reg,1 */ +++ return_reg = (word >> 16) & 0x1f; +++#ifndef XWB20200903 +++ else if (word == 0x43de074f) /* bis sp,sp,fp */ +++ frame_reg = SW_GCC_FP_REGNUM; +++ else if (word == 0x43fe074f) /* bis zero,sp,fp */ +++ frame_reg = SW_GCC_FP_REGNUM; +++#else +++ else if (word == 0x47de040f) /* bis sp,sp,fp */ +++ frame_reg = SW_GCC_FP_REGNUM; +++ else if (word == 0x47fe040f) /* bis zero,sp,fp */ +++ frame_reg = SW_GCC_FP_REGNUM; +++#endif +++ sw_64_heuristic_analyze_probing_loop (gdbarch, &cur_pc, &frame_size); +++ } +++ +++ /* If we haven't found a valid return address register yet, keep +++ searching in the procedure prologue. */ +++ if (return_reg == -1) +++ { +++ while (cur_pc < (limit_pc + 80) && cur_pc < (start_pc + 80)) +++ { +++ unsigned int word = sw_64_read_insn (gdbarch, cur_pc); +++ +++ +++#ifndef XWB20200903 +++ if ((word & 0xfc1f0000) ==0xac1e0000 /* stl reg,n($sp) */ +++ || (word & 0xfc1f0000) == 0xac0f0000 /* stl reg,n($fp) */ +++ || (word & 0xfc1f0000) == 0xa80f0000 /* stw reg,n($fp) */ +++ || (word & 0xfc1f0000) == 0xa81e0000) /* stw reg,n($sp) */ +++#else +++ if ((word & 0xfc1f0000) == 0xb41e0000) /* stq reg,n($sp) */ +++#endif +++ +++ { +++ reg = (word & 0x03e00000) >> 21; +++ if (reg == SW_T7_REGNUM +++ || reg == SW_T9_REGNUM +++ || reg == SW_RA_REGNUM) +++ { +++ return_reg = reg; +++ break; +++ } +++ } +++#ifndef XWB20200903 +++ else if ((word & 0xffe0ffff) == 0x0be00001) /* ret zero,reg,1 */ +++#else +++ else if ((word & 0xffe0ffff) == 0x6be08001) /* ret zero,reg,1 */ +++#endif +++ +++ { +++ return_reg = (word >> 16) & 0x1f; +++ break; +++ } +++ +++ cur_pc += SW_INSN_SIZE; +++ } +++ } +++ } +++ +++ /* Failing that, do default to the customary RA. */ +++ if (return_reg == -1) +++ return_reg = SW_RA_REGNUM; +++ info->return_reg = return_reg; +++ +++ val = get_frame_register_unsigned (this_frame, frame_reg); +++ info->vfp = val + frame_size; +++ +++ /* Convert offsets to absolute addresses. See above about adding +++ one to the offsets to make all detected offsets non-zero. */ +++ for (reg = 0; reg < SW_NUM_REGS; ++reg) +++ if (trad_frame_addr_p(info->saved_regs, reg)) +++ info->saved_regs[reg].addr += val - 1; +++ +++ /* The stack pointer of the previous frame is computed by popping +++ the current stack frame. */ +++ if (!trad_frame_addr_p (info->saved_regs, SW_SP_REGNUM)) +++ trad_frame_set_value (info->saved_regs, SW_SP_REGNUM, info->vfp); +++ +++#ifndef XWB20200903 +++ if (frame_reg != SW_SP_REGNUM ) +++ info->saved_regs[SW_SP_REGNUM].addr = info->saved_regs[frame_reg].addr; +++#endif +++ return info; +++} +++ +++/* Given a GDB frame, determine the address of the calling function's +++ frame. This will be used to create a new GDB frame struct. */ +++ +++static void +++sw_64_heuristic_frame_this_id (struct frame_info *this_frame, +++ void **this_prologue_cache, +++ struct frame_id *this_id) +++{ +++ struct sw_64_heuristic_unwind_cache *info +++ = sw_64_heuristic_frame_unwind_cache (this_frame, this_prologue_cache, 0); +++ +++ *this_id = frame_id_build (info->vfp, info->start_pc); +++} +++ +++/* Retrieve the value of REGNUM in FRAME. Don't give up! */ +++ +++static struct value * +++sw_64_heuristic_frame_prev_register (struct frame_info *this_frame, +++ void **this_prologue_cache, int regnum) +++{ +++ struct sw_64_heuristic_unwind_cache *info +++ = sw_64_heuristic_frame_unwind_cache (this_frame, this_prologue_cache, 0); +++ +++ /* The PC of the previous frame is stored in the link register of +++ the current frame. Frob regnum so that we pull the value from +++ the correct place. */ +++ if (regnum == SW_PC_REGNUM) +++ regnum = info->return_reg; +++ +++ return trad_frame_get_prev_register (this_frame, info->saved_regs, regnum); +++} +++ +++static const struct frame_unwind sw_64_heuristic_frame_unwind = { +++ NORMAL_FRAME, +++ default_frame_unwind_stop_reason, +++ sw_64_heuristic_frame_this_id, +++ sw_64_heuristic_frame_prev_register, +++ NULL, +++ default_frame_sniffer +++}; +++ +++static CORE_ADDR +++sw_64_heuristic_frame_base_address (struct frame_info *this_frame, +++ void **this_prologue_cache) +++{ +++ struct sw_64_heuristic_unwind_cache *info +++ = sw_64_heuristic_frame_unwind_cache (this_frame, this_prologue_cache, 0); +++ +++ return info->vfp; +++} +++ +++static const struct frame_base sw_64_heuristic_frame_base = { +++ &sw_64_heuristic_frame_unwind, +++ sw_64_heuristic_frame_base_address, +++ sw_64_heuristic_frame_base_address, +++ sw_64_heuristic_frame_base_address +++}; +++ +++/* Just like reinit_frame_cache, but with the right arguments to be +++ callable as an sfunc. Used by the "set heuristic-fence-post" command. */ +++ +++static void +++reinit_frame_cache_sfunc (const char *args, +++ int from_tty, struct cmd_list_element *c) +++{ +++ reinit_frame_cache (); +++} +++ +++/* Helper routines for sw_64*-nat.c files to move register sets to and +++ from core files. The UNIQUE pointer is allowed to be NULL, as most +++ targets don't supply this value in their core files. */ +++ +++void +++sw_64_supply_int_regs (struct regcache *regcache, int regno, +++ const void *r0_r30, const void *pc, const void *unique) +++{ +++ const gdb_byte *regs = (const gdb_byte *) r0_r30; +++ int i; +++ +++ for (i = 0; i < 31; ++i) +++ if (regno == i || regno == -1) +++ regcache->raw_supply (i, regs + i * 8); +++ +++ if (regno == SW_ZERO_REGNUM || regno == -1) +++ { +++ const gdb_byte zero[8] = { 0 }; +++ +++ regcache->raw_supply (SW_ZERO_REGNUM, zero); +++ } +++ +++ if (regno == SW_PC_REGNUM || regno == -1) +++ regcache->raw_supply (SW_PC_REGNUM, pc); +++ +++ if (regno == SW_UNIQUE_REGNUM || regno == -1) +++ regcache->raw_supply (SW_UNIQUE_REGNUM, unique); +++} +++ +++void +++sw_64_fill_int_regs (const struct regcache *regcache, +++ int regno, void *r0_r30, void *pc, void *unique) +++{ +++ gdb_byte *regs = (gdb_byte *) r0_r30; +++ int i; +++ +++ for (i = 0; i < 31; ++i) +++ if (regno == i || regno == -1) +++ regcache->raw_collect (i, regs + i * 8); +++ +++ if (regno == SW_PC_REGNUM || regno == -1) +++ regcache->raw_collect (SW_PC_REGNUM, pc); +++ +++ if (unique && (regno == SW_UNIQUE_REGNUM || regno == -1)) +++ regcache->raw_collect (SW_UNIQUE_REGNUM, unique); +++} +++ +++void +++sw_64_supply_fp_regs (struct regcache *regcache, int regno, +++ const void *f0_f30, const void *fpcr) +++{ +++ const gdb_byte *regs = (const gdb_byte *) f0_f30; +++ int i; +++ +++ for (i = SW_FP0_REGNUM; i < SW_FP0_REGNUM + 31; ++i) +++ if (regno == i || regno == -1) +++ regcache->raw_supply (i, regs + (i - SW_FP0_REGNUM) * 8); +++ +++ if (regno == SW_FPCR_REGNUM || regno == -1) +++ regcache->raw_supply (SW_FPCR_REGNUM, fpcr); +++} +++ +++void +++sw_64_fill_fp_regs (const struct regcache *regcache, +++ int regno, void *f0_f30, void *fpcr) +++{ +++ gdb_byte *regs = (gdb_byte *) f0_f30; +++ int i; +++ +++ for (i = SW_FP0_REGNUM; i < SW_FP0_REGNUM + 31; ++i) +++ if (regno == i || regno == -1) +++ regcache->raw_collect (i, regs + (i - SW_FP0_REGNUM) * 8); +++ +++ if (regno == SW_FPCR_REGNUM || regno == -1) +++ regcache->raw_collect (SW_FPCR_REGNUM, fpcr); +++} +++ +++ +++ +++/* Return nonzero if the G_floating register value in REG is equal to +++ zero for FP control instructions. */ +++ +++static int +++fp_register_zero_p (LONGEST reg) +++{ +++ /* Check that all bits except the sign bit are zero. */ +++ const LONGEST zero_mask = ((LONGEST) 1 << 63) ^ -1; +++ +++ return ((reg & zero_mask) == 0); +++} +++ +++/* Return the value of the sign bit for the G_floating register +++ value held in REG. */ +++ +++static int +++fp_register_sign_bit (LONGEST reg) +++{ +++ const LONGEST sign_mask = (LONGEST) 1 << 63; +++ +++ return ((reg & sign_mask) != 0); +++} +++ +++/* sw_64_software_single_step() is called just before we want to resume +++ the inferior, if we want to single-step it but there is no hardware +++ or kernel single-step support (NetBSD on SW_64, for example). We find +++ the target of the coming instruction and breakpoint it. */ +++ +++static CORE_ADDR +++sw_64_next_pc (struct regcache *regcache, CORE_ADDR pc) +++{ +++ struct gdbarch *gdbarch = regcache->arch (); +++ unsigned int insn; +++ unsigned int op; +++ int regno; +++ int offset; +++ LONGEST rav; +++ +++ insn = sw_64_read_insn (gdbarch, pc); +++ +++ /* Opcode is top 6 bits. */ +++ op = (insn >> 26) & 0x3f; +++ +++#if 1 +++ +++ switch (op) { +++ case 0x1: +++ case 0x2: +++ case 0x3: +++ return (regcache_raw_get_unsigned (regcache, (insn >> 16) & 0x1f) & ~3); +++ case 0x4: /* BR */ +++ case 0x5: /* BSR */ +++#else +++ if (op == 0x1a) +++ { +++ /* Jump format: target PC is: +++ RB & ~3 */ +++ return (regcache_raw_get_unsigned (regcache, (insn >> 16) & 0x1f) & ~3); +++ } +++ +++ if ((op & 0x30) == 0x30) +++ { +++ /* Branch format: target PC is: +++ (new PC) + (4 * sext(displacement)) */ +++ if (op == 0x30 /* BR */ +++ || op == 0x34) /* BSR */ +++ { +++#endif +++ +++branch_taken: +++ offset = (insn & 0x001fffff); +++ if (offset & 0x00100000) +++ offset |= 0xffe00000; +++ offset *= SW_INSN_SIZE; +++ return (pc + SW_INSN_SIZE + offset); +++ } +++#ifndef XWB20200903 +++ if ((op & 0x30) == 0x30){ +++#endif +++ regno = (insn >> 21) & 0x1f; +++ switch (op) +++ { +++ case 0x38: /* FBEQ */ +++ case 0x39: /* FBGE */ +++ case 0x3a: /* FBGT */ +++ case 0x3b: /* FBLE */ +++ case 0x3c: /* FBLT */ +++ case 0x3d: /* FBNE */ +++ regno += gdbarch_fp0_regnum (gdbarch); +++ } +++ +++ rav = regcache_raw_get_signed (regcache, regno); +++ switch (op) +++ { +++ case 0x36: /* BLBC */ +++ if ((rav & 1) == 0) +++ goto branch_taken; +++ break; +++ case 0x37: /* BLBS */ +++ if (rav & 1) +++ goto branch_taken; +++ break; +++ case 0x30: /* BEQ */ +++ if (rav == 0) +++ goto branch_taken; +++ break; +++ case 0x31: /* BNE */ +++ if (rav != 0) +++ goto branch_taken; +++ break; +++ case 0x32: /* BLT */ +++ if (rav < 0) +++ goto branch_taken; +++ break; +++ case 0x33: /* BLE */ +++ if (rav <= 0) +++ goto branch_taken; +++ break; +++ case 0x34: /* BGT */ +++ if (rav > 0) +++ goto branch_taken; +++ break; +++ case 0x35: /* BGE */ +++ if (rav >= 0) +++ goto branch_taken; +++ break; +++ +++ /* Floating point branches. */ +++ +++ case 0x38: /* FBEQ */ +++ if (fp_register_zero_p (rav)) +++ goto branch_taken; +++ break; +++ case 0x3d: /* FBGE */ +++ if (fp_register_sign_bit (rav) == 0 || fp_register_zero_p (rav)) +++ goto branch_taken; +++ break; +++ case 0x3c: /* FBGT */ +++ if (fp_register_sign_bit (rav) == 0 && ! fp_register_zero_p (rav)) +++ goto branch_taken; +++ break; +++ case 0x3b: /* FBLE */ +++ if (fp_register_sign_bit (rav) == 1 || fp_register_zero_p (rav)) +++ goto branch_taken; +++ break; +++ case 0x3a: /* FBLT */ +++ if (fp_register_sign_bit (rav) == 1 && ! fp_register_zero_p (rav)) +++ goto branch_taken; +++ break; +++ case 0x39: /* FBNE */ +++#ifndef LHX20201026 +++ if (! fp_register_zero_p (rav)) +++#else +++ if ( fp_register_zero_p (rav)) +++#endif +++ goto branch_taken; +++ break; +++ } +++#ifndef _SW64_ +++ } +++#endif +++ +++ /* Not a branch or branch not taken; target PC is: +++ pc + 4 */ +++ return (pc + SW_INSN_SIZE); +++ +++} +++ +++ +++std::vector +++sw_64_software_single_step (struct regcache *regcache) +++{ +++ struct gdbarch *gdbarch = regcache->arch (); +++ +++ CORE_ADDR pc = regcache_read_pc (regcache); +++ +++ std::vector next_pcs +++ = sw_64_deal_with_atomic_sequence (gdbarch, pc); +++ if (!next_pcs.empty ()) +++ return next_pcs; +++ +++ CORE_ADDR next_pc = sw_64_next_pc (regcache, pc); +++ return {next_pc}; +++} +++ +++ +++/* Initialize the current architecture based on INFO. If possible, re-use an +++ architecture from ARCHES, which is a list of architectures already created +++ during this debugging session. +++ +++ Called e.g. at program startup, when reading a core file, and when reading +++ a binary file. */ +++ +++static struct gdbarch * +++sw_64_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches) +++{ +++ struct gdbarch_tdep *tdep; +++ struct gdbarch *gdbarch; +++ +++ /* Find a candidate among extant architectures. */ +++ arches = gdbarch_list_lookup_by_info (arches, &info); +++ if (arches != NULL) +++ return arches->gdbarch; +++ +++ tdep = XCNEW (struct gdbarch_tdep); +++ gdbarch = gdbarch_alloc (&info, tdep); +++ +++ /* Lowest text address. This is used by heuristic_proc_start() +++ to decide when to stop looking. */ +++ tdep->vm_min_address = (CORE_ADDR) 0x120000000LL; +++ +++ tdep->dynamic_sigtramp_offset = NULL; +++ tdep->sigcontext_addr = NULL; +++ tdep->sc_pc_offset = 2 * 8; +++ tdep->sc_regs_offset = 4 * 8; +++ tdep->sc_fpregs_offset = tdep->sc_regs_offset + 32 * 8 + 8; +++ +++ tdep->jb_pc = -1; /* longjmp support not enabled by default. */ +++ +++ tdep->return_in_memory = sw_64_return_in_memory_always; +++ +++ /* Type sizes */ +++ set_gdbarch_short_bit (gdbarch, 16); +++ set_gdbarch_int_bit (gdbarch, 32); +++ set_gdbarch_long_bit (gdbarch, 64); +++ set_gdbarch_long_long_bit (gdbarch, 64); +++ set_gdbarch_wchar_bit (gdbarch, 64); +++ set_gdbarch_wchar_signed (gdbarch, 0); +++ set_gdbarch_float_bit (gdbarch, 32); +++ set_gdbarch_double_bit (gdbarch, 64); +++ set_gdbarch_long_double_bit (gdbarch, 64); +++ set_gdbarch_ptr_bit (gdbarch, 64); +++ +++ /* Register info */ +++ set_gdbarch_num_regs (gdbarch, SW_NUM_REGS); +++ set_gdbarch_sp_regnum (gdbarch, SW_SP_REGNUM); +++ set_gdbarch_pc_regnum (gdbarch, SW_PC_REGNUM); +++ set_gdbarch_fp0_regnum (gdbarch, SW_FP0_REGNUM); +++ +++ set_gdbarch_register_name (gdbarch, sw_64_register_name); +++ set_gdbarch_register_type (gdbarch, sw_64_register_type); +++ +++ set_gdbarch_cannot_fetch_register (gdbarch, sw_64_cannot_fetch_register); +++ set_gdbarch_cannot_store_register (gdbarch, sw_64_cannot_store_register); +++ +++ set_gdbarch_convert_register_p (gdbarch, sw_64_convert_register_p); +++ set_gdbarch_register_to_value (gdbarch, sw_64_register_to_value); +++ set_gdbarch_value_to_register (gdbarch, sw_64_value_to_register); +++ +++ set_gdbarch_register_reggroup_p (gdbarch, sw_64_register_reggroup_p); +++ +++ /* Prologue heuristics. */ +++ set_gdbarch_skip_prologue (gdbarch, sw_64_skip_prologue); +++#ifndef _SW64_ //2017-11 +++ set_gdbarch_skip_entrypoint (gdbarch, sw_64_skip_prologue); +++#endif +++ +++ +++ //set_gdbarch_skip_entrypoint (gdbarch, sw_64_skip_prologue); +++ set_gdbarch_num_pseudo_regs (gdbarch, NVEC_REGS); +++ set_gdbarch_pseudo_register_read (gdbarch, sw_64_vec_register_read); +++ set_gdbarch_pseudo_register_write (gdbarch, sw_64_vec_register_write); +++ set_gdbarch_have_nonsteppable_watchpoint (gdbarch, 1); //2012 +++ /* Call info. */ +++ +++ set_gdbarch_return_value (gdbarch, sw_64_return_value); +++ +++ /* Settings for calling functions in the inferior. */ +++ set_gdbarch_push_dummy_call (gdbarch, sw_64_push_dummy_call); +++ +++ set_gdbarch_inner_than (gdbarch, core_addr_lessthan); +++ set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target); +++ +++#ifndef XWB20200903 +++ set_gdbarch_skip_permanent_breakpoint (gdbarch, sw_64_skip_permanent_breakpoint); +++#endif +++ set_gdbarch_breakpoint_kind_from_pc (gdbarch, +++ sw_64_breakpoint::kind_from_pc); +++ set_gdbarch_sw_breakpoint_from_kind (gdbarch, +++ sw_64_breakpoint::bp_from_kind); +++ set_gdbarch_decr_pc_after_break (gdbarch, SW_INSN_SIZE); +++ set_gdbarch_cannot_step_breakpoint (gdbarch, 1); +++#ifndef _SW64_ +++ tdep->sw_64_vec_type = 0; +++ //tdep->slave_vec_type = 0; +++ +++ set_gdbarch_num_pseudo_regs (gdbarch, NVEC_REGS); +++ set_gdbarch_pseudo_register_read (gdbarch, sw_64_vec_register_read); +++ set_gdbarch_pseudo_register_write (gdbarch, sw_64_vec_register_write); +++ set_gdbarch_have_nonsteppable_watchpoint (gdbarch, 1); //2012 +++#endif +++ /* Handles single stepping of atomic sequences. */ +++ set_gdbarch_software_single_step (gdbarch, sw_64_software_single_step); +++ +++ /* Hook in ABI-specific overrides, if they have been registered. */ +++ gdbarch_init_osabi (info, gdbarch); +++ +++ /* Now that we have tuned the configuration, set a few final things +++ based on what the OS ABI has told us. */ +++ +++ if (tdep->jb_pc >= 0) +++ set_gdbarch_get_longjmp_target (gdbarch, sw_64_get_longjmp_target); +++ +++ frame_unwind_append_unwinder (gdbarch, &sw_64_sigtramp_frame_unwind); +++ frame_unwind_append_unwinder (gdbarch, &sw_64_heuristic_frame_unwind); +++ +++ frame_base_set_default (gdbarch, &sw_64_heuristic_frame_base); +++ +++ return gdbarch; +++} +++/* SW_64 process record-replay related structures, defines etc. */ +++ +++#define REG_ALLOC(REGS, LENGTH, RECORD_BUF) \ +++ do \ +++ { \ +++ unsigned int reg_len = LENGTH; \ +++ if (reg_len) \ +++ { \ +++ REGS = XNEWVEC (uint32_t, reg_len); \ +++ memcpy(®S[0], &RECORD_BUF[0], sizeof(uint32_t)*LENGTH); \ +++ } \ +++ } \ +++ while (0) +++ +++ +++#define MEM_ALLOC(MEMS, LENGTH, RECORD_BUF) \ +++ do \ +++ { \ +++ unsigned int mem_len = LENGTH; \ +++ if (mem_len) \ +++ { \ +++ MEMS = XNEWVEC (struct sw_64_mem_r, mem_len); \ +++ memcpy(&MEMS->len, &RECORD_BUF[0], \ +++ sizeof(struct sw_64_mem_r) * LENGTH); \ +++ } \ +++ } \ +++ while (0) +++void +++sw_64_dwarf2_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch) +++{ +++ dwarf2_append_unwinders (gdbarch); +++ frame_base_append_sniffer (gdbarch, dwarf2_frame_base_sniffer); +++} +++ +++extern initialize_file_ftype _initialize_sw_64_tdep; /* -Wmissing-prototypes */ +++ +++void _initialize_sw_64_tdep (); +++void +++_initialize_sw_64_tdep () +++{ +++ +++ gdbarch_register (bfd_arch_sw_64, sw_64_gdbarch_init, NULL); +++ +++ /* Let the user set the fence post for heuristic_proc_start. */ +++ +++ /* We really would like to have both "0" and "unlimited" work, but +++ command.c doesn't deal with that. So make it a var_zinteger +++ because the user can always use "999999" or some such for unlimited. */ +++ /* We need to throw away the frame cache when we set this, since it +++ might change our ability to get backtraces. */ +++ add_setshow_zinteger_cmd ("heuristic-fence-post", class_support, +++ &heuristic_fence_post, _("\ +++Set the distance searched for the start of a function."), _("\ +++Show the distance searched for the start of a function."), _("\ +++If you are debugging a stripped executable, GDB needs to search through the\n\ +++program for the start of a function. This command sets the distance of the\n\ +++search. The only need to set it is when debugging a stripped executable."), +++ reinit_frame_cache_sfunc, +++ NULL, /* FIXME: i18n: The distance searched for +++ the start of a function is \"%d\". */ +++ &setlist, &showlist); +++} +++ +++struct sw_64_mem_r +++{ +++ uint64_t len; /* Record length. */ +++ uint64_t addr; /* Memory address. */ +++}; +++ +++typedef struct insn_decode_record_t +++{ +++ struct gdbarch *gdbarch; +++ struct regcache *regcache; +++ CORE_ADDR this_addr; /* Address of insn to be recorded. */ +++ uint32_t sw_64_insn; /* Insn to be recorded. */ +++ uint32_t mem_rec_count; /* Count of memory records. */ +++ uint32_t reg_rec_count; /* Count of register records. */ +++ uint32_t *sw_64_regs; /* Registers to be recorded. */ +++ struct sw_64_mem_r *sw_64_mems; /* Memory locations to be recorded. */ +++} insn_decode_record; +++ +++unsigned int +++sw_64_record_data_proc_reg (insn_decode_record *sw_64_insn_r) +++{ +++ uint8_t insn_bits21_25; +++ insn_bits21_25 = (rigg (sw_64_insn_r->sw_64_insn, 21) & 0x1F); +++ uint8_t ins_bits5_12; +++ ins_bits5_12 = (rigg(sw_64_insn_r->sw_64_insn,5) & 0xff); +++ uint32_t ins_bit31_26; +++ ins_bit31_26 = rigg (sw_64_insn_r->sw_64_insn,26); +++ uint8_t ins_bits0_4; +++ ins_bits0_4 = (sw_64_insn_r->sw_64_insn & 0x1F); +++ uint32_t record_buf[4]; +++ record_buf[0] = ins_bits0_4; +++ if(ins_bit31_26 == 0x18) +++ { +++ if(ins_bits5_12 == 0x50) +++ { +++ record_buf[0] = insn_bits21_25+31; +++ } +++ else if(ins_bits5_12 == 0x51 || (0x54 <= ins_bits5_12 && ins_bits5_12 <= 0x57)) +++ { +++ record_buf[0] = SW_FPCR_REGNUM; +++ } +++ else +++ { +++ record_buf[0] = ins_bits0_4+32; +++ } +++ } +++ if(0x14 <= ins_bit31_26 && ins_bit31_26<= 0x17) +++ { +++ record_buf[0] = ins_bits0_4;//+167; +++ } +++ if(ins_bit31_26 == 0x1a) +++ { +++ if(ins_bits5_12 == 0x2 || ins_bits5_12 == 0x22 || ins_bits5_12 == 0x18 || ins_bits5_12 == 0x19) +++ { +++ record_buf[0] = ins_bits0_4+32; +++ } +++ else +++ { +++ record_buf[0] = ins_bits0_4;//+167; +++ } +++ } +++ if(ins_bit31_26 == 0x1b) +++ { +++ if(ins_bits5_12 == 0x22 || ins_bits5_12 == 0x23) +++ { +++ record_buf[0] = ins_bits0_4+32; +++ } +++ record_buf[0] = ins_bits0_4;//+167; +++ } +++ sw_64_insn_r->reg_rec_count = 1; +++ REG_ALLOC (sw_64_insn_r->sw_64_regs, sw_64_insn_r->reg_rec_count,record_buf); +++ return SW_64_RECORD_SUCCESS; +++} +++ +++static unsigned int +++sw_64_record_data_proc_imm (insn_decode_record *sw_64_insn_r) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (sw_64_insn_r->gdbarch); +++ int ret; +++ if(sw_64_insn_r->sw_64_insn == 0x200009e) +++ { +++ for(int i=0;i<32;i++) +++ { +++ record_full_arch_list_add_reg(sw_64_insn_r->regcache,i); +++ } +++ return SW_64_RECORD_SUCCESS; +++ } +++ if (tdep->sw_64_syscall_record != NULL) +++ { +++ ret=tdep->sw_64_syscall_record (sw_64_insn_r->regcache); +++ +++ } +++ else +++ printf_unfiltered (_("Process record does not support instruction syscall.\n")); +++ if (ret==0) +++ return ret; +++ else +++ return SW_64_RECORD_UNSUPPORTED; +++} +++ +++static unsigned int +++sw_64_record_branch_except_sys (insn_decode_record *sw_64_insn_r) +++{ +++ struct gdbarch_tdep *tdep = gdbarch_tdep (sw_64_insn_r->gdbarch); +++ uint32_t ins_bit31_26; +++ ins_bit31_26 = rigg (sw_64_insn_r->sw_64_insn, 26); +++ uint32_t record_buf[4]; +++ uint8_t insn_bits21_25; +++ insn_bits21_25 = (rigg (sw_64_insn_r->sw_64_insn, 21) & 0x1F); +++ /*Test & branch*/ +++ if (0x30 <= ins_bit31_26 && ins_bit31_26<= 0x3D) +++ { +++ record_buf[sw_64_insn_r->reg_rec_count++] = SW_PC_REGNUM; +++ } +++ else +++ { record_buf[sw_64_insn_r->reg_rec_count++] = SW_PC_REGNUM; +++ record_buf[sw_64_insn_r->reg_rec_count++] = insn_bits21_25; +++ } +++ REG_ALLOC (sw_64_insn_r->sw_64_regs, sw_64_insn_r->reg_rec_count, +++ record_buf); +++ return SW_64_RECORD_SUCCESS; +++} +++ +++static unsigned int +++sw_64_record_load_store (insn_decode_record *sw_64_insn_r) +++{ +++ uint8_t bit12; +++ bit12=bit(sw_64_insn_r->sw_64_insn, 12); +++ uint8_t insn_bits12_15; +++ insn_bits12_15=(rigg(sw_64_insn_r->sw_64_insn, 12) & 0x1f); +++ uint8_t insn_bits21_25; +++ uint8_t insn_bits16_20; +++ uint8_t insn_bits8_15; +++ insn_bits8_15 = (rigg(sw_64_insn_r->sw_64_insn, 8) & 0xff); +++ uint32_t ins_bit31_26; +++ ins_bit31_26 = rigg (sw_64_insn_r->sw_64_insn, 26); +++ insn_bits16_20 = (rigg(sw_64_insn_r->sw_64_insn, 16) & 0x1f); +++ uint8_t insn_bit0_16; +++ insn_bit0_16=(sw_64_insn_r->sw_64_insn & 0xffff); +++ uint32_t record_buf[8]; +++ uint64_t record_buf_mem[8]; +++ CORE_ADDR address; +++ int save_size; +++ insn_bits21_25 = (rigg (sw_64_insn_r->sw_64_insn, 21) & 0x1F);// +++ int Byte4_len; +++ int disp15,disp11; +++ disp15 = sw_64_insn_r->sw_64_insn & 0xffff; +++ disp11 = sw_64_insn_r->sw_64_insn & 0xfff; +++ if(sw_64_insn_r->sw_64_insn & 0x8000) +++ { +++ disp15 |= 0xffff0000; +++ } +++ if(sw_64_insn_r->sw_64_insn & 0x800) +++ { +++ disp11 |= 0xfffff000; +++ } +++ /*load imme , transfer*/ +++ if ((0x3E <= ins_bit31_26 && ins_bit31_26<= 0x3F) || ins_bit31_26 ==0x07 || ins_bit31_26 == 0x25) +++ { +++ if (record_debug) +++ debug_printf ("Process record: load register (literal)\n"); +++ record_buf[0] = insn_bits21_25; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ else if((0x09 <= ins_bit31_26 && ins_bit31_26<= 0x0F) || ins_bit31_26 == 0x1C)//simd save and load +++ { +++ if(0x09 <= ins_bit31_26 && ins_bit31_26<= 0x0D) +++ { +++ record_buf[0] = insn_bits21_25;//+167; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ if(0x0E == ins_bit31_26 || ins_bit31_26 == 0x0F || ins_bit31_26 == 0x1C) +++ { +++ if(ins_bit31_26 == 0x1C && insn_bits12_15 == 0xe) +++ { +++ regcache_raw_read_unsigned (sw_64_insn_r->regcache, insn_bits16_20, +++ &address); +++ address+=disp11; +++ record_buf_mem[0] = 32; +++ record_buf_mem[1] = address; +++ sw_64_insn_r->mem_rec_count = 1; +++ } +++ regcache_raw_read_unsigned (sw_64_insn_r->regcache, insn_bits16_20, +++ &address); +++ if(ins_bit31_26 == 0xe && ins_bit31_26 == 0xf) +++ { +++ address+=disp15; +++ } +++ address+=(sw_64_insn_r->sw_64_insn & 0xfff); +++ if(ins_bit31_26 == 0x1C) +++ { +++ switch(insn_bits12_15) +++ { +++ case 0x9: +++ case 0x8: +++ case 0x1: +++ Byte4_len = ((address & 0x1f) >> 2); +++ address=address & 0xffffffffffffffe0; +++ break; +++ case 0xb: +++ case 0xa: +++ case 0x3: +++ Byte4_len = ((address & 0xf) >> 2); +++ address=address & 0xfffffffffffffff0; +++ break; +++ case 0xf: +++ save_size=32; +++ break; +++ case 0xd: +++ case 0xc: +++ case 0x5: +++ Byte4_len = ((address & 0x1f) >> 3); +++ address=address & 0xffffffffffffffe0; +++ break; +++ default: +++ goto simdsave; +++ break; +++ } +++ } +++ switch(ins_bit31_26) +++ { +++ case 0x0e: +++ save_size=16; +++ break; +++ case 0xf: +++ save_size=32; +++ break; +++ case 0x1C: +++ switch(insn_bits12_15) +++ { +++ case 0x01: +++ save_size=32; +++ break; +++ case 0x03: +++ case 0x05: +++ save_size=16; +++ break; +++ case 0x8: +++ save_size=32-4*Byte4_len; +++ address+=Byte4_len*4; +++ break; +++ case 0xf: +++ save_size=32; +++ break; +++ case 0xc: +++ case 0xA: +++ save_size=4*(4-Byte4_len); +++ address+=Byte4_len*4; +++ break; +++ case 0xB: +++ case 0x9: +++ case 0xd: +++ if(Byte4_len == 0) +++ { +++ return SW_64_RECORD_UNSUPPORTED; +++ } +++ else +++ { +++ save_size = Byte4_len*4; +++ } +++ break; +++ default: +++ goto simdsave; +++ break; +++ } +++ default: +++ return SW_64_RECORD_UNSUPPORTED; +++ } +++ record_buf_mem[0] = save_size; +++ record_buf_mem[1] = address; +++ sw_64_insn_r->mem_rec_count = 1; +++ } +++ } +++ else if(0x01 <= ins_bit31_26 && ins_bit31_26<= 0x03) +++ { +++ record_buf[sw_64_insn_r->reg_rec_count++] = SW_PC_REGNUM; +++ record_buf[sw_64_insn_r->reg_rec_count++] = insn_bits21_25; +++ goto log; +++ } +++ else if(ins_bit31_26 == 0x06 || ins_bit31_26 == 0x08 || ins_bit31_26 == 0x2D)//misc +++ { +++ if(ins_bit31_26 == 0x06 && (insn_bits8_15 == 0xff || insn_bits8_15 == 0xfe)) +++ { +++ if(insn_bits8_15 == 0xff) +++ { +++ record_buf[0] = SW_CSR_REGNUM; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ else +++ { +++ record_buf[0] = insn_bits21_25; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ } +++ if(ins_bit31_26 == 0x08 && insn_bits12_15 == 0xc) +++ { +++ record_buf[0] = insn_bits21_25+32; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ if(insn_bit0_16 == 0x20 || insn_bit0_16 == 0x40 || insn_bit0_16 == 0x1040) +++ { +++ record_buf[0] = insn_bits21_25; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ if((ins_bit31_26 == 0x2D) || (ins_bit31_26 == 0x08 && ((0x2 <=insn_bits12_15 && insn_bits12_15 <= 0x7) || (0xd <=insn_bits12_15 && insn_bits12_15 <= 0xf)))) +++ { +++ switch(insn_bits12_15) +++ { +++ case 0x2: +++ case 0x4: +++ case 0x6: +++ case 0xd: +++ save_size=4; +++ break; +++ case 0x3: +++ case 0x5: +++ case 0x7: +++ case 0xe: +++ case 0xf: +++ save_size=8; +++ break; +++ } +++ if(bit12 == 0) +++ { +++ save_size=4; +++ } +++ else +++ { +++ save_size=8; +++ } +++ regcache_raw_read_unsigned (sw_64_insn_r->regcache, insn_bits16_20, +++ &address); +++ address+=disp11; +++ record_buf_mem[0] = save_size; +++ record_buf_mem[1] = address; +++ sw_64_insn_r->mem_rec_count = 1; +++ } +++ } +++ else if(ins_bit31_26 == 0x26 || ins_bit31_26 == 0x27)//float save +++ { +++ record_buf[0] = insn_bits21_25+32; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ else +++ { +++ if (record_debug) +++ debug_printf ("Process record: load/store exclusive\n"); +++ +++ if (0x20 <= ins_bit31_26 && ins_bit31_26<= 0x24) +++ { +++ record_buf[0] = insn_bits21_25; +++ sw_64_insn_r->reg_rec_count = 1; +++ } +++ else +++ { +++ switch(ins_bit31_26) +++ { +++ case 0x28: +++ save_size=1; +++ break; +++ case 0x29: +++ save_size=2; +++ break; +++ case 0x2A: +++ case 0x2E: +++ save_size=4; +++ break; +++ case 0x2B: +++ case 0x2F: +++ case 0x24: +++ save_size=8; +++ break; +++ } +++ regcache_raw_read_unsigned (sw_64_insn_r->regcache, insn_bits16_20, +++ &address); +++ address+=disp15; +++ switch(ins_bit31_26) +++ { +++ case 0x24: +++ address&=0xfffffffffffffff8; +++ } +++ record_buf_mem[0] = save_size; +++ record_buf_mem[1] = address; +++ sw_64_insn_r->mem_rec_count = 1; +++ } +++ } +++simdsave: +++ record_buf[0] = insn_bits21_25;//+167; +++ sw_64_insn_r->reg_rec_count = 1; +++log: +++ MEM_ALLOC (sw_64_insn_r->sw_64_mems, sw_64_insn_r->mem_rec_count, +++ record_buf_mem); +++ REG_ALLOC (sw_64_insn_r->sw_64_regs, sw_64_insn_r->reg_rec_count, +++ record_buf); +++ return SW_64_RECORD_SUCCESS; +++} +++ +++static unsigned int +++sw_64_record_data_proc_simd_fp (insn_decode_record *sw_64_insn_r) +++{ +++ uint8_t ins_bits0_4; +++ ins_bits0_4 = (sw_64_insn_r->sw_64_insn & 0x1F); +++ uint32_t record_buf[4]; +++ record_buf[0] = ins_bits0_4; +++ sw_64_insn_r->reg_rec_count = 1; +++ REG_ALLOC (sw_64_insn_r->sw_64_regs, sw_64_insn_r->reg_rec_count,record_buf); +++ return SW_64_RECORD_SUCCESS; +++} +++ +++/* Decodes insns type and invokes its record handler. */ +++static unsigned int +++sw_64_record_decode_insn_handler (insn_decode_record *sw_64_insn_r) +++{ +++ uint32_t ins_bit31_26; +++ ins_bit31_26 = rigg (sw_64_insn_r->sw_64_insn, 26); +++ /*five differrent instruction format*/ +++/* system format. */ +++ if (ins_bit31_26 == 0) +++ return sw_64_record_data_proc_imm (sw_64_insn_r); +++ +++ /* transfer format */ +++ if (ins_bit31_26 == 0x04 || ins_bit31_26 == 0x05 || (0x30 <= ins_bit31_26 && ins_bit31_26<= 0x3D)) +++ return sw_64_record_branch_except_sys (sw_64_insn_r); +++ +++ /* Load and store format. */ +++ if ((0x01 <= ins_bit31_26 && ins_bit31_26<= 0x03)/*jump*/|| (0x28 <= ins_bit31_26 && ins_bit31_26<= 0x2C)//save and load +++ || (0x20 <= ins_bit31_26 && ins_bit31_26<= 0x24) +++ || (ins_bit31_26 == 0x25)//PRI_LD +++ || (0x26 <= ins_bit31_26 && ins_bit31_26<= 0x27) +++ || (0x2D == ins_bit31_26)//PRI_ST +++ || (0x2E <= ins_bit31_26 && ins_bit31_26<= 0x2F) +++ || (0x3E <= ins_bit31_26 && ins_bit31_26<= 0x3F)//load immedia +++ || (ins_bit31_26 == 0x06)//PRI_RWCSR +++ || (ins_bit31_26 == 0x07)//PRI_RET:W +++ || (ins_bit31_26 == 0x08)//misc +++ || (0x09 <= ins_bit31_26 && ins_bit31_26<= 0x0F)//simd load and save +++ || (ins_bit31_26 == 0x1c)) +++ return sw_64_record_load_store (sw_64_insn_r); +++ +++ /* simple calculate format */ +++ if (ins_bit31_26 == 0x10 || ins_bit31_26 == 0x12//integer calculate +++ || ins_bit31_26 == 0x18//float calculate +++ || ins_bit31_26 == 0x1A//integer or float simd calculate +++ || (0x14 <= ins_bit31_26 && ins_bit31_26<= 0x17))//reconfig +++ return sw_64_record_data_proc_reg (sw_64_insn_r); +++ +++ /* combination calculate format */ +++ if (ins_bit31_26 == 0x1B || ins_bit31_26 == 0x19 || ins_bit31_26 == 0x11 || ins_bit31_26 == 0x13) +++ return sw_64_record_data_proc_simd_fp (sw_64_insn_r); +++ +++ return SW_64_RECORD_UNSUPPORTED; +++} +++ +++static void +++deallocate_reg_mem (insn_decode_record *record) +++{ +++ xfree (record->sw_64_regs); +++ xfree (record->sw_64_mems); +++} +++ +++int +++sw_64_process_record (struct gdbarch *gdbarch, struct regcache *regcache, +++ CORE_ADDR insn_addr) +++{ +++ uint32_t rec_no = 0; +++ uint8_t insn_size = 4; +++ uint32_t ret = 0; +++ gdb_byte buf[insn_size]; +++ insn_decode_record sw_64_record; +++ +++ memset (&buf[0], 0, insn_size); +++ memset (&sw_64_record, 0, sizeof (insn_decode_record)); +++ target_read_memory (insn_addr, &buf[0], insn_size); +++ sw_64_record.sw_64_insn +++ = (uint32_t) extract_unsigned_integer (&buf[0], +++ insn_size, +++ gdbarch_byte_order (gdbarch)); +++ sw_64_record.regcache = regcache; +++ sw_64_record.this_addr = insn_addr; +++ sw_64_record.gdbarch = gdbarch; +++ +++ ret = sw_64_record_decode_insn_handler (&sw_64_record); +++ if (ret == SW_64_RECORD_UNSUPPORTED) +++ { +++ printf_unfiltered (_("Process record does not support instruction " +++ "0x%0x at address %s.\n"), +++ sw_64_record.sw_64_insn, +++ paddress (gdbarch, insn_addr)); +++ ret = -1; +++ } +++ +++ if (0 == ret) +++ { +++ /* Record registers. */ +++ record_full_arch_list_add_reg (sw_64_record.regcache, +++ SW_PC_REGNUM); +++ /* Always record register CPSR. */ +++ record_full_arch_list_add_reg (sw_64_record.regcache, +++ SW_CSR_REGNUM); +++ if (sw_64_record.sw_64_regs) +++ for (rec_no = 0; rec_no < sw_64_record.reg_rec_count; rec_no++) +++ if (record_full_arch_list_add_reg (sw_64_record.regcache, +++ sw_64_record.sw_64_regs[rec_no])) +++ ret = -1; +++ +++ /* Record memories. */ +++ if (sw_64_record.sw_64_mems) +++ for (rec_no = 0; rec_no < sw_64_record.mem_rec_count; rec_no++) +++ if (record_full_arch_list_add_mem +++ ((CORE_ADDR)sw_64_record.sw_64_mems[rec_no].addr, +++ sw_64_record.sw_64_mems[rec_no].len)) +++ ret = -1; +++ +++ if (record_full_arch_list_add_end ()) +++ ret = -1; +++ } +++ +++ deallocate_reg_mem (&sw_64_record); +++ return ret; +++} ++diff -Nuar gdb-10.2/gdb/sw_64-tdep.h gdb-10.2/gdb/sw_64-tdep.h ++--- gdb-10.2/gdb/sw_64-tdep.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/sw_64-tdep.h 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,174 @@ +++/* Common target dependent code for GDB on SW_64 systems. +++ Copyright (C) 1993-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#ifndef SW_64_TDEP_H +++#define SW_64_TDEP_H +++ +++struct regcache; +++ +++/* Say how long (ordinary) registers are. This is a piece of bogosity +++ used in push_word and a few other places; register_size() is the +++ real way to know how big a register is. */ +++#define SW_REGISTER_SIZE 8 +++ +++/* Number of machine registers. */ +++#ifndef LHX20201026 +++#define SW_NUM_REGS 167 +++#else +++#define SW_NUM_REGS 165 +++#endif +++ +++/* Register numbers of various important registers. Note that most of +++ these values are "real" register numbers, and correspond to the +++ general registers of the machine. */ +++enum sw_64_regnum{ +++ SW_V0_REGNUM, +++ SW_T7_REGNUM=8, +++ SW_S0_REGNUM=9, +++ SW_GCC_FP_REGNUM=15, +++ SW_A0_REGNUM=16, +++ SW_T9_REGNUM=23, +++ SW_RA_REGNUM=26, +++ SW_T12_REGNUM, +++ SW_GP_REGNUM=29, +++ SW_SP_REGNUM, +++ SW_ZERO_REGNUM, +++ SW_FP0_REGNUM, +++ SW_FPA0_REGNUM=48, +++ SW_FPCR_REGNUM=63, +++ SW_UNIQUE_REGNUM=66 +++}; +++//#define SW_V0_REGNUM 0 /* Function integer return value */ +++#define SW_T7_REGNUM 8 /* Return address register for OSF/1 __add* */ +++#define SW_S0_REGNUM 9 /* First saved register */ +++#define SW_GCC_FP_REGNUM 15 /* Used by gcc as frame register */ +++#define SW_A0_REGNUM 16 /* Loc of first arg during a subr call */ +++#define SW_T9_REGNUM 23 /* Return address register for OSF/1 __div* */ +++#define SW_RA_REGNUM 26 /* Contains return address value */ +++#define SW_T12_REGNUM 27 /* Contains start addr of current proc */ +++#define SW_GP_REGNUM 29 /* Contains the global pointer */ +++#define SW_SP_REGNUM 30 /* Contains address of top of stack */ +++#define SW_ZERO_REGNUM 31 /* Read-only register, always 0 */ +++#define SW_FP0_REGNUM 32 /* Floating point register 0 */ +++#define SW_FPA0_REGNUM 48 /* First float arg during a subr call */ +++#define SW_FPCR_REGNUM 63 /* Floating point control register */ +++#define SW_PC_REGNUM 64 /* Contains program counter */ +++#define SW_UNIQUE_REGNUM 66 /* PAL_rduniq value */ +++#define SW_CSR_REGNUM 66 /* Current Program Status Register. *///rewrite +++ +++#ifndef LHX20201026 +++ #define SW2_V0F1_REGNUM 67 +++ #define SW2_V0F2_REGNUM 99 +++ #define SW2_V0F3_REGNUM 131 +++ #define SW2_V0_REGNUM 167 +++#endif +++ +++/* Instruction size. */ +++#define SW_INSN_SIZE 4 +++ +++/* The sw_64 has two different virtual pointers for arguments and locals. +++ +++ The virtual argument pointer is pointing to the bottom of the argument +++ transfer area, which is located immediately below the virtual frame +++ pointer. Its size is fixed for the native compiler, it is either zero +++ (for the no arguments case) or large enough to hold all argument registers. +++ gcc uses a variable sized argument transfer area. As it has +++ to stay compatible with the native debugging tools it has to use the same +++ virtual argument pointer and adjust the argument offsets accordingly. +++ +++ The virtual local pointer is localoff bytes below the virtual frame +++ pointer, the value of localoff is obtained from the PDR. */ +++#define SW_NUM_ARG_REGS 6 +++ +++/* Target-dependent structure in gdbarch. */ +++struct gdbarch_tdep +++{ +++ CORE_ADDR vm_min_address; /* Used by sw_64_heuristic_proc_start. */ +++ +++ /* If PC is inside a dynamically-generated signal trampoline function +++ (i.e. one copied onto the user stack at run-time), return how many +++ bytes PC is beyond the start of that function. Otherwise, return -1. */ +++ LONGEST (*dynamic_sigtramp_offset) (struct gdbarch *, CORE_ADDR); +++ +++ /* Translate a signal handler stack base address into the address of +++ the sigcontext structure for that signal handler. */ +++ CORE_ADDR (*sigcontext_addr) (struct frame_info *); +++ +++ /* Does the PC fall in a signal trampoline. */ +++ /* NOTE: cagney/2004-04-30: Do not copy/clone this code. Instead +++ look at tramp-frame.h and other simplier per-architecture +++ sigtramp unwinders. */ +++ int (*pc_in_sigtramp) (struct gdbarch *gdbarch, CORE_ADDR pc, +++ const char *name); +++ +++ /* If TYPE will be returned in memory, return true. */ +++ int (*return_in_memory) (struct type *type); +++ +++ /* Offset of registers in `struct sigcontext'. */ +++ int sc_pc_offset; +++ uint64_t vq; +++ bool has_sve () const +++ { +++ return vq != 0; +++ } +++ int sc_regs_offset; +++ int sc_fpregs_offset; +++ +++ int jb_pc; /* Offset to PC value in jump buffer. +++ If htis is negative, longjmp support +++ will be disabled. */ +++ size_t jb_elt_size; /* And the size of each entry in the buf. */ +++#ifndef LHX20201026 +++ struct type *sw_64_vec_type; +++#else +++ struct type *master_vec_type; +++#endif +++/* syscall record. */ +++ int (*sw_64_syscall_record) (struct regcache *regcache); +++}; +++ +++extern unsigned int sw_64_read_insn (struct gdbarch *gdbarch, CORE_ADDR pc); +++extern std::vector sw_64_software_single_step +++ (struct regcache *regcache); +++extern CORE_ADDR sw_64_after_prologue (CORE_ADDR pc); +++ +++extern void sw_64_mdebug_init_abi (struct gdbarch_info, struct gdbarch *); +++extern void sw_64_dwarf2_init_abi (struct gdbarch_info, struct gdbarch *); +++ +++extern void sw_64_supply_int_regs (struct regcache *, int, const void *, +++ const void *, const void *); +++extern int aarch64_process_record (struct gdbarch *gdbarch, +++ struct regcache *regcache, CORE_ADDR addr); +++extern void sw_64_fill_int_regs (const struct regcache *, int, +++ void *, void *, void *); +++extern void sw_64_supply_fp_regs (struct regcache *, int, +++ const void *, const void *); +++extern void sw_64_fill_fp_regs (const struct regcache *, +++ int, void *, void *); +++extern int sw_64_process_record (struct gdbarch *gdbarch, +++ struct regcache *regcache, CORE_ADDR addr); +++ +++#define SW64_VEC0 SW_NUM_REGS +++#define REG_BASE 0 +++#define NGP_REGS 32 +++#define NFP_REGS 32 +++#define NVEC_REGS 32 +++#define GPR_BASE REG_BASE +++#define FPR_BASE (GPR_BASE+NGP_REGS) +++ +++#endif /* SW_64_TDEP_H */ ++diff -Nuar gdb-10.2/gdb/symfile.c gdb-10.2/gdb/symfile.c ++--- gdb-10.2/gdb/symfile.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/symfile.c 2025-04-16 17:06:41.922086800 +0800 ++@@ -652,7 +652,26 @@ ++ for (cur_sec = abfd->sections; cur_sec != NULL; cur_sec = cur_sec->next) ++ /* We do not expect this to happen; just skip this step if the ++ relocatable file has a section with an assigned VMA. */ ++- if (bfd_section_vma (cur_sec) != 0) +++ if (bfd_section_vma (cur_sec) != 0 +++ /* +++ * Kernel modules may have some non-zero VMAs, i.e., like the +++ * __ksymtab and __ksymtab_gpl sections in this example: +++ * +++ * Section Headers: +++ * [Nr] Name Type Address Offset +++ * Size EntSize Flags Link Info Align +++ * ... +++ * [ 8] __ksymtab PROGBITS 0000000000000060 0000ad90 +++ * 0000000000000010 0000000000000000 A 0 0 16 +++ * [ 9] .rela__ksymtab RELA 0000000000000000 0000ada0 +++ * 0000000000000030 0000000000000018 43 8 8 +++ * [10] __ksymtab_gpl PROGBITS 0000000000000070 0000add0 +++ * 00000000000001a0 0000000000000000 A 0 0 16 +++ * ... +++ * +++ * but they should be treated as if they are NULL. +++ */ +++ && strncmp (bfd_section_name (cur_sec), "__k", 3) != 0) ++ break; ++ ++ if (cur_sec == NULL) ++@@ -1083,6 +1102,12 @@ ++ if (mainline) ++ flags |= OBJF_MAINLINE; ++ objfile = objfile::make (abfd, name, flags, parent); +++#ifdef CRASH_MERGE +++ if (add_flags & SYMFILE_MAINLINE) { +++ extern struct objfile *gdb_kernel_objfile; +++ gdb_kernel_objfile = objfile; +++ } +++#endif ++ ++ /* We either created a new mapped symbol table, mapped an existing ++ symbol table file which has not had initial symbol reading ++@@ -1375,6 +1400,10 @@ ++ #if ! defined (DEBUG_SUBDIRECTORY) ++ #define DEBUG_SUBDIRECTORY ".debug" ++ #endif +++#ifdef CRASH_MERGE +++extern "C" int check_specified_module_tree(const char *, const char *); +++extern "C" char *check_specified_kernel_debug_file(); +++#endif ++ ++ /* Find a separate debuginfo file for OBJFILE, using DIR as the directory ++ where the original file resides (may not be the same as ++@@ -1410,6 +1439,15 @@ ++ if (separate_debug_file_exists (debugfile, crc32, objfile)) ++ return debugfile; ++ +++#ifdef CRASH_MERGE +++{ +++ if (check_specified_module_tree(objfile_name (objfile), debugfile.c_str()) && +++ separate_debug_file_exists(debugfile, crc32, objfile)) { +++ return debugfile; +++ } +++} +++#endif +++ ++ /* Then try in the global debugfile directories. ++ ++ Keep backward compatibility so that DEBUG_FILE_DIRECTORY being "" will ++@@ -1568,6 +1606,14 @@ ++ } ++ } ++ +++#ifdef CRASH_MERGE +++ if (debugfile.empty ()) { +++ char *name_copy; +++ name_copy = check_specified_kernel_debug_file(); +++ return name_copy ? std::string (name_copy) : std::string (); +++ } +++#endif +++ ++ return debugfile; ++ } ++ ++@@ -2334,8 +2380,10 @@ ++ else if (section_addrs.empty ()) ++ printf_unfiltered ("\n"); ++ +++#ifndef CRASH_MERGE ++ if (from_tty && (!query ("%s", ""))) ++ error (_("Not confirmed.")); +++#endif ++ ++ objf = symbol_file_add (filename.get (), add_flags, §ion_addrs, ++ flags); ++@@ -3622,6 +3670,15 @@ ++ symfile_relocate_debug_section (struct objfile *objfile, ++ asection *sectp, bfd_byte *buf) ++ { +++#ifdef CRASH_MERGE +++ /* Executable files have all the relocations already resolved. +++ * Handle files linked with --emit-relocs. +++ * http://sources.redhat.com/ml/gdb/2006-08/msg00137.html +++ */ +++ bfd *abfd = objfile->obfd; +++ if ((abfd->flags & EXEC_P) != 0) +++ return NULL; +++#endif ++ gdb_assert (objfile->sf->sym_relocate); ++ ++ return (*objfile->sf->sym_relocate) (objfile, sectp, buf); ++diff -Nuar gdb-10.2/gdb/symtab.c gdb-10.2/gdb/symtab.c ++--- gdb-10.2/gdb/symtab.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/symtab.c 2025-04-16 17:06:41.952086800 +0800 ++@@ -1870,27 +1870,46 @@ ++ variable and thus can probably assume it will never hit the C++ ++ code). */ ++ +++#ifdef CRASH_MERGE +++static void gdb_bait_and_switch(char *, struct symbol *); +++#endif +++ ++ struct block_symbol ++ lookup_symbol_in_language (const char *name, const struct block *block, ++ const domain_enum domain, enum language lang, ++ struct field_of_this_result *is_a_field_of_this) ++ { +++ struct block_symbol result; ++ demangle_result_storage storage; ++ const char *modified_name = demangle_for_lookup (name, lang, storage); ++ ++- return lookup_symbol_aux (modified_name, +++ result = lookup_symbol_aux (modified_name, ++ symbol_name_match_type::FULL, ++ block, domain, lang, ++ is_a_field_of_this); +++#ifdef CRASH_MERGE +++ if (result.symbol && (domain == VAR_DOMAIN)) +++ gdb_bait_and_switch((char *)modified_name, result.symbol); +++#endif +++ return result; ++ } ++ ++ /* See symtab.h. */ ++ +++#ifdef CRASH_MERGE +++static const struct block *gdb_get_crash_block(void); +++#endif +++ ++ struct block_symbol ++ lookup_symbol (const char *name, const struct block *block, ++ domain_enum domain, ++ struct field_of_this_result *is_a_field_of_this) ++ { +++#ifdef CRASH_MERGE +++ if (!block) +++ block = gdb_get_crash_block(); +++#endif +++ ++ return lookup_symbol_in_language (name, block, domain, ++ current_language->la_language, ++ is_a_field_of_this); ++@@ -6886,3 +6905,902 @@ ++ gdb::observers::new_objfile.attach (symtab_new_objfile_observer); ++ gdb::observers::free_objfile.attach (symtab_free_objfile_observer); ++ } +++ +++#ifdef CRASH_MERGE +++#include "gdb-stabs.h" +++#include "gdbsupport/version.h" +++#define GDB_COMMON +++#include "../../defs.h" +++ +++static void get_member_data(struct gnu_request *, struct type *, long, int); +++static void walk_enum(struct type *, struct gnu_request *); +++static void eval_enum(struct type *, struct gnu_request *); +++static void gdb_get_line_number(struct gnu_request *); +++static void gdb_get_datatype(struct gnu_request *); +++static void gdb_get_symbol_type(struct gnu_request *); +++static void gdb_command_exists(struct gnu_request *); +++static void gdb_debug_command(struct gnu_request *); +++static void gdb_function_numargs(struct gnu_request *); +++static void gdb_add_symbol_file(struct gnu_request *); +++static void gdb_delete_symbol_file(struct gnu_request *); +++static void gdb_patch_symbol_values(struct gnu_request *); +++static void get_user_print_option_address(struct gnu_request *); +++extern int get_frame_offset(CORE_ADDR); +++static void gdb_set_crash_block(struct gnu_request *); +++extern "C" void gdb_command_funnel(struct gnu_request *); +++void gdb_command_funnel_1(struct gnu_request *); +++static long lookup_struct_contents(struct gnu_request *); +++static void iterate_datatypes(struct gnu_request *); +++ +++struct objfile *gdb_kernel_objfile = { 0 }; +++ +++static ulong gdb_merge_flags = 0; +++#define KERNEL_SYMBOLS_PATCHED (0x1) +++ +++#undef STREQ +++#define STREQ(A, B) (A && B && (strcmp(A, B) == 0)) +++#define TYPE_CODE(t) (t->code ()) +++#define TYPE_TAG_NAME(t) (TYPE_MAIN_TYPE(t)->name) +++#define TYPE_NFIELDS(t) (t->num_fields ()) +++#define TYPE_NAME(t) (t->name ()) +++ +++/* +++ * All commands from above come through here. +++ */ +++void +++gdb_command_funnel(struct gnu_request *req) +++{ +++ try { +++ gdb_command_funnel_1(req); +++ } catch (const gdb_exception &ex) { +++ if (req->flags & GNU_RETURN_ON_ERROR) +++ req->flags |= GNU_COMMAND_FAILED; +++ else +++ throw ex; +++ } +++} +++ +++void +++gdb_command_funnel_1(struct gnu_request *req) +++{ +++ struct symbol *sym; +++ +++ if (req->command != GNU_VERSION && req->command != GNU_USER_PRINT_OPTION) { +++ (dynamic_castgdb_stdout)->set_stream(req->fp); +++ (dynamic_castgdb_stderr)->set_stream(req->fp); +++ } +++ +++ switch (req->command) +++ { +++ case GNU_VERSION: +++ req->buf = (char *)version; +++ break; +++ +++ case GNU_PASS_THROUGH: +++ execute_command(req->buf, +++ req->flags & GNU_FROM_TTY_OFF ? FALSE : TRUE); +++ break; +++ +++ case GNU_USER_PRINT_OPTION: +++ get_user_print_option_address(req); +++ break; +++ +++ case GNU_RESOLVE_TEXT_ADDR: +++ sym = find_pc_function(req->addr); +++ if (!sym || TYPE_CODE(sym->type) != TYPE_CODE_FUNC) +++ req->flags |= GNU_COMMAND_FAILED; +++ break; +++ +++ case GNU_DISASSEMBLE: +++ if (req->addr2) +++ sprintf(req->buf, "disassemble 0x%lx 0x%lx", +++ req->addr, req->addr2); +++ else +++ sprintf(req->buf, "disassemble 0x%lx", req->addr); +++ execute_command(req->buf, TRUE); +++ break; +++ +++ case GNU_ADD_SYMBOL_FILE: +++ gdb_add_symbol_file(req); +++ break; +++ +++ case GNU_DELETE_SYMBOL_FILE: +++ gdb_delete_symbol_file(req); +++ break; +++ +++ case GNU_GET_LINE_NUMBER: +++ gdb_get_line_number(req); +++ break; +++ +++ case GNU_GET_DATATYPE: +++ gdb_get_datatype(req); +++ break; +++ +++ case GNU_GET_SYMBOL_TYPE: +++ gdb_get_symbol_type(req); +++ break; +++ +++ case GNU_COMMAND_EXISTS: +++ gdb_command_exists(req); +++ break; +++ +++ case GNU_ALPHA_FRAME_OFFSET: +++ req->value = 0; +++ break; +++ +++ case GNU_FUNCTION_NUMARGS: +++ gdb_function_numargs(req); +++ break; +++ +++ case GNU_DEBUG_COMMAND: +++ gdb_debug_command(req); +++ break; +++ +++ case GNU_PATCH_SYMBOL_VALUES: +++ gdb_patch_symbol_values(req); +++ break; +++ +++ case GNU_SET_CRASH_BLOCK: +++ gdb_set_crash_block(req); +++ break; +++ +++ case GNU_GET_FUNCTION_RANGE: +++ { +++ CORE_ADDR start, end; +++ if (!find_pc_partial_function(req->pc, NULL, &start, &end)) +++ req->flags |= GNU_COMMAND_FAILED; +++ else { +++ req->addr = (ulong)start; +++ req->addr2 = (ulong)end; +++ } +++ } +++ break; +++ +++ case GNU_LOOKUP_STRUCT_CONTENTS: +++ req->value = lookup_struct_contents(req); +++ break; +++ +++ case GNU_ITERATE_DATATYPES: +++ iterate_datatypes(req); +++ break; +++ +++ default: +++ req->flags |= GNU_COMMAND_FAILED; +++ break; +++ } +++} +++ +++/* +++ * Given a PC value, return the file and line number. +++ */ +++static void +++gdb_get_line_number(struct gnu_request *req) +++{ +++ struct symtab_and_line sal; +++ struct objfile *objfile; +++ CORE_ADDR pc; +++ +++#define LASTCHAR(s) (s[strlen(s)-1]) +++ +++ /* +++ * Prime the addrmap pump. +++ */ +++ pc = req->addr; +++ +++ sal = find_pc_line(pc, 0); +++ +++ if (!sal.symtab) { +++ /* +++ * If a module address line number can't be found, it's typically +++ * due to its addrmap still containing offset values because its +++ * objfile doesn't have full symbols loaded. +++ */ +++ if (req->lm) { +++ objfile = req->lm->loaded_objfile; +++ if (!objfile_has_full_symbols(objfile) && objfile->sf) { +++ objfile->sf->qf->expand_all_symtabs(objfile); +++ sal = find_pc_line(pc, 0); +++ } +++ } +++ if (!sal.symtab) { +++ req->buf[0] = '\0'; +++ return; +++ } +++ } +++ +++ if (sal.symtab->filename && SYMTAB_DIRNAME(sal.symtab)) { +++ if (sal.symtab->filename[0] == '/') +++ sprintf(req->buf, "%s: %d", +++ sal.symtab->filename, sal.line); +++ else +++ sprintf(req->buf, "%s%s%s: %d", +++ SYMTAB_DIRNAME(sal.symtab), +++ LASTCHAR(SYMTAB_DIRNAME(sal.symtab)) == '/' ? "" : "/", +++ sal.symtab->filename, sal.line); +++ } +++} +++ +++ +++/* +++ * Follow the type linkage for full member and value type resolution, with callback +++ */ +++static void drillDownType(struct gnu_request *req, struct type *type) +++{ +++ while (type) +++ { +++ /* check out for stub types and pull in the definition instead */ +++ if (TYPE_STUB(type) && TYPE_TAG_NAME(type)) { +++ struct symbol *sym; +++ sym = lookup_symbol(TYPE_TAG_NAME(type), 0, STRUCT_DOMAIN, 0).symbol; +++ if (sym) +++ type = sym->type; +++ } +++ switch (TYPE_CODE(type)) { +++ drill_ops_t op; +++ long l1, l2; +++ int typecode; +++ +++ case TYPE_CODE_PTR: +++ req->tcb(EOP_POINTER, req, 0, 0, 0, 0); +++ break; +++ +++ case TYPE_CODE_TYPEDEF: +++ req->is_typedef = 1; +++ req->typecode = TYPE_CODE(type); +++ if (!req->tcb(EOP_TYPEDEF, req, TYPE_NAME(type), 0, 0, 0)) +++ return; +++ break; +++ +++ case TYPE_CODE_FUNC: +++ req->tcb(EOP_FUNCTION, req, 0, 0, 0, 0); +++ break; +++ +++ case TYPE_CODE_ARRAY: +++ l1 = TYPE_LENGTH (type); +++ l2 = TYPE_LENGTH (check_typedef(TYPE_TARGET_TYPE (type))); +++ req->tcb(EOP_ARRAY, req, &l1, &l2, 0, 0); +++ break; +++ +++ case TYPE_CODE_VOID: +++ case TYPE_CODE_INT: +++ case TYPE_CODE_BOOL: +++ l1 = TYPE_LENGTH(type); +++ req->tcb(EOP_INT, req, &l1, 0, 0, 0); +++ break; +++ +++ case TYPE_CODE_UNION: +++ op = EOP_UNION; +++ goto label; +++ +++ case TYPE_CODE_ENUM: +++ op = EOP_ENUM; +++ goto label; +++ +++ case TYPE_CODE_STRUCT: +++ op = EOP_STRUCT; +++ goto label; +++ +++ default: +++ typecode = TYPE_CODE(type); +++ req->tcb(EOP_OOPS, req, &typecode, "Unknown typecode", 0, 0); +++ return; /* not reached */ +++ +++ label: +++ l1 = TYPE_LENGTH(type); +++ req->tcb(op, req, &l1, type, TYPE_TAG_NAME(type), 0); +++ } +++ type = TYPE_TARGET_TYPE(type); +++ } +++ req->tcb(EOP_DONE, req, 0, 0, 0, 0); +++} +++ +++/* +++ * General purpose routine for determining datatypes. +++ */ +++ +++static void +++gdb_get_datatype(struct gnu_request *req) +++{ +++ struct type *type; +++ struct type *typedef_type; +++ expression_up expr; +++ struct symbol *sym; +++ struct value *val; +++ +++ if (gdb_CRASHDEBUG(2)) +++ console("gdb_get_datatype [%s] (a)\n", req->name); +++ +++ req->typecode = TYPE_CODE_UNDEF; +++ +++ /* +++ * lookup_symbol() will pick up struct and union names. +++ */ +++ sym = lookup_symbol(req->name, 0, STRUCT_DOMAIN, 0).symbol; +++ if (sym) { +++ req->typecode = TYPE_CODE(sym->type); +++ req->length = TYPE_LENGTH(sym->type); +++ if (req->member) +++ get_member_data(req, sym->type, 0, 1); +++ +++ if (TYPE_CODE(sym->type) == TYPE_CODE_ENUM) +++ walk_enum(sym->type, req); +++ +++ return; +++ } +++ +++ /* +++ * Otherwise parse the expression. +++ */ +++ if (gdb_CRASHDEBUG(2)) +++ console("gdb_get_datatype [%s] (b)\n", req->name); +++ +++ expr = parse_expression(req->name); +++ +++ +++ switch (expr.get()->elts[0].opcode) +++ { +++ case OP_VAR_VALUE: +++ if (gdb_CRASHDEBUG(2)) +++ console("expr->elts[0].opcode: OP_VAR_VALUE\n"); +++ type = expr.get()->elts[2].symbol->type; +++ if (req->tcb) { +++ long value = SYMBOL_VALUE(expr->elts[2].symbol); +++ /* callback with symbol value */ +++ req->typecode = TYPE_CODE(type); +++ req->tcb(EOP_VALUE, req, &value, 0, 0, 0); +++ drillDownType(req, type); +++ } else { +++ if (req->flags & GNU_VAR_LENGTH_TYPECODE) { +++ req->typecode = TYPE_CODE(type); +++ req->length = TYPE_LENGTH(type); +++ } +++ if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +++ req->typecode = TYPE_CODE(type); +++ req->value = SYMBOL_VALUE(expr->elts[2].symbol); +++ req->tagname = (char *)TYPE_TAG_NAME(type); +++ if (!req->tagname) { +++ val = evaluate_type(expr.get()); +++ eval_enum(value_type(val), req); +++ } +++ } +++ } +++ break; +++ +++ case OP_TYPE: +++ if (gdb_CRASHDEBUG(2)) +++ console("expr->elts[0].opcode: OP_TYPE\n"); +++ type = expr.get()->elts[1].type; +++ +++ if (req->tcb) { +++ drillDownType(req, type); +++ } else { +++ req->typecode = TYPE_CODE(type); +++ req->length = TYPE_LENGTH(type); +++ if (TYPE_CODE(type) == TYPE_CODE_TYPEDEF) { +++ req->is_typedef = TYPE_CODE_TYPEDEF; +++ if ((typedef_type = check_typedef(type))) { +++ req->typecode = TYPE_CODE(typedef_type); +++ req->length = TYPE_LENGTH(typedef_type); +++ type = typedef_type; +++ } +++ } +++ if (TYPE_CODE(type) == TYPE_CODE_ENUM) +++ walk_enum(type, req); +++ } +++ +++ if (req->member) +++ get_member_data(req, type, 0, 1); +++ +++ break; +++ +++ default: +++ if (gdb_CRASHDEBUG(2)) +++ console("expr.get()->elts[0].opcode: %d (?)\n", +++ expr.get()->elts[0].opcode); +++ break; +++ +++ } +++} +++ +++/* +++ * More robust enum list dump that gdb's, showing the value of each +++ * identifier, each on its own line. +++ */ +++static void +++walk_enum(struct type *type, struct gnu_request *req) +++{ +++ int i; +++ int len, print = (req->flags & GNU_PRINT_ENUMERATORS); +++ long long lastval; +++ +++ if (print) { +++ if (req->is_typedef) +++ fprintf_filtered(gdb_stdout, "typedef "); +++ if (TYPE_TAG_NAME(type)) +++ fprintf_filtered(gdb_stdout, "enum %s {\n", TYPE_TAG_NAME (type)); +++ else +++ fprintf_filtered(gdb_stdout, "enum {\n"); +++ } +++ +++ len = TYPE_NFIELDS (type); +++ for (i = 0; i < len; i++) { +++ if (print) +++ fprintf_filtered(gdb_stdout, " %s", TYPE_FIELD_NAME (type, i)); +++ lastval = TYPE_FIELD_ENUMVAL (type, i); +++ if (print) { +++ fprintf_filtered(gdb_stdout, " = %s", plongest(lastval)); +++ fprintf_filtered(gdb_stdout, "\n"); +++ } else if (req->tcb) +++ req->tcb(EOP_ENUMVAL, req, TYPE_FIELD_NAME (type, i), &lastval, 0, 0); +++ } +++ if (print) { +++ if (TYPE_TAG_NAME(type)) +++ fprintf_filtered(gdb_stdout, "};\n"); +++ else +++ fprintf_filtered(gdb_stdout, "} %s;\n", req->name); +++ } +++} +++ +++/* +++ * Given an enum type with no tagname, determine its value. +++ */ +++static void +++eval_enum(struct type *type, struct gnu_request *req) +++{ +++ int i; +++ int len; +++ long long lastval; +++ +++ len = TYPE_NFIELDS (type); +++ lastval = 0; +++ +++ for (i = 0; i < len; i++) { +++ if (lastval != TYPE_FIELD_ENUMVAL (type, i)) +++ lastval = TYPE_FIELD_ENUMVAL (type, i); +++ +++ if (STREQ(TYPE_FIELD_NAME(type, i), req->name)) { +++ req->tagname = "(unknown)"; +++ req->value = lastval; +++ return; +++ } +++ lastval++; +++ } +++} +++ +++/* +++ * Walk through a struct type's list of fields looking for the desired +++ * member field, and when found, return its relevant data. +++ */ +++static void +++get_member_data(struct gnu_request *req, struct type *type, long offset, int is_first) +++{ +++ short i; +++ struct field *nextfield; +++ short nfields; +++ struct type *typedef_type, *target_type; +++ +++ req->member_offset = -1; +++ +++ nfields = TYPE_MAIN_TYPE(type)->nfields; +++ nextfield = TYPE_MAIN_TYPE(type)->flds_bnds.fields; +++ +++ if (nfields == 0 && is_first /* The first call */) { +++ struct type *newtype; +++ newtype = lookup_transparent_type(req->name); +++ if (newtype) { +++ console("get_member_data(%s.%s): switching type from %lx to %lx\n", +++ req->name, req->member, type, newtype); +++ nfields = TYPE_MAIN_TYPE(newtype)->nfields; +++ nextfield = TYPE_MAIN_TYPE(newtype)->flds_bnds.fields; +++ } +++ } +++ +++ for (i = 0; i < nfields; i++) { +++ if (*nextfield->name == 0) { /* Anonymous struct/union */ +++ get_member_data(req, nextfield->type(), +++ offset + nextfield->loc.bitpos, 0); +++ if (req->member_offset != -1) +++ return; +++ } else { +++ /* callback may be just looking for a specific member name */ +++ if (req->tcb) { +++ if (req->tcb(EOP_MEMBER_NAME, req, nextfield->name, 0, 0, 0)) { +++ long bitpos = FIELD_BITPOS(*nextfield); +++ long bitsize = FIELD_BITSIZE(*nextfield); +++ long len = TYPE_LENGTH(nextfield->type()); +++ long byteOffset; +++ offset += nextfield->loc.bitpos; +++ byteOffset = offset/8; +++ console("EOP_MEMBER_SIZES\n"); +++ req->tcb(EOP_MEMBER_SIZES, req, &byteOffset, &len, &bitpos, &bitsize); +++ /* callback with full type info */ +++ drillDownType(req, nextfield->type()); +++ } +++ } else if (STREQ(req->member, nextfield->name)) { +++ req->member_offset = offset + nextfield->loc.bitpos; +++ req->member_length = TYPE_LENGTH(nextfield->type()); +++ req->member_typecode = TYPE_CODE(nextfield->type()); +++ req->member_main_type_name = (char *)TYPE_NAME(nextfield->type()); +++ req->member_main_type_tag_name = (char *)TYPE_TAG_NAME(nextfield->type()); +++ target_type = TYPE_TARGET_TYPE(nextfield->type()); +++ if (target_type) { +++ req->member_target_type_name = (char *)TYPE_NAME(target_type); +++ req->member_target_type_tag_name = (char *)TYPE_TAG_NAME(target_type); +++ } +++ if ((req->member_typecode == TYPE_CODE_TYPEDEF) && +++ (typedef_type = check_typedef(nextfield->type()))) { +++ req->member_length = TYPE_LENGTH(typedef_type); +++ } +++ return; +++ } +++ } +++ nextfield++; +++ } +++} +++ +++/* +++ * Check whether a command exists. If it doesn't, the command will be +++ * returned indirectly via the error_hook. +++ */ +++static void +++gdb_command_exists(struct gnu_request *req) +++{ +++ extern struct cmd_list_element *cmdlist; +++ +++ req->value = FALSE; +++ lookup_cmd((const char **)&req->name, cmdlist, "", NULL, 0, 1); +++ req->value = TRUE; +++} +++ +++static void +++gdb_function_numargs(struct gnu_request *req) +++{ +++ struct symbol *sym; +++ +++ sym = find_pc_function(req->pc); +++ +++ if (!sym || TYPE_CODE(sym->type) != TYPE_CODE_FUNC) { +++ req->flags |= GNU_COMMAND_FAILED; +++ return; +++ } +++ +++ req->value = (ulong)TYPE_NFIELDS(sym->type); +++} +++ +++struct load_module *gdb_current_load_module = NULL; +++ +++static void +++gdb_add_symbol_file(struct gnu_request *req) +++{ +++ struct load_module *lm; +++ int i; +++ int allsect = 0; +++ char *secname; +++ char buf[96]; +++ +++ gdb_current_load_module = lm = (struct load_module *)req->addr; +++ +++ req->name = lm->mod_namelist; +++ gdb_delete_symbol_file(req); +++ lm->loaded_objfile = NULL; +++ +++ if ((lm->mod_flags & MOD_NOPATCH) == 0) { +++ for (i = 0 ; i < lm->mod_sections; i++) { +++ if (STREQ(lm->mod_section_data[i].name, ".text") && +++ (lm->mod_section_data[i].flags & SEC_FOUND)) +++ allsect = 1; +++ } +++ +++ if (!allsect) { +++ sprintf(req->buf, "add-symbol-file %s 0x%lx %s", lm->mod_namelist, +++ lm->mod_text_start ? lm->mod_text_start : lm->mod_base, +++ lm->mod_flags & MOD_DO_READNOW ? "-readnow" : ""); +++ if (lm->mod_data_start) { +++ sprintf(buf, " -s .data 0x%lx", lm->mod_data_start); +++ strcat(req->buf, buf); +++ } +++ if (lm->mod_bss_start) { +++ sprintf(buf, " -s .bss 0x%lx", lm->mod_bss_start); +++ strcat(req->buf, buf); +++ } +++ if (lm->mod_rodata_start) { +++ sprintf(buf, " -s .rodata 0x%lx", lm->mod_rodata_start); +++ strcat(req->buf, buf); +++ } +++ } else { +++ sprintf(req->buf, "add-symbol-file %s 0x%lx %s", lm->mod_namelist, +++ lm->mod_text_start, lm->mod_flags & MOD_DO_READNOW ? +++ "-readnow" : ""); +++ for (i = 0; i < lm->mod_sections; i++) { +++ secname = lm->mod_section_data[i].name; +++ if ((lm->mod_section_data[i].flags & SEC_FOUND) && +++ !STREQ(secname, ".text")) { +++ if (lm->mod_section_data[i].addr) +++ sprintf(buf, " -s %s 0x%lx", secname, lm->mod_section_data[i].addr); +++ else +++ sprintf(buf, " -s %s 0x%lx", secname, +++ lm->mod_section_data[i].offset + lm->mod_base); +++ strcat(req->buf, buf); +++ } +++ } +++ } +++ } + + +-+ crash_target_init(); +++ if (gdb_CRASHDEBUG(1)) +++ fprintf_filtered(gdb_stdout, "%s\n", req->buf); + + +-+ /* Back to crash. */ +-+ main_loop(); +-+#endif +++ execute_command(req->buf, FALSE); +++ +++ for (objfile *objfile : current_program_space->objfiles ()) { +++ if (same_file((char *)objfile_name(objfile), lm->mod_namelist)) { +++ if (objfile->separate_debug_objfile) +++ lm->loaded_objfile = objfile->separate_debug_objfile; +++ else +++ lm->loaded_objfile = objfile; +++ break; +++ } +++ } +++ +++ if (!lm->loaded_objfile) +++ req->flags |= GNU_COMMAND_FAILED; +++} +++ +++static void +++gdb_delete_symbol_file(struct gnu_request *req) +++{ +++ for (objfile *objfile : current_program_space->objfiles ()) { +++ if (STREQ(objfile_name(objfile), req->name) || +++ same_file((char *)objfile_name(objfile), req->name)) { +++ objfile->unlink (); +++ break; +++ } +++ } +++ +++ if (gdb_CRASHDEBUG(2)) { +++ fprintf_filtered(gdb_stdout, "current object files:\n"); +++ for (objfile *objfile : current_program_space->objfiles ()) +++ fprintf_filtered(gdb_stdout, " %s\n", objfile_name(objfile)); +++ } +++} + + +- /* NOTE: cagney/1999-11-07: There is probably no reason for not +- moving this loop and the code found in captured_command_loop() +- into the command_loop() proper. The main thing holding back that +-@@ -1256,6 +1298,9 @@ captured_main (void *data) +- { +- exception_print (gdb_stderr, ex); +- } +-+#ifdef CRASH_MERGE +-+ console("\n"); +-+#endif +- } +- /* No exit -- exit is through quit_command. */ +- } +-@@ -1277,6 +1322,22 @@ gdb_main (struct captured_main_args *args) +- return 1; +- } +- +-+#ifdef CRASH_MERGE + +/* +-+ * NOTE: adapted from gdb.c, which is no longer built in; changed name of +-+ * original main() to gdb_main_entry() for use as crash entry point +++ * Walk through all minimal_symbols, patching their values with the +++ * correct addresses. + + */ +-+int +-+gdb_main_entry (int argc, char **argv) +++static void +++gdb_patch_symbol_values(struct gnu_request *req) + +{ +-+ struct captured_main_args args; +-+ memset (&args, 0, sizeof args); +-+ args.argc = argc; +-+ args.argv = argv; +-+ args.interpreter_p = INTERP_CONSOLE; +-+ return gdb_main (&args); +++ req->name = PATCH_KERNEL_SYMBOLS_START; +++ patch_kernel_symbol(req); +++ +++ for (objfile *objfile : current_program_space->objfiles ()) +++ for (minimal_symbol *msymbol : objfile->msymbols ()) +++ { +++ req->name = (char *)msymbol->m_name; +++ req->addr = (ulong)(&MSYMBOL_VALUE(msymbol)); +++ if (!patch_kernel_symbol(req)) { +++ req->flags |= GNU_COMMAND_FAILED; +++ break; +++ } +++ } +++ +++ req->name = PATCH_KERNEL_SYMBOLS_STOP; +++ patch_kernel_symbol(req); +++ +++ clear_symtab_users(0); +++ gdb_merge_flags |= KERNEL_SYMBOLS_PATCHED; + +} +-+#endif +- +- /* Don't use *_filtered for printing help. We don't want to prompt +- for continue no matter how small the screen or how much we're going +---- gdb-10.2/gdb/objfiles.h.orig +-+++ gdb-10.2/gdb/objfiles.h +-@@ -747,9 +747,9 @@ extern int objfile_has_full_symbols (struct objfile *objfile); +- +- extern int objfile_has_symbols (struct objfile *objfile); +- +--extern int have_partial_symbols (void); +-+extern "C" int have_partial_symbols (void); +- +--extern int have_full_symbols (void); +-+extern "C" int have_full_symbols (void); +- +- extern void objfile_set_sym_fns (struct objfile *objfile, +- const struct sym_fns *sf); +---- gdb-10.2/gdb/printcmd.c.orig +-+++ gdb-10.2/gdb/printcmd.c +-@@ -524,6 +524,9 @@ set_next_address (struct gdbarch *gdbarch, CORE_ADDR addr) +- form. However note that DO_DEMANGLE can be overridden by the specific +- settings of the demangle and asm_demangle variables. Returns +- non-zero if anything was printed; zero otherwise. */ +-+#ifdef CRASH_MERGE +-+extern "C" int gdb_print_callback(unsigned long); +-+#endif +- +- int +- print_address_symbolic (struct gdbarch *gdbarch, CORE_ADDR addr, +-@@ -535,6 +538,12 @@ print_address_symbolic (struct gdbarch *gdbarch, CORE_ADDR addr, +- int offset = 0; +- int line = 0; +- +-+#ifdef CRASH_MERGE +-+ if (!gdb_print_callback(addr)) { +-+ return 0; +-+ } +-+#endif + + +- if (build_address_symbolic (gdbarch, addr, do_demangle, false, &name, +- &offset, &filename, &line, &unmapped)) +- return 0; +-@@ -1221,6 +1230,43 @@ print_command_1 (const char *args, int voidprint) +- print_value (val, print_opts); +- } +- +-+static void +-+print_command_2 (const char *args, int voidprint) +-+{ +-+ struct value *val; +-+ value_print_options print_opts; +++static void +++gdb_get_symbol_type(struct gnu_request *req) +++{ +++ expression_up expr; +++ struct value *val; +++ struct type *type; +++ struct type *target_type; +++ +++ req->typecode = TYPE_CODE_UNDEF; +++ +++ expr = parse_expression (req->name); +++ val = evaluate_type (expr.get()); +++ +++ type = value_type(val); +++ +++ req->type_name = (char *)TYPE_MAIN_TYPE(type)->name; +++ req->typecode = TYPE_MAIN_TYPE(type)->code; +++ req->length = type->length; +++ req->type_tag_name = (char *)TYPE_TAG_NAME(type); +++ target_type = TYPE_MAIN_TYPE(type)->target_type; +++ +++ if (target_type) { +++ req->target_typename = (char *)TYPE_MAIN_TYPE(target_type)->name; +++ req->target_typecode = TYPE_MAIN_TYPE(target_type)->code; +++ req->target_length = target_type->length; +++ } +++ +++ if (req->member) +++ get_member_data(req, type, 0, 1); +++} +++ +++static void +++gdb_debug_command(struct gnu_request *req) +++{ +++ +++} +++ +++/* +++ * Only necessary on "patched" kernel symbol sessions, and called only by +++ * lookup_symbol(), pull a symbol value bait-and-switch operation by altering +++ * either a data symbol's address value or a text symbol's block start address. +++ */ +++static void +++gdb_bait_and_switch(char *name, struct symbol *sym) +++{ +++ struct bound_minimal_symbol msym; +++ struct block *block; +++ +++ if ((gdb_merge_flags & KERNEL_SYMBOLS_PATCHED) && +++ (msym = lookup_minimal_symbol(name, NULL, gdb_kernel_objfile)).minsym) { +++ if (SYMBOL_CLASS(sym) == LOC_BLOCK) { +++ block = (struct block *)SYMBOL_BLOCK_VALUE(sym); +++ BLOCK_START(block) = BMSYMBOL_VALUE_ADDRESS(msym); +++ } else +++ SET_SYMBOL_VALUE_ADDRESS(sym, BMSYMBOL_VALUE_ADDRESS(msym)); +++ } +++} +++ +++#include "valprint.h" +++ +++void +++get_user_print_option_address(struct gnu_request *req) +++{ +++ extern struct value_print_options user_print_options; +++ +++ req->addr = 0; +++ +++ if (strcmp(req->name, "output_format") == 0) +++ req->addr = (ulong)&user_print_options.output_format; +++ if (strcmp(req->name, "print_max") == 0) +++ req->addr = (ulong)&user_print_options.print_max; +++ if (strcmp(req->name, "prettyprint_structs") == 0) +++ req->addr = (ulong)&user_print_options.prettyformat_structs; +++ if (strcmp(req->name, "prettyprint_arrays") == 0) +++ req->addr = (ulong)&user_print_options.prettyformat_arrays; +++ if (strcmp(req->name, "repeat_count_threshold") == 0) +++ req->addr = (ulong)&user_print_options.repeat_count_threshold; +++ if (strcmp(req->name, "stop_print_at_null") == 0) +++ req->addr = (ulong)&user_print_options.stop_print_at_null; +++ if (strcmp(req->name, "output_radix") == 0) +++ req->addr = (ulong)&output_radix; +++} +++ +++CORE_ADDR crash_text_scope; +++ +++static void +++gdb_set_crash_block(struct gnu_request *req) +++{ +++ if (!req->addr) { /* debug */ +++ crash_text_scope = 0; +++ return; +++ } +++ +++ if ((req->addr2 = (ulong)block_for_pc(req->addr))) +++ crash_text_scope = req->addr; +++ else { +++ crash_text_scope = 0; +++ req->flags |= GNU_COMMAND_FAILED; +++ } +++} +++ +++static const struct block * +++gdb_get_crash_block(void) +++{ +++ if (crash_text_scope) +++ return block_for_pc(crash_text_scope); +++ else +++ return NULL; +++} +++ +++static long +++lookup_struct_contents(struct gnu_request *req) +++{ +++ int i; +++ long r; +++ struct field *f; +++ struct main_type *m; +++ const char *n; +++ struct main_type *top_m = (struct main_type *)req->addr; +++ char *type_name = req->type_name; +++ +++ if (!top_m || !type_name) +++ return 0; +++ +++ for (i = 0; i < top_m->nfields; i++) +++ { +++ f = top_m->flds_bnds.fields + i; +++ if (!f->type()) +++ continue; +++ m = f->type()->main_type; + + +-+ get_user_print_options (&print_opts); +-+ /* Override global settings with explicit options, if any. */ +-+ auto group = make_value_print_options_def_group (&print_opts); +-+ gdb::option::process_options +-+ (&args, gdb::option::PROCESS_OPTIONS_REQUIRE_DELIMITER, group); +++ // If the field is an array, check the target type - +++ // it might be structure, or might not be. +++ // - struct request_sock *syn_table[0]; +++ // here m->target_type->main_type->code is expected +++ // to be TYPE_CODE_PTR +++ // - struct list_head vec[TVN_SIZE]; +++ // here m->target_type->main_type->code should be +++ // TYPE_CODE_STRUCT +++ if (m->code == TYPE_CODE_ARRAY && m->target_type) +++ m = m->target_type->main_type; + + +-+ print_command_parse_format (&args, "print", &print_opts); +++ /* Here is a recursion. +++ * If we have struct variable (not pointer), +++ * scan this inner structure +++ */ +++ if (m->code == TYPE_CODE_STRUCT) { +++ req->addr = (ulong)m; +++ r = lookup_struct_contents(req); +++ req->addr = (ulong)top_m; +++ if (r) +++ return 1; +++ } + + +-+ const char *exp = args; +++ if (m->code == TYPE_CODE_PTR && m->target_type) +++ m = m->target_type->main_type; +++ if (m->name) +++ n = m->name; +++ else +++ continue; + + +-+ if (exp != nullptr && *exp) +-+ { +-+ expression_up expr = parse_expression (exp); +-+ val = evaluate_expression (expr.get ()); +++ if (strstr(n, type_name)) +++ return 1; + + } +-+ else +-+ val = access_value_history (0); + + +-+ printf_filtered ("%d %d %ld %ld %ld %ld\n", +-+ check_typedef(value_type (val))->code(), +-+ TYPE_UNSIGNED (check_typedef(value_type (val))), +-+ TYPE_LENGTH (check_typedef(value_type(val))), +-+ value_offset (val), value_bitpos (val), value_bitsize(val)); +++ return 0; + +} + + + +static void +-+printm_command (const char *exp, int from_tty) +++iterate_datatypes (struct gnu_request *req) + +{ +-+ print_command_2 (exp, 1); +-+} +++ for (objfile *objfile : current_program_space->objfiles ()) +++ { +++ if (objfile->sf) +++ objfile->sf->qf->expand_all_symtabs(objfile); + + +- /* See valprint.h. */ +- +- void +-@@ -2855,6 +2901,12 @@ but no count or size letter (see \"x\" command)."), +- c = add_com ("print", class_vars, print_command, print_help.c_str ()); +- set_cmd_completer_handle_brkchars (c, print_command_completer); +- add_com_alias ("p", "print", class_vars, 1); +++ for (compunit_symtab *cust : objfile->compunits ()) +++ { +++ const struct blockvector *bv = COMPUNIT_BLOCKVECTOR (cust); + + +-+ c = add_com ("printm", class_vars, printm_command, _("\ +-+Similar to \"print\" command, but it used to print the type, size, offset,\n\ +-+bitpos and bitsize of the expression EXP.")); +-+ set_cmd_completer (c, expression_completer); +++ for (int i = GLOBAL_BLOCK; i <= STATIC_BLOCK; ++i) +++ { +++ const struct block *b = BLOCKVECTOR_BLOCK (bv, i); +++ struct block_iterator iter; +++ struct symbol *sym; + + +- add_com_alias ("inspect", "print", class_vars, 1); +- +- add_setshow_uinteger_cmd ("max-symbolic-offset", no_class, +---- gdb-10.2/gdb/psymtab.c.orig +-+++ gdb-10.2/gdb/psymtab.c +-@@ -283,6 +283,9 @@ find_pc_sect_psymtab_closer (struct objfile *objfile, +- return best_pst; +- } +- +-+#ifdef CRASH_MERGE +-+ extern "C" int gdb_line_number_callback(unsigned long, unsigned long, unsigned long); +-+#endif +- /* Find which partial symtab contains PC and SECTION. Return NULL if +- none. We return the psymtab that contains a symbol whose address +- exactly matches PC, or, if we cannot find an exact match, the +-@@ -363,7 +366,12 @@ find_pc_sect_psymtab (struct objfile *objfile, CORE_ADDR pc, +- +- best_pst = find_pc_sect_psymtab_closer (objfile, pc, section, pst, +- msymbol); +-+#ifdef CRASH_MERGE +-+ if ((best_pst != NULL) && +-+ gdb_line_number_callback(pc, pst->text_low (objfile), pst->text_high (objfile))) +-+#else +- if (best_pst != NULL) +-+#endif +- return best_pst; +- } +- +---- gdb-10.2/gdb/symfile.c.orig +-+++ gdb-10.2/gdb/symfile.c +-@@ -652,7 +652,26 @@ default_symfile_offsets (struct objfile *objfile, +- for (cur_sec = abfd->sections; cur_sec != NULL; cur_sec = cur_sec->next) +- /* We do not expect this to happen; just skip this step if the +- relocatable file has a section with an assigned VMA. */ +-- if (bfd_section_vma (cur_sec) != 0) +-+ if (bfd_section_vma (cur_sec) != 0 +-+ /* +-+ * Kernel modules may have some non-zero VMAs, i.e., like the +-+ * __ksymtab and __ksymtab_gpl sections in this example: +-+ * +-+ * Section Headers: +-+ * [Nr] Name Type Address Offset +-+ * Size EntSize Flags Link Info Align +-+ * ... +-+ * [ 8] __ksymtab PROGBITS 0000000000000060 0000ad90 +-+ * 0000000000000010 0000000000000000 A 0 0 16 +-+ * [ 9] .rela__ksymtab RELA 0000000000000000 0000ada0 +-+ * 0000000000000030 0000000000000018 43 8 8 +-+ * [10] __ksymtab_gpl PROGBITS 0000000000000070 0000add0 +-+ * 00000000000001a0 0000000000000000 A 0 0 16 +-+ * ... +-+ * +-+ * but they should be treated as if they are NULL. +-+ */ +-+ && strncmp (bfd_section_name (cur_sec), "__k", 3) != 0) +- break; +- +- if (cur_sec == NULL) +-@@ -1083,6 +1102,12 @@ symbol_file_add_with_addrs (bfd *abfd, const char *name, +- if (mainline) +- flags |= OBJF_MAINLINE; +- objfile = objfile::make (abfd, name, flags, parent); +-+#ifdef CRASH_MERGE +-+ if (add_flags & SYMFILE_MAINLINE) { +-+ extern struct objfile *gdb_kernel_objfile; +-+ gdb_kernel_objfile = objfile; +-+ } +-+#endif +- +- /* We either created a new mapped symbol table, mapped an existing +- symbol table file which has not had initial symbol reading +-@@ -1375,6 +1400,10 @@ show_debug_file_directory (struct ui_file *file, int from_tty, +- #if ! defined (DEBUG_SUBDIRECTORY) +- #define DEBUG_SUBDIRECTORY ".debug" +- #endif +-+#ifdef CRASH_MERGE +-+extern "C" int check_specified_module_tree(const char *, const char *); +-+extern "C" char *check_specified_kernel_debug_file(); +-+#endif +- +- /* Find a separate debuginfo file for OBJFILE, using DIR as the directory +- where the original file resides (may not be the same as +-@@ -1410,6 +1439,15 @@ find_separate_debug_file (const char *dir, +- if (separate_debug_file_exists (debugfile, crc32, objfile)) +- return debugfile; +- +-+#ifdef CRASH_MERGE +-+{ +-+ if (check_specified_module_tree(objfile_name (objfile), debugfile.c_str()) && +-+ separate_debug_file_exists(debugfile, crc32, objfile)) { +-+ return debugfile; +-+ } +++ ALL_BLOCK_SYMBOLS (b, iter, sym) +++ { +++ QUIT; +++ +++ if (SYMBOL_CLASS (sym) != LOC_TYPEDEF) +++ continue; +++ +++ if (req->highest && +++ !(req->lowest <= sym->type->length && sym->type->length <= req->highest)) +++ continue; +++ +++ req->addr = (ulong)(sym->type->main_type); +++ req->name = (char *)(sym->m_name); +++ req->length = sym->type->length; +++ +++ if (req->member) { +++ req->value = lookup_struct_contents(req); +++ if (!req->value) +++ continue; +++ } +++ req->callback(req, req->callback_data); +++ } +++ } +++ } +++ } + +} + +#endif ++diff -Nuar gdb-10.2/gdb/syscalls/sw_64-linux.xml gdb-10.2/gdb/syscalls/sw_64-linux.xml ++--- gdb-10.2/gdb/syscalls/sw_64-linux.xml 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/syscalls/sw_64-linux.xml 2025-04-16 17:06:51.982086800 +0800 ++@@ -0,0 +1,478 @@ +++ +++ + + +- return debugfile; +- } +- +-@@ -2334,8 +2380,10 @@ add_symbol_file_command (const char *args, int from_tty) +- else if (section_addrs.empty ()) +- printf_unfiltered ("\n"); +- +-+#ifndef CRASH_MERGE +- if (from_tty && (!query ("%s", ""))) +- error (_("Not confirmed.")); +-+#endif +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/syscalls/sw_64-linux.xml.in gdb-10.2/gdb/syscalls/sw_64-linux.xml.in ++--- gdb-10.2/gdb/syscalls/sw_64-linux.xml.in 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdb/syscalls/sw_64-linux.xml.in 2025-04-16 17:06:51.992086800 +0800 ++@@ -0,0 +1,479 @@ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ +++ ++diff -Nuar gdb-10.2/gdb/ui-file.h gdb-10.2/gdb/ui-file.h ++--- gdb-10.2/gdb/ui-file.h 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdb/ui-file.h 2025-04-16 17:06:41.912086800 +0800 ++@@ -195,10 +195,10 @@ + +- objf = symbol_file_add (filename.get (), add_flags, §ion_addrs, +- flags); +-@@ -3622,6 +3670,15 @@ bfd_byte * +- symfile_relocate_debug_section (struct objfile *objfile, +- asection *sectp, bfd_byte *buf) +- { +-+#ifdef CRASH_MERGE +-+ /* Executable files have all the relocations already resolved. +-+ * Handle files linked with --emit-relocs. +-+ * http://sources.redhat.com/ml/gdb/2006-08/msg00137.html +-+ */ +-+ bfd *abfd = objfile->obfd; +-+ if ((abfd->flags & EXEC_P) != 0) +-+ return NULL; +-+#endif +- gdb_assert (objfile->sf->sym_relocate); ++ bool can_emit_style_escape () override; + +- return (*objfile->sf->sym_relocate) (objfile, sectp, buf); +---- gdb-10.2/gdb/symtab.c.orig +-+++ gdb-10.2/gdb/symtab.c +-@@ -1870,27 +1870,46 @@ search_name_hash (enum language language, const char *search_name) +- variable and thus can probably assume it will never hit the C++ +- code). */ ++-private: ++ /* Sets the internal stream to FILE, and saves the FILE's file ++ descriptor in M_FD. */ ++ void set_stream (FILE *file); +++private: + +-+#ifdef CRASH_MERGE +-+static void gdb_bait_and_switch(char *, struct symbol *); +-+#endif +-+ +- struct block_symbol +- lookup_symbol_in_language (const char *name, const struct block *block, +- const domain_enum domain, enum language lang, +- struct field_of_this_result *is_a_field_of_this) ++ /* The file. */ ++ FILE *m_file; ++diff -Nuar gdb-10.2/gdb/xml-syscall.c gdb-10.2/gdb/xml-syscall.c ++--- gdb-10.2/gdb/xml-syscall.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdb/xml-syscall.c 2025-04-16 17:06:41.912086800 +0800 ++@@ -37,7 +37,11 @@ ++ static void ++ syscall_warn_user (void) + { +-+ struct block_symbol result; +- demangle_result_storage storage; +- const char *modified_name = demangle_for_lookup (name, lang, storage); +- +-- return lookup_symbol_aux (modified_name, +-+ result = lookup_symbol_aux (modified_name, +- symbol_name_match_type::FULL, +- block, domain, lang, +- is_a_field_of_this); + +#ifdef CRASH_MERGE +-+ if (result.symbol && (domain == VAR_DOMAIN)) +-+ gdb_bait_and_switch((char *)modified_name, result.symbol); +++ static int have_warned = 1; +++#else ++ static int have_warned = 0; + +#endif +-+ return result; +- } +- +- /* See symtab.h. */ +- +-+#ifdef CRASH_MERGE +-+static const struct block *gdb_get_crash_block(void); ++ if (!have_warned) ++ { ++ have_warned = 1; ++diff -Nuar gdb-10.2/gdbserver/configure.srv gdb-10.2/gdbserver/configure.srv ++--- gdb-10.2/gdbserver/configure.srv 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdbserver/configure.srv 2025-04-16 17:06:51.992086800 +0800 ++@@ -372,8 +372,31 @@ ++ srv_linux_regsets=yes ++ srv_linux_thread_db=yes ++ ;; +++# sw_64*-*-linux*) srv_regobj="sw_64-linux.o" +++# srv_regobj="${srv_regobj} sw_64-linux.o" +++# srv_tgtobj="$srv_linux_obj linux-sw_64-low.o" +++# srv_tgtobj="${srv_tgtobj} nat/sw_64-linux-watch.o" +++# srv_xmlfiles="sw_64-linux.xml" +++# srv_xmlfiles="${srv_xmlfiles} sw_64-linux.xml" +++# srv_xmlfiles="${srv_xmlfiles} sw_64-cpu.xml" +++# srv_xmlfiles="${srv_xmlfiles} sw_64-fpu.xml" +++# srv_xmlfiles="${srv_xmlfiles} sw_64-efu.xml" +++# srv_xmlfiles="${srv_xmlfiles} sw_64-vec.xml" +++# srv_linux_regsets=yes +++# srv_linux_usrregs=yes +++# srv_linux_thread_db=yes +++# ;; +++ +++# alpha*-*-linux* | sw_64*-*-linux*) srv_regobj="sw_64-linux.o" +++# srv_tgtobj="linux-sw_64-low.o sw_64-linux-watch.o" +++# srv_tgtobj="${srv_tgtobj} $srv_linux_obj " +++# srv_linux_usrregs=yes +++# srv_linux_regsets=no +++# srv_linux_thread_db=yes +++# srv_xmlfiles="sw_64-linux.xml" +++# ;; ++ *) ++- # Who are you? +++ # Who are you? SBW_ ++ UNSUPPORTED=1 ++ ;; ++ esac ++diff -Nuar gdb-10.2/gdbserver/linux-sw_64-low.cc gdb-10.2/gdbserver/linux-sw_64-low.cc ++--- gdb-10.2/gdbserver/linux-sw_64-low.cc 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/gdbserver/linux-sw_64-low.cc 2025-04-16 17:06:51.992086800 +0800 ++@@ -0,0 +1,958 @@ +++/* GNU/Linux/sw_64 specific low level interface, for the remote server for GDB. +++ Copyright (C) 1995-2020 Free Software Foundation, Inc. +++ +++ This file is part of GDB. +++ +++ This program is free software; you can redistribute it and/or modify +++ it under the terms of the GNU General Public License as published by +++ the Free Software Foundation; either version 3 of the License, or +++ (at your option) any later version. +++ +++ This program is distributed in the hope that it will be useful, +++ but WITHOUT ANY WARRANTY; without even the implied warranty of +++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +++ GNU General Public License for more details. +++ +++ You should have received a copy of the GNU General Public License +++ along with this program. If not, see . */ +++ +++#include "server.h" +++#include "linux-low.h" +++#include "tdesc.h" +++#include "nat/gdb_ptrace.h" +++#include +++ +++#include "nat/sw_64-linux-watch.h" +++#include "gdb_proc_service.h" +++ +++ +++/* Linux target op definitions for the MIPS architecture. */ +++ +++class sw_64_target : public linux_process_target +++{ +++public: +++ +++ const regs_info *get_regs_info () override; +++ +++ const gdb_byte *sw_breakpoint_from_kind (int kind, int *size) override; +++ +++ bool supports_z_point_type (char z_type) override; +++ +++protected: +++ +++ void low_arch_setup () override; +++ +++ bool low_cannot_fetch_register (int regno) override; +++ +++ bool low_cannot_store_register (int regno) override; +++ +++ bool low_fetch_register (regcache *regcache, int regno) override; +++ +++ bool low_supports_breakpoints () override; +++ +++ CORE_ADDR low_get_pc (regcache *regcache) override; +++ +++ void low_set_pc (regcache *regcache, CORE_ADDR newpc) override; +++ +++ bool low_breakpoint_at (CORE_ADDR pc) override; +++ +++ int low_insert_point (raw_bkpt_type type, CORE_ADDR addr, +++ int size, raw_breakpoint *bp) override; +++ +++ int low_remove_point (raw_bkpt_type type, CORE_ADDR addr, +++ int size, raw_breakpoint *bp) override; +++ +++ bool low_stopped_by_watchpoint () override; +++ +++ CORE_ADDR low_stopped_data_address () override; +++ +++ void low_collect_ptrace_register (regcache *regcache, int regno, +++ char *buf) override; +++ +++ void low_supply_ptrace_register (regcache *regcache, int regno, +++ const char *buf) override; +++ +++ arch_process_info *low_new_process () override; +++ +++ void low_delete_process (arch_process_info *info) override; +++ +++ void low_new_thread (lwp_info *) override; +++ +++ void low_delete_thread (arch_lwp_info *) override; +++ +++ void low_new_fork (process_info *parent, process_info *child) override; +++ +++ void low_prepare_to_resume (lwp_info *lwp) override; +++}; +++ +++/* The singleton target ops object. */ +++ +++static sw_64_target the_sw_64_target; +++ +++/* Defined in auto-generated file sw_64-linux.c. */ +++void init_registers_sw_64_linux (void); +++extern const struct target_desc *tdesc_sw_64_linux; +++ +++ +++#ifndef PTRACE_GET_THREAD_AREA +++#define PTRACE_GET_THREAD_AREA 25 + +#endif + + +- struct block_symbol +- lookup_symbol (const char *name, const struct block *block, +- domain_enum domain, +- struct field_of_this_result *is_a_field_of_this) +- { +-+#ifdef CRASH_MERGE +-+ if (!block) +-+ block = gdb_get_crash_block(); +++#ifdef HAVE_SYS_REG_H +++#include + +#endif +++//#define sw_64_num_regs 73 +++#include +++#include + + +- return lookup_symbol_in_language (name, block, domain, +- current_language->la_language, +- is_a_field_of_this); +-@@ -6886,3 +6905,806 @@ If zero then the symbol cache is disabled."), +- gdb::observers::new_objfile.attach (symtab_new_objfile_observer); +- gdb::observers::free_objfile.attach (symtab_free_objfile_observer); +- } + + +-+#ifdef CRASH_MERGE +-+#include "gdb-stabs.h" +-+#include "gdbsupport/version.h" +-+#define GDB_COMMON +-+#include "../../defs.h" +++union sw_64_register +++{ +++ unsigned char buf[8]; + + +-+static void get_member_data(struct gnu_request *, struct type *, long, int); +-+static void dump_enum(struct type *, struct gnu_request *); +-+static void eval_enum(struct type *, struct gnu_request *); +-+static void gdb_get_line_number(struct gnu_request *); +-+static void gdb_get_datatype(struct gnu_request *); +-+static void gdb_get_symbol_type(struct gnu_request *); +-+static void gdb_command_exists(struct gnu_request *); +-+static void gdb_debug_command(struct gnu_request *); +-+static void gdb_function_numargs(struct gnu_request *); +-+static void gdb_add_symbol_file(struct gnu_request *); +-+static void gdb_delete_symbol_file(struct gnu_request *); +-+static void gdb_patch_symbol_values(struct gnu_request *); +-+static void get_user_print_option_address(struct gnu_request *); +-+extern int get_frame_offset(CORE_ADDR); +-+static void gdb_set_crash_block(struct gnu_request *); +-+extern "C" void gdb_command_funnel(struct gnu_request *); +-+void gdb_command_funnel_1(struct gnu_request *); +-+static long lookup_struct_contents(struct gnu_request *); +-+static void iterate_datatypes(struct gnu_request *); +++ /* Deliberately signed, for proper sign extension. */ +++ int reg32; +++ long long reg64; +++}; + + +-+struct objfile *gdb_kernel_objfile = { 0 }; +++int gcc_backtrace(); +++void exc_handler(int, siginfo_t*, void*); +++extern int tohex (int nib); +++extern int bin2hex (const gdb_byte *bin, char *hex, int count); +++extern long dva_match_addr; +++extern long status_cg[]; +++extern struct lwp_info *add_lwp (ptid_t ptid); + + +-+static ulong gdb_merge_flags = 0; +-+#define KERNEL_SYMBOLS_PATCHED (0x1) +++/* Return the ptrace ``address'' of register REGNO. */ +++#define FPR_BASE 32 + + +-+#undef STREQ +-+#define STREQ(A, B) (A && B && (strcmp(A, B) == 0)) +-+#define TYPE_CODE(t) (t->code ()) +-+#define TYPE_TAG_NAME(t) (TYPE_MAIN_TYPE(t)->name) +-+#define TYPE_NFIELDS(t) (t->num_fields ()) +-+#define TYPE_NAME(t) (t->name ()) +++/* 0~63 general, 64 pc, 65-69 hwbpt/da_match,70-101 simd */ +++static int sw_64_regmap[] = { +++ 0, 1, 2, 3, 4, 5, 6, 7, +++ 8, 9, 10, 11, 12, 13, 14, 15, +++ 16, 17, 18, 19, 20, 21, 22, 23, +++ 24, 25, 26, 27, 28, 29, 30, 31, +++ FPR_BASE, FPR_BASE + 1, FPR_BASE + 2, FPR_BASE + 3, +++ FPR_BASE + 4, FPR_BASE + 5, FPR_BASE + 6, FPR_BASE + 7, +++ FPR_BASE + 8, FPR_BASE + 9, FPR_BASE + 10, FPR_BASE + 11, +++ FPR_BASE + 12, FPR_BASE + 13, FPR_BASE + 14, FPR_BASE + 15, +++ FPR_BASE + 16, FPR_BASE + 17, FPR_BASE + 18, FPR_BASE + 19, +++ FPR_BASE + 20, FPR_BASE + 21, FPR_BASE + 22, FPR_BASE + 23, +++ FPR_BASE + 24, FPR_BASE + 25, FPR_BASE + 26, FPR_BASE + 27, +++ FPR_BASE + 28, FPR_BASE + 29, FPR_BASE + 30, FPR_BASE + 31, +++ REG_PC, -1,-1, /* NULL and unique */ +++ REG_V0F1, REG_V0F1 + 1, REG_V0F1 + 2, REG_V0F1 + 3, +++ REG_V0F1 + 4, REG_V0F1 + 5, REG_V0F1 + 6, REG_V0F1 + 7, +++ REG_V0F1 + 8, REG_V0F1 + 9, REG_V0F1 + 10, REG_V0F1 + 11, +++ REG_V0F1 + 12, REG_V0F1 + 13, REG_V0F1 + 14, REG_V0F1 + 15, +++ REG_V0F1 + 16, REG_V0F1 + 17, REG_V0F1 + 18, REG_V0F1 + 19, +++ REG_V0F1 + 20, REG_V0F1 + 21, REG_V0F1 + 22, REG_V0F1 + 23, +++ REG_V0F1 + 24, REG_V0F1 + 25, REG_V0F1 + 26, REG_V0F1 + 27, +++ REG_V0F1 + 28, REG_V0F1 + 29, REG_V0F1 + 30, REG_V0F1 + 31, +++ REG_V0F2, REG_V0F2 + 1, REG_V0F2 + 2, REG_V0F2 + 3, +++ REG_V0F2 + 4, REG_V0F2 + 5, REG_V0F2 + 6, REG_V0F2 + 7, +++ REG_V0F2 + 8, REG_V0F2 + 9, REG_V0F2 + 10, REG_V0F2 + 11, +++ REG_V0F2 + 12, REG_V0F2 + 13, REG_V0F2 + 14, REG_V0F2 + 15, +++ REG_V0F2 + 16, REG_V0F2 + 17, REG_V0F2 + 18, REG_V0F2 + 19, +++ REG_V0F2 + 20, REG_V0F2 + 21, REG_V0F2 + 22, REG_V0F2 + 23, +++ REG_V0F2 + 24, REG_V0F2 + 25, REG_V0F2 + 26, REG_V0F2 + 27, +++ REG_V0F2 + 28, REG_V0F2 + 29, REG_V0F2 + 30, REG_V0F2 + 31, +++ REG_V0F3, REG_V0F3 + 1, REG_V0F3 + 2, REG_V0F3 + 3, +++ REG_V0F3 + 4, REG_V0F3 + 5, REG_V0F3 + 6, REG_V0F3 + 7, +++ REG_V0F3 + 8, REG_V0F3 + 9, REG_V0F3 + 10, REG_V0F3 + 11, +++ REG_V0F3 + 12, REG_V0F3 + 13, REG_V0F3 + 14, REG_V0F3 + 15, +++ REG_V0F3 + 16, REG_V0F3 + 17, REG_V0F3 + 18, REG_V0F3 + 19, +++ REG_V0F3 + 20, REG_V0F3 + 21, REG_V0F3 + 22, REG_V0F3 + 23, +++ REG_V0F3 + 24, REG_V0F3 + 25, REG_V0F3 + 26, REG_V0F3 + 27, +++ REG_V0F3 + 28, REG_V0F3 + 29, REG_V0F3 + 30, REG_V0F3 + 31, +++ -1, +++}; + + +-+/* +-+ * All commands from above come through here. +-+ */ +-+void +-+gdb_command_funnel(struct gnu_request *req) +++ +++/* Try peeking at an arbitrarily chosen DSP register and pick the available +++ user register set accordingly. */ +++ +++static const struct target_desc * +++sw_64_read_description (void) + +{ +-+ try { +-+ gdb_command_funnel_1(req); +-+ } catch (const gdb_exception &ex) { +-+ if (req->flags & GNU_RETURN_ON_ERROR) +-+ req->flags |= GNU_COMMAND_FAILED; +-+ else +-+ throw ex; +-+ } +++ return tdesc_sw_64_linux; + +} + + + +void +-+gdb_command_funnel_1(struct gnu_request *req) +++sw_64_target::low_arch_setup () + +{ +-+ struct symbol *sym; +-+ +-+ if (req->command != GNU_VERSION && req->command != GNU_USER_PRINT_OPTION) { +-+ (dynamic_castgdb_stdout)->set_stream(req->fp); +-+ (dynamic_castgdb_stderr)->set_stream(req->fp); +-+ } +++ current_process ()->tdesc = sw_64_read_description (); +++} + + +-+ switch (req->command) +-+ { +-+ case GNU_VERSION: +-+ req->buf = (char *)version; +-+ break; +++/* Per-process arch-specific data we want to keep. */ + + +-+ case GNU_PASS_THROUGH: +-+ execute_command(req->buf, +-+ req->flags & GNU_FROM_TTY_OFF ? FALSE : TRUE); +-+ break; +++struct arch_process_info +++{ +++//#if 0 +++/* -1 if the kernel and/or CPU do not support watch registers. +++ 1 if watch_readback is valid and we can read style, num_valid +++ and the masks. +++ 0 if we need to read the watch_readback. */ + + +-+ case GNU_USER_PRINT_OPTION: +-+ get_user_print_option_address(req); +-+ break; +++ int watch_readback_valid; + + +-+ case GNU_RESOLVE_TEXT_ADDR: +-+ sym = find_pc_function(req->addr); +-+ if (!sym || TYPE_CODE(sym->type) != TYPE_CODE_FUNC) +-+ req->flags |= GNU_COMMAND_FAILED; +-+ break; +++ /* Cached watch register read values. */ + + +-+ case GNU_DISASSEMBLE: +-+ if (req->addr2) +-+ sprintf(req->buf, "disassemble 0x%lx 0x%lx", +-+ req->addr, req->addr2); +-+ else +-+ sprintf(req->buf, "disassemble 0x%lx", req->addr); +-+ execute_command(req->buf, TRUE); +-+ break; +++ struct pt_watch_regs watch_readback; + + +-+ case GNU_ADD_SYMBOL_FILE: +-+ gdb_add_symbol_file(req); +-+ break; +++ /* Current watchpoint requests for this process. */ + + +-+ case GNU_DELETE_SYMBOL_FILE: +-+ gdb_delete_symbol_file(req); +-+ break; +++ struct sw_64_watchpoint *current_watches; + + +-+ case GNU_GET_LINE_NUMBER: +-+ gdb_get_line_number(req); +-+ break; +++ /* The current set of watch register values for writing the +++ registers. */ + + +-+ case GNU_GET_DATATYPE: +-+ gdb_get_datatype(req); +-+ break; +++ struct pt_watch_regs watch_mirror; +++//#endif +++}; + + +-+ case GNU_GET_SYMBOL_TYPE: +-+ gdb_get_symbol_type(req); +-+ break; +++/* Per-thread arch-specific data we want to keep. */ +++/* +++struct arch_lwp_info +++{ +++ Non-zero if our copy differs from what's recorded in the thread. */ +++ //int watch_registers_changed; +++//}; + + +-+ case GNU_COMMAND_EXISTS: +-+ gdb_command_exists(req); +-+ break; +++/* From sw_64-linux-nat.c. */ + + +-+ case GNU_ALPHA_FRAME_OFFSET: +-+ req->value = 0; +-+ break; +++/* Pseudo registers can not be read. ptrace does not provide a way to +++ read (or set) PS_REGNUM, and there's no point in reading or setting +++ ZERO_REGNUM, it's always 0. We also can not set BADVADDR, CAUSE, +++ or FCRIR via ptrace(). */ +++bool +++sw_64_target::low_cannot_fetch_register (int regno) +++{ +++ const struct target_desc *tdesc; + + +-+ case GNU_FUNCTION_NUMARGS: +-+ gdb_function_numargs(req); +-+ break; +++ if (get_regs_info ()->usrregs->regmap[regno] == -1) +++ return true; + + +-+ case GNU_DEBUG_COMMAND: +-+ gdb_debug_command(req); +-+ break; +++} +++bool +++sw_64_target::low_cannot_store_register (int regno) +++{ + + +-+ case GNU_PATCH_SYMBOL_VALUES: +-+ gdb_patch_symbol_values(req); +-+ break; +++ if (get_regs_info ()->usrregs->regmap[regno] == -1) +++ return true; + + +-+ case GNU_SET_CRASH_BLOCK: +-+ gdb_set_crash_block(req); +-+ break; +++ return false; +++} + + +-+ case GNU_GET_FUNCTION_RANGE: +-+ { +-+ CORE_ADDR start, end; +-+ if (!find_pc_partial_function(req->pc, NULL, &start, &end)) +-+ req->flags |= GNU_COMMAND_FAILED; +-+ else { +-+ req->addr = (ulong)start; +-+ req->addr2 = (ulong)end; +-+ } +-+ } +-+ break; +++bool +++sw_64_target::low_fetch_register (regcache *regcache, int regno) +++{ +++ const struct target_desc *tdesc = current_process ()->tdesc; + + +-+ case GNU_LOOKUP_STRUCT_CONTENTS: +-+ req->value = lookup_struct_contents(req); +-+ break; +++ if (find_regno (tdesc, "r0") == regno) +++ { +++ supply_register_zeroed (regcache, regno); +++ return true; +++ } + + +-+ case GNU_ITERATE_DATATYPES: +-+ iterate_datatypes(req); +-+ break; +++ return false; +++} + + +-+ default: +-+ req->flags |= GNU_COMMAND_FAILED; +-+ break; +-+ } +++bool +++sw_64_target::low_supports_breakpoints () +++{ +++ return true; + +} + + +-+/* +-+ * Given a PC value, return the file and line number. +-+ */ +-+static void +-+gdb_get_line_number(struct gnu_request *req) +++CORE_ADDR +++sw_64_target::low_get_pc (regcache *regcache) + +{ +-+ struct symtab_and_line sal; +-+ struct objfile *objfile; +-+ CORE_ADDR pc; +++ union sw_64_register pc; +++ collect_register_by_name (regcache, "pc", pc.buf); +++ return pc.reg64; +++} + + +-+#define LASTCHAR(s) (s[strlen(s)-1]) +++void +++sw_64_target::low_set_pc (regcache *regcache, CORE_ADDR pc) +++{ +++ union sw_64_register newpc; +++ newpc.reg64 = pc; + + +-+ /* +-+ * Prime the addrmap pump. +-+ */ +-+ pc = req->addr; +++ supply_register_by_name (regcache, "pc", newpc.buf); +++} + + +-+ sal = find_pc_line(pc, 0); +++/* Correct in either endianness. */ +++static const unsigned int sw_64_breakpoint = 0x00000080; +++#define sw_64_breakpoint_len 4 + + +-+ if (!sal.symtab) { +-+ /* +-+ * If a module address line number can't be found, it's typically +-+ * due to its addrmap still containing offset values because its +-+ * objfile doesn't have full symbols loaded. +-+ */ +-+ if (req->lm) { +-+ objfile = req->lm->loaded_objfile; +-+ if (!objfile_has_full_symbols(objfile) && objfile->sf) { +-+ objfile->sf->qf->expand_all_symtabs(objfile); +-+ sal = find_pc_line(pc, 0); +-+ } +-+ } +-+ if (!sal.symtab) { +-+ req->buf[0] = '\0'; +-+ return; +-+ } +-+ } +++/* Implementation of target ops method "sw_breakpoint_from_kind". */ + + +-+ if (sal.symtab->filename && SYMTAB_DIRNAME(sal.symtab)) { +-+ if (sal.symtab->filename[0] == '/') +-+ sprintf(req->buf, "%s: %d", +-+ sal.symtab->filename, sal.line); +-+ else +-+ sprintf(req->buf, "%s%s%s: %d", +-+ SYMTAB_DIRNAME(sal.symtab), +-+ LASTCHAR(SYMTAB_DIRNAME(sal.symtab)) == '/' ? "" : "/", +-+ sal.symtab->filename, sal.line); +-+ } +++const gdb_byte * +++sw_64_target::sw_breakpoint_from_kind (int kind, int *size) +++{ +++ *size = sw_64_breakpoint_len; +++ return (const gdb_byte *) &sw_64_breakpoint; + +} + + +++bool +++sw_64_target::low_breakpoint_at (CORE_ADDR where) +++{ +++ unsigned int insn; + + +-+/* +-+ * General purpose routine for determining datatypes. +-+ */ +++ read_memory (where, (unsigned char *) &insn, 4); +++ if (insn == sw_64_breakpoint) +++ return true; +++ +++ /* If necessary, recognize more trap instructions here. GDB only uses the +++ one. */ +++ return false; +++} +++ +++/* Mark the watch registers of lwp, represented by ENTRY, as changed. */ + + + +static void +-+gdb_get_datatype(struct gnu_request *req) +++update_watch_registers_callback (thread_info *thread) + +{ +-+ register struct type *type; +-+ register struct type *typedef_type; +-+ expression_up expr; +-+ struct symbol *sym; +-+ struct value *val; +++ struct lwp_info *lwp = get_thread_lwp (thread); + + +-+ if (gdb_CRASHDEBUG(2)) +-+ console("gdb_get_datatype [%s] (a)\n", req->name); +++ /* The actual update is done later just before resuming the lwp, +++ we just mark that the registers need updating. */ +++ lwp->arch_private->watch_registers_changed = 1; + + +-+ req->typecode = TYPE_CODE_UNDEF; +++ /* If the lwp isn't stopped, force it to momentarily pause, so +++ we can update its watch registers. */ +++ if (!lwp->stopped) +++ linux_stop_lwp (lwp); +++} + + +-+ /* +-+ * lookup_symbol() will pick up struct and union names. +-+ */ +-+ sym = lookup_symbol(req->name, 0, STRUCT_DOMAIN, 0).symbol; +-+ if (sym) { +-+ req->typecode = TYPE_CODE(sym->type); +-+ req->length = TYPE_LENGTH(sym->type); +-+ if (req->member) +-+ get_member_data(req, sym->type, 0, 1); +++/* This is the implementation of linux target ops method +++ low_new_process. */ + + +-+ if (TYPE_CODE(sym->type) == TYPE_CODE_ENUM) { +-+ if (req->flags & GNU_PRINT_ENUMERATORS) +-+ dump_enum(sym->type, req); +-+ } +++arch_process_info * +++sw_64_target::low_new_process () +++{ +++ struct arch_process_info *info = XCNEW (struct arch_process_info); + + +-+ return; +-+ } +++ return info; +++} + + +-+ /* +-+ * Otherwise parse the expression. +-+ */ +-+ if (gdb_CRASHDEBUG(2)) +-+ console("gdb_get_datatype [%s] (b)\n", req->name); +++/* This is the implementation of linux target ops method +++ low_delete_process. */ + + +-+ expr = parse_expression(req->name); +++void +++sw_64_target::low_delete_process (arch_process_info *info) +++{ +++ xfree (info); +++} + + +++/* This is the implementation of linux target ops method low_new_thread. +++ Mark the watch registers as changed, so the threads' copies will +++ be updated. */ + + +-+ switch (expr.get()->elts[0].opcode) +-+ { +-+ case OP_VAR_VALUE: +-+ if (gdb_CRASHDEBUG(2)) +-+ console("expr->elts[0].opcode: OP_VAR_VALUE\n"); +-+ type = expr.get()->elts[2].symbol->type; +-+ if (req->flags & GNU_VAR_LENGTH_TYPECODE) { +-+ req->typecode = TYPE_CODE(type); +-+ req->length = TYPE_LENGTH(type); +-+ } +-+ if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +-+ req->typecode = TYPE_CODE(type); +-+ req->value = SYMBOL_VALUE(expr.get()->elts[2].symbol); +-+ req->tagname = (char *)TYPE_TAG_NAME(type); +-+ if (!req->tagname) { +-+ val = evaluate_type(expr.get()); +-+ eval_enum(value_type(val), req); +-+ } +-+ } +-+ break; +++void +++sw_64_target::low_new_thread (lwp_info *lwp) +++{ +++ struct arch_lwp_info *info = XCNEW (struct arch_lwp_info); + + +-+ case OP_TYPE: +-+ if (gdb_CRASHDEBUG(2)) +-+ console("expr->elts[0].opcode: OP_TYPE\n"); +-+ type = expr.get()->elts[1].type; +++ info->watch_registers_changed = 1; + + +-+ req->typecode = TYPE_CODE(type); +-+ req->length = TYPE_LENGTH(type); +++ lwp->arch_private = info; +++} + + +-+ if (TYPE_CODE(type) == TYPE_CODE_TYPEDEF) { +-+ req->is_typedef = TYPE_CODE_TYPEDEF; +-+ if ((typedef_type = check_typedef(type))) { +-+ req->typecode = TYPE_CODE(typedef_type); +-+ req->length = TYPE_LENGTH(typedef_type); +-+ type = typedef_type; +-+ } +-+ } +++/* Function to call when a thread is being deleted. */ + + +-+ if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +-+ if (req->is_typedef) +-+ if (req->flags & GNU_PRINT_ENUMERATORS) { +-+ if (req->is_typedef) +-+ fprintf_filtered(gdb_stdout, +-+ "typedef "); +-+ dump_enum(type, req); +-+ } +-+ } +++void +++sw_64_target::low_delete_thread (arch_lwp_info *arch_lwp) +++{ +++ xfree (arch_lwp); +++} + + +-+ if (req->member) +-+ get_member_data(req, type, 0, 1); +++//#if 0 +++/* Create a new sw_64_watchpoint and add it to the list. */ + + +-+ break; +++static void +++sw_64_add_watchpoint (struct arch_process_info *priv, CORE_ADDR addr, int len, +++ enum target_hw_bp_type watch_type) +++{ +++ struct sw_64_watchpoint *new_watch; +++ struct sw_64_watchpoint **pw; + + +-+ default: +-+ if (gdb_CRASHDEBUG(2)) +-+ console("expr.get()->elts[0].opcode: %d (?)\n", +-+ expr.get()->elts[0].opcode); +-+ break; +++ new_watch = XNEW (struct sw_64_watchpoint); +++ new_watch->addr = addr; +++ new_watch->len = len; +++ new_watch->type = watch_type; +++ new_watch->next = NULL; + + +-+ } +++ pw = &priv->current_watches; +++ while (*pw != NULL) +++ pw = &(*pw)->next; +++ *pw = new_watch; + +} +++//#endif +++/* Hook to call when a new fork is attached. */ + + +-+/* +-+ * More robust enum list dump that gdb's, showing the value of each +-+ * identifier, each on its own line. +-+ */ +-+static void +-+dump_enum(struct type *type, struct gnu_request *req) +++void +++sw_64_target::low_new_fork (process_info *parent, +++ process_info *child) + +{ +-+ register int i; +-+ int len; +-+ long long lastval; +++ // struct arch_process_info *parent_private; +++ // struct arch_process_info *child_private; +++// struct sw_64_watchpoint *wp; + + +-+ len = TYPE_NFIELDS (type); +-+ lastval = 0; +-+ if (TYPE_TAG_NAME(type)) +-+ fprintf_filtered(gdb_stdout, +-+ "enum %s {\n", TYPE_TAG_NAME (type)); +-+ else +-+ fprintf_filtered(gdb_stdout, "enum {\n"); +++ /* These are allocated by linux_add_process. */ +++ gdb_assert (parent->priv != NULL +++ && parent->priv->arch_private != NULL); +++ gdb_assert (child->priv != NULL +++ && child->priv->arch_private != NULL); + + +-+ for (i = 0; i < len; i++) { +-+ fprintf_filtered(gdb_stdout, " %s", +-+ TYPE_FIELD_NAME (type, i)); +-+ if (lastval != TYPE_FIELD_ENUMVAL (type, i)) { +-+ fprintf_filtered (gdb_stdout, " = %s", +-+ plongest(TYPE_FIELD_ENUMVAL (type, i))); +-+ lastval = TYPE_FIELD_ENUMVAL (type, i); +-+ } else +-+ fprintf_filtered(gdb_stdout, " = %s", plongest(lastval)); +-+ fprintf_filtered(gdb_stdout, "\n"); +-+ lastval++; +++ /* Linux kernel before 2.6.33 commit +++ 72f674d203cd230426437cdcf7dd6f681dad8b0d +++ will inherit hardware debug registers from parent +++ on fork/vfork/clone. Newer Linux kernels create such tasks with +++ zeroed debug registers. +++ +++ GDB core assumes the child inherits the watchpoints/hw +++ breakpoints of the parent, and will remove them all from the +++ forked off process. Copy the debug registers mirrors into the +++ new process so that all breakpoints and watchpoints can be +++ removed together. The debug registers mirror will become zeroed +++ in the end before detaching the forked off process, thus making +++ this compatible with older Linux kernels too. */ +++ +++ /* parent_private = parent->priv->arch_private; +++ child_private = child->priv->arch_private; +++ +++ child_private->watch_readback_valid = parent_private->watch_readback_valid; +++ child_private->watch_readback = parent_private->watch_readback; +++ +++ for (wp = parent_private->current_watches; wp != NULL; wp = wp->next) +++ sw_64_add_watchpoint (child_private, wp->addr, wp->len, wp->type); +++ +++ child_private->watch_mirror = parent_private->watch_mirror; +++*/ +++} +++/* This is the implementation of linux target ops method +++ low_prepare_to_resume. If the watch regs have changed, update the +++ thread's copies. */ +++ +++enum sw_64_hw_bp_type +++sw_64_hw_bp_type_from_raw_type (enum raw_bkpt_type raw_type) +++{ +++ switch (raw_type) +++ { +++ case raw_bkpt_type_hw: +++ return sw_64_none; +++ case raw_bkpt_type_write_wp: +++ return sw_64_write; +++ case raw_bkpt_type_read_wp: +++ return sw_64_read; +++ case raw_bkpt_type_access_wp: +++ return sw_64_access; +++ case raw_bkpt_type_value_wp: +++ return sw_64_vstore; +++ default: +++ internal_error (__FILE__, __LINE__, +++ "bad raw breakpoint type %d", (int) raw_type); + + } +-+ if (TYPE_TAG_NAME(type)) +-+ fprintf_filtered(gdb_stdout, "};\n"); +-+ else +-+ fprintf_filtered(gdb_stdout, "} %s;\n", req->name); + +} + + +-+/* +-+ * Given an enum type with no tagname, determine its value. +-+ */ +-+static void +-+eval_enum(struct type *type, struct gnu_request *req) +++void +++sw_64_target::low_prepare_to_resume (lwp_info *lwp) + +{ +-+ register int i; +-+ int len; +-+ long long lastval; +++ int i; +++ ptid_t ptid = ptid_of (get_lwp_thread (lwp)); +++ struct arch_lwp_info *priv = lwp->arch_private; +++ //pid_t lwpid = ptid_of_lwp(ptid); +++ pid_t lwpid = ptid.lwp (); + + +-+ len = TYPE_NFIELDS (type); +-+ lastval = 0; +++ if (!lwp->arch_private->watch_registers_changed) +++ return; + + +-+ for (i = 0; i < len; i++) { +-+ if (lastval != TYPE_FIELD_ENUMVAL (type, i)) +-+ lastval = TYPE_FIELD_ENUMVAL (type, i); +++ if ( priv->wpt[1].valid ) +++ { +++ store_debug_register (lwpid, M_DV_MATCH, priv->wpt[1].match); +++ store_debug_register (lwpid, M_DV_MATCH+1, priv->wpt[1].mask); +++ } +++ if ( priv->wpt[0].valid ) +++ { +++ store_debug_register (lwpid, M_DA_MATCH, priv->wpt->match); +++ store_debug_register (lwpid, M_DA_MASK, priv->wpt->mask); +++ } + + +-+ if (STREQ(TYPE_FIELD_NAME(type, i), req->name)) { +-+ req->tagname = "(unknown)"; +-+ req->value = lastval; +-+ return; +++ i = (priv->wpt[1].valid<<1) | priv->wpt[0].valid; +++ +++ // setting dv_ctl +++ switch (i) +++ { +++ //da_match +++ case 0: +++ case 1: +++ //store_debug_register (lwpid, M_DV_MATCH+2, 0L); +++ break; +++ //dv_match +++ case 2: +++ store_debug_register (lwpid, M_DV_MATCH+2, 1); +++ break; +++ //dva_match +++ case 3: +++ store_debug_register (lwpid, M_DV_MATCH+2, 3); +++ break; +++ default: +++ ;; + + } +-+ lastval++; +-+ } +++ +++ lwp->arch_private->watch_registers_changed = 0; + +} + + +-+/* +-+ * Walk through a struct type's list of fields looking for the desired +-+ * member field, and when found, return its relevant data. +-+ */ +-+static void +-+get_member_data(struct gnu_request *req, struct type *type, long offset, int is_first) +++bool +++sw_64_target::supports_z_point_type (char z_type) + +{ +-+ register short i; +-+ struct field *nextfield; +-+ short nfields; +-+ struct type *typedef_type, *target_type; +++ switch (z_type) +++ { +++ case Z_PACKET_SW_BP: +++ case Z_PACKET_HW_BP: +++ case Z_PACKET_WRITE_WP: +++ case Z_PACKET_READ_WP: +++ case Z_PACKET_ACCESS_WP: +++ case Z_PACKET_DV_WP: +++ return true; +++ default: +++ return false; +++ } +++} + + +-+ req->member_offset = -1; +++/* This is the implementation of linux target ops method +++ low_insert_point. */ + + +-+ nfields = TYPE_MAIN_TYPE(type)->nfields; +-+ nextfield = TYPE_MAIN_TYPE(type)->flds_bnds.fields; +++int +++sw_64_target::low_insert_point (raw_bkpt_type type, CORE_ADDR addr, +++ int len, raw_breakpoint *bp) +++{ +++int pid, i; +++ long lwpid, data; +++ enum sw_64_hw_bp_type watch_type; +++ struct lwp_info *lwp = get_thread_lwp (current_thread); +++ struct arch_lwp_info *priv = lwp->arch_private; + + +-+ if (nfields == 0 && is_first /* The first call */) { +-+ struct type *newtype; +-+ newtype = lookup_transparent_type(req->name); +-+ if (newtype) { +-+ console("get_member_data(%s.%s): switching type from %lx to %lx\n", +-+ req->name, req->member, type, newtype); +-+ nfields = TYPE_MAIN_TYPE(newtype)->nfields; +-+ nextfield = TYPE_MAIN_TYPE(newtype)->flds_bnds.fields; +-+ } +-+ } +++ if (!addr) +++ return 0; + + +-+ for (i = 0; i < nfields; i++) { +-+ if (STREQ(req->member, nextfield->name)) { +-+ req->member_offset = offset + nextfield->loc.bitpos; +-+ req->member_length = TYPE_LENGTH(nextfield->type()); +-+ req->member_typecode = TYPE_CODE(nextfield->type()); +-+ req->member_main_type_name = (char *)TYPE_NAME(nextfield->type()); +-+ req->member_main_type_tag_name = (char *)TYPE_TAG_NAME(nextfield->type()); +-+ target_type = TYPE_TARGET_TYPE(nextfield->type()); +-+ if (target_type) { +-+ req->member_target_type_name = (char *)TYPE_NAME(target_type); +-+ req->member_target_type_tag_name = (char *)TYPE_TAG_NAME(target_type); +-+ } +-+ if ((req->member_typecode == TYPE_CODE_TYPEDEF) && +-+ (typedef_type = check_typedef(nextfield->type()))) +-+ req->member_length = TYPE_LENGTH(typedef_type); +-+ return; +-+ } else if (*nextfield->name == 0) { /* Anonymous struct/union */ +-+ get_member_data(req, nextfield->type(), +-+ offset + nextfield->loc.bitpos, 0); +-+ if (req->member_offset != -1) +-+ return; +-+ } +-+ nextfield++; +++ lwpid = lwpid_of (current_thread); +++ pid = pid_of (current_thread); +++ +++ if ( len <= 0 || !is_power_of_2 (len)) +++ return 0; +++ +++ /* Now try to add the new watch. */ +++ watch_type = sw_64_hw_bp_type_from_raw_type(type); +++ +++ if (sw_64_linux_try_one_watch(lwpid, priv, watch_type,addr,len)) +++ //find_inferior (&all_threads, update_watch_registers_callback, &pid); +++/* Only update the threads of this process. */ +++ for_each_thread (pid, update_watch_registers_callback); +++ return 0; +++} +++ +++/* This is the implementation of linux_target_ops method +++ stopped_by_watchpoint. The watchhi R and W bits indicate +++ the watch register triggered. */ +++/* Check master wp only now */ +++ +++static int +++sw_64_stopped_by_watchpoint (void) +++{ +++ pid_t lwpid = lwpid_of(current_thread); +++ struct lwp_info *lwp = get_thread_lwp (current_thread); +++ siginfo_t siginfo; +++ +++ /* Retrieve siginfo. */ +++ errno = 0; +++ ptrace (PTRACE_GETSIGINFO, lwpid, 0, &siginfo); +++ if (errno != 0) +++ { +++ warning("%s:%d GETSIGINFO return %d\n", __FILE__, __LINE__, errno); +++ return 0; } debug("GETSIGINFO %#x si_code=%#x si_signo=%d si_errno = %x", lwpid, siginfo.si_code, siginfo.si_signo,siginfo.si_errno); /* This must be a hardware breakpoint. */ +++ if (siginfo.si_signo != SIGTRAP +++ || (siginfo.si_code & 0xffff) != M_DA_MATCH_TRAP/* TRAP_HWBKPT */) +++ return 0; +++ debug("si_code=%#x si_signo=%d si_errno = %x pc=%#lx, data_address %#lx", siginfo.si_code, siginfo.si_signo,siginfo.si_errno,(long)siginfo.si_value.sival_ptr, (long)siginfo.si_addr); /* siginfo should return the accessed data address, not pc */ +++ if (siginfo.si_errno == 1) +++ lwp->arch_private->stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (lwp->arch_private->wpt->match & ((1L<<53)-1)); +++ else +++ lwp->arch_private->stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (lwp->arch_private->value_address); // get the saved +++ return 1; +++} +++ +++#define BTSIZE 20 +++int gcc_backtrace() +++{ +++ int j, nptrs; +++ void *buffer[BTSIZE]; +++ char **strings; +++ +++ nptrs = backtrace(buffer, BTSIZE); +++ +++ /* The call backtrace_symbols_fd(buffer, nptrs, STDOUT_FILENO) +++ would produce similar output to the following: */ +++ +++ strings = backtrace_symbols(buffer, nptrs); +++ if (strings == NULL) { +++ perror("backtrace_symbols"); +++ return (EXIT_FAILURE); + + } +++ +++ for (j = 0; j < nptrs; j++) +++ printf(" %s", strings[j]); +++ printf("\n"); +++ +++ free(strings); +++ return 0; + +} + + +-+/* +-+ * Check whether a command exists. If it doesn't, the command will be +-+ * returned indirectly via the error_hook. +-+ */ +-+static void +-+gdb_command_exists(struct gnu_request *req) +++void exc_handler(int sig, siginfo_t* info, void *arg) + +{ +-+ extern struct cmd_list_element *cmdlist; +++ //unsigned long ra; +++ //unsigned long sp, pc; +++ //ucontext_t *uc = (ucontext_t *)arg; +++#if 0 +++ register unsigned long __ra __asm__("$26"); +++ pc = uc->uc_mcontext.sc_pc; +++ ra = uc->uc_mcontext.sc_regs[26]; +++ sp = uc->uc_mcontext.sc_regs[30]; +++ printf("pc = %#lx, ra = %#lx, sp=%#lx, called from %#lx\n", pc, ra, sp, *(unsigned long*)sp); fflush(stdout); +++#else +++ gcc_backtrace(); +++#endif +++ exit(1); +++} +++/* This is the implementation of linux target ops method +++ low_remove_point. */ + + +-+ req->value = FALSE; +-+ lookup_cmd((const char **)&req->name, cmdlist, "", NULL, 0, 1); +-+ req->value = TRUE; +++int +++sw_64_target::low_remove_point (raw_bkpt_type type, CORE_ADDR addr, +++ int len, raw_breakpoint *bp) +++{ +++ int pid, i; +++ uint64_t match; +++ uint64_t data; +++ enum sw_64_hw_bp_type watch_type; +++ long lwpid; +++ struct lwp_info *lwp = get_thread_lwp (current_thread); +++ struct arch_lwp_info *priv = lwp->arch_private; +++ +++ /* Search for a known watch that matches. Then unlink and free it. */ +++ watch_type = sw_64_hw_bp_type_from_raw_type(type); +++ +++ pid = pid_of (current_thread); +++ lwpid = lwpid_of(current_thread); +++ if (!sw_64_linux_del_one_watch(lwpid, priv, watch_type,addr,len)) +++ { +++ warning("none wp about %#lx\n", (long)addr); +++ return -1; /* We don't know about it, fail doing nothing. */ +++ } +++ /* Only update the threads of this process. */ +++ //find_inferior (&all_threads, update_watch_registers_callback, &pid); +++ for_each_thread (pid, update_watch_registers_callback); +++ return 0; + +} + + +-+static void +-+gdb_function_numargs(struct gnu_request *req) +-+{ +-+ struct symbol *sym; +++/* This is the implementation of linux target ops method +++ low_stopped_by_watchpoint. The watchhi R and W bits indicate +++ the watch register triggered. */ + + +-+ sym = find_pc_function(req->pc); +-+ +-+ if (!sym || TYPE_CODE(sym->type) != TYPE_CODE_FUNC) { +-+ req->flags |= GNU_COMMAND_FAILED; +-+ return; +-+ } +++bool +++sw_64_target::low_stopped_by_watchpoint () +++{ +++ pid_t lwpid = lwpid_of(current_thread); +++ struct lwp_info *lwp = get_thread_lwp (current_thread); +++ siginfo_t siginfo; + + +-+ req->value = (ulong)TYPE_NFIELDS(sym->type); +++ /* Retrieve siginfo. */ +++ errno = 0; +++ ptrace (PTRACE_GETSIGINFO, lwpid, 0, &siginfo); +++ if (errno != 0) +++ { +++ warning("%s:%d GETSIGINFO return %d\n", __FILE__, __LINE__, errno); +++ return 0; } debug("GETSIGINFO %#x si_code=%#x si_signo=%d si_errno = %x", lwpid, siginfo.si_code, siginfo.si_signo,siginfo.si_errno); +++ /* This must be a hardware breakpoint. */ +++ if (siginfo.si_signo != SIGTRAP +++ || (siginfo.si_code & 0xffff) != M_DA_MATCH_TRAP/* TRAP_HWBKPT */) +++ return 0; +++ debug("si_code=%#x si_signo=%d si_errno = %x pc=%#lx, data_address %#lx", siginfo.si_code, siginfo.si_signo,siginfo.si_errno,(long)siginfo.si_value.sival_ptr, (long)siginfo.si_addr); +++ /* siginfo should return the accessed data address, not pc */ +++ if (siginfo.si_errno == 1) +++ lwp->arch_private->stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (lwp->arch_private->wpt->match & ((1L<<53)-1)); +++ else +++ lwp->arch_private->stopped_data_address +++ = (CORE_ADDR) (uintptr_t) (lwp->arch_private->value_address); // get the saved +++ return 1; + +} +++/* This is the implementation of linux target ops method +++ low_stopped_data_address. */ + + +-+struct load_module *gdb_current_load_module = NULL; +-+ +-+static void +-+gdb_add_symbol_file(struct gnu_request *req) +++CORE_ADDR +++sw_64_target::low_stopped_data_address () + +{ +-+ struct load_module *lm; +-+ int i; +-+ int allsect = 0; +-+ char *secname; +-+ char buf[80]; +++ struct lwp_info *lwp; + + +-+ gdb_current_load_module = lm = (struct load_module *)req->addr; +++ lwp = get_thread_lwp (current_thread); +++ sw_64_stopped_by_watchpoint(); + + +-+ req->name = lm->mod_namelist; +-+ gdb_delete_symbol_file(req); +-+ lm->loaded_objfile = NULL; +++ return lwp->arch_private->stopped_data_address; +++} + + +-+ if ((lm->mod_flags & MOD_NOPATCH) == 0) { +-+ for (i = 0 ; i < lm->mod_sections; i++) { +-+ if (STREQ(lm->mod_section_data[i].name, ".text") && +-+ (lm->mod_section_data[i].flags & SEC_FOUND)) +-+ allsect = 1; +-+ } + + +-+ if (!allsect) { +-+ sprintf(req->buf, "add-symbol-file %s 0x%lx %s", lm->mod_namelist, +-+ lm->mod_text_start ? lm->mod_text_start : lm->mod_base, +-+ lm->mod_flags & MOD_DO_READNOW ? "-readnow" : ""); +-+ if (lm->mod_data_start) { +-+ sprintf(buf, " -s .data 0x%lx", lm->mod_data_start); +-+ strcat(req->buf, buf); +-+ } +-+ if (lm->mod_bss_start) { +-+ sprintf(buf, " -s .bss 0x%lx", lm->mod_bss_start); +-+ strcat(req->buf, buf); +-+ } +-+ if (lm->mod_rodata_start) { +-+ sprintf(buf, " -s .rodata 0x%lx", lm->mod_rodata_start); +-+ strcat(req->buf, buf); +-+ } +-+ } else { +-+ sprintf(req->buf, "add-symbol-file %s 0x%lx %s", lm->mod_namelist, +-+ lm->mod_text_start, lm->mod_flags & MOD_DO_READNOW ? +-+ "-readnow" : ""); +-+ for (i = 0; i < lm->mod_sections; i++) { +-+ secname = lm->mod_section_data[i].name; +-+ if ((lm->mod_section_data[i].flags & SEC_FOUND) && +-+ !STREQ(secname, ".text")) { +-+ sprintf(buf, " -s %s 0x%lx", secname, +-+ lm->mod_section_data[i].offset + lm->mod_base); +-+ strcat(req->buf, buf); +-+ } +-+ } +-+ } +-+ } +++/* Fetch the thread-local storage pointer for libthread_db. */ + + +-+ if (gdb_CRASHDEBUG(1)) +-+ fprintf_filtered(gdb_stdout, "%s\n", req->buf); +++ps_err_e +++ps_get_thread_area (struct ps_prochandle *ph, +++ lwpid_t lwpid, int idx, void **base) +++{ +++ if (ptrace (PTRACE_GET_THREAD_AREA, lwpid, NULL, base) != 0) +++ return PS_ERR; + + +-+ execute_command(req->buf, FALSE); +++ /* IDX is the bias from the thread pointer to the beginning of the +++ thread descriptor. It has to be subtracted due to implementation +++ quirks in libthread_db. */ +++ *base = (void *) ((char *)*base - idx); + + +-+ for (objfile *objfile : current_program_space->objfiles ()) { +-+ if (same_file((char *)objfile_name(objfile), lm->mod_namelist)) { +-+ if (objfile->separate_debug_objfile) +-+ lm->loaded_objfile = objfile->separate_debug_objfile; +-+ else +-+ lm->loaded_objfile = objfile; +-+ break; +-+ } +-+ } +++ return PS_OK; +++} + + +-+ if (!lm->loaded_objfile) +-+ req->flags |= GNU_COMMAND_FAILED; +++/* Fetch the thread-local storage pointer for libthread_db. */ +++ +++#ifdef HAVE_PTRACE_GETREGS +++static void +++sw_64_collect_register (struct regcache *regcache, +++ int use_64bit, int regno, union sw_64_register *reg) +++{ +++ union sw_64_register tmp_reg; +++ +++ if (use_64bit) +++ { +++ collect_register (regcache, regno, &tmp_reg.reg64); +++ *reg = tmp_reg; +++ } +++ else +++ { +++ collect_register (regcache, regno, &tmp_reg.reg32); +++ reg->reg64 = tmp_reg.reg32; +++ } + +} + + + +static void +-+gdb_delete_symbol_file(struct gnu_request *req) +++sw_64_supply_register (struct regcache *regcache, +++ int use_64bit, int regno, const union sw_64_register *reg) + +{ +-+ for (objfile *objfile : current_program_space->objfiles ()) { +-+ if (STREQ(objfile_name(objfile), req->name) || +-+ same_file((char *)objfile_name(objfile), req->name)) { +-+ objfile->unlink (); +-+ break; +-+ } +-+ } +++ int offset = 0; + + +-+ if (gdb_CRASHDEBUG(2)) { +-+ fprintf_filtered(gdb_stdout, "current object files:\n"); +-+ for (objfile *objfile : current_program_space->objfiles ()) +-+ fprintf_filtered(gdb_stdout, " %s\n", objfile_name(objfile)); +-+ } +++ /* For big-endian 32-bit targets, ignore the high four bytes of each +++ eight-byte slot. */ +++ if (__BYTE_ORDER == __BIG_ENDIAN && !use_64bit) +++ offset = 4; +++ +++ supply_register (regcache, regno, reg->buf + offset); + +} + + +-+/* +-+ * Walk through all minimal_symbols, patching their values with the +-+ * correct addresses. +-+ */ +++//#ifdef HAVE_PTRACE_GETREGS +++ +++ + +static void +-+gdb_patch_symbol_values(struct gnu_request *req) +++sw_64_fill_gregset (struct regcache *regcache, void *buf) + +{ +-+ req->name = PATCH_KERNEL_SYMBOLS_START; +-+ patch_kernel_symbol(req); +++ union sw_64_register *regset = (union sw_64_register *) buf; +++ int i, use_64bit; +++ const struct target_desc *tdesc = regcache->tdesc; + + +-+ for (objfile *objfile : current_program_space->objfiles ()) +-+ for (minimal_symbol *msymbol : objfile->msymbols ()) +-+ { +-+ req->name = (char *)msymbol->m_name; +-+ req->addr = (ulong)(&MSYMBOL_VALUE(msymbol)); +-+ if (!patch_kernel_symbol(req)) { +-+ req->flags |= GNU_COMMAND_FAILED; +-+ break; +-+ } +-+ } +++ use_64bit = (register_size (tdesc, 0) == 8); + + +-+ req->name = PATCH_KERNEL_SYMBOLS_STOP; +-+ patch_kernel_symbol(req); +++ for (i = 1; i < 32; i++) +++ sw_64_collect_register (regcache, use_64bit, i, regset + i); + + +-+ clear_symtab_users(0); +-+ gdb_merge_flags |= KERNEL_SYMBOLS_PATCHED; +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "lo"), regset + 32); +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "hi"), regset + 33); +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "pc"), regset + 34); +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "badvaddr"), regset + 35); +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "status"), regset + 36); +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "cause"), regset + 37); +++ +++ sw_64_collect_register (regcache, use_64bit, +++ find_regno (tdesc, "restart"), regset + 0); + +} + + + +static void +-+gdb_get_symbol_type(struct gnu_request *req) +++sw_64_store_gregset (struct regcache *regcache, const void *buf) + +{ +-+ expression_up expr; +-+ struct value *val; +-+ struct type *type; +-+ struct type *target_type; +-+ +-+ req->typecode = TYPE_CODE_UNDEF; +++ const union sw_64_register *regset = (const union sw_64_register *) buf; +++ int i, use_64bit; + + +-+ expr = parse_expression (req->name); +-+ val = evaluate_type (expr.get()); +++ use_64bit = (register_size (regcache->tdesc, 0) == 8); + + +-+ type = value_type(val); +++ supply_register_by_name_zeroed (regcache, "r0"); + + +-+ req->type_name = (char *)TYPE_MAIN_TYPE(type)->name; +-+ req->typecode = TYPE_MAIN_TYPE(type)->code; +-+ req->length = type->length; +-+ req->type_tag_name = (char *)TYPE_TAG_NAME(type); +-+ target_type = TYPE_MAIN_TYPE(type)->target_type; +++ for (i = 1; i < 32; i++) +++ sw_64_supply_register (regcache, use_64bit, i, regset + i); + + +-+ if (target_type) { +-+ req->target_typename = (char *)TYPE_MAIN_TYPE(target_type)->name; +-+ req->target_typecode = TYPE_MAIN_TYPE(target_type)->code; +-+ req->target_length = target_type->length; +-+ } +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "lo"), regset + 32); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "hi"), regset + 33); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "pc"), regset + 34); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "badvaddr"), regset + 35); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "status"), regset + 36); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "cause"), regset + 37); + + +-+ if (req->member) +-+ get_member_data(req, type, 0, 1); +++ sw_64_supply_register (regcache, use_64bit, +++ find_regno (regcache->tdesc, "restart"), regset + 0); + +} + + + +static void +-+gdb_debug_command(struct gnu_request *req) +++sw_64_fill_fpregset (struct regcache *regcache, void *buf) + +{ +++ union sw_64_register *regset = (union sw_64_register *) buf; +++ int i, use_64bit, first_fp, big_endian; + + +++ use_64bit = (register_size (regcache->tdesc, 0) == 8); +++ first_fp = find_regno (regcache->tdesc, "f0"); +++ big_endian = (__BYTE_ORDER == __BIG_ENDIAN); +++ +++ /* See GDB for a discussion of this peculiar layout. */ +++ for (i = 0; i < 32; i++) +++ if (use_64bit) +++ collect_register (regcache, first_fp + i, regset[i].buf); +++ else +++ collect_register (regcache, first_fp + i, +++ regset[i & ~1].buf + 4 * (big_endian != (i & 1))); +++ +++ //sw_64_collect_register_32bit (regcache, use_64bit, +++ // find_regno (regcache->tdesc, "fcsr"), regset[32].buf); +++ //sw_64_collect_register_32bit (regcache, use_64bit, +++ // find_regno (regcache->tdesc, "fir"), +++ // regset[32].buf + 4); + +} + + +-+/* +-+ * Only necessary on "patched" kernel symbol sessions, and called only by +-+ * lookup_symbol(), pull a symbol value bait-and-switch operation by altering +-+ * either a data symbol's address value or a text symbol's block start address. +-+ */ + +static void +-+gdb_bait_and_switch(char *name, struct symbol *sym) +++sw_64_store_fpregset (struct regcache *regcache, const void *buf) + +{ +-+ struct bound_minimal_symbol msym; +-+ struct block *block; +++ const union sw_64_register *regset = (const union sw_64_register *) buf; +++ int i, use_64bit, first_fp, big_endian; +++ +++ use_64bit = (register_size (regcache->tdesc, 0) == 8); +++ first_fp = find_regno (regcache->tdesc, "f0"); +++ big_endian = (__BYTE_ORDER == __BIG_ENDIAN); +++ +++ /* See GDB for a discussion of this peculiar layout. */ +++ for (i = 0; i < 32; i++) +++ if (use_64bit) +++ supply_register (regcache, first_fp + i, regset[i].buf); +++ else +++ supply_register (regcache, first_fp + i, +++ regset[i & ~1].buf + 4 * (big_endian != (i & 1))); + + +-+ if ((gdb_merge_flags & KERNEL_SYMBOLS_PATCHED) && +-+ (msym = lookup_minimal_symbol(name, NULL, gdb_kernel_objfile)).minsym) { +-+ if (SYMBOL_CLASS(sym) == LOC_BLOCK) { +-+ block = (struct block *)SYMBOL_BLOCK_VALUE(sym); +-+ BLOCK_START(block) = BMSYMBOL_VALUE_ADDRESS(msym); +-+ } else +-+ SET_SYMBOL_VALUE_ADDRESS(sym, BMSYMBOL_VALUE_ADDRESS(msym)); +-+ } + +} +++//#endif /* HAVE_PTRACE_GETREGS */ + + +-+#include "valprint.h" +++/* Take care of 32-bit registers with 64-bit ptrace, POKEUSER side. */ +++static struct regset_info sw_64_regsets[] = { +++ { PTRACE_GETREGS, PTRACE_SETREGS, 0, 38 * 8, GENERAL_REGS, +++ sw_64_fill_gregset, sw_64_store_gregset }, +++ { PTRACE_GETFPREGS, PTRACE_SETFPREGS, 0, 33 * 8, FP_REGS, +++ sw_64_fill_fpregset, sw_64_store_fpregset }, +++ NULL_REGSET +++}; + + +++static struct regsets_info sw_64_regsets_info = +++ { +++ sw_64_regsets, /* regsets */ +++ 0, /* num_regsets */ +++ NULL, /* disabled_regsets */ +++ }; +++#endif /* HAVE_PTRACE_GETREGS */ + +void +-+get_user_print_option_address(struct gnu_request *req) +++sw_64_target::low_collect_ptrace_register (regcache *regcache, int regno, +++ char *buf) + +{ +-+ extern struct value_print_options user_print_options; +++ int use_64bit = sizeof (PTRACE_XFER_TYPE) == 8; + + +-+ req->addr = 0; +++ if (use_64bit && register_size (regcache->tdesc, regno) == 4) +++ { +++ union sw_64_register reg; + + +-+ if (strcmp(req->name, "output_format") == 0) +-+ req->addr = (ulong)&user_print_options.output_format; +-+ if (strcmp(req->name, "print_max") == 0) +-+ req->addr = (ulong)&user_print_options.print_max; +-+ if (strcmp(req->name, "prettyprint_structs") == 0) +-+ req->addr = (ulong)&user_print_options.prettyformat_structs; +-+ if (strcmp(req->name, "prettyprint_arrays") == 0) +-+ req->addr = (ulong)&user_print_options.prettyformat_arrays; +-+ if (strcmp(req->name, "repeat_count_threshold") == 0) +-+ req->addr = (ulong)&user_print_options.repeat_count_threshold; +-+ if (strcmp(req->name, "stop_print_at_null") == 0) +-+ req->addr = (ulong)&user_print_options.stop_print_at_null; +-+ if (strcmp(req->name, "output_radix") == 0) +-+ req->addr = (ulong)&output_radix; +++ sw_64_collect_register (regcache, 0, regno, ®); +++ memcpy (buf, ®, sizeof (reg)); +++ } +++ else +++ collect_register (regcache, regno, buf); + +} + + +-+CORE_ADDR crash_text_scope; +++/* Take care of 32-bit registers with 64-bit ptrace, PEEKUSER side. */ + + +-+static void +-+gdb_set_crash_block(struct gnu_request *req) +++void +++sw_64_target::low_supply_ptrace_register (regcache *regcache, int regno, +++ const char *buf) + +{ +-+ if (!req->addr) { /* debug */ +-+ crash_text_scope = 0; +-+ return; +-+ } +++ int use_64bit = sizeof (PTRACE_XFER_TYPE) == 8; + + +-+ if ((req->addr2 = (ulong)block_for_pc(req->addr))) +-+ crash_text_scope = req->addr; +-+ else { +-+ crash_text_scope = 0; +-+ req->flags |= GNU_COMMAND_FAILED; +-+ } +-+} +++ if (use_64bit && register_size (regcache->tdesc, regno) == 4) +++ { +++ union sw_64_register reg; + + +-+static const struct block * +-+gdb_get_crash_block(void) +-+{ +-+ if (crash_text_scope) +-+ return block_for_pc(crash_text_scope); +-+ else +-+ return NULL; +++ memcpy (®, buf, sizeof (reg)); +++ sw_64_supply_register (regcache, 0, regno, ®); +++ } +++ else +++ supply_register (regcache, regno, buf); + +} + + +-+static long +-+lookup_struct_contents(struct gnu_request *req) +-+{ +-+ int i; +-+ long r; +-+ struct field *f; +-+ struct main_type *m; +-+ const char *n; +-+ struct main_type *top_m = (struct main_type *)req->addr; +-+ char *type_name = req->type_name; +-+ +-+ if (!top_m || !type_name) +-+ return 0; + + +-+ for (i = 0; i < top_m->nfields; i++) +-+ { +-+ f = top_m->flds_bnds.fields + i; +-+ if (!f->type()) +-+ continue; +-+ m = f->type()->main_type; +++static struct usrregs_info sw_64_usrregs_info = +++ { +++ 165, +++ sw_64_regmap, +++ }; + + +-+ // If the field is an array, check the target type - +-+ // it might be structure, or might not be. +-+ // - struct request_sock *syn_table[0]; +-+ // here m->target_type->main_type->code is expected +-+ // to be TYPE_CODE_PTR +-+ // - struct list_head vec[TVN_SIZE]; +-+ // here m->target_type->main_type->code should be +-+ // TYPE_CODE_STRUCT +-+ if (m->code == TYPE_CODE_ARRAY && m->target_type) +-+ m = m->target_type->main_type; + + +-+ /* Here is a recursion. +-+ * If we have struct variable (not pointer), +-+ * scan this inner structure +-+ */ +-+ if (m->code == TYPE_CODE_STRUCT) { +-+ req->addr = (ulong)m; +-+ r = lookup_struct_contents(req); +-+ req->addr = (ulong)top_m; +-+ if (r) +-+ return 1; +-+ } +++static struct regs_info myregs_info = +++ { +++ NULL, /* regset_bitmap */ +++ &sw_64_usrregs_info, +++#ifdef HAVE_PTRACE_GETREGS +++ &sw_64_regsets_info +++#endif +++ }; + + +-+ if (m->code == TYPE_CODE_PTR && m->target_type) +-+ m = m->target_type->main_type; +-+ if (m->name) +-+ n = m->name; +-+ else +-+ continue; +++static int have_dsp = -1; +++/* The linux target ops object. */ + + +-+ if (strstr(n, type_name)) +-+ return 1; +-+ } +++linux_process_target *the_linux_target = &the_sw_64_target; + + +-+ return 0; +-+} + + +-+static void +-+iterate_datatypes (struct gnu_request *req) +++void +++initialize_low_arch (void) + +{ +-+ for (objfile *objfile : current_program_space->objfiles ()) +-+ { +-+ if (objfile->sf) +-+ objfile->sf->qf->expand_all_symtabs(objfile); +++ struct sigaction sa, old_sa; +++ /* Initialize the Linux target descriptions. */ +++ init_registers_sw_64_linux (); + + +-+ for (compunit_symtab *cust : objfile->compunits ()) +-+ { +-+ const struct blockvector *bv = COMPUNIT_BLOCKVECTOR (cust); +++ // initialize_regsets_info (&mips_regsets_info); + + +-+ for (int i = GLOBAL_BLOCK; i <= STATIC_BLOCK; ++i) +-+ { +-+ const struct block *b = BLOCKVECTOR_BLOCK (bv, i); +-+ struct block_iterator iter; +-+ struct symbol *sym; +++ sa.sa_sigaction = exc_handler; +++ sigemptyset (&sa.sa_mask); +++ sa.sa_flags = SA_RESTART|SA_SIGINFO; +++ sigaction (11, &sa, &old_sa); +++ sigaction (4, &sa, &old_sa); +++ sigaction (8, &sa, &old_sa); +++} ++diff -Nuar gdb-10.2/gdbserver/mem-break.cc gdb-10.2/gdbserver/mem-break.cc ++--- gdb-10.2/gdbserver/mem-break.cc 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdbserver/mem-break.cc 2025-04-16 17:06:51.992086800 +0800 ++@@ -1,5 +1,5 @@ ++ /* Memory breakpoint operations for the remote server for GDB. ++- Copyright (C) 2002-2021 Free Software Foundation, Inc. +++ Copyright (C) 2002-2020 Free Software Foundation, Inc. ++ ++ Contributed by MontaVista Software. ++ ++@@ -252,6 +252,10 @@ ++ return hw_read; ++ case raw_bkpt_type_access_wp: ++ return hw_access; +++#ifndef XWB20200308 +++ case raw_bkpt_type_value_wp: +++ return hw_vstore; +++#endif ++ default: ++ internal_error (__FILE__, __LINE__, ++ "bad raw breakpoint type %d", (int) raw_type); ++@@ -285,6 +289,10 @@ ++ return raw_bkpt_type_read_wp; ++ case Z_PACKET_ACCESS_WP: ++ return raw_bkpt_type_access_wp; +++#ifndef XWB20200308 +++ case Z_PACKET_DV_WP: +++ return raw_bkpt_type_value_wp; +++#endif ++ default: ++ gdb_assert_not_reached ("unhandled Z packet type."); ++ } ++diff -Nuar gdb-10.2/gdbserver/mem-break.h gdb-10.2/gdbserver/mem-break.h ++--- gdb-10.2/gdbserver/mem-break.h 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdbserver/mem-break.h 2025-04-16 17:06:51.992086800 +0800 ++@@ -1,5 +1,5 @@ ++ /* Memory breakpoint interfaces for the remote server for GDB. ++- Copyright (C) 2002-2021 Free Software Foundation, Inc. +++ Copyright (C) 2002-2020 Free Software Foundation, Inc. ++ ++ Contributed by MontaVista Software. ++ ++@@ -35,6 +35,9 @@ ++ #define Z_PACKET_WRITE_WP '2' ++ #define Z_PACKET_READ_WP '3' ++ #define Z_PACKET_ACCESS_WP '4' +++#ifndef XWB20200308 +++#define Z_PACKET_DV_WP '5' +++#endif ++ ++ /* The low level breakpoint types. */ ++ ++@@ -54,6 +57,9 @@ ++ ++ /* Hardware-assisted access watchpoint. */ ++ raw_bkpt_type_access_wp +++#ifndef XWB20200308 +++ ,raw_bkpt_type_value_wp +++#endif ++ }; ++ ++ /* Map the protocol breakpoint/watchpoint type Z_TYPE to the internal ++diff -Nuar gdb-10.2/gdbserver/server.h gdb-10.2/gdbserver/server.h ++--- gdb-10.2/gdbserver/server.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gdbserver/server.h 2025-04-16 17:06:52.022086800 +0800 ++@@ -1,5 +1,5 @@ ++ /* Common definitions for remote server for GDB. ++- Copyright (C) 1993-2021 Free Software Foundation, Inc. +++ Copyright (C) 1993-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -197,4 +197,16 @@ ++ #include "gdbthread.h" ++ #include "inferiors.h" ++ +++#ifndef _SW64_ +++#define debug(format, ... ) \ +++ do { \ +++ if (debug_threads) \ +++ { \ +++ debug_printf("%s:%d,%s:", __FILE__, __LINE__, __func__); \ +++ debug_printf(format, ##__VA_ARGS__); \ +++ debug_printf("\n"); \ +++ }\ +++ }while(0); +++#endif + + +-+ ALL_BLOCK_SYMBOLS (b, iter, sym) +-+ { +-+ QUIT; ++ #endif /* GDBSERVER_SERVER_H */ ++diff -Nuar gdb-10.2/gdbsupport/break-common.h gdb-10.2/gdbsupport/break-common.h ++--- gdb-10.2/gdbsupport/break-common.h 2021-04-25 12:04:35.000000000 +0800 +++++ gdb-10.2/gdbsupport/break-common.h 2025-04-16 17:06:51.992086800 +0800 ++@@ -1,6 +1,6 @@ ++ /* Data structures associated with breakpoints shared in both GDB and ++ GDBserver. ++- Copyright (C) 1992-2021 Free Software Foundation, Inc. +++ Copyright (C) 1992-2020 Free Software Foundation, Inc. ++ ++ This file is part of GDB. ++ ++@@ -26,6 +26,9 @@ ++ hw_read = 1, /* Read HW watchpoint */ ++ hw_access = 2, /* Access HW watchpoint */ ++ hw_execute = 3 /* Execute HW breakpoint */ +++#ifndef XWB20200308 +++,hw_vstore = 4 +++#endif ++ }; ++ ++ #endif /* COMMON_BREAK_COMMON_H */ ++diff -Nuar gdb-10.2/gnulib/configure gdb-10.2/gnulib/configure ++--- gdb-10.2/gnulib/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gnulib/configure 2025-04-16 17:06:51.992086800 +0800 ++@@ -6468,6 +6468,20 @@ ++ CPPFLAGS="$CPPFLAGS -ieee" ++ fi ++ ;; +++ sw_64*) +++ # On SW_64 systems, a compiler option provides the behaviour. +++ # See the ieee(3) manual page, also available at +++ # +++ if test -n "$GCC"; then +++ # GCC has the option -mieee. +++ # For full IEEE compliance (rarely needed), use option -mieee-with-inexact. +++ CPPFLAGS="$CPPFLAGS -mieee" +++ else +++ # Compaq (ex-DEC) C has the option -ieee, equivalent to -ieee_with_no_inexact. +++ # For full IEEE compliance (rarely needed), use option -ieee_with_inexact. +++ CPPFLAGS="$CPPFLAGS -ieee" +++ fi +++ ;; ++ sh*) ++ if test -n "$GCC"; then ++ # GCC has the option -mieee. ++diff -Nuar gdb-10.2/gnulib/import/cdefs.h gdb-10.2/gnulib/import/cdefs.h ++--- gdb-10.2/gnulib/import/cdefs.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gnulib/import/cdefs.h 2025-04-16 17:06:41.932086800 +0800 ++@@ -1,17 +1,18 @@ ++-/* Copyright (C) 1992-2020 Free Software Foundation, Inc. +++/* Copyright (C) 1992-2023 Free Software Foundation, Inc. +++ Copyright The GNU Toolchain Authors. ++ This file is part of the GNU C Library. ++ ++ The GNU C Library is free software; you can redistribute it and/or ++- modify it under the terms of the GNU General Public +++ modify it under the terms of the GNU Lesser General Public ++ License as published by the Free Software Foundation; either ++- version 3 of the License, or (at your option) any later version. +++ version 2.1 of the License, or (at your option) any later version. ++ ++ The GNU C Library 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. +++ Lesser General Public License for more details. ++ ++- You should have received a copy of the GNU General Public +++ You should have received a copy of the GNU Lesser General Public ++ License along with the GNU C Library; if not, see ++ . */ ++ ++@@ -25,16 +26,38 @@ ++ ++ /* The GNU libc does not support any K&R compilers or the traditional mode ++ of ISO C compilers anymore. Check for some of the combinations not ++- anymore supported. */ ++-#if defined __GNUC__ && !defined __STDC__ ++-# error "You need a ISO C conforming compiler to use the glibc headers" +++ supported anymore. */ +++#if defined __GNUC__ && !defined __STDC__ && !defined __cplusplus +++# error "You need a ISO C or C++ conforming compiler to use the glibc headers" ++ #endif ++ ++ /* Some user header file might have defined this before. */ ++ #undef __P ++ #undef __PMT ++ ++-#ifdef __GNUC__ +++/* Compilers that lack __has_attribute may object to +++ #if defined __has_attribute && __has_attribute (...) +++ even though they do not need to evaluate the right-hand side of the &&. +++ Similarly for __has_builtin, etc. */ +++#if (defined __has_attribute \ +++ && (!defined __clang_minor__ \ +++ || 3 < __clang_major__ + (5 <= __clang_minor__))) +++# define __glibc_has_attribute(attr) __has_attribute (attr) +++#else +++# define __glibc_has_attribute(attr) 0 +++#endif +++#ifdef __has_builtin +++# define __glibc_has_builtin(name) __has_builtin (name) +++#else +++# define __glibc_has_builtin(name) 0 +++#endif +++#ifdef __has_extension +++# define __glibc_has_extension(ext) __has_extension (ext) +++#else +++# define __glibc_has_extension(ext) 0 +++#endif + + +-+ if (SYMBOL_CLASS (sym) != LOC_TYPEDEF) +-+ continue; +++#if defined __GNUC__ || defined __clang__ ++ ++ /* All functions, except those with callbacks or those that ++ synchronize memory, are leaf functions. */ ++@@ -47,21 +70,26 @@ ++ # endif ++ ++ /* GCC can always grok prototypes. For C++ programs we add throw() ++- to help it optimize the function calls. But this works only with ++- gcc 2.8.x and egcs. For gcc 3.2 and up we even mark C functions +++ to help it optimize the function calls. But this only works with +++ gcc 2.8.x and egcs. For gcc 3.4 and up we even mark C functions ++ as non-throwing using a function attribute since programs can use ++ the -fexceptions options for C code as well. */ ++-# if !defined __cplusplus && __GNUC_PREREQ (3, 3) +++# if !defined __cplusplus \ +++ && (__GNUC_PREREQ (3, 4) || __glibc_has_attribute (__nothrow__)) ++ # define __THROW __attribute__ ((__nothrow__ __LEAF)) ++ # define __THROWNL __attribute__ ((__nothrow__)) ++ # define __NTH(fct) __attribute__ ((__nothrow__ __LEAF)) fct ++ # define __NTHNL(fct) __attribute__ ((__nothrow__)) fct ++ # else ++-# if defined __cplusplus && __GNUC_PREREQ (2,8) ++-# define __THROW throw () ++-# define __THROWNL throw () ++-# define __NTH(fct) __LEAF_ATTR fct throw () ++-# define __NTHNL(fct) fct throw () +++# if defined __cplusplus && (__GNUC_PREREQ (2,8) || __clang_major >= 4) +++# if __cplusplus >= 201103L +++# define __THROW noexcept (true) +++# else +++# define __THROW throw () +++# endif +++# define __THROWNL __THROW +++# define __NTH(fct) __LEAF_ATTR fct __THROW +++# define __NTHNL(fct) fct __THROW ++ # else ++ # define __THROW ++ # define __THROWNL ++@@ -70,7 +98,7 @@ ++ # endif ++ # endif ++ ++-#else /* Not GCC. */ +++#else /* Not GCC or clang. */ ++ ++ # if (defined __cplusplus \ ++ || (defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L)) ++@@ -83,16 +111,7 @@ ++ # define __THROWNL ++ # define __NTH(fct) fct ++ ++-#endif /* GCC. */ ++- ++-/* Compilers that are not clang may object to ++- #if defined __clang__ && __has_extension(...) ++- even though they do not need to evaluate the right-hand side of the &&. */ ++-#if defined __clang__ && defined __has_extension ++-# define __glibc_clang_has_extension(ext) __has_extension (ext) ++-#else ++-# define __glibc_clang_has_extension(ext) 0 ++-#endif +++#endif /* GCC || clang. */ ++ ++ /* These two macros are not used in glibc anymore. They are kept here ++ only because some other projects expect the macros to be defined. */ ++@@ -123,14 +142,70 @@ ++ #define __bos(ptr) __builtin_object_size (ptr, __USE_FORTIFY_LEVEL > 1) ++ #define __bos0(ptr) __builtin_object_size (ptr, 0) ++ +++/* Use __builtin_dynamic_object_size at _FORTIFY_SOURCE=3 when available. */ +++#if __USE_FORTIFY_LEVEL == 3 && (__glibc_clang_prereq (9, 0) \ +++ || __GNUC_PREREQ (12, 0)) +++# define __glibc_objsize0(__o) __builtin_dynamic_object_size (__o, 0) +++# define __glibc_objsize(__o) __builtin_dynamic_object_size (__o, 1) +++#else +++# define __glibc_objsize0(__o) __bos0 (__o) +++# define __glibc_objsize(__o) __bos (__o) +++#endif + + +-+ if (req->highest && +-+ !(req->lowest <= sym->type->length && sym->type->length <= req->highest)) +-+ continue; +++#if __USE_FORTIFY_LEVEL > 0 +++/* Compile time conditions to choose between the regular, _chk and _chk_warn +++ variants. These conditions should get evaluated to constant and optimized +++ away. */ + + +-+ req->addr = (ulong)(sym->type->main_type); +-+ req->name = (char *)(sym->m_name); +-+ req->length = sym->type->length; +++#define __glibc_safe_len_cond(__l, __s, __osz) ((__l) <= (__osz) / (__s)) +++#define __glibc_unsigned_or_positive(__l) \ +++ ((__typeof (__l)) 0 < (__typeof (__l)) -1 \ +++ || (__builtin_constant_p (__l) && (__l) > 0)) + + +-+ if (req->member) { +-+ req->value = lookup_struct_contents(req); +-+ if (!req->value) +-+ continue; +-+ } +-+ req->callback(req, req->callback_data); +-+ } +-+ } +-+ } +-+ } +-+} +++/* Length is known to be safe at compile time if the __L * __S <= __OBJSZ +++ condition can be folded to a constant and if it is true, or unknown (-1) */ +++#define __glibc_safe_or_unknown_len(__l, __s, __osz) \ +++ ((__builtin_constant_p (__osz) && (__osz) == (__SIZE_TYPE__) -1) \ +++ || (__glibc_unsigned_or_positive (__l) \ +++ && __builtin_constant_p (__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), \ +++ (__s), (__osz))) \ +++ && __glibc_safe_len_cond ((__SIZE_TYPE__) (__l), (__s), (__osz)))) +++ +++/* Conversely, we know at compile time that the length is unsafe if the +++ __L * __S <= __OBJSZ condition can be folded to a constant and if it is +++ false. */ +++#define __glibc_unsafe_len(__l, __s, __osz) \ +++ (__glibc_unsigned_or_positive (__l) \ +++ && __builtin_constant_p (__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), \ +++ __s, __osz)) \ +++ && !__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), __s, __osz)) +++ +++/* Fortify function f. __f_alias, __f_chk and __f_chk_warn must be +++ declared. */ +++ +++#define __glibc_fortify(f, __l, __s, __osz, ...) \ +++ (__glibc_safe_or_unknown_len (__l, __s, __osz) \ +++ ? __ ## f ## _alias (__VA_ARGS__) \ +++ : (__glibc_unsafe_len (__l, __s, __osz) \ +++ ? __ ## f ## _chk_warn (__VA_ARGS__, __osz) \ +++ : __ ## f ## _chk (__VA_ARGS__, __osz))) +++ +++/* Fortify function f, where object size argument passed to f is the number of +++ elements and not total size. */ +++ +++#define __glibc_fortify_n(f, __l, __s, __osz, ...) \ +++ (__glibc_safe_or_unknown_len (__l, __s, __osz) \ +++ ? __ ## f ## _alias (__VA_ARGS__) \ +++ : (__glibc_unsafe_len (__l, __s, __osz) \ +++ ? __ ## f ## _chk_warn (__VA_ARGS__, (__osz) / (__s)) \ +++ : __ ## f ## _chk (__VA_ARGS__, (__osz) / (__s)))) + +#endif +---- gdb-10.2/gdb/ui-file.h.orig +-+++ gdb-10.2/gdb/ui-file.h +-@@ -195,10 +195,10 @@ class stdio_file : public ui_file +- +- bool can_emit_style_escape () override; +++ ++ #if __GNUC_PREREQ (4,3) ++-# define __warndecl(name, msg) \ ++- extern void name (void) __attribute__((__warning__ (msg))) ++ # define __warnattr(msg) __attribute__((__warning__ (msg))) ++ # define __errordecl(name, msg) \ ++ extern void name (void) __attribute__((__error__ (msg))) ++ #else ++-# define __warndecl(name, msg) extern void name (void) ++ # define __warnattr(msg) ++ # define __errordecl(name, msg) extern void name (void) ++ #endif ++@@ -142,8 +217,8 @@ ++ #if defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L && !defined __HP_cc ++ # define __flexarr [] ++ # define __glibc_c99_flexarr_available 1 ++-#elif __GNUC_PREREQ (2,97) ++-/* GCC 2.97 supports C99 flexible array members as an extension, +++#elif __GNUC_PREREQ (2,97) || defined __clang__ +++/* GCC 2.97 and clang support C99 flexible array members as an extension, ++ even when in C89 mode or compiling C++ (any version). */ ++ # define __flexarr [] ++ # define __glibc_c99_flexarr_available 1 ++@@ -169,7 +244,7 @@ ++ Example: ++ int __REDIRECT(setpgrp, (__pid_t pid, __pid_t pgrp), setpgid); */ + +--private: +- /* Sets the internal stream to FILE, and saves the FILE's file +- descriptor in M_FD. */ +- void set_stream (FILE *file); +-+private: ++-#if defined __GNUC__ && __GNUC__ >= 2 +++#if (defined __GNUC__ && __GNUC__ >= 2) || (__clang_major__ >= 4) + +- /* The file. */ +- FILE *m_file; +---- gdb-10.2/gdb/xml-syscall.c.orig +-+++ gdb-10.2/gdb/xml-syscall.c +-@@ -37,7 +37,11 @@ +- static void +- syscall_warn_user (void) +- { +-+#ifdef CRASH_MERGE +-+ static int have_warned = 1; +-+#else +- static int have_warned = 0; +-+#endif +- if (!have_warned) +- { +- have_warned = 1; +---- gdb-10.2/libiberty/Makefile.in.orig +-+++ gdb-10.2/libiberty/Makefile.in +-@@ -180,6 +180,7 @@ REQUIRED_OFILES = \ +- ./getruntime.$(objext) ./hashtab.$(objext) ./hex.$(objext) \ +- ./lbasename.$(objext) ./lrealpath.$(objext) \ +- ./make-relative-prefix.$(objext) ./make-temp-file.$(objext) \ +-+ ./mkstemps.$(objext) \ +- ./objalloc.$(objext) \ +- ./obstack.$(objext) \ +- ./partition.$(objext) ./pexecute.$(objext) ./physmem.$(objext) \ +-@@ -213,7 +214,7 @@ CONFIGURED_OFILES = ./asprintf.$(objext) ./atexit.$(objext) \ +- ./index.$(objext) ./insque.$(objext) \ +- ./memchr.$(objext) ./memcmp.$(objext) ./memcpy.$(objext) \ +- ./memmem.$(objext) ./memmove.$(objext) \ +-- ./mempcpy.$(objext) ./memset.$(objext) ./mkstemps.$(objext) \ +-+ ./mempcpy.$(objext) ./memset.$(objext) \ +- ./pex-djgpp.$(objext) ./pex-msdos.$(objext) \ +- ./pex-unix.$(objext) ./pex-win32.$(objext) \ +- ./putenv.$(objext) \ +---- gdb-10.2/opcodes/i386-dis.c.orig +-+++ gdb-10.2/opcodes/i386-dis.c +-@@ -9778,6 +9778,10 @@ print_insn (bfd_vma pc, disassemble_info *info) +- threebyte = *codep; +- dp = &dis386_twobyte[threebyte]; +- need_modrm = twobyte_has_modrm[*codep]; +-+ if (dp->name && ((strcmp(dp->name, "ud2a") == 0) || (strcmp(dp->name, "ud2") == 0))) { +-+ extern int kernel_BUG_encoding_bytes(void); +-+ codep += kernel_BUG_encoding_bytes(); +-+ } +- codep++; +- } +- else +---- gdb-10.2/readline/readline/misc.c.orig +-+++ gdb-10.2/readline/readline/misc.c +-@@ -403,7 +403,7 @@ _rl_history_set_point (void) ++ # define __REDIRECT(name, proto, alias) name proto __asm__ (__ASMNAME (#alias)) ++ # ifdef __cplusplus ++@@ -194,17 +269,17 @@ ++ */ ++ #endif + +- #if defined (VI_MODE) +- if (rl_editing_mode == vi_mode && _rl_keymap != vi_insertion_keymap) +-- rl_point = 0; +-+ rl_point = rl_end; +- #endif /* VI_MODE */ ++-/* GCC has various useful declarations that can be made with the ++- `__attribute__' syntax. All of the ways we use this do fine if ++- they are omitted for compilers that don't understand it. */ ++-#if !defined __GNUC__ || __GNUC__ < 2 +++/* GCC and clang have various useful declarations that can be made with +++ the '__attribute__' syntax. All of the ways we use this do fine if +++ they are omitted for compilers that don't understand it. */ +++#if !(defined __GNUC__ || defined __clang__) ++ # define __attribute__(xyz) /* Ignore */ ++ #endif + +- if (rl_editing_mode == emacs_mode) +---- gdb-10.2/readline/readline/readline.h.orig +-+++ gdb-10.2/readline/readline/readline.h +-@@ -395,7 +395,7 @@ extern int rl_crlf PARAMS((void)); +- #if defined (USE_VARARGS) && defined (PREFER_STDARG) +- extern int rl_message (const char *, ...) __attribute__((__format__ (printf, 1, 2))); ++ /* At some point during the gcc 2.96 development the `malloc' attribute ++ for functions was introduced. We don't want to use it unconditionally ++ (although this would be possible) since it generates warnings. */ ++-#if __GNUC_PREREQ (2,96) +++#if __GNUC_PREREQ (2,96) || __glibc_has_attribute (__malloc__) ++ # define __attribute_malloc__ __attribute__ ((__malloc__)) + #else +--extern int rl_message (); +-+extern int rl_message (void); ++ # define __attribute_malloc__ /* Ignore */ ++@@ -219,26 +294,41 @@ ++ # define __attribute_alloc_size__(params) /* Ignore. */ + #endif + +- extern int rl_show_char PARAMS((int)); +---- gdb-10.2/readline/readline/rltypedefs.h.orig +-+++ gdb-10.2/readline/readline/rltypedefs.h +-@@ -32,10 +32,10 @@ extern "C" { +- # define _FUNCTION_DEF +++/* Tell the compiler which argument to an allocation function +++ indicates the alignment of the allocation. */ +++#if __GNUC_PREREQ (4, 9) || __glibc_has_attribute (__alloc_align__) +++# define __attribute_alloc_align__(param) \ +++ __attribute__ ((__alloc_align__ param)) +++#else +++# define __attribute_alloc_align__(param) /* Ignore. */ +++#endif +++ ++ /* At some point during the gcc 2.96 development the `pure' attribute ++ for functions was introduced. We don't want to use it unconditionally ++ (although this would be possible) since it generates warnings. */ ++-#if __GNUC_PREREQ (2,96) +++#if __GNUC_PREREQ (2,96) || __glibc_has_attribute (__pure__) ++ # define __attribute_pure__ __attribute__ ((__pure__)) ++ #else ++ # define __attribute_pure__ /* Ignore */ ++ #endif + +- #if defined(__GNUC__) || defined(__clang__) +--typedef int Function () __attribute__ ((deprecated)); +--typedef void VFunction () __attribute__ ((deprecated)); +--typedef char *CPFunction () __attribute__ ((deprecated)); +--typedef char **CPPFunction () __attribute__ ((deprecated)); +-+typedef int Function (void) __attribute__ ((deprecated)); +-+typedef void VFunction (void) __attribute__ ((deprecated)); +-+typedef char *CPFunction (void) __attribute__ ((deprecated)); +-+typedef char **CPPFunction (void) __attribute__ ((deprecated)); ++ /* This declaration tells the compiler that the value is constant. */ ++-#if __GNUC_PREREQ (2,5) +++#if __GNUC_PREREQ (2,5) || __glibc_has_attribute (__const__) ++ # define __attribute_const__ __attribute__ ((__const__)) + #else +- typedef int Function (); +- typedef void VFunction (); +---- gdb-10.2/readline/readline/util.c.orig +-+++ gdb-10.2/readline/readline/util.c +-@@ -487,10 +487,13 @@ _rl_trace (va_alist) ++ # define __attribute_const__ /* Ignore */ ++ #endif + +- if (_rl_tracefp == 0) +- _rl_tropen (); +-+ if (!_rl_tracefp) +-+ goto out; +- vfprintf (_rl_tracefp, format, args); +- fprintf (_rl_tracefp, "\n"); +- fflush (_rl_tracefp); +++#if __GNUC_PREREQ (2,7) || __glibc_has_attribute (__unused__) +++# define __attribute_maybe_unused__ __attribute__ ((__unused__)) +++#else +++# define __attribute_maybe_unused__ /* Ignore */ +++#endif +++ ++ /* At some point during the gcc 3.1 development the `used' attribute ++ for functions was introduced. We don't want to use it unconditionally ++ (although this would be possible) since it generates warnings. */ ++-#if __GNUC_PREREQ (3,1) +++#if __GNUC_PREREQ (3,1) || __glibc_has_attribute (__used__) ++ # define __attribute_used__ __attribute__ ((__used__)) ++ # define __attribute_noinline__ __attribute__ ((__noinline__)) ++ #else ++@@ -247,7 +337,7 @@ ++ #endif + +-+out: +- va_end (args); +- } ++ /* Since version 3.2, gcc allows marking deprecated functions. */ ++-#if __GNUC_PREREQ (3,2) +++#if __GNUC_PREREQ (3,2) || __glibc_has_attribute (__deprecated__) ++ # define __attribute_deprecated__ __attribute__ ((__deprecated__)) ++ #else ++ # define __attribute_deprecated__ /* Ignore */ ++@@ -256,8 +346,8 @@ ++ /* Since version 4.5, gcc also allows one to specify the message printed ++ when a deprecated function is used. clang claims to be gcc 4.2, but ++ may also support this feature. */ ++-#if __GNUC_PREREQ (4,5) || \ ++- __glibc_clang_has_extension (__attribute_deprecated_with_message__) +++#if __GNUC_PREREQ (4,5) \ +++ || __glibc_has_extension (__attribute_deprecated_with_message__) ++ # define __attribute_deprecated_msg__(msg) \ ++ __attribute__ ((__deprecated__ (msg))) ++ #else ++@@ -270,7 +360,7 @@ ++ If several `format_arg' attributes are given for the same function, in ++ gcc-3.0 and older, all but the last one are ignored. In newer gccs, ++ all designated arguments are considered. */ ++-#if __GNUC_PREREQ (2,8) +++#if __GNUC_PREREQ (2,8) || __glibc_has_attribute (__format_arg__) ++ # define __attribute_format_arg__(x) __attribute__ ((__format_arg__ (x))) ++ #else ++ # define __attribute_format_arg__(x) /* Ignore */ ++@@ -280,7 +370,7 @@ ++ attribute for functions was introduced. We don't want to use it ++ unconditionally (although this would be possible) since it ++ generates warnings. */ ++-#if __GNUC_PREREQ (2,97) +++#if __GNUC_PREREQ (2,97) || __glibc_has_attribute (__format__) ++ # define __attribute_format_strfmon__(a,b) \ ++ __attribute__ ((__format__ (__strfmon__, a, b))) ++ #else ++@@ -288,19 +378,33 @@ ++ #endif + +-@@ -513,16 +516,17 @@ _rl_tropen (void) +- sprintf (fnbuf, "/var/tmp/rltrace.%ld", (long) getpid ()); ++ /* The nonnull function attribute marks pointer parameters that ++- must not be NULL. Do not define __nonnull if it is already defined, ++- for portability when this file is used in Gnulib. */ +++ must not be NULL. This has the name __nonnull in glibc, +++ and __attribute_nonnull__ in files shared with Gnulib to avoid +++ collision with a different __nonnull in DragonFlyBSD 5.9. */ +++#ifndef __attribute_nonnull__ +++# if __GNUC_PREREQ (3,3) || __glibc_has_attribute (__nonnull__) +++# define __attribute_nonnull__(params) __attribute__ ((__nonnull__ params)) +++# else +++# define __attribute_nonnull__(params) +++# endif +++#endif ++ #ifndef __nonnull ++-# if __GNUC_PREREQ (3,3) ++-# define __nonnull(params) __attribute__ ((__nonnull__ params)) +++# define __nonnull(params) __attribute_nonnull__ (params) +++#endif +++ +++/* The returns_nonnull function attribute marks the return type of the function +++ as always being non-null. */ +++#ifndef __returns_nonnull +++# if __GNUC_PREREQ (4, 9) || __glibc_has_attribute (__returns_nonnull__) +++# define __returns_nonnull __attribute__ ((__returns_nonnull__)) ++ # else ++-# define __nonnull(params) +++# define __returns_nonnull ++ # endif ++ #endif ++ ++ /* If fortification mode, we warn about unused results of certain ++ function calls which can lead to problems. */ ++-#if __GNUC_PREREQ (3,4) +++#if __GNUC_PREREQ (3,4) || __glibc_has_attribute (__warn_unused_result__) ++ # define __attribute_warn_unused_result__ \ ++ __attribute__ ((__warn_unused_result__)) ++ # if defined __USE_FORTIFY_LEVEL && __USE_FORTIFY_LEVEL > 0 ++@@ -314,7 +418,7 @@ + #endif +- unlink (fnbuf); +-- _rl_tracefp = fopen (fnbuf, "w+"); +-+ _rl_tracefp = fopen (fnbuf, "w+xe"); +- return _rl_tracefp != 0; +- } + +- int +- _rl_trclose (void) +- { +-- int r; +-+ int r = 0; ++ /* Forces a function to be always inlined. */ ++-#if __GNUC_PREREQ (3,2) +++#if __GNUC_PREREQ (3,2) || __glibc_has_attribute (__always_inline__) ++ /* The Linux kernel defines __always_inline in stddef.h (283d7573), and ++ it conflicts with this definition. Therefore undefine it first to ++ allow either header to be included first. */ ++@@ -327,7 +431,7 @@ + +-- r = fclose (_rl_tracefp); +-+ if (_rl_tracefp) +-+ r = fclose (_rl_tracefp); +- _rl_tracefp = 0; +- return r; +- } +---- gdb-10.2/gdb/completer.c.orig +-+++ gdb-10.2/gdb/completer.c +-@@ -2949,6 +2949,8 @@ ++ /* Associate error messages with the source location of the call site rather ++ than with the source location inside the function. */ ++-#if __GNUC_PREREQ (4,3) +++#if __GNUC_PREREQ (4,3) || __glibc_has_attribute (__artificial__) ++ # define __attribute_artificial__ __attribute__ ((__artificial__)) ++ #else ++ # define __attribute_artificial__ /* Ignore */ ++@@ -370,12 +474,14 @@ ++ run in pedantic mode if the uses are carefully marked using the ++ `__extension__' keyword. But this is not generally available before ++ version 2.8. */ ++-#if !__GNUC_PREREQ (2,8) +++#if !(__GNUC_PREREQ (2,8) || defined __clang__) ++ # define __extension__ /* Ignore */ ++ #endif + +- /* How many items of MAX length can we fit in the screen window? */ +- cols = gdb_complete_get_screenwidth (displayer); +-+ rl_reset_screen_size(); +-+ rl_get_screen_size(NULL, &cols); +- max += 2; +- limit = cols / max; +- if (limit != 1 && (limit * max == cols)) +---- gdb-10.2/gdb/ada-lang.c.orig +-+++ gdb-10.2/gdb/ada-lang.c +-@@ -997,7 +997,7 @@ ada_fold_name (gdb::string_view name) +- int len = name.size (); +- GROW_VECT (fold_buffer, fold_buffer_size, len + 1); ++-/* __restrict is known in EGCS 1.2 and above. */ ++-#if !__GNUC_PREREQ (2,92) +++/* __restrict is known in EGCS 1.2 and above, and in clang. +++ It works also in C++ mode (outside of arrays), but only when spelled +++ as '__restrict', not 'restrict'. */ +++#if !(__GNUC_PREREQ (2,92) || __clang_major__ >= 3) ++ # if defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L ++ # define __restrict restrict ++ # else ++@@ -385,8 +491,9 @@ + +-- if (name[0] == '\'') +-+ if (!name.empty () && name[0] == '\'') +- { +- strncpy (fold_buffer, name.data () + 1, len - 2); +- fold_buffer[len - 2] = '\000'; +-@@ -1006,8 +1006,9 @@ ada_fold_name (gdb::string_view name) +- { +- int i; ++ /* ISO C99 also allows to declare arrays as non-overlapping. The syntax is ++ array_name[restrict] ++- GCC 3.1 supports this. */ ++-#if __GNUC_PREREQ (3,1) && !defined __GNUG__ +++ GCC 3.1 and clang support this. +++ This syntax is not usable in C++ mode. */ +++#if (__GNUC_PREREQ (3,1) || __clang_major__ >= 3) && !defined __cplusplus ++ # define __restrict_arr __restrict ++ #else ++ # ifdef __GNUC__ ++@@ -401,7 +508,7 @@ ++ # endif ++ #endif + +-- for (i = 0; i <= len; i += 1) +-+ for (i = 0; i < len; i += 1) +- fold_buffer[i] = tolower (name[i]); +-+ fold_buffer[i] = '\0'; +- } ++-#if __GNUC__ >= 3 +++#if (__GNUC__ >= 3) || __glibc_has_builtin (__builtin_expect) ++ # define __glibc_unlikely(cond) __builtin_expect ((cond), 0) ++ # define __glibc_likely(cond) __builtin_expect ((cond), 1) ++ #else ++@@ -409,15 +516,10 @@ ++ # define __glibc_likely(cond) (cond) ++ #endif + +- return fold_buffer; +-@@ -13596,7 +13597,7 @@ ada_lookup_name_info::ada_lookup_name_info (const lookup_name_info &lookup_name) +- { +- gdb::string_view user_name = lookup_name.name (); ++-#ifdef __has_attribute ++-# define __glibc_has_attribute(attr) __has_attribute (attr) ++-#else ++-# define __glibc_has_attribute(attr) 0 ++-#endif ++- ++ #if (!defined _Noreturn \ ++ && (defined __STDC_VERSION__ ? __STDC_VERSION__ : 0) < 201112 \ ++- && !__GNUC_PREREQ (4,7)) +++ && !(__GNUC_PREREQ (4,7) \ +++ || (3 < __clang_major__ + (5 <= __clang_minor__)))) ++ # if __GNUC_PREREQ (2,8) ++ # define _Noreturn __attribute__ ((__noreturn__)) ++ # else ++@@ -434,22 +536,63 @@ ++ # define __attribute_nonstring__ ++ #endif + +-- if (user_name[0] == '<') +-+ if (!user_name.empty () && user_name[0] == '<') +- { +- if (user_name.back () == '>') +- m_encoded_name +---- gdb-10.2/gdb/Makefile.in.orig +-+++ gdb-10.2/gdb/Makefile.in +-@@ -1865,7 +1865,7 @@ libgdb.a: $(LIBGDB_OBS) +- # Removing the old gdb first works better if it is running, at least on SunOS. +- gdb$(EXEEXT): gdb.o $(LIBGDB_OBS) $(CDEPS) $(TDEPLIBS) +- $(SILENCE) rm -f gdb$(EXEEXT) +-- @(cd ../..; make --no-print-directory GDB_FLAGS=-DGDB_10_2 library) +-+ @$(MAKE) -C ../.. GDB_FLAGS=-DGDB_10_2 library +- $(ECHO_CXXLD) $(CC_LD) $(INTERNAL_LDFLAGS) $(WIN32LDAPP) \ +- -o $(shell /bin/cat mergeobj) $(LIBGDB_OBS) \ +- $(TDEPLIBS) $(TUI_LIBRARY) $(CLIBS) $(LOADLIBES) $(shell /bin/cat mergelibs) +---- gdb-10.2/gdb/c-typeprint.c.orig +-+++ gdb-10.2/gdb/c-typeprint.c +-@@ -1202,6 +1202,9 @@ c_type_print_base_struct_union (struct t +- = podata->end_bitpos +- - TYPE_LENGTH (type->field (i).type ()) * TARGET_CHAR_BIT; +- } +-+ else if (strlen(TYPE_FIELD_NAME (type, i)) == 0) +-+ /* crash: Print details for unnamed struct and union. */ +-+ newshow = show; +- +- c_print_type_1 (type->field (i).type (), +- TYPE_FIELD_NAME (type, i), +---- gdb-10.2/gdb/symfile.c.orig +-+++ gdb-10.2/gdb/symfile.c +-@@ -1610,7 +1610,7 @@ find_separate_debug_file_by_debuglink (struct objfile *objfile) +- if (debugfile.empty ()) { +- char *name_copy; +- name_copy = check_specified_kernel_debug_file(); +-- return std::string (name_copy); +-+ return name_copy ? std::string (name_copy) : std::string (); +- } +++/* Undefine (also defined in libc-symbols.h). */ +++#undef __attribute_copy__ +++#if __GNUC_PREREQ (9, 0) +++/* Copies attributes from the declaration or type referenced by +++ the argument. */ +++# define __attribute_copy__(arg) __attribute__ ((__copy__ (arg))) +++#else +++# define __attribute_copy__(arg) +++#endif +++ ++ #if (!defined _Static_assert && !defined __cplusplus \ ++ && (defined __STDC_VERSION__ ? __STDC_VERSION__ : 0) < 201112 \ ++- && (!__GNUC_PREREQ (4, 6) || defined __STRICT_ANSI__)) +++ && (!(__GNUC_PREREQ (4, 6) || __clang_major__ >= 4) \ +++ || defined __STRICT_ANSI__)) ++ # define _Static_assert(expr, diagnostic) \ ++ extern int (*__Static_assert_function (void)) \ ++ [!!sizeof (struct { int __error_if_negative: (expr) ? 2 : -1; })] + #endif + +---- gdb-10.2/gdb/printcmd.c.orig +-+++ gdb-10.2/gdb/printcmd.c +-@@ -576,6 +576,10 @@ print_address_symbolic (struct gdbarch *gdbarch, CORE_ADDR addr, ++-/* The #ifndef lets Gnulib avoid including these on non-glibc ++- platforms, where the includes typically do not exist. */ ++-#ifndef __WORDSIZE +++/* Gnulib avoids including these, as they don't work on non-glibc or +++ older glibc platforms. */ +++#ifndef __GNULIB_CDEFS ++ # include ++ # include ++ #endif + +- /* See valprint.h. */ ++-#if defined __LONG_DOUBLE_MATH_OPTIONAL && defined __NO_LONG_DOUBLE_MATH +++#if __LDOUBLE_REDIRECTS_TO_FLOAT128_ABI == 1 +++# ifdef __REDIRECT +++ +++/* Alias name defined automatically. */ +++# define __LDBL_REDIR(name, proto) ... unused__ldbl_redir +++# define __LDBL_REDIR_DECL(name) \ +++ extern __typeof (name) name __asm (__ASMNAME ("__" #name "ieee128")); +++ +++/* Alias name defined automatically, with leading underscores. */ +++# define __LDBL_REDIR2_DECL(name) \ +++ extern __typeof (__##name) __##name \ +++ __asm (__ASMNAME ("__" #name "ieee128")); +++ +++/* Alias name defined manually. */ +++# define __LDBL_REDIR1(name, proto, alias) ... unused__ldbl_redir1 +++# define __LDBL_REDIR1_DECL(name, alias) \ +++ extern __typeof (name) name __asm (__ASMNAME (#alias)); +++ +++# define __LDBL_REDIR1_NTH(name, proto, alias) \ +++ __REDIRECT_NTH (name, proto, alias) +++# define __REDIRECT_NTH_LDBL(name, proto, alias) \ +++ __LDBL_REDIR1_NTH (name, proto, __##alias##ieee128) +++ +++/* Unused. */ +++# define __REDIRECT_LDBL(name, proto, alias) ... unused__redirect_ldbl +++# define __LDBL_REDIR_NTH(name, proto) ... unused__ldbl_redir_nth +++ +++# else +++_Static_assert (0, "IEEE 128-bits long double requires redirection on this platform"); +++# endif +++#elif defined __LONG_DOUBLE_MATH_OPTIONAL && defined __NO_LONG_DOUBLE_MATH ++ # define __LDBL_COMPAT 1 ++ # ifdef __REDIRECT ++ # define __LDBL_REDIR1(name, proto, alias) __REDIRECT (name, proto, alias) ++@@ -458,6 +601,8 @@ ++ # define __LDBL_REDIR1_NTH(name, proto, alias) __REDIRECT_NTH (name, proto, alias) ++ # define __LDBL_REDIR_NTH(name, proto) \ ++ __LDBL_REDIR1_NTH (name, proto, __nldbl_##name) +++# define __LDBL_REDIR2_DECL(name) \ +++ extern __typeof (__##name) __##name __asm (__ASMNAME ("__nldbl___" #name)); ++ # define __LDBL_REDIR1_DECL(name, alias) \ ++ extern __typeof (name) name __asm (__ASMNAME (#alias)); ++ # define __LDBL_REDIR_DECL(name) \ ++@@ -468,11 +613,13 @@ ++ __LDBL_REDIR1_NTH (name, proto, __nldbl_##alias) ++ # endif ++ #endif ++-#if !defined __LDBL_COMPAT || !defined __REDIRECT +++#if (!defined __LDBL_COMPAT && __LDOUBLE_REDIRECTS_TO_FLOAT128_ABI == 0) \ +++ || !defined __REDIRECT ++ # define __LDBL_REDIR1(name, proto, alias) name proto ++ # define __LDBL_REDIR(name, proto) name proto ++ # define __LDBL_REDIR1_NTH(name, proto, alias) name proto __THROW ++ # define __LDBL_REDIR_NTH(name, proto) name proto __THROW +++# define __LDBL_REDIR2_DECL(name) ++ # define __LDBL_REDIR_DECL(name) ++ # ifdef __REDIRECT ++ # define __REDIRECT_LDBL(name, proto, alias) __REDIRECT (name, proto, alias) ++@@ -503,7 +650,7 @@ ++ check is required to enable the use of generic selection. */ ++ #if !defined __cplusplus \ ++ && (__GNUC_PREREQ (4, 9) \ ++- || __glibc_clang_has_extension (c_generic_selections) \ +++ || __glibc_has_extension (c_generic_selections) \ ++ || (!defined __GNUC__ && defined __STDC_VERSION__ \ ++ && __STDC_VERSION__ >= 201112L)) ++ # define __HAVE_GENERIC_SELECTION 1 ++@@ -511,4 +658,50 @@ ++ # define __HAVE_GENERIC_SELECTION 0 ++ #endif + +-+#ifdef CRASH_MERGE +-+extern "C" char *gdb_lookup_module_symbol(unsigned long, unsigned long *); +++#if __GNUC_PREREQ (10, 0) +++/* Designates a 1-based positional argument ref-index of pointer type +++ that can be used to access size-index elements of the pointed-to +++ array according to access mode, or at least one element when +++ size-index is not provided: +++ access (access-mode, [, ]) */ +++# define __attr_access(x) __attribute__ ((__access__ x)) +++/* For _FORTIFY_SOURCE == 3 we use __builtin_dynamic_object_size, which may +++ use the access attribute to get object sizes from function definition +++ arguments, so we can't use them on functions we fortify. Drop the object +++ size hints for such functions. */ +++# if __USE_FORTIFY_LEVEL == 3 +++# define __fortified_attr_access(a, o, s) __attribute__ ((__access__ (a, o))) +++# else +++# define __fortified_attr_access(a, o, s) __attr_access ((a, o, s)) +++# endif +++# if __GNUC_PREREQ (11, 0) +++# define __attr_access_none(argno) __attribute__ ((__access__ (__none__, argno))) +++# else +++# define __attr_access_none(argno) +++# endif +++#else +++# define __fortified_attr_access(a, o, s) +++# define __attr_access(x) +++# define __attr_access_none(argno) +++#endif +++ +++#if __GNUC_PREREQ (11, 0) +++/* Designates dealloc as a function to call to deallocate objects +++ allocated by the declared function. */ +++# define __attr_dealloc(dealloc, argno) \ +++ __attribute__ ((__malloc__ (dealloc, argno))) +++# define __attr_dealloc_free __attr_dealloc (__builtin_free, 1) +++#else +++# define __attr_dealloc(dealloc, argno) +++# define __attr_dealloc_free + +#endif + + +- int +- build_address_symbolic (struct gdbarch *gdbarch, +- CORE_ADDR addr, /* IN */ +-@@ -682,7 +686,19 @@ build_address_symbolic (struct gdbarch *gdbarch, +- } +- } +- if (symbol == NULL && msymbol.minsym == NULL) +-+#ifdef CRASH_MERGE +-+ { +-+ char *name_ptr = gdb_lookup_module_symbol(addr, (unsigned long *)offset); +-+ if (name_ptr) { +-+ *name = name_ptr; +-+ return 0; +-+ } else { +-+ return 1; +-+ } +-+ } +++/* Specify that a function such as setjmp or vfork may return +++ twice. */ +++#if __GNUC_PREREQ (4, 1) +++# define __attribute_returns_twice__ __attribute__ ((__returns_twice__)) + +#else +- return 1; +++# define __attribute_returns_twice__ /* Ignore. */ + +#endif +++ ++ #endif /* sys/cdefs.h */ ++diff -Nuar gdb-10.2/gnulib/import/libc-config.h gdb-10.2/gnulib/import/libc-config.h ++--- gdb-10.2/gnulib/import/libc-config.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gnulib/import/libc-config.h 2025-04-16 17:06:41.932086800 +0800 ++@@ -79,13 +79,9 @@ ++ #ifndef _FEATURES_H ++ # define _FEATURES_H 1 ++ #endif ++-/* Define __WORDSIZE so that does not attempt to include ++- nonexistent files. Make it a syntax error, since Gnulib does not ++- use __WORDSIZE now, and if Gnulib uses it later the syntax error ++- will let us know that __WORDSIZE needs configuring. */ ++-#ifndef __WORDSIZE ++-# define __WORDSIZE %%% ++-#endif +++/* Define __GNULIB_CDEFS so that does not attempt to include +++ nonexistent files. */ +++# define __GNULIB_CDEFS ++ /* Undef the macros unconditionally defined by our copy of glibc ++ , so that they do not clash with any system-defined ++ versions. */ ++diff -Nuar gdb-10.2/gnulib/import/m4/fpieee.m4 gdb-10.2/gnulib/import/m4/fpieee.m4 ++--- gdb-10.2/gnulib/import/m4/fpieee.m4 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gnulib/import/m4/fpieee.m4 2025-04-16 17:06:52.002086800 +0800 ++@@ -44,6 +44,16 @@ ++ CPPFLAGS="$CPPFLAGS -ieee" ++ fi ++ ;; +++ sw_64*) +++ # On Sw_64 systems, a compiler option provides the behaviour. +++ # See the ieee(3) manual page, also available at +++ # if test -n "$GCC"; then +++ # GCC has the option -mieee. +++ # For full IEEE compliance (rarely needed), use option -mieee-with-inexact. CPPFLAGS="$CPPFLAGS -mieee" +++ else +++ # Compaq (ex-DEC) C has the option -ieee, equivalent to -ieee_with_no_inexact. # For full IEEE compliance (rarely needed), use option -ieee_with_inexact. +++ CPPFLAGS="$CPPFLAGS -ieee" fi +++ ;; ++ sh*) ++ if test -n "$GCC"; then ++ # GCC has the option -mieee. ++diff -Nuar gdb-10.2/gnulib/import/unistd.in.h gdb-10.2/gnulib/import/unistd.in.h ++--- gdb-10.2/gnulib/import/unistd.in.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/gnulib/import/unistd.in.h 2025-04-16 17:06:52.002086800 +0800 ++@@ -947,7 +947,7 @@ ++ # endif ++ /* This is for older VMS. */ ++ # if !defined _gl_getpagesize && defined __VMS ++-# ifdef __ALPHA +++# ifdef (__ALPHA_) || defined (__SW_64)//sbw ++ # define _gl_getpagesize() 8192 ++ # else ++ # define _gl_getpagesize() 512 ++diff -Nuar gdb-10.2/include/coff/ecoff.h gdb-10.2/include/coff/ecoff.h ++--- gdb-10.2/include/coff/ecoff.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/include/coff/ecoff.h 2025-04-16 17:06:52.002086800 +0800 ++@@ -47,6 +47,12 @@ ++ /* A compressed version of an ALPHA_MAGIC file created by DEC's tools. */ ++ #define ALPHA_MAGIC_COMPRESSED 0x188 + +- /* If the nearest symbol is too far away, don't print anything symbolic. */ +- +---- gdb-10.2/gdb/symtab.c.orig +-+++ gdb-10.2/gdb/symtab.c +-@@ -7128,8 +7128,8 @@ gdb_get_line_number(struct gnu_request * +- static void +- gdb_get_datatype(struct gnu_request *req) +- { +-- register struct type *type; +-- register struct type *typedef_type; +-+ struct type *type; +-+ struct type *typedef_type; +- expression_up expr; +- struct symbol *sym; +- struct value *val; +-@@ -7235,7 +7235,7 @@ gdb_get_datatype(struct gnu_request *req +- static void +- dump_enum(struct type *type, struct gnu_request *req) +- { +-- register int i; +-+ int i; +- int len; +- long long lastval; +- +-@@ -7271,7 +7271,7 @@ dump_enum(struct type *type, struct gnu_ +- static void +- eval_enum(struct type *type, struct gnu_request *req) +- { +-- register int i; +-+ int i; +- int len; +- long long lastval; +- +-@@ -7298,7 +7298,7 @@ eval_enum(struct type *type, struct gnu_ +- static void +- get_member_data(struct gnu_request *req, struct type *type, long offset, int is_first) +- { +-- register short i; +-+ short i; +- struct field *nextfield; +- short nfields; +- struct type *typedef_type, *target_type; +---- gdb-10.2/gdb/symtab.c.orig +-+++ gdb-10.2/gdb/symtab.c +-@@ -6913,7 +6913,7 @@ +- #include "../../defs.h" +- +- static void get_member_data(struct gnu_request *, struct type *, long, int); +--static void dump_enum(struct type *, struct gnu_request *); +-+static void walk_enum(struct type *, struct gnu_request *); +- static void eval_enum(struct type *, struct gnu_request *); +- static void gdb_get_line_number(struct gnu_request *); +- static void gdb_get_datatype(struct gnu_request *); +-@@ -7122,6 +7122,79 @@ +++/* SW_64 magic numbers used in filehdr. */ +++#define SW_64_MAGIC 0x184 +++#define SW_64_MAGIC_BSD 0x186 +++/* A compressed version of an SW_64_MAGIC file created by DEC's tools. */ +++#define SW_64_MAGIC_COMPRESSED 0x189 +++ ++ /* Magic numbers used in a.out header. */ ++ #define ECOFF_AOUT_OMAGIC 0407 /* not demand paged (ld -N). */ ++ #define ECOFF_AOUT_ZMAGIC 0413 /* demand load format, eg normal ld output */ ++diff -Nuar gdb-10.2/include/coff/sw_64.h gdb-10.2/include/coff/sw_64.h ++--- gdb-10.2/include/coff/sw_64.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/include/coff/sw_64.h 2025-04-16 17:06:52.022086800 +0800 ++@@ -0,0 +1,391 @@ +++/* ECOFF support on SW_64 machines. +++ coff/ecoff.h must be included before this file. +++ +++ Copyright (C) 2001-2019 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++/********************** FILE HEADER **********************/ +++ +++struct external_filehdr +++{ +++ unsigned char f_magic[2]; /* magic number */ +++ unsigned char f_nscns[2]; /* number of sections */ +++ unsigned char f_timdat[4]; /* time & date stamp */ +++ unsigned char f_symptr[8]; /* file pointer to symtab */ +++ unsigned char f_nsyms[4]; /* number of symtab entries */ +++ unsigned char f_opthdr[2]; /* sizeof(optional hdr) */ +++ unsigned char f_flags[2]; /* flags */ +++}; +++ +++/* Magic numbers are defined in coff/ecoff.h. */ +++#define SW_64_ECOFF_BADMAG(x) \ +++ ((x).f_magic != SW_64_MAGIC && (x).f_magic != SW_64_MAGIC_BSD) +++ +++#define SW_64_ECOFF_COMPRESSEDMAG(x) \ +++ ((x).f_magic == SW_64_MAGIC_COMPRESSED) +++ +++/* The object type is encoded in the f_flags. */ +++#define F_SW_64_OBJECT_TYPE_MASK 0x3000 +++#define F_SW_64_NO_SHARED 0x1000 +++#define F_SW_64_SHARABLE 0x2000 +++#define F_SW_64_CALL_SHARED 0x3000 +++ +++#define FILHDR struct external_filehdr +++#define FILHSZ 24 +++ +++/********************** AOUT "OPTIONAL HEADER" **********************/ +++ +++typedef struct external_aouthdr +++{ +++ unsigned char magic[2]; /* type of file */ +++ unsigned char vstamp[2]; /* version stamp */ +++ unsigned char bldrev[2]; /* ?? */ +++ unsigned char padding[2]; /* pad to quadword boundary */ +++ unsigned char tsize[8]; /* text size in bytes */ +++ unsigned char dsize[8]; /* initialized data " " */ +++ unsigned char bsize[8]; /* uninitialized data " " */ +++ unsigned char entry[8]; /* entry pt. */ +++ unsigned char text_start[8]; /* base of text used for this file */ +++ unsigned char data_start[8]; /* base of data used for this file */ +++ unsigned char bss_start[8]; /* base of bss used for this file */ +++ unsigned char gprmask[4]; /* bitmask of general registers used */ +++ unsigned char fprmask[4]; /* bitmask of floating point registers used */ +++ unsigned char gp_value[8]; /* value for gp register */ +++} AOUTHDR; +++ +++/* compute size of a header */ +++ +++#define AOUTSZ 80 +++#define AOUTHDRSZ 80 +++ +++/********************** SECTION HEADER **********************/ +++ +++struct external_scnhdr +++{ +++ unsigned char s_name[8]; /* section name */ +++ unsigned char s_paddr[8]; /* physical address, aliased s_nlib */ +++ unsigned char s_vaddr[8]; /* virtual address */ +++ unsigned char s_size[8]; /* section size */ +++ unsigned char s_scnptr[8]; /* file ptr to raw data for section */ +++ unsigned char s_relptr[8]; /* file ptr to relocation */ +++ unsigned char s_lnnoptr[8]; /* file ptr to line numbers */ +++ unsigned char s_nreloc[2]; /* number of relocation entries */ +++ unsigned char s_nlnno[2]; /* number of line number entries*/ +++ unsigned char s_flags[4]; /* flags */ +++}; +++ +++#define SCNHDR struct external_scnhdr +++#define SCNHSZ 64 +++ +++/********************** RELOCATION DIRECTIVES **********************/ +++ +++struct external_reloc +++{ +++ unsigned char r_vaddr[8]; +++ unsigned char r_symndx[4]; +++ unsigned char r_bits[4]; +++}; +++ +++#define RELOC struct external_reloc +++#define RELSZ 16 +++ +++/* Constants to unpack the r_bits field. The SW_64 seems to always be +++ little endian, so I haven't bothered to define big endian variants +++ of these. */ +++ +++#define RELOC_BITS0_TYPE_LITTLE 0xff +++#define RELOC_BITS0_TYPE_SH_LITTLE 0 +++ +++#define RELOC_BITS1_EXTERN_LITTLE 0x01 +++ +++#define RELOC_BITS1_OFFSET_LITTLE 0x7e +++#define RELOC_BITS1_OFFSET_SH_LITTLE 1 +++ +++#define RELOC_BITS1_RESERVED_LITTLE 0x80 +++#define RELOC_BITS1_RESERVED_SH_LITTLE 7 +++#define RELOC_BITS2_RESERVED_LITTLE 0xff +++#define RELOC_BITS2_RESERVED_SH_LEFT_LITTLE 1 +++#define RELOC_BITS3_RESERVED_LITTLE 0x03 +++#define RELOC_BITS3_RESERVED_SH_LEFT_LITTLE 9 +++ +++#define RELOC_BITS3_SIZE_LITTLE 0xfc +++#define RELOC_BITS3_SIZE_SH_LITTLE 2 +++ +++/* The r_type field in a reloc is one of the following values. */ +++#define SW_64_R_IGNORE 0 +++#define SW_64_R_REFLONG 1 +++#define SW_64_R_REFQUAD 2 +++#define SW_64_R_GPREL32 3 +++#define SW_64_R_LITERAL 4 +++#define SW_64_R_LITUSE 5 +++#define SW_64_R_GPDISP 6 +++#define SW_64_R_BRADDR 7 +++#define SW_64_R_HINT 8 +++#define SW_64_R_SREL16 9 +++#define SW_64_R_SREL32 10 +++#define SW_64_R_SREL64 11 +++#define SW_64_R_OP_PUSH 12 +++#define SW_64_R_OP_STORE 13 +++#define SW_64_R_OP_PSUB 14 +++#define SW_64_R_OP_PRSHIFT 15 +++#define SW_64_R_GPVALUE 16 +++#define SW_64_R_GPRELHIGH 17 +++#define SW_64_R_GPRELLOW 18 +++#define SW_64_R_IMMED 19 +++ +++#ifndef _SW64_ +++#define SW_64_R_BR18ADDR 20 +++#define SW_64_R_BR22ADDR 21 +++#endif +++ +++/* Overloaded reloc value used by Net- and OpenBSD. */ +++#define SW_64_R_LITERALSLEAZY 17 +++ +++/* With SW_64_R_LITUSE, the r_size field is one of the following values. */ +++#define SW_64_R_LU_BASE 1 +++#define SW_64_R_LU_BYTOFF 2 +++#define SW_64_R_LU_JSR 3 +++ +++/* With SW_64_R_IMMED, the r_size field is one of the following values. */ +++#define SW_64_R_IMMED_GP_16 1 +++#define SW_64_R_IMMED_GP_HI32 2 +++#define SW_64_R_IMMED_SCN_HI32 3 +++#define SW_64_R_IMMED_BR_HI32 4 +++#define SW_64_R_IMMED_LO32 5 +++ +++/********************** SYMBOLIC INFORMATION **********************/ +++ +++/* Written by John Gilmore. */ +++ +++/* ECOFF uses COFF-like section structures, but its own symbol format. +++ This file defines the symbol format in fields whose size and alignment +++ will not vary on different host systems. */ +++ +++/* File header as a set of bytes */ +++ +++struct hdr_ext +++{ +++ unsigned char h_magic[2]; +++ unsigned char h_vstamp[2]; +++ unsigned char h_ilineMax[4]; +++ unsigned char h_idnMax[4]; +++ unsigned char h_ipdMax[4]; +++ unsigned char h_isymMax[4]; +++ unsigned char h_ioptMax[4]; +++ unsigned char h_iauxMax[4]; +++ unsigned char h_issMax[4]; +++ unsigned char h_issExtMax[4]; +++ unsigned char h_ifdMax[4]; +++ unsigned char h_crfd[4]; +++ unsigned char h_iextMax[4]; +++ unsigned char h_cbLine[8]; +++ unsigned char h_cbLineOffset[8]; +++ unsigned char h_cbDnOffset[8]; +++ unsigned char h_cbPdOffset[8]; +++ unsigned char h_cbSymOffset[8]; +++ unsigned char h_cbOptOffset[8]; +++ unsigned char h_cbAuxOffset[8]; +++ unsigned char h_cbSsOffset[8]; +++ unsigned char h_cbSsExtOffset[8]; +++ unsigned char h_cbFdOffset[8]; +++ unsigned char h_cbRfdOffset[8]; +++ unsigned char h_cbExtOffset[8]; +++}; +++ +++/* File descriptor external record */ +++ +++struct fdr_ext +++{ +++ unsigned char f_adr[8]; +++ unsigned char f_cbLineOffset[8]; +++ unsigned char f_cbLine[8]; +++ unsigned char f_cbSs[8]; +++ unsigned char f_rss[4]; +++ unsigned char f_issBase[4]; +++ unsigned char f_isymBase[4]; +++ unsigned char f_csym[4]; +++ unsigned char f_ilineBase[4]; +++ unsigned char f_cline[4]; +++ unsigned char f_ioptBase[4]; +++ unsigned char f_copt[4]; +++ unsigned char f_ipdFirst[4]; +++ unsigned char f_cpd[4]; +++ unsigned char f_iauxBase[4]; +++ unsigned char f_caux[4]; +++ unsigned char f_rfdBase[4]; +++ unsigned char f_crfd[4]; +++ unsigned char f_bits1[1]; +++ unsigned char f_bits2[3]; +++ unsigned char f_padding[4]; +++}; +++ +++#define FDR_BITS1_LANG_BIG 0xF8 +++#define FDR_BITS1_LANG_SH_BIG 3 +++#define FDR_BITS1_LANG_LITTLE 0x1F +++#define FDR_BITS1_LANG_SH_LITTLE 0 +++ +++#define FDR_BITS1_FMERGE_BIG 0x04 +++#define FDR_BITS1_FMERGE_LITTLE 0x20 +++ +++#define FDR_BITS1_FREADIN_BIG 0x02 +++#define FDR_BITS1_FREADIN_LITTLE 0x40 +++ +++#define FDR_BITS1_FBIGENDIAN_BIG 0x01 +++#define FDR_BITS1_FBIGENDIAN_LITTLE 0x80 +++ +++#define FDR_BITS2_GLEVEL_BIG 0xC0 +++#define FDR_BITS2_GLEVEL_SH_BIG 6 +++#define FDR_BITS2_GLEVEL_LITTLE 0x03 +++#define FDR_BITS2_GLEVEL_SH_LITTLE 0 +++ +++/* We ignore the `reserved' field in bits2. */ +++ +++/* Procedure descriptor external record */ +++ +++struct pdr_ext { +++ unsigned char p_adr[8]; +++ unsigned char p_cbLineOffset[8]; +++ unsigned char p_isym[4]; +++ unsigned char p_iline[4]; +++ unsigned char p_regmask[4]; +++ unsigned char p_regoffset[4]; +++ unsigned char p_iopt[4]; +++ unsigned char p_fregmask[4]; +++ unsigned char p_fregoffset[4]; +++ unsigned char p_frameoffset[4]; +++ unsigned char p_lnLow[4]; +++ unsigned char p_lnHigh[4]; +++ unsigned char p_gp_prologue[1]; +++ unsigned char p_bits1[1]; +++ unsigned char p_bits2[1]; +++ unsigned char p_localoff[1]; +++ unsigned char p_framereg[2]; +++ unsigned char p_pcreg[2]; +++}; +++ +++#define PDR_BITS1_GP_USED_BIG 0x80 +++#define PDR_BITS1_REG_FRAME_BIG 0x40 +++#define PDR_BITS1_PROF_BIG 0x20 +++#define PDR_BITS1_RESERVED_BIG 0x1f +++#define PDR_BITS1_RESERVED_SH_LEFT_BIG 8 +++#define PDR_BITS2_RESERVED_BIG 0xff +++#define PDR_BITS2_RESERVED_SH_BIG 0 +++ +++#define PDR_BITS1_GP_USED_LITTLE 0x01 +++#define PDR_BITS1_REG_FRAME_LITTLE 0x02 +++#define PDR_BITS1_PROF_LITTLE 0x04 +++#define PDR_BITS1_RESERVED_LITTLE 0xf8 +++#define PDR_BITS1_RESERVED_SH_LITTLE 3 +++#define PDR_BITS2_RESERVED_LITTLE 0xff +++#define PDR_BITS2_RESERVED_SH_LEFT_LITTLE 5 +++ +++/* Line numbers */ +++ +++struct line_ext { +++ unsigned char l_line[4]; +++}; +++ +++/* Symbol external record */ +++ +++struct sym_ext { +++ unsigned char s_value[8]; +++ unsigned char s_iss[4]; +++ unsigned char s_bits1[1]; +++ unsigned char s_bits2[1]; +++ unsigned char s_bits3[1]; +++ unsigned char s_bits4[1]; +++}; +++ +++#define SYM_BITS1_ST_BIG 0xFC +++#define SYM_BITS1_ST_SH_BIG 2 +++#define SYM_BITS1_ST_LITTLE 0x3F +++#define SYM_BITS1_ST_SH_LITTLE 0 +++ +++#define SYM_BITS1_SC_BIG 0x03 +++#define SYM_BITS1_SC_SH_LEFT_BIG 3 +++#define SYM_BITS1_SC_LITTLE 0xC0 +++#define SYM_BITS1_SC_SH_LITTLE 6 +++ +++#define SYM_BITS2_SC_BIG 0xE0 +++#define SYM_BITS2_SC_SH_BIG 5 +++#define SYM_BITS2_SC_LITTLE 0x07 +++#define SYM_BITS2_SC_SH_LEFT_LITTLE 2 +++ +++#define SYM_BITS2_RESERVED_BIG 0x10 +++#define SYM_BITS2_RESERVED_LITTLE 0x08 +++ +++#define SYM_BITS2_INDEX_BIG 0x0F +++#define SYM_BITS2_INDEX_SH_LEFT_BIG 16 +++#define SYM_BITS2_INDEX_LITTLE 0xF0 +++#define SYM_BITS2_INDEX_SH_LITTLE 4 +++ +++#define SYM_BITS3_INDEX_SH_LEFT_BIG 8 +++#define SYM_BITS3_INDEX_SH_LEFT_LITTLE 4 +++ +++#define SYM_BITS4_INDEX_SH_LEFT_BIG 0 +++#define SYM_BITS4_INDEX_SH_LEFT_LITTLE 12 +++ +++/* External symbol external record */ +++ +++struct ext_ext { +++ struct sym_ext es_asym; +++ unsigned char es_bits1[1]; +++ unsigned char es_bits2[3]; +++ unsigned char es_ifd[4]; +++}; +++ +++#define EXT_BITS1_JMPTBL_BIG 0x80 +++#define EXT_BITS1_JMPTBL_LITTLE 0x01 +++ +++#define EXT_BITS1_COBOL_MAIN_BIG 0x40 +++#define EXT_BITS1_COBOL_MAIN_LITTLE 0x02 +++ +++#define EXT_BITS1_WEAKEXT_BIG 0x20 +++#define EXT_BITS1_WEAKEXT_LITTLE 0x04 +++ +++/* Dense numbers external record */ +++ +++struct dnr_ext { +++ unsigned char d_rfd[4]; +++ unsigned char d_index[4]; +++}; +++ +++/* Relative file descriptor */ +++ +++struct rfd_ext { +++ unsigned char rfd[4]; +++}; +++ +++/* Optimizer symbol external record */ +++ +++struct opt_ext { +++ unsigned char o_bits1[1]; +++ unsigned char o_bits2[1]; +++ unsigned char o_bits3[1]; +++ unsigned char o_bits4[1]; +++ struct rndx_ext o_rndx; +++ unsigned char o_offset[4]; +++}; +++ +++#define OPT_BITS2_VALUE_SH_LEFT_BIG 16 +++#define OPT_BITS2_VALUE_SH_LEFT_LITTLE 0 +++ +++#define OPT_BITS3_VALUE_SH_LEFT_BIG 8 +++#define OPT_BITS3_VALUE_SH_LEFT_LITTLE 8 +++ +++#define OPT_BITS4_VALUE_SH_LEFT_BIG 0 +++#define OPT_BITS4_VALUE_SH_LEFT_LITTLE 16 ++diff -Nuar gdb-10.2/include/elf/common.h gdb-10.2/include/elf/common.h ++--- gdb-10.2/include/elf/common.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/include/elf/common.h 2025-04-16 17:06:52.002086800 +0800 ++@@ -396,7 +396,8 @@ + ++ /* Alpha backend magic number. Written in the absence of an ABI. */ ++ #define EM_ALPHA 0x9026 ++- +++/* SW_64 backend magic number. Written in the absence of an ABI. */ +++#define EM_SW_64 0x9916 ++ /* Cygnus M32R ELF backend. Written in the absence of an ABI. */ ++ #define EM_CYGNUS_M32R 0x9041 + +- /* +-+ * Follow the type linkage for full member and value type resolution, with callback +-+ */ +-+static void drillDownType(struct gnu_request *req, struct type *type) ++diff -Nuar gdb-10.2/include/elf/sw_64.h gdb-10.2/include/elf/sw_64.h ++--- gdb-10.2/include/elf/sw_64.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/include/elf/sw_64.h 2025-04-16 17:06:52.022086800 +0800 ++@@ -0,0 +1,135 @@ +++/* SW_64 ELF support for BFD. +++ Copyright (C) 1996-2019 Free Software Foundation, Inc. +++ +++ By Eric Youngdale, . No processor supplement available +++ for this platform. +++ +++ This file is part of BFD, the Binary File Descriptor library. +++ +++ 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, write to the Free Software +++ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++/* This file holds definitions specific to the SW_64 ELF ABI. Note +++ that most of this is not actually implemented by BFD. */ +++ +++#ifndef _ELF_SW_64_H +++#define _ELF_SW_64_H +++ +++/* Processor specific flags for the ELF header e_flags field. */ +++ +++/* All addresses must be below 2GB. */ +++#define EF_SW_64_32BIT 0x00000001 +++ +++/* All relocations needed for relaxation with code movement are present. */ +++#define EF_SW_64_CANRELAX 0x00000002 +++ +++/* Processor specific section flags. */ +++ +++/* This section must be in the global data area. */ +++#define SHF_SW_64_GPREL 0x10000000 +++ +++/* Section contains some sort of debugging information. The exact +++ format is unspecified. It's probably ECOFF symbols. */ +++#define SHT_SW_64_DEBUG 0x70000001 +++ +++/* Section contains register usage information. */ +++#define SHT_SW_64_REGINFO 0x70000002 +++ +++/* A section of type SHT_MIPS_REGINFO contains the following +++ structure. */ +++typedef struct + +{ +-+ while (type) +-+ { +-+ /* check out for stub types and pull in the definition instead */ +-+ if (TYPE_STUB(type) && TYPE_TAG_NAME(type)) { +-+ struct symbol *sym; +-+ sym = lookup_symbol(TYPE_TAG_NAME(type), 0, STRUCT_DOMAIN, 0).symbol; +-+ if (sym) +-+ type = sym->type; +-+ } +-+ switch (TYPE_CODE(type)) { +-+ drill_ops_t op; +-+ long l1, l2; +-+ int typecode; +++ /* Mask of general purpose registers used. */ +++ unsigned long ri_gprmask; +++ /* Mask of co-processor registers used. */ +++ unsigned long ri_cprmask[4]; +++ /* GP register value for this object file. */ +++ long ri_gp_value; +++} Elf64_RegInfo; + + +-+ case TYPE_CODE_PTR: +-+ req->tcb(EOP_POINTER, req, 0, 0, 0, 0); +-+ break; +++/* Special values for the st_other field in the symbol table. */ + + +-+ case TYPE_CODE_TYPEDEF: +-+ req->is_typedef = 1; +-+ req->typecode = TYPE_CODE(type); +-+ if (!req->tcb(EOP_TYPEDEF, req, TYPE_NAME(type), 0, 0, 0)) +-+ return; +-+ break; +++#define STO_SW_64_NOPV 0x80 +++#define STO_SW_64_STD_GPLOAD 0x88 + + +-+ case TYPE_CODE_FUNC: +-+ req->tcb(EOP_FUNCTION, req, 0, 0, 0, 0); +-+ break; +++/* Special values for Elf64_Dyn tag. */ +++#define DT_SW_64_PLTRO DT_LOPROC + + +-+ case TYPE_CODE_ARRAY: +-+ l1 = TYPE_LENGTH (type); +-+ l2 = TYPE_LENGTH (check_typedef(TYPE_TARGET_TYPE (type))); +-+ req->tcb(EOP_ARRAY, req, &l1, &l2, 0, 0); +-+ break; +++#include "elf/reloc-macros.h" + + +-+ case TYPE_CODE_VOID: +-+ case TYPE_CODE_INT: +-+ case TYPE_CODE_BOOL: +-+ l1 = TYPE_LENGTH(type); +-+ req->tcb(EOP_INT, req, &l1, 0, 0, 0); +-+ break; +++/* sw_64 relocs. */ +++START_RELOC_NUMBERS (elf_sw_64_reloc_type) +++ RELOC_NUMBER (R_SW_64_NONE, 0) /* No reloc */ +++ RELOC_NUMBER (R_SW_64_REFLONG, 1) /* Direct 32 bit */ +++ RELOC_NUMBER (R_SW_64_REFQUAD, 2) /* Direct 64 bit */ +++ RELOC_NUMBER (R_SW_64_GPREL32, 3) /* GP relative 32 bit */ +++ RELOC_NUMBER (R_SW_64_LITERAL, 4) /* GP relative 16 bit w/optimization */ +++ RELOC_NUMBER (R_SW_64_LITUSE, 5) /* Optimization hint for LITERAL */ +++ RELOC_NUMBER (R_SW_64_GPDISP, 6) /* Add displacement to GP */ +++ RELOC_NUMBER (R_SW_64_BRADDR, 7) /* PC+4 relative 23 bit shifted */ +++ RELOC_NUMBER (R_SW_64_HINT, 8) /* PC+4 relative 16 bit shifted */ +++ RELOC_NUMBER (R_SW_64_SREL16, 9) /* PC relative 16 bit */ +++ RELOC_NUMBER (R_SW_64_SREL32, 10) /* PC relative 32 bit */ +++ RELOC_NUMBER (R_SW_64_SREL64, 11) /* PC relative 64 bit */ +++ +++ /* Skip 12 - 16; deprecated ECOFF relocs. */ +++#ifndef _SW64_ +++ RELOC_NUMBER (R_SW_64_BR18ADDR, 12) /* PC+4 relative 20 bit shifted */ +++ RELOC_NUMBER (R_SW_64_BR22ADDR, 13) /* PC+4 relative 24 bit shifted */ +++#endif +++ +++ RELOC_NUMBER (R_SW_64_GPRELHIGH, 17) /* GP relative 32 bit, high 16 bits */ +++ RELOC_NUMBER (R_SW_64_GPRELLOW, 18) /* GP relative 32 bit, low 16 bits */ +++ RELOC_NUMBER (R_SW_64_GPREL16, 19) /* GP relative 16 bit */ +++ +++ /* Skip 20 - 23; deprecated ECOFF relocs. */ +++ +++ /* These relocations are specific to shared libraries. */ +++ RELOC_NUMBER (R_SW_64_COPY, 24) /* Copy symbol at runtime */ +++ RELOC_NUMBER (R_SW_64_GLOB_DAT, 25) /* Create GOT entry */ +++ RELOC_NUMBER (R_SW_64_JMP_SLOT, 26) /* Create PLT entry */ +++ RELOC_NUMBER (R_SW_64_RELATIVE, 27) /* Adjust by program base */ +++ +++ /* Like BRADDR, but assert that the source and target object file +++ share the same GP value, and adjust the target address for +++ STO_SW_64_STD_GPLOAD. */ +++ RELOC_NUMBER (R_SW_64_BRSGP, 28) +++ +++ /* Thread-Local Storage. */ +++ RELOC_NUMBER (R_SW_64_TLSGD, 29) +++ RELOC_NUMBER (R_SW_64_TLSLDM, 30) +++ RELOC_NUMBER (R_SW_64_DTPMOD64, 31) +++ RELOC_NUMBER (R_SW_64_GOTDTPREL, 32) +++ RELOC_NUMBER (R_SW_64_DTPREL64, 33) +++ RELOC_NUMBER (R_SW_64_DTPRELHI, 34) +++ RELOC_NUMBER (R_SW_64_DTPRELLO, 35) +++ RELOC_NUMBER (R_SW_64_DTPREL16, 36) +++ RELOC_NUMBER (R_SW_64_GOTTPREL, 37) +++ RELOC_NUMBER (R_SW_64_TPREL64, 38) +++ RELOC_NUMBER (R_SW_64_TPRELHI, 39) +++ RELOC_NUMBER (R_SW_64_TPRELLO, 40) +++ RELOC_NUMBER (R_SW_64_TPREL16, 41) +++ +++END_RELOC_NUMBERS (R_SW_64_max) +++ +++#define LITUSE_SW_64_ADDR 0 +++#define LITUSE_SW_64_BASE 1 +++#define LITUSE_SW_64_BYTOFF 2 +++#define LITUSE_SW_64_JSR 3 +++#define LITUSE_SW_64_TLSGD 4 +++#define LITUSE_SW_64_TLSLDM 5 +++#define LITUSE_SW_64_JSRDIRECT 6 +++ +++#endif /* _ELF_SW_64_H */ ++diff -Nuar gdb-10.2/include/opcode/sw_64.h gdb-10.2/include/opcode/sw_64.h ++--- gdb-10.2/include/opcode/sw_64.h 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/include/opcode/sw_64.h 2025-04-16 17:06:52.002086800 +0800 ++@@ -0,0 +1,247 @@ +++/* sw_64.h -- Header file for Sw_64 opcode table +++ Copyright (C) 1996-2018 Free Software Foundation, Inc. +++ Contributed by Richard Henderson , +++ patterned after the PPC opcode table written by Ian Lance Taylor. +++ +++ This file is part of GDB, GAS, and the GNU binutils. +++ +++ GDB, GAS, and the GNU binutils are free software; you can redistribute +++ them and/or modify them under the terms of the GNU General Public +++ License as published by the Free Software Foundation; either version 3, +++ or (at your option) any later version. +++ +++ GDB, GAS, and the GNU binutils are distributed in the hope that they +++ 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 file; see the file COPYING3. If not, write to the Free +++ Software Foundation, 51 Franklin Street - Fifth Floor, Boston, +++ MA 02110-1301, USA. */ +++ +++#ifndef OPCODE_SW_64_H +++#define OPCODE_SW_64_H +++ +++/* The opcode table is an array of struct sw_64_opcode. */ +++ +++struct sw_64_opcode +++{ +++ /* The opcode name. */ +++ const char *name; +++ +++ /* The opcode itself. Those bits which will be filled in with +++ operands are zeroes. */ +++ unsigned opcode; +++ +++ /* The opcode mask. This is used by the disassembler. This is a +++ mask containing ones indicating those bits which must match the +++ opcode field, and zeroes indicating those bits which need not +++ match (and are presumably filled in by operands). */ +++ unsigned mask; +++ +++ /* One bit flags for the opcode. These are primarily used to +++ indicate specific processors and environments support the +++ instructions. The defined values are listed below. */ +++ unsigned flags; +++ +++ /* An array of operand codes. Each code is an index into the +++ operand table. They appear in the order which the operands must +++ appear in assembly code, and are terminated by a zero. */ +++ unsigned char operands[5]; +++}; +++ +++/* The table itself is sorted by major opcode number, and is otherwise +++ in the order in which the disassembler should consider +++ instructions. */ +++extern const struct sw_64_opcode sw_64_opcodes[]; +++extern const unsigned sw_64_num_opcodes; +++ +++/* Values defined for the flags field of a struct sw_64_opcode. */ +++ +++/* CPU Availability */ +++#define AXP_OPCODE_BASE 0x0001 /* Base architecture -- all cpus. */ +++#define AXP_OPCODE_SW6 0x0800 /* SW6 insns. */ +++#define AXP_OPCODE_SW6A 0x1000 /* SW6A insns. */ +++#define AXP_OPCODE_SW6B 0x2000 /* SW6B insns. */ +++ +++#define AXP_LITOP(i) (((i) >> 26) & 0x3D) +++ +++#define AXP_OPCODE_NOPAL (~(AXP_OPCODE_SW6|AXP_OPCODE_SW6A|AXP_OPCODE_SW6B)) +++ +++/* A macro to extract the major opcode from an instruction. */ +++#define AXP_OP(i) (((i) >> 26) & 0x3F) +++ +++/* The total number of major opcodes. */ +++#define AXP_NOPS 0x40 +++ +++ +++/* The operands table is an array of struct sw_64_operand. */ +++ +++struct sw_64_operand +++{ +++ /* The number of bits in the operand. */ +++ unsigned int bits : 5; +++ +++ /* How far the operand is left shifted in the instruction. */ +++ unsigned int shift : 5; +++ +++ /* The default relocation type for this operand. */ +++ signed int default_reloc : 16; +++ +++ /* One bit syntax flags. */ +++ unsigned int flags : 16; +++ +++ /* Insertion function. This is used by the assembler. To insert an +++ operand value into an instruction, check this field. +++ +++ If it is NULL, execute +++ i |= (op & ((1 << o->bits) - 1)) << o->shift; +++ (i is the instruction which we are filling in, o is a pointer to +++ this structure, and op is the opcode value; this assumes twos +++ complement arithmetic). +++ +++ If this field is not NULL, then simply call it with the +++ instruction and the operand value. It will return the new value +++ of the instruction. If the ERRMSG argument is not NULL, then if +++ the operand value is illegal, *ERRMSG will be set to a warning +++ string (the operand will be inserted in any case). If the +++ operand value is legal, *ERRMSG will be unchanged (most operands +++ can accept any value). */ +++ unsigned (*insert) (unsigned instruction, int op, const char **errmsg); +++ +++ /* Extraction function. This is used by the disassembler. To +++ extract this operand type from an instruction, check this field. +++ +++ If it is NULL, compute +++ op = ((i) >> o->shift) & ((1 << o->bits) - 1); +++ if ((o->flags & AXP_OPERAND_SIGNED) != 0 +++ && (op & (1 << (o->bits - 1))) != 0) +++ op -= 1 << o->bits; +++ (i is the instruction, o is a pointer to this structure, and op +++ is the result; this assumes twos complement arithmetic). +++ +++ If this field is not NULL, then simply call it with the +++ instruction value. It will return the value of the operand. If +++ the INVALID argument is not NULL, *INVALID will be set to +++ non-zero if this operand type can not actually be extracted from +++ this operand (i.e., the instruction does not match). If the +++ operand is valid, *INVALID will not be changed. */ +++ int (*extract) (unsigned instruction, int *invalid); +++}; +++ +++/* Elements in the table are retrieved by indexing with values from +++ the operands field of the sw_64_opcodes table. */ +++ +++extern const struct sw_64_operand sw_64_operands[]; +++extern const unsigned sw_64_num_operands; +++ +++/* Values defined for the flags field of a struct sw_64_operand. */ +++ +++/* Mask for selecting the type for typecheck purposes */ +++#define AXP_OPERAND_TYPECHECK_MASK \ +++ (AXP_OPERAND_PARENS | AXP_OPERAND_COMMA | AXP_OPERAND_IR | \ +++ AXP_OPERAND_FPR | AXP_OPERAND_RELATIVE | AXP_OPERAND_SIGNED | \ +++ AXP_OPERAND_UNSIGNED) +++ +++/* This operand does not actually exist in the assembler input. This +++ is used to support extended mnemonics, for which two operands fields +++ are identical. The assembler should call the insert function with +++ any op value. The disassembler should call the extract function, +++ ignore the return value, and check the value placed in the invalid +++ argument. */ +++#define AXP_OPERAND_FAKE 01 +++ +++/* The operand should be wrapped in parentheses rather than separated +++ from the previous by a comma. This is used for the load and store +++ instructions which want their operands to look like "Ra,disp(Rb)". */ +++#define AXP_OPERAND_PARENS 02 +++ +++/* Used in combination with PARENS, this supresses the supression of +++ the comma. This is used for "jmp Ra,(Rb),hint". */ +++#define AXP_OPERAND_COMMA 04 +++ +++/* This operand names an integer register. */ +++#define AXP_OPERAND_IR 010 +++ +++/* This operand names a floating point register. */ +++#define AXP_OPERAND_FPR 020 +++ +++/* This operand is a relative branch displacement. The disassembler +++ prints these symbolically if possible. */ +++#define AXP_OPERAND_RELATIVE 040 +++ +++/* This operand takes signed values. */ +++#define AXP_OPERAND_SIGNED 0100 +++ +++/* This operand takes unsigned values. This exists primarily so that +++ a flags value of 0 can be treated as end-of-arguments. */ +++#define AXP_OPERAND_UNSIGNED 0200 +++ +++/* Supress overflow detection on this field. This is used for hints. */ +++#define AXP_OPERAND_NOOVERFLOW 0400 +++ +++/* Mask for optional argument default value. */ +++#define AXP_OPERAND_OPTIONAL_MASK 07000 + + +-+ case TYPE_CODE_UNION: +-+ op = EOP_UNION; +-+ goto label; +++/* This operand defaults to zero. This is used for jump hints. */ +++#define AXP_OPERAND_DEFAULT_ZERO 01000 + + +-+ case TYPE_CODE_ENUM: +-+ op = EOP_ENUM; +-+ goto label; +++/* This operand should default to the first (real) operand and is used +++ in conjunction with AXP_OPERAND_OPTIONAL. This allows +++ "and $0,3,$0" to be written as "and $0,3", etc. I don't like +++ it, but it's what DEC does. */ +++#define AXP_OPERAND_DEFAULT_FIRST 02000 + + +-+ case TYPE_CODE_STRUCT: +-+ op = EOP_STRUCT; +-+ goto label; +++/* Similarly, this operand should default to the second (real) operand. +++ This allows "negl $0" instead of "negl $0,$0". */ +++#define AXP_OPERAND_DEFAULT_SECOND 04000 + + +-+ default: +-+ typecode = TYPE_CODE(type); +-+ req->tcb(EOP_OOPS, req, &typecode, "Unknown typecode", 0, 0); +-+ return; /* not reached */ +++#ifndef XWB20200308 +++/* Similarly, this operand should default to the third (real) operand. +++ This allows "selne $0,$1,$2,$2" to be written as "selne $0,$1,$2" */ +++#define AXP_OPERAND_DEFAULT_THIRD 0xa00 + + +-+ label: +-+ l1 = TYPE_LENGTH(type); +-+ req->tcb(op, req, &l1, type, TYPE_TAG_NAME(type), 0); +-+ } +-+ type = TYPE_TARGET_TYPE(type); +-+ } +-+ req->tcb(EOP_DONE, req, 0, 0, 0, 0); +-+} +++/* This operand names a vect register. */ +++#define AXP_OPERAND_VPR 0100000 + + +-+/* +- * General purpose routine for determining datatypes. +- */ +++#endif +++ +++ +++/* Register common names */ +++ +++#define AXP_REG_V0 0 +++#define AXP_REG_T0 1 +++#define AXP_REG_T1 2 +++#define AXP_REG_T2 3 +++#define AXP_REG_T3 4 +++#define AXP_REG_T4 5 +++#define AXP_REG_T5 6 +++#define AXP_REG_T6 7 +++#define AXP_REG_T7 8 +++#define AXP_REG_S0 9 +++#define AXP_REG_S1 10 +++#define AXP_REG_S2 11 +++#define AXP_REG_S3 12 +++#define AXP_REG_S4 13 +++#define AXP_REG_S5 14 +++#define AXP_REG_FP 15 +++#define AXP_REG_A0 16 +++#define AXP_REG_A1 17 +++#define AXP_REG_A2 18 +++#define AXP_REG_A3 19 +++#define AXP_REG_A4 20 +++#define AXP_REG_A5 21 +++#define AXP_REG_T8 22 +++#define AXP_REG_T9 23 +++#define AXP_REG_T10 24 +++#define AXP_REG_T11 25 +++#define AXP_REG_RA 26 +++#define AXP_REG_PV 27 +++#define AXP_REG_T12 27 +++#define AXP_REG_AT 28 +++#define AXP_REG_GP 29 +++#define AXP_REG_SP 30 +++#define AXP_REG_ZERO 31 +++ +++#endif /* OPCODE_SW_64_H */ ++diff -Nuar gdb-10.2/intl/configure gdb-10.2/intl/configure ++--- gdb-10.2/intl/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/intl/configure 2025-04-16 17:06:52.002086800 +0800 ++@@ -4721,7 +4721,7 @@ + +-@@ -7149,10 +7222,8 @@ +- if (req->member) +- get_member_data(req, sym->type, 0, 1); ++ # Guess based on the CPU. ++ case "$host_cpu" in ++- alpha* | i3456786 | m68k | s390*) +++ alpha* | sw_64* | i3456786 | m68k | s390*) ++ gt_cv_int_divbyzero_sigfpe="guessing yes";; ++ *) ++ gt_cv_int_divbyzero_sigfpe="guessing no";; ++diff -Nuar gdb-10.2/intl/dcigettext.c gdb-10.2/intl/dcigettext.c ++--- gdb-10.2/intl/dcigettext.c 2020-09-13 10:33:41.000000000 +0800 +++++ gdb-10.2/intl/dcigettext.c 2025-04-16 17:06:52.002086800 +0800 ++@@ -72,7 +72,7 @@ ++ #ifdef _LIBC ++ /* Guess whether integer division by zero raises signal SIGFPE. ++ Set to 1 only if you know for sure. In case of doubt, set to 0. */ ++-# if defined __alpha__ || defined __arm__ || defined __i386__ \ +++# if defined __alpha__ || defined __sw_64__ || defined __arm__ || defined __i386__ \ ++ || defined __m68k__ || defined __s390__ ++ # define INTDIV0_RAISES_SIGFPE 1 ++ # else ++diff -Nuar gdb-10.2/libiberty/aclocal.m4 gdb-10.2/libiberty/aclocal.m4 ++--- gdb-10.2/libiberty/aclocal.m4 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/libiberty/aclocal.m4 2025-04-16 17:06:41.932086800 +0800 ++@@ -16,6 +16,8 @@ ++ [AC_TRY_RUN([ ++ /* Test by Jim Wilson and Kaveh Ghazi. ++ Check whether strncmp reads past the end of its string parameters. */ +++#include +++#include ++ #include + +-- if (TYPE_CODE(sym->type) == TYPE_CODE_ENUM) { +-- if (req->flags & GNU_PRINT_ENUMERATORS) +-- dump_enum(sym->type, req); +-- } +-+ if (TYPE_CODE(sym->type) == TYPE_CODE_ENUM) +-+ walk_enum(sym->type, req); ++ #ifdef HAVE_FCNTL_H ++@@ -43,7 +45,8 @@ + +- return; +- } +-@@ -7172,17 +7243,25 @@ +- if (gdb_CRASHDEBUG(2)) +- console("expr->elts[0].opcode: OP_VAR_VALUE\n"); +- type = expr.get()->elts[2].symbol->type; +-- if (req->flags & GNU_VAR_LENGTH_TYPECODE) { +-+ if (req->tcb) { +-+ long value = SYMBOL_VALUE(expr->elts[2].symbol); +-+ /* callback with symbol value */ +- req->typecode = TYPE_CODE(type); +-- req->length = TYPE_LENGTH(type); +-- } +-- if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +-- req->typecode = TYPE_CODE(type); +-- req->value = SYMBOL_VALUE(expr.get()->elts[2].symbol); +-- req->tagname = (char *)TYPE_TAG_NAME(type); +-- if (!req->tagname) { +-- val = evaluate_type(expr.get()); +-- eval_enum(value_type(val), req); +-+ req->tcb(EOP_VALUE, req, &value, 0, 0, 0); +-+ drillDownType(req, type); +-+ } else { +-+ if (req->flags & GNU_VAR_LENGTH_TYPECODE) { +-+ req->typecode = TYPE_CODE(type); +-+ req->length = TYPE_LENGTH(type); +-+ } +-+ if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +-+ req->typecode = TYPE_CODE(type); +-+ req->value = SYMBOL_VALUE(expr->elts[2].symbol); +-+ req->tagname = (char *)TYPE_TAG_NAME(type); +-+ if (!req->tagname) { +-+ val = evaluate_type(expr.get()); +-+ eval_enum(value_type(val), req); +-+ } +- } +- } +- break; +-@@ -7192,26 +7271,21 @@ +- console("expr->elts[0].opcode: OP_TYPE\n"); +- type = expr.get()->elts[1].type; +- +-- req->typecode = TYPE_CODE(type); +-- req->length = TYPE_LENGTH(type); +-- +-- if (TYPE_CODE(type) == TYPE_CODE_TYPEDEF) { +-- req->is_typedef = TYPE_CODE_TYPEDEF; +-- if ((typedef_type = check_typedef(type))) { +-- req->typecode = TYPE_CODE(typedef_type); +-- req->length = TYPE_LENGTH(typedef_type); +-- type = typedef_type; +-- } +-- } +-- +-- if (TYPE_CODE(type) == TYPE_CODE_ENUM) { +-- if (req->is_typedef) +-- if (req->flags & GNU_PRINT_ENUMERATORS) { +-- if (req->is_typedef) +-- fprintf_filtered(gdb_stdout, +-- "typedef "); +-- dump_enum(type, req); +-+ if (req->tcb) { +-+ drillDownType(req, type); +-+ } else { +-+ req->typecode = TYPE_CODE(type); +-+ req->length = TYPE_LENGTH(type); +-+ if (TYPE_CODE(type) == TYPE_CODE_TYPEDEF) { +-+ req->is_typedef = TYPE_CODE_TYPEDEF; +-+ if ((typedef_type = check_typedef(type))) { +-+ req->typecode = TYPE_CODE(typedef_type); +-+ req->length = TYPE_LENGTH(typedef_type); +-+ type = typedef_type; +-+ } +- } +-+ if (TYPE_CODE(type) == TYPE_CODE_ENUM) +-+ walk_enum(type, req); +- } ++ #define MAP_LEN 0x10000 + +- if (req->member) +-@@ -7233,36 +7307,38 @@ +- * identifier, each on its own line. +- */ +- static void +--dump_enum(struct type *type, struct gnu_request *req) +-+walk_enum(struct type *type, struct gnu_request *req) ++-main () +++int +++main (void) + { +- int i; +-- int len; +-+ int len, print = (req->flags & GNU_PRINT_ENUMERATORS); +- long long lastval; +- +-- len = TYPE_NFIELDS (type); +-- lastval = 0; +-- if (TYPE_TAG_NAME(type)) +-- fprintf_filtered(gdb_stdout, +-- "enum %s {\n", TYPE_TAG_NAME (type)); +-- else +-- fprintf_filtered(gdb_stdout, "enum {\n"); +-+ if (print) { +-+ if (req->is_typedef) +-+ fprintf_filtered(gdb_stdout, "typedef "); +-+ if (TYPE_TAG_NAME(type)) +-+ fprintf_filtered(gdb_stdout, "enum %s {\n", TYPE_TAG_NAME (type)); +-+ else +-+ fprintf_filtered(gdb_stdout, "enum {\n"); +-+ } ++ #if defined(HAVE_MMAP) || defined(HAVE_MMAP_ANYWHERE) ++ char *p; ++@@ -149,7 +152,10 @@ ++ fi + +-+ len = TYPE_NFIELDS (type); +- for (i = 0; i < len; i++) { +-- fprintf_filtered(gdb_stdout, " %s", +-- TYPE_FIELD_NAME (type, i)); +-- if (lastval != TYPE_FIELD_ENUMVAL (type, i)) { +-- fprintf_filtered (gdb_stdout, " = %s", +-- plongest(TYPE_FIELD_ENUMVAL (type, i))); +-- lastval = TYPE_FIELD_ENUMVAL (type, i); +-- } else +-+ if (print) +-+ fprintf_filtered(gdb_stdout, " %s", TYPE_FIELD_NAME (type, i)); +-+ lastval = TYPE_FIELD_ENUMVAL (type, i); +-+ if (print) { +- fprintf_filtered(gdb_stdout, " = %s", plongest(lastval)); +-- fprintf_filtered(gdb_stdout, "\n"); +-- lastval++; +-+ fprintf_filtered(gdb_stdout, "\n"); +-+ } else if (req->tcb) +-+ req->tcb(EOP_ENUMVAL, req, TYPE_FIELD_NAME (type, i), &lastval, 0, 0); +-+ } +-+ if (print) { +-+ if (TYPE_TAG_NAME(type)) +-+ fprintf_filtered(gdb_stdout, "};\n"); +-+ else +-+ fprintf_filtered(gdb_stdout, "} %s;\n", req->name); +- } +-- if (TYPE_TAG_NAME(type)) +-- fprintf_filtered(gdb_stdout, "};\n"); +-- else +-- fprintf_filtered(gdb_stdout, "} %s;\n", req->name); ++ AC_CACHE_CHECK(stack direction for C alloca, ac_cv_c_stack_direction, ++-[AC_TRY_RUN([find_stack_direction () +++[AC_TRY_RUN([#include +++ +++int +++find_stack_direction (void) ++ { ++ static char *addr = 0; ++ auto char dummy; ++@@ -161,7 +167,9 @@ ++ else ++ return (&dummy > addr) ? 1 : -1; + } +- +- /* +-@@ -7320,26 +7396,43 @@ +- } +- +- for (i = 0; i < nfields; i++) { +-- if (STREQ(req->member, nextfield->name)) { +-- req->member_offset = offset + nextfield->loc.bitpos; +-- req->member_length = TYPE_LENGTH(nextfield->type()); +-- req->member_typecode = TYPE_CODE(nextfield->type()); +-- req->member_main_type_name = (char *)TYPE_NAME(nextfield->type()); +-- req->member_main_type_tag_name = (char *)TYPE_TAG_NAME(nextfield->type()); +-- target_type = TYPE_TARGET_TYPE(nextfield->type()); +-- if (target_type) { +-- req->member_target_type_name = (char *)TYPE_NAME(target_type); +-- req->member_target_type_tag_name = (char *)TYPE_TAG_NAME(target_type); +-- } +-- if ((req->member_typecode == TYPE_CODE_TYPEDEF) && +-- (typedef_type = check_typedef(nextfield->type()))) +-- req->member_length = TYPE_LENGTH(typedef_type); +-- return; +-- } else if (*nextfield->name == 0) { /* Anonymous struct/union */ +-+ if (*nextfield->name == 0) { /* Anonymous struct/union */ +- get_member_data(req, nextfield->type(), +- offset + nextfield->loc.bitpos, 0); +- if (req->member_offset != -1) +- return; +-+ } else { +-+ /* callback may be just looking for a specific member name */ +-+ if (req->tcb) { +-+ if (req->tcb(EOP_MEMBER_NAME, req, nextfield->name, 0, 0, 0)) { +-+ long bitpos = FIELD_BITPOS(*nextfield); +-+ long bitsize = FIELD_BITSIZE(*nextfield); +-+ long len = TYPE_LENGTH(nextfield->type()); +-+ long byteOffset; +-+ offset += nextfield->loc.bitpos; +-+ byteOffset = offset/8; +-+ console("EOP_MEMBER_SIZES\n"); +-+ req->tcb(EOP_MEMBER_SIZES, req, &byteOffset, &len, &bitpos, &bitsize); +-+ /* callback with full type info */ +-+ drillDownType(req, nextfield->type()); +-+ } +-+ } else if (STREQ(req->member, nextfield->name)) { +-+ req->member_offset = offset + nextfield->loc.bitpos; +-+ req->member_length = TYPE_LENGTH(nextfield->type()); +-+ req->member_typecode = TYPE_CODE(nextfield->type()); +-+ req->member_main_type_name = (char *)TYPE_NAME(nextfield->type()); +-+ req->member_main_type_tag_name = (char *)TYPE_TAG_NAME(nextfield->type()); +-+ target_type = TYPE_TARGET_TYPE(nextfield->type()); +-+ if (target_type) { +-+ req->member_target_type_name = (char *)TYPE_NAME(target_type); +-+ req->member_target_type_tag_name = (char *)TYPE_TAG_NAME(target_type); +-+ } +-+ if ((req->member_typecode == TYPE_CODE_TYPEDEF) && +-+ (typedef_type = check_typedef(nextfield->type()))) { +-+ req->member_length = TYPE_LENGTH(typedef_type); +-+ } +-+ return; +-+ } +- } +- nextfield++; +- } +---- gdb-10.2/gdb/gdbtypes.c.orig +-+++ gdb-10.2/gdb/gdbtypes.c +-@@ -5492,27 +5492,25 @@ copy_type_recursive (struct objfile *objfile, ++-main () +++ +++int +++main (void) ++ { ++ exit (find_stack_direction() < 0); ++ }], ++diff -Nuar gdb-10.2/libiberty/configure gdb-10.2/libiberty/configure ++--- gdb-10.2/libiberty/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/libiberty/configure 2025-04-16 17:06:41.942086800 +0800 ++@@ -6724,7 +6724,10 @@ ++ else ++ cat confdefs.h - <<_ACEOF >conftest.$ac_ext ++ /* end confdefs.h. */ ++-find_stack_direction () +++#include +++ +++int +++find_stack_direction (void) ++ { ++ static char *addr = 0; ++ auto char dummy; ++@@ -6736,7 +6739,9 @@ ++ else ++ return (&dummy > addr) ? 1 : -1; + } +- +- /* Make a copy of the given TYPE, except that the pointer & reference +-- types are not preserved. +-- +-- This function assumes that the given type has an associated objfile. +-- This objfile is used to allocate the new type. */ +-+ types are not preserved. */ +- +- struct type * +- copy_type (const struct type *type) ++-main () +++ +++int +++main (void) + { +-- struct type *new_type; +-- +-- gdb_assert (TYPE_OBJFILE_OWNED (type)); +-+ struct type *new_type = alloc_type_copy (type); +- +-- new_type = alloc_type_copy (type); +- TYPE_INSTANCE_FLAGS (new_type) = TYPE_INSTANCE_FLAGS (type); +- TYPE_LENGTH (new_type) = TYPE_LENGTH (type); +- memcpy (TYPE_MAIN_TYPE (new_type), TYPE_MAIN_TYPE (type), +- sizeof (struct main_type)); +- if (type->main_type->dyn_prop_list != NULL) +-- new_type->main_type->dyn_prop_list +-- = copy_dynamic_prop_list (&TYPE_OBJFILE (type) -> objfile_obstack, +-- type->main_type->dyn_prop_list); +-+ { +-+ struct obstack *storage = (TYPE_OBJFILE_OWNED (type) +-+ ? &TYPE_OBJFILE (type)->objfile_obstack +-+ : gdbarch_obstack (TYPE_OWNER (type).gdbarch)); +-+ new_type->main_type->dyn_prop_list +-+ = copy_dynamic_prop_list (storage, type->main_type->dyn_prop_list); +-+ } +- +- return new_type; ++ exit (find_stack_direction() < 0); + } +---- gdb-10.2/bfd/elf-bfd.h.orig +-+++ gdb-10.2/bfd/elf-bfd.h +-@@ -27,6 +27,8 @@ +- #include "elf/internal.h" +- #include "bfdlink.h" ++@@ -7557,6 +7562,8 @@ + ++ /* Test by Jim Wilson and Kaveh Ghazi. ++ Check whether strncmp reads past the end of its string parameters. */ +++#include + +#include +-+ +- #ifdef __cplusplus +- extern "C" { +- #endif +---- gdb-10.2/gnulib/import/cdefs.h.orig +-+++ gdb-10.2/gnulib/import/cdefs.h +-@@ -1,17 +1,18 @@ +--/* Copyright (C) 1992-2020 Free Software Foundation, Inc. +-+/* Copyright (C) 1992-2023 Free Software Foundation, Inc. +-+ Copyright The GNU Toolchain Authors. +- This file is part of the GNU C Library. ++ #include + +- The GNU C Library is free software; you can redistribute it and/or +-- modify it under the terms of the GNU General Public +-+ modify it under the terms of the GNU Lesser General Public +- License as published by the Free Software Foundation; either +-- version 3 of the License, or (at your option) any later version. +-+ version 2.1 of the License, or (at your option) any later version. ++ #ifdef HAVE_FCNTL_H ++@@ -7584,7 +7591,8 @@ + +- The GNU C Library 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. +-+ Lesser General Public License for more details. ++ #define MAP_LEN 0x10000 + +-- You should have received a copy of the GNU General Public +-+ You should have received a copy of the GNU Lesser General Public +- License along with the GNU C Library; if not, see +- . */ ++-main () +++int +++main (void) ++ { ++ #if defined(HAVE_MMAP) || defined(HAVE_MMAP_ANYWHERE) ++ char *p; ++diff -Nuar gdb-10.2/libiberty/Makefile.in gdb-10.2/libiberty/Makefile.in ++--- gdb-10.2/libiberty/Makefile.in 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/libiberty/Makefile.in 2025-04-16 17:06:41.912086800 +0800 ++@@ -180,6 +180,7 @@ ++ ./getruntime.$(objext) ./hashtab.$(objext) ./hex.$(objext) \ ++ ./lbasename.$(objext) ./lrealpath.$(objext) \ ++ ./make-relative-prefix.$(objext) ./make-temp-file.$(objext) \ +++ ./mkstemps.$(objext) \ ++ ./objalloc.$(objext) \ ++ ./obstack.$(objext) \ ++ ./partition.$(objext) ./pexecute.$(objext) ./physmem.$(objext) \ ++@@ -213,7 +214,7 @@ ++ ./index.$(objext) ./insque.$(objext) \ ++ ./memchr.$(objext) ./memcmp.$(objext) ./memcpy.$(objext) \ ++ ./memmem.$(objext) ./memmove.$(objext) \ ++- ./mempcpy.$(objext) ./memset.$(objext) ./mkstemps.$(objext) \ +++ ./mempcpy.$(objext) ./memset.$(objext) \ ++ ./pex-djgpp.$(objext) ./pex-msdos.$(objext) \ ++ ./pex-unix.$(objext) ./pex-win32.$(objext) \ ++ ./putenv.$(objext) \ ++diff -Nuar gdb-10.2/libiberty/pex-common.h gdb-10.2/libiberty/pex-common.h ++--- gdb-10.2/libiberty/pex-common.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/libiberty/pex-common.h 2025-04-16 17:06:52.002086800 +0800 ++@@ -99,10 +99,10 @@ ++ { ++ /* Open file NAME for reading. If BINARY is non-zero, open in ++ binary mode. Return >= 0 on success, -1 on error. */ ++- int (*open_read) (struct pex_obj *, const char */* name */, int /* binary */); +++ int (*open_read) (struct pex_obj *, const char * /* name */, int /* binary */); ++ /* Open file NAME for writing. If BINARY is non-zero, open in ++ binary mode. Return >= 0 on success, -1 on error. */ ++- int (*open_write) (struct pex_obj *, const char */* name */, +++ int (*open_write) (struct pex_obj *, const char * /* name */, ++ int /* binary */, int /* append */); ++ /* Execute a child process. FLAGS, EXECUTABLE, ARGV, ERR are from ++ pex_run. IN, OUT, ERRDES, TOCLOSE are all descriptors, from ++@@ -114,11 +114,11 @@ ++ PEX_STDERR_TO_STDOUT flag. Return >= 0 on success, or -1 on ++ error and set *ERRMSG and *ERR. */ ++ pid_t (*exec_child) (struct pex_obj *, int /* flags */, ++- const char */* executable */, char * const * /* argv */, +++ const char * /* executable */, char * const * /* argv */, ++ char * const * /* env */, ++ int /* in */, int /* out */, int /* errdes */, ++- int /* toclose */, const char **/* errmsg */, ++- int */* err */); +++ int /* toclose */, const char ** /* errmsg */, +++ int * /* err */); ++ /* Close a descriptor. Return 0 on success, -1 on error. */ ++ int (*close) (struct pex_obj *, int); ++ /* Wait for a child to complete, returning exit status in *STATUS ++diff -Nuar gdb-10.2/Makefile.in gdb-10.2/Makefile.in ++--- gdb-10.2/Makefile.in 2021-04-25 12:07:50.000000000 +0800 +++++ gdb-10.2/Makefile.in 2025-04-16 17:06:41.892086800 +0800 ++@@ -340,6 +340,9 @@ ++ AS_FOR_BUILD = @AS_FOR_BUILD@ ++ CC_FOR_BUILD = @CC_FOR_BUILD@ ++ CFLAGS_FOR_BUILD = @CFLAGS_FOR_BUILD@ +++ifeq (${CRASH_TARGET}, PPC64) +++CFLAGS_FOR_BUILD += -m64 -fPIC +++endif ++ CXXFLAGS_FOR_BUILD = @CXXFLAGS_FOR_BUILD@ ++ CXX_FOR_BUILD = @CXX_FOR_BUILD@ ++ DLLTOOL_FOR_BUILD = @DLLTOOL_FOR_BUILD@ ++@@ -406,6 +409,9 @@ ++ GNATMAKE = @GNATMAKE@ + +-@@ -25,16 +26,38 @@ ++ CFLAGS = @CFLAGS@ +++ifeq (${CRASH_TARGET}, PPC64) +++CFLAGS += -m64 -fPIC +++endif ++ LDFLAGS = @LDFLAGS@ ++ LIBCFLAGS = $(CFLAGS) ++ CXXFLAGS = @CXXFLAGS@ ++diff -Nuar gdb-10.2/opcodes/configure gdb-10.2/opcodes/configure ++--- gdb-10.2/opcodes/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/configure 2025-04-16 17:06:52.012086800 +0800 ++@@ -12866,6 +12866,7 @@ ++ case "$arch" in ++ bfd_aarch64_arch) ta="$ta aarch64-asm.lo aarch64-dis.lo aarch64-opc.lo aarch64-asm-2.lo aarch64-dis-2.lo aarch64-opc-2.lo" ;; ++ bfd_alpha_arch) ta="$ta alpha-dis.lo alpha-opc.lo" ;; +++ bfd_sw_64_arch) ta="$ta sw_64-dis.lo sw_64-opc.lo" ;; ++ bfd_arc_arch) ta="$ta arc-dis.lo arc-opc.lo arc-ext.lo" ;; ++ bfd_arm_arch) ta="$ta arm-dis.lo" ;; ++ bfd_avr_arch) ta="$ta avr-dis.lo" ;; ++diff -Nuar gdb-10.2/opcodes/configure.ac gdb-10.2/opcodes/configure.ac ++--- gdb-10.2/opcodes/configure.ac 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/configure.ac 2025-04-16 17:06:52.012086800 +0800 ++@@ -341,6 +341,7 @@ ++ bfd_z8k_arch) ta="$ta z8k-dis.lo" ;; ++ bfd_bpf_arch) ta="$ta bpf-asm.lo bpf-desc.lo bpf-dis.lo bpf-ibld.lo bpf-opc.lo" using_cgen=yes ;; + +- /* The GNU libc does not support any K&R compilers or the traditional mode +- of ISO C compilers anymore. Check for some of the combinations not +-- anymore supported. */ +--#if defined __GNUC__ && !defined __STDC__ +--# error "You need a ISO C conforming compiler to use the glibc headers" +-+ supported anymore. */ +-+#if defined __GNUC__ && !defined __STDC__ && !defined __cplusplus +-+# error "You need a ISO C or C++ conforming compiler to use the glibc headers" +++ bfd_sw_64_arch) ta="$ta sw_64-dis.lo sw_64-opc.lo" ;; ++ "") ;; ++ *) AC_MSG_ERROR(*** unknown target architecture $arch) ;; ++ esac ++diff -Nuar gdb-10.2/opcodes/configure.com gdb-10.2/opcodes/configure.com ++--- gdb-10.2/opcodes/configure.com 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/configure.com 2025-04-16 17:06:52.012086800 +0800 ++@@ -44,6 +44,14 @@ ++ $ DEFS="""ARCH_alpha""" ++ $EOD ++ $ endif +++$ if arch.eqs."sw_64" +++$ then +++$ create build.com +++$DECK +++$ FILES="sw_64-dis,sw_64-opc" +++$ DEFS="""ARCH_sw_64""" +++$EOD +++$ endif ++ $! ++ $ append sys$input build.com ++ $DECK ++diff -Nuar gdb-10.2/opcodes/disassemble.c gdb-10.2/opcodes/disassemble.c ++--- gdb-10.2/opcodes/disassemble.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/disassemble.c 2025-04-16 17:06:52.012086800 +0800 ++@@ -100,6 +100,7 @@ ++ #define ARCH_xtensa ++ #define ARCH_z80 ++ #define ARCH_z8k +++#define ARCH_sw_64 + #endif + +- /* Some user header file might have defined this before. */ +- #undef __P +- #undef __PMT ++ #ifdef ARCH_m32c ++@@ -135,6 +136,11 @@ ++ { ++ /* If you add a case to this table, also add it to the ++ ARCH_all definition right above this function. */ +++#ifdef ARCH_sw_64 +++ case bfd_arch_sw_64: +++ disassemble = print_insn_sw_64; +++ break; +++#endif ++ #ifdef ARCH_aarch64 ++ case bfd_arch_aarch64: ++ disassemble = print_insn_aarch64; ++diff -Nuar gdb-10.2/opcodes/disassemble.h gdb-10.2/opcodes/disassemble.h ++--- gdb-10.2/opcodes/disassemble.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/disassemble.h 2025-04-16 17:06:52.012086800 +0800 ++@@ -100,6 +100,7 @@ ++ extern int print_insn_z80 (bfd_vma, disassemble_info *); ++ extern int print_insn_z8001 (bfd_vma, disassemble_info *); ++ extern int print_insn_z8002 (bfd_vma, disassemble_info *); +++extern int print_insn_sw_64 (bfd_vma, disassemble_info *); + +--#ifdef __GNUC__ +-+/* Compilers that lack __has_attribute may object to +-+ #if defined __has_attribute && __has_attribute (...) +-+ even though they do not need to evaluate the right-hand side of the &&. +-+ Similarly for __has_builtin, etc. */ +-+#if (defined __has_attribute \ +-+ && (!defined __clang_minor__ \ +-+ || 3 < __clang_major__ + (5 <= __clang_minor__))) +-+# define __glibc_has_attribute(attr) __has_attribute (attr) ++ extern disassembler_ftype csky_get_disassembler (bfd *); ++ extern disassembler_ftype rl78_get_disassembler (bfd *); ++diff -Nuar gdb-10.2/opcodes/i386-dis.c gdb-10.2/opcodes/i386-dis.c ++--- gdb-10.2/opcodes/i386-dis.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/i386-dis.c 2025-04-16 17:06:41.912086800 +0800 ++@@ -9778,6 +9778,10 @@ ++ threebyte = *codep; ++ dp = &dis386_twobyte[threebyte]; ++ need_modrm = twobyte_has_modrm[*codep]; +++ if (dp->name && ((strcmp(dp->name, "ud2a") == 0) || (strcmp(dp->name, "ud2") == 0))) { +++ extern int kernel_BUG_encoding_bytes(void); +++ codep += kernel_BUG_encoding_bytes(); +++ } ++ codep++; ++ } ++ else ++diff -Nuar gdb-10.2/opcodes/Makefile.am gdb-10.2/opcodes/Makefile.am ++--- gdb-10.2/opcodes/Makefile.am 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/Makefile.am 2025-04-16 17:06:52.002086800 +0800 ++@@ -96,6 +96,8 @@ ++ aarch64-opc-2.c \ ++ alpha-dis.c \ ++ alpha-opc.c \ +++ sw_64-dis.c \ +++ sw_64-opc.c \ ++ arc-dis.c \ ++ arc-ext.c \ ++ arc-opc.c \ ++diff -Nuar gdb-10.2/opcodes/Makefile.in gdb-10.2/opcodes/Makefile.in ++--- gdb-10.2/opcodes/Makefile.in 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/opcodes/Makefile.in 2025-04-16 17:06:52.002086800 +0800 ++@@ -486,6 +486,8 @@ ++ aarch64-opc-2.c \ ++ alpha-dis.c \ ++ alpha-opc.c \ +++ sw_64-dis.c \ +++ sw_64-opc.c \ ++ arc-dis.c \ ++ arc-ext.c \ ++ arc-opc.c \ ++@@ -897,6 +899,8 @@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/aarch64-opc.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/alpha-dis.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/alpha-opc.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sw_64-dis.Plo@am__quote@ +++@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sw_64-opc.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/arc-dis.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/arc-ext.Plo@am__quote@ ++ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/arc-opc.Plo@am__quote@ ++diff -Nuar gdb-10.2/opcodes/sw_64-dis.c gdb-10.2/opcodes/sw_64-dis.c ++--- gdb-10.2/opcodes/sw_64-dis.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/opcodes/sw_64-dis.c 2025-04-16 17:06:52.012086800 +0800 ++@@ -0,0 +1,221 @@ +++/* sw_64-dis.c -- Disassemble Sw_64 AXP instructions +++ Copyright (C) 1996-2016 Free Software Foundation, Inc. +++ Contributed by Richard Henderson , +++ patterned after the PPC opcode handling written by Ian Lance Taylor. +++ +++ This file is part of libopcodes. +++ +++ This library 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, or (at your option) +++ any later version. +++ +++ It 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 file; see the file COPYING. If not, write to the Free +++ Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA +++ 02110-1301, USA. */ +++ +++#include "sysdep.h" +++#include +++#include "disassemble.h" +++#include "opcode/sw_64.h" +++ +++/* OSF register names. */ +++ +++static const char * const osf_regnames[96] = { +++#ifndef XWB20181112 +++ "$r0", "$r1", "$r2", "$r3" , "$r4", "$r5", "$r6", "$r7", +++ "$r8", "$r9", "$r10", "$r11" , "$r12", "$r13", "$r14", "fp", +++ "$r16", "$r17", "$r18", "$r19" , "$r20", "$r21", "$r22", "$r23", +++ "$r24", "$r25", "ra", "$r27" , "$r28", "$r29", "sp", "$r31", + +#else +-+# define __glibc_has_attribute(attr) 0 +++ "v0", "t0", "t1", "t2", "t3", "t4", "t5", "t6", +++ "t7", "s0", "s1", "s2", "s3", "s4", "s5", "fp", +++ "a0", "a1", "a2", "a3", "a4", "a5", "t8", "t9", +++ "t10", "t11", "ra", "t12", "at", "gp", "sp", "zero", + +#endif +-+#ifdef __has_builtin +-+# define __glibc_has_builtin(name) __has_builtin (name) +-+#else +-+# define __glibc_has_builtin(name) 0 +++ "$f0", "$f1", "$f2", "$f3", "$f4", "$f5", "$f6", "$f7", +++ "$f8", "$f9", "$f10", "$f11", "$f12", "$f13", "$f14", "$f15", +++ "$f16", "$f17", "$f18", "$f19", "$f20", "$f21", "$f22", "$f23", +++ "$f24", "$f25", "$f26", "$f27", "$f28", "$f29", "$f30", "$f31" +++#ifndef XWB20180523 +++ , +++ "$V0", "$V1", "$V2", "$V3", "$V4", "$V5", "$V6", "$V7", +++ "$V8", "$V9", "$V10", "$V11", "$V12", "$V13", "$V14", "$V15", +++ "$V16", "$V17", "$V18", "$V19", "$V20", "$V21", "$V22", "$V23", +++ "$V24", "$V25", "$V26", "$V27", "$V28", "$V29", "$V30", "$V31" + +#endif +-+#ifdef __has_extension +-+# define __glibc_has_extension(ext) __has_extension (ext) +-+#else +-+# define __glibc_has_extension(ext) 0 +++}; +++ +++/* VMS register names. */ +++ +++static const char * const vms_regnames[64] = { +++ "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", +++ "R8", "R9", "R10", "R11", "R12", "R13", "R14", "R15", +++ "R16", "R17", "R18", "R19", "R20", "R21", "R22", "R23", +++ "R24", "AI", "RA", "PV", "AT", "FP", "SP", "RZ", +++ "F0", "F1", "F2", "F3", "F4", "F5", "F6", "F7", +++ "F8", "F9", "F10", "F11", "F12", "F13", "F14", "F15", +++ "F16", "F17", "F18", "F19", "F20", "F21", "F22", "F23", +++ "F24", "F25", "F26", "F27", "F28", "F29", "F30", "FZ" +++}; +++ +++int +++print_insn_sw_64(bfd_vma memaddr, struct disassemble_info *info) +++{ +++ static const struct sw_64_opcode *opcode_index[AXP_NOPS+1]; +++ const char * const * regnames; +++ const struct sw_64_opcode *opcode, *opcode_end; +++ const unsigned char *opindex; +++ unsigned insn, op, isa_mask; +++ int need_comma; +++ +++ /* Initialize the majorop table the first time through */ +++ if (!opcode_index[0]) +++ { +++ opcode = sw_64_opcodes; +++ opcode_end = opcode + sw_64_num_opcodes; +++ +++ for (op = 0; op < AXP_NOPS; ++op) +++ { +++ opcode_index[op] = opcode; +++ while (opcode < opcode_end && op == AXP_OP (opcode->opcode)) +++ ++opcode; +++ } +++ opcode_index[op] = opcode; +++ } +++ +++ if (info->flavour == bfd_target_evax_flavour) +++ regnames = vms_regnames; +++ else +++ regnames = osf_regnames; +++ isa_mask = AXP_OPCODE_NOPAL; +++ +++ switch (info->mach) +++ { +++ case bfd_mach_sw_64_sw6a: +++ isa_mask |= AXP_OPCODE_SW6; +++ break; +++ } +++ +++ /* Read the insn into a host word */ +++ { +++ bfd_byte buffer[4]; +++ int status = (*info->read_memory_func) (memaddr, buffer, 4, info); +++ if (status != 0) +++ { +++ (*info->memory_error_func) (status, memaddr, info); +++ return -1; +++ } +++ insn = bfd_getl32 (buffer); +++ } +++ /* Get the major opcode of the instruction. */ +++ op = AXP_OP (insn); +++ +++ /* Find the first match in the opcode table. */ +++ opcode_end = opcode_index[op + 1]; +++ for (opcode = opcode_index[op]; opcode < opcode_end; ++opcode) +++ { +++ if ((insn ^ opcode->opcode) & opcode->mask) +++ continue; +++ +++ if (!(opcode->flags & isa_mask)) +++ continue; +++ +++ /* Make two passes over the operands. First see if any of them +++ have extraction functions, and, if they do, make sure the +++ instruction is valid. */ +++ { +++ int invalid = 0; +++ for (opindex = opcode->operands; *opindex != 0; opindex++) +++ { +++ const struct sw_64_operand *operand = sw_64_operands + *opindex; +++ if (operand->extract) +++ (*operand->extract) (insn, &invalid); +++ } +++ if (invalid) +++ continue; +++ } +++ +++ /* The instruction is valid. */ +++ goto found; +++ } +++ +++ /* No instruction found */ +++ (*info->fprintf_func) (info->stream, ".long %#08x", insn); +++ +++ return 4; +++ +++found: +++ (*info->fprintf_func) (info->stream, "%s", opcode->name); +++#ifndef XWB20200308 +++ /* for recomposing intr... */ +++ if (op > 0x13 && op < 0x18 ) +++ (*info->fprintf_func) (info->stream, "%x", (((insn>>26)&0x3))<<6|((insn>>10)&0x3f)); + +#endif +++ if (opcode->operands[0] != 0) +++ (*info->fprintf_func) (info->stream, "\t"); + + +-+#if defined __GNUC__ || defined __clang__ +- +- /* All functions, except those with callbacks or those that +- synchronize memory, are leaf functions. */ +-@@ -47,21 +70,26 @@ +- # endif +- +- /* GCC can always grok prototypes. For C++ programs we add throw() +-- to help it optimize the function calls. But this works only with +-- gcc 2.8.x and egcs. For gcc 3.2 and up we even mark C functions +-+ to help it optimize the function calls. But this only works with +-+ gcc 2.8.x and egcs. For gcc 3.4 and up we even mark C functions +- as non-throwing using a function attribute since programs can use +- the -fexceptions options for C code as well. */ +--# if !defined __cplusplus && __GNUC_PREREQ (3, 3) +-+# if !defined __cplusplus \ +-+ && (__GNUC_PREREQ (3, 4) || __glibc_has_attribute (__nothrow__)) +- # define __THROW __attribute__ ((__nothrow__ __LEAF)) +- # define __THROWNL __attribute__ ((__nothrow__)) +- # define __NTH(fct) __attribute__ ((__nothrow__ __LEAF)) fct +- # define __NTHNL(fct) __attribute__ ((__nothrow__)) fct +- # else +--# if defined __cplusplus && __GNUC_PREREQ (2,8) +--# define __THROW throw () +--# define __THROWNL throw () +--# define __NTH(fct) __LEAF_ATTR fct throw () +--# define __NTHNL(fct) fct throw () +-+# if defined __cplusplus && (__GNUC_PREREQ (2,8) || __clang_major >= 4) +-+# if __cplusplus >= 201103L +-+# define __THROW noexcept (true) +-+# else +-+# define __THROW throw () +-+# endif +-+# define __THROWNL __THROW +-+# define __NTH(fct) __LEAF_ATTR fct __THROW +-+# define __NTHNL(fct) fct __THROW +- # else +- # define __THROW +- # define __THROWNL +-@@ -70,7 +98,7 @@ +- # endif +- # endif +- +--#else /* Not GCC. */ +-+#else /* Not GCC or clang. */ +- +- # if (defined __cplusplus \ +- || (defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L)) +-@@ -83,16 +111,7 @@ +- # define __THROWNL +- # define __NTH(fct) fct +- +--#endif /* GCC. */ +-- +--/* Compilers that are not clang may object to +-- #if defined __clang__ && __has_extension(...) +-- even though they do not need to evaluate the right-hand side of the &&. */ +--#if defined __clang__ && defined __has_extension +--# define __glibc_clang_has_extension(ext) __has_extension (ext) +--#else +--# define __glibc_clang_has_extension(ext) 0 +--#endif +-+#endif /* GCC || clang. */ +- +- /* These two macros are not used in glibc anymore. They are kept here +- only because some other projects expect the macros to be defined. */ +-@@ -123,14 +142,70 @@ +- #define __bos(ptr) __builtin_object_size (ptr, __USE_FORTIFY_LEVEL > 1) +- #define __bos0(ptr) __builtin_object_size (ptr, 0) +- +-+/* Use __builtin_dynamic_object_size at _FORTIFY_SOURCE=3 when available. */ +-+#if __USE_FORTIFY_LEVEL == 3 && (__glibc_clang_prereq (9, 0) \ +-+ || __GNUC_PREREQ (12, 0)) +-+# define __glibc_objsize0(__o) __builtin_dynamic_object_size (__o, 0) +-+# define __glibc_objsize(__o) __builtin_dynamic_object_size (__o, 1) +++ /* Now extract and print the operands. */ +++ need_comma = 0; +++ for (opindex = opcode->operands; *opindex != 0; opindex++) +++ { +++ const struct sw_64_operand *operand = sw_64_operands + *opindex; +++ int value; +++ +++ /* Operands that are marked FAKE are simply ignored. We +++ already made sure that the extract function considered +++ the instruction to be valid. */ +++ if ((operand->flags & AXP_OPERAND_FAKE) != 0) +++ continue; +++ +++ /* Extract the value from the instruction. */ +++ if (operand->extract) +++ value = (*operand->extract) (insn, (int *) NULL); +++ else +++ { +++ value = (insn >> operand->shift) & ((1 << operand->bits) - 1); +++ if (operand->flags & AXP_OPERAND_SIGNED) +++ { +++ int signbit = 1 << (operand->bits - 1); +++ value = (value ^ signbit) - signbit; +++ } +++ } +++ +++ if (need_comma && +++ ((operand->flags & (AXP_OPERAND_PARENS | AXP_OPERAND_COMMA)) +++ != AXP_OPERAND_PARENS)) +++ { +++ (*info->fprintf_func) (info->stream, ","); +++ } +++ if (operand->flags & AXP_OPERAND_PARENS) +++ (*info->fprintf_func) (info->stream, "("); +++ +++ /* Print the operand as directed by the flags. */ +++ if (operand->flags & AXP_OPERAND_IR) +++ (*info->fprintf_func) (info->stream, "%s", regnames[value]); +++ else if (operand->flags & AXP_OPERAND_FPR) +++ (*info->fprintf_func) (info->stream, "%s", regnames[value + 32]); +++#ifndef XWB20200308 +++ else if (operand->flags & AXP_OPERAND_VPR) +++ (*info->fprintf_func) (info->stream, "%s", regnames[value + 64]); +++#endif +++ else if (operand->flags & AXP_OPERAND_RELATIVE) +++ (*info->print_address_func) (memaddr + 4 + value, info); +++ else if (operand->flags & AXP_OPERAND_SIGNED) +++ (*info->fprintf_func) (info->stream, "%d", value); +++ else +++ (*info->fprintf_func) (info->stream, "%#x", value); +++ +++ if (operand->flags & AXP_OPERAND_PARENS) +++ (*info->fprintf_func) (info->stream, ")"); +++ need_comma = 1; +++ } +++ +++ return 4; +++} ++diff -Nuar gdb-10.2/opcodes/sw_64-opc.c gdb-10.2/opcodes/sw_64-opc.c ++--- gdb-10.2/opcodes/sw_64-opc.c 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/opcodes/sw_64-opc.c 2025-04-16 17:06:52.012086800 +0800 ++@@ -0,0 +1,1042 @@ +++/* sw_64-opc.c -- Sw_64 AXP opcode list +++ Copyright (C) 1996-2015 Free Software Foundation, Inc. +++ Contributed by Richard Henderson , +++ patterned after the PPC opcode handling written by Ian Lance Taylor. +++ +++ This file is part of libopcodes. +++ +++ This library 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, or (at your option) +++ any later version. +++ +++ It 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 file; see the file COPYING. If not, write to the +++ Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA +++ 02110-1301, USA. */ +++ +++#include "sysdep.h" +++#include +++#include "opcode/sw_64.h" +++#include "bfd.h" +++#include "opintl.h" +++ +++/* This file holds the Sw_64 AXP opcode table. The opcode table includes +++ almost all of the extended instruction mnemonics. This permits the +++ disassembler to use them, and simplifies the assembler logic, at the +++ cost of increasing the table size. The table is strictly constant +++ data, so the compiler should be able to put it in the text segment. +++ +++ This file also holds the operand table. All knowledge about inserting +++ and extracting operands from instructions is kept in this file. +++ +++ The information for the base instruction set was compiled from the +++ _Sw_64 Architecture Handbook_, Digital Order Number EC-QD2KB-TE, +++ version 2. +++ +++ The information for the post-ev5 architecture extensions BWX, CIX and +++ MAX came from version 3 of this same document, which is also available +++ on-line at http://ftp.digital.com/pub/Digital/info/semiconductor +++ /literature/sw_64hb2.pdf +++ +++ +++/* The RB field when it is the same as the RA field in the same insn. +++ This operand is marked fake. The insertion function just copies +++ the RA field into the RB field, and the extraction function just +++ checks that the fields are the same. */ +++ +++static unsigned +++insert_rba (unsigned insn, +++ int value ATTRIBUTE_UNUSED, +++ const char **errmsg ATTRIBUTE_UNUSED) +++{ +++ return insn | (((insn >> 21) & 0x1f) << 16); +++} +++ +++static int +++extract_rba (unsigned insn, int *invalid) +++{ +++ if (invalid != (int *) NULL +++ && ((insn >> 21) & 0x1f) != ((insn >> 16) & 0x1f)) +++ *invalid = 1; +++ return 0; +++} +++ +++/* The same for the RC field. */ +++ +++static unsigned +++insert_rca (unsigned insn, +++ int value ATTRIBUTE_UNUSED, +++ const char **errmsg ATTRIBUTE_UNUSED) +++{ +++ return insn | ((insn >> 21) & 0x1f); +++} +++ +++static int +++extract_rca (unsigned insn, int *invalid) +++{ +++ if (invalid != (int *) NULL +++ && ((insn >> 21) & 0x1f) != (insn & 0x1f)) +++ *invalid = 1; +++ return 0; +++} +++ +++/* Fake arguments in which the registers must be set to ZERO. */ +++ +++static unsigned +++insert_za (unsigned insn, +++ int value ATTRIBUTE_UNUSED, +++ const char **errmsg ATTRIBUTE_UNUSED) +++{ +++ return insn | (31 << 21); +++} +++ +++static int +++extract_za (unsigned insn, int *invalid) +++{ +++ if (invalid != (int *) NULL && ((insn >> 21) & 0x1f) != 31) +++ *invalid = 1; +++ return 0; +++} +++ +++static unsigned +++insert_zb (unsigned insn, +++ int value ATTRIBUTE_UNUSED, +++ const char **errmsg ATTRIBUTE_UNUSED) +++{ +++ return insn | (31 << 16); +++} +++ +++static int +++extract_zb (unsigned insn, int *invalid) +++{ +++ if (invalid != (int *) NULL && ((insn >> 16) & 0x1f) != 31) +++ *invalid = 1; +++ return 0; +++} +++ +++static unsigned +++insert_zc (unsigned insn, +++ int value ATTRIBUTE_UNUSED, +++ const char **errmsg ATTRIBUTE_UNUSED) +++{ +++ return insn | 31; +++} +++ +++static int +++extract_zc (unsigned insn, int *invalid) +++{ +++ if (invalid != (int *) NULL && (insn & 0x1f) != 31) +++ *invalid = 1; +++ return 0; +++} +++ +++ +++/* The displacement field of a Branch format insn. */ +++ +++static unsigned +++insert_bdisp (unsigned insn, int value, const char **errmsg) +++{ +++ if (errmsg != (const char **)NULL && (value & 3)) +++ *errmsg = _("branch operand unaligned"); +++ return insn | ((value / 4) & 0x1FFFFF); +++} +++ +++static int +++extract_bdisp (unsigned insn, int *invalid ATTRIBUTE_UNUSED) +++{ +++ return 4 * (((insn & 0x1FFFFF) ^ 0x100000) - 0x100000); +++} +++ +++/* The hint field of a JMP/JSR insn. */ +++ +++static unsigned +++insert_jhint (unsigned insn, int value, const char **errmsg) +++{ +++ if (errmsg != (const char **)NULL && (value & 3)) +++ *errmsg = _("jump hint unaligned"); +++ return insn | ((value / 4) & 0x3FFF); +++} +++ +++static int +++extract_jhint (unsigned insn, int *invalid ATTRIBUTE_UNUSED) +++{ +++ return 4 * (((insn & 0x3FFF) ^ 0x2000) - 0x2000); +++} +++ +++/* The hint field of an SW6 HW_JMP/JSR insn. */ +++ +++static unsigned +++insert_sw6hwjhint (unsigned insn, int value, const char **errmsg) +++{ +++ if (errmsg != (const char **)NULL && (value & 3)) +++ *errmsg = _("jump hint unaligned"); +++ return insn | ((value / 4) & 0x1FFF); +++} +++ +++static int +++extract_sw6hwjhint (unsigned insn, int *invalid ATTRIBUTE_UNUSED) +++{ +++ return 4 * (((insn & 0x1FFF) ^ 0x1000) - 0x1000); +++} +++ +++/* The operands table. */ +++ +++const struct sw_64_operand sw_64_operands[] = +++{ +++ /* The fields are bits, shift, insert, extract, flags */ +++ /* The zero index is used to indicate end-of-list */ +++#define UNUSED 0 +++ { 0, 0, 0, 0, 0, 0 }, +++ +++ /* The plain integer register fields. */ +++#define RA (UNUSED + 1) +++ { 5, 21, 0, AXP_OPERAND_IR, 0, 0 }, +++#define RB (RA + 1) +++ { 5, 16, 0, AXP_OPERAND_IR, 0, 0 }, +++#define RC (RB + 1) +++ { 5, 0, 0, AXP_OPERAND_IR, 0, 0 }, +++ +++ /* The plain fp register fields. */ +++#define FA (RC + 1) +++ { 5, 21, 0, AXP_OPERAND_FPR, 0, 0 }, +++#define FB (FA + 1) +++ { 5, 16, 0, AXP_OPERAND_FPR, 0, 0 }, +++#define FC (FB + 1) +++ { 5, 0, 0, AXP_OPERAND_FPR, 0, 0 }, +++ +++ /* The integer registers when they are ZERO. */ +++#define ZA (FC + 1) +++ { 5, 21, 0, AXP_OPERAND_FAKE, insert_za, extract_za }, +++#define ZB (ZA + 1) +++ { 5, 16, 0, AXP_OPERAND_FAKE, insert_zb, extract_zb }, +++#define ZC (ZB + 1) +++ { 5, 0, 0, AXP_OPERAND_FAKE, insert_zc, extract_zc }, +++ +++ /* The RB field when it needs parentheses. */ +++#define PRB (ZC + 1) +++ { 5, 16, 0, AXP_OPERAND_IR|AXP_OPERAND_PARENS, 0, 0 }, +++ +++ /* The RB field when it needs parentheses _and_ a preceding comma. */ +++#define CPRB (PRB + 1) +++ { 5, 16, 0, +++ AXP_OPERAND_IR|AXP_OPERAND_PARENS|AXP_OPERAND_COMMA, 0, 0 }, +++ +++ /* The RB field when it must be the same as the RA field. */ +++#define RBA (CPRB + 1) +++ { 5, 16, 0, AXP_OPERAND_FAKE, insert_rba, extract_rba }, +++ +++ /* The RC field when it must be the same as the RB field. */ +++#define RCA (RBA + 1) +++ { 5, 0, 0, AXP_OPERAND_FAKE, insert_rca, extract_rca }, +++ +++ /* The RC field when it can *default* to RA. */ +++#define DRC1 (RCA + 1) +++ { 5, 0, 0, +++ AXP_OPERAND_IR|AXP_OPERAND_DEFAULT_FIRST, 0, 0 }, +++ +++ /* The RC field when it can *default* to RB. */ +++#define DRC2 (DRC1 + 1) +++ { 5, 0, 0, +++ AXP_OPERAND_IR|AXP_OPERAND_DEFAULT_SECOND, 0, 0 }, +++ +++ /* The FC field when it can *default* to RA. */ +++#define DFC1 (DRC2 + 1) +++ { 5, 0, 0, +++ AXP_OPERAND_FPR|AXP_OPERAND_DEFAULT_FIRST, 0, 0 }, +++ +++ /* The FC field when it can *default* to RB. */ +++#define DFC2 (DFC1 + 1) +++ { 5, 0, 0, +++ AXP_OPERAND_FPR|AXP_OPERAND_DEFAULT_SECOND, 0, 0 }, +++ +++ /* The unsigned 8-bit literal of Operate format insns. */ +++#define LIT (DFC2 + 1) +++ { 8, 13, -LIT, AXP_OPERAND_UNSIGNED, 0, 0 }, +++ +++ /* The signed 16-bit displacement of Memory format insns. From here +++ we can't tell what relocation should be used, so don't use a default. */ +++#define MDISP (LIT + 1) +++ { 16, 0, -MDISP, AXP_OPERAND_SIGNED, 0, 0 }, +++ +++ /* The signed "23-bit" aligned displacement of Branch format insns. */ +++#define BDISP (MDISP + 1) +++ { 21, 0, BFD_RELOC_23_PCREL_S2, +++ AXP_OPERAND_RELATIVE, insert_bdisp, extract_bdisp }, +++ /* The 26-bit PALcode function */ +++#ifdef XWB20180315 +++#define PALFN (BDISP + 1) +++ { 26, 0, -PALFN, AXP_OPERAND_UNSIGNED, 0, 0 }, + +#else +-+# define __glibc_objsize0(__o) __bos0 (__o) +-+# define __glibc_objsize(__o) __bos (__o) +++#define PALFN (BDISP + 1) +++ { 25, 0, -PALFN, AXP_OPERAND_UNSIGNED, 0, 0 }, + +#endif +++ /* The optional signed "16-bit" aligned displacement of the JMP/JSR hint. */ +++#define JMPHINT (PALFN + 1) +++ { 14, 0, BFD_RELOC_SW_64_HINT, +++ AXP_OPERAND_RELATIVE|AXP_OPERAND_DEFAULT_ZERO|AXP_OPERAND_NOOVERFLOW, +++ insert_jhint, extract_jhint }, + + +-+#if __USE_FORTIFY_LEVEL > 0 +-+/* Compile time conditions to choose between the regular, _chk and _chk_warn +-+ variants. These conditions should get evaluated to constant and optimized +-+ away. */ +++ /* The optional hint to RET/JSR_COROUTINE. */ +++#define RETHINT (JMPHINT + 1) +++ { 14, 0, -RETHINT, +++ AXP_OPERAND_UNSIGNED|AXP_OPERAND_DEFAULT_ZERO, 0, 0 }, + + +-+#define __glibc_safe_len_cond(__l, __s, __osz) ((__l) <= (__osz) / (__s)) +-+#define __glibc_unsigned_or_positive(__l) \ +-+ ((__typeof (__l)) 0 < (__typeof (__l)) -1 \ +-+ || (__builtin_constant_p (__l) && (__l) > 0)) +++ /* The 12-bit displacement for the ev[46] hw_{ld,st} (pal1b/pal1f) insns. */ +++#define SW6HWDISP (RETHINT + 1) +++ { 12, 0, -SW6HWDISP, AXP_OPERAND_SIGNED, 0, 0 }, + + +-+/* Length is known to be safe at compile time if the __L * __S <= __OBJSZ +-+ condition can be folded to a constant and if it is true, or unknown (-1) */ +-+#define __glibc_safe_or_unknown_len(__l, __s, __osz) \ +-+ ((__builtin_constant_p (__osz) && (__osz) == (__SIZE_TYPE__) -1) \ +-+ || (__glibc_unsigned_or_positive (__l) \ +-+ && __builtin_constant_p (__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), \ +-+ (__s), (__osz))) \ +-+ && __glibc_safe_len_cond ((__SIZE_TYPE__) (__l), (__s), (__osz)))) +++ /* The 8-bit index for the oddly unqualified hw_m[tf]pr insns +++ that occur in DEC PALcode. */ +++#define EV4EXTHWINDEX (SW6HWDISP + 1) +++ { 8, 0, -EV4EXTHWINDEX, AXP_OPERAND_UNSIGNED, 0, 0 }, + + +-+/* Conversely, we know at compile time that the length is unsafe if the +-+ __L * __S <= __OBJSZ condition can be folded to a constant and if it is +-+ false. */ +-+#define __glibc_unsafe_len(__l, __s, __osz) \ +-+ (__glibc_unsigned_or_positive (__l) \ +-+ && __builtin_constant_p (__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), \ +-+ __s, __osz)) \ +-+ && !__glibc_safe_len_cond ((__SIZE_TYPE__) (__l), __s, __osz)) +++ /* The 16-bit combined index/scoreboard mask for the ev6 +++ hw_m[ft]pr (pal19/pal1d) insns. */ +++#define SW6HWINDEX (EV4EXTHWINDEX + 1) +++ { 16, 0, -SW6HWINDEX, AXP_OPERAND_UNSIGNED, 0, 0 }, + + +-+/* Fortify function f. __f_alias, __f_chk and __f_chk_warn must be +-+ declared. */ +++ /* The 13-bit branch hint for the ev6 hw_jmp/jsr (pal1e) insn. */ +++#define SW6HWJMPHINT (SW6HWINDEX+ 1) +++ { 8, 0, -SW6HWJMPHINT, +++ AXP_OPERAND_RELATIVE|AXP_OPERAND_DEFAULT_ZERO|AXP_OPERAND_NOOVERFLOW, +++ insert_sw6hwjhint, extract_sw6hwjhint } +++#ifndef SPS20160530 +++, +++#define PRIDISP (SW6HWJMPHINT+ 1) +++ { 8, 0, -PRIDISP, AXP_OPERAND_SIGNED, 0, 0 }, + + +-+#define __glibc_fortify(f, __l, __s, __osz, ...) \ +-+ (__glibc_safe_or_unknown_len (__l, __s, __osz) \ +-+ ? __ ## f ## _alias (__VA_ARGS__) \ +-+ : (__glibc_unsafe_len (__l, __s, __osz) \ +-+ ? __ ## f ## _chk_warn (__VA_ARGS__, __osz) \ +-+ : __ ## f ## _chk (__VA_ARGS__, __osz))) +++/* The RC for sw6 interger composite insns */ +++#define SRC (PRIDISP + 1) +++ { 5, 5, 0, AXP_OPERAND_IR, 0, 0 }, + + +-+/* Fortify function f, where object size argument passed to f is the number of +-+ elements and not total size. */ +++/* The RD for sw6 interger composite insns */ +++#define SRD RC +++ +++/* The RC for sw6 interger composite insns */ +++#define SFC (SRC + 1) +++ { 5, 5, 0, AXP_OPERAND_FPR, 0, 0 }, +++ +++/* The RD for sw6 interger composite insns */ +++#define SFD FC +++ +++ /* The plain f31 register fields. */ +++#define ZFA (SFC + 1) +++ { 5, 21, 0, AXP_OPERAND_FPR|AXP_OPERAND_FAKE, insert_za, extract_za }, +++ +++#define ZFB (ZFA + 1) +++ { 5, 16, 0, AXP_OPERAND_FPR|AXP_OPERAND_FAKE, insert_zb, extract_zb }, +++ +++#define ZFC (ZFB + 1) +++ { 5, 0, 0, AXP_OPERAND_FPR|AXP_OPERAND_FAKE, insert_zc, extract_zc }, +++ +++ /* The unsigned 5-bit literal of Operate format insns. */ +++#define CIB (ZFC + 1) +++ { 5, 5, -CIB, AXP_OPERAND_UNSIGNED, 0, 0 }, +++ +++ /* The plain vector register fields. */ +++#define VA (CIB + 1) +++ { 5, 21, 0, AXP_OPERAND_VPR, 0, 0 }, +++#define VB (VA + 1) +++ { 5, 16, 0, AXP_OPERAND_VPR, 0, 0 }, +++#define VC (VB + 1) +++ { 5, 0, 0, AXP_OPERAND_VPR, 0, 0 }, +++#define VD (VC + 1) +++ { 5, 5, 0, AXP_OPERAND_VPR, 0, 0 }, +++ +++#define SPE_RC (VD + 1) +++ { 5, 5, 0, AXP_OPERAND_IR, 0, 0 }, +++ +++ /* The unsigned 8-bit literal of Operate format insns. */ +++#define HX_LIT (SPE_RC + 1) +++ { 8, 5, -HX_LIT, AXP_OPERAND_UNSIGNED, 0, 0 }, + + +-+#define __glibc_fortify_n(f, __l, __s, __osz, ...) \ +-+ (__glibc_safe_or_unknown_len (__l, __s, __osz) \ +-+ ? __ ## f ## _alias (__VA_ARGS__) \ +-+ : (__glibc_unsafe_len (__l, __s, __osz) \ +-+ ? __ ## f ## _chk_warn (__VA_ARGS__, (__osz) / (__s)) \ +-+ : __ ## f ## _chk (__VA_ARGS__, (__osz) / (__s)))) + +#endif +++#ifndef XWB20161017 +++/* for the third operand of ternary operands integer insn. */ +++#define R3 (SW6HWJMPHINT + 1) +++ { 5, 5, 0, AXP_OPERAND_IR, 0, 0 }, +++ /* The plain fp register fields */ +++#define F3 (R3 + 1) +++ { 5, 5, 0, AXP_OPERAND_FPR, 0, 0 }, +++/* sw6 simd settle instruction lit */ +++#define FMALIT (F3 + 1) +++ { 5,5, -FMALIT, AXP_OPERAND_UNSIGNED, 0, 0 },//V1.1 +++/*for pal to check disp which must be plus sign and less than 0x8000,WCH20080901*/ +++#define LMDISP (FMALIT + 1) +++ { 15, 0, -LMDISP, AXP_OPERAND_UNSIGNED, 0, 0 }, +++#define RPIINDEX (LMDISP + 1) +++ { 8, 0, -RPIINDEX, AXP_OPERAND_UNSIGNED, 0, 0 }, + + +- #if __GNUC_PREREQ (4,3) +--# define __warndecl(name, msg) \ +-- extern void name (void) __attribute__((__warning__ (msg))) +- # define __warnattr(msg) __attribute__((__warning__ (msg))) +- # define __errordecl(name, msg) \ +- extern void name (void) __attribute__((__error__ (msg))) +++#define ATMDISP (RPIINDEX + 1) +++ { 12, 0, -ATMDISP, AXP_OPERAND_SIGNED, 0, 0 } +++#endif +++ +++}; +++ +++const unsigned sw_64_num_operands = sizeof(sw_64_operands)/sizeof(*sw_64_operands); +++ +++ +++/* Macros used to form opcodes. */ +++ +++/* The main opcode. */ +++#define OP(x) (((x) & 0x3F) << 26) +++#define OP_MASK 0xFC000000 +++ +++/* Branch format instructions. */ +++#define BRA_(oo) OP(oo) +++#define BRA_MASK OP_MASK +++#define BRA(oo) BRA_(oo), BRA_MASK +++ +++#ifndef SPS20160530 +++/* Simple computing format instructions. */ +++#define SIMP_(oo,fff) (OP(oo) | (((fff) & 0xFF) << 5)) +++#define SIMP_MASK (OP_MASK | 0x1FE0) +++#define SIMP(oo,fff) SIMP_(oo,fff), SIMP_MASK +++#else +++/* Floating point format instructions. */ +++#define FP_(oo,fff) (OP(oo) | (((fff) & 0x7FF) << 5)) +++#define FP_MASK (OP_MASK | 0xFFE0) +++#define FP(oo,fff) FP_(oo,fff), FP_MASK +++#endif +++ +++/* Memory format instructions. */ +++#define MEM_(oo) OP(oo) +++#define MEM_MASK OP_MASK +++#define MEM(oo) MEM_(oo), MEM_MASK +++ +++/* Memory/Func Code format instructions. */ +++#ifndef SPS20160530 +++#define MFC_(oo,ffff) (OP(oo) | (((ffff) & 0xF)<<12)) +++//#define MFC_MASK (OP_MASK | 0xFFFF) +++#define MFC_MASK (OP_MASK | 0xF000) +++#define MFC(oo,ffff) MFC_(oo,ffff), MFC_MASK +++#else +++#define MFC_(oo,ffff) (OP(oo) | ((ffff) & 0xFFFF)) +++#define MFC_MASK (OP_MASK | 0xFFFF) +++#define MFC(oo,ffff) MFC_(oo,ffff), MFC_MASK +++#endif +++ +++/* Memory/Branch format instructions. */ +++#define MBR_(oo,h) (OP(oo) | (((h) & 3) << 14)) +++#define MBR_MASK (OP_MASK | 0xC000) +++#define MBR(oo,h) MBR_(oo,h), MBR_MASK +++ +++#ifndef SPS20160530 +++/* Memory/miscellaneous atom format instructions. */ +++#define MAT_(oo,h) (OP(oo) | ((h) & 0xffff) ) +++#define MAT_MASK (OP_MASK | 0xFFFF) +++#define MAT(oo,h) MAT_(oo,h), MAT_MASK +++ +++/* priority format instructions. */ +++#define PRI_(oo,ty,len) (OP(oo) | (((ty) & 0x7)<<13) | (((len) & 0x1)<<12)) +++#define PRI_MASK (OP_MASK | 0xF000) +++#define PRI(oo,ty,len) PRI_(oo,ty,len), PRI_MASK +++#define PRI_SR_(oo,h) (OP(oo) | (((h) & 0xff)<<8) ) +++#define PRI_SR_MASK (OP_MASK | 0xFF00) +++#define PRI_SR(oo,h) PRI_SR_(oo,h), PRI_SR_MASK +++#define PRI_RET_(oo,h) (OP(oo) | (((h) & 0x1)<<20) ) +++#define PRI_RET_MASK (OP_MASK | (0x1<<20)) +++#define PRI_RET(oo,h) PRI_RET_(oo,h), PRI_RET_MASK +++ +++/* interger composite intr... */ +++#define INT_COM_(oo,h) (OP(oo) | (((h) & 7) << 10)) +++#define INT_COM_MASK (OP_MASK | 0x1C00) +++#define INT_COM(oo,h) INT_COM_(oo,h), INT_COM_MASK +++ +++/* float composite intr... */ +++#define FP_COM_(oo,h) (OP(oo) | (((h) & 0x3f) << 10)) +++#define FP_COM_MASK (OP_MASK | 0xFC00) +++#define FP_COM(oo,h) FP_COM_(oo,h), FP_COM_MASK +++#else +++ +++/* Operate format instructions. The OPRL variant specifies a +++ literal second argument. */ +++#define OPR_(oo,ff) (OP(oo) | (((ff) & 0x7F) << 5)) +++#define OPRL_(oo,ff) (OPR_((oo),(ff)) | 0x1000) +++#define OPR_MASK (OP_MASK | 0x1FE0) +++#define OPR(oo,ff) OPR_(oo,ff), OPR_MASK +++#define OPRL(oo,ff) OPRL_(oo,ff), OPR_MASK +++#endif +++ +++/* Generic PALcode format instructions. */ +++#define PCD_(oo) OP(oo) +++#define PCD_MASK OP_MASK +++#define PCD(oo) PCD_(oo), PCD_MASK +++#ifndef XWB20170510 +++#define PCDL_(oo,ff) (OP(oo) | (ff << 25)) +++#define PCDL_MASK OP_MASK +++#define PCDL(oo,ff) PCDL_(oo,ff), PCDL_MASK +++#endif +++ +++/* Specific PALcode instructions. */ +++#define SPCD_(oo,ffff) (OP(oo) | ((ffff) & 0x3FFFFFF)) +++#define SPCD_MASK 0xFFFFFFFF +++#define SPCD(oo,ffff) SPCD_(oo,ffff), SPCD_MASK +++ +++/* Hardware memory (hw_{ld,st}) instructions. */ +++#define SW6HWMEM_(oo,f) (OP(oo) | (((f) & 0xF) << 12)) +++#define SW6HWMEM_MASK (OP_MASK | 0xF000) +++#define SW6HWMEM(oo,f) SW6HWMEM_(oo,f), SW6HWMEM_MASK +++ +++#define SW6HWMBR_(oo,h) (OP(oo) | (((h) & 7) << 13)) +++#define SW6HWMBR_MASK (OP_MASK | 0xE000) +++#define SW6HWMBR(oo,h) SW6HWMBR_(oo,h), SW6HWMBR_MASK +++ +++/* Abbreviations for instruction subsets. */ +++#define BASE AXP_OPCODE_BASE +++#define SW6 AXP_OPCODE_SW6 +++#define BWX AXP_OPCODE_BWX +++#define CIX AXP_OPCODE_CIX +++#define MAX AXP_OPCODE_MAX +++ +++/* Common combinations of arguments. */ +++#define ARG_NONE { 0 } +++#define ARG_BRA { RA, BDISP } +++#define ARG_FBRA { FA, BDISP } +++#ifdef SPS20160530 +++#define ARG_FP { FA, FB, DFC1 } +++#define ARG_FPZ1 { ZA, FB, DFC1 } +++#endif +++#define ARG_MEM { RA, MDISP, PRB } +++#define ARG_FMEM { FA, MDISP, PRB } +++ +++#ifndef SPS20160530 +++#define ARG_FMEM_12DISP { FA, SW6HWDISP, PRB } +++#define ARG_VMEM_12DISP { VA, SW6HWDISP, PRB } +++#define ARG_FP { FA, FB, FC } +++#define ARG_FPZ1 { FB, FC } +++#define ARG_FPZB { FA, FC } +++#define ARG_OPR { RA, RB, RC } +++#define ARG_OPRL { RA, LIT, RC } +++#define ARG_OPRZ1 { RB, RC } +++#define ARG_OPRLZ1 { LIT, RC } +++#define ARG_VMEM { VA, MDISP, PRB } +++#define ARG_VOPR { VA, VB, VC } +++#define ARG_VOPRL { RA, LIT, RC } +++#define ARG_VOPR4 { VA, VB, VD, VC } +++#define ARG_VOPRL4 { VA, VB, CIB, VC } +++#else +++#define ARG_OPR { RA, RB, DRC1 } +++#define ARG_OPRL { RA, LIT, DRC1 } +++#define ARG_OPRZ1 { ZA, RB, DRC1 } +++#define ARG_OPRLZ1 { ZA, LIT, RC } +++#endif +++ +++#define ARG_PCD { PALFN } +++#define ARG_SW6HWMEM { RA, SW6HWDISP, PRB } +++ +++#ifndef SPS20160530 +++#define ARG_INT_COM { RA, RB, SRC, SRD } +++#define ARG_INT_COML { RA, LIT, SRC, SRD } +++#define ARG_FP_COM { FA, FB, SFC, SFD } +++#define ARG_FP_COML { FA, FB, CIB, SFD } +++#define ARG_FP_COMZL { FA, LIT, FC } +++#define ARG_FP_COMLC { FA, CIB, FC } +++#define ARG_FP_VCOMZL { VA, LIT, VC } +++#define ARG_FP_ITOF { RA, FC } +++#define ARG_FP_FTOI { FA, RC } +++#define ARG_ATOM {RA , PRIDISP, PRB } +++#endif +++#define ARG_VUAMEM { FA, ATMDISP, PRB } //WCH20090805 New V1.1 add +++ +++ +++ +++/* The opcode table. +++ +++ The format of the opcode table is: +++ +++ NAME OPCODE MASK { OPERANDS } +++ +++ NAME is the name of the instruction. +++ +++ OPCODE is the instruction opcode. +++ +++ MASK is the opcode mask; this is used to tell the disassembler +++ which bits in the actual opcode must match OPCODE. +++ +++ OPERANDS is the list of operands. +++ +++ The preceding macros merge the text of the OPCODE and MASK fields. +++ +++ The disassembler reads the table in order and prints the first +++ instruction which matches, so this table is sorted to put more +++ specific instructions before more general instructions. +++ +++ Otherwise, it is sorted by major opcode and minor function code. +++ +++ There are three classes of not-really-instructions in this table: +++ +++ ALIAS is another name for another instruction. Some of +++ these come from the Architecture Handbook, some +++ come from the original gas opcode tables. In all +++ cases, the functionality of the opcode is unchanged. +++ +++ PSEUDO a stylized code form endorsed by Chapter A.4 of the +++ Architecture Handbook. +++ +++ EXTRA a stylized code form found in the original gas tables. +++ +++ And two annotations: */ +++ +++ +++const struct sw_64_opcode sw_64_opcodes[] = +++{ +++ { "halt", SPCD(0x00,0x0000), BASE, ARG_NONE }, +++ { "draina", SPCD(0x00,0x0002), BASE, ARG_NONE }, +++ { "bpt", SPCD(0x00,0x0080), BASE, ARG_NONE }, +++ { "bugchk", SPCD(0x00,0x0081), BASE, ARG_NONE }, +++ { "callsys", SPCD(0x00,0x0083), BASE, ARG_NONE }, +++ { "chmk", SPCD(0x00,0x0083), BASE, ARG_NONE }, +++ { "imb", SPCD(0x00,0x0086), BASE, ARG_NONE }, +++ { "rduniq", SPCD(0x00,0x009e), BASE, ARG_NONE }, +++ { "wruniq", SPCD(0x00,0x009f), BASE, ARG_NONE }, +++ { "gentrap", SPCD(0x00,0x00aa), BASE, ARG_NONE }, +++ { "sys_call", PCDL(0x00,0x01), BASE, ARG_PCD }, +++ { "sys_call/b", PCDL(0x00,0x00), BASE, ARG_PCD }, +++ +++ { "call", MEM(0x1), BASE, { RA, CPRB, JMPHINT } }, +++ { "ret", MEM(0x2), BASE, { RA, CPRB, JMPHINT } }, +++ { "jmp", MEM(0x3), BASE, { RA, CPRB, JMPHINT } }, +++ { "br", BRA(0x4), BASE, ARG_BRA }, +++ { "bsr", BRA(0x5), BASE, ARG_BRA }, +++ { "memb", MAT(0x06,0x0), BASE, ARG_NONE }, +++ { "imemb", MAT(0x06,0x1), BASE, ARG_NONE }, +++ { "rtc", MAT(0x06,0x0020), BASE, {RA, RB } }, +++ { "rcid", MAT(0x06,0x0040), BASE, {RA, RB } }, +++ { "halt", MAT(0x06,0x0080), BASE, {RA, RB } }, +++ { "rd_f", MAT(0x06,0x1000), BASE, {RA, RB } }, +++ { "wr_f", MAT(0x06,0x1020), BASE, {RA, RB } }, +++ { "rtid", MAT(0x06,0x1040), BASE, { RA } }, +++ { "pri_rcsr", PRI_SR(0x06,0xfe), BASE, {RA, ZB, EV4EXTHWINDEX } }, +++ { "pri_wcsr", PRI_SR(0x06,0xff), BASE, {RA, ZB, EV4EXTHWINDEX } }, +++ { "pri_ret", PRI_RET(0x07,0x0), BASE, {RA } }, +++ { "pri_ret_barrier",PRI_RET(0x07,0x1), BASE, {RA } }, +++ +++ { "lldw", MFC(0x08,0x0), BASE, ARG_SW6HWMEM }, +++ { "lldl", MFC(0x08,0x1), BASE, ARG_SW6HWMEM }, +++ { "ldw_inc", MFC(0x08,0x2), BASE, ARG_SW6HWMEM }, +++ { "ldl_inc", MFC(0x08,0x3), BASE, ARG_SW6HWMEM }, +++ { "ldw_dec", MFC(0x08,0x4), BASE, ARG_SW6HWMEM }, +++ { "ldl_dec", MFC(0x08,0x5), BASE, ARG_SW6HWMEM }, +++ { "ldw_set", MFC(0x08,0x6), BASE, ARG_SW6HWMEM }, +++ { "ldl_set", MFC(0x08,0x7), BASE, ARG_SW6HWMEM }, +++ { "lstw", MFC(0x08,0x8), BASE, ARG_SW6HWMEM }, +++ { "lstl", MFC(0x08,0x9), BASE, ARG_SW6HWMEM }, +++ { "ldw_nc", MFC(0x08,0xa), BASE, ARG_SW6HWMEM }, +++ { "ldl_nc", MFC(0x08,0xb), BASE, ARG_SW6HWMEM }, +++ { "ldd_nc", MFC(0x08,0xc), BASE, ARG_SW6HWMEM }, +++ { "stw_nc", MFC(0x08,0xd), BASE, ARG_SW6HWMEM }, +++ { "stl_nc", MFC(0x08,0xe), BASE, ARG_SW6HWMEM }, +++ { "std_nc", MFC(0x08,0xf), BASE, ARG_SW6HWMEM }, +++ +++ { "ldwe", MEM(0x09), BASE, ARG_FMEM }, +++ { "ldse", MEM(0x0A), BASE, ARG_FMEM }, +++ { "ldde", MEM(0x0B), BASE, ARG_FMEM }, +++ { "vlds", MEM(0x0C), BASE, ARG_VMEM }, +++ { "vldd", MEM(0x0D), BASE, ARG_VMEM }, +++ { "vsts", MEM(0x0E), BASE, ARG_VMEM }, +++ { "vstd", MEM(0x0F), BASE, ARG_VMEM }, +++ +++ { "addw", SIMP(0x10,0x00), BASE, ARG_OPR }, +++ { "subw", SIMP(0x10,0x01), BASE, ARG_OPR }, +++ { "s4addw", SIMP(0x10,0x02), BASE, ARG_OPR }, +++ { "s4subw", SIMP(0x10,0x03), BASE, ARG_OPR }, +++ { "s8addw", SIMP(0x10,0x04), BASE, ARG_OPR }, +++ { "s8subw", SIMP(0x10,0x05), BASE, ARG_OPR }, +++ { "addl", SIMP(0x10,0x08), BASE, ARG_OPR }, +++ { "subl", SIMP(0x10,0x09), BASE, ARG_OPR }, +++ { "s4addl", SIMP(0x10,0x0A), BASE, ARG_OPR }, +++ { "s4subl", SIMP(0x10,0x0B), BASE, ARG_OPR }, +++ { "s8addl", SIMP(0x10,0x0C), BASE, ARG_OPR }, +++ { "s8subl", SIMP(0x10,0x0D), BASE, ARG_OPR }, +++ { "mulw", SIMP(0x10,0x10), BASE, ARG_OPR }, +++ { "mull", SIMP(0x10,0x18), BASE, ARG_OPR }, +++ { "umulh", SIMP(0x10,0x19), BASE, ARG_OPR }, +++ { "cmpeq", SIMP(0x10,0x28), BASE, ARG_OPR }, +++ { "cmplt", SIMP(0x10,0x29), BASE, ARG_OPR }, +++ { "cmple", SIMP(0x10,0x2A), BASE, ARG_OPR }, +++ { "cmpult", SIMP(0x10,0x2B), BASE, ARG_OPR }, +++ { "cmpule", SIMP(0x10,0x2C), BASE, ARG_OPR }, +++ +++ { "and", SIMP(0x10,0x38), BASE, ARG_OPR }, +++ { "bic", SIMP(0x10,0x39), BASE, ARG_OPR }, +++ { "bis", SIMP(0x10,0x3A), BASE, ARG_OPR }, +++ { "ornot", SIMP(0x10,0x3B), BASE, ARG_OPR }, +++ { "xor", SIMP(0x10,0x3c), BASE, ARG_OPR }, +++ { "eqv", SIMP(0x10,0x3D), BASE, ARG_OPR }, +++ +++ { "ins0b", SIMP(0x10,0x40), BASE, ARG_OPR }, +++ { "ins1b", SIMP(0x10,0x41), BASE, ARG_OPR }, +++ { "ins2b", SIMP(0x10,0x42), BASE, ARG_OPR }, +++ { "ins3b", SIMP(0x10,0x43), BASE, ARG_OPR }, +++ { "ins4b", SIMP(0x10,0x44), BASE, ARG_OPR }, +++ { "ins5b", SIMP(0x10,0x45), BASE, ARG_OPR }, +++ { "ins6b", SIMP(0x10,0x46), BASE, ARG_OPR }, +++ { "ins7b", SIMP(0x10,0x47), BASE, ARG_OPR }, +++ +++ { "sll", SIMP(0x10,0x48), BASE, ARG_OPR }, +++ { "srl", SIMP(0x10,0x49), BASE, ARG_OPR }, +++ { "sra", SIMP(0x10,0x4A), BASE, ARG_OPR }, +++ +++ { "ext0b", SIMP(0x10,0x50), BASE, ARG_OPR }, +++ { "ext1b", SIMP(0x10,0x51), BASE, ARG_OPR }, +++ { "ext2b", SIMP(0x10,0x52), BASE, ARG_OPR }, +++ { "ext3b", SIMP(0x10,0x53), BASE, ARG_OPR }, +++ { "ext4b", SIMP(0x10,0x54), BASE, ARG_OPR }, +++ { "ext5b", SIMP(0x10,0x55), BASE, ARG_OPR }, +++ { "ext6b", SIMP(0x10,0x56), BASE, ARG_OPR }, +++ { "ext7b", SIMP(0x10,0x57), BASE, ARG_OPR }, +++ +++ { "ctpop", SIMP(0x10,0x58), BASE, ARG_OPRZ1 }, +++ { "ctlz", SIMP(0x10,0x59), BASE, ARG_OPRZ1 }, +++ { "cttz", SIMP(0x10,0x5A), BASE, ARG_OPRZ1 }, +++ +++ { "mask0b", SIMP(0x10,0x60), BASE, ARG_OPR }, +++ { "mask1b", SIMP(0x10,0x61), BASE, ARG_OPR }, +++ { "mask2b", SIMP(0x10,0x62), BASE, ARG_OPR }, +++ { "mask3b", SIMP(0x10,0x63), BASE, ARG_OPR }, +++ { "mask4b", SIMP(0x10,0x64), BASE, ARG_OPR }, +++ { "mask5b", SIMP(0x10,0x65), BASE, ARG_OPR }, +++ { "mask6b", SIMP(0x10,0x66), BASE, ARG_OPR }, +++ { "mask7b", SIMP(0x10,0x67), BASE, ARG_OPR }, +++ { "zap", SIMP(0x10,0x68), BASE, ARG_OPR }, +++ { "zapnot", SIMP(0x10,0x69), BASE, ARG_OPR }, +++ { "sextb", SIMP(0x10,0x6A), BASE, ARG_OPRZ1 }, +++ { "sexth", SIMP(0x10,0x6B), BASE, ARG_OPRZ1 }, +++ { "cmpgeb", SIMP(0x10,0x6c), BASE, ARG_OPR }, +++ { "ftois", SIMP(0x10,0x70), BASE, ARG_FP_FTOI }, +++ { "ftoid", SIMP(0x10,0x78), BASE, ARG_FP_FTOI }, +++ { "SelEq", INT_COM(0x11,0x0), BASE, ARG_INT_COM }, +++ { "SelGe", INT_COM(0x11,0x1), BASE, ARG_INT_COM }, +++ { "SelGt", INT_COM(0x11,0x2), BASE, ARG_INT_COM }, +++ { "SelLe", INT_COM(0x11,0x3), BASE, ARG_INT_COM }, +++ { "SelLt", INT_COM(0x11,0x4), BASE, ARG_INT_COM }, +++ { "SelNe", INT_COM(0x11,0x5), BASE, ARG_INT_COM }, +++ { "SelLbC", INT_COM(0x11,0x6), BASE, ARG_INT_COM }, +++ { "selLbS", INT_COM(0x11,0x7), BASE, ARG_INT_COM }, +++ +++ { "addw", SIMP(0x12,0x00), BASE, ARG_OPRL }, +++ { "subw", SIMP(0x12,0x01), BASE, ARG_OPRL }, +++ { "s4addw", SIMP(0x12,0x02), BASE, ARG_OPRL }, +++ { "s4subw", SIMP(0x12,0x03), BASE, ARG_OPRL }, +++ { "s8addw", SIMP(0x12,0x04), BASE, ARG_OPRL }, +++ { "s8subw", SIMP(0x12,0x05), BASE, ARG_OPRL }, +++ { "addl", SIMP(0x12,0x08), BASE, ARG_OPRL }, +++ { "subl", SIMP(0x12,0x09), BASE, ARG_OPRL }, +++ { "s4addl", SIMP(0x12,0x0A), BASE, ARG_OPRL }, +++ { "s4subl", SIMP(0x12,0x0B), BASE, ARG_OPRL }, +++ { "s8addl", SIMP(0x12,0x0C), BASE, ARG_OPRL }, +++ { "s8subl", SIMP(0x12,0x0D), BASE, ARG_OPRL }, +++ { "mulw", SIMP(0x12,0x10), BASE, ARG_OPRL }, +++ { "mull", SIMP(0x12,0x18), BASE, ARG_OPRL }, +++ { "umulh", SIMP(0x12,0x19), BASE, ARG_OPRL }, +++ { "cmpeq", SIMP(0x12,0x28), BASE, ARG_OPRL }, +++ { "cmplt", SIMP(0x12,0x29), BASE, ARG_OPRL }, +++ { "cmple", SIMP(0x12,0x2A), BASE, ARG_OPRL }, +++ { "cmpult", SIMP(0x12,0x2B), BASE, ARG_OPRL }, +++ { "cmpule", SIMP(0x12,0x2C), BASE, ARG_OPRL }, +++ +++ { "and", SIMP(0x12,0x38), BASE, ARG_OPRL }, +++ { "bic", SIMP(0x12,0x39), BASE, ARG_OPRL }, +++ { "bis", SIMP(0x12,0x3A), BASE, ARG_OPRL }, +++ { "ornot", SIMP(0x12,0x3B), BASE, ARG_OPRL }, +++ { "xor", SIMP(0x12,0x3c), BASE, ARG_OPRL }, +++ { "eqv", SIMP(0x12,0x3D), BASE, ARG_OPRL }, +++ { "ins0b", SIMP(0x12,0x40), BASE, ARG_OPRL }, +++ { "ins1b", SIMP(0x12,0x41), BASE, ARG_OPRL }, +++ { "ins2b", SIMP(0x12,0x42), BASE, ARG_OPRL }, +++ { "ins3b", SIMP(0x12,0x43), BASE, ARG_OPRL }, +++ { "ins4b", SIMP(0x12,0x44), BASE, ARG_OPRL }, +++ { "ins5b", SIMP(0x12,0x45), BASE, ARG_OPRL }, +++ { "ins6b", SIMP(0x12,0x46), BASE, ARG_OPRL }, +++ { "ins7b", SIMP(0x12,0x47), BASE, ARG_OPRL }, +++ +++ { "sll", SIMP(0x12,0x48), BASE, ARG_OPRL }, +++ { "srl", SIMP(0x12,0x49), BASE, ARG_OPRL }, +++ { "sra", SIMP(0x12,0x4A), BASE, ARG_OPRL }, +++ { "ext0b", SIMP(0x12,0x50), BASE, ARG_OPRL }, +++ { "ext1b", SIMP(0x12,0x51), BASE, ARG_OPRL }, +++ { "ext2b", SIMP(0x12,0x52), BASE, ARG_OPRL }, +++ { "ext3b", SIMP(0x12,0x53), BASE, ARG_OPRL }, +++ { "ext4b", SIMP(0x12,0x54), BASE, ARG_OPRL }, +++ { "ext5b", SIMP(0x12,0x55), BASE, ARG_OPRL }, +++ { "ext6b", SIMP(0x12,0x56), BASE, ARG_OPRL }, +++ { "ext7b", SIMP(0x12,0x57), BASE, ARG_OPRL }, +++ +++ { "mask0b", SIMP(0x12,0x60), BASE, ARG_OPRL }, +++ { "mask1b", SIMP(0x12,0x61), BASE, ARG_OPRL }, +++ { "mask2b", SIMP(0x12,0x62), BASE, ARG_OPRL }, +++ { "mask3b", SIMP(0x12,0x63), BASE, ARG_OPRL }, +++ { "mask4b", SIMP(0x12,0x64), BASE, ARG_OPRL }, +++ { "mask5b", SIMP(0x12,0x65), BASE, ARG_OPRL }, +++ { "mask6b", SIMP(0x12,0x66), BASE, ARG_OPRL }, +++ { "mask7b", SIMP(0x12,0x67), BASE, ARG_OPRL }, +++ { "zap", SIMP(0x12,0x68), BASE, ARG_OPRLZ1 }, +++ { "zapnot", SIMP(0x12,0x69), BASE, ARG_OPRL }, +++ { "sextb", SIMP(0x12,0x6A), BASE, ARG_OPRLZ1 }, +++ { "sexth", SIMP(0x12,0x6B), BASE, ARG_OPRLZ1 }, +++ { "cmpgeb", SIMP(0x12,0x6c), BASE, ARG_OPRL }, +++ +++ { "SelEqI", INT_COM(0x13,0x0), BASE, ARG_INT_COML }, +++ { "SelGeI", INT_COM(0x13,0x1), BASE, ARG_INT_COML }, +++ { "SelGtI", INT_COM(0x13,0x2), BASE, ARG_INT_COML }, +++ { "SelLeI", INT_COM(0x13,0x3), BASE, ARG_INT_COML }, +++ { "SelLtI", INT_COM(0x13,0x4), BASE, ARG_INT_COML }, +++ { "SelNeI", INT_COM(0x13,0x5), BASE, ARG_INT_COML }, +++ { "SelLbCI", INT_COM(0x13,0x6), BASE, ARG_INT_COML }, +++ { "selLbSI", INT_COM(0x13,0x7), BASE, ARG_INT_COML }, +++ +++ { "vlog", MEM(0x14), BASE, ARG_VOPR4 }, +++ { "vlog", MEM(0x15), BASE, ARG_VOPR4 }, +++ { "vlog", MEM(0x16), BASE, ARG_VOPR4 }, +++ { "vlog", MEM(0x17), BASE, ARG_VOPR4 }, +++ { "fadds", SIMP(0x18,0x00), BASE, ARG_FP }, +++ { "faddd", SIMP(0x18,0x01), BASE, ARG_FP }, +++ { "fsubs", SIMP(0x18,0x02), BASE, ARG_FP }, +++ { "fsubd", SIMP(0x18,0x03), BASE, ARG_FP }, +++ { "fmuls", SIMP(0x18,0x04), BASE, ARG_FP }, +++ { "fmuld", SIMP(0x18,0x05), BASE, ARG_FP }, +++ { "fdivs", SIMP(0x18,0x06), BASE, ARG_FP }, +++ { "fdivd", SIMP(0x18,0x07), BASE, ARG_FP }, +++ { "fsqrts", SIMP(0x18,0x08), BASE, ARG_FPZ1 }, +++ { "fsqrtd", SIMP(0x18,0x09), BASE, ARG_FPZ1 }, +++ { "fcmpEq", SIMP(0x18,0x10), BASE, ARG_FP }, +++ { "fcmpLe", SIMP(0x18,0x11), BASE, ARG_FP }, +++ { "fcmpLt", SIMP(0x18,0x12), BASE, ARG_FP }, +++ { "fcmpUn", SIMP(0x18,0x13), BASE, ARG_FP }, +++ { "fcvtSD", SIMP(0x18,0x20), BASE, ARG_FPZ1 }, +++ { "fcvtDS", SIMP(0x18,0x21), BASE, ARG_FPZ1 }, +++ +++ { "fcvtdl_g", SIMP(0x18,0x22), BASE, ARG_FPZ1 }, +++ { "fcvtdl_p", SIMP(0x18,0x23), BASE, ARG_FPZ1 }, +++ { "fcvtdl_z", SIMP(0x18,0x24), BASE, ARG_FPZ1 }, +++ { "fcvtdl_n", SIMP(0x18,0x25), BASE, ARG_FPZ1 }, +++ { "fcvtDL", SIMP(0x18,0x27), BASE, ARG_FPZ1 }, +++ { "fcvtWL", SIMP(0x18,0x28), BASE, ARG_FPZ1 }, +++ { "fcvtLW", SIMP(0x18,0x29), BASE, ARG_FPZ1 }, +++ { "fcvtLS", SIMP(0x18,0x2D), BASE, ARG_FPZ1 }, +++ { "fcvtLD", SIMP(0x18,0x2F), BASE, ARG_FPZ1 }, +++ { "fcpys", SIMP(0x18,0x30), BASE, ARG_FP }, +++ { "fcpyse", SIMP(0x18,0x31), BASE, ARG_FP }, +++ { "fcpysn", SIMP(0x18,0x32), BASE, ARG_FP }, +++ { "ItoFS", SIMP(0x18,0x40), BASE, ARG_FP_ITOF }, +++ { "ItoFD", SIMP(0x18,0x41), BASE, ARG_FP_ITOF }, +++ { "rfpcr", SIMP(0x18,0x50), BASE, { FA } }, +++ { "wfpcr", SIMP(0x18,0x51), BASE, { FA } }, +++ { "setfpec0", SIMP(0x18,0x54), BASE, ARG_NONE }, +++ { "setfpec1", SIMP(0x18,0x55), BASE, ARG_NONE }, +++ { "setfpec2", SIMP(0x18,0x56), BASE, ARG_NONE }, +++ { "setfpec3", SIMP(0x18,0x57), BASE, ARG_NONE }, +++ +++ { "fmas", FP_COM(0x19,0x00), BASE, ARG_FP_COM }, +++ { "fmad", FP_COM(0x19,0x01), BASE, ARG_FP_COM }, +++ { "fmss", FP_COM(0x19,0x02), BASE, ARG_FP_COM }, +++ { "fmsd", FP_COM(0x19,0x03), BASE, ARG_FP_COM }, +++ { "fnmas", FP_COM(0x19,0x04), BASE, ARG_FP_COM }, +++ { "fnmad", FP_COM(0x19,0x05), BASE, ARG_FP_COM }, +++ { "fnmss", FP_COM(0x19,0x06), BASE, ARG_FP_COM }, +++ { "fnmsd", FP_COM(0x19,0x07), BASE, ARG_FP_COM }, +++ { "fselEq", FP_COM(0x19,0x10), BASE, ARG_FP_COM }, +++ { "fselNe", FP_COM(0x19,0x11), BASE, ARG_FP_COM }, +++ { "fselLt", FP_COM(0x19,0x12), BASE, ARG_FP_COM }, +++ { "fselLe", FP_COM(0x19,0x13), BASE, ARG_FP_COM }, +++ { "fselGt", FP_COM(0x19,0x14), BASE, ARG_FP_COM }, +++ { "fselGe", FP_COM(0x19,0x15), BASE, ARG_FP_COM }, +++ { "vaddw", SIMP(0x1A,0x00), BASE, ARG_VOPR }, +++ { "vsubw", SIMP(0x1A,0x01), BASE, ARG_VOPR }, +++ { "vcmpgew", SIMP(0x1A,0x02), BASE, {VA, VB, FC} }, +++ { "vcmpeqw", SIMP(0x1A,0x03), BASE, ARG_VOPR }, +++ { "vcmplew", SIMP(0x1A,0x04), BASE, ARG_VOPR }, +++ { "vcmpltw", SIMP(0x1A,0x05), BASE, ARG_VOPR }, +++ { "vcmpulew", SIMP(0x1A,0x06), BASE, ARG_VOPR }, +++ { "vcmpultw", SIMP(0x1A,0x07), BASE, ARG_VOPR }, +++ { "vsllw", SIMP(0x1A,0x08), BASE, {VA, FB, VC} }, +++ { "vsrlw", SIMP(0x1A,0x09), BASE, {VA, FB, VC} }, +++ { "vsraw", SIMP(0x1A,0x0A), BASE, {VA, FB, VC} }, +++ { "vrolw", SIMP(0x1A,0x0B), BASE, {VA, FB, VC} }, +++ { "sllow", SIMP(0x1A,0x0C), BASE, {VA, FB, VC} }, +++ { "srlow", SIMP(0x1A,0x0D), BASE, {VA, FB, VC} }, +++ { "vaddl", SIMP(0x1A,0x0E), BASE, ARG_VOPR }, +++ { "vsubl", SIMP(0x1A,0x0F), BASE, ARG_VOPR }, +++ { "ctpopow", SIMP(0x1A,0x18), BASE, {VA, FC} }, +++ { "ctlzow", SIMP(0x1A,0x19), BASE, {VA, FC} }, +++ { "vaddw", SIMP(0x1A,0x20), BASE, ARG_FP_VCOMZL }, +++ { "vsubw", SIMP(0x1A,0x21), BASE, ARG_FP_VCOMZL }, +++ { "vcmpgew", SIMP(0x1A,0x22), BASE, ARG_FP_VCOMZL }, +++ { "vcmpeqw", SIMP(0x1A,0x23), BASE, ARG_FP_VCOMZL }, +++ { "vcmplew", SIMP(0x1A,0x24), BASE, ARG_FP_VCOMZL }, +++ { "vcmpltw", SIMP(0x1A,0x25), BASE, ARG_FP_VCOMZL }, +++ { "vcmpulew", SIMP(0x1A,0x26), BASE, ARG_FP_VCOMZL }, +++ { "vcmpultw", SIMP(0x1A,0x27), BASE, ARG_FP_VCOMZL }, +++ +++ { "vsllw", SIMP(0x1A,0x28), BASE, ARG_FP_VCOMZL }, +++ { "vsrlw", SIMP(0x1A,0x29), BASE, ARG_FP_VCOMZL }, +++ { "vsraw", SIMP(0x1A,0x2A), BASE, ARG_FP_VCOMZL }, +++ { "vrolw", SIMP(0x1A,0x0B), BASE, ARG_FP_VCOMZL }, +++ { "sllow", SIMP(0x1A,0x2C), BASE, ARG_FP_VCOMZL }, +++ { "srlow", SIMP(0x1A,0x2D), BASE, ARG_FP_VCOMZL }, +++ { "vaddl", SIMP(0x1A,0x2E), BASE, ARG_FP_VCOMZL }, +++ { "vsubl", SIMP(0x1A,0x2F), BASE, ARG_FP_VCOMZL }, +++#ifdef SPS20160315 +++ { "vbicw", PSE_LOGX(0x14,0x30), SW6, { FA , FB , DFC1 } }, +++ { "vxorw", PSE_LOGX(0x14,0x3c), SW6, { FA , FB , DFC1 } }, +++ { "vandw", PSE_LOGX(0x14,0xc0), SW6, { FA , FB , DFC1 } }, +++ { "veqvw", PSE_LOGX(0x14,0xc3), SW6, { FA , FB , DFC1 } }, +++ { "vornotw", PSE_LOGX(0x14,0xf3), SW6, { FA , FB , DFC1 } }, +++ { "vbisw", PSE_LOGX(0x14,0xfc), SW6, { FA , FB , DFC1 } }, +++#endif +++ +++ { "vucaddw", SIMP(0x1A,0x40), BASE, ARG_VOPR }, +++ { "vucsubw", SIMP(0x1A,0x41), BASE, ARG_VOPR }, +++ { "vucaddh", SIMP(0x1A,0x42), BASE, ARG_VOPR }, +++ { "vucsubh", SIMP(0x1A,0x43), BASE, ARG_VOPR }, +++ { "vucaddb", SIMP(0x1A,0x44), BASE, ARG_VOPR }, +++ { "vucsubb", SIMP(0x1A,0x45), BASE, ARG_VOPR }, +++ +++ { "vucaddw", SIMP(0x1A,0x60), BASE, ARG_FP_VCOMZL }, +++ { "vucsubw", SIMP(0x1A,0x61), BASE, ARG_FP_VCOMZL }, +++ { "vucaddh", SIMP(0x1A,0x62), BASE, ARG_FP_VCOMZL }, +++ { "vucsubh", SIMP(0x1A,0x63), BASE, ARG_FP_VCOMZL }, +++ { "vucaddb", SIMP(0x1A,0x64), BASE, ARG_FP_VCOMZL }, +++ { "vucsubb", SIMP(0x1A,0x65), BASE, ARG_FP_VCOMZL }, +++ +++ { "vadds", SIMP(0x1A,0x80), BASE, ARG_VOPR }, +++ { "vaddd", SIMP(0x1A,0x81), BASE, ARG_VOPR }, +++ { "vsubs", SIMP(0x1A,0x82), BASE, ARG_VOPR }, +++ { "vsubd", SIMP(0x1A,0x83), BASE, ARG_VOPR }, +++ { "vmuls", SIMP(0x1A,0x84), BASE, ARG_VOPR }, +++ { "vmuld", SIMP(0x1A,0x85), BASE, ARG_VOPR }, +++ { "vdivs", SIMP(0x1A,0x86), BASE, ARG_VOPR }, +++ { "vdivd", SIMP(0x1A,0x87), BASE, ARG_VOPR }, +++ { "vsqrts", SIMP(0x1A,0x88), BASE, { VB, VC } }, +++ { "vsqrtd", SIMP(0x1A,0x89), BASE, { VB, VC } }, +++ { "vfcmpeq", SIMP(0x1A,0x8c), BASE, ARG_VOPR }, +++ { "vfcmple", SIMP(0x1A,0x8d), BASE, ARG_VOPR }, +++ { "vfcmplt", SIMP(0x1A,0x8e), BASE, ARG_VOPR }, +++ { "vfcmpun", SIMP(0x1A,0x8f), BASE, ARG_VOPR }, +++ +++ { "vcpys", SIMP(0x1A,0x90), BASE, ARG_VOPR }, +++ { "vcpyse", SIMP(0x1A,0x91), BASE, ARG_VOPR }, +++ { "vcpysn", SIMP(0x1A,0x92), BASE, ARG_VOPR }, +++ +++ { "vmas", FP_COM(0x1B,0x00), BASE, ARG_VOPR4 }, +++ { "vmad", FP_COM(0x1B,0x01), BASE, ARG_VOPR4 }, +++ { "vmss", FP_COM(0x1B,0x02), BASE, ARG_VOPR4 }, +++ { "vmsd", FP_COM(0x1B,0x03), BASE, ARG_VOPR4 }, +++ { "vnmas", FP_COM(0x1B,0x04), BASE, ARG_VOPR4 }, +++ { "vnmad", FP_COM(0x1B,0x05), BASE, ARG_VOPR4 }, +++ { "vnmss", FP_COM(0x1B,0x06), BASE, ARG_VOPR4 }, +++ { "vnmsd", FP_COM(0x1B,0x07), BASE, ARG_VOPR4 }, +++ { "vfseleq", FP_COM(0x1B,0x10), BASE, ARG_VOPR4 }, +++ { "vfsellt", FP_COM(0x1B,0x12), BASE, ARG_VOPR4 }, +++ { "vfselle", FP_COM(0x1B,0x13), BASE, ARG_VOPR4 }, +++ +++ { "vseleqw", FP_COM(0x1B,0x18), BASE, ARG_VOPR4 }, +++ { "vsellbcw", FP_COM(0x1B,0x19), BASE, ARG_VOPR4 }, +++ { "vselltw", FP_COM(0x1B,0x1A), BASE, ARG_VOPR4 }, +++ { "vsellew", FP_COM(0x1B,0x1B), BASE, ARG_VOPR4 }, +++ +++ { "vseleqw", FP_COM(0x1B,0x38), BASE, ARG_VOPRL4 }, +++ { "vsellbcw", FP_COM(0x1B,0x39), BASE, ARG_VOPRL4 }, +++ { "vselltw", FP_COM(0x1B,0x3A), BASE, ARG_VOPRL4 }, +++ { "vsellew", FP_COM(0x1B,0x3B), BASE, ARG_VOPRL4 }, +++ +++ { "vinsw", FP_COM(0x1B,0x20), BASE, { FA, VB, CIB, VC } }, +++ { "vinsf", FP_COM(0x1B,0x21), BASE, { FA, VB, CIB, VC } }, +++ { "vextw", FP_COM(0x1B,0x22), BASE, { FA, CIB, SFD } }, +++ { "vextf", FP_COM(0x1B,0x23), BASE, { FA, CIB, SFD } }, +++ { "vcpyw", FP_COM(0x1B,0x24), BASE, { FA, VC } }, +++ { "vcpyf", FP_COM(0x1B,0x25), BASE, { FA, VC } }, +++ { "vconw", FP_COM(0x1B,0x26), BASE, ARG_VOPR4 }, +++ { "vshfw", FP_COM(0x1B,0x27), BASE, ARG_VOPR4 }, +++ { "vcons", FP_COM(0x1B,0x28), BASE, ARG_VOPR4 }, +++ { "vcond", FP_COM(0x1B,0x29), BASE, ARG_VOPR4 }, +++ +++#ifdef XWB20170510 +++ { "vldw_ul", MFC(0x1C,0), BASE, ARG_VMEM_12DISP }, +++ { "vldw_uh", MFC(0x1C,1), BASE, ARG_VMEM_12DISP }, +++ { "vlds_ul", MFC(0x1C,2), BASE, ARG_VMEM_12DISP }, +++ { "vlds_uh", MFC(0x1C,3), BASE, ARG_VMEM_12DISP }, +++ { "vldd_ul", MFC(0x1C,4), BASE, ARG_VMEM_12DISP }, +++ { "vldd_uh", MFC(0x1C,5), BASE, ARG_VMEM_12DISP }, +++ { "vldd_nc", MFC(0x1C,6), BASE, ARG_VMEM_12DISP }, +++#else +++ { "vldw_u", MFC(0x1C,0), BASE, ARG_SW6HWMEM }, +++ { "vstw_u", MFC(0x1C,1), BASE, ARG_SW6HWMEM }, +++ { "vlds_u", MFC(0x1C,2), BASE, ARG_SW6HWMEM }, +++ { "vsts_u", MFC(0x1C,3), BASE, ARG_SW6HWMEM }, +++ { "vldd_u", MFC(0x1C,4), BASE, ARG_SW6HWMEM }, +++ { "vstd_u", MFC(0x1C,5), BASE, ARG_SW6HWMEM }, +++#endif +++ { "vstw_ul", MFC(0x1C,8), BASE, ARG_SW6HWMEM }, +++ { "vstw_uh", MFC(0x1C,9), BASE, ARG_SW6HWMEM }, +++ { "vsts_ul", MFC(0x1C,0xA), BASE, ARG_SW6HWMEM }, +++ { "vsts_uh", MFC(0x1C,0xB), BASE, ARG_SW6HWMEM }, +++ { "vstd_ul", MFC(0x1C,0xC), BASE, ARG_SW6HWMEM }, +++ { "vstd_uh", MFC(0x1C,0xD), BASE, ARG_SW6HWMEM }, +++#ifdef XWB20170510 +++ { "vstd_nc", MFC(0x1C,0xE), BASE, ARG_VMEM_12DISP }, +++#else +++ { "vldd_nc", MFC(0x1C,0xE), BASE, ARG_VMEM_12DISP }, +++ { "vstd_nc", MFC(0x1C,0xF), BASE, ARG_VMEM_12DISP }, +++#endif +++ { "ldbu", MEM(0x20), BASE, ARG_MEM }, +++ { "ldhu", MEM(0x21), BASE, ARG_MEM }, +++ { "ldw", MEM(0x22), BASE, ARG_MEM }, +++ { "ldl", MEM(0x23), BASE, ARG_MEM }, +++ { "ldl_u", MEM(0x24), BASE, ARG_MEM }, +++ +++ { "pri_ldw/p", PRI(0x25,0x0,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldw_inc/p", PRI(0x25,0x2,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldw/v", PRI(0x25,0x4,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldw/vpte", PRI(0x25,0x6,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldl/p", PRI(0x25,0x0,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldl_inc/p", PRI(0x25,0x2,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldl/v", PRI(0x25,0x4,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_ldl/vpte", PRI(0x25,0x6,0x1), BASE, {RA, PRIDISP, PRB } }, +++ +++ { "flds", MEM(0x26), BASE, ARG_FMEM }, +++ { "fldd", MEM(0x27), BASE, ARG_FMEM }, +++ { "stb", MEM(0x28), BASE, ARG_MEM }, +++ { "sth", MEM(0x29), BASE, ARG_MEM }, +++ { "stw", MEM(0x2A), BASE, ARG_MEM }, +++ { "stl", MEM(0x2B), BASE, ARG_MEM }, +++ { "stl_u", MEM(0x2C), BASE, ARG_MEM }, +++ +++ { "pri_stw/p", PRI(0x2d,0x0,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stw_inc/p", PRI(0x2d,0x2,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stw/v", PRI(0x2d,0x4,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stw/vpte", PRI(0x2d,0x6,0x0), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stl/p", PRI(0x2d,0x0,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stl_inc/p", PRI(0x2d,0x2,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stl/v", PRI(0x2d,0x4,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "pri_stl/vpte", PRI(0x2d,0x6,0x1), BASE, {RA, PRIDISP, PRB } }, +++ { "fsts", MEM(0x2E), BASE, ARG_FMEM }, +++ { "fstd", MEM(0x2F), BASE, ARG_FMEM }, +++ +++ { "beq", BRA(0x30), BASE, ARG_BRA }, +++ { "bne", BRA(0x31), BASE, ARG_BRA }, +++ { "blt", BRA(0x32), BASE, ARG_BRA }, +++ { "ble", BRA(0x33), BASE, ARG_BRA }, +++ { "bgt", BRA(0x34), BASE, ARG_BRA }, +++ { "bge", BRA(0x35), BASE, ARG_BRA }, +++ { "blbc", BRA(0x36), BASE, ARG_BRA }, +++ { "blbs", BRA(0x37), BASE, ARG_BRA }, +++ { "fbeq", BRA(0x38), BASE, ARG_FBRA }, +++ { "fbne", BRA(0x39), BASE, ARG_FBRA }, +++ { "fblt", BRA(0x3A), BASE, ARG_FBRA }, +++ { "fble", BRA(0x3B), BASE, ARG_FBRA }, +++ { "fbgt", BRA(0x3C), BASE, ARG_FBRA }, +++ { "fbge", BRA(0x3D), BASE, ARG_FBRA }, +++ +++ { "ldi", MEM(0x3E), BASE, ARG_MEM }, +++ { "ldih", MEM(0x3F), BASE, ARG_MEM }, +++}; +++ +++const unsigned sw_64_num_opcodes = sizeof(sw_64_opcodes)/sizeof(*sw_64_opcodes); ++diff -Nuar gdb-10.2/readline/readline/aclocal.m4 gdb-10.2/readline/readline/aclocal.m4 ++--- gdb-10.2/readline/readline/aclocal.m4 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/aclocal.m4 2025-04-16 17:06:52.012086800 +0800 ++@@ -10,6 +10,7 @@ ++ ac_cv_c_long_long=yes ++ else ++ AC_TRY_RUN([ +++#include ++ int ++ main() ++ { ++@@ -33,6 +34,7 @@ ++ ac_cv_c_long_double=yes ++ else ++ AC_TRY_RUN([ +++#include ++ int ++ main() ++ { ++@@ -134,6 +136,8 @@ + #else +--# define __warndecl(name, msg) extern void name (void) +- # define __warnattr(msg) +- # define __errordecl(name, msg) extern void name (void) ++ typedef int (*_bashfunc)(); + #endif +-@@ -142,8 +217,8 @@ +- #if defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L && !defined __HP_cc +- # define __flexarr [] +- # define __glibc_c99_flexarr_available 1 +--#elif __GNUC_PREREQ (2,97) +--/* GCC 2.97 supports C99 flexible array members as an extension, +-+#elif __GNUC_PREREQ (2,97) || defined __clang__ +-+/* GCC 2.97 and clang support C99 flexible array members as an extension, +- even when in C89 mode or compiling C++ (any version). */ +- # define __flexarr [] +- # define __glibc_c99_flexarr_available 1 +-@@ -169,7 +244,7 @@ +- Example: +- int __REDIRECT(setpgrp, (__pid_t pid, __pid_t pgrp), setpgid); */ +- +--#if defined __GNUC__ && __GNUC__ >= 2 +-+#if (defined __GNUC__ && __GNUC__ >= 2) || (__clang_major__ >= 4) +- +- # define __REDIRECT(name, proto, alias) name proto __asm__ (__ASMNAME (#alias)) +- # ifdef __cplusplus +-@@ -194,17 +269,17 @@ +- */ +++#include +++int ++ main() ++ { ++ _bashfunc pf; ++@@ -191,9 +195,11 @@ ++ #ifdef HAVE_UNISTD_H ++ #include + #endif +- +--/* GCC has various useful declarations that can be made with the +-- `__attribute__' syntax. All of the ways we use this do fine if +-- they are omitted for compilers that don't understand it. */ +--#if !defined __GNUC__ || __GNUC__ < 2 +-+/* GCC and clang have various useful declarations that can be made with +-+ the '__attribute__' syntax. All of the ways we use this do fine if +-+ they are omitted for compilers that don't understand it. */ +-+#if !(defined __GNUC__ || defined __clang__) +- # define __attribute__(xyz) /* Ignore */ +++#include ++ #ifndef UNDER_SYS_SIGLIST_DECLARED ++ extern char *_sys_siglist[]; ++ #endif +++int ++ main() ++ { ++ char *msg = (char *)_sys_siglist[2]; ++@@ -218,9 +224,11 @@ ++ #ifdef HAVE_UNISTD_H ++ #include ++ #endif +++#include ++ #if !HAVE_DECL_SYS_SIGLIST ++ extern char *sys_siglist[]; ++ #endif +++int ++ main() ++ { ++ char *msg = sys_siglist[2]; ++@@ -273,6 +281,8 @@ ++ [AC_TRY_RUN([ ++ #include ++ #include +++#include +++int ++ main() ++ { ++ int fd1, fd2, fl; ++@@ -335,6 +345,8 @@ ++ # include ++ # endif ++ #endif /* HAVE_DIRENT_H */ +++#include +++int ++ main() ++ { ++ DIR *dir; ++@@ -514,6 +526,8 @@ ++ #include ++ #include ++ #include +++#include +++int ++ main() ++ { ++ #ifdef HAVE_QUAD_T ++@@ -583,6 +597,7 @@ ++ #ifdef HAVE_UNISTD_H ++ # include + #endif +++#include ++ #ifndef __STDC__ ++ # ifndef const ++ # define const ++@@ -598,6 +613,7 @@ ++ { ++ return "42"; ++ } +++int ++ main() ++ { ++ char *s; ++@@ -786,7 +802,9 @@ ++ #include ++ #include ++ #include +++#include + +- /* At some point during the gcc 2.96 development the `malloc' attribute +- for functions was introduced. We don't want to use it unconditionally +- (although this would be possible) since it generates warnings. */ +--#if __GNUC_PREREQ (2,96) +-+#if __GNUC_PREREQ (2,96) || __glibc_has_attribute (__malloc__) +- # define __attribute_malloc__ __attribute__ ((__malloc__)) +- #else +- # define __attribute_malloc__ /* Ignore */ +-@@ -219,26 +294,41 @@ +- # define __attribute_alloc_size__(params) /* Ignore. */ +++int ++ main() ++ { ++ #if !defined (_POSIX_VERSION) || !defined (HAVE_POSIX_SIGNALS) ++@@ -835,7 +853,10 @@ ++ #if defined (HAVE_LOCALE_H) ++ #include + #endif +++#include +++#include + +-+/* Tell the compiler which argument to an allocation function +-+ indicates the alignment of the allocation. */ +-+#if __GNUC_PREREQ (4, 9) || __glibc_has_attribute (__alloc_align__) +-+# define __attribute_alloc_align__(param) \ +-+ __attribute__ ((__alloc_align__ param)) +-+#else +-+# define __attribute_alloc_align__(param) /* Ignore. */ +-+#endif +-+ +- /* At some point during the gcc 2.96 development the `pure' attribute +- for functions was introduced. We don't want to use it unconditionally +- (although this would be possible) since it generates warnings. */ +--#if __GNUC_PREREQ (2,96) +-+#if __GNUC_PREREQ (2,96) || __glibc_has_attribute (__pure__) +- # define __attribute_pure__ __attribute__ ((__pure__)) +- #else +- # define __attribute_pure__ /* Ignore */ +- #endif +++int ++ main(c, v) ++ int c; ++ char *v[]; ++@@ -881,6 +902,7 @@ ++ [AC_TRY_RUN([ ++ #include ++ #include +++#include + +- /* This declaration tells the compiler that the value is constant. */ +--#if __GNUC_PREREQ (2,5) +-+#if __GNUC_PREREQ (2,5) || __glibc_has_attribute (__const__) +- # define __attribute_const__ __attribute__ ((__const__)) +- #else +- # define __attribute_const__ /* Ignore */ ++ int ++ main() ++@@ -1241,6 +1263,8 @@ ++ #ifdef HAVE_UNISTD_H ++ # include + #endif +- +-+#if __GNUC_PREREQ (2,7) || __glibc_has_attribute (__unused__) +-+# define __attribute_maybe_unused__ __attribute__ ((__unused__)) +-+#else +-+# define __attribute_maybe_unused__ /* Ignore */ +-+#endif +-+ +- /* At some point during the gcc 3.1 development the `used' attribute +- for functions was introduced. We don't want to use it unconditionally +- (although this would be possible) since it generates warnings. */ +--#if __GNUC_PREREQ (3,1) +-+#if __GNUC_PREREQ (3,1) || __glibc_has_attribute (__used__) +- # define __attribute_used__ __attribute__ ((__used__)) +- # define __attribute_noinline__ __attribute__ ((__noinline__)) +- #else +-@@ -247,7 +337,7 @@ +++#include +++int ++ main() ++ { ++ # ifdef GETPGRP_VOID ++@@ -1305,6 +1329,7 @@ ++ #ifdef HAVE_UNISTD_H ++ #include + #endif +++#include + +- /* Since version 3.2, gcc allows marking deprecated functions. */ +--#if __GNUC_PREREQ (3,2) +-+#if __GNUC_PREREQ (3,2) || __glibc_has_attribute (__deprecated__) +- # define __attribute_deprecated__ __attribute__ ((__deprecated__)) +- #else +- # define __attribute_deprecated__ /* Ignore */ +-@@ -256,8 +346,8 @@ +- /* Since version 4.5, gcc also allows one to specify the message printed +- when a deprecated function is used. clang claims to be gcc 4.2, but +- may also support this feature. */ +--#if __GNUC_PREREQ (4,5) || \ +-- __glibc_clang_has_extension (__attribute_deprecated_with_message__) +-+#if __GNUC_PREREQ (4,5) \ +-+ || __glibc_has_extension (__attribute_deprecated_with_message__) +- # define __attribute_deprecated_msg__(msg) \ +- __attribute__ ((__deprecated__ (msg))) +- #else +-@@ -270,7 +360,7 @@ +- If several `format_arg' attributes are given for the same function, in +- gcc-3.0 and older, all but the last one are ignored. In newer gccs, +- all designated arguments are considered. */ +--#if __GNUC_PREREQ (2,8) +-+#if __GNUC_PREREQ (2,8) || __glibc_has_attribute (__format_arg__) +- # define __attribute_format_arg__(x) __attribute__ ((__format_arg__ (x))) +- #else +- # define __attribute_format_arg__(x) /* Ignore */ +-@@ -280,7 +370,7 @@ +- attribute for functions was introduced. We don't want to use it +- unconditionally (although this would be possible) since it +- generates warnings. */ +--#if __GNUC_PREREQ (2,97) +-+#if __GNUC_PREREQ (2,97) || __glibc_has_attribute (__format__) +- # define __attribute_format_strfmon__(a,b) \ +- __attribute__ ((__format__ (__strfmon__, a, b))) +- #else +-@@ -288,19 +378,33 @@ +- #endif ++ typedef RETSIGTYPE sigfunc(); + +- /* The nonnull function attribute marks pointer parameters that +-- must not be NULL. Do not define __nonnull if it is already defined, +-- for portability when this file is used in Gnulib. */ +-+ must not be NULL. This has the name __nonnull in glibc, +-+ and __attribute_nonnull__ in files shared with Gnulib to avoid +-+ collision with a different __nonnull in DragonFlyBSD 5.9. */ +-+#ifndef __attribute_nonnull__ +-+# if __GNUC_PREREQ (3,3) || __glibc_has_attribute (__nonnull__) +-+# define __attribute_nonnull__(params) __attribute__ ((__nonnull__ params)) +-+# else +-+# define __attribute_nonnull__(params) +-+# endif +-+#endif +- #ifndef __nonnull +--# if __GNUC_PREREQ (3,3) +--# define __nonnull(params) __attribute__ ((__nonnull__ params)) +-+# define __nonnull(params) __attribute_nonnull__ (params) +-+#endif +-+ +-+/* The returns_nonnull function attribute marks the return type of the function +-+ as always being non-null. */ +-+#ifndef __returns_nonnull +-+# if __GNUC_PREREQ (4, 9) || __glibc_has_attribute (__returns_nonnull__) +-+# define __returns_nonnull __attribute__ ((__returns_nonnull__)) +- # else +--# define __nonnull(params) +-+# define __returns_nonnull +- # endif +- #endif ++@@ -1335,6 +1360,7 @@ ++ nsigint++; ++ } + +- /* If fortification mode, we warn about unused results of certain +- function calls which can lead to problems. */ +--#if __GNUC_PREREQ (3,4) +-+#if __GNUC_PREREQ (3,4) || __glibc_has_attribute (__warn_unused_result__) +- # define __attribute_warn_unused_result__ \ +- __attribute__ ((__warn_unused_result__)) +- # if defined __USE_FORTIFY_LEVEL && __USE_FORTIFY_LEVEL > 0 +-@@ -314,7 +418,7 @@ +++int ++ main() ++ { ++ nsigint = 0; ++@@ -1418,8 +1444,11 @@ ++ #ifdef HAVE_UNISTD_H ++ #include + #endif +++#include +++#include + +- /* Forces a function to be always inlined. */ +--#if __GNUC_PREREQ (3,2) +-+#if __GNUC_PREREQ (3,2) || __glibc_has_attribute (__always_inline__) +- /* The Linux kernel defines __always_inline in stddef.h (283d7573), and +- it conflicts with this definition. Therefore undefine it first to +- allow either header to be included first. */ +-@@ -327,7 +431,7 @@ ++ /* Add more tests in here as appropriate. */ +++int ++ main() ++ { ++ int fd, err; ++@@ -1651,11 +1680,13 @@ ++ [AC_TRY_RUN([ ++ #include ++ #include +++#include + +- /* Associate error messages with the source location of the call site rather +- than with the source location inside the function. */ +--#if __GNUC_PREREQ (4,3) +-+#if __GNUC_PREREQ (4,3) || __glibc_has_attribute (__artificial__) +- # define __attribute_artificial__ __attribute__ ((__artificial__)) +- #else +- # define __attribute_artificial__ /* Ignore */ +-@@ -370,12 +474,14 @@ +- run in pedantic mode if the uses are carefully marked using the +- `__extension__' keyword. But this is not generally available before +- version 2.8. */ +--#if !__GNUC_PREREQ (2,8) +-+#if !(__GNUC_PREREQ (2,8) || defined __clang__) +- # define __extension__ /* Ignore */ ++ #ifndef NSIG ++ # define NSIG 64 + #endif + +--/* __restrict is known in EGCS 1.2 and above. */ +--#if !__GNUC_PREREQ (2,92) +-+/* __restrict is known in EGCS 1.2 and above, and in clang. +-+ It works also in C++ mode (outside of arrays), but only when spelled +-+ as '__restrict', not 'restrict'. */ +-+#if !(__GNUC_PREREQ (2,92) || __clang_major__ >= 3) +- # if defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L +- # define __restrict restrict +- # else +-@@ -385,8 +491,9 @@ +++int ++ main () ++ { ++ int n_sigs = 2 * NSIG; ++@@ -1770,6 +1801,7 @@ ++ #include ++ #include + +- /* ISO C99 also allows to declare arrays as non-overlapping. The syntax is +- array_name[restrict] +-- GCC 3.1 supports this. */ +--#if __GNUC_PREREQ (3,1) && !defined __GNUG__ +-+ GCC 3.1 and clang support this. +-+ This syntax is not usable in C++ mode. */ +-+#if (__GNUC_PREREQ (3,1) || __clang_major__ >= 3) && !defined __cplusplus +- # define __restrict_arr __restrict +- #else +- # ifdef __GNUC__ +-@@ -401,7 +508,7 @@ +- # endif +- #endif +++int ++ main(c, v) ++ int c; ++ char **v; ++@@ -1834,9 +1866,11 @@ ++ [AC_TRY_RUN([ ++ #include ++ #include +++#include + +--#if __GNUC__ >= 3 +-+#if (__GNUC__ >= 3) || __glibc_has_builtin (__builtin_expect) +- # define __glibc_unlikely(cond) __builtin_expect ((cond), 0) +- # define __glibc_likely(cond) __builtin_expect ((cond), 1) +- #else +-@@ -409,15 +516,10 @@ +- # define __glibc_likely(cond) (cond) +- #endif ++ extern int rl_gnu_readline_p; + +--#ifdef __has_attribute +--# define __glibc_has_attribute(attr) __has_attribute (attr) +--#else +--# define __glibc_has_attribute(attr) 0 +--#endif +-- +- #if (!defined _Noreturn \ +- && (defined __STDC_VERSION__ ? __STDC_VERSION__ : 0) < 201112 \ +-- && !__GNUC_PREREQ (4,7)) +-+ && !(__GNUC_PREREQ (4,7) \ +-+ || (3 < __clang_major__ + (5 <= __clang_minor__)))) +- # if __GNUC_PREREQ (2,8) +- # define _Noreturn __attribute__ ((__noreturn__)) +- # else +-@@ -434,22 +536,63 @@ +- # define __attribute_nonstring__ +++int ++ main() ++ { ++ FILE *fp; ++@@ -1926,7 +1960,9 @@ + #endif ++ #include ++ #include +++#include + +-+/* Undefine (also defined in libc-symbols.h). */ +-+#undef __attribute_copy__ +-+#if __GNUC_PREREQ (9, 0) +-+/* Copies attributes from the declaration or type referenced by +-+ the argument. */ +-+# define __attribute_copy__(arg) __attribute__ ((__copy__ (arg))) +-+#else +-+# define __attribute_copy__(arg) +-+#endif +-+ +- #if (!defined _Static_assert && !defined __cplusplus \ +- && (defined __STDC_VERSION__ ? __STDC_VERSION__ : 0) < 201112 \ +-- && (!__GNUC_PREREQ (4, 6) || defined __STRICT_ANSI__)) +-+ && (!(__GNUC_PREREQ (4, 6) || __clang_major__ >= 4) \ +-+ || defined __STRICT_ANSI__)) +- # define _Static_assert(expr, diagnostic) \ +- extern int (*__Static_assert_function (void)) \ +- [!!sizeof (struct { int __error_if_negative: (expr) ? 2 : -1; })] +- #endif +++int ++ main(c, v) ++ int c; ++ char *v[]; ++@@ -2657,7 +2693,7 @@ ++ [ ++ # Guess based on the CPU. ++ case "$host_cpu" in ++- alpha* | i[34567]86 | m68k | s390*) +++ w_64* | alpha* | i[34567]86 | m68k | s390*) ++ gt_cv_int_divbyzero_sigfpe="guessing yes";; ++ *) ++ gt_cv_int_divbyzero_sigfpe="guessing no";; ++@@ -4068,7 +4104,9 @@ ++ AC_CACHE_CHECK([for standard-conformant snprintf], [bash_cv_func_snprintf], ++ [AC_TRY_RUN([ ++ #include +++#include + +--/* The #ifndef lets Gnulib avoid including these on non-glibc +-- platforms, where the includes typically do not exist. */ +--#ifndef __WORDSIZE +-+/* Gnulib avoids including these, as they don't work on non-glibc or +-+ older glibc platforms. */ +-+#ifndef __GNULIB_CDEFS +- # include +- # include +- #endif +++int ++ main() ++ { ++ int n; ++@@ -4154,6 +4192,7 @@ + +--#if defined __LONG_DOUBLE_MATH_OPTIONAL && defined __NO_LONG_DOUBLE_MATH +-+#if __LDOUBLE_REDIRECTS_TO_FLOAT128_ABI == 1 +-+# ifdef __REDIRECT +-+ +-+/* Alias name defined automatically. */ +-+# define __LDBL_REDIR(name, proto) ... unused__ldbl_redir +-+# define __LDBL_REDIR_DECL(name) \ +-+ extern __typeof (name) name __asm (__ASMNAME ("__" #name "ieee128")); +-+ +-+/* Alias name defined automatically, with leading underscores. */ +-+# define __LDBL_REDIR2_DECL(name) \ +-+ extern __typeof (__##name) __##name \ +-+ __asm (__ASMNAME ("__" #name "ieee128")); ++ #include ++ +++int ++ main(c, v) ++ int c; ++ char **v; ++diff -Nuar gdb-10.2/readline/readline/aclocal.m4.orig gdb-10.2/readline/readline/aclocal.m4.orig ++--- gdb-10.2/readline/readline/aclocal.m4.orig 1970-01-01 08:00:00.000000000 +0800 +++++ gdb-10.2/readline/readline/aclocal.m4.orig 2025-04-16 17:06:41.942086800 +0800 ++@@ -0,0 +1,4301 @@ +++nl +++dnl Bash specific tests +++dnl +++dnl Some derived from PDKSH 5.1.3 autoconf tests +++dnl + + +-+/* Alias name defined manually. */ +-+# define __LDBL_REDIR1(name, proto, alias) ... unused__ldbl_redir1 +-+# define __LDBL_REDIR1_DECL(name, alias) \ +-+ extern __typeof (name) name __asm (__ASMNAME (#alias)); +++AC_DEFUN(BASH_C_LONG_LONG, +++[AC_CACHE_CHECK(for long long, ac_cv_c_long_long, +++[if test "$GCC" = yes; then +++ ac_cv_c_long_long=yes +++else +++AC_TRY_RUN([ +++#include +++int +++main() +++{ +++long long foo = 0; +++exit(sizeof(long long) < sizeof(long)); +++} +++], ac_cv_c_long_long=yes, ac_cv_c_long_long=no) +++fi]) +++if test $ac_cv_c_long_long = yes; then +++ AC_DEFINE(HAVE_LONG_LONG, 1, [Define if the `long long' type works.]) +++fi +++]) + + +-+# define __LDBL_REDIR1_NTH(name, proto, alias) \ +-+ __REDIRECT_NTH (name, proto, alias) +-+# define __REDIRECT_NTH_LDBL(name, proto, alias) \ +-+ __LDBL_REDIR1_NTH (name, proto, __##alias##ieee128) +++dnl +++dnl This is very similar to AC_C_LONG_DOUBLE, with the fix for IRIX +++dnl (< changed to <=) added. +++dnl +++AC_DEFUN(BASH_C_LONG_DOUBLE, +++[AC_CACHE_CHECK(for long double, ac_cv_c_long_double, +++[if test "$GCC" = yes; then +++ ac_cv_c_long_double=yes +++else +++AC_TRY_RUN([ +++#include +++int +++main() +++{ +++ /* The Stardent Vistra knows sizeof(long double), but does not +++ support it. */ +++ long double foo = 0.0; +++ /* On Ultrix 4.3 cc, long double is 4 and double is 8. */ +++ /* On IRIX 5.3, the compiler converts long double to double with a warning, +++ but compiles this successfully. */ +++ exit(sizeof(long double) <= sizeof(double)); +++} +++], ac_cv_c_long_double=yes, ac_cv_c_long_double=no) +++fi]) +++if test $ac_cv_c_long_double = yes; then +++ AC_DEFINE(HAVE_LONG_DOUBLE, 1, [Define if the `long double' type works.]) +++fi +++]) + + +-+/* Unused. */ +-+# define __REDIRECT_LDBL(name, proto, alias) ... unused__redirect_ldbl +-+# define __LDBL_REDIR_NTH(name, proto) ... unused__ldbl_redir_nth +++dnl +++dnl Check for . This is separated out so that it can be +++dnl AC_REQUIREd. +++dnl +++dnl BASH_HEADER_INTTYPES +++AC_DEFUN(BASH_HEADER_INTTYPES, +++[ +++ AC_CHECK_HEADERS(inttypes.h) +++]) + + +-+# else +-+_Static_assert (0, "IEEE 128-bits long double requires redirection on this platform"); +-+# endif +-+#elif defined __LONG_DOUBLE_MATH_OPTIONAL && defined __NO_LONG_DOUBLE_MATH +- # define __LDBL_COMPAT 1 +- # ifdef __REDIRECT +- # define __LDBL_REDIR1(name, proto, alias) __REDIRECT (name, proto, alias) +-@@ -458,6 +601,8 @@ +- # define __LDBL_REDIR1_NTH(name, proto, alias) __REDIRECT_NTH (name, proto, alias) +- # define __LDBL_REDIR_NTH(name, proto) \ +- __LDBL_REDIR1_NTH (name, proto, __nldbl_##name) +-+# define __LDBL_REDIR2_DECL(name) \ +-+ extern __typeof (__##name) __##name __asm (__ASMNAME ("__nldbl___" #name)); +- # define __LDBL_REDIR1_DECL(name, alias) \ +- extern __typeof (name) name __asm (__ASMNAME (#alias)); +- # define __LDBL_REDIR_DECL(name) \ +-@@ -468,11 +613,13 @@ +- __LDBL_REDIR1_NTH (name, proto, __nldbl_##alias) +- # endif +- #endif +--#if !defined __LDBL_COMPAT || !defined __REDIRECT +-+#if (!defined __LDBL_COMPAT && __LDOUBLE_REDIRECTS_TO_FLOAT128_ABI == 0) \ +-+ || !defined __REDIRECT +- # define __LDBL_REDIR1(name, proto, alias) name proto +- # define __LDBL_REDIR(name, proto) name proto +- # define __LDBL_REDIR1_NTH(name, proto, alias) name proto __THROW +- # define __LDBL_REDIR_NTH(name, proto) name proto __THROW +-+# define __LDBL_REDIR2_DECL(name) +- # define __LDBL_REDIR_DECL(name) +- # ifdef __REDIRECT +- # define __REDIRECT_LDBL(name, proto, alias) __REDIRECT (name, proto, alias) +-@@ -503,7 +650,7 @@ +- check is required to enable the use of generic selection. */ +- #if !defined __cplusplus \ +- && (__GNUC_PREREQ (4, 9) \ +-- || __glibc_clang_has_extension (c_generic_selections) \ +-+ || __glibc_has_extension (c_generic_selections) \ +- || (!defined __GNUC__ && defined __STDC_VERSION__ \ +- && __STDC_VERSION__ >= 201112L)) +- # define __HAVE_GENERIC_SELECTION 1 +-@@ -511,4 +658,50 @@ +- # define __HAVE_GENERIC_SELECTION 0 +- #endif +- +-+#if __GNUC_PREREQ (10, 0) +-+/* Designates a 1-based positional argument ref-index of pointer type +-+ that can be used to access size-index elements of the pointed-to +-+ array according to access mode, or at least one element when +-+ size-index is not provided: +-+ access (access-mode, [, ]) */ +-+# define __attr_access(x) __attribute__ ((__access__ x)) +-+/* For _FORTIFY_SOURCE == 3 we use __builtin_dynamic_object_size, which may +-+ use the access attribute to get object sizes from function definition +-+ arguments, so we can't use them on functions we fortify. Drop the object +-+ size hints for such functions. */ +-+# if __USE_FORTIFY_LEVEL == 3 +-+# define __fortified_attr_access(a, o, s) __attribute__ ((__access__ (a, o))) +-+# else +-+# define __fortified_attr_access(a, o, s) __attr_access ((a, o, s)) +-+# endif +-+# if __GNUC_PREREQ (11, 0) +-+# define __attr_access_none(argno) __attribute__ ((__access__ (__none__, argno))) +-+# else +-+# define __attr_access_none(argno) +-+# endif +-+#else +-+# define __fortified_attr_access(a, o, s) +-+# define __attr_access(x) +-+# define __attr_access_none(argno) +++dnl +++dnl check for typedef'd symbols in header files, but allow the caller to +++dnl specify the include files to be checked in addition to the default +++dnl +++dnl BASH_CHECK_TYPE(TYPE, HEADERS, DEFAULT[, VALUE-IF-FOUND]) +++AC_DEFUN(BASH_CHECK_TYPE, +++[ +++AC_REQUIRE([AC_HEADER_STDC])dnl +++AC_REQUIRE([BASH_HEADER_INTTYPES]) +++AC_MSG_CHECKING(for $1) +++AC_CACHE_VAL(bash_cv_type_$1, +++[AC_EGREP_CPP($1, [#include +++#if STDC_HEADERS +++#include +++#include +++#endif +++#if HAVE_INTTYPES_H +++#include + +#endif +++#if HAVE_STDINT_H +++#include +++#endif +++$2 +++], bash_cv_type_$1=yes, bash_cv_type_$1=no)]) +++AC_MSG_RESULT($bash_cv_type_$1) +++ifelse($#, 4, [if test $bash_cv_type_$1 = yes; then +++ AC_DEFINE($4) +++ fi]) +++if test $bash_cv_type_$1 = no; then +++ AC_DEFINE_UNQUOTED($1, $3) +++fi +++]) + + +-+#if __GNUC_PREREQ (11, 0) +-+/* Designates dealloc as a function to call to deallocate objects +-+ allocated by the declared function. */ +-+# define __attr_dealloc(dealloc, argno) \ +-+ __attribute__ ((__malloc__ (dealloc, argno))) +-+# define __attr_dealloc_free __attr_dealloc (__builtin_free, 1) +-+#else +-+# define __attr_dealloc(dealloc, argno) +-+# define __attr_dealloc_free +++dnl +++dnl BASH_CHECK_DECL(FUNC) +++dnl +++dnl Check for a declaration of FUNC in stdlib.h and inttypes.h like +++dnl AC_CHECK_DECL +++dnl +++AC_DEFUN(BASH_CHECK_DECL, +++[ +++AC_REQUIRE([AC_HEADER_STDC]) +++AC_REQUIRE([BASH_HEADER_INTTYPES]) +++AC_CACHE_CHECK([for declaration of $1], bash_cv_decl_$1, +++[AC_TRY_LINK( +++[ +++#if STDC_HEADERS +++# include + +#endif +++#if HAVE_INTTYPES_H +++# include +++#endif +++], +++[return !$1;], +++bash_cv_decl_$1=yes, bash_cv_decl_$1=no)]) +++bash_tr_func=HAVE_DECL_`echo $1 | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'` +++if test $bash_cv_decl_$1 = yes; then +++ AC_DEFINE_UNQUOTED($bash_tr_func, 1) +++else +++ AC_DEFINE_UNQUOTED($bash_tr_func, 0) +++fi +++]) + + +-+/* Specify that a function such as setjmp or vfork may return +-+ twice. */ +-+#if __GNUC_PREREQ (4, 1) +-+# define __attribute_returns_twice__ __attribute__ ((__returns_twice__)) +++AC_DEFUN(BASH_DECL_PRINTF, +++[AC_MSG_CHECKING(for declaration of printf in ) +++AC_CACHE_VAL(bash_cv_printf_declared, +++[AC_TRY_RUN([ +++#include +++#ifdef __STDC__ +++typedef int (*_bashfunc)(const char *, ...); + +#else +-+# define __attribute_returns_twice__ /* Ignore. */ +++typedef int (*_bashfunc)(); + +#endif +-+ +- #endif /* sys/cdefs.h */ +---- gdb-10.2/gnulib/import/libc-config.h.orig +-+++ gdb-10.2/gnulib/import/libc-config.h +-@@ -79,13 +79,9 @@ +- #ifndef _FEATURES_H +- # define _FEATURES_H 1 +- #endif +--/* Define __WORDSIZE so that does not attempt to include +-- nonexistent files. Make it a syntax error, since Gnulib does not +-- use __WORDSIZE now, and if Gnulib uses it later the syntax error +-- will let us know that __WORDSIZE needs configuring. */ +--#ifndef __WORDSIZE +--# define __WORDSIZE %%% +--#endif +-+/* Define __GNULIB_CDEFS so that does not attempt to include +-+ nonexistent files. */ +-+# define __GNULIB_CDEFS +- /* Undef the macros unconditionally defined by our copy of glibc +- , so that they do not clash with any system-defined +- versions. */ +---- gdb-10.2/libiberty/aclocal.m4.orig +-+++ gdb-10.2/libiberty/aclocal.m4 +-@@ -16,6 +16,8 @@ AC_CACHE_CHECK([for working strncmp], ac +- [AC_TRY_RUN([ +- /* Test by Jim Wilson and Kaveh Ghazi. +- Check whether strncmp reads past the end of its string parameters. */ + +#include +-+#include +- #include +- +- #ifdef HAVE_FCNTL_H +-@@ -43,7 +45,8 @@ AC_CACHE_CHECK([for working strncmp], ac +- +- #define MAP_LEN 0x10000 +- +--main () + +int +-+main (void) +- { +- #if defined(HAVE_MMAP) || defined(HAVE_MMAP_ANYWHERE) +- char *p; +-@@ -149,7 +152,10 @@ if test $ac_cv_os_cray = yes; then +- fi +- +- AC_CACHE_CHECK(stack direction for C alloca, ac_cv_c_stack_direction, +--[AC_TRY_RUN([find_stack_direction () +-+[AC_TRY_RUN([#include +++main() +++{ +++_bashfunc pf; +++pf = (_bashfunc) printf; +++exit(pf == 0); +++} +++], bash_cv_printf_declared=yes, bash_cv_printf_declared=no, +++ [AC_MSG_WARN(cannot check printf declaration if cross compiling -- defaulting to yes) +++ bash_cv_printf_declared=yes] +++)]) +++AC_MSG_RESULT($bash_cv_printf_declared) +++if test $bash_cv_printf_declared = yes; then +++AC_DEFINE(PRINTF_DECLARED) +++fi +++]) +++ +++AC_DEFUN(BASH_DECL_SBRK, +++[AC_MSG_CHECKING(for declaration of sbrk in ) +++AC_CACHE_VAL(bash_cv_sbrk_declared, +++[AC_EGREP_HEADER(sbrk, unistd.h, +++ bash_cv_sbrk_declared=yes, bash_cv_sbrk_declared=no)]) +++AC_MSG_RESULT($bash_cv_sbrk_declared) +++if test $bash_cv_sbrk_declared = yes; then +++AC_DEFINE(SBRK_DECLARED) +++fi +++]) +++ +++dnl +++dnl Check for sys_siglist[] or _sys_siglist[] +++dnl +++AC_DEFUN(BASH_DECL_UNDER_SYS_SIGLIST, +++[AC_MSG_CHECKING([for _sys_siglist in signal.h or unistd.h]) +++AC_CACHE_VAL(bash_cv_decl_under_sys_siglist, +++[AC_TRY_COMPILE([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif], [ char *msg = _sys_siglist[2]; ], +++ bash_cv_decl_under_sys_siglist=yes, bash_cv_decl_under_sys_siglist=no, +++ [AC_MSG_WARN(cannot check for _sys_siglist[] if cross compiling -- defaulting to no)])])dnl +++AC_MSG_RESULT($bash_cv_decl_under_sys_siglist) +++if test $bash_cv_decl_under_sys_siglist = yes; then +++AC_DEFINE(UNDER_SYS_SIGLIST_DECLARED) +++fi +++]) + + +++AC_DEFUN(BASH_UNDER_SYS_SIGLIST, +++[AC_REQUIRE([BASH_DECL_UNDER_SYS_SIGLIST]) +++AC_MSG_CHECKING([for _sys_siglist in system C library]) +++AC_CACHE_VAL(bash_cv_under_sys_siglist, +++[AC_TRY_RUN([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include +++#ifndef UNDER_SYS_SIGLIST_DECLARED +++extern char *_sys_siglist[]; +++#endif + +int +-+find_stack_direction (void) +- { +- static char *addr = 0; +- auto char dummy; +-@@ -161,7 +167,9 @@ AC_CACHE_CHECK(stack direction for C all +- else +- return (&dummy > addr) ? 1 : -1; +- } +--main () +++main() +++{ +++char *msg = (char *)_sys_siglist[2]; +++exit(msg == 0); +++}], +++ bash_cv_under_sys_siglist=yes, bash_cv_under_sys_siglist=no, +++ [AC_MSG_WARN(cannot check for _sys_siglist[] if cross compiling -- defaulting to no) +++ bash_cv_under_sys_siglist=no])]) +++AC_MSG_RESULT($bash_cv_under_sys_siglist) +++if test $bash_cv_under_sys_siglist = yes; then +++AC_DEFINE(HAVE_UNDER_SYS_SIGLIST) +++fi +++]) + + +++AC_DEFUN(BASH_SYS_SIGLIST, +++[AC_REQUIRE([AC_DECL_SYS_SIGLIST]) +++AC_MSG_CHECKING([for sys_siglist in system C library]) +++AC_CACHE_VAL(bash_cv_sys_siglist, +++[AC_TRY_RUN([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include +++#if !HAVE_DECL_SYS_SIGLIST +++extern char *sys_siglist[]; +++#endif + +int +-+main (void) +- { +- exit (find_stack_direction() < 0); +- }], +---- gdb-10.2/libiberty/configure.orig +-+++ gdb-10.2/libiberty/configure +-@@ -6724,7 +6724,10 @@ else +- else +- cat confdefs.h - <<_ACEOF >conftest.$ac_ext +- /* end confdefs.h. */ +--find_stack_direction () +++main() +++{ +++char *msg = sys_siglist[2]; +++exit(msg == 0); +++}], +++ bash_cv_sys_siglist=yes, bash_cv_sys_siglist=no, +++ [AC_MSG_WARN(cannot check for sys_siglist if cross compiling -- defaulting to no) +++ bash_cv_sys_siglist=no])]) +++AC_MSG_RESULT($bash_cv_sys_siglist) +++if test $bash_cv_sys_siglist = yes; then +++AC_DEFINE(HAVE_SYS_SIGLIST) +++fi +++]) +++ +++dnl Check for the various permutations of sys_siglist and make sure we +++dnl compile in siglist.o if they're not defined +++AC_DEFUN(BASH_CHECK_SYS_SIGLIST, [ +++AC_REQUIRE([BASH_SYS_SIGLIST]) +++AC_REQUIRE([BASH_DECL_UNDER_SYS_SIGLIST]) +++AC_REQUIRE([BASH_FUNC_STRSIGNAL]) +++if test "$bash_cv_sys_siglist" = no && test "$bash_cv_under_sys_siglist" = no && test "$bash_cv_have_strsignal" = no; then +++ SIGLIST_O=siglist.o +++else +++ SIGLIST_O= +++fi +++AC_SUBST([SIGLIST_O]) +++]) +++ +++dnl Check for sys_errlist[] and sys_nerr, check for declaration +++AC_DEFUN(BASH_SYS_ERRLIST, +++[AC_MSG_CHECKING([for sys_errlist and sys_nerr]) +++AC_CACHE_VAL(bash_cv_sys_errlist, +++[AC_TRY_LINK([#include ], +++[extern char *sys_errlist[]; +++ extern int sys_nerr; +++ char *msg = sys_errlist[sys_nerr - 1];], +++ bash_cv_sys_errlist=yes, bash_cv_sys_errlist=no)])dnl +++AC_MSG_RESULT($bash_cv_sys_errlist) +++if test $bash_cv_sys_errlist = yes; then +++AC_DEFINE(HAVE_SYS_ERRLIST) +++fi +++]) +++ +++dnl +++dnl Check if dup2() does not clear the close on exec flag +++dnl +++AC_DEFUN(BASH_FUNC_DUP2_CLOEXEC_CHECK, +++[AC_MSG_CHECKING(if dup2 fails to clear the close-on-exec flag) +++AC_CACHE_VAL(bash_cv_dup2_broken, +++[AC_TRY_RUN([ +++#include +++#include + +#include +++int +++main() +++{ +++ int fd1, fd2, fl; +++ fd1 = open("/dev/null", 2); +++ if (fcntl(fd1, 2, 1) < 0) +++ exit(1); +++ fd2 = dup2(fd1, 1); +++ if (fd2 < 0) +++ exit(2); +++ fl = fcntl(fd2, 1, 0); +++ /* fl will be 1 if dup2 did not reset the close-on-exec flag. */ +++ exit(fl != 1); +++} +++], bash_cv_dup2_broken=yes, bash_cv_dup2_broken=no, +++ [AC_MSG_WARN(cannot check dup2 if cross compiling -- defaulting to no) +++ bash_cv_dup2_broken=no]) +++]) +++AC_MSG_RESULT($bash_cv_dup2_broken) +++if test $bash_cv_dup2_broken = yes; then +++AC_DEFINE(DUP2_BROKEN) +++fi +++]) + + +++AC_DEFUN(BASH_FUNC_STRSIGNAL, +++[AC_MSG_CHECKING([for the existence of strsignal]) +++AC_CACHE_VAL(bash_cv_have_strsignal, +++[AC_TRY_LINK([#include +++#include ], +++[char *s = (char *)strsignal(2);], +++ bash_cv_have_strsignal=yes, bash_cv_have_strsignal=no)]) +++AC_MSG_RESULT($bash_cv_have_strsignal) +++if test $bash_cv_have_strsignal = yes; then +++AC_DEFINE(HAVE_STRSIGNAL) +++fi +++]) +++ +++dnl Check to see if opendir will open non-directories (not a nice thing) +++AC_DEFUN(BASH_FUNC_OPENDIR_CHECK, +++[AC_REQUIRE([AC_HEADER_DIRENT])dnl +++AC_MSG_CHECKING(if opendir() opens non-directories) +++AC_CACHE_VAL(bash_cv_opendir_not_robust, +++[AC_TRY_RUN([ +++#include +++#include +++#include +++#ifdef HAVE_UNISTD_H +++# include +++#endif /* HAVE_UNISTD_H */ +++#if defined(HAVE_DIRENT_H) +++# include +++#else +++# define dirent direct +++# ifdef HAVE_SYS_NDIR_H +++# include +++# endif /* SYSNDIR */ +++# ifdef HAVE_SYS_DIR_H +++# include +++# endif /* SYSDIR */ +++# ifdef HAVE_NDIR_H +++# include +++# endif +++#endif /* HAVE_DIRENT_H */ +++#include + +int +-+find_stack_direction (void) +- { +- static char *addr = 0; +- auto char dummy; +-@@ -6736,7 +6739,9 @@ find_stack_direction () +- else +- return (&dummy > addr) ? 1 : -1; +- } +--main () +++main() +++{ +++DIR *dir; +++int fd, err; +++err = mkdir("bash-aclocal", 0700); +++if (err < 0) { +++ perror("mkdir"); +++ exit(1); +++} +++unlink("bash-aclocal/not_a_directory"); +++fd = open("bash-aclocal/not_a_directory", O_WRONLY|O_CREAT|O_EXCL, 0666); +++write(fd, "\n", 1); +++close(fd); +++dir = opendir("bash-aclocal/not_a_directory"); +++unlink("bash-aclocal/not_a_directory"); +++rmdir("bash-aclocal"); +++exit (dir == 0); +++}], bash_cv_opendir_not_robust=yes,bash_cv_opendir_not_robust=no, +++ [AC_MSG_WARN(cannot check opendir if cross compiling -- defaulting to no) +++ bash_cv_opendir_not_robust=no] +++)]) +++AC_MSG_RESULT($bash_cv_opendir_not_robust) +++if test $bash_cv_opendir_not_robust = yes; then +++AC_DEFINE(OPENDIR_NOT_ROBUST) +++fi +++]) +++ +++dnl +++AC_DEFUN(BASH_TYPE_SIGHANDLER, +++[AC_MSG_CHECKING([whether signal handlers are of type void]) +++AC_CACHE_VAL(bash_cv_void_sighandler, +++[AC_TRY_COMPILE([#include +++#include +++#ifdef signal +++#undef signal +++#endif +++#ifdef __cplusplus +++extern "C" +++#endif +++void (*signal ()) ();], +++[int i;], bash_cv_void_sighandler=yes, bash_cv_void_sighandler=no)])dnl +++AC_MSG_RESULT($bash_cv_void_sighandler) +++if test $bash_cv_void_sighandler = yes; then +++AC_DEFINE(VOID_SIGHANDLER) +++fi +++]) +++ +++dnl +++dnl A signed 16-bit integer quantity +++dnl +++AC_DEFUN(BASH_TYPE_BITS16_T, +++[ +++if test "$ac_cv_sizeof_short" = 2; then +++ AC_CHECK_TYPE(bits16_t, short) +++elif test "$ac_cv_sizeof_char" = 2; then +++ AC_CHECK_TYPE(bits16_t, char) +++else +++ AC_CHECK_TYPE(bits16_t, short) +++fi +++]) +++ +++dnl +++dnl An unsigned 16-bit integer quantity +++dnl +++AC_DEFUN(BASH_TYPE_U_BITS16_T, +++[ +++if test "$ac_cv_sizeof_short" = 2; then +++ AC_CHECK_TYPE(u_bits16_t, unsigned short) +++elif test "$ac_cv_sizeof_char" = 2; then +++ AC_CHECK_TYPE(u_bits16_t, unsigned char) +++else +++ AC_CHECK_TYPE(u_bits16_t, unsigned short) +++fi +++]) +++ +++dnl +++dnl A signed 32-bit integer quantity +++dnl +++AC_DEFUN(BASH_TYPE_BITS32_T, +++[ +++if test "$ac_cv_sizeof_int" = 4; then +++ AC_CHECK_TYPE(bits32_t, int) +++elif test "$ac_cv_sizeof_long" = 4; then +++ AC_CHECK_TYPE(bits32_t, long) +++else +++ AC_CHECK_TYPE(bits32_t, int) +++fi +++]) +++ +++dnl +++dnl An unsigned 32-bit integer quantity +++dnl +++AC_DEFUN(BASH_TYPE_U_BITS32_T, +++[ +++if test "$ac_cv_sizeof_int" = 4; then +++ AC_CHECK_TYPE(u_bits32_t, unsigned int) +++elif test "$ac_cv_sizeof_long" = 4; then +++ AC_CHECK_TYPE(u_bits32_t, unsigned long) +++else +++ AC_CHECK_TYPE(u_bits32_t, unsigned int) +++fi +++]) + + +++AC_DEFUN(BASH_TYPE_PTRDIFF_T, +++[ +++if test "$ac_cv_sizeof_int" = "$ac_cv_sizeof_char_p"; then +++ AC_CHECK_TYPE(ptrdiff_t, int) +++elif test "$ac_cv_sizeof_long" = "$ac_cv_sizeof_char_p"; then +++ AC_CHECK_TYPE(ptrdiff_t, long) +++elif test "$ac_cv_type_long_long" = yes && test "$ac_cv_sizeof_long_long" = "$ac_cv_sizeof_char_p"; then +++ AC_CHECK_TYPE(ptrdiff_t, [long long]) +++else +++ AC_CHECK_TYPE(ptrdiff_t, int) +++fi +++]) +++ +++dnl +++dnl A signed 64-bit quantity +++dnl +++AC_DEFUN(BASH_TYPE_BITS64_T, +++[ +++if test "$ac_cv_sizeof_char_p" = 8; then +++ AC_CHECK_TYPE(bits64_t, char *) +++elif test "$ac_cv_sizeof_double" = 8; then +++ AC_CHECK_TYPE(bits64_t, double) +++elif test -n "$ac_cv_type_long_long" && test "$ac_cv_sizeof_long_long" = 8; then +++ AC_CHECK_TYPE(bits64_t, [long long]) +++elif test "$ac_cv_sizeof_long" = 8; then +++ AC_CHECK_TYPE(bits64_t, long) +++else +++ AC_CHECK_TYPE(bits64_t, double) +++fi +++]) +++ +++AC_DEFUN(BASH_TYPE_LONG_LONG, +++[ +++AC_CACHE_CHECK([for long long], bash_cv_type_long_long, +++[AC_TRY_LINK([ +++long long ll = 1; int i = 63;], +++[ +++long long llm = (long long) -1; +++return ll << i | ll >> i | llm / ll | llm % ll; +++], bash_cv_type_long_long='long long', bash_cv_type_long_long='long')]) +++if test "$bash_cv_type_long_long" = 'long long'; then +++ AC_DEFINE(HAVE_LONG_LONG, 1) +++fi +++]) +++ +++AC_DEFUN(BASH_TYPE_UNSIGNED_LONG_LONG, +++[ +++AC_CACHE_CHECK([for unsigned long long], bash_cv_type_unsigned_long_long, +++[AC_TRY_LINK([ +++unsigned long long ull = 1; int i = 63;], +++[ +++unsigned long long ullmax = (unsigned long long) -1; +++return ull << i | ull >> i | ullmax / ull | ullmax % ull; +++], bash_cv_type_unsigned_long_long='unsigned long long', +++ bash_cv_type_unsigned_long_long='unsigned long')]) +++if test "$bash_cv_type_unsigned_long_long" = 'unsigned long long'; then +++ AC_DEFINE(HAVE_UNSIGNED_LONG_LONG, 1) +++fi +++]) +++ +++dnl +++dnl Type of struct rlimit fields: some systems (OSF/1, NetBSD, RISC/os 5.0) +++dnl have a rlim_t, others (4.4BSD based systems) use quad_t, others use +++dnl long and still others use int (HP-UX 9.01, SunOS 4.1.3). To simplify +++dnl matters, this just checks for rlim_t, quad_t, or long. +++dnl +++AC_DEFUN(BASH_TYPE_RLIMIT, +++[AC_MSG_CHECKING(for size and type of struct rlimit fields) +++AC_CACHE_VAL(bash_cv_type_rlimit, +++[AC_TRY_COMPILE([#include +++#include ], +++[rlim_t xxx;], bash_cv_type_rlimit=rlim_t,[ +++AC_TRY_RUN([ +++#include +++#include +++#include +++#include + +int +-+main (void) +- { +- exit (find_stack_direction() < 0); +- } +-@@ -7557,6 +7562,8 @@ else +- +- /* Test by Jim Wilson and Kaveh Ghazi. +- Check whether strncmp reads past the end of its string parameters. */ +++main() +++{ +++#ifdef HAVE_QUAD_T +++ struct rlimit rl; +++ if (sizeof(rl.rlim_cur) == sizeof(quad_t)) +++ exit(0); +++#endif +++ exit(1); +++}], bash_cv_type_rlimit=quad_t, bash_cv_type_rlimit=long, +++ [AC_MSG_WARN(cannot check quad_t if cross compiling -- defaulting to long) +++ bash_cv_type_rlimit=long])]) +++]) +++AC_MSG_RESULT($bash_cv_type_rlimit) +++if test $bash_cv_type_rlimit = quad_t; then +++AC_DEFINE(RLIMTYPE, quad_t) +++elif test $bash_cv_type_rlimit = rlim_t; then +++AC_DEFINE(RLIMTYPE, rlim_t) +++fi +++]) +++ +++AC_DEFUN(BASH_TYPE_SIG_ATOMIC_T, +++[AC_CACHE_CHECK([for sig_atomic_t in signal.h], ac_cv_have_sig_atomic_t, +++[AC_TRY_LINK([ +++#include +++],[ sig_atomic_t x; ], +++ac_cv_have_sig_atomic_t=yes, ac_cv_have_sig_atomic_t=no)]) +++if test "$ac_cv_have_sig_atomic_t" = "no" +++then +++ AC_CHECK_TYPE(sig_atomic_t,int) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_LSTAT, +++[dnl Cannot use AC_CHECK_FUNCS(lstat) because Linux defines lstat() as an +++dnl inline function in . +++AC_CACHE_CHECK([for lstat], bash_cv_func_lstat, +++[AC_TRY_LINK([ +++#include +++#include +++],[ lstat(".",(struct stat *)0); ], +++bash_cv_func_lstat=yes, bash_cv_func_lstat=no)]) +++if test $bash_cv_func_lstat = yes; then +++ AC_DEFINE(HAVE_LSTAT) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_INET_ATON, +++[ +++AC_CACHE_CHECK([for inet_aton], bash_cv_func_inet_aton, +++[AC_TRY_LINK([ +++#include +++#include +++#include +++struct in_addr ap;], [ inet_aton("127.0.0.1", &ap); ], +++bash_cv_func_inet_aton=yes, bash_cv_func_inet_aton=no)]) +++if test $bash_cv_func_inet_aton = yes; then +++ AC_DEFINE(HAVE_INET_ATON) +++else +++ AC_LIBOBJ(inet_aton) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_GETENV, +++[AC_MSG_CHECKING(to see if getenv can be redefined) +++AC_CACHE_VAL(bash_cv_getenv_redef, +++[AC_TRY_RUN([ +++#ifdef HAVE_UNISTD_H +++# include +++#endif + +#include +-+#include +- #include +- +- #ifdef HAVE_FCNTL_H +-@@ -7584,7 +7591,8 @@ else +- +- #define MAP_LEN 0x10000 +- +--main () +++#ifndef __STDC__ +++# ifndef const +++# define const +++# endif +++#endif +++char * +++getenv (name) +++#if defined (__linux__) || defined (__bsdi__) || defined (convex) +++ const char *name; +++#else +++ char const *name; +++#endif /* !__linux__ && !__bsdi__ && !convex */ +++{ +++return "42"; +++} + +int +-+main (void) +- { +- #if defined(HAVE_MMAP) || defined(HAVE_MMAP_ANYWHERE) +- char *p; +---- gdb-10.2/readline/readline/aclocal.m4.orig +-+++ gdb-10.2/readline/readline/aclocal.m4 +-@@ -10,6 +10,7 @@ AC_DEFUN(BASH_C_LONG_LONG, +- ac_cv_c_long_long=yes +- else +- AC_TRY_RUN([ +++main() +++{ +++char *s; +++/* The next allows this program to run, but does not allow bash to link +++ when it redefines getenv. I'm not really interested in figuring out +++ why not. */ +++#if defined (NeXT) +++exit(1); +++#endif +++s = getenv("ABCDE"); +++exit(s == 0); /* force optimizer to leave getenv in */ +++} +++], bash_cv_getenv_redef=yes, bash_cv_getenv_redef=no, +++ [AC_MSG_WARN(cannot check getenv redefinition if cross compiling -- defaulting to yes) +++ bash_cv_getenv_redef=yes] +++)]) +++AC_MSG_RESULT($bash_cv_getenv_redef) +++if test $bash_cv_getenv_redef = yes; then +++AC_DEFINE(CAN_REDEFINE_GETENV) +++fi +++]) +++ +++# We should check for putenv before calling this +++AC_DEFUN(BASH_FUNC_STD_PUTENV, +++[ +++AC_REQUIRE([AC_HEADER_STDC]) +++AC_REQUIRE([AC_C_PROTOTYPES]) +++AC_CACHE_CHECK([for standard-conformant putenv declaration], bash_cv_std_putenv, +++[AC_TRY_LINK([ +++#if STDC_HEADERS + +#include +- int +- main() +- { +-@@ -33,6 +34,7 @@ AC_DEFUN(BASH_C_LONG_DOUBLE, +- ac_cv_c_long_double=yes +- else +- AC_TRY_RUN([ +++#include +++#endif +++#ifndef __STDC__ +++# ifndef const +++# define const +++# endif +++#endif +++#ifdef PROTOTYPES +++extern int putenv (char *); +++#else +++extern int putenv (); +++#endif +++], +++[return (putenv == 0);], +++bash_cv_std_putenv=yes, bash_cv_std_putenv=no +++)]) +++if test $bash_cv_std_putenv = yes; then +++AC_DEFINE(HAVE_STD_PUTENV) +++fi +++]) +++ +++# We should check for unsetenv before calling this +++AC_DEFUN(BASH_FUNC_STD_UNSETENV, +++[ +++AC_REQUIRE([AC_HEADER_STDC]) +++AC_REQUIRE([AC_C_PROTOTYPES]) +++AC_CACHE_CHECK([for standard-conformant unsetenv declaration], bash_cv_std_unsetenv, +++[AC_TRY_LINK([ +++#if STDC_HEADERS + +#include +- int +- main() +- { +-@@ -134,6 +136,8 @@ typedef int (*_bashfunc)(const char *, . +- #else +- typedef int (*_bashfunc)(); +- #endif +++#include +++#endif +++#ifndef __STDC__ +++# ifndef const +++# define const +++# endif +++#endif +++#ifdef PROTOTYPES +++extern int unsetenv (const char *); +++#else +++extern int unsetenv (); +++#endif +++], +++[return (unsetenv == 0);], +++bash_cv_std_unsetenv=yes, bash_cv_std_unsetenv=no +++)]) +++if test $bash_cv_std_unsetenv = yes; then +++AC_DEFINE(HAVE_STD_UNSETENV) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_ULIMIT_MAXFDS, +++[AC_MSG_CHECKING(whether ulimit can substitute for getdtablesize) +++AC_CACHE_VAL(bash_cv_ulimit_maxfds, +++[AC_TRY_RUN([ +++main() +++{ +++long maxfds = ulimit(4, 0L); +++exit (maxfds == -1L); +++} +++], bash_cv_ulimit_maxfds=yes, bash_cv_ulimit_maxfds=no, +++ [AC_MSG_WARN(cannot check ulimit if cross compiling -- defaulting to no) +++ bash_cv_ulimit_maxfds=no] +++)]) +++AC_MSG_RESULT($bash_cv_ulimit_maxfds) +++if test $bash_cv_ulimit_maxfds = yes; then +++AC_DEFINE(ULIMIT_MAXFDS) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_GETCWD, +++[AC_MSG_CHECKING([if getcwd() will dynamically allocate memory with 0 size]) +++AC_CACHE_VAL(bash_cv_getcwd_malloc, +++[AC_TRY_RUN([ +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++ +++main() +++{ +++ char *xpwd; +++ xpwd = getcwd(0, 0); +++ exit (xpwd == 0); +++} +++], bash_cv_getcwd_malloc=yes, bash_cv_getcwd_malloc=no, +++ [AC_MSG_WARN(cannot check whether getcwd allocates memory when cross-compiling -- defaulting to no) +++ bash_cv_getcwd_malloc=no] +++)]) +++AC_MSG_RESULT($bash_cv_getcwd_malloc) +++if test $bash_cv_getcwd_malloc = no; then +++AC_DEFINE(GETCWD_BROKEN) +++AC_LIBOBJ(getcwd) +++fi +++]) +++ +++dnl +++dnl This needs BASH_CHECK_SOCKLIB, but since that's not called on every +++dnl system, we can't use AC_PREREQ +++dnl +++AC_DEFUN(BASH_FUNC_GETHOSTBYNAME, +++[if test "X$bash_cv_have_gethostbyname" = "X"; then +++_bash_needmsg=yes +++else +++AC_MSG_CHECKING(for gethostbyname in socket library) +++_bash_needmsg= +++fi +++AC_CACHE_VAL(bash_cv_have_gethostbyname, +++[AC_TRY_LINK([#include ], +++[ struct hostent *hp; +++ hp = gethostbyname("localhost"); +++], bash_cv_have_gethostbyname=yes, bash_cv_have_gethostbyname=no)] +++) +++if test "X$_bash_needmsg" = Xyes; then +++ AC_MSG_CHECKING(for gethostbyname in socket library) +++fi +++AC_MSG_RESULT($bash_cv_have_gethostbyname) +++if test "$bash_cv_have_gethostbyname" = yes; then +++AC_DEFINE(HAVE_GETHOSTBYNAME) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_FNMATCH_EXTMATCH, +++[AC_MSG_CHECKING(if fnmatch does extended pattern matching with FNM_EXTMATCH) +++AC_CACHE_VAL(bash_cv_fnm_extmatch, +++[AC_TRY_RUN([ +++#include +++ +++main() +++{ +++#ifdef FNM_EXTMATCH +++ exit (0); +++#else +++ exit (1); +++#endif +++} +++], bash_cv_fnm_extmatch=yes, bash_cv_fnm_extmatch=no, +++ [AC_MSG_WARN(cannot check FNM_EXTMATCH if cross compiling -- defaulting to no) +++ bash_cv_fnm_extmatch=no]) +++]) +++AC_MSG_RESULT($bash_cv_fnm_extmatch) +++if test $bash_cv_fnm_extmatch = yes; then +++AC_DEFINE(HAVE_LIBC_FNM_EXTMATCH) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_POSIX_SETJMP, +++[AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE]) +++AC_MSG_CHECKING(for presence of POSIX-style sigsetjmp/siglongjmp) +++AC_CACHE_VAL(bash_cv_func_sigsetjmp, +++[AC_TRY_RUN([ +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include +++#include +++#include + +#include +++ + +int +- main() +- { +- _bashfunc pf; +-@@ -191,9 +195,11 @@ AC_CACHE_VAL(bash_cv_under_sys_siglist, +- #ifdef HAVE_UNISTD_H +- #include +- #endif +++main() +++{ +++#if !defined (_POSIX_VERSION) || !defined (HAVE_POSIX_SIGNALS) +++exit (1); +++#else +++ +++int code; +++sigset_t set, oset; +++sigjmp_buf xx; +++ +++/* get the mask */ +++sigemptyset(&set); +++sigemptyset(&oset); +++sigprocmask(SIG_BLOCK, (sigset_t *)NULL, &set); +++sigprocmask(SIG_BLOCK, (sigset_t *)NULL, &oset); +++ +++/* save it */ +++code = sigsetjmp(xx, 1); +++if (code) +++ exit(0); /* could get sigmask and compare to oset here. */ +++ +++/* change it */ +++sigaddset(&set, SIGINT); +++sigprocmask(SIG_BLOCK, &set, (sigset_t *)NULL); +++ +++/* and siglongjmp */ +++siglongjmp(xx, 10); +++exit(1); +++#endif +++}], bash_cv_func_sigsetjmp=present, bash_cv_func_sigsetjmp=missing, +++ [AC_MSG_WARN(cannot check for sigsetjmp/siglongjmp if cross-compiling -- defaulting to missing) +++ bash_cv_func_sigsetjmp=missing] +++)]) +++AC_MSG_RESULT($bash_cv_func_sigsetjmp) +++if test $bash_cv_func_sigsetjmp = present; then +++AC_DEFINE(HAVE_POSIX_SIGSETJMP) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_STRCOLL, +++[ +++AC_MSG_CHECKING(whether or not strcoll and strcmp differ) +++AC_CACHE_VAL(bash_cv_func_strcoll_broken, +++[AC_TRY_RUN([ +++#include +++#if defined (HAVE_LOCALE_H) +++#include +++#endif +++#include + +#include +- #ifndef UNDER_SYS_SIGLIST_DECLARED +- extern char *_sys_siglist[]; +- #endif +++ + +int +- main() +- { +- char *msg = (char *)_sys_siglist[2]; +-@@ -218,9 +224,11 @@ AC_CACHE_VAL(bash_cv_sys_siglist, +- #ifdef HAVE_UNISTD_H +- #include +- #endif +++main(c, v) +++int c; +++char *v[]; +++{ +++ int r1, r2; +++ char *deflocale, *defcoll; +++ +++#ifdef HAVE_SETLOCALE +++ deflocale = setlocale(LC_ALL, ""); +++ defcoll = setlocale(LC_COLLATE, ""); +++#endif +++ +++#ifdef HAVE_STRCOLL +++ /* These two values are taken from tests/glob-test. */ +++ r1 = strcoll("abd", "aXd"); +++#else +++ r1 = 0; +++#endif +++ r2 = strcmp("abd", "aXd"); +++ +++ /* These two should both be greater than 0. It is permissible for +++ a system to return different values, as long as the sign is the +++ same. */ +++ +++ /* Exit with 1 (failure) if these two values are both > 0, since +++ this tests whether strcoll(3) is broken with respect to strcmp(3) +++ in the default locale. */ +++ exit (r1 > 0 && r2 > 0); +++} +++], bash_cv_func_strcoll_broken=yes, bash_cv_func_strcoll_broken=no, +++ [AC_MSG_WARN(cannot check strcoll if cross compiling -- defaulting to no) +++ bash_cv_func_strcoll_broken=no] +++)]) +++AC_MSG_RESULT($bash_cv_func_strcoll_broken) +++if test $bash_cv_func_strcoll_broken = yes; then +++AC_DEFINE(STRCOLL_BROKEN) +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_PRINTF_A_FORMAT, +++[AC_MSG_CHECKING([for printf floating point output in hex notation]) +++AC_CACHE_VAL(bash_cv_printf_a_format, +++[AC_TRY_RUN([ +++#include +++#include + +#include +- #if !HAVE_DECL_SYS_SIGLIST +- extern char *sys_siglist[]; +- #endif +++ + +int +- main() +- { +- char *msg = sys_siglist[2]; +-@@ -273,6 +281,8 @@ AC_CACHE_VAL(bash_cv_dup2_broken, +- [AC_TRY_RUN([ +- #include +- #include +++main() +++{ +++ double y = 0.0; +++ char abuf[1024]; +++ +++ sprintf(abuf, "%A", y); +++ exit(strchr(abuf, 'P') == (char *)0); +++} +++], bash_cv_printf_a_format=yes, bash_cv_printf_a_format=no, +++ [AC_MSG_WARN(cannot check printf if cross compiling -- defaulting to no) +++ bash_cv_printf_a_format=no] +++)]) +++AC_MSG_RESULT($bash_cv_printf_a_format) +++if test $bash_cv_printf_a_format = yes; then +++AC_DEFINE(HAVE_PRINTF_A_FORMAT) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_TERMIOS_LDISC, +++[ +++AC_CHECK_MEMBER(struct termios.c_line, AC_DEFINE(TERMIOS_LDISC), ,[ +++#include +++#include +++]) +++]) +++ +++AC_DEFUN(BASH_STRUCT_TERMIO_LDISC, +++[ +++AC_CHECK_MEMBER(struct termio.c_line, AC_DEFINE(TERMIO_LDISC), ,[ +++#include +++#include +++]) +++]) +++ +++dnl +++dnl Like AC_STRUCT_ST_BLOCKS, but doesn't muck with LIBOBJS +++dnl +++dnl sets bash_cv_struct_stat_st_blocks +++dnl +++dnl unused for now; we'll see how AC_CHECK_MEMBERS works +++dnl +++AC_DEFUN(BASH_STRUCT_ST_BLOCKS, +++[ +++AC_MSG_CHECKING([for struct stat.st_blocks]) +++AC_CACHE_VAL(bash_cv_struct_stat_st_blocks, +++[AC_TRY_COMPILE( +++[ +++#include +++#include +++], +++[ +++main() +++{ +++static struct stat a; +++if (a.st_blocks) return 0; +++return 0; +++} +++], bash_cv_struct_stat_st_blocks=yes, bash_cv_struct_stat_st_blocks=no) +++]) +++AC_MSG_RESULT($bash_cv_struct_stat_st_blocks) +++if test "$bash_cv_struct_stat_st_blocks" = "yes"; then +++AC_DEFINE(HAVE_STRUCT_STAT_ST_BLOCKS) +++fi +++]) +++ +++AC_DEFUN([BASH_CHECK_LIB_TERMCAP], +++[ +++if test "X$bash_cv_termcap_lib" = "X"; then +++_bash_needmsg=yes +++else +++AC_MSG_CHECKING(which library has the termcap functions) +++_bash_needmsg= +++fi +++AC_CACHE_VAL(bash_cv_termcap_lib, +++[AC_CHECK_FUNC(tgetent, bash_cv_termcap_lib=libc, +++ [AC_CHECK_LIB(termcap, tgetent, bash_cv_termcap_lib=libtermcap, +++ [AC_CHECK_LIB(tinfo, tgetent, bash_cv_termcap_lib=libtinfo, +++ [AC_CHECK_LIB(curses, tgetent, bash_cv_termcap_lib=libcurses, +++ [AC_CHECK_LIB(ncurses, tgetent, bash_cv_termcap_lib=libncurses, +++ [AC_CHECK_LIB(ncursesw, tgetent, bash_cv_termcap_lib=libncursesw, +++ bash_cv_termcap_lib=gnutermcap)])])])])])]) +++if test "X$_bash_needmsg" = "Xyes"; then +++AC_MSG_CHECKING(which library has the termcap functions) +++fi +++AC_MSG_RESULT(using $bash_cv_termcap_lib) +++if test $bash_cv_termcap_lib = gnutermcap && test -z "$prefer_curses"; then +++LDFLAGS="$LDFLAGS -L./lib/termcap" +++TERMCAP_LIB="./lib/termcap/libtermcap.a" +++TERMCAP_DEP="./lib/termcap/libtermcap.a" +++elif test $bash_cv_termcap_lib = libtermcap && test -z "$prefer_curses"; then +++TERMCAP_LIB=-ltermcap +++TERMCAP_DEP= +++elif test $bash_cv_termcap_lib = libtinfo; then +++TERMCAP_LIB=-ltinfo +++TERMCAP_DEP= +++elif test $bash_cv_termcap_lib = libncurses; then +++TERMCAP_LIB=-lncurses +++TERMCAP_DEP= +++elif test $bash_cv_termcap_lib = libc; then +++TERMCAP_LIB= +++TERMCAP_DEP= +++else +++TERMCAP_LIB=-lcurses +++TERMCAP_DEP= +++fi +++]) +++ +++dnl +++dnl Check for the presence of getpeername in libsocket. +++dnl If libsocket is present, check for libnsl and add it to LIBS if +++dnl it's there, since most systems with libsocket require linking +++dnl with libnsl as well. This should only be called if getpeername +++dnl was not found in libc. +++dnl +++dnl NOTE: IF WE FIND GETPEERNAME, WE ASSUME THAT WE HAVE BIND/CONNECT +++dnl AS WELL +++dnl +++AC_DEFUN(BASH_CHECK_LIB_SOCKET, +++[ +++if test "X$bash_cv_have_socklib" = "X"; then +++_bash_needmsg= +++else +++AC_MSG_CHECKING(for socket library) +++_bash_needmsg=yes +++fi +++AC_CACHE_VAL(bash_cv_have_socklib, +++[AC_CHECK_LIB(socket, getpeername, +++ bash_cv_have_socklib=yes, bash_cv_have_socklib=no, -lnsl)]) +++if test "X$_bash_needmsg" = Xyes; then +++ AC_MSG_RESULT($bash_cv_have_socklib) +++ _bash_needmsg= +++fi +++if test $bash_cv_have_socklib = yes; then +++ # check for libnsl, add it to LIBS if present +++ if test "X$bash_cv_have_libnsl" = "X"; then +++ _bash_needmsg= +++ else +++ AC_MSG_CHECKING(for libnsl) +++ _bash_needmsg=yes +++ fi +++ AC_CACHE_VAL(bash_cv_have_libnsl, +++ [AC_CHECK_LIB(nsl, t_open, +++ bash_cv_have_libnsl=yes, bash_cv_have_libnsl=no)]) +++ if test "X$_bash_needmsg" = Xyes; then +++ AC_MSG_RESULT($bash_cv_have_libnsl) +++ _bash_needmsg= +++ fi +++ if test $bash_cv_have_libnsl = yes; then +++ LIBS="-lsocket -lnsl $LIBS" +++ else +++ LIBS="-lsocket $LIBS" +++ fi +++ AC_DEFINE(HAVE_LIBSOCKET) +++ AC_DEFINE(HAVE_GETPEERNAME) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_DIRENT_D_INO, +++[AC_REQUIRE([AC_HEADER_DIRENT]) +++AC_MSG_CHECKING(for struct dirent.d_ino) +++AC_CACHE_VAL(bash_cv_dirent_has_dino, +++[AC_TRY_COMPILE([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++# include +++#endif /* HAVE_UNISTD_H */ +++#if defined(HAVE_DIRENT_H) +++# include +++#else +++# define dirent direct +++# ifdef HAVE_SYS_NDIR_H +++# include +++# endif /* SYSNDIR */ +++# ifdef HAVE_SYS_DIR_H +++# include +++# endif /* SYSDIR */ +++# ifdef HAVE_NDIR_H +++# include +++# endif +++#endif /* HAVE_DIRENT_H */ +++],[ +++struct dirent d; int z; z = d.d_ino; +++], bash_cv_dirent_has_dino=yes, bash_cv_dirent_has_dino=no)]) +++AC_MSG_RESULT($bash_cv_dirent_has_dino) +++if test $bash_cv_dirent_has_dino = yes; then +++AC_DEFINE(HAVE_STRUCT_DIRENT_D_INO) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_DIRENT_D_FILENO, +++[AC_REQUIRE([AC_HEADER_DIRENT]) +++AC_MSG_CHECKING(for struct dirent.d_fileno) +++AC_CACHE_VAL(bash_cv_dirent_has_d_fileno, +++[AC_TRY_COMPILE([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++# include +++#endif /* HAVE_UNISTD_H */ +++#if defined(HAVE_DIRENT_H) +++# include +++#else +++# define dirent direct +++# ifdef HAVE_SYS_NDIR_H +++# include +++# endif /* SYSNDIR */ +++# ifdef HAVE_SYS_DIR_H +++# include +++# endif /* SYSDIR */ +++# ifdef HAVE_NDIR_H +++# include +++# endif +++#endif /* HAVE_DIRENT_H */ +++],[ +++struct dirent d; int z; z = d.d_fileno; +++], bash_cv_dirent_has_d_fileno=yes, bash_cv_dirent_has_d_fileno=no)]) +++AC_MSG_RESULT($bash_cv_dirent_has_d_fileno) +++if test $bash_cv_dirent_has_d_fileno = yes; then +++AC_DEFINE(HAVE_STRUCT_DIRENT_D_FILENO) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_DIRENT_D_NAMLEN, +++[AC_REQUIRE([AC_HEADER_DIRENT]) +++AC_MSG_CHECKING(for struct dirent.d_namlen) +++AC_CACHE_VAL(bash_cv_dirent_has_d_namlen, +++[AC_TRY_COMPILE([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++# include +++#endif /* HAVE_UNISTD_H */ +++#if defined(HAVE_DIRENT_H) +++# include +++#else +++# define dirent direct +++# ifdef HAVE_SYS_NDIR_H +++# include +++# endif /* SYSNDIR */ +++# ifdef HAVE_SYS_DIR_H +++# include +++# endif /* SYSDIR */ +++# ifdef HAVE_NDIR_H +++# include +++# endif +++#endif /* HAVE_DIRENT_H */ +++],[ +++struct dirent d; int z; z = d.d_namlen; +++], bash_cv_dirent_has_d_namlen=yes, bash_cv_dirent_has_d_namlen=no)]) +++AC_MSG_RESULT($bash_cv_dirent_has_d_namlen) +++if test $bash_cv_dirent_has_d_namlen = yes; then +++AC_DEFINE(HAVE_STRUCT_DIRENT_D_NAMLEN) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_TIMEVAL, +++[AC_MSG_CHECKING(for struct timeval in sys/time.h and time.h) +++AC_CACHE_VAL(bash_cv_struct_timeval, +++[ +++AC_EGREP_HEADER(struct timeval, sys/time.h, +++ bash_cv_struct_timeval=yes, +++ AC_EGREP_HEADER(struct timeval, time.h, +++ bash_cv_struct_timeval=yes, +++ bash_cv_struct_timeval=no)) +++]) +++AC_MSG_RESULT($bash_cv_struct_timeval) +++if test $bash_cv_struct_timeval = yes; then +++ AC_DEFINE(HAVE_TIMEVAL) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_TIMEZONE, +++[AC_MSG_CHECKING(for struct timezone in sys/time.h and time.h) +++AC_CACHE_VAL(bash_cv_struct_timezone, +++[ +++AC_EGREP_HEADER(struct timezone, sys/time.h, +++ bash_cv_struct_timezone=yes, +++ AC_EGREP_HEADER(struct timezone, time.h, +++ bash_cv_struct_timezone=yes, +++ bash_cv_struct_timezone=no)) +++]) +++AC_MSG_RESULT($bash_cv_struct_timezone) +++if test $bash_cv_struct_timezone = yes; then +++ AC_DEFINE(HAVE_STRUCT_TIMEZONE) +++fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_WINSIZE, +++[AC_MSG_CHECKING(for struct winsize in sys/ioctl.h and termios.h) +++AC_CACHE_VAL(bash_cv_struct_winsize_header, +++[AC_TRY_COMPILE([#include +++#include ], [struct winsize x;], +++ bash_cv_struct_winsize_header=ioctl_h, +++ [AC_TRY_COMPILE([#include +++#include ], [struct winsize x;], +++ bash_cv_struct_winsize_header=termios_h, bash_cv_struct_winsize_header=other) +++])]) +++if test $bash_cv_struct_winsize_header = ioctl_h; then +++ AC_MSG_RESULT(sys/ioctl.h) +++ AC_DEFINE(STRUCT_WINSIZE_IN_SYS_IOCTL) +++elif test $bash_cv_struct_winsize_header = termios_h; then +++ AC_MSG_RESULT(termios.h) +++ AC_DEFINE(STRUCT_WINSIZE_IN_TERMIOS) +++else +++ AC_MSG_RESULT(not found) +++fi +++]) +++ +++dnl Check type of signal routines (posix, 4.2bsd, 4.1bsd or v7) +++AC_DEFUN(BASH_SYS_SIGNAL_VINTAGE, +++[AC_REQUIRE([AC_TYPE_SIGNAL]) +++AC_MSG_CHECKING(for type of signal functions) +++AC_CACHE_VAL(bash_cv_signal_vintage, +++[ +++ AC_TRY_LINK([#include ],[ +++ sigset_t ss; +++ struct sigaction sa; +++ sigemptyset(&ss); sigsuspend(&ss); +++ sigaction(SIGINT, &sa, (struct sigaction *) 0); +++ sigprocmask(SIG_BLOCK, &ss, (sigset_t *) 0); +++ ], bash_cv_signal_vintage=posix, +++ [ +++ AC_TRY_LINK([#include ], [ +++ int mask = sigmask(SIGINT); +++ sigsetmask(mask); sigblock(mask); sigpause(mask); +++ ], bash_cv_signal_vintage=4.2bsd, +++ [ +++ AC_TRY_LINK([ +++ #include +++ RETSIGTYPE foo() { }], [ +++ int mask = sigmask(SIGINT); +++ sigset(SIGINT, foo); sigrelse(SIGINT); +++ sighold(SIGINT); sigpause(SIGINT); +++ ], bash_cv_signal_vintage=svr3, bash_cv_signal_vintage=v7 +++ )] +++ )] +++) +++]) +++AC_MSG_RESULT($bash_cv_signal_vintage) +++if test "$bash_cv_signal_vintage" = posix; then +++AC_DEFINE(HAVE_POSIX_SIGNALS) +++elif test "$bash_cv_signal_vintage" = "4.2bsd"; then +++AC_DEFINE(HAVE_BSD_SIGNALS) +++elif test "$bash_cv_signal_vintage" = svr3; then +++AC_DEFINE(HAVE_USG_SIGHOLD) +++fi +++]) +++ +++dnl Check if the pgrp of setpgrp() can't be the pid of a zombie process. +++AC_DEFUN(BASH_SYS_PGRP_SYNC, +++[AC_REQUIRE([AC_FUNC_GETPGRP]) +++AC_MSG_CHECKING(whether pgrps need synchronization) +++AC_CACHE_VAL(bash_cv_pgrp_pipe, +++[AC_TRY_RUN([ +++#ifdef HAVE_UNISTD_H +++# include +++#endif + +#include + +int +- main() +- { +- int fd1, fd2, fl; +-@@ -335,6 +345,8 @@ AC_CACHE_VAL(bash_cv_opendir_not_robust, +- # include +- # endif +- #endif /* HAVE_DIRENT_H */ +++main() +++{ +++# ifdef GETPGRP_VOID +++# define getpgID() getpgrp() +++# else +++# define getpgID() getpgrp(0) +++# define setpgid(x,y) setpgrp(x,y) +++# endif +++ int pid1, pid2, fds[2]; +++ int status; +++ char ok; +++ +++ switch (pid1 = fork()) { +++ case -1: +++ exit(1); +++ case 0: +++ setpgid(0, getpid()); +++ exit(0); +++ } +++ setpgid(pid1, pid1); +++ +++ sleep(2); /* let first child die */ +++ +++ if (pipe(fds) < 0) +++ exit(2); +++ +++ switch (pid2 = fork()) { +++ case -1: +++ exit(3); +++ case 0: +++ setpgid(0, pid1); +++ ok = getpgID() == pid1; +++ write(fds[1], &ok, 1); +++ exit(0); +++ } +++ setpgid(pid2, pid1); +++ +++ close(fds[1]); +++ if (read(fds[0], &ok, 1) != 1) +++ exit(4); +++ wait(&status); +++ wait(&status); +++ exit(ok ? 0 : 5); +++} +++], bash_cv_pgrp_pipe=no,bash_cv_pgrp_pipe=yes, +++ [AC_MSG_WARN(cannot check pgrp synchronization if cross compiling -- defaulting to no) +++ bash_cv_pgrp_pipe=no]) +++]) +++AC_MSG_RESULT($bash_cv_pgrp_pipe) +++if test $bash_cv_pgrp_pipe = yes; then +++AC_DEFINE(PGRP_PIPE) +++fi +++]) +++ +++AC_DEFUN(BASH_SYS_REINSTALL_SIGHANDLERS, +++[AC_REQUIRE([AC_TYPE_SIGNAL]) +++AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE]) +++AC_MSG_CHECKING([if signal handlers must be reinstalled when invoked]) +++AC_CACHE_VAL(bash_cv_must_reinstall_sighandlers, +++[AC_TRY_RUN([ +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif + +#include +++ +++typedef RETSIGTYPE sigfunc(); +++ +++volatile int nsigint; +++ +++#ifdef HAVE_POSIX_SIGNALS +++sigfunc * +++set_signal_handler(sig, handler) +++ int sig; +++ sigfunc *handler; +++{ +++ struct sigaction act, oact; +++ act.sa_handler = handler; +++ act.sa_flags = 0; +++ sigemptyset (&act.sa_mask); +++ sigemptyset (&oact.sa_mask); +++ sigaction (sig, &act, &oact); +++ return (oact.sa_handler); +++} +++#else +++#define set_signal_handler(s, h) signal(s, h) +++#endif +++ +++RETSIGTYPE +++sigint(s) +++int s; +++{ +++ nsigint++; +++} +++ + +int +- main() +- { +- DIR *dir; +-@@ -514,6 +526,8 @@ AC_TRY_RUN([ +- #include +- #include +- #include +++main() +++{ +++ nsigint = 0; +++ set_signal_handler(SIGINT, sigint); +++ kill((int)getpid(), SIGINT); +++ kill((int)getpid(), SIGINT); +++ exit(nsigint != 2); +++} +++], bash_cv_must_reinstall_sighandlers=no, bash_cv_must_reinstall_sighandlers=yes, +++ [AC_MSG_WARN(cannot check signal handling if cross compiling -- defaulting to no) +++ bash_cv_must_reinstall_sighandlers=no] +++)]) +++AC_MSG_RESULT($bash_cv_must_reinstall_sighandlers) +++if test $bash_cv_must_reinstall_sighandlers = yes; then +++AC_DEFINE(MUST_REINSTALL_SIGHANDLERS) +++fi +++]) +++ +++dnl check that some necessary job control definitions are present +++AC_DEFUN(BASH_SYS_JOB_CONTROL_MISSING, +++[AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE]) +++AC_MSG_CHECKING(for presence of necessary job control definitions) +++AC_CACHE_VAL(bash_cv_job_control_missing, +++[AC_TRY_COMPILE([ +++#include +++#ifdef HAVE_SYS_WAIT_H +++#include +++#endif +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include +++ +++/* add more tests in here as appropriate */ +++ +++/* signal type */ +++#if !defined (HAVE_POSIX_SIGNALS) && !defined (HAVE_BSD_SIGNALS) +++#error +++#endif +++ +++/* signals and tty control. */ +++#if !defined (SIGTSTP) || !defined (SIGSTOP) || !defined (SIGCONT) +++#error +++#endif +++ +++/* process control */ +++#if !defined (WNOHANG) || !defined (WUNTRACED) +++#error +++#endif +++ +++/* Posix systems have tcgetpgrp and waitpid. */ +++#if defined (_POSIX_VERSION) && !defined (HAVE_TCGETPGRP) +++#error +++#endif +++ +++#if defined (_POSIX_VERSION) && !defined (HAVE_WAITPID) +++#error +++#endif +++ +++/* Other systems have TIOCSPGRP/TIOCGPRGP and wait3. */ +++#if !defined (_POSIX_VERSION) && !defined (HAVE_WAIT3) +++#error +++#endif +++ +++], , bash_cv_job_control_missing=present, bash_cv_job_control_missing=missing +++)]) +++AC_MSG_RESULT($bash_cv_job_control_missing) +++if test $bash_cv_job_control_missing = missing; then +++AC_DEFINE(JOB_CONTROL_MISSING) +++fi +++]) +++ +++dnl check whether named pipes are present +++dnl this requires a previous check for mkfifo, but that is awkward to specify +++AC_DEFUN(BASH_SYS_NAMED_PIPES, +++[AC_MSG_CHECKING(for presence of named pipes) +++AC_CACHE_VAL(bash_cv_sys_named_pipes, +++[AC_TRY_RUN([ +++#include +++#include +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include + +#include +++ +++/* Add more tests in here as appropriate. */ + +int +- main() +- { +- #ifdef HAVE_QUAD_T +-@@ -583,6 +597,7 @@ AC_CACHE_VAL(bash_cv_getenv_redef, +- #ifdef HAVE_UNISTD_H +- # include +- #endif +++main() +++{ +++int fd, err; +++ +++#if defined (HAVE_MKFIFO) +++exit (0); +++#endif +++ +++#if !defined (S_IFIFO) && (defined (_POSIX_VERSION) && !defined (S_ISFIFO)) +++exit (1); +++#endif +++ +++#if defined (NeXT) +++exit (1); +++#endif +++err = mkdir("bash-aclocal", 0700); +++if (err < 0) { +++ perror ("mkdir"); +++ exit(1); +++} +++fd = mknod ("bash-aclocal/sh-np-autoconf", 0666 | S_IFIFO, 0); +++if (fd == -1) { +++ rmdir ("bash-aclocal"); +++ exit (1); +++} +++close(fd); +++unlink ("bash-aclocal/sh-np-autoconf"); +++rmdir ("bash-aclocal"); +++exit(0); +++}], bash_cv_sys_named_pipes=present, bash_cv_sys_named_pipes=missing, +++ [AC_MSG_WARN(cannot check for named pipes if cross-compiling -- defaulting to missing) +++ bash_cv_sys_named_pipes=missing] +++)]) +++AC_MSG_RESULT($bash_cv_sys_named_pipes) +++if test $bash_cv_sys_named_pipes = missing; then +++AC_DEFINE(NAMED_PIPES_MISSING) +++fi +++]) +++ +++AC_DEFUN(BASH_SYS_DEFAULT_MAIL_DIR, +++[AC_MSG_CHECKING(for default mail directory) +++AC_CACHE_VAL(bash_cv_mail_dir, +++[if test -d /var/mail; then +++ bash_cv_mail_dir=/var/mail +++ elif test -d /var/spool/mail; then +++ bash_cv_mail_dir=/var/spool/mail +++ elif test -d /usr/mail; then +++ bash_cv_mail_dir=/usr/mail +++ elif test -d /usr/spool/mail; then +++ bash_cv_mail_dir=/usr/spool/mail +++ else +++ bash_cv_mail_dir=unknown +++ fi +++]) +++AC_MSG_RESULT($bash_cv_mail_dir) +++AC_DEFINE_UNQUOTED(DEFAULT_MAIL_DIRECTORY, "$bash_cv_mail_dir") +++]) +++ +++AC_DEFUN(BASH_HAVE_TIOCGWINSZ, +++[AC_MSG_CHECKING(for TIOCGWINSZ in sys/ioctl.h) +++AC_CACHE_VAL(bash_cv_tiocgwinsz_in_ioctl, +++[AC_TRY_COMPILE([#include +++#include ], [int x = TIOCGWINSZ;], +++ bash_cv_tiocgwinsz_in_ioctl=yes,bash_cv_tiocgwinsz_in_ioctl=no)]) +++AC_MSG_RESULT($bash_cv_tiocgwinsz_in_ioctl) +++if test $bash_cv_tiocgwinsz_in_ioctl = yes; then +++AC_DEFINE(GWINSZ_IN_SYS_IOCTL) +++fi +++]) +++ +++AC_DEFUN(BASH_HAVE_TIOCSTAT, +++[AC_MSG_CHECKING(for TIOCSTAT in sys/ioctl.h) +++AC_CACHE_VAL(bash_cv_tiocstat_in_ioctl, +++[AC_TRY_COMPILE([#include +++#include ], [int x = TIOCSTAT;], +++ bash_cv_tiocstat_in_ioctl=yes,bash_cv_tiocstat_in_ioctl=no)]) +++AC_MSG_RESULT($bash_cv_tiocstat_in_ioctl) +++if test $bash_cv_tiocstat_in_ioctl = yes; then +++AC_DEFINE(TIOCSTAT_IN_SYS_IOCTL) +++fi +++]) +++ +++AC_DEFUN(BASH_HAVE_FIONREAD, +++[AC_MSG_CHECKING(for FIONREAD in sys/ioctl.h) +++AC_CACHE_VAL(bash_cv_fionread_in_ioctl, +++[AC_TRY_COMPILE([#include +++#include ], [int x = FIONREAD;], +++ bash_cv_fionread_in_ioctl=yes,bash_cv_fionread_in_ioctl=no)]) +++AC_MSG_RESULT($bash_cv_fionread_in_ioctl) +++if test $bash_cv_fionread_in_ioctl = yes; then +++AC_DEFINE(FIONREAD_IN_SYS_IOCTL) +++fi +++]) +++ +++dnl +++dnl See if speed_t is declared in . Some versions of linux +++dnl require a definition of speed_t each time is included, +++dnl but you can only get speed_t if you include (on some +++dnl versions) or (on others). +++dnl +++AC_DEFUN(BASH_CHECK_SPEED_T, +++[AC_MSG_CHECKING(for speed_t in sys/types.h) +++AC_CACHE_VAL(bash_cv_speed_t_in_sys_types, +++[AC_TRY_COMPILE([#include ], [speed_t x;], +++ bash_cv_speed_t_in_sys_types=yes,bash_cv_speed_t_in_sys_types=no)]) +++AC_MSG_RESULT($bash_cv_speed_t_in_sys_types) +++if test $bash_cv_speed_t_in_sys_types = yes; then +++AC_DEFINE(SPEED_T_IN_SYS_TYPES) +++fi +++]) +++ +++AC_DEFUN(BASH_CHECK_GETPW_FUNCS, +++[AC_MSG_CHECKING(whether getpw functions are declared in pwd.h) +++AC_CACHE_VAL(bash_cv_getpw_declared, +++[AC_EGREP_CPP(getpwuid, +++[ +++#include +++#ifdef HAVE_UNISTD_H +++# include +++#endif +++#include +++], +++bash_cv_getpw_declared=yes,bash_cv_getpw_declared=no)]) +++AC_MSG_RESULT($bash_cv_getpw_declared) +++if test $bash_cv_getpw_declared = yes; then +++AC_DEFINE(HAVE_GETPW_DECLS) +++fi +++]) +++ +++AC_DEFUN(BASH_CHECK_DEV_FD, +++[AC_MSG_CHECKING(whether /dev/fd is available) +++AC_CACHE_VAL(bash_cv_dev_fd, +++[bash_cv_dev_fd="" +++if test -d /dev/fd && (exec test -r /dev/fd/0 < /dev/null) ; then +++# check for systems like FreeBSD 5 that only provide /dev/fd/[012] +++ if (exec test -r /dev/fd/3 3 +++#include +++], +++[ +++ int f; +++ f = RLIMIT_DATA; +++], bash_cv_kernel_rlimit=no, +++[AC_TRY_COMPILE([ +++#include +++#define _KERNEL +++#include +++#undef _KERNEL +++], +++[ +++ int f; +++ f = RLIMIT_DATA; +++], bash_cv_kernel_rlimit=yes, bash_cv_kernel_rlimit=no)] +++)]) +++AC_MSG_RESULT($bash_cv_kernel_rlimit) +++if test $bash_cv_kernel_rlimit = yes; then +++AC_DEFINE(RLIMIT_NEEDS_KERNEL) +++fi +++]) +++ +++dnl +++dnl Check for 64-bit off_t -- used for malloc alignment +++dnl +++dnl C does not allow duplicate case labels, so the compile will fail if +++dnl sizeof(off_t) is > 4. +++dnl +++AC_DEFUN(BASH_CHECK_OFF_T_64, +++[AC_CACHE_CHECK(for 64-bit off_t, bash_cv_off_t_64, +++AC_TRY_COMPILE([ +++#ifdef HAVE_UNISTD_H +++#include +++#endif +++#include +++],[ +++switch (0) case 0: case (sizeof (off_t) <= 4):; +++], bash_cv_off_t_64=no, bash_cv_off_t_64=yes)) +++if test $bash_cv_off_t_64 = yes; then +++ AC_DEFINE(HAVE_OFF_T_64) +++fi]) +++ +++AC_DEFUN(BASH_CHECK_RTSIGS, +++[AC_MSG_CHECKING(for unusable real-time signals due to large values) +++AC_CACHE_VAL(bash_cv_unusable_rtsigs, +++[AC_TRY_RUN([ +++#include +++#include + +#include +- #ifndef __STDC__ +- # ifndef const +- # define const +-@@ -598,6 +613,7 @@ getenv (name) +- { +- return "42"; +- } +++ +++#ifndef NSIG +++# define NSIG 64 +++#endif +++ + +int +- main() +- { +- char *s; +-@@ -786,7 +802,9 @@ AC_CACHE_VAL(bash_cv_func_sigsetjmp, +- #include +- #include +- #include +++main () +++{ +++ int n_sigs = 2 * NSIG; +++#ifdef SIGRTMIN +++ int rtmin = SIGRTMIN; +++#else +++ int rtmin = 0; +++#endif +++ +++ exit(rtmin < n_sigs); +++}], bash_cv_unusable_rtsigs=yes, bash_cv_unusable_rtsigs=no, +++ [AC_MSG_WARN(cannot check real-time signals if cross compiling -- defaulting to yes) +++ bash_cv_unusable_rtsigs=yes] +++)]) +++AC_MSG_RESULT($bash_cv_unusable_rtsigs) +++if test $bash_cv_unusable_rtsigs = yes; then +++AC_DEFINE(UNUSABLE_RT_SIGNALS) +++fi +++]) +++ +++dnl +++dnl check for availability of multibyte characters and functions +++dnl +++dnl geez, I wish I didn't have to check for all of this stuff separately +++dnl +++AC_DEFUN(BASH_CHECK_MULTIBYTE, +++[ +++AC_CHECK_HEADERS(wctype.h) +++AC_CHECK_HEADERS(wchar.h) +++AC_CHECK_HEADERS(langinfo.h) +++ +++AC_CHECK_HEADERS(mbstr.h) +++ +++AC_CHECK_FUNC(mbrlen, AC_DEFINE(HAVE_MBRLEN)) +++AC_CHECK_FUNC(mbscasecmp, AC_DEFINE(HAVE_MBSCMP)) +++AC_CHECK_FUNC(mbscmp, AC_DEFINE(HAVE_MBSCMP)) +++AC_CHECK_FUNC(mbsnrtowcs, AC_DEFINE(HAVE_MBSNRTOWCS)) +++AC_CHECK_FUNC(mbsrtowcs, AC_DEFINE(HAVE_MBSRTOWCS)) +++ +++AC_REPLACE_FUNCS(mbschr) +++ +++AC_CHECK_FUNC(wcrtomb, AC_DEFINE(HAVE_WCRTOMB)) +++AC_CHECK_FUNC(wcscoll, AC_DEFINE(HAVE_WCSCOLL)) +++AC_CHECK_FUNC(wcsdup, AC_DEFINE(HAVE_WCSDUP)) +++AC_CHECK_FUNC(wcwidth, AC_DEFINE(HAVE_WCWIDTH)) +++AC_CHECK_FUNC(wctype, AC_DEFINE(HAVE_WCTYPE)) +++ +++AC_REPLACE_FUNCS(wcswidth) +++ +++dnl checks for both mbrtowc and mbstate_t +++AC_FUNC_MBRTOWC +++if test $ac_cv_func_mbrtowc = yes; then +++ AC_DEFINE(HAVE_MBSTATE_T) +++fi +++ +++AC_CHECK_FUNCS(iswlower iswupper towlower towupper iswctype) +++ +++AC_CACHE_CHECK([for nl_langinfo and CODESET], bash_cv_langinfo_codeset, +++[AC_TRY_LINK( +++[#include ], +++[char* cs = nl_langinfo(CODESET);], +++bash_cv_langinfo_codeset=yes, bash_cv_langinfo_codeset=no)]) +++if test $bash_cv_langinfo_codeset = yes; then +++ AC_DEFINE(HAVE_LANGINFO_CODESET) +++fi +++ +++dnl check for wchar_t in +++AC_CACHE_CHECK([for wchar_t in wchar.h], bash_cv_type_wchar_t, +++[AC_TRY_COMPILE( +++[#include +++], +++[ +++ wchar_t foo; +++ foo = 0; +++], bash_cv_type_wchar_t=yes, bash_cv_type_wchar_t=no)]) +++if test $bash_cv_type_wchar_t = yes; then +++ AC_DEFINE(HAVE_WCHAR_T, 1, [systems should define this type here]) +++fi +++ +++dnl check for wctype_t in +++AC_CACHE_CHECK([for wctype_t in wctype.h], bash_cv_type_wctype_t, +++[AC_TRY_COMPILE( +++[#include ], +++[ +++ wctype_t foo; +++ foo = 0; +++], bash_cv_type_wctype_t=yes, bash_cv_type_wctype_t=no)]) +++if test $bash_cv_type_wctype_t = yes; then +++ AC_DEFINE(HAVE_WCTYPE_T, 1, [systems should define this type here]) +++fi +++ +++dnl check for wint_t in +++AC_CACHE_CHECK([for wint_t in wctype.h], bash_cv_type_wint_t, +++[AC_TRY_COMPILE( +++[#include ], +++[ +++ wint_t foo; +++ foo = 0; +++], bash_cv_type_wint_t=yes, bash_cv_type_wint_t=no)]) +++if test $bash_cv_type_wint_t = yes; then +++ AC_DEFINE(HAVE_WINT_T, 1, [systems should define this type here]) +++fi +++ +++dnl check for broken wcwidth +++AC_CACHE_CHECK([for wcwidth broken with unicode combining characters], +++bash_cv_wcwidth_broken, +++[AC_TRY_RUN([ +++#include + +#include +- +++#include +++ +++#include +++#include +++ + +int +- main() +- { +- #if !defined (_POSIX_VERSION) || !defined (HAVE_POSIX_SIGNALS) +-@@ -835,7 +853,10 @@ AC_CACHE_VAL(bash_cv_func_strcoll_broken +- #if defined (HAVE_LOCALE_H) +- #include +- #endif +-+#include +++main(c, v) +++int c; +++char **v; +++{ +++ int w; +++ +++ setlocale(LC_ALL, "en_US.UTF-8"); +++ w = wcwidth (0x0301); +++ exit (w == 0); /* exit 0 if wcwidth broken */ +++} +++], +++bash_cv_wcwidth_broken=yes, bash_cv_wcwidth_broken=no, bash_cv_wcwidth_broken=no)]) +++if test "$bash_cv_wcwidth_broken" = yes; then +++ AC_DEFINE(WCWIDTH_BROKEN, 1, [wcwidth is usually not broken]) +++fi +++ +++if test "$am_cv_func_iconv" = yes; then +++ OLDLIBS="$LIBS" +++ LIBS="$LIBS $LIBINTL $LIBICONV" +++ AC_CHECK_FUNCS(locale_charset) +++ LIBS="$OLDLIBS" +++fi +++ +++AC_CHECK_SIZEOF(wchar_t, 4) +++ +++]) +++ +++dnl need: prefix exec_prefix libdir includedir CC TERMCAP_LIB +++dnl require: +++dnl AC_PROG_CC +++dnl BASH_CHECK_LIB_TERMCAP +++ +++AC_DEFUN([RL_LIB_READLINE_VERSION], +++[ +++AC_REQUIRE([BASH_CHECK_LIB_TERMCAP]) +++ +++AC_MSG_CHECKING([version of installed readline library]) +++ +++# What a pain in the ass this is. +++ +++# save cpp and ld options +++_save_CFLAGS="$CFLAGS" +++_save_LDFLAGS="$LDFLAGS" +++_save_LIBS="$LIBS" +++ +++# Don't set ac_cv_rl_prefix if the caller has already assigned a value. This +++# allows the caller to do something like $_rl_prefix=$withval if the user +++# specifies --with-installed-readline=PREFIX as an argument to configure +++ +++if test -z "$ac_cv_rl_prefix"; then +++test "x$prefix" = xNONE && ac_cv_rl_prefix=$ac_default_prefix || ac_cv_rl_prefix=${prefix} +++fi +++ +++eval ac_cv_rl_includedir=${ac_cv_rl_prefix}/include +++eval ac_cv_rl_libdir=${ac_cv_rl_prefix}/lib +++ +++LIBS="$LIBS -lreadline ${TERMCAP_LIB}" +++CFLAGS="$CFLAGS -I${ac_cv_rl_includedir}" +++LDFLAGS="$LDFLAGS -L${ac_cv_rl_libdir}" +++ +++AC_CACHE_VAL(ac_cv_rl_version, +++[AC_TRY_RUN([ +++#include +++#include + +#include +- +++ +++extern int rl_gnu_readline_p; +++ + +int +- main(c, v) +- int c; +- char *v[]; +-@@ -881,6 +902,7 @@ AC_CACHE_VAL(bash_cv_printf_a_format, +- [AC_TRY_RUN([ +- #include +- #include +-+#include +- +- int +- main() +-@@ -1241,6 +1263,8 @@ AC_CACHE_VAL(bash_cv_pgrp_pipe, +- #ifdef HAVE_UNISTD_H +- # include +- #endif +++main() +++{ +++ FILE *fp; +++ fp = fopen("conftest.rlv", "w"); +++ if (fp == 0) +++ exit(1); +++ if (rl_gnu_readline_p != 1) +++ fprintf(fp, "0.0\n"); +++ else +++ fprintf(fp, "%s\n", rl_library_version ? rl_library_version : "0.0"); +++ fclose(fp); +++ exit(0); +++} +++], +++ac_cv_rl_version=`cat conftest.rlv`, +++ac_cv_rl_version='0.0', +++ac_cv_rl_version='8.0')]) +++ +++CFLAGS="$_save_CFLAGS" +++LDFLAGS="$_save_LDFLAGS" +++LIBS="$_save_LIBS" +++ +++RL_MAJOR=0 +++RL_MINOR=0 +++ +++# ( +++case "$ac_cv_rl_version" in +++2*|3*|4*|5*|6*|7*|8*|9*) +++ RL_MAJOR=`echo $ac_cv_rl_version | sed 's:\..*$::'` +++ RL_MINOR=`echo $ac_cv_rl_version | sed -e 's:^.*\.::' -e 's:[[a-zA-Z]]*$::'` +++ ;; +++esac +++ +++# ((( +++case $RL_MAJOR in +++[[0-9][0-9]]) _RL_MAJOR=$RL_MAJOR ;; +++[[0-9]]) _RL_MAJOR=0$RL_MAJOR ;; +++*) _RL_MAJOR=00 ;; +++esac +++ +++# ((( +++case $RL_MINOR in +++[[0-9][0-9]]) _RL_MINOR=$RL_MINOR ;; +++[[0-9]]) _RL_MINOR=0$RL_MINOR ;; +++*) _RL_MINOR=00 ;; +++esac +++ +++RL_VERSION="0x${_RL_MAJOR}${_RL_MINOR}" +++ +++# Readline versions greater than 4.2 have these defines in readline.h +++ +++if test $ac_cv_rl_version = '0.0' ; then +++ AC_MSG_WARN([Could not test version of installed readline library.]) +++elif test $RL_MAJOR -gt 4 || { test $RL_MAJOR = 4 && test $RL_MINOR -gt 2 ; } ; then +++ # set these for use by the caller +++ RL_PREFIX=$ac_cv_rl_prefix +++ RL_LIBDIR=$ac_cv_rl_libdir +++ RL_INCLUDEDIR=$ac_cv_rl_includedir +++ AC_MSG_RESULT($ac_cv_rl_version) +++else +++ +++AC_DEFINE_UNQUOTED(RL_READLINE_VERSION, $RL_VERSION, [encoded version of the installed readline library]) +++AC_DEFINE_UNQUOTED(RL_VERSION_MAJOR, $RL_MAJOR, [major version of installed readline library]) +++AC_DEFINE_UNQUOTED(RL_VERSION_MINOR, $RL_MINOR, [minor version of installed readline library]) +++ +++AC_SUBST(RL_VERSION) +++AC_SUBST(RL_MAJOR) +++AC_SUBST(RL_MINOR) +++ +++# set these for use by the caller +++RL_PREFIX=$ac_cv_rl_prefix +++RL_LIBDIR=$ac_cv_rl_libdir +++RL_INCLUDEDIR=$ac_cv_rl_includedir +++ +++AC_MSG_RESULT($ac_cv_rl_version) +++ +++fi +++]) +++ +++AC_DEFUN(BASH_FUNC_CTYPE_NONASCII, +++[ +++AC_MSG_CHECKING(whether the ctype macros accept non-ascii characters) +++AC_CACHE_VAL(bash_cv_func_ctype_nonascii, +++[AC_TRY_RUN([ +++#ifdef HAVE_LOCALE_H +++#include +++#endif +++#include +++#include + +#include +++ + +int +- main() +- { +- # ifdef GETPGRP_VOID +-@@ -1305,6 +1329,7 @@ AC_CACHE_VAL(bash_cv_must_reinstall_sigh +- #ifdef HAVE_UNISTD_H +- #include +- #endif +++main(c, v) +++int c; +++char *v[]; +++{ +++ char *deflocale; +++ unsigned char x; +++ int r1, r2; +++ +++#ifdef HAVE_SETLOCALE +++ /* We take a shot here. If that locale is not known, try the +++ system default. We try this one because '\342' (226) is +++ known to be a printable character in that locale. */ +++ deflocale = setlocale(LC_ALL, "en_US.ISO8859-1"); +++ if (deflocale == 0) +++ deflocale = setlocale(LC_ALL, ""); +++#endif +++ +++ x = '\342'; +++ r1 = isprint(x); +++ x -= 128; +++ r2 = isprint(x); +++ exit (r1 == 0 || r2 == 0); +++} +++], bash_cv_func_ctype_nonascii=yes, bash_cv_func_ctype_nonascii=no, +++ [AC_MSG_WARN(cannot check ctype macros if cross compiling -- defaulting to no) +++ bash_cv_func_ctype_nonascii=no] +++)]) +++AC_MSG_RESULT($bash_cv_func_ctype_nonascii) +++if test $bash_cv_func_ctype_nonascii = yes; then +++AC_DEFINE(CTYPE_NON_ASCII) +++fi +++]) +++ +++AC_DEFUN(BASH_CHECK_WCONTINUED, +++[ +++AC_MSG_CHECKING(whether WCONTINUED flag to waitpid is unavailable or available but broken) +++AC_CACHE_VAL(bash_cv_wcontinued_broken, +++[AC_TRY_RUN([ +++#include +++#include +++#include +++#include +++ +++#ifndef errno +++extern int errno; +++#endif +++main() +++{ +++ int x; +++ +++ x = waitpid(-1, (int *)0, WNOHANG|WCONTINUED); +++ if (x == -1 && errno == EINVAL) +++ exit (1); +++ else +++ exit (0); +++} +++], bash_cv_wcontinued_broken=no,bash_cv_wcontinued_broken=yes, +++ [AC_MSG_WARN(cannot check WCONTINUED if cross compiling -- defaulting to no) +++ bash_cv_wcontinued_broken=no] +++)]) +++AC_MSG_RESULT($bash_cv_wcontinued_broken) +++if test $bash_cv_wcontinued_broken = yes; then +++AC_DEFINE(WCONTINUED_BROKEN) +++fi +++]) +++ +++dnl +++dnl tests added for bashdb +++dnl +++ +++ +++AC_DEFUN([AM_PATH_LISPDIR], +++ [AC_ARG_WITH(lispdir, AC_HELP_STRING([--with-lispdir], [override the default lisp directory]), +++ [ lispdir="$withval" +++ AC_MSG_CHECKING([where .elc files should go]) +++ AC_MSG_RESULT([$lispdir])], +++ [ +++ # If set to t, that means we are running in a shell under Emacs. +++ # If you have an Emacs named "t", then use the full path. +++ test x"$EMACS" = xt && EMACS= +++ AC_CHECK_PROGS(EMACS, emacs xemacs, no) +++ if test $EMACS != "no"; then +++ if test x${lispdir+set} != xset; then +++ AC_CACHE_CHECK([where .elc files should go], [am_cv_lispdir], [dnl +++ am_cv_lispdir=`$EMACS -batch -q -eval '(while load-path (princ (concat (car load-path) "\n")) (setq load-path (cdr load-path)))' | sed -n -e 's,/$,,' -e '/.*\/lib\/\(x\?emacs\/site-lisp\)$/{s,,${libdir}/\1,;p;q;}' -e '/.*\/share\/\(x\?emacs\/site-lisp\)$/{s,,${datadir}/\1,;p;q;}'` +++ if test -z "$am_cv_lispdir"; then +++ am_cv_lispdir='${datadir}/emacs/site-lisp' +++ fi +++ ]) +++ lispdir="$am_cv_lispdir" +++ fi +++ fi +++ ]) +++ AC_SUBST(lispdir) +++]) +++ +++dnl +++dnl tests added for gettext +++dnl +++# codeset.m4 serial AM1 (gettext-0.10.40) +++dnl Copyright (C) 2000-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++AC_DEFUN([AM_LANGINFO_CODESET], +++[ +++ AC_CACHE_CHECK([for nl_langinfo and CODESET], am_cv_langinfo_codeset, +++ [AC_TRY_LINK([#include ], +++ [char* cs = nl_langinfo(CODESET);], +++ am_cv_langinfo_codeset=yes, +++ am_cv_langinfo_codeset=no) +++ ]) +++ if test $am_cv_langinfo_codeset = yes; then +++ AC_DEFINE(HAVE_LANGINFO_CODESET, 1, +++ [Define if you have and nl_langinfo(CODESET).]) +++ fi +++]) +++# gettext.m4 serial 20 (gettext-0.12) +++dnl Copyright (C) 1995-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++dnl +++dnl This file can can be used in projects which are not available under +++dnl the GNU General Public License or the GNU Library General Public +++dnl License but which still want to provide support for the GNU gettext +++dnl functionality. +++dnl Please note that the actual code of the GNU gettext library is covered +++dnl by the GNU Library General Public License, and the rest of the GNU +++dnl gettext package package is covered by the GNU General Public License. +++dnl They are *not* in the public domain. +++ +++dnl Authors: +++dnl Ulrich Drepper , 1995-2000. +++dnl Bruno Haible , 2000-2003. +++ +++dnl Macro to add for using GNU gettext. +++ +++dnl Usage: AM_GNU_GETTEXT([INTLSYMBOL], [NEEDSYMBOL], [INTLDIR]). +++dnl INTLSYMBOL can be one of 'external', 'no-libtool', 'use-libtool'. The +++dnl default (if it is not specified or empty) is 'no-libtool'. +++dnl INTLSYMBOL should be 'external' for packages with no intl directory, +++dnl and 'no-libtool' or 'use-libtool' for packages with an intl directory. +++dnl If INTLSYMBOL is 'use-libtool', then a libtool library +++dnl $(top_builddir)/intl/libintl.la will be created (shared and/or static, +++dnl depending on --{enable,disable}-{shared,static} and on the presence of +++dnl AM-DISABLE-SHARED). If INTLSYMBOL is 'no-libtool', a static library +++dnl $(top_builddir)/intl/libintl.a will be created. +++dnl If NEEDSYMBOL is specified and is 'need-ngettext', then GNU gettext +++dnl implementations (in libc or libintl) without the ngettext() function +++dnl will be ignored. If NEEDSYMBOL is specified and is +++dnl 'need-formatstring-macros', then GNU gettext implementations that don't +++dnl support the ISO C 99 formatstring macros will be ignored. +++dnl INTLDIR is used to find the intl libraries. If empty, +++dnl the value `$(top_builddir)/intl/' is used. +++dnl +++dnl The result of the configuration is one of three cases: +++dnl 1) GNU gettext, as included in the intl subdirectory, will be compiled +++dnl and used. +++dnl Catalog format: GNU --> install in $(datadir) +++dnl Catalog extension: .mo after installation, .gmo in source tree +++dnl 2) GNU gettext has been found in the system's C library. +++dnl Catalog format: GNU --> install in $(datadir) +++dnl Catalog extension: .mo after installation, .gmo in source tree +++dnl 3) No internationalization, always use English msgid. +++dnl Catalog format: none +++dnl Catalog extension: none +++dnl If INTLSYMBOL is 'external', only cases 2 and 3 can occur. +++dnl The use of .gmo is historical (it was needed to avoid overwriting the +++dnl GNU format catalogs when building on a platform with an X/Open gettext), +++dnl but we keep it in order not to force irrelevant filename changes on the +++dnl maintainers. +++dnl +++AC_DEFUN([AM_GNU_GETTEXT], +++[ +++ dnl Argument checking. +++ ifelse([$1], [], , [ifelse([$1], [external], , [ifelse([$1], [no-libtool], , [ifelse([$1], [use-libtool], , +++ [errprint([ERROR: invalid first argument to AM_GNU_GETTEXT +++])])])])]) +++ ifelse([$2], [], , [ifelse([$2], [need-ngettext], , [ifelse([$2], [need-formatstring-macros], , +++ [errprint([ERROR: invalid second argument to AM_GNU_GETTEXT +++])])])]) +++ define(gt_included_intl, ifelse([$1], [external], [no], [yes])) +++ define(gt_libtool_suffix_prefix, ifelse([$1], [use-libtool], [l], [])) +++ +++ AC_REQUIRE([AM_PO_SUBDIRS])dnl +++ ifelse(gt_included_intl, yes, [ +++ AC_REQUIRE([AM_INTL_SUBDIR])dnl +++ ]) +++ +++ dnl Prerequisites of AC_LIB_LINKFLAGS_BODY. +++ AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) +++ AC_REQUIRE([AC_LIB_RPATH]) +++ +++ dnl Sometimes libintl requires libiconv, so first search for libiconv. +++ dnl Ideally we would do this search only after the +++ dnl if test "$USE_NLS" = "yes"; then +++ dnl if test "$gt_cv_func_gnugettext_libc" != "yes"; then +++ dnl tests. But if configure.in invokes AM_ICONV after AM_GNU_GETTEXT +++ dnl the configure script would need to contain the same shell code +++ dnl again, outside any 'if'. There are two solutions: +++ dnl - Invoke AM_ICONV_LINKFLAGS_BODY here, outside any 'if'. +++ dnl - Control the expansions in more detail using AC_PROVIDE_IFELSE. +++ dnl Since AC_PROVIDE_IFELSE is only in autoconf >= 2.52 and not +++ dnl documented, we avoid it. +++ ifelse(gt_included_intl, yes, , [ +++ AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY]) +++ ]) +++ +++ dnl Set USE_NLS. +++ AM_NLS +++ +++ ifelse(gt_included_intl, yes, [ +++ BUILD_INCLUDED_LIBINTL=no +++ USE_INCLUDED_LIBINTL=no +++ ]) +++ LIBINTL= +++ LTLIBINTL= +++ POSUB= +++ +++ dnl If we use NLS figure out what method +++ if test "$USE_NLS" = "yes"; then +++ gt_use_preinstalled_gnugettext=no +++ ifelse(gt_included_intl, yes, [ +++ AC_MSG_CHECKING([whether included gettext is requested]) +++ AC_ARG_WITH(included-gettext, +++ [ --with-included-gettext use the GNU gettext library included here], +++ nls_cv_force_use_gnu_gettext=$withval, +++ nls_cv_force_use_gnu_gettext=no) +++ AC_MSG_RESULT($nls_cv_force_use_gnu_gettext) +++ +++ nls_cv_use_gnu_gettext="$nls_cv_force_use_gnu_gettext" +++ if test "$nls_cv_force_use_gnu_gettext" != "yes"; then +++ ]) +++ dnl User does not insist on using GNU NLS library. Figure out what +++ dnl to use. If GNU gettext is available we use this. Else we have +++ dnl to fall back to GNU NLS library. +++ +++ dnl Add a version number to the cache macros. +++ define([gt_api_version], ifelse([$2], [need-formatstring-macros], 3, ifelse([$2], [need-ngettext], 2, 1))) +++ define([gt_cv_func_gnugettext_libc], [gt_cv_func_gnugettext]gt_api_version[_libc]) +++ define([gt_cv_func_gnugettext_libintl], [gt_cv_func_gnugettext]gt_api_version[_libintl]) +++ +++ AC_CACHE_CHECK([for GNU gettext in libc], gt_cv_func_gnugettext_libc, +++ [AC_TRY_LINK([#include +++]ifelse([$2], [need-formatstring-macros], +++[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION +++#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1) +++#endif +++changequote(,)dnl +++typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1]; +++changequote([,])dnl +++], [])[extern int _nl_msg_cat_cntr; +++extern int *_nl_domain_bindings;], +++ [bindtextdomain ("", ""); +++return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_domain_bindings], +++ gt_cv_func_gnugettext_libc=yes, +++ gt_cv_func_gnugettext_libc=no)]) +++ +++ if test "$gt_cv_func_gnugettext_libc" != "yes"; then +++ dnl Sometimes libintl requires libiconv, so first search for libiconv. +++ ifelse(gt_included_intl, yes, , [ +++ AM_ICONV_LINK +++ ]) +++ dnl Search for libintl and define LIBINTL, LTLIBINTL and INCINTL +++ dnl accordingly. Don't use AC_LIB_LINKFLAGS_BODY([intl],[iconv]) +++ dnl because that would add "-liconv" to LIBINTL and LTLIBINTL +++ dnl even if libiconv doesn't exist. +++ AC_LIB_LINKFLAGS_BODY([intl]) +++ AC_CACHE_CHECK([for GNU gettext in libintl], +++ gt_cv_func_gnugettext_libintl, +++ [gt_save_CPPFLAGS="$CPPFLAGS" +++ CPPFLAGS="$CPPFLAGS $INCINTL" +++ gt_save_LIBS="$LIBS" +++ LIBS="$LIBS $LIBINTL" +++ dnl Now see whether libintl exists and does not depend on libiconv. +++ AC_TRY_LINK([#include +++]ifelse([$2], [need-formatstring-macros], +++[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION +++#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1) +++#endif +++changequote(,)dnl +++typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1]; +++changequote([,])dnl +++], [])[extern int _nl_msg_cat_cntr; +++extern +++#ifdef __cplusplus +++"C" +++#endif +++const char *_nl_expand_alias ();], +++ [bindtextdomain ("", ""); +++return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_expand_alias (0)], +++ gt_cv_func_gnugettext_libintl=yes, +++ gt_cv_func_gnugettext_libintl=no) +++ dnl Now see whether libintl exists and depends on libiconv. +++ if test "$gt_cv_func_gnugettext_libintl" != yes && test -n "$LIBICONV"; then +++ LIBS="$LIBS $LIBICONV" +++ AC_TRY_LINK([#include +++]ifelse([$2], [need-formatstring-macros], +++[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION +++#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1) +++#endif +++changequote(,)dnl +++typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1]; +++changequote([,])dnl +++], [])[extern int _nl_msg_cat_cntr; +++extern +++#ifdef __cplusplus +++"C" +++#endif +++const char *_nl_expand_alias ();], +++ [bindtextdomain ("", ""); +++return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_expand_alias (0)], +++ [LIBINTL="$LIBINTL $LIBICONV" +++ LTLIBINTL="$LTLIBINTL $LTLIBICONV" +++ gt_cv_func_gnugettext_libintl=yes +++ ]) +++ fi +++ CPPFLAGS="$gt_save_CPPFLAGS" +++ LIBS="$gt_save_LIBS"]) +++ fi +++ +++ dnl If an already present or preinstalled GNU gettext() is found, +++ dnl use it. But if this macro is used in GNU gettext, and GNU +++ dnl gettext is already preinstalled in libintl, we update this +++ dnl libintl. (Cf. the install rule in intl/Makefile.in.) +++ if test "$gt_cv_func_gnugettext_libc" = "yes" \ +++ || { test "$gt_cv_func_gnugettext_libintl" = "yes" \ +++ && test "$PACKAGE" != gettext-runtime \ +++ && test "$PACKAGE" != gettext-tools; }; then +++ gt_use_preinstalled_gnugettext=yes +++ else +++ dnl Reset the values set by searching for libintl. +++ LIBINTL= +++ LTLIBINTL= +++ INCINTL= +++ fi +++ +++ ifelse(gt_included_intl, yes, [ +++ if test "$gt_use_preinstalled_gnugettext" != "yes"; then +++ dnl GNU gettext is not found in the C library. +++ dnl Fall back on included GNU gettext library. +++ nls_cv_use_gnu_gettext=yes +++ fi +++ fi +++ +++ if test "$nls_cv_use_gnu_gettext" = "yes"; then +++ dnl Mark actions used to generate GNU NLS library. +++ BUILD_INCLUDED_LIBINTL=yes +++ USE_INCLUDED_LIBINTL=yes +++ LIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LIBICONV" +++ LTLIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LTLIBICONV" +++ LIBS=`echo " $LIBS " | sed -e 's/ -lintl / /' -e 's/^ //' -e 's/ $//'` +++ fi +++ +++ if test "$gt_use_preinstalled_gnugettext" = "yes" \ +++ || test "$nls_cv_use_gnu_gettext" = "yes"; then +++ dnl Mark actions to use GNU gettext tools. +++ CATOBJEXT=.gmo +++ fi +++ ]) +++ +++ if test "$gt_use_preinstalled_gnugettext" = "yes" \ +++ || test "$nls_cv_use_gnu_gettext" = "yes"; then +++ AC_DEFINE(ENABLE_NLS, 1, +++ [Define to 1 if translation of program messages to the user's native language +++ is requested.]) +++ else +++ USE_NLS=no +++ fi +++ fi +++ +++ AC_MSG_CHECKING([whether to use NLS]) +++ AC_MSG_RESULT([$USE_NLS]) +++ if test "$USE_NLS" = "yes"; then +++ AC_MSG_CHECKING([where the gettext function comes from]) +++ if test "$gt_use_preinstalled_gnugettext" = "yes"; then +++ if test "$gt_cv_func_gnugettext_libintl" = "yes"; then +++ gt_source="external libintl" +++ else +++ gt_source="libc" +++ fi +++ else +++ gt_source="included intl directory" +++ fi +++ AC_MSG_RESULT([$gt_source]) +++ fi +++ +++ if test "$USE_NLS" = "yes"; then +++ +++ if test "$gt_use_preinstalled_gnugettext" = "yes"; then +++ if test "$gt_cv_func_gnugettext_libintl" = "yes"; then +++ AC_MSG_CHECKING([how to link with libintl]) +++ AC_MSG_RESULT([$LIBINTL]) +++ AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCINTL]) +++ fi +++ +++ dnl For backward compatibility. Some packages may be using this. +++ AC_DEFINE(HAVE_GETTEXT, 1, +++ [Define if the GNU gettext() function is already present or preinstalled.]) +++ AC_DEFINE(HAVE_DCGETTEXT, 1, +++ [Define if the GNU dcgettext() function is already present or preinstalled.]) +++ fi +++ +++ dnl We need to process the po/ directory. +++ POSUB=po +++ fi +++ +++ ifelse(gt_included_intl, yes, [ +++ dnl If this is used in GNU gettext we have to set BUILD_INCLUDED_LIBINTL +++ dnl to 'yes' because some of the testsuite requires it. +++ if test "$PACKAGE" = gettext-runtime || test "$PACKAGE" = gettext-tools; then +++ BUILD_INCLUDED_LIBINTL=yes +++ fi +++ +++ dnl Make all variables we use known to autoconf. +++ AC_SUBST(BUILD_INCLUDED_LIBINTL) +++ AC_SUBST(USE_INCLUDED_LIBINTL) +++ AC_SUBST(CATOBJEXT) +++ +++ dnl For backward compatibility. Some configure.ins may be using this. +++ nls_cv_header_intl= +++ nls_cv_header_libgt= +++ +++ dnl For backward compatibility. Some Makefiles may be using this. +++ DATADIRNAME=share +++ AC_SUBST(DATADIRNAME) +++ +++ dnl For backward compatibility. Some Makefiles may be using this. +++ INSTOBJEXT=.mo +++ AC_SUBST(INSTOBJEXT) +++ +++ dnl For backward compatibility. Some Makefiles may be using this. +++ GENCAT=gencat +++ AC_SUBST(GENCAT) +++ +++ dnl For backward compatibility. Some Makefiles may be using this. +++ if test "$USE_INCLUDED_LIBINTL" = yes; then +++ INTLOBJS="\$(GETTOBJS)" +++ fi +++ AC_SUBST(INTLOBJS) +++ +++ dnl Enable libtool support if the surrounding package wishes it. +++ INTL_LIBTOOL_SUFFIX_PREFIX=gt_libtool_suffix_prefix +++ AC_SUBST(INTL_LIBTOOL_SUFFIX_PREFIX) +++ ]) +++ +++ dnl For backward compatibility. Some Makefiles may be using this. +++ INTLLIBS="$LIBINTL" +++ AC_SUBST(INTLLIBS) +++ +++ dnl Make all documented variables known to autoconf. +++ AC_SUBST(LIBINTL) +++ AC_SUBST(LTLIBINTL) +++ AC_SUBST(POSUB) +++]) +++ +++ +++dnl Checks for all prerequisites of the intl subdirectory, +++dnl except for INTL_LIBTOOL_SUFFIX_PREFIX (and possibly LIBTOOL), INTLOBJS, +++dnl USE_INCLUDED_LIBINTL, BUILD_INCLUDED_LIBINTL. +++AC_DEFUN([AM_INTL_SUBDIR], +++[ +++ AC_REQUIRE([AC_PROG_INSTALL])dnl +++ AC_REQUIRE([AM_MKINSTALLDIRS])dnl +++ AC_REQUIRE([AC_PROG_CC])dnl +++ AC_REQUIRE([AC_CANONICAL_HOST])dnl +++ AC_REQUIRE([AC_PROG_RANLIB])dnl +++ AC_REQUIRE([AC_ISC_POSIX])dnl +++ AC_REQUIRE([AC_HEADER_STDC])dnl +++ AC_REQUIRE([AC_C_CONST])dnl +++ AC_REQUIRE([AC_C_INLINE])dnl +++ AC_REQUIRE([AC_TYPE_OFF_T])dnl +++ AC_REQUIRE([AC_TYPE_SIZE_T])dnl +++ AC_REQUIRE([AC_FUNC_ALLOCA])dnl +++ AC_REQUIRE([AC_FUNC_MMAP])dnl +++ AC_REQUIRE([jm_GLIBC21])dnl +++ AC_REQUIRE([gt_INTDIV0])dnl +++ AC_REQUIRE([jm_AC_TYPE_UINTMAX_T])dnl +++ AC_REQUIRE([gt_HEADER_INTTYPES_H])dnl +++ AC_REQUIRE([gt_INTTYPES_PRI])dnl +++ +++ AC_CHECK_HEADERS([argz.h limits.h locale.h nl_types.h malloc.h stddef.h \ +++stdlib.h string.h unistd.h sys/param.h]) +++ AC_CHECK_FUNCS([feof_unlocked fgets_unlocked getc_unlocked getcwd getegid \ +++geteuid getgid getuid mempcpy munmap putenv setenv setlocale localeconv stpcpy \ +++strcasecmp strdup strtoul tsearch __argz_count __argz_stringify __argz_next \ +++__fsetlocking]) +++ +++ AM_ICONV +++ AM_LANGINFO_CODESET +++ if test $ac_cv_header_locale_h = yes; then +++ AM_LC_MESSAGES +++ fi +++ +++ dnl intl/plural.c is generated from intl/plural.y. It requires bison, +++ dnl because plural.y uses bison specific features. It requires at least +++ dnl bison-1.26 because earlier versions generate a plural.c that doesn't +++ dnl compile. +++ dnl bison is only needed for the maintainer (who touches plural.y). But in +++ dnl order to avoid separate Makefiles or --enable-maintainer-mode, we put +++ dnl the rule in general Makefile. Now, some people carelessly touch the +++ dnl files or have a broken "make" program, hence the plural.c rule will +++ dnl sometimes fire. To avoid an error, defines BISON to ":" if it is not +++ dnl present or too old. +++ AC_CHECK_PROGS([INTLBISON], [bison]) +++ if test -z "$INTLBISON"; then +++ ac_verc_fail=yes +++ else +++ dnl Found it, now check the version. +++ AC_MSG_CHECKING([version of bison]) +++changequote(<<,>>)dnl +++ ac_prog_version=`$INTLBISON --version 2>&1 | sed -n 's/^.*GNU Bison.* \([0-9]*\.[0-9.]*\).*$/\1/p'` +++ case $ac_prog_version in +++ '') ac_prog_version="v. ?.??, bad"; ac_verc_fail=yes;; +++ 1.2[6-9]* | 1.[3-9][0-9]* | [2-9].*) +++changequote([,])dnl +++ ac_prog_version="$ac_prog_version, ok"; ac_verc_fail=no;; +++ *) ac_prog_version="$ac_prog_version, bad"; ac_verc_fail=yes;; +++ esac +++ AC_MSG_RESULT([$ac_prog_version]) +++ fi +++ if test $ac_verc_fail = yes; then +++ INTLBISON=: +++ fi +++]) +++ +++ +++dnl Usage: AM_GNU_GETTEXT_VERSION([gettext-version]) +++AC_DEFUN([AM_GNU_GETTEXT_VERSION], []) +++# glibc21.m4 serial 2 (fileutils-4.1.3, gettext-0.10.40) +++dnl Copyright (C) 2000-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++# Test for the GNU C Library, version 2.1 or newer. +++# From Bruno Haible. +++ +++AC_DEFUN([jm_GLIBC21], +++ [ +++ AC_CACHE_CHECK(whether we are using the GNU C Library 2.1 or newer, +++ ac_cv_gnu_library_2_1, +++ [AC_EGREP_CPP([Lucky GNU user], +++ [ +++#include +++#ifdef __GNU_LIBRARY__ +++ #if (__GLIBC__ == 2 && __GLIBC_MINOR__ >= 1) || (__GLIBC__ > 2) +++ Lucky GNU user +++ #endif +++#endif +++ ], +++ ac_cv_gnu_library_2_1=yes, +++ ac_cv_gnu_library_2_1=no) +++ ] +++ ) +++ AC_SUBST(GLIBC21) +++ GLIBC21="$ac_cv_gnu_library_2_1" +++ ] +++) +++# iconv.m4 serial AM4 (gettext-0.11.3) +++dnl Copyright (C) 2000-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++AC_DEFUN([AM_ICONV_LINKFLAGS_BODY], +++[ +++ dnl Prerequisites of AC_LIB_LINKFLAGS_BODY. +++ AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) +++ AC_REQUIRE([AC_LIB_RPATH]) +++ +++ dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV +++ dnl accordingly. +++ AC_LIB_LINKFLAGS_BODY([iconv]) +++]) +++ +++AC_DEFUN([AM_ICONV_LINK], +++[ +++ dnl Some systems have iconv in libc, some have it in libiconv (OSF/1 and +++ dnl those with the standalone portable GNU libiconv installed). +++ +++ dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV +++ dnl accordingly. +++ AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY]) +++ +++ dnl Add $INCICONV to CPPFLAGS before performing the following checks, +++ dnl because if the user has installed libiconv and not disabled its use +++ dnl via --without-libiconv-prefix, he wants to use it. The first +++ dnl AC_TRY_LINK will then fail, the second AC_TRY_LINK will succeed. +++ am_save_CPPFLAGS="$CPPFLAGS" +++ AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCICONV]) +++ +++ AC_CACHE_CHECK(for iconv, am_cv_func_iconv, [ +++ am_cv_func_iconv="no, consider installing GNU libiconv" +++ am_cv_lib_iconv=no +++ AC_TRY_LINK([#include +++#include ], +++ [iconv_t cd = iconv_open("",""); +++ iconv(cd,NULL,NULL,NULL,NULL); +++ iconv_close(cd);], +++ am_cv_func_iconv=yes) +++ if test "$am_cv_func_iconv" != yes; then +++ am_save_LIBS="$LIBS" +++ LIBS="$LIBS $LIBICONV" +++ AC_TRY_LINK([#include +++#include ], +++ [iconv_t cd = iconv_open("",""); +++ iconv(cd,NULL,NULL,NULL,NULL); +++ iconv_close(cd);], +++ am_cv_lib_iconv=yes +++ am_cv_func_iconv=yes) +++ LIBS="$am_save_LIBS" +++ fi +++ ]) +++ if test "$am_cv_func_iconv" = yes; then +++ AC_DEFINE(HAVE_ICONV, 1, [Define if you have the iconv() function.]) +++ fi +++ if test "$am_cv_lib_iconv" = yes; then +++ AC_MSG_CHECKING([how to link with libiconv]) +++ AC_MSG_RESULT([$LIBICONV]) +++ else +++ dnl If $LIBICONV didn't lead to a usable library, we don't need $INCICONV +++ dnl either. +++ CPPFLAGS="$am_save_CPPFLAGS" +++ LIBICONV= +++ LTLIBICONV= +++ fi +++ AC_SUBST(LIBICONV) +++ AC_SUBST(LTLIBICONV) +++]) +++ +++AC_DEFUN([AM_ICONV], +++[ +++ AM_ICONV_LINK +++ if test "$am_cv_func_iconv" = yes; then +++ AC_MSG_CHECKING([for iconv declaration]) +++ AC_CACHE_VAL(am_cv_proto_iconv, [ +++ AC_TRY_COMPILE([ + +#include +- +- typedef RETSIGTYPE sigfunc(); +- +-@@ -1335,6 +1360,7 @@ int s; +- nsigint++; +- } +- +-+int +- main() +- { +- nsigint = 0; +-@@ -1418,8 +1444,11 @@ AC_CACHE_VAL(bash_cv_sys_named_pipes, +- #ifdef HAVE_UNISTD_H +- #include +- #endif +++#include +++extern +++#ifdef __cplusplus +++"C" +++#endif +++#if defined(__STDC__) || defined(__cplusplus) +++size_t iconv (iconv_t cd, char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft); +++#else +++size_t iconv(); +++#endif +++], [], am_cv_proto_iconv_arg1="", am_cv_proto_iconv_arg1="const") +++ am_cv_proto_iconv="extern size_t iconv (iconv_t cd, $am_cv_proto_iconv_arg1 char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft);"]) +++ am_cv_proto_iconv=`echo "[$]am_cv_proto_iconv" | tr -s ' ' | sed -e 's/( /(/'` +++ AC_MSG_RESULT([$]{ac_t:- +++ }[$]am_cv_proto_iconv) +++ AC_DEFINE_UNQUOTED(ICONV_CONST, $am_cv_proto_iconv_arg1, +++ [Define as const if the declaration of iconv() needs const.]) +++ fi +++]) +++# intdiv0.m4 serial 1 (gettext-0.11.3) +++dnl Copyright (C) 2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++AC_DEFUN([gt_INTDIV0], +++[ +++ AC_REQUIRE([AC_PROG_CC])dnl +++ AC_REQUIRE([AC_CANONICAL_HOST])dnl +++ +++ AC_CACHE_CHECK([whether integer division by zero raises SIGFPE], +++ gt_cv_int_divbyzero_sigfpe, +++ [ +++ AC_TRY_RUN([ +++#include +++#include +++ +++static void +++#ifdef __cplusplus +++sigfpe_handler (int sig) +++#else +++sigfpe_handler (sig) int sig; +++#endif +++{ +++ /* Exit with code 0 if SIGFPE, with code 1 if any other signal. */ +++ exit (sig != SIGFPE); +++} +++ +++int x = 1; +++int y = 0; +++int z; +++int nan; +++ +++int main () +++{ +++ signal (SIGFPE, sigfpe_handler); +++/* IRIX and AIX (when "xlc -qcheck" is used) yield signal SIGTRAP. */ +++#if (defined (__sgi) || defined (_AIX)) && defined (SIGTRAP) +++ signal (SIGTRAP, sigfpe_handler); +++#endif +++/* Linux/SPARC yields signal SIGILL. */ +++#if defined (__sparc__) && defined (__linux__) +++ signal (SIGILL, sigfpe_handler); +++#endif +++ +++ z = x / y; +++ nan = y / y; +++ exit (1); +++} +++], gt_cv_int_divbyzero_sigfpe=yes, gt_cv_int_divbyzero_sigfpe=no, +++ [ +++ # Guess based on the CPU. +++ case "$host_cpu" in +++ alpha* | i[34567]86 | m68k | s390*) +++ gt_cv_int_divbyzero_sigfpe="guessing yes";; +++ *) +++ gt_cv_int_divbyzero_sigfpe="guessing no";; +++ esac +++ ]) +++ ]) +++ case "$gt_cv_int_divbyzero_sigfpe" in +++ *yes) value=1;; +++ *) value=0;; +++ esac +++ AC_DEFINE_UNQUOTED(INTDIV0_RAISES_SIGFPE, $value, +++ [Define if integer division by zero raises signal SIGFPE.]) +++]) +++# inttypes.m4 serial 1 (gettext-0.11.4) +++dnl Copyright (C) 1997-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Paul Eggert. +++ +++# Define HAVE_INTTYPES_H if exists and doesn't clash with +++# . +++ +++AC_DEFUN([gt_HEADER_INTTYPES_H], +++[ +++ AC_CACHE_CHECK([for inttypes.h], gt_cv_header_inttypes_h, +++ [ +++ AC_TRY_COMPILE( +++ [#include +++#include ], +++ [], gt_cv_header_inttypes_h=yes, gt_cv_header_inttypes_h=no) +++ ]) +++ if test $gt_cv_header_inttypes_h = yes; then +++ AC_DEFINE_UNQUOTED(HAVE_INTTYPES_H, 1, +++ [Define if exists and doesn't clash with .]) +++ fi +++]) +++# inttypes_h.m4 serial 5 (gettext-0.12) +++dnl Copyright (C) 1997-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Paul Eggert. +++ +++# Define HAVE_INTTYPES_H_WITH_UINTMAX if exists, +++# doesn't clash with , and declares uintmax_t. +++ +++AC_DEFUN([jm_AC_HEADER_INTTYPES_H], +++[ +++ AC_CACHE_CHECK([for inttypes.h], jm_ac_cv_header_inttypes_h, +++ [AC_TRY_COMPILE( +++ [#include +++#include ], +++ [uintmax_t i = (uintmax_t) -1;], +++ jm_ac_cv_header_inttypes_h=yes, +++ jm_ac_cv_header_inttypes_h=no)]) +++ if test $jm_ac_cv_header_inttypes_h = yes; then +++ AC_DEFINE_UNQUOTED(HAVE_INTTYPES_H_WITH_UINTMAX, 1, +++ [Define if exists, doesn't clash with , +++ and declares uintmax_t. ]) +++ fi +++]) +++# inttypes-pri.m4 serial 1 (gettext-0.11.4) +++dnl Copyright (C) 1997-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++# Define PRI_MACROS_BROKEN if exists and defines the PRI* +++# macros to non-string values. This is the case on AIX 4.3.3. +++ +++AC_DEFUN([gt_INTTYPES_PRI], +++[ +++ AC_REQUIRE([gt_HEADER_INTTYPES_H]) +++ if test $gt_cv_header_inttypes_h = yes; then +++ AC_CACHE_CHECK([whether the inttypes.h PRIxNN macros are broken], +++ gt_cv_inttypes_pri_broken, +++ [ +++ AC_TRY_COMPILE([#include +++#ifdef PRId32 +++char *p = PRId32; +++#endif +++], [], gt_cv_inttypes_pri_broken=no, gt_cv_inttypes_pri_broken=yes) +++ ]) +++ fi +++ if test "$gt_cv_inttypes_pri_broken" = yes; then +++ AC_DEFINE_UNQUOTED(PRI_MACROS_BROKEN, 1, +++ [Define if exists and defines unusable PRI* macros.]) +++ fi +++]) +++# isc-posix.m4 serial 2 (gettext-0.11.2) +++dnl Copyright (C) 1995-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++# This file is not needed with autoconf-2.53 and newer. Remove it in 2005. +++ +++# This test replaces the one in autoconf. +++# Currently this macro should have the same name as the autoconf macro +++# because gettext's gettext.m4 (distributed in the automake package) +++# still uses it. Otherwise, the use in gettext.m4 makes autoheader +++# give these diagnostics: +++# configure.in:556: AC_TRY_COMPILE was called before AC_ISC_POSIX +++# configure.in:556: AC_TRY_RUN was called before AC_ISC_POSIX +++ +++undefine([AC_ISC_POSIX]) +++ +++AC_DEFUN([AC_ISC_POSIX], +++ [ +++ dnl This test replaces the obsolescent AC_ISC_POSIX kludge. +++ AC_CHECK_LIB(cposix, strerror, [LIBS="$LIBS -lcposix"]) +++ ] +++) +++# lcmessage.m4 serial 3 (gettext-0.11.3) +++dnl Copyright (C) 1995-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++dnl +++dnl This file can can be used in projects which are not available under +++dnl the GNU General Public License or the GNU Library General Public +++dnl License but which still want to provide support for the GNU gettext +++dnl functionality. +++dnl Please note that the actual code of the GNU gettext library is covered +++dnl by the GNU Library General Public License, and the rest of the GNU +++dnl gettext package package is covered by the GNU General Public License. +++dnl They are *not* in the public domain. +++ +++dnl Authors: +++dnl Ulrich Drepper , 1995. +++ +++# Check whether LC_MESSAGES is available in . +++ +++AC_DEFUN([AM_LC_MESSAGES], +++[ +++ AC_CACHE_CHECK([for LC_MESSAGES], am_cv_val_LC_MESSAGES, +++ [AC_TRY_LINK([#include ], [return LC_MESSAGES], +++ am_cv_val_LC_MESSAGES=yes, am_cv_val_LC_MESSAGES=no)]) +++ if test $am_cv_val_LC_MESSAGES = yes; then +++ AC_DEFINE(HAVE_LC_MESSAGES, 1, +++ [Define if your file defines LC_MESSAGES.]) +++ fi +++]) +++# lib-ld.m4 serial 2 (gettext-0.12) +++dnl Copyright (C) 1996-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl Subroutines of libtool.m4, +++dnl with replacements s/AC_/AC_LIB/ and s/lt_cv/acl_cv/ to avoid collision +++dnl with libtool.m4. +++ +++dnl From libtool-1.4. Sets the variable with_gnu_ld to yes or no. +++AC_DEFUN([AC_LIB_PROG_LD_GNU], +++[AC_CACHE_CHECK([if the linker ($LD) is GNU ld], acl_cv_prog_gnu_ld, +++[# I'd rather use --version here, but apparently some GNU ld's only accept -v. +++if $LD -v 2>&1 &5; then +++ acl_cv_prog_gnu_ld=yes +++else +++ acl_cv_prog_gnu_ld=no +++fi]) +++with_gnu_ld=$acl_cv_prog_gnu_ld +++]) +++ +++dnl From libtool-1.4. Sets the variable LD. +++AC_DEFUN([AC_LIB_PROG_LD], +++[AC_ARG_WITH(gnu-ld, +++[ --with-gnu-ld assume the C compiler uses GNU ld [default=no]], +++test "$withval" = no || with_gnu_ld=yes, with_gnu_ld=no) +++AC_REQUIRE([AC_PROG_CC])dnl +++AC_REQUIRE([AC_CANONICAL_HOST])dnl +++# Prepare PATH_SEPARATOR. +++# The user is always right. +++if test "${PATH_SEPARATOR+set}" != set; then +++ echo "#! /bin/sh" >conf$$.sh +++ echo "exit 0" >>conf$$.sh +++ chmod +x conf$$.sh +++ if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then +++ PATH_SEPARATOR=';' +++ else +++ PATH_SEPARATOR=: +++ fi +++ rm -f conf$$.sh +++fi +++ac_prog=ld +++if test "$GCC" = yes; then +++ # Check if gcc -print-prog-name=ld gives a path. +++ AC_MSG_CHECKING([for ld used by GCC]) +++ case $host in +++ *-*-mingw*) +++ # gcc leaves a trailing carriage return which upsets mingw +++ ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; +++ *) +++ ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; +++ esac +++ case $ac_prog in +++ # Accept absolute paths. +++ [[\\/]* | [A-Za-z]:[\\/]*)] +++ [re_direlt='/[^/][^/]*/\.\./'] +++ # Canonicalize the path of ld +++ ac_prog=`echo $ac_prog| sed 's%\\\\%/%g'` +++ while echo $ac_prog | grep "$re_direlt" > /dev/null 2>&1; do +++ ac_prog=`echo $ac_prog| sed "s%$re_direlt%/%"` +++ done +++ test -z "$LD" && LD="$ac_prog" +++ ;; +++ "") +++ # If it fails, then pretend we aren't using GCC. +++ ac_prog=ld +++ ;; +++ *) +++ # If it is relative, then search for the first ld in PATH. +++ with_gnu_ld=unknown +++ ;; +++ esac +++elif test "$with_gnu_ld" = yes; then +++ AC_MSG_CHECKING([for GNU ld]) +++else +++ AC_MSG_CHECKING([for non-GNU ld]) +++fi +++AC_CACHE_VAL(acl_cv_path_LD, +++[if test -z "$LD"; then +++ IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}${PATH_SEPARATOR-:}" +++ for ac_dir in $PATH; do +++ test -z "$ac_dir" && ac_dir=. +++ if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then +++ acl_cv_path_LD="$ac_dir/$ac_prog" +++ # Check to see if the program is GNU ld. I'd rather use --version, +++ # but apparently some GNU ld's only accept -v. +++ # Break only if it was the GNU/non-GNU ld that we prefer. +++ if "$acl_cv_path_LD" -v 2>&1 < /dev/null | egrep '(GNU|with BFD)' > /dev/null; then +++ test "$with_gnu_ld" != no && break +++ else +++ test "$with_gnu_ld" != yes && break +++ fi +++ fi +++ done +++ IFS="$ac_save_ifs" +++else +++ acl_cv_path_LD="$LD" # Let the user override the test with a path. +++fi]) +++LD="$acl_cv_path_LD" +++if test -n "$LD"; then +++ AC_MSG_RESULT($LD) +++else +++ AC_MSG_RESULT(no) +++fi +++test -z "$LD" && AC_MSG_ERROR([no acceptable ld found in \$PATH]) +++AC_LIB_PROG_LD_GNU +++]) +++# lib-link.m4 serial 4 (gettext-0.12) +++dnl Copyright (C) 2001-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++dnl AC_LIB_LINKFLAGS(name [, dependencies]) searches for libname and +++dnl the libraries corresponding to explicit and implicit dependencies. +++dnl Sets and AC_SUBSTs the LIB${NAME} and LTLIB${NAME} variables and +++dnl augments the CPPFLAGS variable. +++AC_DEFUN([AC_LIB_LINKFLAGS], +++[ +++ AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) +++ AC_REQUIRE([AC_LIB_RPATH]) +++ define([Name],[translit([$1],[./-], [___])]) +++ define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], +++ [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) +++ AC_CACHE_CHECK([how to link with lib[]$1], [ac_cv_lib[]Name[]_libs], [ +++ AC_LIB_LINKFLAGS_BODY([$1], [$2]) +++ ac_cv_lib[]Name[]_libs="$LIB[]NAME" +++ ac_cv_lib[]Name[]_ltlibs="$LTLIB[]NAME" +++ ac_cv_lib[]Name[]_cppflags="$INC[]NAME" +++ ]) +++ LIB[]NAME="$ac_cv_lib[]Name[]_libs" +++ LTLIB[]NAME="$ac_cv_lib[]Name[]_ltlibs" +++ INC[]NAME="$ac_cv_lib[]Name[]_cppflags" +++ AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME) +++ AC_SUBST([LIB]NAME) +++ AC_SUBST([LTLIB]NAME) +++ dnl Also set HAVE_LIB[]NAME so that AC_LIB_HAVE_LINKFLAGS can reuse the +++ dnl results of this search when this library appears as a dependency. +++ HAVE_LIB[]NAME=yes +++ undefine([Name]) +++ undefine([NAME]) +++]) +++ +++dnl AC_LIB_HAVE_LINKFLAGS(name, dependencies, includes, testcode) +++dnl searches for libname and the libraries corresponding to explicit and +++dnl implicit dependencies, together with the specified include files and +++dnl the ability to compile and link the specified testcode. If found, it +++dnl sets and AC_SUBSTs HAVE_LIB${NAME}=yes and the LIB${NAME} and +++dnl LTLIB${NAME} variables and augments the CPPFLAGS variable, and +++dnl #defines HAVE_LIB${NAME} to 1. Otherwise, it sets and AC_SUBSTs +++dnl HAVE_LIB${NAME}=no and LIB${NAME} and LTLIB${NAME} to empty. +++AC_DEFUN([AC_LIB_HAVE_LINKFLAGS], +++[ +++ AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) +++ AC_REQUIRE([AC_LIB_RPATH]) +++ define([Name],[translit([$1],[./-], [___])]) +++ define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], +++ [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) +++ +++ dnl Search for lib[]Name and define LIB[]NAME, LTLIB[]NAME and INC[]NAME +++ dnl accordingly. +++ AC_LIB_LINKFLAGS_BODY([$1], [$2]) +++ +++ dnl Add $INC[]NAME to CPPFLAGS before performing the following checks, +++ dnl because if the user has installed lib[]Name and not disabled its use +++ dnl via --without-lib[]Name-prefix, he wants to use it. +++ ac_save_CPPFLAGS="$CPPFLAGS" +++ AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME) +++ +++ AC_CACHE_CHECK([for lib[]$1], [ac_cv_lib[]Name], [ +++ ac_save_LIBS="$LIBS" +++ LIBS="$LIBS $LIB[]NAME" +++ AC_TRY_LINK([$3], [$4], [ac_cv_lib[]Name=yes], [ac_cv_lib[]Name=no]) +++ LIBS="$ac_save_LIBS" +++ ]) +++ if test "$ac_cv_lib[]Name" = yes; then +++ HAVE_LIB[]NAME=yes +++ AC_DEFINE([HAVE_LIB]NAME, 1, [Define if you have the $1 library.]) +++ AC_MSG_CHECKING([how to link with lib[]$1]) +++ AC_MSG_RESULT([$LIB[]NAME]) +++ else +++ HAVE_LIB[]NAME=no +++ dnl If $LIB[]NAME didn't lead to a usable library, we don't need +++ dnl $INC[]NAME either. +++ CPPFLAGS="$ac_save_CPPFLAGS" +++ LIB[]NAME= +++ LTLIB[]NAME= +++ fi +++ AC_SUBST([HAVE_LIB]NAME) +++ AC_SUBST([LIB]NAME) +++ AC_SUBST([LTLIB]NAME) +++ undefine([Name]) +++ undefine([NAME]) +++]) +++ +++dnl Determine the platform dependent parameters needed to use rpath: +++dnl libext, shlibext, hardcode_libdir_flag_spec, hardcode_libdir_separator, +++dnl hardcode_direct, hardcode_minus_L. +++AC_DEFUN([AC_LIB_RPATH], +++[ +++ AC_REQUIRE([AC_PROG_CC]) dnl we use $CC, $GCC, $LDFLAGS +++ AC_REQUIRE([AC_LIB_PROG_LD]) dnl we use $LD, $with_gnu_ld +++ AC_REQUIRE([AC_CANONICAL_HOST]) dnl we use $host +++ AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT]) dnl we use $ac_aux_dir +++ AC_CACHE_CHECK([for shared library run path origin], acl_cv_rpath, [ +++ CC="$CC" GCC="$GCC" LDFLAGS="$LDFLAGS" LD="$LD" with_gnu_ld="$with_gnu_ld" \ +++ ${CONFIG_SHELL-/bin/sh} "$ac_aux_dir/config.rpath" "$host" > conftest.sh +++ . ./conftest.sh +++ rm -f ./conftest.sh +++ acl_cv_rpath=done +++ ]) +++ wl="$acl_cv_wl" +++ libext="$acl_cv_libext" +++ shlibext="$acl_cv_shlibext" +++ hardcode_libdir_flag_spec="$acl_cv_hardcode_libdir_flag_spec" +++ hardcode_libdir_separator="$acl_cv_hardcode_libdir_separator" +++ hardcode_direct="$acl_cv_hardcode_direct" +++ hardcode_minus_L="$acl_cv_hardcode_minus_L" +++ dnl Determine whether the user wants rpath handling at all. +++ AC_ARG_ENABLE(rpath, +++ [ --disable-rpath do not hardcode runtime library paths], +++ :, enable_rpath=yes) +++]) +++ +++dnl AC_LIB_LINKFLAGS_BODY(name [, dependencies]) searches for libname and +++dnl the libraries corresponding to explicit and implicit dependencies. +++dnl Sets the LIB${NAME}, LTLIB${NAME} and INC${NAME} variables. +++AC_DEFUN([AC_LIB_LINKFLAGS_BODY], +++[ +++ define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-], +++ [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])]) +++ dnl By default, look in $includedir and $libdir. +++ use_additional=yes +++ AC_LIB_WITH_FINAL_PREFIX([ +++ eval additional_includedir=\"$includedir\" +++ eval additional_libdir=\"$libdir\" +++ ]) +++ AC_LIB_ARG_WITH([lib$1-prefix], +++[ --with-lib$1-prefix[=DIR] search for lib$1 in DIR/include and DIR/lib +++ --without-lib$1-prefix don't search for lib$1 in includedir and libdir], +++[ +++ if test "X$withval" = "Xno"; then +++ use_additional=no +++ else +++ if test "X$withval" = "X"; then +++ AC_LIB_WITH_FINAL_PREFIX([ +++ eval additional_includedir=\"$includedir\" +++ eval additional_libdir=\"$libdir\" +++ ]) +++ else +++ additional_includedir="$withval/include" +++ additional_libdir="$withval/lib" +++ fi +++ fi +++]) +++ dnl Search the library and its dependencies in $additional_libdir and +++ dnl $LDFLAGS. Using breadth-first-seach. +++ LIB[]NAME= +++ LTLIB[]NAME= +++ INC[]NAME= +++ rpathdirs= +++ ltrpathdirs= +++ names_already_handled= +++ names_next_round='$1 $2' +++ while test -n "$names_next_round"; do +++ names_this_round="$names_next_round" +++ names_next_round= +++ for name in $names_this_round; do +++ already_handled= +++ for n in $names_already_handled; do +++ if test "$n" = "$name"; then +++ already_handled=yes +++ break +++ fi +++ done +++ if test -z "$already_handled"; then +++ names_already_handled="$names_already_handled $name" +++ dnl See if it was already located by an earlier AC_LIB_LINKFLAGS +++ dnl or AC_LIB_HAVE_LINKFLAGS call. +++ uppername=`echo "$name" | sed -e 'y|abcdefghijklmnopqrstuvwxyz./-|ABCDEFGHIJKLMNOPQRSTUVWXYZ___|'` +++ eval value=\"\$HAVE_LIB$uppername\" +++ if test -n "$value"; then +++ if test "$value" = yes; then +++ eval value=\"\$LIB$uppername\" +++ test -z "$value" || LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$value" +++ eval value=\"\$LTLIB$uppername\" +++ test -z "$value" || LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$value" +++ else +++ dnl An earlier call to AC_LIB_HAVE_LINKFLAGS has determined +++ dnl that this library doesn't exist. So just drop it. +++ : +++ fi +++ else +++ dnl Search the library lib$name in $additional_libdir and $LDFLAGS +++ dnl and the already constructed $LIBNAME/$LTLIBNAME. +++ found_dir= +++ found_la= +++ found_so= +++ found_a= +++ if test $use_additional = yes; then +++ if test "X$prefer_shared" = "Xyes" && test -n "$shlibext" && test -f "$additional_libdir/lib$name.$shlibext"; then +++ found_dir="$additional_libdir" +++ found_so="$additional_libdir/lib$name.$shlibext" +++ if test -f "$additional_libdir/lib$name.la"; then +++ found_la="$additional_libdir/lib$name.la" +++ fi +++ else +++ if test -f "$additional_libdir/lib$name.$libext"; then +++ found_dir="$additional_libdir" +++ found_a="$additional_libdir/lib$name.$libext" +++ if test -f "$additional_libdir/lib$name.la"; then +++ found_la="$additional_libdir/lib$name.la" +++ fi +++ fi +++ fi +++ fi +++ if test "X$found_dir" = "X"; then +++ for x in $LDFLAGS $LTLIB[]NAME; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ case "$x" in +++ -L*) +++ dir=`echo "X$x" | sed -e 's/^X-L//'` +++ if test "X$prefer_shared" = "Xyes" && test -n "$shlibext" && test -f "$dir/lib$name.$shlibext"; then +++ found_dir="$dir" +++ found_so="$dir/lib$name.$shlibext" +++ if test -f "$dir/lib$name.la"; then +++ found_la="$dir/lib$name.la" +++ fi +++ else +++ if test -f "$dir/lib$name.$libext"; then +++ found_dir="$dir" +++ found_a="$dir/lib$name.$libext" +++ if test -f "$dir/lib$name.la"; then +++ found_la="$dir/lib$name.la" +++ fi +++ fi +++ fi +++ ;; +++ esac +++ if test "X$found_dir" != "X"; then +++ break +++ fi +++ done +++ fi +++ if test "X$found_dir" != "X"; then +++ dnl Found the library. +++ LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$found_dir -l$name" +++ if test "X$found_so" != "X"; then +++ dnl Linking with a shared library. We attempt to hardcode its +++ dnl directory into the executable's runpath, unless it's the +++ dnl standard /usr/lib. +++ if test "$enable_rpath" = no || test "X$found_dir" = "X/usr/lib"; then +++ dnl No hardcoding is needed. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" +++ else +++ dnl Use an explicit option to hardcode DIR into the resulting +++ dnl binary. +++ dnl Potentially add DIR to ltrpathdirs. +++ dnl The ltrpathdirs will be appended to $LTLIBNAME at the end. +++ haveit= +++ for x in $ltrpathdirs; do +++ if test "X$x" = "X$found_dir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ ltrpathdirs="$ltrpathdirs $found_dir" +++ fi +++ dnl The hardcoding into $LIBNAME is system dependent. +++ if test "$hardcode_direct" = yes; then +++ dnl Using DIR/libNAME.so during linking hardcodes DIR into the +++ dnl resulting binary. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" +++ else +++ if test -n "$hardcode_libdir_flag_spec" && test "$hardcode_minus_L" = no; then +++ dnl Use an explicit option to hardcode DIR into the resulting +++ dnl binary. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" +++ dnl Potentially add DIR to rpathdirs. +++ dnl The rpathdirs will be appended to $LIBNAME at the end. +++ haveit= +++ for x in $rpathdirs; do +++ if test "X$x" = "X$found_dir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ rpathdirs="$rpathdirs $found_dir" +++ fi +++ else +++ dnl Rely on "-L$found_dir". +++ dnl But don't add it if it's already contained in the LDFLAGS +++ dnl or the already constructed $LIBNAME +++ haveit= +++ for x in $LDFLAGS $LIB[]NAME; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-L$found_dir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir" +++ fi +++ if test "$hardcode_minus_L" != no; then +++ dnl FIXME: Not sure whether we should use +++ dnl "-L$found_dir -l$name" or "-L$found_dir $found_so" +++ dnl here. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so" +++ else +++ dnl We cannot use $hardcode_runpath_var and LD_RUN_PATH +++ dnl here, because this doesn't fit in flags passed to the +++ dnl compiler. So give up. No hardcoding. This affects only +++ dnl very old systems. +++ dnl FIXME: Not sure whether we should use +++ dnl "-L$found_dir -l$name" or "-L$found_dir $found_so" +++ dnl here. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name" +++ fi +++ fi +++ fi +++ fi +++ else +++ if test "X$found_a" != "X"; then +++ dnl Linking with a static library. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_a" +++ else +++ dnl We shouldn't come here, but anyway it's good to have a +++ dnl fallback. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir -l$name" +++ fi +++ fi +++ dnl Assume the include files are nearby. +++ additional_includedir= +++ case "$found_dir" in +++ */lib | */lib/) +++ basedir=`echo "X$found_dir" | sed -e 's,^X,,' -e 's,/lib/*$,,'` +++ additional_includedir="$basedir/include" +++ ;; +++ esac +++ if test "X$additional_includedir" != "X"; then +++ dnl Potentially add $additional_includedir to $INCNAME. +++ dnl But don't add it +++ dnl 1. if it's the standard /usr/include, +++ dnl 2. if it's /usr/local/include and we are using GCC on Linux, +++ dnl 3. if it's already present in $CPPFLAGS or the already +++ dnl constructed $INCNAME, +++ dnl 4. if it doesn't exist as a directory. +++ if test "X$additional_includedir" != "X/usr/include"; then +++ haveit= +++ if test "X$additional_includedir" = "X/usr/local/include"; then +++ if test -n "$GCC"; then +++ case $host_os in +++ linux*) haveit=yes;; +++ esac +++ fi +++ fi +++ if test -z "$haveit"; then +++ for x in $CPPFLAGS $INC[]NAME; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-I$additional_includedir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ if test -d "$additional_includedir"; then +++ dnl Really add $additional_includedir to $INCNAME. +++ INC[]NAME="${INC[]NAME}${INC[]NAME:+ }-I$additional_includedir" +++ fi +++ fi +++ fi +++ fi +++ fi +++ dnl Look for dependencies. +++ if test -n "$found_la"; then +++ dnl Read the .la file. It defines the variables +++ dnl dlname, library_names, old_library, dependency_libs, current, +++ dnl age, revision, installed, dlopen, dlpreopen, libdir. +++ save_libdir="$libdir" +++ case "$found_la" in +++ */* | *\\*) . "$found_la" ;; +++ *) . "./$found_la" ;; +++ esac +++ libdir="$save_libdir" +++ dnl We use only dependency_libs. +++ for dep in $dependency_libs; do +++ case "$dep" in +++ -L*) +++ additional_libdir=`echo "X$dep" | sed -e 's/^X-L//'` +++ dnl Potentially add $additional_libdir to $LIBNAME and $LTLIBNAME. +++ dnl But don't add it +++ dnl 1. if it's the standard /usr/lib, +++ dnl 2. if it's /usr/local/lib and we are using GCC on Linux, +++ dnl 3. if it's already present in $LDFLAGS or the already +++ dnl constructed $LIBNAME, +++ dnl 4. if it doesn't exist as a directory. +++ if test "X$additional_libdir" != "X/usr/lib"; then +++ haveit= +++ if test "X$additional_libdir" = "X/usr/local/lib"; then +++ if test -n "$GCC"; then +++ case $host_os in +++ linux*) haveit=yes;; +++ esac +++ fi +++ fi +++ if test -z "$haveit"; then +++ haveit= +++ for x in $LDFLAGS $LIB[]NAME; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-L$additional_libdir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ if test -d "$additional_libdir"; then +++ dnl Really add $additional_libdir to $LIBNAME. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$additional_libdir" +++ fi +++ fi +++ haveit= +++ for x in $LDFLAGS $LTLIB[]NAME; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-L$additional_libdir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ if test -d "$additional_libdir"; then +++ dnl Really add $additional_libdir to $LTLIBNAME. +++ LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$additional_libdir" +++ fi +++ fi +++ fi +++ fi +++ ;; +++ -R*) +++ dir=`echo "X$dep" | sed -e 's/^X-R//'` +++ if test "$enable_rpath" != no; then +++ dnl Potentially add DIR to rpathdirs. +++ dnl The rpathdirs will be appended to $LIBNAME at the end. +++ haveit= +++ for x in $rpathdirs; do +++ if test "X$x" = "X$dir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ rpathdirs="$rpathdirs $dir" +++ fi +++ dnl Potentially add DIR to ltrpathdirs. +++ dnl The ltrpathdirs will be appended to $LTLIBNAME at the end. +++ haveit= +++ for x in $ltrpathdirs; do +++ if test "X$x" = "X$dir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ ltrpathdirs="$ltrpathdirs $dir" +++ fi +++ fi +++ ;; +++ -l*) +++ dnl Handle this in the next round. +++ names_next_round="$names_next_round "`echo "X$dep" | sed -e 's/^X-l//'` +++ ;; +++ *.la) +++ dnl Handle this in the next round. Throw away the .la's +++ dnl directory; it is already contained in a preceding -L +++ dnl option. +++ names_next_round="$names_next_round "`echo "X$dep" | sed -e 's,^X.*/,,' -e 's,^lib,,' -e 's,\.la$,,'` +++ ;; +++ *) +++ dnl Most likely an immediate library name. +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$dep" +++ LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$dep" +++ ;; +++ esac +++ done +++ fi +++ else +++ dnl Didn't find the library; assume it is in the system directories +++ dnl known to the linker and runtime loader. (All the system +++ dnl directories known to the linker should also be known to the +++ dnl runtime loader, otherwise the system is severely misconfigured.) +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name" +++ LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-l$name" +++ fi +++ fi +++ fi +++ done +++ done +++ if test "X$rpathdirs" != "X"; then +++ if test -n "$hardcode_libdir_separator"; then +++ dnl Weird platform: only the last -rpath option counts, the user must +++ dnl pass all path elements in one option. We can arrange that for a +++ dnl single library, but not when more than one $LIBNAMEs are used. +++ alldirs= +++ for found_dir in $rpathdirs; do +++ alldirs="${alldirs}${alldirs:+$hardcode_libdir_separator}$found_dir" +++ done +++ dnl Note: hardcode_libdir_flag_spec uses $libdir and $wl. +++ acl_save_libdir="$libdir" +++ libdir="$alldirs" +++ eval flag=\"$hardcode_libdir_flag_spec\" +++ libdir="$acl_save_libdir" +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag" +++ else +++ dnl The -rpath options are cumulative. +++ for found_dir in $rpathdirs; do +++ acl_save_libdir="$libdir" +++ libdir="$found_dir" +++ eval flag=\"$hardcode_libdir_flag_spec\" +++ libdir="$acl_save_libdir" +++ LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag" +++ done +++ fi +++ fi +++ if test "X$ltrpathdirs" != "X"; then +++ dnl When using libtool, the option that works for both libraries and +++ dnl executables is -R. The -R options are cumulative. +++ for found_dir in $ltrpathdirs; do +++ LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-R$found_dir" +++ done +++ fi +++]) +++ +++dnl AC_LIB_APPENDTOVAR(VAR, CONTENTS) appends the elements of CONTENTS to VAR, +++dnl unless already present in VAR. +++dnl Works only for CPPFLAGS, not for LIB* variables because that sometimes +++dnl contains two or three consecutive elements that belong together. +++AC_DEFUN([AC_LIB_APPENDTOVAR], +++[ +++ for element in [$2]; do +++ haveit= +++ for x in $[$1]; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X$element"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ [$1]="${[$1]}${[$1]:+ }$element" +++ fi +++ done +++]) +++# lib-prefix.m4 serial 2 (gettext-0.12) +++dnl Copyright (C) 2001-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Bruno Haible. +++ +++dnl AC_LIB_ARG_WITH is synonymous to AC_ARG_WITH in autoconf-2.13, and +++dnl similar to AC_ARG_WITH in autoconf 2.52...2.57 except that is doesn't +++dnl require excessive bracketing. +++ifdef([AC_HELP_STRING], +++[AC_DEFUN([AC_LIB_ARG_WITH], [AC_ARG_WITH([$1],[[$2]],[$3],[$4])])], +++[AC_DEFUN([AC_LIB_ARG_WITH], [AC_ARG_WITH([$1],[$2],[$3],[$4])])]) +++ +++dnl AC_LIB_PREFIX adds to the CPPFLAGS and LDFLAGS the flags that are needed +++dnl to access previously installed libraries. The basic assumption is that +++dnl a user will want packages to use other packages he previously installed +++dnl with the same --prefix option. +++dnl This macro is not needed if only AC_LIB_LINKFLAGS is used to locate +++dnl libraries, but is otherwise very convenient. +++AC_DEFUN([AC_LIB_PREFIX], +++[ +++ AC_BEFORE([$0], [AC_LIB_LINKFLAGS]) +++ AC_REQUIRE([AC_PROG_CC]) +++ AC_REQUIRE([AC_CANONICAL_HOST]) +++ AC_REQUIRE([AC_LIB_PREPARE_PREFIX]) +++ dnl By default, look in $includedir and $libdir. +++ use_additional=yes +++ AC_LIB_WITH_FINAL_PREFIX([ +++ eval additional_includedir=\"$includedir\" +++ eval additional_libdir=\"$libdir\" +++ ]) +++ AC_LIB_ARG_WITH([lib-prefix], +++[ --with-lib-prefix[=DIR] search for libraries in DIR/include and DIR/lib +++ --without-lib-prefix don't search for libraries in includedir and libdir], +++[ +++ if test "X$withval" = "Xno"; then +++ use_additional=no +++ else +++ if test "X$withval" = "X"; then +++ AC_LIB_WITH_FINAL_PREFIX([ +++ eval additional_includedir=\"$includedir\" +++ eval additional_libdir=\"$libdir\" +++ ]) +++ else +++ additional_includedir="$withval/include" +++ additional_libdir="$withval/lib" +++ fi +++ fi +++]) +++ if test $use_additional = yes; then +++ dnl Potentially add $additional_includedir to $CPPFLAGS. +++ dnl But don't add it +++ dnl 1. if it's the standard /usr/include, +++ dnl 2. if it's already present in $CPPFLAGS, +++ dnl 3. if it's /usr/local/include and we are using GCC on Linux, +++ dnl 4. if it doesn't exist as a directory. +++ if test "X$additional_includedir" != "X/usr/include"; then +++ haveit= +++ for x in $CPPFLAGS; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-I$additional_includedir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ if test "X$additional_includedir" = "X/usr/local/include"; then +++ if test -n "$GCC"; then +++ case $host_os in +++ linux*) haveit=yes;; +++ esac +++ fi +++ fi +++ if test -z "$haveit"; then +++ if test -d "$additional_includedir"; then +++ dnl Really add $additional_includedir to $CPPFLAGS. +++ CPPFLAGS="${CPPFLAGS}${CPPFLAGS:+ }-I$additional_includedir" +++ fi +++ fi +++ fi +++ fi +++ dnl Potentially add $additional_libdir to $LDFLAGS. +++ dnl But don't add it +++ dnl 1. if it's the standard /usr/lib, +++ dnl 2. if it's already present in $LDFLAGS, +++ dnl 3. if it's /usr/local/lib and we are using GCC on Linux, +++ dnl 4. if it doesn't exist as a directory. +++ if test "X$additional_libdir" != "X/usr/lib"; then +++ haveit= +++ for x in $LDFLAGS; do +++ AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"]) +++ if test "X$x" = "X-L$additional_libdir"; then +++ haveit=yes +++ break +++ fi +++ done +++ if test -z "$haveit"; then +++ if test "X$additional_libdir" = "X/usr/local/lib"; then +++ if test -n "$GCC"; then +++ case $host_os in +++ linux*) haveit=yes;; +++ esac +++ fi +++ fi +++ if test -z "$haveit"; then +++ if test -d "$additional_libdir"; then +++ dnl Really add $additional_libdir to $LDFLAGS. +++ LDFLAGS="${LDFLAGS}${LDFLAGS:+ }-L$additional_libdir" +++ fi +++ fi +++ fi +++ fi +++ fi +++]) +++ +++dnl AC_LIB_PREPARE_PREFIX creates variables acl_final_prefix, +++dnl acl_final_exec_prefix, containing the values to which $prefix and +++dnl $exec_prefix will expand at the end of the configure script. +++AC_DEFUN([AC_LIB_PREPARE_PREFIX], +++[ +++ dnl Unfortunately, prefix and exec_prefix get only finally determined +++ dnl at the end of configure. +++ if test "X$prefix" = "XNONE"; then +++ acl_final_prefix="$ac_default_prefix" +++ else +++ acl_final_prefix="$prefix" +++ fi +++ if test "X$exec_prefix" = "XNONE"; then +++ acl_final_exec_prefix='${prefix}' +++ else +++ acl_final_exec_prefix="$exec_prefix" +++ fi +++ acl_save_prefix="$prefix" +++ prefix="$acl_final_prefix" +++ eval acl_final_exec_prefix=\"$acl_final_exec_prefix\" +++ prefix="$acl_save_prefix" +++]) +++ +++dnl AC_LIB_WITH_FINAL_PREFIX([statement]) evaluates statement, with the +++dnl variables prefix and exec_prefix bound to the values they will have +++dnl at the end of the configure script. +++AC_DEFUN([AC_LIB_WITH_FINAL_PREFIX], +++[ +++ acl_save_prefix="$prefix" +++ prefix="$acl_final_prefix" +++ acl_save_exec_prefix="$exec_prefix" +++ exec_prefix="$acl_final_exec_prefix" +++ $1 +++ exec_prefix="$acl_save_exec_prefix" +++ prefix="$acl_save_prefix" +++]) +++# nls.m4 serial 1 (gettext-0.12) +++dnl Copyright (C) 1995-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++dnl +++dnl This file can can be used in projects which are not available under +++dnl the GNU General Public License or the GNU Library General Public +++dnl License but which still want to provide support for the GNU gettext +++dnl functionality. +++dnl Please note that the actual code of the GNU gettext library is covered +++dnl by the GNU Library General Public License, and the rest of the GNU +++dnl gettext package package is covered by the GNU General Public License. +++dnl They are *not* in the public domain. +++ +++dnl Authors: +++dnl Ulrich Drepper , 1995-2000. +++dnl Bruno Haible , 2000-2003. +++ +++AC_DEFUN([AM_NLS], +++[ +++ AC_MSG_CHECKING([whether NLS is requested]) +++ dnl Default is enabled NLS +++ AC_ARG_ENABLE(nls, +++ [ --disable-nls do not use Native Language Support], +++ USE_NLS=$enableval, USE_NLS=yes) +++ AC_MSG_RESULT($USE_NLS) +++ AC_SUBST(USE_NLS) +++]) +++ +++AC_DEFUN([AM_MKINSTALLDIRS], +++[ +++ dnl If the AC_CONFIG_AUX_DIR macro for autoconf is used we possibly +++ dnl find the mkinstalldirs script in another subdir but $(top_srcdir). +++ dnl Try to locate it. +++ MKINSTALLDIRS= +++ if test -n "$ac_aux_dir"; then +++ case "$ac_aux_dir" in +++ /*) MKINSTALLDIRS="$ac_aux_dir/mkinstalldirs" ;; +++ *) MKINSTALLDIRS="\$(top_builddir)/$ac_aux_dir/mkinstalldirs" ;; +++ esac +++ fi +++ if test -z "$MKINSTALLDIRS"; then +++ MKINSTALLDIRS="\$(top_srcdir)/mkinstalldirs" +++ fi +++ AC_SUBST(MKINSTALLDIRS) +++]) +++# po.m4 serial 1 (gettext-0.12) +++dnl Copyright (C) 1995-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++dnl +++dnl This file can can be used in projects which are not available under +++dnl the GNU General Public License or the GNU Library General Public +++dnl License but which still want to provide support for the GNU gettext +++dnl functionality. +++dnl Please note that the actual code of the GNU gettext library is covered +++dnl by the GNU Library General Public License, and the rest of the GNU +++dnl gettext package package is covered by the GNU General Public License. +++dnl They are *not* in the public domain. +++ +++dnl Authors: +++dnl Ulrich Drepper , 1995-2000. +++dnl Bruno Haible , 2000-2003. +++ +++dnl Checks for all prerequisites of the po subdirectory. +++AC_DEFUN([AM_PO_SUBDIRS], +++[ +++ AC_REQUIRE([AC_PROG_MAKE_SET])dnl +++ AC_REQUIRE([AC_PROG_INSTALL])dnl +++ AC_REQUIRE([AM_MKINSTALLDIRS])dnl +++ AC_REQUIRE([AM_NLS])dnl +++ +++ dnl Perform the following tests also if --disable-nls has been given, +++ dnl because they are needed for "make dist" to work. +++ +++ dnl Search for GNU msgfmt in the PATH. +++ dnl The first test excludes Solaris msgfmt and early GNU msgfmt versions. +++ dnl The second test excludes FreeBSD msgfmt. +++ AM_PATH_PROG_WITH_TEST(MSGFMT, msgfmt, +++ [$ac_dir/$ac_word --statistics /dev/null >/dev/null 2>&1 && +++ (if $ac_dir/$ac_word --statistics /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)], +++ :) +++ AC_PATH_PROG(GMSGFMT, gmsgfmt, $MSGFMT) +++ +++ dnl Search for GNU xgettext 0.12 or newer in the PATH. +++ dnl The first test excludes Solaris xgettext and early GNU xgettext versions. +++ dnl The second test excludes FreeBSD xgettext. +++ AM_PATH_PROG_WITH_TEST(XGETTEXT, xgettext, +++ [$ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null >/dev/null 2>&1 && +++ (if $ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)], +++ :) +++ dnl Remove leftover from FreeBSD xgettext call. +++ rm -f messages.po +++ +++ dnl Search for GNU msgmerge 0.11 or newer in the PATH. +++ AM_PATH_PROG_WITH_TEST(MSGMERGE, msgmerge, +++ [$ac_dir/$ac_word --update -q /dev/null /dev/null >/dev/null 2>&1], :) +++ +++ dnl This could go away some day; the PATH_PROG_WITH_TEST already does it. +++ dnl Test whether we really found GNU msgfmt. +++ if test "$GMSGFMT" != ":"; then +++ dnl If it is no GNU msgfmt we define it as : so that the +++ dnl Makefiles still can work. +++ if $GMSGFMT --statistics /dev/null >/dev/null 2>&1 && +++ (if $GMSGFMT --statistics /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi); then +++ : ; +++ else +++ GMSGFMT=`echo "$GMSGFMT" | sed -e 's,^.*/,,'` +++ AC_MSG_RESULT( +++ [found $GMSGFMT program is not GNU msgfmt; ignore it]) +++ GMSGFMT=":" +++ fi +++ fi +++ +++ dnl This could go away some day; the PATH_PROG_WITH_TEST already does it. +++ dnl Test whether we really found GNU xgettext. +++ if test "$XGETTEXT" != ":"; then +++ dnl If it is no GNU xgettext we define it as : so that the +++ dnl Makefiles still can work. +++ if $XGETTEXT --omit-header --copyright-holder= --msgid-bugs-address= /dev/null >/dev/null 2>&1 && +++ (if $XGETTEXT --omit-header --copyright-holder= --msgid-bugs-address= /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi); then +++ : ; +++ else +++ AC_MSG_RESULT( +++ [found xgettext program is not GNU xgettext; ignore it]) +++ XGETTEXT=":" +++ fi +++ dnl Remove leftover from FreeBSD xgettext call. +++ rm -f messages.po +++ fi +++ +++ AC_OUTPUT_COMMANDS([ +++ for ac_file in $CONFIG_FILES; do +++ # Support "outfile[:infile[:infile...]]" +++ case "$ac_file" in +++ *:*) ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; +++ esac +++ # PO directories have a Makefile.in generated from Makefile.in.in. +++ case "$ac_file" in */Makefile.in) +++ # Adjust a relative srcdir. +++ ac_dir=`echo "$ac_file"|sed 's%/[^/][^/]*$%%'` +++ ac_dir_suffix="/`echo "$ac_dir"|sed 's%^\./%%'`" +++ ac_dots=`echo "$ac_dir_suffix"|sed 's%/[^/]*%../%g'` +++ # In autoconf-2.13 it is called $ac_given_srcdir. +++ # In autoconf-2.50 it is called $srcdir. +++ test -n "$ac_given_srcdir" || ac_given_srcdir="$srcdir" +++ case "$ac_given_srcdir" in +++ .) top_srcdir=`echo $ac_dots|sed 's%/$%%'` ;; +++ /*) top_srcdir="$ac_given_srcdir" ;; +++ *) top_srcdir="$ac_dots$ac_given_srcdir" ;; +++ esac +++ if test -f "$ac_given_srcdir/$ac_dir/POTFILES.in"; then +++ rm -f "$ac_dir/POTFILES" +++ test -n "$as_me" && echo "$as_me: creating $ac_dir/POTFILES" || echo "creating $ac_dir/POTFILES" +++ cat "$ac_given_srcdir/$ac_dir/POTFILES.in" | sed -e "/^#/d" -e "/^[ ]*\$/d" -e "s,.*, $top_srcdir/& \\\\," | sed -e "\$s/\(.*\) \\\\/\1/" > "$ac_dir/POTFILES" +++ POMAKEFILEDEPS="POTFILES.in" +++ # ALL_LINGUAS, POFILES, GMOFILES, UPDATEPOFILES, DUMMYPOFILES depend +++ # on $ac_dir but don't depend on user-specified configuration +++ # parameters. +++ if test -f "$ac_given_srcdir/$ac_dir/LINGUAS"; then +++ # The LINGUAS file contains the set of available languages. +++ if test -n "$OBSOLETE_ALL_LINGUAS"; then +++ test -n "$as_me" && echo "$as_me: setting ALL_LINGUAS in configure.in is obsolete" || echo "setting ALL_LINGUAS in configure.in is obsolete" +++ fi +++ ALL_LINGUAS_=`sed -e "/^#/d" "$ac_given_srcdir/$ac_dir/LINGUAS"` +++ # Hide the ALL_LINGUAS assigment from automake. +++ eval 'ALL_LINGUAS''=$ALL_LINGUAS_' +++ POMAKEFILEDEPS="$POMAKEFILEDEPS LINGUAS" +++ else +++ # The set of available languages was given in configure.in. +++ eval 'ALL_LINGUAS''=$OBSOLETE_ALL_LINGUAS' +++ fi +++ case "$ac_given_srcdir" in +++ .) srcdirpre= ;; +++ *) srcdirpre='$(srcdir)/' ;; +++ esac +++ POFILES= +++ GMOFILES= +++ UPDATEPOFILES= +++ DUMMYPOFILES= +++ for lang in $ALL_LINGUAS; do +++ POFILES="$POFILES $srcdirpre$lang.po" +++ GMOFILES="$GMOFILES $srcdirpre$lang.gmo" +++ UPDATEPOFILES="$UPDATEPOFILES $lang.po-update" +++ DUMMYPOFILES="$DUMMYPOFILES $lang.nop" +++ done +++ # CATALOGS depends on both $ac_dir and the user's LINGUAS +++ # environment variable. +++ INST_LINGUAS= +++ if test -n "$ALL_LINGUAS"; then +++ for presentlang in $ALL_LINGUAS; do +++ useit=no +++ if test "%UNSET%" != "$LINGUAS"; then +++ desiredlanguages="$LINGUAS" +++ else +++ desiredlanguages="$ALL_LINGUAS" +++ fi +++ for desiredlang in $desiredlanguages; do +++ # Use the presentlang catalog if desiredlang is +++ # a. equal to presentlang, or +++ # b. a variant of presentlang (because in this case, +++ # presentlang can be used as a fallback for messages +++ # which are not translated in the desiredlang catalog). +++ case "$desiredlang" in +++ "$presentlang"*) useit=yes;; +++ esac +++ done +++ if test $useit = yes; then +++ INST_LINGUAS="$INST_LINGUAS $presentlang" +++ fi +++ done +++ fi +++ CATALOGS= +++ if test -n "$INST_LINGUAS"; then +++ for lang in $INST_LINGUAS; do +++ CATALOGS="$CATALOGS $lang.gmo" +++ done +++ fi +++ test -n "$as_me" && echo "$as_me: creating $ac_dir/Makefile" || echo "creating $ac_dir/Makefile" +++ sed -e "/^POTFILES =/r $ac_dir/POTFILES" -e "/^# Makevars/r $ac_given_srcdir/$ac_dir/Makevars" -e "s|@POFILES@|$POFILES|g" -e "s|@GMOFILES@|$GMOFILES|g" -e "s|@UPDATEPOFILES@|$UPDATEPOFILES|g" -e "s|@DUMMYPOFILES@|$DUMMYPOFILES|g" -e "s|@CATALOGS@|$CATALOGS|g" -e "s|@POMAKEFILEDEPS@|$POMAKEFILEDEPS|g" "$ac_dir/Makefile.in" > "$ac_dir/Makefile" +++ for f in "$ac_given_srcdir/$ac_dir"/Rules-*; do +++ if test -f "$f"; then +++ case "$f" in +++ *.orig | *.bak | *~) ;; +++ *) cat "$f" >> "$ac_dir/Makefile" ;; +++ esac +++ fi +++ done +++ fi +++ ;; +++ esac +++ done], +++ [# Capture the value of obsolete ALL_LINGUAS because we need it to compute +++ # POFILES, GMOFILES, UPDATEPOFILES, DUMMYPOFILES, CATALOGS. But hide it +++ # from automake. +++ eval 'OBSOLETE_ALL_LINGUAS''="$ALL_LINGUAS"' +++ # Capture the value of LINGUAS because we need it to compute CATALOGS. +++ LINGUAS="${LINGUAS-%UNSET%}" +++ ]) +++]) +++# progtest.m4 serial 3 (gettext-0.12) +++dnl Copyright (C) 1996-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++dnl +++dnl This file can can be used in projects which are not available under +++dnl the GNU General Public License or the GNU Library General Public +++dnl License but which still want to provide support for the GNU gettext +++dnl functionality. +++dnl Please note that the actual code of the GNU gettext library is covered +++dnl by the GNU Library General Public License, and the rest of the GNU +++dnl gettext package package is covered by the GNU General Public License. +++dnl They are *not* in the public domain. +++ +++dnl Authors: +++dnl Ulrich Drepper , 1996. +++ +++# Search path for a program which passes the given test. +++ +++dnl AM_PATH_PROG_WITH_TEST(VARIABLE, PROG-TO-CHECK-FOR, +++dnl TEST-PERFORMED-ON-FOUND_PROGRAM [, VALUE-IF-NOT-FOUND [, PATH]]) +++AC_DEFUN([AM_PATH_PROG_WITH_TEST], +++[ +++# Prepare PATH_SEPARATOR. +++# The user is always right. +++if test "${PATH_SEPARATOR+set}" != set; then +++ echo "#! /bin/sh" >conf$$.sh +++ echo "exit 0" >>conf$$.sh +++ chmod +x conf$$.sh +++ if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then +++ PATH_SEPARATOR=';' +++ else +++ PATH_SEPARATOR=: +++ fi +++ rm -f conf$$.sh +++fi +++ +++# Find out how to test for executable files. Don't use a zero-byte file, +++# as systems may use methods other than mode bits to determine executability. +++cat >conf$$.file <<_ASEOF +++#! /bin/sh +++exit 0 +++_ASEOF +++chmod +x conf$$.file +++if test -x conf$$.file >/dev/null 2>&1; then +++ ac_executable_p="test -x" +++else +++ ac_executable_p="test -f" +++fi +++rm -f conf$$.file +++ +++# Extract the first word of "$2", so it can be a program name with args. +++set dummy $2; ac_word=[$]2 +++AC_MSG_CHECKING([for $ac_word]) +++AC_CACHE_VAL(ac_cv_path_$1, +++[case "[$]$1" in +++ [[\\/]]* | ?:[[\\/]]*) +++ ac_cv_path_$1="[$]$1" # Let the user override the test with a path. +++ ;; +++ *) +++ ac_save_IFS="$IFS"; IFS=$PATH_SEPARATOR +++ for ac_dir in ifelse([$5], , $PATH, [$5]); do +++ IFS="$ac_save_IFS" +++ test -z "$ac_dir" && ac_dir=. +++ for ac_exec_ext in '' $ac_executable_extensions; do +++ if $ac_executable_p "$ac_dir/$ac_word$ac_exec_ext"; then +++ if [$3]; then +++ ac_cv_path_$1="$ac_dir/$ac_word$ac_exec_ext" +++ break 2 +++ fi +++ fi +++ done +++ done +++ IFS="$ac_save_IFS" +++dnl If no 4th arg is given, leave the cache variable unset, +++dnl so AC_PATH_PROGS will keep looking. +++ifelse([$4], , , [ test -z "[$]ac_cv_path_$1" && ac_cv_path_$1="$4" +++])dnl +++ ;; +++esac])dnl +++$1="$ac_cv_path_$1" +++if test ifelse([$4], , [-n "[$]$1"], ["[$]$1" != "$4"]); then +++ AC_MSG_RESULT([$]$1) +++else +++ AC_MSG_RESULT(no) +++fi +++AC_SUBST($1)dnl +++]) +++# stdint_h.m4 serial 3 (gettext-0.12) +++dnl Copyright (C) 1997-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Paul Eggert. +++ +++# Define HAVE_STDINT_H_WITH_UINTMAX if exists, +++# doesn't clash with , and declares uintmax_t. +++ +++AC_DEFUN([jm_AC_HEADER_STDINT_H], +++[ +++ AC_CACHE_CHECK([for stdint.h], jm_ac_cv_header_stdint_h, +++ [AC_TRY_COMPILE( +++ [#include +++#include ], +++ [uintmax_t i = (uintmax_t) -1;], +++ jm_ac_cv_header_stdint_h=yes, +++ jm_ac_cv_header_stdint_h=no)]) +++ if test $jm_ac_cv_header_stdint_h = yes; then +++ AC_DEFINE_UNQUOTED(HAVE_STDINT_H_WITH_UINTMAX, 1, +++ [Define if exists, doesn't clash with , +++ and declares uintmax_t. ]) +++ fi +++]) +++# uintmax_t.m4 serial 7 (gettext-0.12) +++dnl Copyright (C) 1997-2003 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Paul Eggert. +++ +++AC_PREREQ(2.13) +++ +++# Define uintmax_t to 'unsigned long' or 'unsigned long long' +++# if it is not already defined in or . +++ +++AC_DEFUN([jm_AC_TYPE_UINTMAX_T], +++[ +++ AC_REQUIRE([jm_AC_HEADER_INTTYPES_H]) +++ AC_REQUIRE([jm_AC_HEADER_STDINT_H]) +++ if test $jm_ac_cv_header_inttypes_h = no && test $jm_ac_cv_header_stdint_h = no; then +++ AC_REQUIRE([jm_AC_TYPE_UNSIGNED_LONG_LONG]) +++ test $ac_cv_type_unsigned_long_long = yes \ +++ && ac_type='unsigned long long' \ +++ || ac_type='unsigned long' +++ AC_DEFINE_UNQUOTED(uintmax_t, $ac_type, +++ [Define to unsigned long or unsigned long long +++ if and don't define.]) +++ else +++ AC_DEFINE(HAVE_UINTMAX_T, 1, +++ [Define if you have the 'uintmax_t' type in or .]) +++ fi +++]) +++# ulonglong.m4 serial 2 (fileutils-4.0.32, gettext-0.10.40) +++dnl Copyright (C) 1999-2002 Free Software Foundation, Inc. +++dnl This file is free software, distributed under the terms of the GNU +++dnl General Public License. As a special exception to the GNU General +++dnl Public License, this file may be distributed as part of a program +++dnl that contains a configuration script generated by Autoconf, under +++dnl the same distribution terms as the rest of that program. +++ +++dnl From Paul Eggert. +++ +++AC_DEFUN([jm_AC_TYPE_UNSIGNED_LONG_LONG], +++[ +++ AC_CACHE_CHECK([for unsigned long long], ac_cv_type_unsigned_long_long, +++ [AC_TRY_LINK([unsigned long long ull = 1; int i = 63;], +++ [unsigned long long ullmax = (unsigned long long) -1; +++ return ull << i | ull >> i | ullmax / ull | ullmax % ull;], +++ ac_cv_type_unsigned_long_long=yes, +++ ac_cv_type_unsigned_long_long=no)]) +++ if test $ac_cv_type_unsigned_long_long = yes; then +++ AC_DEFINE(HAVE_UNSIGNED_LONG_LONG, 1, +++ [Define if you have the unsigned long long type.]) +++ fi +++]) +++ +++dnl From gnulib +++AC_DEFUN([BASH_FUNC_FPURGE], +++[ +++ AC_CHECK_FUNCS_ONCE([fpurge]) +++ AC_CHECK_FUNCS_ONCE([__fpurge]) +++ AC_CHECK_DECLS([fpurge], , , [#include ]) +++]) +++ +++AC_DEFUN([BASH_FUNC_SNPRINTF], +++[ +++ AC_CHECK_FUNCS_ONCE([snprintf]) +++ if test X$ac_cv_func_snprintf = Xyes; then +++ AC_CACHE_CHECK([for standard-conformant snprintf], [bash_cv_func_snprintf], +++ [AC_TRY_RUN([ + +#include + +#include +- +- /* Add more tests in here as appropriate. */ +++ + +int +- main() +- { +- int fd, err; +-@@ -1651,11 +1680,13 @@ AC_CACHE_VAL(bash_cv_unusable_rtsigs, +- [AC_TRY_RUN([ +- #include +- #include +++main() +++{ +++ int n; +++ n = snprintf (0, 0, "%s", "0123456"); +++ exit(n != 7); +++} +++], bash_cv_func_snprintf=yes, bash_cv_func_snprintf=no, +++ [AC_MSG_WARN([cannot check standard snprintf if cross-compiling]) +++ bash_cv_func_snprintf=yes] +++)]) +++ if test $bash_cv_func_snprintf = no; then +++ ac_cv_func_snprintf=no +++ fi +++ fi +++ if test $ac_cv_func_snprintf = no; then +++ AC_DEFINE(HAVE_SNPRINTF, 0, +++ [Define if you have a standard-conformant snprintf function.]) +++ fi +++]) +++ +++AC_DEFUN([BASH_FUNC_VSNPRINTF], +++[ +++ AC_CHECK_FUNCS_ONCE([vsnprintf]) +++ if test X$ac_cv_func_vsnprintf = Xyes; then +++ AC_CACHE_CHECK([for standard-conformant vsnprintf], [bash_cv_func_vsnprintf], +++ [AC_TRY_RUN([ +++#if HAVE_STDARG_H +++#include +++#else +++#include +++#endif +++#include + +#include +- +- #ifndef NSIG +- # define NSIG 64 +- #endif +- +-+int +- main () +- { +- int n_sigs = 2 * NSIG; +-@@ -1770,6 +1801,7 @@ bash_cv_wcwidth_broken, +- #include +- #include +- +-+int +- main(c, v) +- int c; +- char **v; +-@@ -1834,9 +1866,11 @@ AC_CACHE_VAL(ac_cv_rl_version, +- [AC_TRY_RUN([ +- #include +- #include +++ +++static int +++#if HAVE_STDARG_H +++foo(const char *fmt, ...) +++#else +++foo(format, va_alist) +++ const char *format; +++ va_dcl +++#endif +++{ +++ va_list args; +++ int n; +++ +++#if HAVE_STDARG_H +++ va_start(args, fmt); +++#else +++ va_start(args); +++#endif +++ n = vsnprintf(0, 0, fmt, args); +++ va_end (args); +++ return n; +++} +++ +++main() +++{ +++ int n; +++ n = foo("%s", "0123456"); +++ exit(n != 7); +++} +++], bash_cv_func_vsnprintf=yes, bash_cv_func_vsnprintf=no, +++ [AC_MSG_WARN([cannot check standard vsnprintf if cross-compiling]) +++ bash_cv_func_vsnprintf=yes] +++)]) +++ if test $bash_cv_func_vsnprintf = no; then +++ ac_cv_func_vsnprintf=no +++ fi +++ fi +++ if test $ac_cv_func_vsnprintf = no; then +++ AC_DEFINE(HAVE_VSNPRINTF, 0, +++ [Define if you have a standard-conformant vsnprintf function.]) +++ fi +++]) +++ +++AC_DEFUN(BASH_STRUCT_WEXITSTATUS_OFFSET, +++[AC_MSG_CHECKING(for offset of exit status in return status from wait) +++AC_CACHE_VAL(bash_cv_wexitstatus_offset, +++[AC_TRY_RUN([ + +#include +- +- extern int rl_gnu_readline_p; +- +++#include +++ +++#include +++ + +int +- main() +- { +- FILE *fp; +-@@ -1926,7 +1960,9 @@ AC_CACHE_VAL(bash_cv_func_ctype_nonascii +- #endif +- #include +- #include +++main(c, v) +++ int c; +++ char **v; +++{ +++ pid_t pid, p; +++ int s, i, n; +++ +++ s = 0; +++ pid = fork(); +++ if (pid == 0) +++ exit (42); +++ +++ /* wait for the process */ +++ p = wait(&s); +++ if (p != pid) +++ exit (255); +++ +++ /* crack s */ +++ for (i = 0; i < (sizeof(s) - 8); i++) +++ { +++ n = (s >> i) & 0xff; +++ if (n == 42) +++ exit (i); +++ } +++ +++ exit (254); +++} +++], bash_cv_wexitstatus_offset=0, bash_cv_wexitstatus_offset=$?, +++ [AC_MSG_WARN(cannot check WEXITSTATUS offset if cross compiling -- defaulting to 0) +++ bash_cv_wexitstatus_offset=0] +++)]) +++if test "$bash_cv_wexitstatus_offset" -gt 32 ; then +++ AC_MSG_WARN(bad exit status from test program -- defaulting to 0) +++ bash_cv_wexitstatus_offset=0 +++fi +++AC_MSG_RESULT($bash_cv_wexitstatus_offset) +++AC_DEFINE_UNQUOTED([WEXITSTATUS_OFFSET], [$bash_cv_wexitstatus_offset], [Offset of exit status in wait status word]) +++]) +++ +++AC_DEFUN([BASH_FUNC_SBRK], +++[ +++ AC_CHECK_FUNCS_ONCE([sbrk]) +++ if test X$ac_cv_func_sbrk = Xyes; then +++ AC_CACHE_CHECK([for working sbrk], [bash_cv_func_sbrk], +++ [AC_TRY_RUN([ + +#include +- +++#include +++ + +int +- main(c, v) +- int c; +- char *v[]; +-@@ -4068,7 +4104,9 @@ AC_DEFUN([BASH_FUNC_SNPRINTF], +- AC_CACHE_CHECK([for standard-conformant snprintf], [bash_cv_func_snprintf], +- [AC_TRY_RUN([ +- #include +++main(int c, char **v) +++{ +++ void *x; +++ +++ x = sbrk (4096); +++ exit ((x == (void *)-1) ? 1 : 0); +++} +++], bash_cv_func_sbrk=yes, bash_cv_func_snprintf=sbrk, +++ [AC_MSG_WARN([cannot check working sbrk if cross-compiling]) +++ bash_cv_func_sbrk=yes] +++)]) +++ if test $bash_cv_func_sbrk = no; then +++ ac_cv_func_sbrk=no +++ fi +++ fi +++ if test $ac_cv_func_sbrk = no; then +++ AC_DEFINE(HAVE_SBRK, 0, +++ [Define if you have a working sbrk function.]) +++ fi +++]) +++ +++AC_DEFUN(BASH_FUNC_FNMATCH_EQUIV_FALLBACK, +++[AC_MSG_CHECKING(whether fnmatch can be used to check bracket equivalence classes) +++AC_CACHE_VAL(bash_cv_fnmatch_equiv_fallback, +++[AC_TRY_RUN([ + +#include +- +-+int +- main() +- { +- int n; +-@@ -4154,6 +4192,7 @@ AC_CACHE_VAL(bash_cv_wexitstatus_offset, +- +- #include +- +++#include +++#include +++#include +++#include +++ +++char *pattern = "[[=a=]]"; +++ +++/* char *string = "ä"; */ +++unsigned char string[4] = { '\xc3', '\xa4', '\0' }; +++ + +int +- main(c, v) +- int c; +- char **v; +---- gdb-10.2/readline/readline/configure.orig +-+++ gdb-10.2/readline/readline/configure +++main (int c, char **v) +++{ +++ setlocale (LC_ALL, "de_DE.UTF-8"); +++ if (fnmatch (pattern, (const char *)string, 0) != FNM_NOMATCH) +++ exit (0); +++ exit (1); +++} +++ +++], bash_cv_fnmatch_equiv_fallback=yes, bash_cv_fnmatch_equiv_fallback=no, +++ [AC_MSG_WARN(cannot check fnmatch if cross compiling -- defaulting to no) +++ bash_cv_fnmatch_equiv_fallback=no] +++)]) +++AC_MSG_RESULT($bash_cv_fnmatch_equiv_fallback) +++if test "$bash_cv_fnmatch_equiv_fallback" = "yes" ; then +++ bash_cv_fnmatch_equiv_value=1 +++else +++ bash_cv_fnmatch_equiv_value=0 +++fi +++AC_DEFINE_UNQUOTED([FNMATCH_EQUIV_FALLBACK], [$bash_cv_fnmatch_equiv_value], [Whether fnmatch can be used for bracket equivalence classes]) +++]) ++diff -Nuar gdb-10.2/readline/readline/configure gdb-10.2/readline/readline/configure ++--- gdb-10.2/readline/readline/configure 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/configure 2025-04-16 17:06:41.942086800 +0800 + @@ -1,5 +1,5 @@ + #! /bin/sh + -# From configure.ac for Readline 8.0, version 2.85. +@@ -3028,7 +99462,7 @@ exit 0 + # Guess values for system-dependent variables and create Makefiles. + # Generated by GNU Autoconf 2.69 for readline 8.0. + # +-@@ -5316,6 +5316,7 @@ else ++@@ -5316,6 +5316,7 @@ + #ifdef HAVE_UNISTD_H + #include + #endif +@@ -3036,7 +99470,7 @@ exit 0 + + typedef RETSIGTYPE sigfunc(); + +-@@ -5346,7 +5347,8 @@ int s; ++@@ -5346,7 +5347,8 @@ + nsigint++; + } + +@@ -3046,7 +99480,7 @@ exit 0 + { + nsigint = 0; + set_signal_handler(SIGINT, sigint); +-@@ -5396,8 +5398,10 @@ else ++@@ -5396,8 +5398,10 @@ + #include + #include + #include +@@ -3058,7 +99492,7 @@ exit 0 + { + #if !defined (_POSIX_VERSION) || !defined (HAVE_POSIX_SIGNALS) + exit (1); +-@@ -5499,7 +5503,10 @@ else ++@@ -5499,7 +5503,10 @@ + #if defined (HAVE_LOCALE_H) + #include + #endif +@@ -3069,7 +99503,7 @@ exit 0 + main(c, v) + int c; + char *v[]; +-@@ -5569,7 +5576,9 @@ else ++@@ -5569,7 +5576,9 @@ + #endif + #include + #include +@@ -3079,7 +99513,7 @@ exit 0 + main(c, v) + int c; + char *v[]; +-@@ -6713,6 +6722,7 @@ else ++@@ -6713,6 +6722,7 @@ + #include + #include + +@@ -3087,9 +99521,10 @@ exit 0 + main(c, v) + int c; + char **v; +---- gdb-10.2/readline/readline/configure.ac.orig +-+++ gdb-10.2/readline/readline/configure.ac +-@@ -5,7 +5,7 @@ dnl report bugs to chet@po.cwru.edu ++diff -Nuar gdb-10.2/readline/readline/configure.ac gdb-10.2/readline/readline/configure.ac ++--- gdb-10.2/readline/readline/configure.ac 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/configure.ac 2025-04-16 17:06:41.942086800 +0800 ++@@ -5,7 +5,7 @@ + dnl + dnl Process this file with autoconf to produce a configure script. + +@@ -3098,7 +99533,7 @@ exit 0 + + # 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 +-@@ -20,7 +20,7 @@ dnl Process this file with autoconf to p ++@@ -20,7 +20,7 @@ + # You should have received a copy of the GNU General Public License + # along with this program. If not, see . + +@@ -3107,83 +99542,113 @@ exit 0 + + m4_include([../../config/override.m4]) + +---- gdb-10.2/gdb/dwarf2/read.c.orig +-+++ gdb-10.2/gdb/dwarf2/read.c +-@@ -4925,7 +4925,10 @@ dw2_find_pc_sect_compunit_symtab (struct objfile *objfile, +- result = recursively_find_pc_sect_compunit_symtab +- (dw2_instantiate_symtab (data, per_objfile, false), pc); +- +-- gdb_assert (result != NULL); +-+ if (warn_if_readin && result == nullptr) +-+ warning (_("(Error: pc %s in address map, but not in symtab.)"), +-+ paddress (objfile->arch (), pc)); +-+ +- return result; +- } ++diff -Nuar gdb-10.2/readline/readline/misc.c gdb-10.2/readline/readline/misc.c ++--- gdb-10.2/readline/readline/misc.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/misc.c 2025-04-16 17:06:41.912086800 +0800 ++@@ -403,7 +403,7 @@ + +---- gdb-10.2/gdb/symtab.c.orig +-+++ gdb-10.2/gdb/symtab.c +-@@ -7476,7 +7476,7 @@ gdb_add_symbol_file(struct gnu_request * +- int i; +- int allsect = 0; +- char *secname; +-- char buf[80]; +-+ char buf[96]; ++ #if defined (VI_MODE) ++ if (rl_editing_mode == vi_mode && _rl_keymap != vi_insertion_keymap) ++- rl_point = 0; +++ rl_point = rl_end; ++ #endif /* VI_MODE */ + +- gdb_current_load_module = lm = (struct load_module *)req->addr; ++ if (rl_editing_mode == emacs_mode) ++diff -Nuar gdb-10.2/readline/readline/readline.h gdb-10.2/readline/readline/readline.h ++--- gdb-10.2/readline/readline/readline.h 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/readline.h 2025-04-16 17:06:41.922086800 +0800 ++@@ -395,7 +395,7 @@ ++ #if defined (USE_VARARGS) && defined (PREFER_STDARG) ++ extern int rl_message (const char *, ...) __attribute__((__format__ (printf, 1, 2))); ++ #else ++-extern int rl_message (); +++extern int rl_message (void); ++ #endif + +-@@ -7515,8 +7515,11 @@ gdb_add_symbol_file(struct gnu_request * +- secname = lm->mod_section_data[i].name; +- if ((lm->mod_section_data[i].flags & SEC_FOUND) && +- !STREQ(secname, ".text")) { +-- sprintf(buf, " -s %s 0x%lx", secname, +-- lm->mod_section_data[i].offset + lm->mod_base); +-+ if (lm->mod_section_data[i].addr) +-+ sprintf(buf, " -s %s 0x%lx", secname, lm->mod_section_data[i].addr); +-+ else +-+ sprintf(buf, " -s %s 0x%lx", secname, +-+ lm->mod_section_data[i].offset + lm->mod_base); +- strcat(req->buf, buf); +- } +- } +---- gdb-10.2/gdb/ada-lang.c.orig +-+++ gdb-10.2/gdb/ada-lang.c +-@@ -1158,7 +1158,7 @@ ada_decode (const char *encoded) +- i -= 1; +- if (i > 1 && encoded[i] == '_' && encoded[i - 1] == '_') +- len0 = i - 1; +-- else if (encoded[i] == '$') +-+ else if (i >= 0 && encoded[i] == '$') +- len0 = i; +- } ++ extern int rl_show_char PARAMS((int)); ++diff -Nuar gdb-10.2/readline/readline/rltypedefs.h gdb-10.2/readline/readline/rltypedefs.h ++--- gdb-10.2/readline/readline/rltypedefs.h 2020-09-13 10:33:41.000000000 +0800 +++++ gdb-10.2/readline/readline/rltypedefs.h 2025-04-16 17:06:41.922086800 +0800 ++@@ -32,10 +32,10 @@ ++ # define _FUNCTION_DEF + +---- gdb-10.2/gdb/coffread.c.orig +-+++ gdb-10.2/gdb/coffread.c +-@@ -159,6 +159,7 @@ static long linetab_offset; +- static unsigned long linetab_size; ++ #if defined(__GNUC__) || defined(__clang__) ++-typedef int Function () __attribute__ ((deprecated)); ++-typedef void VFunction () __attribute__ ((deprecated)); ++-typedef char *CPFunction () __attribute__ ((deprecated)); ++-typedef char **CPPFunction () __attribute__ ((deprecated)); +++typedef int Function (void) __attribute__ ((deprecated)); +++typedef void VFunction (void) __attribute__ ((deprecated)); +++typedef char *CPFunction (void) __attribute__ ((deprecated)); +++typedef char **CPPFunction (void) __attribute__ ((deprecated)); ++ #else ++ typedef int Function (); ++ typedef void VFunction (); ++diff -Nuar gdb-10.2/readline/readline/support/config.guess gdb-10.2/readline/readline/support/config.guess ++--- gdb-10.2/readline/readline/support/config.guess 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/support/config.guess 2025-04-16 17:06:52.012086800 +0800 ++@@ -941,6 +941,15 @@ ++ if test "$?" = 0 ; then LIBC=gnulibc1 ; fi ++ echo "$UNAME_MACHINE"-unknown-linux-"$LIBC" ++ exit ;; +++ sw_64:Linux:*:*) +++ case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in +++ SW6A) UNAME_MACHINE=sw_64sw6a ;; +++ SW6B) UNAME_MACHINE=sw_64sw6b ;; +++ esac +++ objdump --private-headers /bin/sh | grep -q ld.so.1 +++ if test "$?" = 0 ; then LIBC=gnulibc1 ; fi +++ echo "$UNAME_MACHINE"-unknown-linux-"$LIBC" +++ exit ;; ++ arc:Linux:*:* | arceb:Linux:*:*) ++ echo "$UNAME_MACHINE"-unknown-linux-"$LIBC" ++ exit ;; ++diff -Nuar gdb-10.2/readline/readline/support/config.sub gdb-10.2/readline/readline/support/config.sub ++--- gdb-10.2/readline/readline/support/config.sub 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/support/config.sub 2025-04-16 17:06:52.012086800 +0800 ++@@ -1164,6 +1164,7 @@ ++ | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] \ ++ | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] \ ++ | alphapca5[67] | alpha64pca5[67] \ +++ | sw_64 | sw_64sw6a | sw_64sw6b \ ++ | am33_2.0 \ ++ | amdgcn \ ++ | arc | arceb \ ++diff -Nuar gdb-10.2/readline/readline/util.c gdb-10.2/readline/readline/util.c ++--- gdb-10.2/readline/readline/util.c 2021-04-25 12:06:26.000000000 +0800 +++++ gdb-10.2/readline/readline/util.c 2025-04-16 17:06:41.922086800 +0800 ++@@ -487,10 +487,13 @@ + +- static char *stringtab = NULL; +-+static long stringtab_length = 0; ++ if (_rl_tracefp == 0) ++ _rl_tropen (); +++ if (!_rl_tracefp) +++ goto out; ++ vfprintf (_rl_tracefp, format, args); ++ fprintf (_rl_tracefp, "\n"); ++ fflush (_rl_tracefp); + +- extern void stabsread_clear_cache (void); +++out: ++ va_end (args); ++ } + +-@@ -1297,6 +1298,7 @@ init_stringtab (bfd *abfd, long offset, gdb::unique_xmalloc_ptr *storage) +- /* This is in target format (probably not very useful, and not +- currently used), not host format. */ +- memcpy (stringtab, lengthbuf, sizeof lengthbuf); +-+ stringtab_length = length; +- if (length == sizeof length) /* Empty table -- just the count. */ +- return 0; ++@@ -513,16 +516,17 @@ ++ sprintf (fnbuf, "/var/tmp/rltrace.%ld", (long) getpid ()); ++ #endif ++ unlink (fnbuf); ++- _rl_tracefp = fopen (fnbuf, "w+"); +++ _rl_tracefp = fopen (fnbuf, "w+xe"); ++ return _rl_tracefp != 0; ++ } + +-@@ -1316,8 +1318,9 @@ getsymname (struct internal_syment *symbol_entry) ++ int ++ _rl_trclose (void) ++ { ++- int r; +++ int r = 0; + +- if (symbol_entry->_n._n_n._n_zeroes == 0) +- { +-- /* FIXME: Probably should be detecting corrupt symbol files by +-- seeing whether offset points to within the stringtab. */ +-+ if (symbol_entry->_n._n_n._n_offset > stringtab_length) +-+ error (_("COFF Error: string table offset (%ld) outside string table (length %ld)"), +-+ symbol_entry->_n._n_n._n_offset, stringtab_length); +- result = stringtab + symbol_entry->_n._n_n._n_offset; +- } +- else ++- r = fclose (_rl_tracefp); +++ if (_rl_tracefp) +++ r = fclose (_rl_tracefp); ++ _rl_tracefp = 0; ++ return r; ++ } +diff --git a/gdb_interface.c b/gdb_interface.c +index b14319c..17ffa40 100644 +--- a/gdb_interface.c ++++ b/gdb_interface.c +@@ -75,7 +75,7 @@ gdb_main_loop(int argc, char **argv) + #if defined(GDB_5_3) || defined(GDB_6_0) || defined(GDB_6_1) + command_loop_hook = main_loop; + #else +- deprecated_command_loop_hook = main_loop; ++// deprecated_command_loop_hook = main_loop; + #endif + #endif + gdb_main_entry(argc, argv); +@@ -126,7 +126,7 @@ display_gdb_banner(void) + #if defined(GDB_5_3) || defined(GDB_6_0) || defined(GDB_6_1) + command_loop_hook = exit_after_gdb_info; + #else +- deprecated_command_loop_hook = exit_after_gdb_info; ++// deprecated_command_loop_hook = exit_after_gdb_info; + #endif + #endif + args[0] = "gdb"; +diff --git a/lkcd_vmdump_v1.h b/lkcd_vmdump_v1.h +index 98ee094..dd57746 100644 +--- a/lkcd_vmdump_v1.h ++++ b/lkcd_vmdump_v1.h +@@ -114,7 +114,7 @@ typedef struct _dump_header_s { + struct new_utsname dh_utsname; + + /* the dump registers */ +-#if !defined(IA64) && !defined(S390) && !defined(S390X) && !defined(ARM64) && !defined(RISCV64) ++#if !defined(IA64) && !defined(S390) && !defined(S390X) && !defined(ARM64) && !defined(RISCV64) && !defined(SW_64) + struct pt_regs dh_regs; + #endif + +diff --git a/lkcd_vmdump_v2_v3.h b/lkcd_vmdump_v2_v3.h +index ef3067f..63609bb 100644 +--- a/lkcd_vmdump_v2_v3.h ++++ b/lkcd_vmdump_v2_v3.h +@@ -94,7 +94,7 @@ typedef struct _dump_header_asm_s { + + #endif /* ARM || X86 || PPC */ + +-#if defined(ALPHA) || defined(IA64) || defined(X86_64) || defined(PPC64) ++#if defined(ALPHA) || defined(SW_64) || defined(IA64) || defined(X86_64) || defined(PPC64) + + /* + * Plug in the real ../arch/alpha/vmdump.h when available. For now the +@@ -130,8 +130,10 @@ typedef struct _dump_header_asm_s { + + /* the dump registers */ + #ifndef IA64 ++#ifndef SW_64 + struct pt_regs dha_regs; + #endif ++#endif + + } dump_header_asm_t; + +diff --git a/sw_64.c b/sw_64.c +new file mode 100644 +index 0000000..5ce132f +--- /dev/null ++++ b/sw_64.c +@@ -0,0 +1,2716 @@ ++/* sw64.c - core analysis suite ++ * ++ * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. ++ * Copyright (C) 2002-2006, 2010-2013 David Anderson ++ * Copyright (C) 2002-2006, 2010-2013 Red Hat, Inc. All rights reserved. ++ * ++ * 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 2 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. ++ * ++ */ ++#ifdef SW_64 ++#include "defs.h" ++#include ++#include ++#include ++ ++static struct machine_specific sw64_machine_specific = { 0 }; ++ ++static int sw64_trace_status(struct gnu_request *, struct bt_info *); ++static void sw64_exception_frame(ulong, ulong, ++ struct gnu_request *, struct bt_info *); ++static void sw64_frame_offset(struct gnu_request *, ulong); ++static int sw64_backtrace_resync(struct gnu_request *, ulong, ++ struct bt_info *); ++static void sw64_print_stack_entry(struct gnu_request *, ulong, ++ char *, ulong, struct bt_info *); ++static int sw64_resync_speculate(struct gnu_request *, ulong,struct bt_info *); ++static int sw64_dis_filter(ulong, char *, unsigned int); ++static void dis_address_translation(ulong, char *, unsigned int); ++static void sw64_cmd_mach(void); ++static int sw64_get_smp_cpus(void); ++static void sw64_display_machine_stats(void); ++static void sw64_dump_line_number(char *, ulong); ++static void display_hwrpb(unsigned int); ++static void sw64_post_init(void); ++static struct line_number_hook sw64_line_number_hooks[]; ++ ++ ++#define SW64_CONTINUE_TRACE (1) ++#define SW64_END_OF_TRACE (2) ++#define SW64_EXCEPTION_FRAME (3) ++#define SW64_SYSCALL_FRAME (4) ++#define SW64_MM_FAULT (5) ++#define SW64_INTERRUPT_PENDING (6) ++#define SW64_RESCHEDULE (7) ++#define SW64_DOWN_FAILED (8) ++#define SW64_RET_FROM_SMP_FORK (9) ++#define SW64_SIGNAL_RETURN (10) ++#define SW64_STRACE (11) ++ ++static int sw64_eframe_search(struct bt_info *); ++static int sw64_uvtop(struct task_context *, ulong, physaddr_t *, int); ++static int sw64_is_kvddr(ulong addr); ++static int sw3231_kvtop(struct task_context *, ulong, physaddr_t *, int); ++static int sw6432_kvtop(struct task_context *, ulong, physaddr_t *, int); ++static void sw64_back_trace_cmd(struct bt_info *); ++static void sw64_kernel_back_trace(struct gnu_request *req, struct bt_info *bt); ++static ulong sw64_get_task_pgd(ulong task); ++static ulong sw64_processor_speed(void); ++static void sw64_get_stack_frame(struct bt_info *, ulong *, ulong *); ++static void get_sw64_frame(struct bt_info *, ulong *, ulong *); ++static int verify_user_eframe(struct bt_info *, ulong, ulong); ++static int sw64_translate_pte(ulong, void *, ulonglong); ++static uint64_t sw64_memory_size(void); ++static ulong sw64_vmalloc_start(void); ++static int sw64_is_task_addr(ulong); ++static int sw64_verify_symbol(const char *, ulong, char); ++ ++struct percpu_data { ++ ulong halt_PC; ++ ulong halt_ra; ++ ulong halt_pv; ++}; ++#define GET_HALT_PC 0x1 ++#define GET_HALT_RA 0x2 ++#define GET_HALT_PV 0x3 ++static ulong get_percpu_data(int, ulong, struct percpu_data *); ++ ++#define SW64_MAX_PHYSMEM_BITS 48 ++#define SW64_SECTION_SIZE_BITS 28 ++ ++/* ++ * Retrieve task registers for the time of the crash. ++ */ ++static int ++sw64_get_crash_notes(void) ++{ ++ struct machine_specific *ms = machdep->machspec; ++ ulong crash_notes, mini_coco; ++ Elf64_Nhdr *note; ++ ulong offset; ++ char *buf, *p; ++ struct sw64_pt_regs *pt_regs; ++ ulong *notes_ptrs; ++ ulong i; ++ ++ if (!symbol_exists("crash_notes")) ++ return FALSE; ++ ++ crash_notes = symbol_value("crash_notes"); ++ ++ notes_ptrs = (ulong *)GETBUF(kt->cpus*sizeof(notes_ptrs[0])); ++ ++ /* ++ * Read crash_notes for the first CPU. crash_notes are in standard ELF ++ * note format. ++ */ ++ if (!readmem(crash_notes, KVADDR, ¬es_ptrs[kt->cpus-1], ++ sizeof(notes_ptrs[kt->cpus-1]), "crash_notes", RETURN_ON_ERROR)) { ++ error(WARNING, "cannot read crash_notes\n"); ++ FREEBUF(notes_ptrs); ++ return FALSE; ++ } ++ ++ if (symbol_exists("__per_cpu_offset")) { ++ /* ++ * Add __per_cpu_offset for each cpu to form the notes pointer. ++ */ ++ for (i = 0; icpus; i++){ ++ notes_ptrs[i] = notes_ptrs[kt->cpus-1] + kt->__per_cpu_offset[i]; ++ } ++ } ++ ++ buf = GETBUF(SIZE(note_buf)); ++ ++ if (!(ms->panic_task_regs = calloc((size_t)kt->cpus, sizeof(struct sw64_pt_regs)))) ++ error(FATAL, "cannot calloc panic_task_regs space. cpus:%d\n", kt->cpus); ++ ++ for (i = 0; i < kt->cpus; i++) { ++ ++ if (!readmem(notes_ptrs[i], KVADDR, buf, SIZE(note_buf), ++ "note_buf_t", RETURN_ON_ERROR)) { ++ error(WARNING, "failed to read note_buf_t\n"); ++ goto fail; ++ } ++ ++ /* ++ * Do some sanity checks for this note before reading registers from it. ++ */ ++ note = (Elf64_Nhdr *)buf; ++ p = buf + sizeof(Elf64_Nhdr); ++ /* ++ * dumpfiles created with qemu won't have crash_notes, but there will ++ * be elf notes; dumpfiles created by kdump do not create notes for ++ * offline cpus. ++ */ ++ if (note->n_namesz == 0 && (DISKDUMP_DUMPFILE() || KDUMP_DUMPFILE())) { ++ if (DISKDUMP_DUMPFILE()) ++ note = diskdump_get_prstatus_percpu(i); ++ else if (KDUMP_DUMPFILE()) ++ note = netdump_get_prstatus_percpu(i); ++ if (note) { ++ /* ++ * SIZE(note_buf) accounts for a "final note", which is a ++ * trailing empty elf note header. ++ */ ++ long notesz = SIZE(note_buf) - sizeof(Elf64_Nhdr); ++ ++ if (sizeof(Elf64_Nhdr) + roundup(note->n_namesz, 4) + ++ note->n_descsz == notesz) ++ BCOPY((char *)note, buf, notesz); ++ } else { ++ error(WARNING, ++ "cannot find NT_PRSTATUS note for cpu: %d\n", i); ++ continue; ++ } ++ } ++ ++ if (note->n_type != NT_PRSTATUS) { ++ error(WARNING, "invalid note (n_type != NT_PRSTATUS)\n"); ++ goto fail; ++ } ++ if (p[0] != 'C' || p[1] != 'O' || p[2] != 'R' || p[3] != 'E') { ++ error(WARNING, "invalid note (name != \"CORE\"\n"); ++ goto fail; ++ } ++ offset = sizeof(Elf64_Nhdr); ++ offset = roundup(offset + note->n_namesz, 4); ++ p = buf + offset; ++ ++ BCOPY(p + OFFSET(elf_prstatus_pr_reg), &ms->panic_task_regs[i], ++ sizeof(struct sw64_pt_regs)); ++ } ++ FREEBUF(buf); ++ FREEBUF(notes_ptrs); ++ return TRUE; ++fail: ++ FREEBUF(buf); ++ FREEBUF(notes_ptrs); ++ free(ms->panic_task_regs); ++ ms->panic_task_regs = NULL; ++ return FALSE; ++} ++ ++#define BUFFER_SIZE 1024 ++ ++static int is_sw3231(void) ++{ ++ FILE *file; ++ char buffer[BUFFER_SIZE]; ++ const char *filename = "/proc/cpuinfo"; ++ const char *keyword = "SW3231"; ++ int found = 0; ++ ++ file = fopen(filename, "r"); ++ if (file == NULL) { ++ perror("fopen failed!"); ++ return -1; ++ } ++ ++ while (fgets(buffer, BUFFER_SIZE, file) != NULL) { ++ buffer[strcspn(buffer, "\n")] = 0; ++ ++ if (strstr(buffer, keyword) != NULL) { ++ found = 1; ++ break; ++ } ++ } ++ ++ fclose(file); ++ ++ return found; ++} ++ ++/* ++ * Do all necessary machine-specific setup here. This is called three times, ++ * before symbol table initialization, and before and after GDB has been ++ * initialized. ++ */ ++void ++sw64_init(int when) ++{ ++ int tmp; ++ ++ switch (when) ++ { ++ case SETUP_ENV: ++ machdep->process_elf_notes = process_elf64_notes; ++ break; ++ ++ case PRE_SYMTAB: ++ machdep->machspec = &sw64_machine_specific; ++ machdep->verify_symbol = sw64_verify_symbol; ++ if (pc->flags & KERNEL_DEBUG_QUERY) ++ return; ++ machdep->pagesize = memory_page_size(); ++ machdep->pageshift = ffs(machdep->pagesize) - 1; ++ machdep->pageoffset = machdep->pagesize - 1; ++ machdep->pagemask = ~(machdep->pageoffset); ++ machdep->stacksize = machdep->pagesize; ++ if ((machdep->pgd = (char *)malloc(PAGESIZE())) == NULL) ++ error(FATAL, "cannot malloc pgd space."); ++ if ((machdep->pud = (char *)malloc(PAGESIZE())) == NULL) ++ error(FATAL, "cannot malloc pud space."); ++ if ((machdep->pmd = (char *)malloc(PAGESIZE())) == NULL) ++ error(FATAL, "cannot malloc pmd space."); ++ if ((machdep->ptbl = (char *)malloc(PAGESIZE())) == NULL) ++ error(FATAL, "cannot malloc ptbl space."); ++ machdep->last_pgd_read = 0; ++ machdep->last_pud_read = 0; ++ machdep->last_pmd_read = 0; ++ machdep->last_ptbl_read = 0; ++ machdep->verify_paddr = generic_verify_paddr; ++ machdep->ptrs_per_pgd = PTRS_PER_PGD; ++ break; ++ ++ case PRE_GDB: ++ switch (symbol_value("_stext") & KSEG_BASE) ++ { ++ case KSEG_BASE: ++ machdep->kvbase = KSEG_BASE; ++ break; ++ ++ default: ++ error(FATAL, ++ "cannot determine KSEG base from _stext: %lx\n", ++ symbol_value("_stext")); ++ } ++ ++ machdep->identity_map_base = machdep->kvbase; ++ machdep->is_kvaddr = sw64_is_kvddr; ++ machdep->is_uvaddr = generic_is_uvaddr; ++ machdep->eframe_search = sw64_eframe_search; ++ machdep->back_trace = sw64_back_trace_cmd; ++ machdep->processor_speed = sw64_processor_speed; ++ machdep->uvtop = sw64_uvtop; ++ if (is_sw3231()) ++ machdep->kvtop = sw3231_kvtop; ++ else ++ machdep->kvtop = sw6432_kvtop; ++ machdep->get_task_pgd = sw64_get_task_pgd; ++ machdep->dump_irq = generic_dump_irq; ++ machdep->get_stack_frame = sw64_get_stack_frame; ++ machdep->get_stackbase = generic_get_stackbase; ++ machdep->get_stacktop = generic_get_stacktop; ++ machdep->translate_pte = sw64_translate_pte; ++ machdep->memory_size = sw64_memory_size; ++ machdep->vmalloc_start = sw64_vmalloc_start; ++ machdep->is_task_addr = sw64_is_task_addr; ++ if (symbol_exists("console_crash")) { ++ get_symbol_data("console_crash", sizeof(int), &tmp); ++ if (tmp) ++ machdep->flags |= HWRESET; ++ } ++ machdep->dis_filter = sw64_dis_filter; ++ machdep->cmd_mach = sw64_cmd_mach; ++ machdep->get_smp_cpus = sw64_get_smp_cpus; ++ machdep->line_number_hooks = sw64_line_number_hooks; ++ machdep->value_to_symbol = generic_machdep_value_to_symbol; ++ machdep->init_kernel_pgd = NULL; ++ break; ++ ++ case POST_GDB: ++ MEMBER_OFFSET_INIT(thread_struct_ptbr, ++ "thread_struct", "ptbr"); ++ MEMBER_OFFSET_INIT(hwrpb_struct_cycle_freq, ++ "hwrpb_struct", "cycle_freq"); ++ MEMBER_OFFSET_INIT(hwrpb_struct_processor_offset, ++ "hwrpb_struct", "processor_offset"); ++ MEMBER_OFFSET_INIT(hwrpb_struct_processor_size, ++ "hwrpb_struct", "processor_size"); ++ MEMBER_OFFSET_INIT(percpu_struct_halt_PC, ++ "percpu_struct", "halt_PC"); ++ MEMBER_OFFSET_INIT(percpu_struct_halt_ra, ++ "percpu_struct", "halt_ra"); ++ MEMBER_OFFSET_INIT(percpu_struct_halt_pv, ++ "percpu_struct", "halt_pv"); ++ MEMBER_OFFSET_INIT(switch_stack_r26, ++ "switch_stack", "r26"); ++ ++ if (symbol_exists("irq_desc")) ++ ARRAY_LENGTH_INIT(machdep->nr_irqs, irq_desc, ++ "irq_desc", NULL, 0); ++ else if (kernel_symbol_exists("nr_irqs")) ++ get_symbol_data("nr_irqs", sizeof(unsigned int), ++ &machdep->nr_irqs); ++ else ++ machdep->nr_irqs = 0; ++ if (!machdep->hz) ++ machdep->hz = HZ; ++ machdep->max_physmem_bits = SW64_MAX_PHYSMEM_BITS; ++ machdep->section_size_bits = SW64_SECTION_SIZE_BITS; ++ STRUCT_SIZE_INIT(note_buf, "note_buf_t"); ++ STRUCT_SIZE_INIT(elf_prstatus, "elf_prstatus"); ++ MEMBER_OFFSET_INIT(elf_prstatus_pr_pid, "elf_prstatus", "pr_pid"); ++ MEMBER_OFFSET_INIT(elf_prstatus_pr_reg, "elf_prstatus", "pr_reg"); ++ ++ break; ++ ++ case POST_INIT: ++ sw64_post_init(); ++ break; ++ case POST_VM: ++ /* ++ * crash_notes contains machine specific information about the ++ * crash. In particular, it contains CPU registers at the time ++ * of the crash. We need this information to extract correct ++ * backtraces from the panic task. ++ */ ++ if (!LIVE() && !sw64_get_crash_notes()) ++ error(WARNING, ++ "cannot retrieve registers for active task%s\n\n", ++ kt->cpus > 1 ? "s" : ""); ++ ++ break; ++ } ++} ++ ++/* ++ * Unroll a kernel stack. ++ */ ++static void ++sw64_back_trace_cmd(struct bt_info *bt) ++{ ++ char buf[BUFSIZE]; ++ struct gnu_request *req; ++ ++ bt->flags |= BT_EXCEPTION_FRAME; ++ ++ if (CRASHDEBUG(1) || bt->debug) ++ fprintf(fp, " => PC: %lx (%s) FP: %lx \n", ++ bt->instptr, value_to_symstr(bt->instptr, buf, 0), ++ bt->stkptr ); ++ ++ req = (struct gnu_request *)GETBUF(sizeof(struct gnu_request)); ++ req->command = GNU_STACK_TRACE; ++ req->flags = GNU_RETURN_ON_ERROR; ++ req->buf = GETBUF(BUFSIZE); ++ req->debug = bt->debug; ++ req->task = bt->task; ++ ++ req->pc = bt->instptr; ++ req->sp = bt->stkptr; ++ ++ if (bt->flags & BT_USE_GDB) { ++ strcpy(req->buf, "backtrace"); ++ gdb_interface(req); ++ } ++ else ++ sw64_kernel_back_trace(req, bt); ++ ++ FREEBUF(req->buf); ++ FREEBUF(req); ++ ++ ++} ++ ++ ++/* ++ * Unroll the kernel stack. ++ */ ++ ++#define SW64_BACKTRACE_SPECULATE(X) \ ++{ \ ++ speculate_location = X; \ ++ \ ++ if (bt->flags & BT_SPECULATE) \ ++ return; \ ++ \ ++ BZERO(btloc, sizeof(struct bt_info)); \ ++ btloc->task = req->task; \ ++ btloc->tc = bt->tc; \ ++ btloc->stackbase = bt->stackbase; \ ++ btloc->stacktop = bt->stacktop; \ ++ btloc->flags = BT_TEXT_SYMBOLS_NOPRINT; \ ++ hook.eip = 0; \ ++ hook.esp = req->lastsp ? req->lastsp + sizeof(long) : 0; \ ++ btloc->hp = &hook; \ ++ \ ++ back_trace(btloc); \ ++ \ ++ if (hook.esp && hook.eip) { \ ++ req->hookp = &hook; \ ++ if (sw64_resync_speculate(req, bt->flags, bt)) { \ ++ req->pc = hook.eip; \ ++ req->sp = hook.esp; \ ++ continue; \ ++ } \ ++ goto show_remaining_text; \ ++ } \ ++ goto show_remaining_text; \ ++} ++ ++static void ++sw64_kernel_back_trace(struct gnu_request *req, struct bt_info *bt) ++{ ++ struct machine_specific *ms = machdep->machspec; ++ struct sw64_pt_regs *pt_regs; ++ struct task_context *tc; ++ ulong next_sp, next_pc; ++ int i, idx = 0; ++ ulong *up; ++ struct load_module *lm; ++ char buf1[BUFSIZE]; ++ char buf2[BUFSIZE]; ++ ++ tc = task_to_context(req->task); ++ pt_regs = &ms->panic_task_regs[tc->processor]; ++ ++ for (i = (req->pc - bt->stackbase)/sizeof(ulong); ++ i < LONGS_PER_STACK; i++) { ++ up = (ulong *)(&bt->stackbuf[i*sizeof(ulong)]); ++ if (is_kernel_text_offset(*up)) { ++ if (!next_pc) ++ next_pc = *up; ++ else if (!next_sp) ++ next_sp = bt->stackbase + (i * sizeof(long)); ++ } ++ if (is_kernel_text(*up)) { ++ fprintf(fp, "#%d %s[%s] %s at %lx", ++ idx, ++ bt->flags & BT_ERROR_MASK ? ++ " " : "", ++ mkstring(buf1, VADDR_PRLEN, ++ RJUST|LONG_HEX, ++ MKSTR(bt->stackbase + ++ (i * sizeof(long)))), ++ bt->flags & BT_SYMBOL_OFFSET ? ++ value_to_symstr(*up, buf2, bt->radix) : ++ closest_symbol(*up), *up); ++ if (module_symbol(*up, NULL, &lm, NULL, 0)) ++ fprintf(fp, " [%s]", lm->mod_name); ++ fprintf(fp, "\n"); ++ idx++; ++ } ++ } ++ fprintf(fp, "PC:%lx [%s]\n", pt_regs->pc, value_to_symstr(pt_regs->pc, buf2, bt->radix)); ++ fprintf(fp, "RA:%lx [%s]\n", pt_regs->r26, value_to_symstr(pt_regs->r26, buf2, bt->radix)); ++ fprintf(fp, ++ "v0:%016lx t0:%016lx t1:%016lx\n" ++ "t2:%016lx t3:%016lx t4:%016lx\n" ++ "t5:%016lx t6:%016lx t7:%016lx\n" ++ "r9:%016lx r10:%016lx r11:%016lx\n" ++ "r12:%016lx r13:%016lx r14:%016lx\n" ++ "r15:%016lx r16:%016lx r17:%016lx\n" ++ "r18:%016lx a3:%016lx a4:%016lx\n" ++ "a5:%016lx t8:%016lx t9:%016lx\n" ++ "t10:%016lx t11:%016lx ra:%016lx\n" ++ "pv:%016lx at:%016lx gp:%016lx\n" ++ "usp:%016lx pc:%016lx unique:%016lx\n", ++ pt_regs->r0, ++ pt_regs->r1, ++ pt_regs->r2, ++ pt_regs->r3, ++ pt_regs->r4, ++ pt_regs->r5, ++ pt_regs->r6, ++ pt_regs->r7, ++ pt_regs->r8, ++ pt_regs->r9, ++ pt_regs->r10, ++ pt_regs->r11, ++ pt_regs->r12, ++ pt_regs->r13, ++ pt_regs->r14, ++ pt_regs->r15, ++ pt_regs->r16, ++ pt_regs->r17, ++ pt_regs->r18, ++ pt_regs->r19, ++ pt_regs->r20, ++ pt_regs->r21, ++ pt_regs->r22, ++ pt_regs->r23, ++ pt_regs->r24, ++ pt_regs->r25, ++ pt_regs->r26, ++ pt_regs->r27, ++ pt_regs->r28, ++ pt_regs->gp, ++ pt_regs->usp, ++ pt_regs->pc, ++ pt_regs->ps ++ ); ++} ++/* ++ * print one entry of a stack trace ++ */ ++static void ++sw64_print_stack_entry(struct gnu_request *req, ++ ulong callpc, ++ char *name, ++ ulong flags, ++ struct bt_info *bt) ++{ ++ struct load_module *lm; ++ ++ if (BT_REFERENCE_CHECK(bt)) { ++ switch (bt->ref->cmdflags & (BT_REF_SYMBOL|BT_REF_HEXVAL)) ++ { ++ case BT_REF_SYMBOL: ++ if (STREQ(name, bt->ref->str) || ++ (STREQ(name, "strace") && ++ STREQ(bt->ref->str, "entSys"))) { ++ bt->ref->cmdflags |= BT_REF_FOUND; ++ } ++ break; ++ ++ case BT_REF_HEXVAL: ++ if (bt->ref->hexval == callpc) ++ bt->ref->cmdflags |= BT_REF_FOUND; ++ break; ++ } ++ } else { ++ fprintf(fp, "%s#%d [%lx] %s at %lx", ++ req->curframe < 10 ? " " : "", req->curframe, req->sp, ++ STREQ(name, "strace") ? "strace (via entSys)" : name, ++ callpc); ++ if (module_symbol(callpc, NULL, &lm, NULL, 0)) ++ fprintf(fp, " [%s]", lm->mod_name); ++ fprintf(fp, "\n"); ++ } ++ ++ if (!(flags & BT_SPECULATE)) ++ req->curframe++; ++ ++ if (flags & BT_SAVE_LASTSP) ++ req->lastsp = req->sp; ++ ++ if (BT_REFERENCE_CHECK(bt)) ++ return; ++ ++ if (flags & BT_LINE_NUMBERS) ++ sw64_dump_line_number(name, callpc); ++} ++ ++static const char *hook_files[] = { ++ "arch/sw_64/kernel/entry.S", ++ "arch/sw_64/kernel/head.S", ++ "init/main.c", ++ "arch/sw_64/kernel/smp.c", ++}; ++ ++#define ENTRY_S ((char **)&hook_files[0]) ++#define HEAD_S ((char **)&hook_files[1]) ++#define MAIN_C ((char **)&hook_files[2]) ++#define SMP_C ((char **)&hook_files[3]) ++ ++static struct line_number_hook sw64_line_number_hooks[] = { ++ {"entInt", ENTRY_S}, ++ {"entMM", ENTRY_S}, ++ {"entArith", ENTRY_S}, ++ {"entIF", ENTRY_S}, ++ {"entDbg", ENTRY_S}, ++ {"undo_switch_stack", ENTRY_S}, ++ {"entUna", ENTRY_S}, ++ {"entUnaUser", ENTRY_S}, ++ {"sw_switch_to", ENTRY_S}, ++ {"entSys", ENTRY_S}, ++ {"ret_from_sys_call", ENTRY_S}, ++ {"restore_all", ENTRY_S}, ++ {"strace", ENTRY_S}, ++ {"strace_success", ENTRY_S}, ++ {"strace_error", ENTRY_S}, ++ {"syscall_error", ENTRY_S}, ++ {"ret_success", ENTRY_S}, ++ {"ret_from_fork", ENTRY_S}, ++ {"sys_sigreturn", ENTRY_S}, ++ {"sys_rt_sigreturn", ENTRY_S}, ++ ++ {"_stext", HEAD_S}, ++ {"__start", HEAD_S}, ++ {"__smp_callin", HEAD_S}, ++ {"halt", HEAD_S}, ++ ++ {"start_kernel", MAIN_C}, ++ ++ {"smp_callin", SMP_C}, ++ ++ {NULL, NULL} /* list must be NULL-terminated */ ++}; ++ ++static void ++sw64_dump_line_number(char *name, ulong callpc) ++{ ++ char buf[BUFSIZE], *p; ++ int retries; ++ ++ retries = 0; ++try_closest: ++ get_line_number(callpc, buf, FALSE); ++ if (strlen(buf)) { ++ if (retries) { ++ p = strstr(buf, ": "); ++ if (p) ++ *p = NULLCHAR; ++ } ++ fprintf(fp, " %s\n", buf); ++ } else { ++ if (retries) ++ fprintf(fp, GDB_PATCHED() ? ++ "" : " (cannot determine file and line number)\n"); ++ else { ++ retries++; ++ callpc = closest_symbol_value(callpc); ++ goto try_closest; ++ } ++ } ++} ++ ++ ++/* ++ * Look for the frame size storage at the beginning of a function. ++ * If it's not obvious, try gdb. ++ * ++ * For future reference, here's where the numbers come from: ++ * ++ * 0xfffffc00003217e8 : subq sp,0x50,sp ++ * fffffc00003217e8: 43ca153e ++ * 010000 11110 01010000 1 0101001 11110 ++ * ++ * 0xfffffc0000321668 : subq sp,0x60,sp ++ * fffffc0000321668: 43cc153e ++ * 010000 11110 01100000 1 0101001 11110 ++ * ++ * 0xfffffc000035d028 : subq sp,0x70,sp ++ * fffffc000035d028: 43ce153e ++ * 010000 11110 01110000 1 0101001 11110 ++ * ++ * 0100 0011 110x xxxx xxx1 0101 0011 1110 ++ * 1111 1111 111x xxxx xxx1 1111 1111 1111 ++ * 0000 0000 0001 1111 1110 0000 0000 0000 ++ * f f e 0 1 f f f instruction mask ++ * 0 0 1 f e 0 0 0 offset ++ * ++ * stq ra,0(sp) ++ * fffffc000035d034: b75e0000 ++ */ ++ ++static void ++sw64_frame_offset(struct gnu_request *req, ulong alt_pc) ++{ ++ uint *ip, ival; ++ ulong value; ++ ++ req->value = value = 0; ++ ++ if (alt_pc && !is_kernel_text(alt_pc)) ++ error(FATAL, ++ "trying to get frame offset of non-text address: %lx\n", ++ alt_pc); ++ else if (!alt_pc && !is_kernel_text(req->pc)) ++ error(FATAL, ++ "trying to get frame offset of non-text address: %lx\n", ++ req->pc); ++ ++ ip = alt_pc ? (int *)closest_symbol_value(alt_pc) : ++ (int *)closest_symbol_value(req->pc); ++ if (!ip) ++ goto use_gdb; ++ ++ ival = 0; ++ ++ /* ++ * Don't go any farther than "stq ra,0(sp)" (0xb75e0000) ++ */ ++ while (ival != 0xb75e0000) { ++ if (!text_value_cache((ulong)ip, 0, &ival)) { ++ readmem((ulong)ip, KVADDR, &ival, ++ sizeof(uint), "uncached text value", ++ FAULT_ON_ERROR); ++ text_value_cache((ulong)ip, ival, NULL); ++ } ++ ++ if ((ival & 0xffe01fff) == 0x43c0153e) { ++ value = (ival & 0x1fe000) >> 13; ++ break; ++ } ++ ip++; ++ } ++ ++ if (value) { ++ req->value = value; ++ return; ++ } ++ ++use_gdb: ++#ifndef GDB_5_3 ++{ ++ static int gdb_frame_offset_warnings = 10; ++ ++ if (gdb_frame_offset_warnings-- > 0) ++ error(WARNING, ++ "GNU_ALPHA_FRAME_OFFSET functionality not ported to gdb\n"); ++} ++#endif ++ req->command = GNU_ALPHA_FRAME_OFFSET; ++ if (alt_pc) { ++ ulong pc_save; ++ pc_save = req->pc; ++ req->pc = alt_pc; ++ gdb_interface(req); ++ req->pc = pc_save; ++ } else ++ gdb_interface(req); ++} ++ ++/* ++ * Look for key routines that either mean the trace has ended or has ++ * bumped into an exception frame. ++ */ ++int ++sw64_trace_status(struct gnu_request *req, struct bt_info *bt) ++{ ++ ulong value; ++ char *func; ++ ulong frame; ++ ++ req->addr = 0; ++ func = req->name; ++ frame = req->sp; ++ ++ if (STREQ(func, "start_kernel") || ++ STREQ(func, "smp_callin") || ++ STREQ(func, "kernel_thread") || ++ STREQ(func, "__kernel_thread")) ++ return SW64_END_OF_TRACE; ++ ++ if (STREQ(func, "ret_from_smp_fork") || ++ STREQ(func, "ret_from_smpfork")) ++ return SW64_RET_FROM_SMP_FORK; ++ ++ if (STREQ(func, "entSys")) ++ return SW64_SYSCALL_FRAME; ++ ++ if (STREQ(func, "entMM")) { ++ req->sp += 56; /* see entMM in entry.S */ ++ return SW64_MM_FAULT; ++ } ++ ++ if (STREQ(func, "do_entInt")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "do_entArith")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "do_entIF")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "do_entDbg")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "handle_bottom_half")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "handle_softirq")) ++ return SW64_EXCEPTION_FRAME; ++ ++ if (STREQ(func, "reschedule")) ++ return SW64_RESCHEDULE; ++ ++ if (STREQ(func, "ret_from_reschedule")) ++ return SW64_RESCHEDULE; ++ ++ if (STREQ(func, "signal_return")) ++ return SW64_SIGNAL_RETURN; ++ ++ if (STREQ(func, "strace")) ++ return SW64_STRACE; ++ ++ if (STREQ(func, "__down_failed") || ++ STREQ(func, "__down_failed_interruptible")) { ++ readmem(req->sp + 144, KVADDR, &req->pc, sizeof(ulong), ++ "__down_failed r26", FAULT_ON_ERROR); ++ req->sp += 160; ++ return SW64_DOWN_FAILED; ++ } ++ ++ value = GET_STACK_ULONG(frame); ++ ++ if (STREQ(closest_symbol(value), "do_entInt") || ++ STREQ(closest_symbol(value), "do_entArith") || ++ STREQ(closest_symbol(value), "do_entIF") || ++ STREQ(closest_symbol(value), "do_entDbg")) { ++ req->addr = value; ++ req->frame = 0; ++ ++ while (INSTACK(frame, bt)) { ++ frame += sizeof(ulong); ++ value = GET_STACK_ULONG(frame); ++ if (STREQ(closest_symbol(value), "ret_from_sys_call")) { ++ sw64_frame_offset(req, req->addr); ++ /* req->frame = frame + req->value; XXX */ ++ break; ++ } ++ } ++ return SW64_INTERRUPT_PENDING; ++ } ++ ++ return SW64_CONTINUE_TRACE; ++} ++ ++/* ++ * Redo the gdb pt_regs structure output. ++ */ ++enum regnames { _r0_, _r1_, _r2_, _r3_, _r4_, _r5_, _r6_, _r7_, _r8_, ++ _r19_, _r20_, _r21_, _r22_, _r23_, _r24_, _r25_, _r26_, ++ _r27_, _r28_, _hae_, _trap_a0_, _trap_a1_, _trap_a2_, ++ _ps_, _pc_, _gp_, _r16_, _r17_, _r18_, NUMREGS}; ++ ++struct sw64_eframe { ++ char regs[30][30]; ++ ulong value[29]; ++}; ++ ++static void ++sw64_exception_frame(ulong addr, ++ ulong flags, ++ struct gnu_request *req, ++ struct bt_info *bt) ++{ ++ int i, j; ++ char buf[BUFSIZE]; ++ ulong value; ++ physaddr_t paddr; ++ struct sw64_eframe eframe; ++ ++ if (CRASHDEBUG(4)) ++ fprintf(fp, "sw64_exception_frame: %lx\n", addr); ++ ++ if (flags & BT_SPECULATE) { ++ req->pc = 0; ++ fprintf(fp, "SW64 EXCEPTION FRAME\n"); ++ return; ++ } ++ ++ BZERO(&eframe, sizeof(struct sw64_eframe)); ++ ++ open_tmpfile(); ++ dump_struct("pt_regs", addr, RADIX(16)); ++ rewind(pc->tmpfile); ++ while (fgets(buf, BUFSIZE, pc->tmpfile)) { ++ strip_comma(clean_line(buf)); ++ if (!strstr(buf, "0x")) ++ continue; ++ ++ extract_hex(buf, &value, NULLCHAR, TRUE); ++ if (CRASHDEBUG(4)) ++ fprintf(pc->saved_fp, "<%s> %lx\n", buf, value); ++ ++ if (STRNEQ(buf, "r0 = ")) { ++ sprintf(eframe.regs[_r0_], " V0/R0: %016lx", value); ++ eframe.value[_r0_] = value; ++ } ++ if (STRNEQ(buf, "r1 = ")) { ++ sprintf(eframe.regs[_r1_], " T0/R1: %016lx", value); ++ eframe.value[_r1_] = value; ++ } ++ if (STRNEQ(buf, "r2 = ")) { ++ sprintf(eframe.regs[_r2_], " T1/R2: %016lx", value); ++ eframe.value[_r2_] = value; ++ } ++ if (STRNEQ(buf, "r3 = ")) { ++ sprintf(eframe.regs[_r3_], " T2/R3: %016lx", value); ++ eframe.value[_r3_] = value; ++ } ++ if (STRNEQ(buf, "r4 = ")) { ++ sprintf(eframe.regs[_r4_], " T3/R4: %016lx", value); ++ eframe.value[_r4_] = value; ++ } ++ if (STRNEQ(buf, "r5 = ")) { ++ sprintf(eframe.regs[_r5_], " T4/R5: %016lx", value); ++ eframe.value[_r5_] = value; ++ } ++ if (STRNEQ(buf, "r6 = ")) { ++ sprintf(eframe.regs[_r6_], " T5/R6: %016lx", value); ++ eframe.value[_r6_] = value; ++ } ++ if (STRNEQ(buf, "r7 = ")) { ++ sprintf(eframe.regs[_r7_], " T6/R7: %016lx", value); ++ eframe.value[_r7_] = value; ++ } ++ if (STRNEQ(buf, "r8 = ")) { ++ sprintf(eframe.regs[_r8_], " T7/R8: %016lx", value); ++ eframe.value[_r8_] = value; ++ } ++ if (STRNEQ(buf, "r19 = ")) { ++ sprintf(eframe.regs[_r19_], " A3/R19: %016lx", value); ++ eframe.value[_r19_] = value; ++ } ++ if (STRNEQ(buf, "r20 = ")) { ++ sprintf(eframe.regs[_r20_], " A4/R20: %016lx", value); ++ eframe.value[_r20_] = value; ++ } ++ if (STRNEQ(buf, "r21 = ")) { ++ sprintf(eframe.regs[_r21_], " A5/R21: %016lx", value); ++ eframe.value[_r21_] = value; ++ } ++ if (STRNEQ(buf, "r22 = ")) { ++ sprintf(eframe.regs[_r22_], " T8/R22: %016lx", value); ++ eframe.value[_r22_] = value; ++ } ++ if (STRNEQ(buf, "r23 = ")) { ++ sprintf(eframe.regs[_r23_], " T9/R23: %016lx", value); ++ eframe.value[_r23_] = value; ++ } ++ if (STRNEQ(buf, "r24 = ")) { ++ sprintf(eframe.regs[_r24_], "T10/R24: %016lx", value); ++ eframe.value[_r24_] = value; ++ } ++ if (STRNEQ(buf, "r25 = ")) { ++ sprintf(eframe.regs[_r25_], "T11/R25: %016lx", value); ++ eframe.value[_r25_] = value; ++ } ++ if (STRNEQ(buf, "r26 = ")) { ++ sprintf(eframe.regs[_r26_], " RA/R26: %016lx", value); ++ eframe.value[_r26_] = value; ++ } ++ if (STRNEQ(buf, "r27 = ")) { ++ sprintf(eframe.regs[_r27_], "T12/R27: %016lx", value); ++ eframe.value[_r27_] = value; ++ } ++ if (STRNEQ(buf, "r28 = ")) { ++ sprintf(eframe.regs[_r28_], " AT/R28: %016lx", value); ++ eframe.value[_r28_] = value; ++ } ++ if (STRNEQ(buf, "hae = ")) { ++ sprintf(eframe.regs[_hae_], " HAE: %016lx", value); ++ eframe.value[_hae_] = value; ++ } ++ if (STRNEQ(buf, "trap_a0 = ")) { ++ sprintf(eframe.regs[_trap_a0_], "TRAP_A0: %016lx", ++ value); ++ eframe.value[_trap_a0_] = value; ++ } ++ if (STRNEQ(buf, "trap_a1 = ")) { ++ sprintf(eframe.regs[_trap_a1_], "TRAP_A1: %016lx", ++ value); ++ eframe.value[_trap_a1_] = value; ++ } ++ if (STRNEQ(buf, "trap_a2 = ")) { ++ sprintf(eframe.regs[_trap_a2_], "TRAP_A2: %016lx", ++ value); ++ eframe.value[_trap_a2_] = value; ++ } ++ if (STRNEQ(buf, "ps = ")) { ++ sprintf(eframe.regs[_ps_], " PS: %016lx", value); ++ eframe.value[_ps_] = value; ++ } ++ if (STRNEQ(buf, "pc = ")) { ++ sprintf(eframe.regs[_pc_], " PC: %016lx", value); ++ eframe.value[_pc_] = value; ++ } ++ if (STRNEQ(buf, "gp = ")) { ++ sprintf(eframe.regs[_gp_], " GP/R29: %016lx", value); ++ eframe.value[_gp_] = value; ++ } ++ if (STRNEQ(buf, "r16 = ")) { ++ sprintf(eframe.regs[_r16_], " A0/R16: %016lx", value); ++ eframe.value[_r16_] = value; ++ } ++ if (STRNEQ(buf, "r17 = ")) { ++ sprintf(eframe.regs[_r17_], " A1/R17: %016lx", value); ++ eframe.value[_r17_] = value; ++ } ++ if (STRNEQ(buf, "r18 =")) { ++ sprintf(eframe.regs[_r18_], " A2/R18: %016lx", value); ++ eframe.value[_r18_] = value; ++ } ++ } ++ close_tmpfile(); ++ ++ if ((flags & BT_EXCEPTION_FRAME) && !BT_REFERENCE_CHECK(bt)) { ++dump_eframe: ++ fprintf(fp, " EFRAME: %lx ", addr); ++ fprintf(fp, "%s\n", eframe.regs[_r24_]); ++ ++ for (i = 0; i < (((NUMREGS+1)/2)-1); i++) { ++ fprintf(fp, "%s ", eframe.regs[i]); ++ pad_line(fp, 21 - strlen(eframe.regs[i]), ' '); ++ j = i+((NUMREGS+1)/2); ++ fprintf(fp, "%s", eframe.regs[j]); ++ if (((j == _pc_) || (j == _r26_)) && ++ is_kernel_text(eframe.value[j])) ++ fprintf(fp, " <%s>", ++ value_to_symstr(eframe.value[j], buf, 0)); ++ fprintf(fp, "\n"); ++ } ++ } ++ ++ req->ra = eframe.value[_r26_]; ++ req->pc = eframe.value[_pc_]; ++ req->sp = addr + (29 * sizeof(ulong)); ++ ++ if (flags & BT_USER_EFRAME) { ++ flags &= ~BT_USER_EFRAME; ++ if (!BT_REFERENCE_CHECK(bt) && (eframe.value[_ps_] == 8) && ++ (((uvtop(task_to_context(req->task), req->pc, &paddr, 0) || ++ (volatile ulong)paddr) && ++ (uvtop(task_to_context(req->task), req->ra, &paddr, 0) || ++ (volatile ulong)paddr)) || ++ (IS_ZOMBIE(req->task) || IS_EXITING(req->task)))) { ++ if (!(flags & ++ (BT_RESCHEDULE|BT_RET_FROM_SMP_FORK|BT_STRACE))) ++ fprintf(fp, ++ "NOTE: kernel-entry exception frame:\n"); ++ goto dump_eframe; ++ } ++ } ++} ++ ++/* ++ * Look for likely exception frames in a stack. ++ */ ++struct sw_64_pt_regs { ++ ulong reg_value[NUMREGS]; ++}; ++ ++static int ++sw64_eframe_search(struct bt_info *bt) ++{ ++ ulong *first, *last; ++ ulong eframe; ++ struct sw_64_pt_regs *pt; ++ struct gnu_request *req; /* needed for sw64_exception_frame */ ++ ulong *stack; ++ int cnt; ++ ++ stack = (ulong *)bt->stackbuf; ++ req = (struct gnu_request *)GETBUF(sizeof(struct gnu_request)); ++ req->task = bt->task; ++ ++ first = stack + ++ (roundup(SIZE(task_struct), sizeof(ulong)) / sizeof(ulong)); ++ last = stack + ++ (((bt->stacktop - bt->stackbase) - SIZE(pt_regs)) / sizeof(ulong)); ++ ++ for (cnt = 0; first <= last; first++) { ++ pt = (struct sw_64_pt_regs *)first; ++ ++ /* check for kernel exception frame */ ++ ++ if (!(pt->reg_value[_ps_] & 0xfffffffffffffff8) && ++ (is_kernel_text(pt->reg_value[_pc_]) || ++ IS_MODULE_VADDR(pt->reg_value[_pc_])) && ++ (is_kernel_text(pt->reg_value[_r26_]) || ++ IS_MODULE_VADDR(pt->reg_value[_r26_])) && ++ IS_KVADDR(pt->reg_value[_gp_])) { ++ cnt++; ++ if (bt->flags & BT_EFRAME_COUNT) ++ continue; ++ fprintf(fp, "\nKERNEL-MODE EXCEPTION FRAME:\n"); ++ eframe = bt->task + ((ulong)first - (ulong)stack); ++ sw64_exception_frame(eframe, BT_EXCEPTION_FRAME, ++ req, bt); ++ continue; ++ } ++ ++ /* check for user exception frame */ ++ ++ if ((pt->reg_value[_ps_] == 0x8) && ++ ((IN_TASK_VMA(bt->task, pt->reg_value[_pc_]) && ++ IN_TASK_VMA(bt->task, pt->reg_value[_r26_]) && ++ IS_UVADDR(pt->reg_value[_gp_], bt->tc)) || ++ ((first == last) && ++ (IS_ZOMBIE(bt->task) || IS_EXITING(bt->task))))) { ++ cnt++; ++ if (bt->flags & BT_EFRAME_COUNT) ++ continue; ++ fprintf(fp, "\nUSER-MODE EXCEPTION FRAME:\n"); ++ eframe = bt->task + ((ulong)first - (ulong)stack); ++ sw64_exception_frame(eframe, BT_EXCEPTION_FRAME, ++ req, bt); ++ } ++ } ++ ++ FREEBUF(req); ++ ++ return cnt; ++} ++ ++/* ++ * Before dumping a nonsensical exception frame, give it a quick test. ++ */ ++static int ++verify_user_eframe(struct bt_info *bt, ulong task, ulong sp) ++{ ++ struct sw_64_pt_regs ptbuf, *pt; ++ ++ readmem(sp, KVADDR, &ptbuf, sizeof(struct sw_64_pt_regs), ++ "pt_regs", FAULT_ON_ERROR); ++ ++ pt = &ptbuf; ++ ++ if ((pt->reg_value[_ps_] == 0x8) && ++ ((IN_TASK_VMA(task, pt->reg_value[_pc_]) && ++ IN_TASK_VMA(task, pt->reg_value[_r26_]) && ++ IS_UVADDR(pt->reg_value[_gp_], bt->tc)) || ++ ((pt == (struct sw_64_pt_regs *)USER_EFRAME_ADDR(task)) && ++ (IS_ZOMBIE(task) || IS_EXITING(task))))) { ++ return TRUE; ++ } ++ ++ return FALSE; ++} ++ ++/* ++ * Try to resync the stack location when there is no valid stack frame, ++ * typically just above an exception frame. Use the req->ra value from the ++ * exception frame as the new starting req->pc. Then walk up the stack until ++ * a text routine that calls the newly-assigned pc is found -- that stack ++ * location then becomes the new req->sp. ++ * ++ * If we're not coming from an exception frame, req-ra and req->pc will be ++ * purposely zeroed out. In that case, use the prevsp value to find the ++ * first pc that called the last frame's pc. ++ * ++ * Add any other repeatable "special-case" frames to the beginning of this ++ * routine (ex. debug_spin_lock). Last ditch -- at the end of this routine, ++ * speculate what might have happened (possibly in the background) -- and ++ * if it looks good, run with it. ++ */ ++static int ++sw64_backtrace_resync(struct gnu_request *req, ulong flags, struct bt_info *bt) ++{ ++ char addr[BUFSIZE]; ++ char buf[BUFSIZE]; ++ char lookfor1[BUFSIZE]; ++ char lookfor2[BUFSIZE]; ++ ulong newpc; ++ ulong *stkp; ++ ulong *stkp_newpc, *stkp_next; ++ ulong value; ++ int found; ++ char *name; ++ int exception; ++ ++ if (CRASHDEBUG(1)) ++ fprintf(fp, ++ "RESYNC1: [%lx-%d] ra: %lx pc: %lx sp: %lx\n", ++ flags, req->curframe, req->ra, req->pc, req->sp); ++ ++ if (!req->ra && !req->pc) { ++ req->ra = req->prevpc; ++ exception = FALSE; ++ } else ++ exception = TRUE; ++ ++ if (!IS_KVADDR(req->ra)) ++ return FALSE; ++ ++ name = closest_symbol(req->ra); ++ sprintf(lookfor1, "<%s>", name); ++ sprintf(lookfor2, "<%s+", name); ++ ++ if (CRASHDEBUG(1)) ++ fprintf(fp, "RESYNC2: exception: %s lookfor: %s or %s\n", ++ exception ? "TRUE" : "FALSE", ++ lookfor1, lookfor2); ++ ++ /* ++ * This is common when a non-panicking active CPU is spinning ++ * in debug_spin_lock(). The next pc is offset by 0x30 from ++ * the top of the exception frame, and the next sp is equal ++ * to the frame offset of debug_spin_lock(). I can't explain it... ++ */ ++ if ((flags & BT_FROM_EXCEPTION) && STREQ(name, "debug_spin_lock")) { ++ sw64_print_stack_entry(req, req->ra, ++ closest_symbol(req->ra), flags, bt); ++ ++ if (BT_REFERENCE_FOUND(bt)) ++ return FALSE; ++ ++ sw64_frame_offset(req, req->ra); ++ stkp = (ulong *)(req->sp + 0x30); ++ value = GET_STACK_ULONG(stkp); ++ if (!is_kernel_text(value)) { ++ req->sp = req->prevsp; ++ return FALSE; ++ } ++ req->pc = value; ++ req->sp += req->value; ++ return TRUE; ++ } ++ ++ /* ++ * If the ra is a system call, then all we should have to do is ++ * find the next reference to entSys on the stack, and set the ++ * sp to that value. ++ */ ++ if (is_system_call(name, 0)) { ++ /* stkp = (ulong *)req->sp; */ ++ stkp = (ulong *)req->prevsp; ++ ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ ++ if (IS_KVADDR(value) && is_kernel_text(value)) { ++ if (STREQ(closest_symbol(value), "entSys")) { ++ req->pc = value; ++ req->sp = USER_EFRAME_ADDR(req->task); ++ return TRUE; ++ } ++ } ++ } ++ } ++ ++ /* ++ * Just find the next location containing text. (?) ++ */ ++ if (STREQ(name, "do_coredump")) { ++ stkp = (ulong *)(req->sp + sizeof(long)); ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ ++ if (IS_KVADDR(value) && is_kernel_text(value)) { ++ req->pc = req->ra; ++ req->sp = (ulong)stkp; ++ return TRUE; ++ } ++ } ++ } ++ ++ if (flags & BT_SPECULATE) ++ return FALSE; ++ ++ if (CRASHDEBUG(1)) { ++ fprintf(fp, "RESYNC3: prevsp: %lx ra: %lx name: %s\n", ++ req->prevsp, req->ra, name); ++ fprintf(fp, "RESYNC3: prevpc: %lx\n", req->prevpc); ++ } ++ ++ stkp_newpc = stkp_next = 0; ++ newpc = 0; ++ found = FALSE; ++ if (exception) { ++ newpc = req->ra; ++ stkp = (ulong *)req->sp; ++ } else ++ stkp = (ulong *)req->prevsp; ++ ++ if (CRASHDEBUG(1)) ++ fprintf(fp, "RESYNC4: stkp: %lx newpc: %lx\n", ++ (ulong)stkp, newpc); ++ ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ /* ++ * First find the new pc on the stack. ++ */ ++ if (!found) { ++ if (!exception && is_kernel_text(value)) { ++ found = TRUE; ++ } else if (value == newpc) { ++ found = TRUE; ++ stkp_newpc = stkp; ++ continue; ++ } ++ } ++ ++ if (!IS_KVADDR(value)) ++ continue; ++ ++ if (is_kernel_text(value)) { ++ if (!stkp_next) ++ stkp_next = stkp; ++ if (CRASHDEBUG(2)) { ++ fprintf(fp, ++ "RESYNC6: disassemble %lx (%s)\n", ++ value - sizeof(uint), ++ value_to_symstr(value - sizeof(uint), ++ buf, 0)); ++ } ++ req->command = GNU_DISASSEMBLE; ++ req->addr = value - sizeof(uint); ++ sprintf(addr, "0x%lx", req->addr); ++ open_tmpfile(); ++ req->fp = pc->tmpfile; ++ gdb_interface(req); ++ rewind(pc->tmpfile); ++ while (fgets(buf, BUFSIZE, pc->tmpfile)) { ++ clean_line(buf); ++ if (STRNEQ(buf, "Dump of") || ++ STRNEQ(buf, "End of")) ++ continue; ++ ++ if (STRNEQ(buf, addr)) { ++ if (LASTCHAR(buf) == ':') { ++ fgets(buf, BUFSIZE, ++ pc->tmpfile); ++ clean_line(buf); ++ } ++ if (CRASHDEBUG(2) && ++ (strstr(buf, "jsr") ++ || strstr(buf, "bsr"))) ++ fprintf(pc->saved_fp, "%s\n", ++ buf); ++ if ((strstr(buf, "jsr") || ++ strstr(buf, "bsr")) && ++ (strstr(buf, lookfor1) || ++ strstr(buf, lookfor2))) { ++ if (exception) { ++ req->pc = newpc; ++ req->sp = (ulong)stkp; ++ } else ++ req->pc = req->addr; ++ close_tmpfile(); ++ return TRUE; ++ } ++ } ++ } ++ close_tmpfile(); ++ } ++ } ++ ++ if (CRASHDEBUG(1)) { ++ fprintf(fp, "RESYNC9: [%d] name: %s pc: %lx ra: %lx\n", ++ req->curframe, name, req->pc, req->ra); ++ fprintf(fp, "RESYNC9: sp: %lx lastsp: %lx\n", ++ req->sp, req->lastsp); ++ fprintf(fp, "RESYNC9: prevpc: %lx prevsp: %lx\n", ++ req->prevpc, req->prevsp); ++ } ++ ++ /* ++ * At this point, all we can do is speculate based upon ++ * past experiences... ++ */ ++ return (sw64_resync_speculate(req, flags, bt)); ++} ++ ++/* ++ * Try one level of speculation. If it works, fine -- if not, give up. ++ */ ++static int ++sw64_resync_speculate(struct gnu_request *req, ulong flags, struct bt_info *bt) ++{ ++ ulong *stkp; ++ ulong value; ++ ulong found_sp, found_ra; ++ struct stack_hook hook; ++ struct bt_info bt_info, *btloc; ++ char buf[BUFSIZE]; ++ int kernel_thread; ++ int looks_good; ++ ++ if (flags & BT_SPECULATE) /* already been here on this trace... */ ++ return FALSE; ++ ++ if (pc->tmpfile) ++ return FALSE; ++ ++ found_ra = found_sp = 0; ++ kernel_thread = is_kernel_thread(req->task); ++ ++ /* ++ * Add "known" possibilities here. ++ */ ++ switch (flags & (BT_FROM_EXCEPTION|BT_FROM_CALLFRAME)) ++ { ++ case BT_FROM_EXCEPTION: ++ if (STREQ(closest_symbol(req->prevpc), "read_lock") || ++ STREQ(closest_symbol(req->ra), "do_select") || ++ STREQ(closest_symbol(req->ra), "schedule")) { ++ stkp = (ulong *)req->sp; ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ ++ if (found_ra) { ++ if (is_kernel_text_offset(value)) { ++ found_sp = (ulong)stkp; ++ break; ++ } ++ continue; ++ } ++ ++ if (value == req->ra) ++ found_ra = value; ++ } ++ } ++ break; ++ ++ case BT_FROM_CALLFRAME: ++ if (STREQ(closest_symbol(req->ra), "sys_read")) { ++ value = GET_STACK_ULONG(req->prevsp - 32); ++ if (STREQ(closest_symbol(value), "entSys")) { ++ found_ra = value; ++ found_sp = req->prevsp - 32; ++ } ++ } else if (STREQ(closest_symbol(req->ra), "exit_autofs4_fs")) { ++ stkp = (ulong *)req->sp; ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ ++ if (found_ra && (value != found_ra)) { ++ if (is_kernel_text_offset(value)) { ++ found_sp = (ulong)stkp; ++ break; ++ } ++ continue; ++ } ++ ++ if (is_kernel_text_offset(value)) ++ found_ra = value; ++ } ++ } ++ ++ break; ++ ++ default: ++ if (req->hookp && ++ STREQ(closest_symbol(req->prevpc), "filemap_nopage") && ++ !STREQ(closest_symbol(req->hookp->eip), "do_no_page")) { ++ found_ra = found_sp = 0; ++ stkp = (ulong *)req->prevsp; ++ for (stkp++; INSTACK(stkp, bt); stkp++) { ++ value = GET_STACK_ULONG(stkp); ++ ++ if (found_ra && (value != found_ra)) { ++ if (is_kernel_text_offset(value)) { ++ found_sp = (ulong)stkp; ++ break; ++ } ++ continue; ++ } ++ ++ if (is_kernel_text_offset(value) && ++ STREQ(closest_symbol(value), "do_no_page")) ++ found_ra = value; ++ } ++ if (found_ra && found_sp) { ++ req->hookp->eip = found_ra; ++ req->hookp->esp = found_sp; ++ return TRUE; ++ } ++ } ++ ++ if (req->hookp) { ++ found_ra = req->hookp->eip; ++ found_sp = req->hookp->esp; ++ } ++ ++ break; ++ } ++ ++ if (found_ra && found_sp) { ++ looks_good = FALSE; ++ hook.esp = found_sp; ++ hook.eip = found_ra; ++ ++ if (CRASHDEBUG(1)) ++ fprintf(pc->saved_fp, ++ "----- RESYNC SPECULATE START -----\n"); ++ ++ open_tmpfile(); ++ btloc = &bt_info; ++ BZERO(btloc, sizeof(struct bt_info)); ++ btloc->task = req->task; ++ btloc->tc = bt->tc; ++ btloc->stackbase = bt->stackbase; ++ btloc->stacktop = bt->stacktop; ++ btloc->flags = BT_SPECULATE; ++ btloc->hp = &hook; ++ back_trace(btloc); ++ rewind(pc->tmpfile); ++ while (fgets(buf, BUFSIZE, pc->tmpfile)) { ++ if (CRASHDEBUG(1)) ++ fprintf(pc->saved_fp, "%s", buf); ++ ++ if (strstr(buf, "NOTE: cannot resolve")) { ++ looks_good = FALSE; ++ break; ++ } ++ ++ if (strstr(buf, "SW64 EXCEPTION FRAME")) { ++ looks_good = TRUE; ++ break; ++ } ++ ++ if (kernel_thread) { ++ if (strstr(buf, " kernel_thread ") || ++ strstr(buf, " __kernel_thread ") || ++ strstr(buf, " start_kernel ") || ++ strstr(buf, " smp_callin ")) { ++ looks_good = TRUE; ++ break; ++ } ++ } ++ } ++ close_tmpfile(); ++ ++ if (CRASHDEBUG(1)) ++ fprintf(pc->saved_fp, ++ "----- RESYNC SPECULATE DONE ------\n"); ++ ++ if (looks_good) { ++ req->pc = found_ra; ++ req->sp = found_sp; ++ return TRUE; ++ } ++ } ++ ++ return FALSE; ++} ++ ++/* ++ * Translates a user virtual address to its physical address. cmd_vtop() ++ * sets the verbose flag so that the pte translation gets displayed; all ++ * other callers quietly accept the translation. ++ * ++ * This routine can also take mapped kernel virtual addresses if the -u flag ++ * was passed to cmd_vtop(). If so, it makes the translation using the ++ * kernel-memory PGD entry instead of swapper_pg_dir. ++ */ ++ ++static int ++sw64_uvtop(struct task_context *tc, ulong vaddr, physaddr_t *paddr, int verbose) ++{ ++ ulong mm; ++ ulong *pgd; ++ ulong *page_dir; ++ ulong *page_middle; ++ ulong *page_table; ++ ulong pgd_pte; ++ ulong pmd_pte; ++ ulong pte; ++ ++ if (!tc) ++ error(FATAL, "current context invalid\n"); ++ ++ *paddr = 0; ++ ++ if (is_kernel_thread(tc->task) && IS_KVADDR(vaddr)) { ++ pgd = (ulong *)machdep->get_task_pgd(tc->task); ++ } else { ++ if (!tc->mm_struct) ++ pgd = (ulong *)machdep->get_task_pgd(tc->task); ++ else { ++ if ((mm = task_mm(tc->task, TRUE))) ++ pgd = ULONG_PTR(tt->mm_struct + ++ OFFSET(mm_struct_pgd)); ++ else ++ readmem(tc->mm_struct + OFFSET(mm_struct_pgd), ++ KVADDR, &pgd, sizeof(long), ++ "mm_struct pgd", FAULT_ON_ERROR); ++ } ++ } ++ ++ if (verbose) ++ fprintf(fp, "PAGE DIRECTORY: %lx\n", (ulong)pgd); ++ ++ page_dir = pgd + ((vaddr >> PGDIR_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PGD(PAGEBASE(pgd), KVADDR, PAGESIZE()); ++ pgd_pte = ULONG(machdep->pgd + PAGEOFFSET(page_dir)); ++ ++ if (verbose) ++ fprintf(fp, " PGD: %lx => %lx\n", (ulong)page_dir, pgd_pte); ++ ++ if (!(pgd_pte & _PAGE_VALID)) ++ goto no_upage; ++ ++ page_middle = (ulong *) ++ (PTOV((pgd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + ++ ((vaddr >> PMD_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PMD(PAGEBASE(page_middle), KVADDR, PAGESIZE()); ++ pmd_pte = ULONG(machdep->pmd + PAGEOFFSET(page_middle)); ++ ++ if (verbose) ++ fprintf(fp, " PMD: %lx => %lx\n", (ulong)page_middle, pmd_pte); ++ ++ if (!(pmd_pte & _PAGE_VALID)) ++ goto no_upage; ++ ++ page_table = (ulong *) ++ (PTOV((pmd_pte & _PFN_MASK) >> (32-PAGESHIFT()))) + ++ (BTOP(vaddr) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PTBL(PAGEBASE(page_table), KVADDR, PAGESIZE()); ++ pte = ULONG(machdep->ptbl + PAGEOFFSET(page_table)); ++ ++ if (verbose) ++ fprintf(fp, " PTE: %lx => %lx\n", (ulong)page_table, pte); ++ ++ if (!(pte & (_PAGE_VALID))) { ++ *paddr = pte; ++ if (pte && verbose) { ++ fprintf(fp, "\n"); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ goto no_upage; ++ } ++ ++ *paddr = ((pte & _PFN_MASK) >> (32-PAGESHIFT())) + PAGEOFFSET(vaddr); ++ ++ if (verbose) { ++ fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ ++ return TRUE; ++ ++no_upage: ++ return FALSE; ++} ++ ++/* ++ * Translates a kernel virtual address to its physical address. cmd_vtop() ++ * sets the verbose flag so that the pte translation gets displayed; all ++ * other callers quietly accept the translation. ++ */ ++static int sw64_is_kvddr(ulong addr) ++{ ++ if (addr > 0xffffffff80000000){ ++ return 1; ++ } ++ if (addr > 0xfff0000000000000 && addr < 0xfffff7ffffffffff){ ++ return 1; ++ } ++ return 0; ++} ++ ++static int ++sw3231_kvtop(struct task_context *tc, ulong kvaddr, physaddr_t *paddr, int verbose) ++{ ++ ulong *pgd; ++ ulong *page_dir; ++ ulong *page_upper; ++ ulong *page_middle; ++ ulong *page_table; ++ ulong pgd_pte; ++ ulong pud_pte; ++ ulong pmd_pte; ++ ulong pte; ++ ++ // if (!IS_KVADDR(kvaddr)) ++ // return FALSE; ++ ++ // if (!vt->vmalloc_start) { /* presume KSEG this early */ ++ // *paddr = VTOP(kvaddr); ++ // return TRUE; ++ // } ++ ++ // if (!IS_VMALLOC_ADDR(kvaddr)) { ++ // *paddr = VTOP(kvaddr); ++ // return TRUE; ++ // } ++ ++ if (kvaddr > 0xffffffff80000000){ ++ *paddr = kvaddr - 0xffffffff80000000; ++ // printf("direct map:%-16lx ----> %-16lx\n", kvaddr, *paddr); ++ return TRUE; ++ } ++ if (kvaddr > 0xfff0000000000000 && kvaddr < 0xfff0ffffffffffff){ ++ *paddr = kvaddr - 0xfff0000000000000; ++// printf("direct map:%-16lx ----> %-16lx\n", kvaddr, *paddr); ++ return TRUE; ++ } ++ ++ pgd = (ulong *)vt->kernel_pgd[0]; ++ ++ if (verbose) ++ fprintf(fp, "PAGE DIRECTORY: %lx, kvaddr: %#lx\n", (ulong)pgd, kvaddr); ++ ++ page_dir = pgd + ((kvaddr >> PGDIR_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PGD(PAGEBASE(pgd), KVADDR, PAGESIZE()); ++ pgd_pte = ULONG(machdep->pgd + PAGEOFFSET(page_dir)); ++ ++ if (verbose) ++ fprintf(fp, " PGD: %lx => %lx\n", (ulong)page_dir, pgd_pte); ++ ++ if (!(pgd_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_upper = (ulong *) ++ (PTOV((pgd_pte & _PFN_MASK) >> (PFN_SHIFT - PAGESHIFT()))) + ++ ((kvaddr >> PUD_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PUD(PAGEBASE(page_upper), KVADDR, PAGESIZE()); ++ pud_pte = ULONG(machdep->pud + PAGEOFFSET(page_upper)); ++ ++ if (verbose) ++ fprintf(fp, " PUD: %lx => %lx\n", (ulong)page_upper, pud_pte); ++ ++ if (!(pud_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_middle = (ulong *) ++ (PTOV((pud_pte & _PFN_MASK) >> (PFN_SHIFT - PAGESHIFT()))) + ++ ((kvaddr >> PMD_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PMD(PAGEBASE(page_middle), KVADDR, PAGESIZE()); ++ pmd_pte = ULONG(machdep->pmd + PAGEOFFSET(page_middle)); ++ ++ if (verbose) ++ fprintf(fp, " PMD: %lx => %lx\n", (ulong)page_middle, pmd_pte); ++ ++ if (!(pmd_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_table = (ulong *) ++ (PTOV((pmd_pte & _PFN_MASK) >> (PFN_SHIFT - PAGESHIFT()))) + ++ (BTOP(kvaddr) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PTBL(PAGEBASE(page_table), KVADDR, PAGESIZE()); ++ pte = ULONG(machdep->ptbl + PAGEOFFSET(page_table)); ++ ++ if (verbose) ++ fprintf(fp, " PTE: %lx => %lx\n", (ulong)page_table, pte); ++ ++ if (!(pte & (_PAGE_VALID))) { ++ if (pte && verbose) { ++ fprintf(fp, "\n"); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ goto no_kpage; ++ } ++ ++ *paddr = ((pte & _PFN_MASK) >> (PFN_SHIFT - PAGESHIFT())) + PAGEOFFSET(kvaddr); ++ ++ if (verbose) { ++ fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ ++ return TRUE; ++ ++no_kpage: ++ return FALSE; ++} ++ ++static int ++sw6432_kvtop(struct task_context *tc, ulong kvaddr, physaddr_t *paddr, int verbose) ++{ ++ ulong *pgd; ++ ulong *page_dir; ++ ulong *page_upper; ++ ulong *page_middle; ++ ulong *page_table; ++ ulong pgd_pte; ++ ulong pud_pte; ++ ulong pmd_pte; ++ ulong pte; ++ ++ // if (!IS_KVADDR(kvaddr)) ++ // return FALSE; ++ ++ // if (!vt->vmalloc_start) { /* presume KSEG this early */ ++ // *paddr = VTOP(kvaddr); ++ // return TRUE; ++ // } ++ ++ // if (!IS_VMALLOC_ADDR(kvaddr)) { ++ // *paddr = VTOP(kvaddr); ++ // return TRUE; ++ // } ++ ++ if (kvaddr > 0xffffffff80000000){ ++ *paddr = kvaddr - 0xffffffff80000000; ++ // printf("direct map:%-16lx ----> %-16lx\n", kvaddr, *paddr); ++ return TRUE; ++ } ++ if (kvaddr > 0xfff0000000000000 && kvaddr < 0xfff0ffffffffffff){ ++ *paddr = kvaddr - 0xfff0000000000000; ++// printf("direct map:%-16lx ----> %-16lx\n", kvaddr, *paddr); ++ return TRUE; ++ } ++ ++ pgd = (ulong *)vt->kernel_pgd[0]; ++ ++ if (verbose) ++ fprintf(fp, "PAGE DIRECTORY: %lx, kvaddr: %#lx\n", (ulong)pgd, kvaddr); ++ ++ page_dir = pgd + ((kvaddr >> PGDIR_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PGD(PAGEBASE(pgd), KVADDR, PAGESIZE()); ++ pgd_pte = ULONG(machdep->pgd + PAGEOFFSET(page_dir)); ++ ++ if (verbose) ++ fprintf(fp, " PGD: %lx => %lx\n", (ulong)page_dir, pgd_pte); ++ ++ if (!(pgd_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_upper = (ulong *) ++ (PTOV((pgd_pte & (_PFN_MASK / 32)) >> (PFN_SHIFT - 4 - PAGESHIFT()))) + ++ ((kvaddr >> PUD_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PUD(PAGEBASE(page_upper), KVADDR, PAGESIZE()); ++ pud_pte = ULONG(machdep->pud + PAGEOFFSET(page_upper)); ++ ++ if (verbose) ++ fprintf(fp, " PUD: %lx => %lx\n", (ulong)page_upper, pud_pte); ++ ++ if (!(pud_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_middle = (ulong *) ++ (PTOV((pud_pte & (_PFN_MASK / 32)) >> (PFN_SHIFT - 4 - PAGESHIFT()))) + ++ ((kvaddr >> PMD_SHIFT) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PMD(PAGEBASE(page_middle), KVADDR, PAGESIZE()); ++ pmd_pte = ULONG(machdep->pmd + PAGEOFFSET(page_middle)); ++ ++ if (verbose) ++ fprintf(fp, " PMD: %lx => %lx\n", (ulong)page_middle, pmd_pte); ++ ++ if (!(pmd_pte & _PAGE_VALID)) ++ goto no_kpage; ++ ++ page_table = (ulong *) ++ (PTOV((pmd_pte & (_PFN_MASK / 32)) >> (PFN_SHIFT - 4 - PAGESHIFT()))) + ++ (BTOP(kvaddr) & (PTRS_PER_PAGE - 1)); ++ ++ FILL_PTBL(PAGEBASE(page_table), KVADDR, PAGESIZE()); ++ pte = ULONG(machdep->ptbl + PAGEOFFSET(page_table)); ++ ++ if (verbose) ++ fprintf(fp, " PTE: %lx => %lx\n", (ulong)page_table, pte); ++ ++ if (!(pte & (_PAGE_VALID))) { ++ if (pte && verbose) { ++ fprintf(fp, "\n"); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ goto no_kpage; ++ } ++ ++ *paddr = ((pte & (_PFN_MASK / 32)) >> (PFN_SHIFT - 4 - PAGESHIFT())) + PAGEOFFSET(kvaddr); ++ ++ if (verbose) { ++ fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); ++ sw64_translate_pte(pte, 0, 0); ++ } ++ ++ return TRUE; ++ ++no_kpage: ++ return FALSE; ++} ++ ++ ++/* ++ * Get the relevant page directory pointer from a task structure. ++ */ ++static ulong ++sw64_get_task_pgd(ulong task) ++{ ++ long offset; ++ ulong ptbr; ++ ++ offset = OFFSET_OPTION(task_struct_thread, task_struct_tss); ++ ++ offset += OFFSET(thread_struct_ptbr); ++ ++ readmem(task + offset, KVADDR, &ptbr, ++ sizeof(ulong), "task thread ptbr", FAULT_ON_ERROR); ++ ++ return(PTOV(PTOB(ptbr))); ++} ++ ++/* ++ * Calculate and return the speed of the processor. ++ */ ++static ulong ++sw64_processor_speed(void) ++{ ++ ulong mhz; ++ long cycle_freq = 2400000000; ++ ++ mhz = cycle_freq/1000000; ++ ++ return (machdep->mhz = mhz); ++} ++ ++void ++sw64_dump_machdep_table(ulong arg) ++{ ++ int others; ++ ++ others = 0; ++ fprintf(fp, " flags: %lx (", machdep->flags); ++ if (machdep->flags & HWRESET) ++ fprintf(fp, "%sHWRESET", others++ ? "|" : ""); ++ fprintf(fp, ")\n"); ++ fprintf(fp, " kvbase: %lx\n", machdep->kvbase); ++ fprintf(fp, " identity_map_base: %lx\n", machdep->identity_map_base); ++ fprintf(fp, " pagesize: %d\n", machdep->pagesize); ++ fprintf(fp, " pageshift: %d\n", machdep->pageshift); ++ fprintf(fp, " pagemask: %llx\n", machdep->pagemask); ++ fprintf(fp, " pageoffset: %lx\n", machdep->pageoffset); ++ fprintf(fp, " stacksize: %ld\n", machdep->stacksize); ++ fprintf(fp, " hz: %d\n", machdep->hz); ++ fprintf(fp, " mhz: %ld\n", machdep->mhz); ++ fprintf(fp, " memsize: %ld (0x%lx)\n", ++ machdep->memsize, machdep->memsize); ++ fprintf(fp, " bits: %d\n", machdep->bits); ++ fprintf(fp, " nr_irqs: %d\n", machdep->nr_irqs); ++ fprintf(fp, " eframe_search: sw64_eframe_search()\n"); ++ fprintf(fp, " back_trace: sw64_back_trace_cmd()\n"); ++ fprintf(fp, " processor_speed: sw64_processor_speed()\n"); ++ fprintf(fp, " uvtop: sw64_uvtop()\n"); ++ fprintf(fp, " kvtop: sw64_uvtop()\n"); ++ fprintf(fp, " get_task_pgd: sw64_get_task_pgd()\n"); ++ fprintf(fp, " dump_irq: generic_dump_irq()\n"); ++ fprintf(fp, " get_stack_frame: sw64_get_stack_frame()\n"); ++ fprintf(fp, " get_stackbase: generic_get_stackbase()\n"); ++ fprintf(fp, " get_stacktop: generic_get_stacktop()\n"); ++ fprintf(fp, " translate_pte: sw64_translate_pte()\n"); ++ fprintf(fp, " memory_size: sw64_get_memory_size()\n"); ++ fprintf(fp, " vmalloc_start: sw64_get_vmalloc_start()\n"); ++ fprintf(fp, " is_task_addr: sw64_is_task_addr()\n"); ++ fprintf(fp, " verify_symbol: sw64_verify_symbol()\n"); ++ fprintf(fp, " dis_filter: sw64_dis_filter()\n"); ++ fprintf(fp, " cmd_mach: sw64_cmd_mach()\n"); ++ fprintf(fp, " get_smp_cpus: sw64_get_smp_cpus()\n"); ++ fprintf(fp, " is_kvaddr: generic_is_kvaddr()\n"); ++ fprintf(fp, " is_uvaddr: generic_is_uvaddr()\n"); ++ fprintf(fp, " verify_paddr: generic_verify_paddr()\n"); ++ fprintf(fp, " init_kernel_pgd: NULL\n"); ++ fprintf(fp, " value_to_symbol: generic_machdep_value_to_symbol()\n"); ++ fprintf(fp, " line_number_hooks: sw64_line_number_hooks\n"); ++ fprintf(fp, " last_pgd_read: %lx\n", machdep->last_pgd_read); ++ fprintf(fp, " last_pmd_read: %lx\n", machdep->last_pmd_read); ++ fprintf(fp, " last_ptbl_read: %lx\n", machdep->last_ptbl_read); ++ fprintf(fp, " pgd: %lx\n", (ulong)machdep->pgd); ++ fprintf(fp, " pud: %lx\n", (ulong)machdep->pud); ++ fprintf(fp, " pmd: %lx\n", (ulong)machdep->pmd); ++ fprintf(fp, " ptbl: %lx\n", (ulong)machdep->ptbl); ++ fprintf(fp, " ptrs_per_pgd: %d\n", machdep->ptrs_per_pgd); ++ fprintf(fp, " machspec: %lx\n", (ulong)machdep->machspec); ++} ++ ++/* ++ * Fix up jsr's to show the right target. ++ * ++ * If a value is passed with no buf, then cmd_dis is fishing for whether ++ * the GP can be calculated from the first couple of instructions of the ++ * target routine: ++ * ++ * 0xfffffc0000349fa0 : ldah gp,35(t12) ++ * 0xfffffc0000349fa4 : lda gp,6216(gp) ++ * ++ * If a buf pointer is passed, then check whether the t12 register ++ * is being set up as an offset from gp, then calculate the target address: ++ * ++ * 0xfffffc000042c364 : ldq t12,-29336(gp) ++ * 0xfffffc000042c368 : ++ * jsr ra,(t12),0xfffffc0000429dc0 ++ * ++ * If the next instruction is a jsr ra,(t12), then correct the bracketed ++ * target address translation. ++ * ++ */ ++ ++#define LDAH_GP_T12 (0x27bb0000) ++#define LDA_GP_GP (0x23bd0000) ++#define LDQ_T12_GP (0xa77d0000) ++#define JSR_RA_T12 (0x6b5b0000) ++ ++#define OPCODE_OPERAND_MASK (0xffff0000) ++#define OPCODE_MEM_DISP_MASK (0x0000ffff) ++ ++static struct instruction_data { ++ uint inst[2]; ++ short mem_disp[2]; ++ ulong gp; ++ ulong target; ++ char *curfunc; ++} instruction_data = { {0} }; ++ ++static int ++sw64_dis_filter(ulong vaddr, char *buf, unsigned int output_radix) ++{ ++ struct syment *sp; ++ struct instruction_data *id; ++ char buf2[BUFSIZE], *p1; ++ ++ id = &instruction_data; ++ ++ if (!buf) { ++ BZERO(id, sizeof(struct instruction_data)); ++ ++ if (!(sp = value_search(vaddr, NULL))) ++ return FALSE; ++ ++ readmem(sp->value, KVADDR, &id->inst[0], ++ sizeof(uint) * 2, "two instructions", FAULT_ON_ERROR); ++ ++ if (((id->inst[0] & OPCODE_OPERAND_MASK) == LDAH_GP_T12) && ++ ((id->inst[1] & OPCODE_OPERAND_MASK) == LDA_GP_GP)) { ++ id->mem_disp[0] = (short)(id->inst[0] & ++ OPCODE_MEM_DISP_MASK); ++ id->mem_disp[1] = (short)(id->inst[1] & ++ OPCODE_MEM_DISP_MASK); ++ id->gp = sp->value + (65536*id->mem_disp[0]) + ++ id->mem_disp[1]; ++ id->curfunc = sp->name; ++ ++ if (CRASHDEBUG(1)) ++ console("%s: ldah(%d) and lda(%d) gp: %lx\n", ++ id->curfunc, ++ id->mem_disp[0], id->mem_disp[1], ++ id->gp); ++ ++ return TRUE; ++ } ++ /* send all lines through the generic */ ++ return TRUE; /* dis_address_translation() filter */ ++ } ++ ++ dis_address_translation(vaddr, buf, output_radix); ++ ++ if (!id->gp || !(sp = value_search(vaddr, NULL)) || ++ !STREQ(id->curfunc, sp->name)) { ++ BZERO(id, sizeof(struct instruction_data)); ++ return FALSE; ++ } ++ ++ readmem(vaddr, KVADDR, &id->inst[0], ++ sizeof(uint), "one instruction", FAULT_ON_ERROR); ++ ++ if ((id->inst[0] & OPCODE_OPERAND_MASK) == JSR_RA_T12) { ++ ++ if (!id->target || !strstr(buf, "jsr\tra,(t12)") || ++ !strstr(buf, "<")) ++ return FALSE; ++ ++ p1 = strstr(strstr(buf, "jsr"), "0x"); ++ sprintf(p1, "0x%lx <%s>%s", ++ id->target, ++ value_to_symstr(id->target, buf2, output_radix), ++ CRASHDEBUG(1) ? " [PATCHED]\n" : "\n"); ++ return TRUE; ++ } ++ ++ if ((id->inst[0] & OPCODE_OPERAND_MASK) == LDQ_T12_GP) { ++ id->mem_disp[0] = (short)(id->inst[0] & OPCODE_MEM_DISP_MASK); ++ readmem(id->gp + id->mem_disp[0], KVADDR, &id->target, ++ sizeof(ulong), "jsr target", FAULT_ON_ERROR); ++ } else ++ id->target = 0; ++ ++ return TRUE; ++} ++ ++/* ++ * For some reason gdb can go off into the weeds translating text addresses, ++ * so this routine both fixes the references as well as imposing the current ++ * output radix on the translations. ++ */ ++static void ++dis_address_translation(ulong vaddr, char *inbuf, unsigned int output_radix) ++{ ++ char buf1[BUFSIZE]; ++ char buf2[BUFSIZE]; ++ char *colon, *p1; ++ int argc; ++ char *argv[MAXARGS]; ++ ulong value; ++ ++ console("IN: %s", inbuf); ++ ++ colon = strstr(inbuf, ":"); ++ ++ if (colon) { ++ sprintf(buf1, "0x%lx <%s>", vaddr, ++ value_to_symstr(vaddr, buf2, output_radix)); ++ sprintf(buf2, "%s%s", buf1, colon); ++ strcpy(inbuf, buf2); ++ } ++ ++ strcpy(buf1, inbuf); ++ argc = parse_line(buf1, argv); ++ ++ if ((FIRSTCHAR(argv[argc-1]) == '<') && ++ (LASTCHAR(argv[argc-1]) == '>')) { ++ p1 = rindex(inbuf, '<'); ++ while ((p1 > inbuf) && (*p1 != ',')) ++ p1--; ++ ++ if (!STRNEQ(p1, ",0x")) ++ return; ++ p1++; ++ ++ if (!extract_hex(p1, &value, NULLCHAR, TRUE)) ++ return; ++ ++ sprintf(buf1, "0x%lx <%s>\n", value, ++ value_to_symstr(value, buf2, output_radix)); ++ ++ sprintf(p1, "%s", buf1); ++ } ++ ++ console(" %s", inbuf); ++} ++ ++static int ++sw64_get_dumpfile_stackframe(struct bt_info *bt, ulong *fp, ulong *sp) ++{ ++ struct machine_specific *ms = machdep->machspec; ++ struct sw64_pt_regs *ptregs; ++ ulong pc; ++ ++ if (!ms->panic_task_regs || ++ (!ms->panic_task_regs[bt->tc->processor].usp && ++ !ms->panic_task_regs[bt->tc->processor].pc)) { ++ bt->flags |= BT_REGS_NOT_FOUND; ++ return FALSE; ++ } ++ ++ ptregs = &ms->panic_task_regs[bt->tc->processor]; ++ pc = ptregs->pc; ++// if (user_mode(ptregs)) { ++// sp = ptregs->usp; ++// fp = ptregs->r15; ++// if (is_kernel_text(pc) || ++// !in_user_stack(bt->tc->task, sp)) { ++// error(WARNING, ++// "corrupt NT_PRSTATUS? pstate: 0x%lx, but no user frame found\n", ++// ptregs->pstate); ++// if (is_kernel_text(pc) && ++// INSTACK(sp, bt) && INSTACK(fp, bt)) ++// goto try_kernel; ++// bt->flags |= BT_REGS_NOT_FOUND; ++// return FALSE; ++// } ++// bt->flags |= BT_USER_SPACE; ++// } else { ++// try_kernel: ++ *fp = ptregs->r15; ++ *sp = ptregs->usp; ++ // } ++ ++ return TRUE; ++} ++ ++static int ++sw64_get_stackframe(struct bt_info *bt, ulong *fp, ulong *sp) ++{ ++ if (!fill_task_struct(bt->task)) ++ return FALSE; ++ ++ *sp = ULONG(tt->task_struct + OFFSET(task_struct_thread_context_sp)); ++ *fp = ULONG(tt->task_struct + OFFSET(task_struct_thread_context_fp)); ++ ++ return TRUE; ++} ++ ++static void ++sw64_get_stack_frame(struct bt_info *bt, ulong *fp, ulong *sp) ++{ ++ int ret; ++ if (DUMPFILE()) ++ ret = sw64_get_dumpfile_stackframe(bt, fp, sp); ++ else ++ ret = sw64_get_stackframe(bt, fp, sp); ++ ++ if (!ret) ++ error(WARNING, ++ "cannot determine starting stack frame for task %lx\n", ++ bt->task); ++} ++ ++/* ++ * Do the work formerly done by sw64_get_sp() and sw64_get_pc(). ++ */ ++static void ++get_sw64_frame(struct bt_info *bt, ulong *getpc, ulong *getsp) ++{ ++ int i; ++ ulong ip; ++ ulong r26; ++ ulong ksp, sp; ++ ulong *spp; ++ ulong percpu_ra; ++ ulong percpu_pv; ++ struct percpu_data percpu_data; ++ char buf[BUFSIZE]; ++ ulong task; ++ ulong *stack; ++ ++ task = bt->task; ++ stack = (ulong *)bt->stackbuf; ++ ++ if (tt->flags & THREAD_INFO) { /* pcb.ksp is 1st word in thread_info */ ++ readmem(bt->tc->thread_info, KVADDR, &ksp, sizeof(ulong), ++ "thread_info pcb ksp", FAULT_ON_ERROR); ++ sp = ksp; ++ printf("THREAD_INFO ksp:%lx\n", sp); ++ } else if (VALID_MEMBER(task_struct_tss_ksp)){ ++ ksp = sp = stack[OFFSET(task_struct_tss_ksp)/sizeof(long)]; ++ printf("task_struct_tss_ksp ksp:%lx\n", sp); ++ } ++ else { ++ ksp = sp = stack[OFFSET(task_struct_thread_ksp)/sizeof(long)]; ++ printf("else ksp:%lx\n", sp); ++ } ++ ++ ip = 0; ++ percpu_ra = percpu_pv = 0; ++ spp = &stack[(sp - task)/sizeof(long)]; ++ printf("spp size:%lx\n", (sp - task)/sizeof(long)); ++ if (DUMPFILE() && getsp) { ++ if (HWRESET_TASK(task)) { ++ if (INSTACK(sp, bt)) { ++ *getsp = sp; ++ printf("HWRESET_TASK ksp:%lx\n", sp); ++ return; ++ } ++ else { ++ printf("else\n"); ++ get_percpu_data(0, 0, &percpu_data); ++ percpu_ra = percpu_data.halt_ra; ++ percpu_pv = percpu_data.halt_pv; ++ spp = &stack[roundup(SIZE(task_struct), ++ sizeof(ulong)) / sizeof(ulong)]; ++ } ++ } ++ ++ printf("not HWRESET_TASK\n"); ++ if (!percpu_ra && (STREQ(closest_symbol(*spp), "panic") || ++ STREQ(closest_symbol(*spp), "handle_ipi"))) { ++ *getsp = sp; ++ return; ++ } ++ } ++ ++percpu_retry: ++ ++ printf("percpu_retry\n"); ++ if (CRASHDEBUG(1) && percpu_ra) { ++ fprintf(fp, "get_sw64_frame: look for %lx (%s)\n", ++ percpu_ra, value_to_symstr(percpu_ra, buf, 0)); ++ } ++ printf("get_sw64_frame: look for %lx (%s)\n", ++ percpu_ra, value_to_symstr(percpu_ra, buf, 0)); ++ for (i = 0, spp++; spp < &stack[LONGS_PER_STACK]; spp++,i++) { ++ ++ if (CRASHDEBUG(1) && (percpu_ra || percpu_pv) && ++ is_kernel_text(*spp)) { ++ fprintf(fp, "%lx: %lx (%s)\n", ++ ((ulong)spp - (ulong)stack) + task, ++ *spp, value_to_symstr(*spp, buf, 0)); ++ } ++ ++ if (percpu_ra) { ++ if (*spp == percpu_ra) { ++ *getsp = ((ulong)spp - (ulong)stack) + task; ++ return; ++ } ++ continue; ++ } else if (percpu_pv) { ++ if (*spp == percpu_pv) { ++ *getsp = ((ulong)spp - (ulong)stack) + task; ++ if (getpc) ++ *getpc = percpu_pv; ++ return; ++ } ++ continue; ++ } ++ ++ if (!INSTACK(*spp, bt)) ++ continue; ++ ++ if (is_kernel_text(*(spp+1))) { ++ sp = *spp; ++ ip = *(spp+1); ++ break; ++ } ++ } ++ ++ if (percpu_ra) { ++ percpu_ra = 0; ++ ++ error(INFO, ++ "cannot find return address (percpu_ra) in HARDWARE RESET stack\n"); ++ error(INFO, ++ "looking for procedure address (percpu_pv) in HARDWARE RESET stack\n"); ++ ++ if (CRASHDEBUG(1)) { ++ fprintf(fp, "get_sw64_frame: look for %lx (%s)\n", ++ percpu_pv, value_to_symstr(percpu_pv, buf, 0)); ++ } ++ spp = &stack[roundup(SIZE(task_struct), ++ sizeof(ulong)) / sizeof(ulong)]; ++ ++ goto percpu_retry; ++ } ++ ++ if (percpu_pv) { ++ error(INFO, ++ "cannot find procedure address (percpu_pv) in HARDWARE RESET stack\n"); ++ } ++ ++ /* ++ * Check for a forked task that has not yet run in user space. ++ */ ++ if (!ip) { ++ printf("Check for a forked task that has not yet run in user space.\n"); ++ if (INSTACK(ksp + OFFSET(switch_stack_r26), bt)) { ++ readmem(ksp + OFFSET(switch_stack_r26), KVADDR, ++ &r26, sizeof(ulong), ++ "ret_from_smp_fork check", FAULT_ON_ERROR); ++ if (STREQ(closest_symbol(r26), "ret_from_smp_fork") || ++ STREQ(closest_symbol(r26), "ret_from_smpfork")) { ++ ip = r26; ++ sp = ksp; ++ } ++ } ++ ++ } ++ ++ if (getsp) ++ *getsp = sp; ++ if (getpc) ++ *getpc = ip; ++ ++} ++ ++/* ++ * Fill the percpu_data structure with information from the ++ * hwrpb/percpu_data structures for a given CPU. If requested, ++ * return one of the specified entries. ++ */ ++static ulong ++get_percpu_data(int cpu, ulong flag, struct percpu_data *pd) ++{ ++ ulong hwrpb, halt_ra, halt_PC, halt_pv; ++ unsigned long processor_offset, processor_size; ++ ++ get_symbol_data("hwrpb", sizeof(void *), &hwrpb); ++ ++ readmem(hwrpb+OFFSET(hwrpb_struct_processor_offset), KVADDR, ++ &processor_offset, sizeof(ulong), ++ "hwrpb processor_offset", FAULT_ON_ERROR); ++ ++ readmem(hwrpb+OFFSET(hwrpb_struct_processor_size), KVADDR, ++ &processor_size, sizeof(ulong), ++ "hwrpb processor_size", FAULT_ON_ERROR); ++ ++ readmem(hwrpb + processor_offset + (cpu * processor_size) + ++ OFFSET(percpu_struct_halt_PC), ++ KVADDR, &halt_PC, sizeof(ulong), ++ "percpu halt_PC", FAULT_ON_ERROR); ++ ++ readmem(hwrpb + processor_offset + (cpu * processor_size) + ++ OFFSET(percpu_struct_halt_ra), ++ KVADDR, &halt_ra, sizeof(ulong), ++ "percpu halt_ra", FAULT_ON_ERROR); ++ ++ readmem(hwrpb + processor_offset + (cpu * processor_size) + ++ OFFSET(percpu_struct_halt_pv), ++ KVADDR, &halt_pv, sizeof(ulong), ++ "percpu halt_pv", FAULT_ON_ERROR); ++ ++ if (pd) { ++ pd->halt_PC = halt_PC; ++ pd->halt_ra = halt_ra; ++ pd->halt_pv = halt_pv; ++ } ++ ++ switch (flag) ++ { ++ case GET_HALT_PC: ++ return halt_PC; ++ ++ case GET_HALT_RA: ++ return halt_ra; ++ ++ case GET_HALT_PV: ++ return halt_pv; ++ ++ default: ++ return 0; ++ } ++} ++ ++/* ++ * Translate a PTE, returning TRUE if the page is _PAGE_VALID or _PAGE_PRESENT, ++ * whichever is appropriate for the machine type. If a physaddr pointer is ++ * passed in, don't print anything. ++ */ ++static int ++sw64_translate_pte(ulong pte, void *physaddr, ulonglong unused) ++{ ++ int c, len1, len2, len3, others, page_present; ++ char buf[BUFSIZE]; ++ char buf2[BUFSIZE]; ++ char buf3[BUFSIZE]; ++ char ptebuf[BUFSIZE]; ++ char physbuf[BUFSIZE]; ++ char *arglist[MAXARGS]; ++ physaddr_t paddr; ++ ++ paddr = PTOB(pte >> 32); ++ page_present = (pte & _PAGE_VALID); ++ ++ if (physaddr) { ++ *((ulong *)physaddr) = paddr; ++ return page_present; ++ } ++ ++ sprintf(ptebuf, "%lx", pte); ++ len1 = MAX(strlen(ptebuf), strlen("PTE")); ++ fprintf(fp, "%s ", mkstring(buf, len1, CENTER|LJUST, "PTE")); ++ ++ if (!page_present && pte) { ++ swap_location(pte, buf); ++ if ((c = parse_line(buf, arglist)) != 3) ++ error(FATAL, "cannot determine swap location\n"); ++ ++ len2 = MAX(strlen(arglist[0]), strlen("SWAP")); ++ len3 = MAX(strlen(arglist[2]), strlen("OFFSET")); ++ ++ fprintf(fp, "%s %s\n", ++ mkstring(buf2, len2, CENTER|LJUST, "SWAP"), ++ mkstring(buf3, len3, CENTER|LJUST, "OFFSET")); ++ ++ strcpy(buf2, arglist[0]); ++ strcpy(buf3, arglist[2]); ++ fprintf(fp, "%s %s %s\n", ++ mkstring(ptebuf, len1, CENTER|RJUST, NULL), ++ mkstring(buf2, len2, CENTER|RJUST, NULL), ++ mkstring(buf3, len3, CENTER|RJUST, NULL)); ++ ++ return page_present; ++ } ++ ++ sprintf(physbuf, "%llx", paddr); ++ len2 = MAX(strlen(physbuf), strlen("PHYSICAL")); ++ fprintf(fp, "%s ", mkstring(buf, len2, CENTER|LJUST, "PHYSICAL")); ++ ++ fprintf(fp, "FLAGS\n"); ++ ++ fprintf(fp, "%s %s ", ++ mkstring(ptebuf, len1, CENTER|RJUST, NULL), ++ mkstring(physbuf, len2, CENTER|RJUST, NULL)); ++ fprintf(fp, "("); ++ others = 0; ++ ++ if (pte) { ++ if (pte & _PAGE_VALID) ++ fprintf(fp, "%sVALID", others++ ? "|" : ""); ++ if (pte & _PAGE_FOR) ++ fprintf(fp, "%sFOR", others++ ? "|" : ""); ++ if (pte & _PAGE_FOW) ++ fprintf(fp, "%sFOW", others++ ? "|" : ""); ++ if (pte & _PAGE_FOE) ++ fprintf(fp, "%sFOE", others++ ? "|" : ""); ++ if (pte & _PAGE_ASM) ++ fprintf(fp, "%sASM", others++ ? "|" : ""); ++ if (pte & _PAGE_KRE) ++ fprintf(fp, "%sKRE", others++ ? "|" : ""); ++ if (pte & _PAGE_URE) ++ fprintf(fp, "%sURE", others++ ? "|" : ""); ++ if (pte & _PAGE_KWE) ++ fprintf(fp, "%sKWE", others++ ? "|" : ""); ++ if (pte & _PAGE_UWE) ++ fprintf(fp, "%sUWE", others++ ? "|" : ""); ++ if (pte & _PAGE_DIRTY) ++ fprintf(fp, "%sDIRTY", others++ ? "|" : ""); ++ if (pte & _PAGE_ACCESSED) ++ fprintf(fp, "%sACCESSED", others++ ? "|" : ""); ++ } else { ++ fprintf(fp, "no mapping"); ++ } ++ ++ fprintf(fp, ")\n"); ++ ++ return page_present; ++} ++ ++ ++/* ++ * This is currently not machine-dependent, but eventually I'd prefer to use ++ * the HWPCB for the real physical memory size. ++ */ ++static uint64_t ++sw64_memory_size(void) ++{ ++ return (generic_memory_size()); ++} ++ ++/* ++ * Determine where vmalloc'd memory starts. ++ */ ++static ulong ++sw64_vmalloc_start(void) ++{ ++ return VMALLOC_START; ++} ++ ++/* ++ * SW64 tasks are all stacksize-aligned. ++ */ ++static int ++sw64_is_task_addr(ulong task) ++{ ++ if (tt->flags & THREAD_INFO) ++ return IS_KVADDR(task); ++ else ++ return (IS_KVADDR(task) && (ALIGNED_STACK_OFFSET(task) == 0)); ++} ++ ++/* ++ * Keep or reject a symbol from the kernel namelist. ++ */ ++int ++sw64_verify_symbol(const char *name, ulong value, char type) ++{ ++ if (CRASHDEBUG(8) && name && strlen(name)) ++ fprintf(fp, "%016lx %s\n", value, name); ++ ++ return (name && strlen(name) && (value > MIN_SYMBOL_VALUE)); ++} ++ ++/* ++ * Override smp_num_cpus if possible and necessary. ++ */ ++int ++sw64_get_smp_cpus(void) ++{ ++ int cpus; ++ ++ if ((cpus = get_cpus_present())) ++ return cpus; ++ else ++ return kt->cpus; ++} ++ ++/* ++ * Machine dependent command. ++ */ ++void ++sw64_cmd_mach(void) ++{ ++ int c, cflag; ++ unsigned int radix; ++ ++ cflag = radix = 0; ++ ++ while ((c = getopt(argcnt, args, "cxd")) != EOF) { ++ switch(c) ++ { ++ case 'c': ++ cflag++; ++ break; ++ ++ case 'x': ++ if (radix == 10) ++ error(FATAL, ++ "-d and -x are mutually exclusive\n"); ++ radix = 16; ++ break; ++ ++ case 'd': ++ if (radix == 16) ++ error(FATAL, ++ "-d and -x are mutually exclusive\n"); ++ radix = 10; ++ break; ++ ++ default: ++ argerrs++; ++ break; ++ } ++ } ++ ++ if (argerrs) ++ cmd_usage(pc->curcmd, SYNOPSIS); ++ ++ if (cflag) ++ display_hwrpb(radix); ++ else ++ sw64_display_machine_stats(); ++} ++ ++/* ++ * "mach" command output. ++ */ ++static void ++sw64_display_machine_stats(void) ++{ ++ struct new_utsname *uts; ++ char buf[BUFSIZE]; ++ ulong mhz; ++ ++ uts = &kt->utsname; ++ ++ fprintf(fp, " MACHINE TYPE: %s\n", uts->machine); ++ fprintf(fp, " MEMORY SIZE: %s\n", get_memory_size(buf)); ++ fprintf(fp, " CPUS: %d\n", kt->cpus); ++ fprintf(fp, " PROCESSOR SPEED: "); ++ if ((mhz = machdep->processor_speed())) ++ fprintf(fp, "%ld Mhz\n", mhz); ++ else ++ fprintf(fp, "(unknown)\n"); ++ fprintf(fp, " HZ: %d\n", machdep->hz); ++ fprintf(fp, " PAGE SIZE: %d\n", PAGESIZE()); ++ fprintf(fp, " L1 CACHE SIZE: %d\n", l1_cache_size()); ++ fprintf(fp, "KERNEL VIRTUAL BASE: %lx\n", machdep->kvbase); ++ fprintf(fp, "KERNEL VMALLOC BASE: %lx\n", vt->vmalloc_start); ++ fprintf(fp, " KERNEL STACK SIZE: %ld\n", STACKSIZE()); ++} ++ ++/* ++ * Display the hwrpb_struct and each percpu_struct. ++ */ ++static void ++display_hwrpb(unsigned int radix) ++{ ++ int cpu; ++ ulong hwrpb, percpu; ++ ulong processor_offset, processor_size; ++ ++ get_symbol_data("hwrpb", sizeof(void *), &hwrpb); ++ ++ readmem(hwrpb+OFFSET(hwrpb_struct_processor_offset), KVADDR, ++ &processor_offset, sizeof(ulong), ++ "hwrpb processor_offset", FAULT_ON_ERROR); ++ readmem(hwrpb+OFFSET(hwrpb_struct_processor_size), KVADDR, ++ &processor_size, sizeof(ulong), ++ "hwrpb processor_size", FAULT_ON_ERROR); ++ ++ fprintf(fp, "HWRPB:\n"); ++ dump_struct("hwrpb_struct", hwrpb, radix); ++ ++ for (cpu = 0; cpu < kt->cpus; cpu++) { ++ fprintf(fp, "\nCPU %d:\n", cpu); ++ percpu = hwrpb + processor_offset + (processor_size * cpu); ++ dump_struct("percpu_struct", percpu, radix); ++ } ++} ++ ++/* ++ * Perform any leftover pre-prompt machine-specific initialization tasks here. ++ */ ++static void ++sw64_post_init(void) ++{ ++ modify_signame(7, "SIGEMT", NULL); ++ modify_signame(10, "SIGBUS", NULL); ++ modify_signame(12, "SIGSYS", NULL); ++ modify_signame(16, "SIGURG", NULL); ++ modify_signame(17, "SIGSTOP", NULL); ++ modify_signame(18, "SIGTSTP", NULL); ++ modify_signame(19, "SIGCONT", NULL); ++ modify_signame(20, "SIGCHLD", NULL); ++ modify_signame(23, "SIGIO", "SIGPOLL"); ++ modify_signame(29, "SIGINFO", "SIGPWR"); ++ modify_signame(30, "SIGUSR1", NULL); ++ modify_signame(31, "SIGUSR2", NULL); ++} ++ ++ ++#endif /* SW_64 */ +diff --git a/task.c b/task.c +index ebdb5be..f18ca98 100644 +--- a/task.c ++++ b/task.c +@@ -8566,6 +8566,55 @@ clear_active_set(void) + error(WARNING, \ + "multiple active tasks have called die\n\n"); + ++#ifdef __sw_64__ ++#define SEARCH_STACK_FOR_PANIC_DIE_AND_KEXEC_CALLERS() \ ++ while (fgets(buf, BUFSIZE, pc->tmpfile)) { \ ++ if (strstr(buf, " die+")) { \ ++ switch (die_task) \ ++ { \ ++ case NO_TASK: \ ++ die_task = task; \ ++ break; \ ++ default: \ ++ if (die_task != task) \ ++ die_task = NO_TASK+1; \ ++ break; \ ++ } \ ++ } \ ++ if (strstr(buf, " panic+")) { \ ++ switch (panic_task) \ ++ { \ ++ case NO_TASK: \ ++ panic_task = task; \ ++ if (XENDUMP_DUMPFILE()) \ ++ xendump_panic_hook(buf); \ ++ break; \ ++ default: \ ++ if (panic_task != task) \ ++ panic_task = NO_TASK+1; \ ++ break; \ ++ } \ ++ } \ ++ if (strstr(buf, " crash_kexec+") || \ ++ strstr(buf, " .crash_kexec+")) { \ ++ crash_kexec_task = task; \ ++ } \ ++ if (strstr(buf, " .crash_fadump+")) \ ++ crash_fadump_task = task; \ ++ if (strstr(buf, " machine_crash_shutdown+") || \ ++ strstr(buf, " .machine_crash_shutdown+")) { \ ++ crash_kexec_task = task; \ ++ } \ ++ if (strstr(buf, " xen_panic_event+") || \ ++ strstr(buf, " .xen_panic_event+")){ \ ++ xen_panic_task = task; \ ++ xendump_panic_hook(buf); \ ++ } \ ++ if (machine_type("IA64") && XENDUMP_DUMPFILE() && !xen_panic_task && \ ++ strstr(buf, " sysrq_handle_crashdump+")) \ ++ xen_sysrq_task = task; \ ++ } ++#else + #define SEARCH_STACK_FOR_PANIC_DIE_AND_KEXEC_CALLERS() \ + while (fgets(buf, BUFSIZE, pc->tmpfile)) { \ + if (strstr(buf, " die+")) { \ +@@ -8613,7 +8662,7 @@ clear_active_set(void) + strstr(buf, " sysrq_handle_crashdump+")) \ + xen_sysrq_task = task; \ + } +- ++#endif + /* + * Search the active set tasks for instances of die or panic calls. + */ diff --git a/crash.spec b/crash.spec index fb6b6d21e7c0358739d4618004ef5bf05d50b87c..0c0b968178ff1b1d748415539d01d33d7c1a1271 100644 --- a/crash.spec +++ b/crash.spec @@ -1,6 +1,6 @@ Name: crash Version: 8.0.4 -Release: 10 +Release: 11 Summary: Linux kernel crash utility. License: GPLv3 URL: https://crash-utility.github.io @@ -9,16 +9,17 @@ Source1: http://ftp.gnu.org/gnu/gdb/gdb-10.2.tar.gz Patch0: 0000-lzo_snappy.patch Patch1: 0001-add-SDEI-stack-resolution.patch -##%ifarch sw_64 -Patch2: 0002-crash-8.0.2-sw.patch -##%endif -##%ifarch loongarch64 +%ifarch sw_64 +Patch2: 0002-crash-8.0.4-sw64.patch +%else +%ifarch loongarch64 Patch3: 0003-crash-8.0.4-add-support-for-loongarch64.patch Patch4: 0004-support-vmp_area_list-replaced-with-VMALLOC_START.patch -##%endif +%endif Patch5: 0005-gdb-ignore-Wenum-constexpr-conversion-in-enum-flags.patch Patch6: 0006-arm64-fix-a-potential-segfault-when-unwind-frame.patch Patch7: 0007-arm64-fix-SDEI-stack-frame-unwind-while-UNW_4_14-is-.patch +%endif BuildRequires: ncurses-devel zlib-devel lzo-devel snappy-devel texinfo libzstd-devel BuildRequires: gcc gcc-c++ bison m4 @@ -49,20 +50,21 @@ created by manufacturer-specific firmware. %package_help %prep +%ifarch sw_64 +%autosetup -n %{name}-%{version} -p1 +%else %setup -n %{name}-%{version} %patch 0 -p1 %patch 1 -p1 -%ifarch sw_64 -%patch 2 -p1 -%endif %ifarch loongarch64 %patch 3 -p1 %patch 4 -p1 %endif %autopatch -m5 -p1 +%endif %build cp %{SOURCE1} . @@ -97,6 +99,9 @@ install -D -m 0644 defs.h %{buildroot}%{_includedir}/%{name}/defs.h %{_mandir}/man8/crash.8* %changelog +* Tue Apr 15 2025 Gu Zitao - 8.0.4-11 +- crash: add support for sw64 + * Thu Dec 05 2024 shenzhongwei - 8.0.4-10 - remove the architecture judgment in the patches section; - include all patches in the source package.