[ELF][PPC64] Make --power10-stubs/--no-power10-stubs proper aliases for --power10-stubs={auto,no}

This allows --power10-stubs= and --[no-]power10-stubs to override each other
(they are position dependent in GNU ld).

Also improve --help messages and the manpage.

Note: GNU ld's default "auto" mode uses heuristics to decide whether Power10
instructions are used. Arguably it is a design mistake of R_PPC64_REL24_NOTOC
(acked by the relevant folks on a libc-alpha discussion). We don't implement
"auto", so the default --power10-stubs is the same as "yes".
This commit is contained in:
Fangrui Song 2021-11-26 11:51:45 -08:00
parent c2280b5517
commit 3b4dd68de5
6 changed files with 29 additions and 32 deletions

View File

@ -261,7 +261,7 @@ struct Configuration {
UnresolvedPolicy unresolvedSymbols;
UnresolvedPolicy unresolvedSymbolsInShlib;
Target2Policy target2;
bool Power10Stub;
bool power10Stubs;
ARMVFPArgKind armVFPArgs = ARMVFPArgKind::Default;
BuildIdKind buildId = BuildIdKind::None;
SeparateSegmentKind zSeparate;

View File

@ -750,20 +750,6 @@ static OrphanHandlingPolicy getOrphanHandling(opt::InputArgList &args) {
return OrphanHandlingPolicy::Place;
}
// Parses --power10-stubs= flags, to disable or enable Power 10
// instructions in stubs.
static bool getP10StubOpt(opt::InputArgList &args) {
if (args.getLastArgValue(OPT_power10_stubs_eq)== "no")
return false;
if (!args.hasArg(OPT_power10_stubs_eq) &&
args.hasArg(OPT_no_power10_stubs))
return false;
return true;
}
// Parse --build-id or --build-id=<style>. We handle "tree" as a
// synonym for "sha1" because all our hash functions including
// --build-id=sha1 are actually tree hashes for performance reasons.
@ -1190,7 +1176,7 @@ static void readConfigs(opt::InputArgList &args) {
config->zText = getZFlag(args, "text", "notext", true);
config->zWxneeded = hasZOption(args, "wxneeded");
setUnresolvedSymbolPolicy(args);
config->Power10Stub = getP10StubOpt(args);
config->power10Stubs = args.getLastArgValue(OPT_power10_stubs_eq) != "no";
if (opt::Arg *arg = args.getLastArg(OPT_eb, OPT_el)) {
if (arg->getOption().matches(OPT_eb))

View File

@ -454,16 +454,13 @@ def verbose: F<"verbose">, HelpText<"Verbose mode">;
def version: F<"version">, HelpText<"Display the version number and exit">;
def power10_stubs: F<"power10-stubs">, HelpText<"Alias for --power10-stubs=auto">;
def no_power10_stubs: F<"no-power10-stubs">, HelpText<"Alias for --power10-stubs=no">;
def power10_stubs_eq:
J<"power10-stubs=">, HelpText<
"Enables Power10 instructions in all stubs without options, "
"options override previous flags."
"auto: Allow Power10 instructions in stubs if applicable."
"no: No Power10 instructions in stubs.">;
def power10_stubs_eq: JJ<"power10-stubs=">, MetaVarName<"<mode>">,
HelpText<"Whether to use Power10 instructions in call stubs for R_PPC64_REL24_NOTOC and TOC/NOTOC "
"interworking (yes (default): use; no: don't use). \"auto\" is currently the same as \"yes\"">;
def power10_stubs: FF<"power10-stubs">, Alias<power10_stubs_eq>, AliasArgs<["yes"]>,
HelpText<"Alias for --power10-stubs=auto">;
def no_power10_stubs: FF<"no-power10-stubs">, Alias<power10_stubs_eq>, AliasArgs<["no"]>,
HelpText<"Alias for --power10-stubs=no">;
defm version_script: Eq<"version-script", "Read a version script">;

View File

@ -932,7 +932,7 @@ void PPC64R2SaveStub::writeTo(uint8_t *buf) {
write32(buf + 4, 0x48000000 | (offset & 0x03fffffc)); // b <offset>
} else if (isInt<34>(offset)) {
int nextInstOffset;
if (!config->Power10Stub) {
if (!config->power10Stubs) {
uint64_t tocOffset = destination.getVA() - getPPC64TocBase();
if (tocOffset >> 16 > 0) {
const uint64_t addi = ADDI_R12_TO_R12_NO_DISP | (tocOffset & 0xffff);
@ -980,7 +980,7 @@ void PPC64R12SetupStub::writeTo(uint8_t *buf) {
reportRangeError(buf, offset, 34, destination, "R12 setup stub offset");
int nextInstOffset;
if (!config->Power10Stub) {
if (!config->power10Stubs) {
uint32_t off = destination.getVA(addend) - getThunkTargetSym()->getVA() - 8;
write32(buf + 0, 0x7c0802a6); // mflr r12
write32(buf + 4, 0x429f0005); // bcl 20,31,.+4
@ -1013,7 +1013,7 @@ void PPC64PCRelPLTStub::writeTo(uint8_t *buf) {
int nextInstOffset = 0;
int64_t offset = destination.getGotPltVA() - getThunkTargetSym()->getVA();
if (config->Power10Stub) {
if (config->power10Stubs) {
if (!isInt<34>(offset))
reportRangeError(buf, offset, 34, destination,
"PC-relative PLT stub offset");
@ -1068,7 +1068,7 @@ void PPC64PCRelLongBranchThunk::writeTo(uint8_t *buf) {
"PC-relative long branch stub offset");
int nextInstOffset;
if (!config->Power10Stub) {
if (!config->power10Stubs) {
uint32_t off = destination.getVA(addend) - getThunkTargetSym()->getVA() - 8;
write32(buf + 0, 0x7c0802a6); // mflr r12
write32(buf + 4, 0x429f0005); // bcl 20,31,.+4

View File

@ -454,6 +454,20 @@ is specified, use SHT_ANDROID_RELR instead of SHT_RELR.
Always generate position independent thunks.
.It Fl -pie , Fl -pic-executable
Create a position independent executable.
.It Fl -power10-stubs Ns = Ns Cm mode
Whether to use Power10 instructions in call stubs for R_PPC64_REL24_NOTOC and TOC/NOTOC interworking.
.Ar mode
may be:
.Pp
.Bl -tag -width 2n -compact
.It Cm yes
(default) Use.
.It Cm auto
Currently the same as yes.
.It Cm no
Don't use.
.El
.It Fl -print-gc-sections
List removed unused sections.
.It Fl -print-icf-sections

View File

@ -11,12 +11,12 @@
# RUN: llvm-objdump -d --no-show-raw-insn --mcpu=pwr10 %t | FileCheck %s
# RUN: llvm-mc -filetype=obj -triple=powerpc64 %s -o %t.o
# RUN: ld.lld -T %t.script %t.o -o %t
# RUN: ld.lld -T %t.script %t.o -o %t --no-power10-stubs --power10-stubs=yes
# RUN: llvm-readelf -s %t | FileCheck %s --check-prefix=SYMBOL
# RUN: llvm-objdump -d --no-show-raw-insn --mcpu=pwr10 %t | FileCheck %s
# RUN: llvm-mc -filetype=obj -triple=powerpc64le %s -o %t.o
# RUN: ld.lld -T %t.script %t.o -o %t --no-power10-stubs
# RUN: ld.lld -T %t.script %t.o -o %t --power10-stubs=auto --no-power10-stubs
# RUN: llvm-readelf -s %t | FileCheck %s --check-prefix=SYMBOL
# RUN: llvm-objdump -d --no-show-raw-insn --mcpu=pwr10 %t \
# RUN: | FileCheck %s --check-prefix=CHECK-NOP10