Skip to content

Commit 73acf8d

Browse files
authored
[RISCV] Add -m[no-]scalar-strict-align and -m[no-]vector-strict-align. (#95024)
1 parent 7c15fba commit 73acf8d

File tree

10 files changed

+90
-39
lines changed

10 files changed

+90
-39
lines changed

clang/docs/ReleaseNotes.rst

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1151,6 +1151,10 @@ RISC-V Support
11511151
- ``__attribute__((rvv_vector_bits(N)))`` is now supported for RVV vbool*_t types.
11521152
- Profile names in ``-march`` option are now supported.
11531153
- Passing empty structs/unions as arguments in C++ is now handled correctly. The behavior is similar to GCC's.
1154+
- ``-m[no-]scalar-strict-align`` and ``-m[no-]vector-strict-align`` options have
1155+
been added to give separate control of whether scalar or vector misaligned
1156+
accesses may be created. ``-m[no-]strict-align`` applies to both scalar and
1157+
vector.
11541158

11551159
CUDA/HIP Language Changes
11561160
^^^^^^^^^^^^^^^^^^^^^^^^^

clang/include/clang/Driver/Options.td

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4854,6 +4854,14 @@ def mstrict_align : Flag<["-"], "mstrict-align">, Group<m_Group>,
48544854
HelpText<"Force all memory accesses to be aligned (AArch64/LoongArch/RISC-V only)">;
48554855
def mno_strict_align : Flag<["-"], "mno-strict-align">, Group<m_Group>,
48564856
HelpText<"Allow memory accesses to be unaligned (AArch64/LoongArch/RISC-V only)">;
4857+
def mscalar_strict_align : Flag<["-"], "mscalar-strict-align">, Group<m_Group>,
4858+
HelpText<"Force all scalar memory accesses to be aligned (RISC-V only)">;
4859+
def mno_scalar_strict_align : Flag<["-"], "mno-scalar-strict-align">, Group<m_Group>,
4860+
HelpText<"Allow scalar memory accesses to be unaligned (RISC-V only)">;
4861+
def mvector_strict_align : Flag<["-"], "mvector-strict-align">, Group<m_Group>,
4862+
HelpText<"Force all vector memory accesses to be aligned (RISC-V only)">;
4863+
def mno_vector_strict_align : Flag<["-"], "mno-vector-strict-align">, Group<m_Group>,
4864+
HelpText<"Allow vector memory accesses to be unaligned (RISC-V only)">;
48574865
def mno_thumb : Flag<["-"], "mno-thumb">, Group<m_arm_Features_Group>;
48584866
def mrestrict_it: Flag<["-"], "mrestrict-it">, Group<m_arm_Features_Group>,
48594867
HelpText<"Disallow generation of complex IT blocks. It is off by default.">;

clang/lib/Basic/Targets/RISCV.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -211,7 +211,7 @@ void RISCVTargetInfo::getTargetDefines(const LangOptions &Opts,
211211
Builder.defineMacro("__riscv_v_fixed_vlen",
212212
Twine(VScale->first * llvm::RISCV::RVVBitsPerBlock));
213213

214-
if (FastUnalignedAccess)
214+
if (FastScalarUnalignedAccess)
215215
Builder.defineMacro("__riscv_misaligned_fast");
216216
else
217217
Builder.defineMacro("__riscv_misaligned_avoid");
@@ -353,8 +353,8 @@ bool RISCVTargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
353353
if (ISAInfo->hasExtension("zfh") || ISAInfo->hasExtension("zhinx"))
354354
HasLegalHalfType = true;
355355

356-
FastUnalignedAccess = llvm::is_contained(Features, "+unaligned-scalar-mem") &&
357-
llvm::is_contained(Features, "+unaligned-vector-mem");
356+
FastScalarUnalignedAccess =
357+
llvm::is_contained(Features, "+unaligned-scalar-mem");
358358

359359
if (llvm::is_contained(Features, "+experimental"))
360360
HasExperimental = true;

clang/lib/Basic/Targets/RISCV.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ class RISCVTargetInfo : public TargetInfo {
3030
std::unique_ptr<llvm::RISCVISAInfo> ISAInfo;
3131

3232
private:
33-
bool FastUnalignedAccess;
33+
bool FastScalarUnalignedAccess;
3434
bool HasExperimental = false;
3535

3636
public:

clang/lib/Driver/ToolChains/Arch/RISCV.cpp

Lines changed: 31 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,8 @@ void riscv::getRISCVTargetFeatures(const Driver &D, const llvm::Triple &Triple,
7777
if (!getArchFeatures(D, MArch, Features, Args))
7878
return;
7979

80-
bool CPUFastUnaligned = false;
80+
bool CPUFastScalarUnaligned = false;
81+
bool CPUFastVectorUnaligned = false;
8182

8283
// If users give march and mcpu, get std extension feature from MArch
8384
// and other features (ex. mirco architecture feature) from mcpu
@@ -88,8 +89,10 @@ void riscv::getRISCVTargetFeatures(const Driver &D, const llvm::Triple &Triple,
8889

8990
getRISCFeaturesFromMcpu(D, A, Triple, CPU, Features);
9091

91-
if (llvm::RISCV::hasFastUnalignedAccess(CPU))
92-
CPUFastUnaligned = true;
92+
if (llvm::RISCV::hasFastScalarUnalignedAccess(CPU))
93+
CPUFastScalarUnaligned = true;
94+
if (llvm::RISCV::hasFastVectorUnalignedAccess(CPU))
95+
CPUFastVectorUnaligned = true;
9396
}
9497

9598
// Handle features corresponding to "-ffixed-X" options
@@ -169,20 +172,37 @@ void riscv::getRISCVTargetFeatures(const Driver &D, const llvm::Triple &Triple,
169172
Features.push_back("-relax");
170173
}
171174

172-
// If -mstrict-align or -mno-strict-align is passed, use it. Otherwise, the
173-
// unaligned-*-mem is enabled if the CPU supports it or the target is
175+
// If -mstrict-align, -mno-strict-align, -mscalar-strict-align, or
176+
// -mno-scalar-strict-align is passed, use it. Otherwise, the
177+
// unaligned-scalar-mem is enabled if the CPU supports it or the target is
174178
// Android.
175-
if (const Arg *A = Args.getLastArg(options::OPT_mno_strict_align,
176-
options::OPT_mstrict_align)) {
177-
if (A->getOption().matches(options::OPT_mno_strict_align)) {
179+
if (const Arg *A = Args.getLastArg(
180+
options::OPT_mno_strict_align, options::OPT_mscalar_strict_align,
181+
options::OPT_mstrict_align, options::OPT_mno_scalar_strict_align)) {
182+
if (A->getOption().matches(options::OPT_mno_strict_align) ||
183+
A->getOption().matches(options::OPT_mno_scalar_strict_align)) {
178184
Features.push_back("+unaligned-scalar-mem");
179-
Features.push_back("+unaligned-vector-mem");
180185
} else {
181186
Features.push_back("-unaligned-scalar-mem");
182-
Features.push_back("-unaligned-vector-mem");
183187
}
184-
} else if (CPUFastUnaligned || Triple.isAndroid()) {
188+
} else if (CPUFastScalarUnaligned || Triple.isAndroid()) {
185189
Features.push_back("+unaligned-scalar-mem");
190+
}
191+
192+
// If -mstrict-align, -mno-strict-align, -mvector-strict-align, or
193+
// -mno-vector-strict-align is passed, use it. Otherwise, the
194+
// unaligned-vector-mem is enabled if the CPU supports it or the target is
195+
// Android.
196+
if (const Arg *A = Args.getLastArg(
197+
options::OPT_mno_strict_align, options::OPT_mvector_strict_align,
198+
options::OPT_mstrict_align, options::OPT_mno_vector_strict_align)) {
199+
if (A->getOption().matches(options::OPT_mno_strict_align) ||
200+
A->getOption().matches(options::OPT_mno_vector_strict_align)) {
201+
Features.push_back("+unaligned-vector-mem");
202+
} else {
203+
Features.push_back("-unaligned-vector-mem");
204+
}
205+
} else if (CPUFastVectorUnaligned || Triple.isAndroid()) {
186206
Features.push_back("+unaligned-vector-mem");
187207
}
188208

clang/test/Driver/riscv-features.c

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
// RUN: %clang --target=riscv32-unknown-elf -### %s -fsyntax-only 2>&1 | FileCheck %s
22
// RUN: %clang --target=riscv64-unknown-elf -### %s -fsyntax-only 2>&1 | FileCheck %s
3-
// RUN: %clang --target=riscv64-linux-android -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=ANDROID,DEFAULT,FAST-UNALIGNED-ACCESS
4-
// RUN: %clang -mabi=lp64d --target=riscv64-linux-android -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=ANDROID,DEFAULT,FAST-UNALIGNED-ACCESS
5-
// RUN: %clang -mabi=lp64d --target=riscv64-linux-android -mstrict-align -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=NO-FAST-UNALIGNED-ACCESS
3+
// RUN: %clang --target=riscv64-linux-android -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=ANDROID,DEFAULT,FAST-SCALAR-UNALIGNED-ACCESS,FAST-VECTOR-UNALIGNED-ACCESS
4+
// RUN: %clang -mabi=lp64d --target=riscv64-linux-android -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=ANDROID,DEFAULT,FAST-SCALAR-UNALIGNED-ACCESS,FAST-VECTOR-UNALIGNED-ACCESS
5+
// RUN: %clang -mabi=lp64d --target=riscv64-linux-android -mstrict-align -mvector-strict-align -### %s -fsyntax-only 2>&1 | FileCheck %s -check-prefixes=NO-FAST-SCALAR-UNALIGNED-ACCESS,NO-FAST-VECTOR-UNALIGNED-ACCESS
66

77

88
// CHECK: fno-signed-char
@@ -35,13 +35,23 @@
3535
// NO-FORCE-SW-SCS: "-target-feature" "-forced-sw-shadow-stack"
3636
// DEFAULT-NOT: "-target-feature" "+forced-sw-shadow-stack"
3737

38-
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-strict-align 2>&1 | FileCheck %s -check-prefix=FAST-UNALIGNED-ACCESS
39-
// RUN: %clang --target=riscv32-unknown-elf -### %s -mstrict-align 2>&1 | FileCheck %s -check-prefix=NO-FAST-UNALIGNED-ACCESS
38+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-strict-align 2>&1 | FileCheck %s -check-prefixes=FAST-SCALAR-UNALIGNED-ACCESS,FAST-VECTOR-UNALIGNED-ACCESS
39+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mstrict-align 2>&1 | FileCheck %s -check-prefixes=NO-FAST-SCALAR-UNALIGNED-ACCESS,NO-FAST-VECTOR-UNALIGNED-ACCESS
40+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-scalar-strict-align 2>&1 | FileCheck %s -check-prefix=FAST-SCALAR-UNALIGNED-ACCESS
41+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mscalar-strict-align 2>&1 | FileCheck %s -check-prefix=NO-FAST-SCALAR-UNALIGNED-ACCESS
42+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-scalar-strict-align -mstrict-align 2>&1 | FileCheck %s -check-prefixes=NO-FAST-SCALAR-UNALIGNED-ACCESS,NO-FAST-VECTOR-UNALIGNED-ACCESS
4043
// RUN: touch %t.o
4144
// RUN: %clang --target=riscv32-unknown-elf -### %t.o -mno-strict-align -mstrict-align
4245

43-
// FAST-UNALIGNED-ACCESS: "-target-feature" "+unaligned-scalar-mem" "-target-feature" "+unaligned-vector-mem"
44-
// NO-FAST-UNALIGNED-ACCESS: "-target-feature" "-unaligned-scalar-mem" "-target-feature" "-unaligned-vector-mem"
46+
// FAST-SCALAR-UNALIGNED-ACCESS: "-target-feature" "+unaligned-scalar-mem"
47+
// NO-FAST-SCALAR-UNALIGNED-ACCESS: "-target-feature" "-unaligned-scalar-mem"
48+
49+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-vector-strict-align 2>&1 | FileCheck %s -check-prefix=FAST-VECTOR-UNALIGNED-ACCESS
50+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mvector-strict-align 2>&1 | FileCheck %s -check-prefix=NO-FAST-VECTOR-UNALIGNED-ACCESS
51+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-vector-strict-align -mstrict-align 2>&1 | FileCheck %s -check-prefix=NO-FAST-VECTOR-UNALIGNED-ACCESS
52+
// RUN: %clang --target=riscv32-unknown-elf -### %s -mno-strict-align -mvector-strict-align 2>&1 | FileCheck %s -check-prefix=NO-FAST-VECTOR-UNALIGNED-ACCESS
53+
// FAST-VECTOR-UNALIGNED-ACCESS: "-target-feature" "+unaligned-vector-mem"
54+
// NO-FAST-VECTOR-UNALIGNED-ACCESS: "-target-feature" "-unaligned-vector-mem"
4555

4656
// RUN: %clang --target=riscv32-unknown-elf -### %s 2>&1 | FileCheck %s -check-prefix=NOUWTABLE
4757
// RUN: %clang --target=riscv32-unknown-elf -fasynchronous-unwind-tables -### %s 2>&1 | FileCheck %s -check-prefix=UWTABLE

llvm/include/llvm/TargetParser/RISCVTargetParser.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,8 @@ bool parseTuneCPU(StringRef CPU, bool IsRV64);
3535
StringRef getMArchFromMcpu(StringRef CPU);
3636
void fillValidCPUArchList(SmallVectorImpl<StringRef> &Values, bool IsRV64);
3737
void fillValidTuneCPUArchList(SmallVectorImpl<StringRef> &Values, bool IsRV64);
38-
bool hasFastUnalignedAccess(StringRef CPU);
38+
bool hasFastScalarUnalignedAccess(StringRef CPU);
39+
bool hasFastVectorUnalignedAccess(StringRef CPU);
3940

4041
} // namespace RISCV
4142

llvm/lib/TargetParser/RISCVTargetParser.cpp

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,21 +21,25 @@ namespace llvm {
2121
namespace RISCV {
2222

2323
enum CPUKind : unsigned {
24-
#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGN) CK_##ENUM,
24+
#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_SCALAR_UNALIGN, \
25+
FAST_VECTOR_UNALIGN) \
26+
CK_##ENUM,
2527
#define TUNE_PROC(ENUM, NAME) CK_##ENUM,
2628
#include "llvm/TargetParser/RISCVTargetParserDef.inc"
2729
};
2830

2931
struct CPUInfo {
3032
StringLiteral Name;
3133
StringLiteral DefaultMarch;
32-
bool FastUnalignedAccess;
34+
bool FastScalarUnalignedAccess;
35+
bool FastVectorUnalignedAccess;
3336
bool is64Bit() const { return DefaultMarch.starts_with("rv64"); }
3437
};
3538

3639
constexpr CPUInfo RISCVCPUInfo[] = {
37-
#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGN) \
38-
{NAME, DEFAULT_MARCH, FAST_UNALIGN},
40+
#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_SCALAR_UNALIGN, \
41+
FAST_VECTOR_UNALIGN) \
42+
{NAME, DEFAULT_MARCH, FAST_SCALAR_UNALIGN, FAST_VECTOR_UNALIGN},
3943
#include "llvm/TargetParser/RISCVTargetParserDef.inc"
4044
};
4145

@@ -46,9 +50,14 @@ static const CPUInfo *getCPUInfoByName(StringRef CPU) {
4650
return nullptr;
4751
}
4852

49-
bool hasFastUnalignedAccess(StringRef CPU) {
53+
bool hasFastScalarUnalignedAccess(StringRef CPU) {
5054
const CPUInfo *Info = getCPUInfoByName(CPU);
51-
return Info && Info->FastUnalignedAccess;
55+
return Info && Info->FastScalarUnalignedAccess;
56+
}
57+
58+
bool hasFastVectorUnalignedAccess(StringRef CPU) {
59+
const CPUInfo *Info = getCPUInfoByName(CPU);
60+
return Info && Info->FastVectorUnalignedAccess;
5261
}
5362

5463
bool parseCPU(StringRef CPU, bool IsRV64) {

llvm/test/TableGen/riscv-target-def.td

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -153,13 +153,13 @@ def ROCKET : RISCVTuneProcessorModel<"rocket",
153153
// CHECK: #endif // GET_SUPPORTED_PROFILES
154154

155155
// CHECK: #ifndef PROC
156-
// CHECK-NEXT: #define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGNED_ACCESS)
156+
// CHECK-NEXT: #define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_SCALAR_UNALIGN, FAST_VECTOR_UNALIGN)
157157
// CHECK-NEXT: #endif
158158

159-
// CHECK: PROC(GENERIC_RV32, {"generic-rv32"}, {"rv32i2p1"}, 0)
160-
// CHECK-NEXT: PROC(GENERIC_RV64, {"generic-rv64"}, {"rv64i2p1"}, 0)
161-
// CHECK-NEXT: PROC(ROCKET_RV32, {"rocket-rv32"}, {"rv32i2p1_zicsr2p0_zidummy0p1_zifencei2p0"}, 0)
162-
// CHECK-NEXT: PROC(ROCKET_RV64, {"rocket-rv64"}, {"rv64i2p1_zicsr2p0_zidummy0p1_zifencei2p0"}, 0)
159+
// CHECK: PROC(GENERIC_RV32, {"generic-rv32"}, {"rv32i2p1"}, 0, 0)
160+
// CHECK-NEXT: PROC(GENERIC_RV64, {"generic-rv64"}, {"rv64i2p1"}, 0, 0)
161+
// CHECK-NEXT: PROC(ROCKET_RV32, {"rocket-rv32"}, {"rv32i2p1_zicsr2p0_zidummy0p1_zifencei2p0"}, 0, 0)
162+
// CHECK-NEXT: PROC(ROCKET_RV64, {"rocket-rv64"}, {"rv64i2p1_zicsr2p0_zidummy0p1_zifencei2p0"}, 0, 0)
163163

164164
// CHECK: #undef PROC
165165

llvm/utils/TableGen/RISCVTargetDefEmitter.cpp

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,8 @@ static void emitRISCVProfiles(RecordKeeper &Records, raw_ostream &OS) {
164164

165165
static void emitRISCVProcs(RecordKeeper &RK, raw_ostream &OS) {
166166
OS << "#ifndef PROC\n"
167-
<< "#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGNED_ACCESS)\n"
167+
<< "#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_SCALAR_UNALIGN"
168+
<< ", FAST_VECTOR_UNALIGN)\n"
168169
<< "#endif\n\n";
169170

170171
// Iterate on all definition records.
@@ -180,9 +181,6 @@ static void emitRISCVProcs(RecordKeeper &RK, raw_ostream &OS) {
180181
return Feature->getValueAsString("Name") == "unaligned-vector-mem";
181182
});
182183

183-
bool FastUnalignedAccess =
184-
FastScalarUnalignedAccess && FastVectorUnalignedAccess;
185-
186184
OS << "PROC(" << Rec->getName() << ", {\"" << Rec->getValueAsString("Name")
187185
<< "\"}, {\"";
188186

@@ -193,7 +191,8 @@ static void emitRISCVProcs(RecordKeeper &RK, raw_ostream &OS) {
193191
printMArch(OS, Features);
194192
else
195193
OS << MArch;
196-
OS << "\"}, " << FastUnalignedAccess << ")\n";
194+
OS << "\"}, " << FastScalarUnalignedAccess << ", "
195+
<< FastVectorUnalignedAccess << ")\n";
197196
}
198197
OS << "\n#undef PROC\n";
199198
OS << "\n";

0 commit comments

Comments
 (0)