This is an archive of the discontinued LLVM Phabricator instance.

[AArch64][X86] Allow 64-bit label differences lower to IMAGE_REL_*_REL32
ClosedPublic

Authored by MaskRay on Jun 18 2021, 11:56 AM.

Details

Summary

IMAGE_REL_ARM64_REL64/IMAGE_REL_AMD64_REL64 do not exist and .quad a - . is
currently not representable.

For instrumentation, .quad a - . is useful representing a cross-section
reference in a metadata section, to allow ELF medium/large code models. The COFF
limitation makes such generic instrumentations inconvenient. I plan to make a
PGO/coverage metadata section field relative in D104556.

Diff Detail

Event Timeline

MaskRay created this revision.Jun 18 2021, 11:56 AM
MaskRay requested review of this revision.Jun 18 2021, 11:56 AM
Herald added a project: Restricted Project. · View Herald TranscriptJun 18 2021, 11:56 AM
mstorsjo accepted this revision.Jun 18 2021, 12:21 PM

Looks ok to me. A PE-COFF image is limited to 32 bits in range anyway, so as long as the target symbol doesn't turn out to be from outside of the image (with mingw automatic dllimport), a 32 bit difference should be enough in all cases.

This revision is now accepted and ready to land.Jun 18 2021, 12:21 PM
MaskRay added a comment.EditedJun 18 2021, 12:38 PM

I think the main problem is when the value is negative. How to represent it?

For D104556 compiler-rt/lib/profile/InstrProfilingMerge.c I just truncate Header->CountersDelta to 32-bit for COFF.

This revision was landed with ongoing or failed builds.Jun 21 2021, 2:32 PM
This revision was automatically updated to reflect the committed changes.
rnk added a comment.Jun 21 2021, 2:44 PM

I was going to say, I wonder if it would be better to find a way to put the extension in IR instead of in the assembler. For example, maybe the IR could look like (pseudo-IR):
zext i64 (trunc i32 (sub i64 (ptrtoint i64 @label2)), (ptrtoint i64 @label1))))
So that would slot into the constant inititalizer, and the backend would know to emit that pattern as:

.long 0
.long label2 - label1

Now that I've written it out, it seems worse and more complex. Let's go with .quad I guess.

I was going to say, I wonder if it would be better to find a way to put the extension in IR instead of in the assembler. For example, maybe the IR could look like (pseudo-IR):
zext i64 (trunc i32 (sub i64 (ptrtoint i64 @label2)), (ptrtoint i64 @label1))))
So that would slot into the constant inititalizer, and the backend would know to emit that pattern as:

.long 0
.long label2 - label1

Now that I've written it out, it seems worse and more complex. Let's go with .quad I guess.

Thanks!

The IR approach would mean every new relative metadata usage needs to be different for COFF and non-COFF.
Label differences are probably not that common today but may get more uses in the future, e.g. https://lists.llvm.org/pipermail/llvm-dev/2021-June/151198.html