Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Default to rv64gc on riscv64 #4390

Merged
merged 1 commit into from
Aug 26, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#### Platform support
- Supports LLVM 11.0 - 16.0.
- When nothing else specified now defaults to `-mattr=+m,+a,+f,+d,+c` when targeting hosted 64-bit RISC-V. (#4390)

#### Bug fixes
- Fix function pointers/delegates on Harvard architectures (e.g., AVR). (#4432, #4465)
Expand Down
41 changes: 36 additions & 5 deletions driver/targetmachine.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ static llvm::cl::opt<bool, true> preserveDwarfLineSection(
llvm::cl::init(false));
#endif

const char *getABI(const llvm::Triple &triple) {
const char *getABI(const llvm::Triple &triple, const llvm::SmallVector<llvm::StringRef, 8> &features) {
llvm::StringRef ABIName(opts::mABI);
if (ABIName != "") {
switch (triple.getArch()) {
Expand Down Expand Up @@ -111,6 +111,17 @@ const char *getABI(const llvm::Triple &triple) {
ABIName.str().c_str());
}

// checks if the features include ±<feature>
auto hasFeature = [&features](llvm::StringRef feature) {
for (int i = features.size() - 1; i >= 0; i--) {
auto f = features[i];
if (f.substr(1) == feature) {
return f[0] == '+';
}
}
return false;
};

switch (triple.getArch()) {
case llvm::Triple::mips64:
case llvm::Triple::mips64el:
Expand All @@ -120,6 +131,10 @@ const char *getABI(const llvm::Triple &triple) {
case llvm::Triple::ppc64le:
return "elfv2";
case llvm::Triple::riscv64:
if (hasFeature("d"))
return "lp64d";
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So a -mattr=-d would get me a lp64d ABI; is that intended? Or should it be narrowed to a +d/+f only?

An entry in CHANGELOG.md would be nice too. :)

if (hasFeature("f"))
return "lp64f";
return "lp64";
case llvm::Triple::riscv32:
return "ilp32";
Expand Down Expand Up @@ -430,9 +445,13 @@ createTargetMachine(const std::string targetTriple, const std::string arch,

// checks if the features include ±<feature>
auto hasFeature = [&features](llvm::StringRef feature) {
return std::any_of(
features.begin(), features.end(),
[feature](llvm::StringRef f) { return f.substr(1) == feature; });
for (int i = features.size() - 1; i >= 0; i--) {
auto f = features[i];
if (f.substr(1) == feature) {
return f[0] == '+';
}
}
return false;
};

// cmpxchg16b is not available on old 64bit CPUs. Enable code generation
Expand All @@ -441,6 +460,18 @@ createTargetMachine(const std::string targetTriple, const std::string arch,
features.push_back("+cx16");
}

// For a hosted RISC-V 64-bit target default to rv64gc if nothing has
// been selected
if (triple.getArch() == llvm::Triple::riscv64 &&
triple.getOS() != llvm::Triple::UnknownOS &&
features.empty()) {
features.push_back("+m");
features.push_back("+a");
features.push_back("+f");
features.push_back("+d");
features.push_back("+c");
}

// Handle cases where LLVM picks wrong default relocModel
#if LDC_LLVM_VER >= 1600
if (relocModel.has_value()) {}
Expand Down Expand Up @@ -478,7 +509,7 @@ createTargetMachine(const std::string targetTriple, const std::string arch,
opts::InitTargetOptionsFromCodeGenFlags(triple);

if (targetOptions.MCOptions.ABIName.empty())
targetOptions.MCOptions.ABIName = getABI(triple);
targetOptions.MCOptions.ABIName = getABI(triple, features);

if (floatABI == FloatABI::Default) {
switch (triple.getArch()) {
Expand Down
5 changes: 4 additions & 1 deletion driver/targetmachine.h
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
#pragma once

#include "llvm/ADT/Optional.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Support/CodeGen.h"
#include <string>
#include <vector>
Expand Down Expand Up @@ -73,4 +75,5 @@ MipsABI::Type getMipsABI();
const llvm::Target *lookupTarget(const std::string &arch, llvm::Triple &triple,
std::string &errorMsg);

const char *getABI(const llvm::Triple &triple);
const char *getABI(const llvm::Triple &triple,
const llvm::SmallVector<llvm::StringRef, 8> &features);
6 changes: 3 additions & 3 deletions driver/tool.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -123,14 +123,14 @@ void appendTargetArgsForGcc(std::vector<std::string> &args) {

case Triple::riscv64:
{
std::string mabi = getABI(triple);
args.push_back("-mabi=" + mabi);

extern llvm::TargetMachine* gTargetMachine;
auto featuresStr = gTargetMachine->getTargetFeatureString();
llvm::SmallVector<llvm::StringRef, 8> features;
featuresStr.split(features, ",", -1, false);

std::string mabi = getABI(triple, features);
args.push_back("-mabi=" + mabi);

// Returns true if 'feature' is enabled and false otherwise. Handles the
// case where the feature is specified multiple times ('+m,-m'), and
// takes the last occurrence.
Expand Down
6 changes: 6 additions & 0 deletions tests/driver/riscv_abi4.d
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// REQUIRES: target_RISCV

// RUN: %ldc %s -mtriple=riscv64-unknown-linux --gcc=echo > %t && FileCheck %s < %t
// CHECK: -mabi=lp64d -march=rv64gc

void main() {}
6 changes: 6 additions & 0 deletions tests/driver/riscv_abi5.d
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// REQUIRES: target_RISCV

// RUN: %ldc %s -mtriple=riscv64-unknown-linux -mattr=+m,+a,+f,-d --gcc=echo > %t && FileCheck %s < %t
// CHECK: -mabi=lp64f -march=rv64imaf_zicsr_zifencei

void main() {}