aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdhemerval Zanella <adhemerval.zanella@linaro.org>2025-03-04 11:39:30 -0300
committerAdhemerval Zanella <adhemerval.zanella@linaro.org>2025-03-07 08:48:50 -0300
commit03b4f972f3f509d2d39c1126830811180ed66359 (patch)
treed1ab97636cfec956f2d5fcebc6be3497d395c7e6
parent6f5e2c066bac9ad51d89f159925f9760423be2f7 (diff)
downloadbinutils-azanella/pt_gnu_mutable.zip
binutils-azanella/pt_gnu_mutable.tar.gz
binutils-azanella/pt_gnu_mutable.tar.bz2
elf: Add PT_GNU_MUTABLEazanella/pt_gnu_mutable
The section mark a memory region that should not be sealed if GNU_PROPERTY_MEMORY_SEAL attribute is present. PT_GNU_MUTABLE section names start with ".gnu.mutable" and are maximum page aligned and have a size of maximum page size. For instance the code: unsigned char mutable_array1[64] __attribute__ ((section (GNU_MUTABLE_SECTION_NAME))) = { 0 }; unsigned char mutable_array2[32] __attribute__ ((section (GNU_MUTABLE_SECTION_NAME))) = { 0 }; places both 'mutable_array1' and 'mutable_array2' on a page aligned memory region in a size of a page (the alignment and size can be change with -Wl,-z,max-page-size= linker option). The linker sets the alignment and size to make it easier to loader to avoid sealing the area (since mseal only work on multiple of page size areas), and to simplify the userland process to change protection of either seal the area after initialization. Change-Id: I1304af9ec6b5b2682a1416b2b3d8d5b2c65b9f1c TODO: add tests.
-rw-r--r--bfd/elf.c29
-rw-r--r--binutils/readelf.c1
-rw-r--r--include/elf/common.h4
-rw-r--r--ld/ldgram.y2
-rw-r--r--ld/scripttempl/elf.sc8
-rw-r--r--ld/testsuite/ld-aarch64/variant_pcs-r.d95
-rw-r--r--ld/testsuite/ld-x86-64/pr27590.rd6
-rw-r--r--ld/testsuite/ld-x86-64/split-by-file.rd13
8 files changed, 101 insertions, 57 deletions
diff --git a/bfd/elf.c b/bfd/elf.c
index 3f8bc83..d3ef9dd 100644
--- a/bfd/elf.c
+++ b/bfd/elf.c
@@ -1434,6 +1434,7 @@ get_segment_type (unsigned int p_type)
case PT_GNU_STACK: pt = "STACK"; break;
case PT_GNU_RELRO: pt = "RELRO"; break;
case PT_GNU_SFRAME: pt = "SFRAME"; break;
+ case PT_GNU_MUTABLE: pt = "MUTABLE"; break;
default: pt = NULL; break;
}
return pt;
@@ -3416,6 +3417,9 @@ bfd_section_from_phdr (bfd *abfd, Elf_Internal_Phdr *hdr, int hdr_index)
return _bfd_elf_make_section_from_phdr (abfd, hdr, hdr_index,
"sframe");
+ case PT_GNU_MUTABLE:
+ return _bfd_elf_make_section_from_phdr (abfd, hdr, hdr_index, "mutable");
+
default:
/* Check for any processor-specific program segment types. */
bed = get_elf_backend_data (abfd);
@@ -4766,6 +4770,13 @@ get_program_header_size (bfd *abfd, struct bfd_link_info *info)
++segs;
}
+ s = bfd_get_section_by_name (abfd, GNU_MUTABLE_SECTION_NAME);
+ if (s != NULL)
+ {
+ /* We need a PT_GNU_MUTABLE segment. */
+ ++segs;
+ }
+
s = bfd_get_section_by_name (abfd,
NOTE_GNU_PROPERTY_SECTION_NAME);
if (s != NULL && s->size != 0)
@@ -5032,6 +5043,7 @@ _bfd_elf_map_sections_to_segments (bfd *abfd,
asection *first_mbind = NULL;
asection *dynsec, *eh_frame_hdr;
asection *sframe;
+ asection *mutabledata;
size_t amt;
bfd_vma addr_mask, wrap_to = 0; /* Bytes. */
bfd_size_type phdr_size; /* Octets/bytes. */
@@ -5571,6 +5583,23 @@ _bfd_elf_map_sections_to_segments (bfd *abfd,
pm = &m->next;
}
+ mutabledata = bfd_get_section_by_name (abfd,
+ GNU_MUTABLE_SECTION_NAME);
+ if (mutabledata != NULL && (mutabledata->flags & SEC_LOAD) != 0)
+ {
+ amt = sizeof (struct elf_segment_map);
+ m = bfd_zalloc (abfd, amt);
+ if (m == NULL)
+ goto error_return;
+ m->next = NULL;
+ m->p_type = PT_GNU_MUTABLE;
+ m->count = 1;
+ m->sections[0] = mutabledata->output_section;
+
+ *pm = m;
+ pm = &m->next;
+ }
+
if (info != NULL && info->relro)
{
for (m = mfirst; m != NULL; m = m->next)
diff --git a/binutils/readelf.c b/binutils/readelf.c
index dd1871d..b1f4d5c 100644
--- a/binutils/readelf.c
+++ b/binutils/readelf.c
@@ -5483,6 +5483,7 @@ get_os_specific_segment_type (Filedata * filedata, unsigned long p_type)
case PT_GNU_RELRO: return "GNU_RELRO";
case PT_GNU_PROPERTY: return "GNU_PROPERTY";
case PT_GNU_SFRAME: return "GNU_SFRAME";
+ case PT_GNU_MUTABLE: return "GNU_MUTABLE";
case PT_OPENBSD_MUTABLE: return "OPENBSD_MUTABLE";
case PT_OPENBSD_RANDOMIZE: return "OPENBSD_RANDOMIZE";
diff --git a/include/elf/common.h b/include/elf/common.h
index fd032d1..4e68f2c 100644
--- a/include/elf/common.h
+++ b/include/elf/common.h
@@ -511,6 +511,9 @@
#define PT_GNU_MBIND_LO (PT_LOOS + 0x474e555)
#define PT_GNU_MBIND_HI (PT_GNU_MBIND_LO + PT_GNU_MBIND_NUM - 1)
+/* Memory sealing mutable section */
+#define PT_GNU_MUTABLE (PT_GNU_MBIND_HI + 1) /* Mutable section. */
+
#define PT_LOPROC 0x70000000 /* Processor-specific */
#define PT_HIPROC 0x7FFFFFFF /* Processor-specific */
@@ -887,6 +890,7 @@
#define NOTE_GNU_PROPERTY_SECTION_NAME ".note.gnu.property"
#define GNU_BUILD_ATTRS_SECTION_NAME ".gnu.build.attributes"
+#define GNU_MUTABLE_SECTION_NAME ".gnu.mutable"
/* Values used in GNU .note.gnu.property notes (NT_GNU_PROPERTY_TYPE_0). */
#define GNU_PROPERTY_STACK_SIZE 1
diff --git a/ld/ldgram.y b/ld/ldgram.y
index 6635e59..cbeff7f 100644
--- a/ld/ldgram.y
+++ b/ld/ldgram.y
@@ -1312,6 +1312,8 @@ phdr_type:
$$ = exp_intop (0x6474e552);
else if (strcmp (s, "PT_GNU_PROPERTY") == 0)
$$ = exp_intop (0x6474e553);
+ else if (strcmp (s, "PT_GNU_MUTABLE") == 0)
+ $$ = exp_intop (0x6474f555);
else
{
einfo (_("\
diff --git a/ld/scripttempl/elf.sc b/ld/scripttempl/elf.sc
index be8d19f..5eadc18 100644
--- a/ld/scripttempl/elf.sc
+++ b/ld/scripttempl/elf.sc
@@ -244,7 +244,7 @@ RELA_IPLT=".rela.iplt ${RELOCATING-0} :
DYNAMIC=".dynamic ${RELOCATING-0} : { *(.dynamic) }"
RODATA=".${RODATA_NAME} ${RELOCATING-0} : { *(.${RODATA_NAME}${RELOCATING+ .${RODATA_NAME}.* .gnu.linkonce.r.*}) }"
DATARELRO=".data.rel.ro : { *(.data.rel.ro.local* .gnu.linkonce.d.rel.ro.local.*) *(.data.rel.ro .data.rel.ro.* .gnu.linkonce.d.rel.ro.*) }"
-DISCARDED="/DISCARD/ : { *(.note.GNU-stack) *(.gnu_debuglink) *(.gnu.lto_*) *(.gnu_object_only) }"
+DISCARDED="/DISCARD/ : { *(.note.GNU-stack) *(.gnu_debuglink) *(.gnu.lto_*) *(.gnu_object_only) *(.gnu.mutable) }"
if test -z "${NO_SMALL_DATA}"; then
SBSS=".${SBSS_NAME} ${RELOCATING-0} :
{
@@ -855,6 +855,12 @@ cat <<EOF
${DATA_SDATA-${SDATA}}
${DATA_SDATA-${OTHER_SDATA_SECTIONS}}
+ .gnu.mutable ${RELOCATING-0} : ${RELOCATING+ALIGN(${MAXPAGESIZE})}
+ {
+ *(.gnu.mutable)
+ . = ALIGN(. != 0 ? CONSTANT (MAXPAGESIZE): 1);
+ }
+
${RELOCATING+${SYMBOL_ABI_ALIGNMENT+. = ALIGN(${SYMBOL_ABI_ALIGNMENT});}}
${RELOCATING+${DATA_END_SYMBOLS-${CREATE_SHLIB+PROVIDE (}$(def_symbol "_edata")${CREATE_SHLIB+)};
PROVIDE ($(def_symbol "edata"));}}
diff --git a/ld/testsuite/ld-aarch64/variant_pcs-r.d b/ld/testsuite/ld-aarch64/variant_pcs-r.d
index 2651a68..25b8000 100644
--- a/ld/testsuite/ld-aarch64/variant_pcs-r.d
+++ b/ld/testsuite/ld-aarch64/variant_pcs-r.d
@@ -5,56 +5,57 @@
Relocation section '\.rela\.text' at offset .* contains 24 entries:
Offset Info Type Symbol's Value Symbol's Name \+ Addend
-0000000000000000 000000180000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_def \+ 0
-0000000000000004 000000110000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_undef \+ 0
-0000000000000008 000000120000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_hidden_def \+ 0
-0000000000000010 000000170000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_def \+ 0
-0000000000000014 000000100000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_undef \+ 0
-0000000000000018 000000150000011b R_AARCH64_CALL26 0000000000000000 f_base_global_hidden_def \+ 0
-0000000000000020 000000140000011b R_AARCH64_CALL26 f_spec_global_default_ifunc\(\) f_spec_global_default_ifunc \+ 0
-0000000000000024 000000160000011b R_AARCH64_CALL26 f_spec_global_hidden_ifunc\(\) f_spec_global_hidden_ifunc \+ 0
-0000000000000028 000000060000011b R_AARCH64_CALL26 f_spec_local_ifunc\(\) f_spec_local_ifunc \+ 0
-000000000000002c 000000190000011b R_AARCH64_CALL26 f_base_global_default_ifunc\(\) f_base_global_default_ifunc \+ 0
-0000000000000030 000000130000011b R_AARCH64_CALL26 f_base_global_hidden_ifunc\(\) f_base_global_hidden_ifunc \+ 0
-0000000000000034 000000070000011b R_AARCH64_CALL26 f_base_local_ifunc\(\) f_base_local_ifunc \+ 0
-0000000000000038 000000180000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_def \+ 0
-000000000000003c 000000110000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_undef \+ 0
-0000000000000040 000000120000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_hidden_def \+ 0
-0000000000000048 000000170000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_def \+ 0
-000000000000004c 000000100000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_undef \+ 0
-0000000000000050 000000150000011b R_AARCH64_CALL26 0000000000000000 f_base_global_hidden_def \+ 0
-0000000000000058 000000140000011b R_AARCH64_CALL26 f_spec_global_default_ifunc\(\) f_spec_global_default_ifunc \+ 0
-000000000000005c 000000160000011b R_AARCH64_CALL26 f_spec_global_hidden_ifunc\(\) f_spec_global_hidden_ifunc \+ 0
-0000000000000060 0000000c0000011b R_AARCH64_CALL26 f_spec_local2_ifunc\(\) f_spec_local2_ifunc \+ 0
-0000000000000064 000000190000011b R_AARCH64_CALL26 f_base_global_default_ifunc\(\) f_base_global_default_ifunc \+ 0
-0000000000000068 000000130000011b R_AARCH64_CALL26 f_base_global_hidden_ifunc\(\) f_base_global_hidden_ifunc \+ 0
-000000000000006c 0000000d0000011b R_AARCH64_CALL26 f_base_local2_ifunc\(\) f_base_local2_ifunc \+ 0
+0000000000000000 000000190000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_def \+ 0
+0000000000000004 000000120000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_undef \+ 0
+0000000000000008 000000130000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_hidden_def \+ 0
+0000000000000010 000000180000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_def \+ 0
+0000000000000014 000000110000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_undef \+ 0
+0000000000000018 000000160000011b R_AARCH64_CALL26 0000000000000000 f_base_global_hidden_def \+ 0
+0000000000000020 000000150000011b R_AARCH64_CALL26 f_spec_global_default_ifunc\(\) f_spec_global_default_ifunc \+ 0
+0000000000000024 000000170000011b R_AARCH64_CALL26 f_spec_global_hidden_ifunc\(\) f_spec_global_hidden_ifunc \+ 0
+0000000000000028 000000070000011b R_AARCH64_CALL26 f_spec_local_ifunc\(\) f_spec_local_ifunc \+ 0
+000000000000002c 0000001a0000011b R_AARCH64_CALL26 f_base_global_default_ifunc\(\) f_base_global_default_ifunc \+ 0
+0000000000000030 000000140000011b R_AARCH64_CALL26 f_base_global_hidden_ifunc\(\) f_base_global_hidden_ifunc \+ 0
+0000000000000034 000000080000011b R_AARCH64_CALL26 f_base_local_ifunc\(\) f_base_local_ifunc \+ 0
+0000000000000038 000000190000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_def \+ 0
+000000000000003c 000000120000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_default_undef \+ 0
+0000000000000040 000000130000011b R_AARCH64_CALL26 0000000000000000 f_spec_global_hidden_def \+ 0
+0000000000000048 000000180000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_def \+ 0
+000000000000004c 000000110000011b R_AARCH64_CALL26 0000000000000000 f_base_global_default_undef \+ 0
+0000000000000050 000000160000011b R_AARCH64_CALL26 0000000000000000 f_base_global_hidden_def \+ 0
+0000000000000058 000000150000011b R_AARCH64_CALL26 f_spec_global_default_ifunc\(\) f_spec_global_default_ifunc \+ 0
+000000000000005c 000000170000011b R_AARCH64_CALL26 f_spec_global_hidden_ifunc\(\) f_spec_global_hidden_ifunc \+ 0
+0000000000000060 0000000d0000011b R_AARCH64_CALL26 f_spec_local2_ifunc\(\) f_spec_local2_ifunc \+ 0
+0000000000000064 0000001a0000011b R_AARCH64_CALL26 f_base_global_default_ifunc\(\) f_base_global_default_ifunc \+ 0
+0000000000000068 000000140000011b R_AARCH64_CALL26 f_base_global_hidden_ifunc\(\) f_base_global_hidden_ifunc \+ 0
+000000000000006c 0000000e0000011b R_AARCH64_CALL26 f_base_local2_ifunc\(\) f_base_local2_ifunc \+ 0
-Symbol table '\.symtab' contains 26 entries:
+Symbol table '\.symtab' contains 27 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 0000000000000000 0 NOTYPE LOCAL DEFAULT UND
1: 0000000000000000 0 SECTION LOCAL DEFAULT 1.*
2: 0000000000000000 0 SECTION LOCAL DEFAULT 3.*
3: 0000000000000000 0 SECTION LOCAL DEFAULT 4.*
- 4: 0000000000000000 0 FILE LOCAL DEFAULT ABS .*variant_pcs-1\.o
- 5: 0000000000000000 0 NOTYPE LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local
- 6: 0000000000000000 0 IFUNC LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local_ifunc
- 7: 0000000000000000 0 IFUNC LOCAL DEFAULT 1 f_base_local_ifunc
- 8: 0000000000000000 0 NOTYPE LOCAL DEFAULT 1 f_base_local
- 9: 0000000000000000 0 NOTYPE LOCAL DEFAULT 1 \$x
- 10: 0000000000000000 0 FILE LOCAL DEFAULT ABS .*variant_pcs-2\.o
- 11: 0000000000000038 0 NOTYPE LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local2
- 12: 0000000000000038 0 IFUNC LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local2_ifunc
- 13: 0000000000000038 0 IFUNC LOCAL DEFAULT 1 f_base_local2_ifunc
- 14: 0000000000000038 0 NOTYPE LOCAL DEFAULT 1 f_base_local2
- 15: 0000000000000038 0 NOTYPE LOCAL DEFAULT 1 \$x
- 16: 0000000000000000 0 NOTYPE GLOBAL DEFAULT UND f_base_global_default_undef
- 17: 0000000000000000 0 NOTYPE GLOBAL DEFAULT \[VARIANT_PCS\] UND f_spec_global_default_undef
- 18: 0000000000000000 0 NOTYPE GLOBAL HIDDEN \[VARIANT_PCS\] 1 f_spec_global_hidden_def
- 19: 0000000000000000 0 IFUNC GLOBAL HIDDEN 1 f_base_global_hidden_ifunc
- 20: 0000000000000000 0 IFUNC GLOBAL DEFAULT \[VARIANT_PCS\] 1 f_spec_global_default_ifunc
- 21: 0000000000000000 0 NOTYPE GLOBAL HIDDEN 1 f_base_global_hidden_def
- 22: 0000000000000000 0 IFUNC GLOBAL HIDDEN \[VARIANT_PCS\] 1 f_spec_global_hidden_ifunc
- 23: 0000000000000000 0 NOTYPE GLOBAL DEFAULT 1 f_base_global_default_def
- 24: 0000000000000000 0 NOTYPE GLOBAL DEFAULT \[VARIANT_PCS\] 1 f_spec_global_default_def
- 25: 0000000000000000 0 IFUNC GLOBAL DEFAULT 1 f_base_global_default_ifunc
+ 4: 0000000000000000 0 SECTION LOCAL DEFAULT 5.*
+ 5: 0000000000000000 0 FILE LOCAL DEFAULT ABS .*variant_pcs-1\.o
+ 6: 0000000000000000 0 NOTYPE LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local
+ 7: 0000000000000000 0 IFUNC LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local_ifunc
+ 8: 0000000000000000 0 IFUNC LOCAL DEFAULT 1 f_base_local_ifunc
+ 9: 0000000000000000 0 NOTYPE LOCAL DEFAULT 1 f_base_local
+ 10: 0000000000000000 0 NOTYPE LOCAL DEFAULT 1 \$x
+ 11: 0000000000000000 0 FILE LOCAL DEFAULT ABS .*variant_pcs-2\.o
+ 12: 0000000000000038 0 NOTYPE LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local2
+ 13: 0000000000000038 0 IFUNC LOCAL DEFAULT \[VARIANT_PCS\] 1 f_spec_local2_ifunc
+ 14: 0000000000000038 0 IFUNC LOCAL DEFAULT 1 f_base_local2_ifunc
+ 15: 0000000000000038 0 NOTYPE LOCAL DEFAULT 1 f_base_local2
+ 16: 0000000000000038 0 NOTYPE LOCAL DEFAULT 1 \$x
+ 17: 0000000000000000 0 NOTYPE GLOBAL DEFAULT UND f_base_global_default_undef
+ 18: 0000000000000000 0 NOTYPE GLOBAL DEFAULT \[VARIANT_PCS\] UND f_spec_global_default_undef
+ 19: 0000000000000000 0 NOTYPE GLOBAL HIDDEN \[VARIANT_PCS\] 1 f_spec_global_hidden_def
+ 20: 0000000000000000 0 IFUNC GLOBAL HIDDEN 1 f_base_global_hidden_ifunc
+ 21: 0000000000000000 0 IFUNC GLOBAL DEFAULT \[VARIANT_PCS\] 1 f_spec_global_default_ifunc
+ 22: 0000000000000000 0 NOTYPE GLOBAL HIDDEN 1 f_base_global_hidden_def
+ 23: 0000000000000000 0 IFUNC GLOBAL HIDDEN \[VARIANT_PCS\] 1 f_spec_global_hidden_ifunc
+ 24: 0000000000000000 0 NOTYPE GLOBAL DEFAULT 1 f_base_global_default_def
+ 25: 0000000000000000 0 NOTYPE GLOBAL DEFAULT \[VARIANT_PCS\] 1 f_spec_global_default_def
+ 26: 0000000000000000 0 IFUNC GLOBAL DEFAULT 1 f_base_global_default_ifunc
diff --git a/ld/testsuite/ld-x86-64/pr27590.rd b/ld/testsuite/ld-x86-64/pr27590.rd
index 55ed17d..5c5710d 100644
--- a/ld/testsuite/ld-x86-64/pr27590.rd
+++ b/ld/testsuite/ld-x86-64/pr27590.rd
@@ -1,11 +1,11 @@
#...
\[[ 0-9]+\] .gnu.debuglto_.debug_info PROGBITS +0+ [0-9a-f]+ 0+42 00 +E 0 +0 1
- \[[ 0-9]+\] .rela.gnu.debuglto_.debug_info RELA +0+ [0-9a-f]+ 0+f0 18 +I 26 17 8
+ \[[ 0-9]+\] .rela.gnu.debuglto_.debug_info RELA +0+ [0-9a-f]+ 0+f0 18 +I 27 18 8
\[[ 0-9]+\] .gnu.debuglto_.debug_abbrev PROGBITS +0+ [0-9a-f]+ 0+26 00 +E 0 +0 1
\[[ 0-9]+\] .gnu.debuglto_.debug_macro PROGBITS +0+ [0-9a-f]+ 0+2a 00 +E 0 +0 1
- \[[ 0-9]+\] .rela.gnu.debuglto_.debug_macro RELA +0+ [0-9a-f]+ 0+60 18 +I 26 20 8
+ \[[ 0-9]+\] .rela.gnu.debuglto_.debug_macro RELA +0+ [0-9a-f]+ 0+60 18 +I 27 21 8
\[[ 0-9]+\] .gnu.debuglto_.debug_macro PROGBITS +0+ [0-9a-f]+ 0+10 00 GE 0 +0 1
- \[[ 0-9]+\] .rela.gnu.debuglto_.debug_macro RELA +0+ [0-9a-f]+ 0+30 18 IG 26 22 8
+ \[[ 0-9]+\] .rela.gnu.debuglto_.debug_macro RELA +0+ [0-9a-f]+ 0+30 18 IG 27 23 8
\[[ 0-9]+\] .gnu.debuglto_.debug_line PROGBITS +0+ [0-9a-f]+ 0+8a 00 +E 0 +0 1
\[[ 0-9]+\] .gnu.debuglto_.debug_str PROGBITS +0+ [0-9a-f]+ 0+15c 01 MSE 0 +0 1
#pass
diff --git a/ld/testsuite/ld-x86-64/split-by-file.rd b/ld/testsuite/ld-x86-64/split-by-file.rd
index 4e3e74a..7f9b732 100644
--- a/ld/testsuite/ld-x86-64/split-by-file.rd
+++ b/ld/testsuite/ld-x86-64/split-by-file.rd
@@ -1,4 +1,4 @@
-There are 9 section headers, starting at offset .*:
+There are 10 section headers, starting at offset .*:
Section Headers:
\[Nr\] Name Type Address Off Size ES Flg Lk Inf Al
@@ -6,10 +6,11 @@ Section Headers:
\[ 1\] .text PROGBITS 0000000000000000 000040 000000 00 AX 0 0 1
\[ 2\] .foo PROGBITS 0000000000000000 000040 000003 00 AXl 0 0 1
\[ 3\] .data PROGBITS 0000000000000000 000043 000000 00 WA 0 0 1
- \[ 4\] .bss NOBITS 0000000000000000 000043 000000 00 WA 0 0 1
- \[ 5\] .foo.0 PROGBITS 0000000000000003 000043 000003 00 AXl 0 0 1
- \[ 6\] .symtab SYMTAB 0000000000000000 [0-9a-f]+ [0-9a-f]+ 18 7 [0-9] 8
- \[ 7\] .strtab STRTAB 0000000000000000 [0-9a-f]+ [0-9a-f]+ 00 0 0 1
- \[ 8\] .shstrtab STRTAB 0000000000000000 [0-9a-f]+ 000038 00 0 0 1
+ \[ 4\] .gnu.mutable PROGBITS 0000000000000000 000043 000000 00 W 0 0 1
+ \[ 5\] .bss NOBITS 0000000000000000 000043 000000 00 WA 0 0 1
+ \[ 6\] .foo.0 PROGBITS 0000000000000003 000043 000003 00 AXl 0 0 1
+ \[ 7\] .symtab SYMTAB 0000000000000000 [0-9a-f]+ [0-9a-f]+ 18 7 [0-9] 8
+ \[ 8\] .strtab STRTAB 0000000000000000 [0-9a-f]+ [0-9a-f]+ 00 0 0 1
+ \[ 9\] .shstrtab STRTAB 0000000000000000 [0-9a-f]+ 000045 00 0 0 1
Key to Flags:
#pass