www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.bugs - [Issue 22483] New: DMD generates invalid string sections that work

https://issues.dlang.org/show_bug.cgi?id=22483

          Issue ID: 22483
           Summary: DMD generates invalid string sections that work by
                    coincidence
           Product: D
           Version: D2
          Hardware: x86_64
                OS: Linux
            Status: NEW
          Severity: enhancement
          Priority: P1
         Component: dmd
          Assignee: nobody puremagic.com
          Reporter: default_357-line yahoo.de

See https://github.com/rui314/mold/issues/126

DMD generates .rodata.str1.1 string sections (for char[] strings) with a
sh_entsize of 0, when it should be 1. Linkers apparently react to this by not
treating the section as mergeable at all.

You can confirm this:

```
echo 'string foo() { return "Hello World"; }' > a.d
echo 'string bar() { return "Hello World"; }' > b.d
echo 'import a, b; void main() { assert(foo.ptr is bar.ptr); }' > c.d

dmd a.d -c -ofa.o
dmd b.d -c -ofb.o
dmd a.o b.o c.d -ofstrsectiontest

./strsectiontest
```

Patch:

```
diff --git a/src/dmd/backend/elfobj.d b/src/dmd/backend/elfobj.d
index b555b01e0..02e888e8d 100644
--- a/src/dmd/backend/elfobj.d
+++ b/src/dmd/backend/elfobj.d
   -630,6 +630,7    int ElfObj_string_literal_segment(uint sz)
     const int i = (sz == 4) ? 2 : sz - 1;
     const IDXSEC seg =
         ElfObj_getsegment(".rodata.str".ptr, name[i].ptr, SHT_PROGBITS,
SHF_ALLOC | SHF_MERGE | SHF_STRINGS, sz);
+    MAP_SEG2SEC(seg).sh_entsize = sz;
     return seg;
 }

```

But with this applied, DMD generates invalid revocations:

/usr/bin/ld: a.o: access beyond end of merged section (-4)
/usr/bin/ld: b.o: access beyond end of merged section (-4)
/usr/bin/ld: strsectiontest.o: access beyond end of merged section (-4)

Afaics, the revocations were always invalid, but section merging didn't happen
for the .rodata.str, so we didn't notice. How to fix that is beyond me though.

--
Nov 04 2021