diff --git a/thirdparty/README.md b/thirdparty/README.md index 258a12b840e..b0e7660b8f8 100644 --- a/thirdparty/README.md +++ b/thirdparty/README.md @@ -460,12 +460,14 @@ Files extracted from upstream source: ## libbacktrace - Upstream: https://github.com/ianlancetaylor/libbacktrace -- Version: git (4d2dd0b172f2c9192f83ba93425f868f2a13c553, 2022) +- Version: git (1db85642e3fca189cf4e076f840a45d6934b2456, 2024) - License: BSD-3-Clause Files extracted from upstream source: -- `*.{c,h}` files for Windows platform +- `*.{c,h}` files for Windows platform, i.e. remove the following: + * `allocfail.c`, `instrumented_alloc.c`, `*test*.{c,h}` + * `elf.c`, `macho.c`, `mmap.c`, `mmapio.c`, `nounwind.c`, `unknown.c`, `xcoff.c` - `LICENSE` Important: Some files have Godot-made changes to load big debug symbol files. diff --git a/thirdparty/libbacktrace/alloc.c b/thirdparty/libbacktrace/alloc.c index ff2c8677c06..193e770526b 100644 --- a/thirdparty/libbacktrace/alloc.c +++ b/thirdparty/libbacktrace/alloc.c @@ -1,5 +1,5 @@ /* alloc.c -- Memory allocation without mmap. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/atomic.c b/thirdparty/libbacktrace/atomic.c index fcac485b237..21785a19e87 100644 --- a/thirdparty/libbacktrace/atomic.c +++ b/thirdparty/libbacktrace/atomic.c @@ -1,5 +1,5 @@ /* atomic.c -- Support for atomic functions if not present. - Copyright (C) 2013-2021 Free Software Foundation, Inc. + Copyright (C) 2013-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/backtrace-supported.h b/thirdparty/libbacktrace/backtrace-supported.h index f597195f130..9e779a1d965 100644 --- a/thirdparty/libbacktrace/backtrace-supported.h +++ b/thirdparty/libbacktrace/backtrace-supported.h @@ -1,5 +1,5 @@ /* backtrace-supported.h.in -- Whether stack backtrace is supported. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/backtrace.c b/thirdparty/libbacktrace/backtrace.c index 7b629008525..3e6b81e9a3f 100644 --- a/thirdparty/libbacktrace/backtrace.c +++ b/thirdparty/libbacktrace/backtrace.c @@ -1,5 +1,5 @@ /* backtrace.c -- Entry point for stack backtrace library. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/backtrace.h b/thirdparty/libbacktrace/backtrace.h index 69cea4ca1e4..de92a3afb35 100644 --- a/thirdparty/libbacktrace/backtrace.h +++ b/thirdparty/libbacktrace/backtrace.h @@ -1,5 +1,5 @@ /* backtrace.h -- Public header file for stack backtrace library. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/config.h b/thirdparty/libbacktrace/config.h index 0c745c191b6..03beb614180 100644 --- a/thirdparty/libbacktrace/config.h +++ b/thirdparty/libbacktrace/config.h @@ -21,6 +21,10 @@ don't. */ #define HAVE_DECL_STRNLEN 1 +/* Define to 1 if you have the declaration of `_pgmptr', and to 0 if you + don't. */ +#define HAVE_DECL__PGMPTR 1 + /* Define to 1 if you have the header file. */ /* #undef HAVE_DLFCN_H */ @@ -48,7 +52,7 @@ /* #undef HAVE_KERN_PROC_ARGS */ /* Define if -llzma is available. */ -#define HAVE_LIBLZMA 1 +/* #undef HAVE_LIBLZMA */ /* Define to 1 if you have the header file. */ /* #undef HAVE_LINK_H */ @@ -86,6 +90,9 @@ /* Define to 1 if you have the header file. */ /* #undef HAVE_SYS_LDR_H */ +/* Define to 1 if you have the header file. */ +/* #undef HAVE_SYS_LINK_H */ + /* Define to 1 if you have the header file. */ /* #undef HAVE_SYS_MMAN_H */ @@ -95,12 +102,21 @@ /* Define to 1 if you have the header file. */ #define HAVE_SYS_TYPES_H 1 +/* Define to 1 if you have the header file. */ +#define HAVE_TLHELP32_H 1 + /* Define to 1 if you have the header file. */ #define HAVE_UNISTD_H 1 +/* Define to 1 if you have the header file. */ +#define HAVE_WINDOWS_H 1 + /* Define if -lz is available. */ #define HAVE_ZLIB 1 +/* Define if -lzstd is available. */ +/* #undef HAVE_ZSTD */ + /* Define to the sub-directory in which libtool stores uninstalled libraries. */ #define LT_OBJDIR ".libs/" diff --git a/thirdparty/libbacktrace/dwarf.c b/thirdparty/libbacktrace/dwarf.c index 5b2724e6a72..2f323acb61a 100644 --- a/thirdparty/libbacktrace/dwarf.c +++ b/thirdparty/libbacktrace/dwarf.c @@ -1,5 +1,5 @@ /* dwarf.c -- Get file/line information from DWARF for backtraces. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without @@ -470,7 +470,7 @@ enum attr_val_encoding /* An address. */ ATTR_VAL_ADDRESS, /* An index into the .debug_addr section, whose value is relative to - * the DW_AT_addr_base attribute of the compilation unit. */ + the DW_AT_addr_base attribute of the compilation unit. */ ATTR_VAL_ADDRESS_INDEX, /* A unsigned integer. */ ATTR_VAL_UINT, @@ -608,8 +608,8 @@ struct function struct function_addrs { /* Range is LOW <= PC < HIGH. */ - uint64_t low; - uint64_t high; + uintptr_t low; + uintptr_t high; /* Function for this address range. */ struct function *function; }; @@ -690,8 +690,8 @@ struct unit struct unit_addrs { /* Range is LOW <= PC < HIGH. */ - uint64_t low; - uint64_t high; + uintptr_t low; + uintptr_t high; /* Compilation unit for this address range. */ struct unit *u; }; @@ -722,8 +722,8 @@ struct dwarf_data struct dwarf_data *next; /* The data for .gnu_debugaltlink. */ struct dwarf_data *altlink; - /* The base address for this file. */ - uintptr_t base_address; + /* The base address mapping for this file. */ + struct libbacktrace_base_address base_address; /* A sorted list of address ranges. */ struct unit_addrs *addrs; /* Number of address ranges in list. */ @@ -1428,7 +1428,7 @@ resolve_addr_index (const struct dwarf_sections *dwarf_sections, uint64_t addr_base, int addrsize, int is_bigendian, uint64_t addr_index, backtrace_error_callback error_callback, void *data, - uint64_t *address) + uintptr_t *address) { uint64_t offset; struct dwarf_buf addr_buf; @@ -1449,7 +1449,7 @@ resolve_addr_index (const struct dwarf_sections *dwarf_sections, addr_buf.data = data; addr_buf.reported_underflow = 0; - *address = read_address (&addr_buf, addrsize); + *address = (uintptr_t) read_address (&addr_buf, addrsize); return 1; } @@ -1528,7 +1528,7 @@ function_addrs_search (const void *vkey, const void *ventry) static int add_unit_addr (struct backtrace_state *state, void *rdata, - uint64_t lowpc, uint64_t highpc, + uintptr_t lowpc, uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *pvec) { @@ -1610,6 +1610,194 @@ unit_addrs_search (const void *vkey, const void *ventry) return 0; } +/* Fill in overlapping ranges as needed. This is a subroutine of + resolve_unit_addrs_overlap. */ + +static int +resolve_unit_addrs_overlap_walk (struct backtrace_state *state, + size_t *pfrom, size_t *pto, + struct unit_addrs *enclosing, + struct unit_addrs_vector *old_vec, + backtrace_error_callback error_callback, + void *data, + struct unit_addrs_vector *new_vec) +{ + struct unit_addrs *old_addrs; + size_t old_count; + struct unit_addrs *new_addrs; + size_t from; + size_t to; + + old_addrs = (struct unit_addrs *) old_vec->vec.base; + old_count = old_vec->count; + new_addrs = (struct unit_addrs *) new_vec->vec.base; + + for (from = *pfrom, to = *pto; from < old_count; from++, to++) + { + /* If we are in the scope of a larger range that can no longer + cover any further ranges, return back to the caller. */ + + if (enclosing != NULL + && enclosing->high <= old_addrs[from].low) + { + *pfrom = from; + *pto = to; + return 1; + } + + new_addrs[to] = old_addrs[from]; + + /* If we are in scope of a larger range, fill in any gaps + between this entry and the next one. + + There is an extra entry at the end of the vector, so it's + always OK to refer to from + 1. */ + + if (enclosing != NULL + && enclosing->high > old_addrs[from].high + && old_addrs[from].high < old_addrs[from + 1].low) + { + void *grew; + size_t new_high; + + grew = backtrace_vector_grow (state, sizeof (struct unit_addrs), + error_callback, data, &new_vec->vec); + if (grew == NULL) + return 0; + new_addrs = (struct unit_addrs *) new_vec->vec.base; + to++; + new_addrs[to].low = old_addrs[from].high; + new_high = old_addrs[from + 1].low; + if (enclosing->high < new_high) + new_high = enclosing->high; + new_addrs[to].high = new_high; + new_addrs[to].u = enclosing->u; + } + + /* If this range has a larger scope than the next one, use it to + fill in any gaps. */ + + if (old_addrs[from].high > old_addrs[from + 1].high) + { + *pfrom = from + 1; + *pto = to + 1; + if (!resolve_unit_addrs_overlap_walk (state, pfrom, pto, + &old_addrs[from], old_vec, + error_callback, data, new_vec)) + return 0; + from = *pfrom; + to = *pto; + + /* Undo the increment the loop is about to do. */ + from--; + to--; + } + } + + if (enclosing == NULL) + { + struct unit_addrs *pa; + + /* Add trailing entry. */ + + pa = ((struct unit_addrs *) + backtrace_vector_grow (state, sizeof (struct unit_addrs), + error_callback, data, &new_vec->vec)); + if (pa == NULL) + return 0; + pa->low = 0; + --pa->low; + pa->high = pa->low; + pa->u = NULL; + + new_vec->count = to; + } + + return 1; +} + +/* It is possible for the unit_addrs list to contain overlaps, as in + + 10: low == 10, high == 20, unit 1 + 11: low == 12, high == 15, unit 2 + 12: low == 20, high == 30, unit 1 + + In such a case, for pc == 17, a search using units_addr_search will + return entry 11. However, pc == 17 doesn't fit in that range. We + actually want range 10. + + It seems that in general we might have an arbitrary number of + ranges in between 10 and 12. + + To handle this we look for cases where range R1 is followed by + range R2 such that R2 is a strict subset of R1. In such cases we + insert a new range R3 following R2 that fills in the remainder of + the address space covered by R1. That lets a relatively simple + search find the correct range. + + These overlaps can occur because of the range merging we do in + add_unit_addr. When the linker de-duplicates functions, it can + leave behind an address range that refers to the address range of + the retained duplicate. If the retained duplicate address range is + merged with others, then after sorting we can see overlapping + address ranges. + + See https://github.com/ianlancetaylor/libbacktrace/issues/137. */ + +static int +resolve_unit_addrs_overlap (struct backtrace_state *state, + backtrace_error_callback error_callback, + void *data, struct unit_addrs_vector *addrs_vec) +{ + struct unit_addrs *addrs; + size_t count; + int found; + struct unit_addrs *entry; + size_t i; + struct unit_addrs_vector new_vec; + void *grew; + size_t from; + size_t to; + + addrs = (struct unit_addrs *) addrs_vec->vec.base; + count = addrs_vec->count; + + if (count == 0) + return 1; + + /* Optimistically assume that overlaps are rare. */ + found = 0; + entry = addrs; + for (i = 0; i < count - 1; i++) + { + if (entry->low < (entry + 1)->low + && entry->high > (entry + 1)->high) + { + found = 1; + break; + } + entry++; + } + if (!found) + return 1; + + memset (&new_vec, 0, sizeof new_vec); + grew = backtrace_vector_grow (state, + count * sizeof (struct unit_addrs), + error_callback, data, &new_vec.vec); + if (grew == NULL) + return 0; + + from = 0; + to = 0; + resolve_unit_addrs_overlap_walk (state, &from, &to, NULL, addrs_vec, + error_callback, data, &new_vec); + backtrace_vector_free (state, &addrs_vec->vec, error_callback, data); + *addrs_vec = new_vec; + + return 1; +} + /* Sort the line vector by PC. We want a stable sort here to maintain the order of lines for the same PC values. Since the sequence is being sorted in place, their addresses cannot be relied on to @@ -1864,10 +2052,10 @@ lookup_abbrev (struct abbrevs *abbrevs, uint64_t code, lowpc/highpc is set or ranges is set. */ struct pcrange { - uint64_t lowpc; /* The low PC value. */ + uintptr_t lowpc; /* The low PC value. */ int have_lowpc; /* Whether a low PC value was found. */ int lowpc_is_addr_index; /* Whether lowpc is in .debug_addr. */ - uint64_t highpc; /* The high PC value. */ + uintptr_t highpc; /* The high PC value. */ int have_highpc; /* Whether a high PC value was found. */ int highpc_is_relative; /* Whether highpc is relative to lowpc. */ int highpc_is_addr_index; /* Whether highpc is in .debug_addr. */ @@ -1887,12 +2075,12 @@ update_pcrange (const struct attr* attr, const struct attr_val* val, case DW_AT_low_pc: if (val->encoding == ATTR_VAL_ADDRESS) { - pcrange->lowpc = val->u.uint; + pcrange->lowpc = (uintptr_t) val->u.uint; pcrange->have_lowpc = 1; } else if (val->encoding == ATTR_VAL_ADDRESS_INDEX) { - pcrange->lowpc = val->u.uint; + pcrange->lowpc = (uintptr_t) val->u.uint; pcrange->have_lowpc = 1; pcrange->lowpc_is_addr_index = 1; } @@ -1901,18 +2089,18 @@ update_pcrange (const struct attr* attr, const struct attr_val* val, case DW_AT_high_pc: if (val->encoding == ATTR_VAL_ADDRESS) { - pcrange->highpc = val->u.uint; + pcrange->highpc = (uintptr_t) val->u.uint; pcrange->have_highpc = 1; } else if (val->encoding == ATTR_VAL_UINT) { - pcrange->highpc = val->u.uint; + pcrange->highpc = (uintptr_t) val->u.uint; pcrange->have_highpc = 1; pcrange->highpc_is_relative = 1; } else if (val->encoding == ATTR_VAL_ADDRESS_INDEX) { - pcrange->highpc = val->u.uint; + pcrange->highpc = (uintptr_t) val->u.uint; pcrange->have_highpc = 1; pcrange->highpc_is_addr_index = 1; } @@ -1944,19 +2132,20 @@ update_pcrange (const struct attr* attr, const struct attr_val* val, static int add_low_high_range (struct backtrace_state *state, const struct dwarf_sections *dwarf_sections, - uintptr_t base_address, int is_bigendian, - struct unit *u, const struct pcrange *pcrange, + struct libbacktrace_base_address base_address, + int is_bigendian, struct unit *u, + const struct pcrange *pcrange, int (*add_range) (struct backtrace_state *state, - void *rdata, uint64_t lowpc, - uint64_t highpc, + void *rdata, uintptr_t lowpc, + uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *vec), void *rdata, backtrace_error_callback error_callback, void *data, void *vec) { - uint64_t lowpc; - uint64_t highpc; + uintptr_t lowpc; + uintptr_t highpc; lowpc = pcrange->lowpc; if (pcrange->lowpc_is_addr_index) @@ -1980,8 +2169,8 @@ add_low_high_range (struct backtrace_state *state, /* Add in the base address of the module when recording PC values, so that we can look up the PC directly. */ - lowpc += base_address; - highpc += base_address; + lowpc = libbacktrace_add_base (lowpc, base_address); + highpc = libbacktrace_add_base (highpc, base_address); return add_range (state, rdata, lowpc, highpc, error_callback, data, vec); } @@ -1993,11 +2182,11 @@ static int add_ranges_from_ranges ( struct backtrace_state *state, const struct dwarf_sections *dwarf_sections, - uintptr_t base_address, int is_bigendian, - struct unit *u, uint64_t base, + struct libbacktrace_base_address base_address, int is_bigendian, + struct unit *u, uintptr_t base, const struct pcrange *pcrange, int (*add_range) (struct backtrace_state *state, void *rdata, - uint64_t lowpc, uint64_t highpc, + uintptr_t lowpc, uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *vec), void *rdata, @@ -2036,13 +2225,14 @@ add_ranges_from_ranges ( break; if (is_highest_address (low, u->addrsize)) - base = high; + base = (uintptr_t) high; else { - if (!add_range (state, rdata, - low + base + base_address, - high + base + base_address, - error_callback, data, vec)) + uintptr_t rl, rh; + + rl = libbacktrace_add_base ((uintptr_t) low + base, base_address); + rh = libbacktrace_add_base ((uintptr_t) high + base, base_address); + if (!add_range (state, rdata, rl, rh, error_callback, data, vec)) return 0; } } @@ -2060,11 +2250,11 @@ static int add_ranges_from_rnglists ( struct backtrace_state *state, const struct dwarf_sections *dwarf_sections, - uintptr_t base_address, int is_bigendian, - struct unit *u, uint64_t base, + struct libbacktrace_base_address base_address, int is_bigendian, + struct unit *u, uintptr_t base, const struct pcrange *pcrange, int (*add_range) (struct backtrace_state *state, void *rdata, - uint64_t lowpc, uint64_t highpc, + uintptr_t lowpc, uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *vec), void *rdata, @@ -2130,8 +2320,8 @@ add_ranges_from_rnglists ( case DW_RLE_startx_endx: { uint64_t index; - uint64_t low; - uint64_t high; + uintptr_t low; + uintptr_t high; index = read_uleb128 (&rnglists_buf); if (!resolve_addr_index (dwarf_sections, u->addr_base, @@ -2143,9 +2333,10 @@ add_ranges_from_rnglists ( u->addrsize, is_bigendian, index, error_callback, data, &high)) return 0; - if (!add_range (state, rdata, low + base_address, - high + base_address, error_callback, data, - vec)) + if (!add_range (state, rdata, + libbacktrace_add_base (low, base_address), + libbacktrace_add_base (high, base_address), + error_callback, data, vec)) return 0; } break; @@ -2153,8 +2344,8 @@ add_ranges_from_rnglists ( case DW_RLE_startx_length: { uint64_t index; - uint64_t low; - uint64_t length; + uintptr_t low; + uintptr_t length; index = read_uleb128 (&rnglists_buf); if (!resolve_addr_index (dwarf_sections, u->addr_base, @@ -2162,7 +2353,7 @@ add_ranges_from_rnglists ( error_callback, data, &low)) return 0; length = read_uleb128 (&rnglists_buf); - low += base_address; + low = libbacktrace_add_base (low, base_address); if (!add_range (state, rdata, low, low + length, error_callback, data, vec)) return 0; @@ -2176,39 +2367,41 @@ add_ranges_from_rnglists ( low = read_uleb128 (&rnglists_buf); high = read_uleb128 (&rnglists_buf); - if (!add_range (state, rdata, low + base + base_address, - high + base + base_address, + if (!add_range (state, rdata, + libbacktrace_add_base (low + base, base_address), + libbacktrace_add_base (high + base, base_address), error_callback, data, vec)) return 0; } break; case DW_RLE_base_address: - base = read_address (&rnglists_buf, u->addrsize); + base = (uintptr_t) read_address (&rnglists_buf, u->addrsize); break; case DW_RLE_start_end: { - uint64_t low; - uint64_t high; + uintptr_t low; + uintptr_t high; - low = read_address (&rnglists_buf, u->addrsize); - high = read_address (&rnglists_buf, u->addrsize); - if (!add_range (state, rdata, low + base_address, - high + base_address, error_callback, data, - vec)) + low = (uintptr_t) read_address (&rnglists_buf, u->addrsize); + high = (uintptr_t) read_address (&rnglists_buf, u->addrsize); + if (!add_range (state, rdata, + libbacktrace_add_base (low, base_address), + libbacktrace_add_base (high, base_address), + error_callback, data, vec)) return 0; } break; case DW_RLE_start_length: { - uint64_t low; - uint64_t length; + uintptr_t low; + uintptr_t length; - low = read_address (&rnglists_buf, u->addrsize); - length = read_uleb128 (&rnglists_buf); - low += base_address; + low = (uintptr_t) read_address (&rnglists_buf, u->addrsize); + length = (uintptr_t) read_uleb128 (&rnglists_buf); + low = libbacktrace_add_base (low, base_address); if (!add_range (state, rdata, low, low + length, error_callback, data, vec)) return 0; @@ -2236,10 +2429,10 @@ add_ranges_from_rnglists ( static int add_ranges (struct backtrace_state *state, const struct dwarf_sections *dwarf_sections, - uintptr_t base_address, int is_bigendian, - struct unit *u, uint64_t base, const struct pcrange *pcrange, - int (*add_range) (struct backtrace_state *state, void *rdata, - uint64_t lowpc, uint64_t highpc, + struct libbacktrace_base_address base_address, int is_bigendian, + struct unit *u, uintptr_t base, const struct pcrange *pcrange, + int (*add_range) (struct backtrace_state *state, void *rdata, + uintptr_t lowpc, uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *vec), void *rdata, @@ -2272,7 +2465,8 @@ add_ranges (struct backtrace_state *state, read, 0 if there is some error. */ static int -find_address_ranges (struct backtrace_state *state, uintptr_t base_address, +find_address_ranges (struct backtrace_state *state, + struct libbacktrace_base_address base_address, struct dwarf_buf *unit_buf, const struct dwarf_sections *dwarf_sections, int is_bigendian, struct dwarf_data *altlink, @@ -2427,7 +2621,8 @@ find_address_ranges (struct backtrace_state *state, uintptr_t base_address, on success, 0 on failure. */ static int -build_address_map (struct backtrace_state *state, uintptr_t base_address, +build_address_map (struct backtrace_state *state, + struct libbacktrace_base_address base_address, const struct dwarf_sections *dwarf_sections, int is_bigendian, struct dwarf_data *altlink, backtrace_error_callback error_callback, void *data, @@ -2646,7 +2841,7 @@ add_line (struct backtrace_state *state, struct dwarf_data *ddata, /* Add in the base address here, so that we can look up the PC directly. */ - ln->pc = pc + ddata->base_address; + ln->pc = libbacktrace_add_base (pc, ddata->base_address); ln->filename = filename; ln->lineno = lineno; @@ -3307,7 +3502,7 @@ read_line_info (struct backtrace_state *state, struct dwarf_data *ddata, if (vec.count == 0) { - /* This is not a failure in the sense of a generating an error, + /* This is not a failure in the sense of generating an error, but it is a failure in that sense that we have no useful information. */ goto fail; @@ -3517,7 +3712,7 @@ read_referenced_name (struct dwarf_data *ddata, struct unit *u, static int add_function_range (struct backtrace_state *state, void *rdata, - uint64_t lowpc, uint64_t highpc, + uintptr_t lowpc, uintptr_t highpc, backtrace_error_callback error_callback, void *data, void *pvec) { @@ -3557,7 +3752,7 @@ add_function_range (struct backtrace_state *state, void *rdata, static int read_function_entry (struct backtrace_state *state, struct dwarf_data *ddata, - struct unit *u, uint64_t base, struct dwarf_buf *unit_buf, + struct unit *u, uintptr_t base, struct dwarf_buf *unit_buf, const struct line_header *lhdr, backtrace_error_callback error_callback, void *data, struct function_vector *vec_function, @@ -3621,7 +3816,7 @@ read_function_entry (struct backtrace_state *state, struct dwarf_data *ddata, && abbrev->attrs[i].name == DW_AT_low_pc) { if (val.encoding == ATTR_VAL_ADDRESS) - base = val.u.uint; + base = (uintptr_t) val.u.uint; else if (val.encoding == ATTR_VAL_ADDRESS_INDEX) { if (!resolve_addr_index (&ddata->dwarf_sections, @@ -4285,7 +4480,7 @@ dwarf_fileline (struct backtrace_state *state, uintptr_t pc, static struct dwarf_data * build_dwarf_data (struct backtrace_state *state, - uintptr_t base_address, + struct libbacktrace_base_address base_address, const struct dwarf_sections *dwarf_sections, int is_bigendian, struct dwarf_data *altlink, @@ -4293,11 +4488,7 @@ build_dwarf_data (struct backtrace_state *state, void *data) { struct unit_addrs_vector addrs_vec; - struct unit_addrs *addrs; - size_t addrs_count; struct unit_vector units_vec; - struct unit **units; - size_t units_count; struct dwarf_data *fdata; if (!build_address_map (state, base_address, dwarf_sections, is_bigendian, @@ -4309,12 +4500,12 @@ build_dwarf_data (struct backtrace_state *state, return NULL; if (!backtrace_vector_release (state, &units_vec.vec, error_callback, data)) return NULL; - addrs = (struct unit_addrs *) addrs_vec.vec.base; - units = (struct unit **) units_vec.vec.base; - addrs_count = addrs_vec.count; - units_count = units_vec.count; - backtrace_qsort (addrs, addrs_count, sizeof (struct unit_addrs), - unit_addrs_compare); + + backtrace_qsort ((struct unit_addrs *) addrs_vec.vec.base, addrs_vec.count, + sizeof (struct unit_addrs), unit_addrs_compare); + if (!resolve_unit_addrs_overlap (state, error_callback, data, &addrs_vec)) + return NULL; + /* No qsort for units required, already sorted. */ fdata = ((struct dwarf_data *) @@ -4326,10 +4517,10 @@ build_dwarf_data (struct backtrace_state *state, fdata->next = NULL; fdata->altlink = altlink; fdata->base_address = base_address; - fdata->addrs = addrs; - fdata->addrs_count = addrs_count; - fdata->units = units; - fdata->units_count = units_count; + fdata->addrs = (struct unit_addrs *) addrs_vec.vec.base; + fdata->addrs_count = addrs_vec.count; + fdata->units = (struct unit **) units_vec.vec.base; + fdata->units_count = units_vec.count; fdata->dwarf_sections = *dwarf_sections; fdata->is_bigendian = is_bigendian; memset (&fdata->fvec, 0, sizeof fdata->fvec); @@ -4343,7 +4534,7 @@ build_dwarf_data (struct backtrace_state *state, int backtrace_dwarf_add (struct backtrace_state *state, - uintptr_t base_address, + struct libbacktrace_base_address base_address, const struct dwarf_sections *dwarf_sections, int is_bigendian, struct dwarf_data *fileline_altlink, diff --git a/thirdparty/libbacktrace/fileline.c b/thirdparty/libbacktrace/fileline.c index 0472f4721ab..50a1e830c23 100644 --- a/thirdparty/libbacktrace/fileline.c +++ b/thirdparty/libbacktrace/fileline.c @@ -1,5 +1,5 @@ /* fileline.c -- Get file and line number information in a backtrace. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without @@ -47,6 +47,18 @@ POSSIBILITY OF SUCH DAMAGE. */ #include #endif +#ifdef HAVE_WINDOWS_H +#ifndef WIN32_LEAN_AND_MEAN +#define WIN32_LEAN_AND_MEAN +#endif + +#ifndef NOMINMAX +#define NOMINMAX +#endif + +#include +#endif + #include "backtrace.h" #include "internal.h" @@ -155,6 +167,47 @@ macho_get_executable_path (struct backtrace_state *state, #endif /* !defined (HAVE_MACH_O_DYLD_H) */ +#if HAVE_DECL__PGMPTR + +#define windows_executable_filename() _pgmptr + +#else /* !HAVE_DECL__PGMPTR */ + +#define windows_executable_filename() NULL + +#endif /* !HAVE_DECL__PGMPTR */ + +#ifdef HAVE_WINDOWS_H + +#define FILENAME_BUF_SIZE (MAX_PATH) + +static char * +windows_get_executable_path (char *buf, backtrace_error_callback error_callback, + void *data) +{ + size_t got; + int error; + + got = GetModuleFileNameA (NULL, buf, FILENAME_BUF_SIZE - 1); + error = GetLastError (); + if (got == 0 + || (got == FILENAME_BUF_SIZE - 1 && error == ERROR_INSUFFICIENT_BUFFER)) + { + error_callback (data, + "could not get the filename of the current executable", + error); + return NULL; + } + return buf; +} + +#else /* !defined (HAVE_WINDOWS_H) */ + +#define windows_get_executable_path(buf, error_callback, data) NULL +#define FILENAME_BUF_SIZE 64 + +#endif /* !defined (HAVE_WINDOWS_H) */ + /* Initialize the fileline information from the executable. Returns 1 on success, 0 on failure. */ @@ -168,7 +221,7 @@ fileline_initialize (struct backtrace_state *state, int called_error_callback; int descriptor; const char *filename; - char buf[64]; + char buf[FILENAME_BUF_SIZE]; if (!state->threaded) failed = state->fileline_initialization_failed; @@ -192,7 +245,7 @@ fileline_initialize (struct backtrace_state *state, descriptor = -1; called_error_callback = 0; - for (pass = 0; pass < 8; ++pass) + for (pass = 0; pass < 10; ++pass) { int does_not_exist; @@ -205,25 +258,33 @@ fileline_initialize (struct backtrace_state *state, filename = getexecname (); break; case 2: - filename = "/proc/self/exe"; + /* Test this before /proc/self/exe, as the latter exists but points + to the wine binary (and thus doesn't work). */ + filename = windows_executable_filename (); break; case 3: - filename = "/proc/curproc/file"; + filename = "/proc/self/exe"; break; case 4: + filename = "/proc/curproc/file"; + break; + case 5: snprintf (buf, sizeof (buf), "/proc/%ld/object/a.out", (long) getpid ()); filename = buf; break; - case 5: + case 6: filename = sysctl_exec_name1 (state, error_callback, data); break; - case 6: + case 7: filename = sysctl_exec_name2 (state, error_callback, data); break; - case 7: + case 8: filename = macho_get_executable_path (state, error_callback, data); break; + case 9: + filename = windows_get_executable_path (buf, error_callback, data); + break; default: abort (); } diff --git a/thirdparty/libbacktrace/internal.h b/thirdparty/libbacktrace/internal.h index bb481f373bf..fe2abe50b0f 100644 --- a/thirdparty/libbacktrace/internal.h +++ b/thirdparty/libbacktrace/internal.h @@ -1,5 +1,5 @@ /* internal.h -- Internal header file for stack backtrace library. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without @@ -56,6 +56,11 @@ POSSIBILITY OF SUCH DAMAGE. */ # endif #endif +#ifdef __has_attribute +# if __has_attribute(fallthrough) +# define ATTRIBUTE_FALLTHROUGH __attribute__ ((fallthrough)) +# endif +#endif #ifndef ATTRIBUTE_FALLTHROUGH # if (GCC_VERSION >= 7000) # define ATTRIBUTE_FALLTHROUGH __attribute__ ((__fallthrough__)) @@ -323,10 +328,44 @@ struct dwarf_sections struct dwarf_data; +/* The load address mapping. */ + +#if defined(__FDPIC__) && defined(HAVE_DL_ITERATE_PHDR) && (defined(HAVE_LINK_H) || defined(HAVE_SYS_LINK_H)) + +#ifdef HAVE_LINK_H + #include +#endif +#ifdef HAVE_SYS_LINK_H + #include +#endif + +#define libbacktrace_using_fdpic() (1) + +struct libbacktrace_base_address +{ + struct elf32_fdpic_loadaddr m; +}; + +#define libbacktrace_add_base(pc, base) \ + ((uintptr_t) (__RELOC_POINTER ((pc), (base).m))) + +#else /* not _FDPIC__ */ + +#define libbacktrace_using_fdpic() (0) + +struct libbacktrace_base_address +{ + uintptr_t m; +}; + +#define libbacktrace_add_base(pc, base) ((pc) + (base).m) + +#endif /* not _FDPIC__ */ + /* Add file/line information for a DWARF module. */ extern int backtrace_dwarf_add (struct backtrace_state *state, - uintptr_t base_address, + struct libbacktrace_base_address base_address, const struct dwarf_sections *dwarf_sections, int is_bigendian, struct dwarf_data *fileline_altlink, @@ -368,6 +407,15 @@ extern int backtrace_uncompress_zdebug (struct backtrace_state *, unsigned char **uncompressed, size_t *uncompressed_size); +/* A test-only hook for elf_zstd_decompress. */ + +extern int backtrace_uncompress_zstd (struct backtrace_state *, + const unsigned char *compressed, + size_t compressed_size, + backtrace_error_callback, void *data, + unsigned char *uncompressed, + size_t uncompressed_size); + /* A test-only hook for elf_uncompress_lzma. */ extern int backtrace_uncompress_lzma (struct backtrace_state *, diff --git a/thirdparty/libbacktrace/pecoff.c b/thirdparty/libbacktrace/pecoff.c index 720251900b4..b96ec27af42 100644 --- a/thirdparty/libbacktrace/pecoff.c +++ b/thirdparty/libbacktrace/pecoff.c @@ -1,5 +1,5 @@ /* pecoff.c -- Get debug data from a PE/COFFF file for backtraces. - Copyright (C) 2015-2021 Free Software Foundation, Inc. + Copyright (C) 2015-2024 Free Software Foundation, Inc. Adapted from elf.c by Tristan Gingold, AdaCore. Redistribution and use in source and binary forms, with or without @@ -39,6 +39,58 @@ POSSIBILITY OF SUCH DAMAGE. */ #include "backtrace.h" #include "internal.h" +#ifdef HAVE_WINDOWS_H +#ifndef WIN32_LEAN_AND_MEAN +#define WIN32_LEAN_AND_MEAN +#endif + +#ifndef NOMINMAX +#define NOMINMAX +#endif + +#include + +#ifdef HAVE_TLHELP32_H +#include + +#ifdef UNICODE +/* If UNICODE is defined, all the symbols are replaced by a macro to use the + wide variant. But we need the ansi variant, so undef the macros. */ +#undef MODULEENTRY32 +#undef Module32First +#undef Module32Next +#endif +#endif + +#if defined(_ARM_) +#define NTAPI +#else +#define NTAPI __stdcall +#endif + +/* This is a simplified (but binary compatible) version of what Microsoft + defines in their documentation. */ +struct dll_notification_data +{ + ULONG reserved; + /* The name as UNICODE_STRING struct. */ + PVOID full_dll_name; + PVOID base_dll_name; + PVOID dll_base; + ULONG size_of_image; +}; + +#define LDR_DLL_NOTIFICATION_REASON_LOADED 1 + +typedef LONG NTSTATUS; +typedef VOID (CALLBACK *LDR_DLL_NOTIFICATION)(ULONG, + struct dll_notification_data*, + PVOID); +typedef NTSTATUS (NTAPI *LDR_REGISTER_FUNCTION)(ULONG, + LDR_DLL_NOTIFICATION, PVOID, + PVOID*); +#endif + /* Coff file header. */ typedef struct { @@ -188,7 +240,7 @@ coff_nodebug (struct backtrace_state *state ATTRIBUTE_UNUSED, backtrace_full_callback callback ATTRIBUTE_UNUSED, backtrace_error_callback error_callback, void *data) { - error_callback (data, "no debug info in PE/COFF executable", -1); + error_callback (data, "no debug info in PE/COFF executable (make sure to compile with -g)", -1); return 0; } @@ -330,10 +382,11 @@ coff_is_function_symbol (const b_coff_internal_symbol *isym) static int coff_initialize_syminfo (struct backtrace_state *state, - uintptr_t base_address, int is_64, - const b_coff_section_header *sects, size_t sects_num, - const b_coff_external_symbol *syms, size_t syms_size, - const unsigned char *strtab, size_t strtab_size, + struct libbacktrace_base_address base_address, + int is_64, const b_coff_section_header *sects, + size_t sects_num, const b_coff_external_symbol *syms, + size_t syms_size, const unsigned char *strtab, + size_t strtab_size, backtrace_error_callback error_callback, void *data, struct coff_syminfo_data *sdata) { @@ -438,9 +491,10 @@ coff_initialize_syminfo (struct backtrace_state *state, secnum = coff_read2 (asym->section_number); coff_sym->name = name; - coff_sym->address = (coff_read4 (asym->value) - + sects[secnum - 1].virtual_address - + base_address); + coff_sym->address = + libbacktrace_add_base ((coff_read4 (asym->value) + + sects[secnum - 1].virtual_address), + base_address); coff_sym++; } @@ -580,7 +634,8 @@ coff_syminfo (struct backtrace_state *state, uintptr_t addr, static int coff_add (struct backtrace_state *state, int descriptor, backtrace_error_callback error_callback, void *data, - fileline *fileline_fn, int *found_sym, int *found_dwarf) + fileline *fileline_fn, int *found_sym, int *found_dwarf, + uintptr_t module_handle ATTRIBUTE_UNUSED) { struct backtrace_view fhdr_view; off_t fhdr_off; @@ -609,7 +664,8 @@ coff_add (struct backtrace_state *state, int descriptor, struct backtrace_view debug_view; int debug_view_valid; int is_64; - uintptr_t image_base; + struct libbacktrace_base_address image_base; + struct libbacktrace_base_address base_address; struct dwarf_sections dwarf_sections; *found_sym = 0; @@ -648,7 +704,7 @@ coff_add (struct backtrace_state *state, int descriptor, magic_ok = memcmp (magic, "PE\0", 4) == 0; fhdr_off += 4; - memcpy (&fhdr, fhdr_view.data + 4, sizeof fhdr); + memcpy (&fhdr, (const unsigned char *) fhdr_view.data + 4, sizeof fhdr); } else { @@ -682,16 +738,17 @@ coff_add (struct backtrace_state *state, int descriptor, sects_view_valid = 1; opt_hdr = (const b_coff_optional_header *) sects_view.data; sects = (const b_coff_section_header *) - (sects_view.data + fhdr.size_of_optional_header); + ((const unsigned char *) sects_view.data + fhdr.size_of_optional_header); is_64 = 0; + memset (&image_base, 0, sizeof image_base); if (fhdr.size_of_optional_header > sizeof (*opt_hdr)) { if (opt_hdr->magic == PE_MAGIC) - image_base = opt_hdr->u.pe.image_base; + image_base.m = opt_hdr->u.pe.image_base; else if (opt_hdr->magic == PEP_MAGIC) { - image_base = opt_hdr->u.pep.image_base; + image_base.m = opt_hdr->u.pep.image_base; is_64 = 1; } else @@ -700,8 +757,6 @@ coff_add (struct backtrace_state *state, int descriptor, goto fail; } } - else - image_base = 0; /* Read the symbol table and the string table. */ @@ -726,7 +781,8 @@ coff_add (struct backtrace_state *state, int descriptor, goto fail; syms_view_valid = 1; - str_size = coff_read4 (syms_view.data + syms_size); + str_size = coff_read4 ((const unsigned char *) syms_view.data + + syms_size); str_off = syms_off + syms_size; @@ -856,7 +912,12 @@ coff_add (struct backtrace_state *state, int descriptor, + (sections[i].offset - min_offset)); } - if (!backtrace_dwarf_add (state, /* base_address */ 0, &dwarf_sections, + memset (&base_address, 0, sizeof base_address); +#ifdef HAVE_WINDOWS_H + base_address.m = module_handle - image_base.m; +#endif + + if (!backtrace_dwarf_add (state, base_address, &dwarf_sections, 0, /* FIXME: is_bigendian */ NULL, /* altlink */ error_callback, data, fileline_fn, @@ -881,6 +942,53 @@ coff_add (struct backtrace_state *state, int descriptor, return 0; } +#ifdef HAVE_WINDOWS_H +struct dll_notification_context +{ + struct backtrace_state *state; + backtrace_error_callback error_callback; + void *data; +}; + +static VOID CALLBACK +dll_notification (ULONG reason, + struct dll_notification_data *notification_data, + PVOID context) +{ + char module_name[MAX_PATH]; + int descriptor; + struct dll_notification_context* dll_context = + (struct dll_notification_context*) context; + struct backtrace_state *state = dll_context->state; + void *data = dll_context->data; + backtrace_error_callback error_callback = dll_context->data; + fileline fileline; + int found_sym; + int found_dwarf; + HMODULE module_handle; + + if (reason != LDR_DLL_NOTIFICATION_REASON_LOADED) + return; + + if (!GetModuleHandleExW ((GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS + | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT), + (wchar_t*) notification_data->dll_base, + &module_handle)) + return; + + if (!GetModuleFileNameA ((HMODULE) module_handle, module_name, MAX_PATH - 1)) + return; + + descriptor = backtrace_open (module_name, error_callback, data, NULL); + + if (descriptor < 0) + return; + + coff_add (state, descriptor, error_callback, data, &fileline, &found_sym, + &found_dwarf, (uintptr_t) module_handle); +} +#endif /* defined(HAVE_WINDOWS_H) */ + /* Initialize the backtrace data we need from an ELF executable. At the ELF level, all we need to do is find the debug info sections. */ @@ -895,12 +1003,92 @@ backtrace_initialize (struct backtrace_state *state, int found_sym; int found_dwarf; fileline coff_fileline_fn; + uintptr_t module_handle = 0; +#ifdef HAVE_TLHELP32_H + fileline module_fileline_fn; + int module_found_sym; + HANDLE snapshot; +#endif + +#ifdef HAVE_WINDOWS_H + HMODULE nt_dll_handle; + + module_handle = (uintptr_t) GetModuleHandle (NULL); +#endif ret = coff_add (state, descriptor, error_callback, data, - &coff_fileline_fn, &found_sym, &found_dwarf); + &coff_fileline_fn, &found_sym, &found_dwarf, module_handle); if (!ret) return 0; +#ifdef HAVE_TLHELP32_H + do + { + snapshot = CreateToolhelp32Snapshot (TH32CS_SNAPMODULE, 0); + } + while (snapshot == INVALID_HANDLE_VALUE + && GetLastError () == ERROR_BAD_LENGTH); + + if (snapshot != INVALID_HANDLE_VALUE) + { + MODULEENTRY32 entry; + BOOL ok; + entry.dwSize = sizeof (MODULEENTRY32); + + for (ok = Module32First (snapshot, &entry); ok; ok = Module32Next (snapshot, &entry)) + { + if (strcmp (filename, entry.szExePath) == 0) + continue; + + module_handle = (uintptr_t) entry.hModule; + if (module_handle == 0) + continue; + + descriptor = backtrace_open (entry.szExePath, error_callback, data, + NULL); + if (descriptor < 0) + continue; + + coff_add (state, descriptor, error_callback, data, + &module_fileline_fn, &module_found_sym, &found_dwarf, + module_handle); + if (module_found_sym) + found_sym = 1; + } + + CloseHandle (snapshot); + } +#endif + +#ifdef HAVE_WINDOWS_H + nt_dll_handle = GetModuleHandleW (L"ntdll.dll"); + if (nt_dll_handle) + { + LDR_REGISTER_FUNCTION register_func; + const char register_name[] = "LdrRegisterDllNotification"; + register_func = (void*) GetProcAddress (nt_dll_handle, + register_name); + + if (register_func) + { + PVOID cookie; + struct dll_notification_context *context + = backtrace_alloc (state, + sizeof (struct dll_notification_context), + error_callback, data); + + if (context) + { + context->state = state; + context->data = data; + context->error_callback = error_callback; + + register_func (0, &dll_notification, context, &cookie); + } + } + } +#endif /* defined(HAVE_WINDOWS_H) */ + if (!state->threaded) { if (found_sym) diff --git a/thirdparty/libbacktrace/posix.c b/thirdparty/libbacktrace/posix.c index 924631d2e61..79f4950f84b 100644 --- a/thirdparty/libbacktrace/posix.c +++ b/thirdparty/libbacktrace/posix.c @@ -1,5 +1,5 @@ /* posix.c -- POSIX file I/O routines for the backtrace library. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/print.c b/thirdparty/libbacktrace/print.c index 93d0d3abb49..d4637af9a4f 100644 --- a/thirdparty/libbacktrace/print.c +++ b/thirdparty/libbacktrace/print.c @@ -1,5 +1,5 @@ /* print.c -- Print the current backtrace. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without @@ -47,22 +47,6 @@ struct print_data FILE *f; }; -/* Print one level of a backtrace. */ - -static int -print_callback (void *data, uintptr_t pc, const char *filename, int lineno, - const char *function) -{ - struct print_data *pdata = (struct print_data *) data; - - fprintf (pdata->f, "0x%lx %s\n\t%s:%d\n", - (unsigned long) pc, - function == NULL ? "???" : function, - filename == NULL ? "???" : filename, - lineno); - return 0; -} - /* Print errors to stderr. */ static void @@ -78,6 +62,47 @@ error_callback (void *data, const char *msg, int errnum) fputc ('\n', stderr); } +/* Print one level of a backtrace if we couldn't get a file or function name. + Use syminfo to try to get a symbol name. */ + +static void print_syminfo_callback (void *data, uintptr_t pc, + const char *symname, uintptr_t symval, + uintptr_t symsize ATTRIBUTE_UNUSED) +{ + struct print_data *pdata = (struct print_data *) data; + + if (symname == NULL) + fprintf (pdata->f, "0x%lx ???\n\t???:0\n", (unsigned long) pc); + else + fprintf (pdata->f, "0x%lx ???\n\t%s+0x%lx:0\n", + (unsigned long) pc, + symname, + (unsigned long) (pc - symval)); +} + +/* Print one level of a backtrace. */ + +static int +print_callback (void *data, uintptr_t pc, const char *filename, int lineno, + const char *function) +{ + struct print_data *pdata = (struct print_data *) data; + + if (function == NULL && filename == NULL) + { + backtrace_syminfo (pdata->state, pc, print_syminfo_callback, + error_callback, data); + return 0; + } + + fprintf (pdata->f, "0x%lx %s\n\t%s:%d\n", + (unsigned long) pc, + function == NULL ? "???" : function, + filename == NULL ? "???" : filename, + lineno); + return 0; +} + /* Print a backtrace. */ void __attribute__((noinline)) diff --git a/thirdparty/libbacktrace/read.c b/thirdparty/libbacktrace/read.c index f5e01f01b0b..9f6997c79e0 100644 --- a/thirdparty/libbacktrace/read.c +++ b/thirdparty/libbacktrace/read.c @@ -1,5 +1,5 @@ /* read.c -- File views without mmap. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/simple.c b/thirdparty/libbacktrace/simple.c index 785e726e6be..fd3fac688fa 100644 --- a/thirdparty/libbacktrace/simple.c +++ b/thirdparty/libbacktrace/simple.c @@ -1,5 +1,5 @@ /* simple.c -- The backtrace_simple function. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/sort.c b/thirdparty/libbacktrace/sort.c index a60a980e65e..fedfe21cbdf 100644 --- a/thirdparty/libbacktrace/sort.c +++ b/thirdparty/libbacktrace/sort.c @@ -1,5 +1,5 @@ /* sort.c -- Sort without allocating memory - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without diff --git a/thirdparty/libbacktrace/state.c b/thirdparty/libbacktrace/state.c index 0f368a23907..b564a18b548 100644 --- a/thirdparty/libbacktrace/state.c +++ b/thirdparty/libbacktrace/state.c @@ -1,5 +1,5 @@ /* state.c -- Create the backtrace state. - Copyright (C) 2012-2021 Free Software Foundation, Inc. + Copyright (C) 2012-2024 Free Software Foundation, Inc. Written by Ian Lance Taylor, Google. Redistribution and use in source and binary forms, with or without