Skip to content

Commit bc2da11

Browse files
SC llvm teamSC llvm team
authored andcommitted
Merged main:f590963db836 into amd-gfx:23e4c3a6e3aa
Local branch amd-gfx 23e4c3a Merged main:9abcca5e2529 into amd-gfx:387d39f6081c Remote branch main f590963 [RISCV] Implement RISCVTTIImpl::getPreferredAddressingMode for HasVendorXCVmem (llvm#120533)
2 parents 23e4c3a + f590963 commit bc2da11

18 files changed

+245
-19
lines changed

clang-tools-extra/clangd/tool/ClangdMain.cpp

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -242,13 +242,13 @@ opt<std::string> FallbackStyle{
242242
init(clang::format::DefaultFallbackStyle),
243243
};
244244

245-
opt<int> EnableFunctionArgSnippets{
245+
opt<std::string> EnableFunctionArgSnippets{
246246
"function-arg-placeholders",
247247
cat(Features),
248248
desc("When disabled (0), completions contain only parentheses for "
249249
"function calls. When enabled (1), completions also contain "
250250
"placeholders for method parameters"),
251-
init(-1),
251+
init("-1"),
252252
};
253253

254254
opt<CodeCompleteOptions::IncludeInsertion> HeaderInsertion{
@@ -636,6 +636,22 @@ loadExternalIndex(const Config::ExternalIndexSpec &External,
636636
llvm_unreachable("Invalid ExternalIndexKind.");
637637
}
638638

639+
std::optional<bool> shouldEnableFunctionArgSnippets() {
640+
std::string Val = EnableFunctionArgSnippets;
641+
// Accept the same values that a bool option parser would, but also accept
642+
// -1 to indicate "unspecified", in which case the ArgumentListsPolicy
643+
// config option will be respected.
644+
if (Val == "1" || Val == "true" || Val == "True" || Val == "TRUE")
645+
return true;
646+
if (Val == "0" || Val == "false" || Val == "False" || Val == "FALSE")
647+
return false;
648+
if (Val != "-1")
649+
elog("Value specified by --function-arg-placeholders is invalid. Provide a "
650+
"boolean value or leave unspecified to use ArgumentListsPolicy from "
651+
"config instead.");
652+
return std::nullopt;
653+
}
654+
639655
class FlagsConfigProvider : public config::Provider {
640656
private:
641657
config::CompiledFragment Frag;
@@ -696,10 +712,9 @@ class FlagsConfigProvider : public config::Provider {
696712
BGPolicy = Config::BackgroundPolicy::Skip;
697713
}
698714

699-
if (EnableFunctionArgSnippets >= 0) {
700-
ArgumentLists = EnableFunctionArgSnippets
701-
? Config::ArgumentListsPolicy::FullPlaceholders
702-
: Config::ArgumentListsPolicy::Delimiters;
715+
if (std::optional<bool> Enable = shouldEnableFunctionArgSnippets()) {
716+
ArgumentLists = *Enable ? Config::ArgumentListsPolicy::FullPlaceholders
717+
: Config::ArgumentListsPolicy::Delimiters;
703718
}
704719

705720
Frag = [=](const config::Params &, Config &C) {

clang/lib/Sema/SemaOverload.cpp

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6977,11 +6977,26 @@ void Sema::AddOverloadCandidate(
69776977
/// have linkage. So that all entities of the same should share one
69786978
/// linkage. But in clang, different entities of the same could have
69796979
/// different linkage.
6980-
NamedDecl *ND = Function;
6981-
if (auto *SpecInfo = Function->getTemplateSpecializationInfo())
6980+
const NamedDecl *ND = Function;
6981+
bool IsImplicitlyInstantiated = false;
6982+
if (auto *SpecInfo = Function->getTemplateSpecializationInfo()) {
69826983
ND = SpecInfo->getTemplate();
6983-
6984-
if (ND->getFormalLinkage() == Linkage::Internal) {
6984+
IsImplicitlyInstantiated = SpecInfo->getTemplateSpecializationKind() ==
6985+
TSK_ImplicitInstantiation;
6986+
}
6987+
6988+
/// Don't remove inline functions with internal linkage from the overload
6989+
/// set if they are declared in a GMF, in violation of C++ [basic.link]p17.
6990+
/// However:
6991+
/// - Inline functions with internal linkage are a common pattern in
6992+
/// headers to avoid ODR issues.
6993+
/// - The global module is meant to be a transition mechanism for C and C++
6994+
/// headers, and the current rules as written work against that goal.
6995+
const bool IsInlineFunctionInGMF =
6996+
Function->isFromGlobalModule() &&
6997+
(IsImplicitlyInstantiated || Function->isInlined());
6998+
6999+
if (ND->getFormalLinkage() == Linkage::Internal && !IsInlineFunctionInGMF) {
69857000
Candidate.Viable = false;
69867001
Candidate.FailureKind = ovl_fail_module_mismatched;
69877002
return;
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
// RUN: rm -rf %t
2+
// RUN: mkdir -p %t
3+
// RUN: split-file %s %t
4+
//
5+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm \
6+
// RUN: -DTEST_INLINE
7+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify \
8+
// RUN: -DTEST_INLINE
9+
//
10+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm
11+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify
12+
13+
//--- a.h
14+
#ifdef TEST_INLINE
15+
#define INLINE inline
16+
#else
17+
#define INLINE
18+
#endif
19+
static INLINE void func(long) {}
20+
template <typename T = long> void a() { func(T{}); }
21+
22+
//--- a.cppm
23+
module;
24+
#include "a.h"
25+
export module a;
26+
export using ::a;
27+
28+
//--- test.cc
29+
import a;
30+
auto m = (a(), 0);
31+
32+
#ifdef TEST_INLINE
33+
// expected-no-diagnostics
34+
#else
35+
// [email protected]:7 {{no matching function for call to 'func'}}
36+
// [email protected]:2 {{in instantiation of function template specialization 'a<long>' requested here}}
37+
#endif
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// RUN: rm -rf %t
2+
// RUN: mkdir -p %t
3+
// RUN: split-file %s %t
4+
//
5+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm
6+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify
7+
8+
//--- a.h
9+
template <typename G> static inline void func() {}
10+
template <typename T = long> void a() { func<T>(); }
11+
12+
//--- a.cppm
13+
module;
14+
#include "a.h"
15+
export module a;
16+
export using ::a;
17+
18+
//--- test.cc
19+
import a;
20+
auto m = (a(), 0);
21+
22+
// expected-no-diagnostics
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
// RUN: rm -rf %t
2+
// RUN: mkdir -p %t
3+
// RUN: split-file %s %t
4+
//
5+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm
6+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify
7+
8+
//--- a.h
9+
namespace ns {
10+
template <typename G> static void func() {}
11+
template <typename T = long> void a() { func<T>(); }
12+
}
13+
14+
//--- a.cppm
15+
module;
16+
#include "a.h"
17+
export module a;
18+
export using ns::a;
19+
20+
//--- test.cc
21+
import a;
22+
auto m = (a(), 0);
23+
24+
// expected-no-diagnostics
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
// RUN: rm -rf %t
2+
// RUN: mkdir -p %t
3+
// RUN: split-file %s %t
4+
//
5+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm \
6+
// RUN: -DTEST_INLINE
7+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify \
8+
// RUN: -DTEST_INLINE
9+
//
10+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm
11+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify
12+
13+
//--- a.h
14+
#ifdef TEST_INLINE
15+
#define INLINE inline
16+
#else
17+
#define INLINE
18+
#endif
19+
namespace ns {
20+
template <typename G> static void func() {}
21+
template <> INLINE void func<long>() {}
22+
template <typename T = long> void a() { func<T>(); }
23+
}
24+
25+
//--- a.cppm
26+
module;
27+
#include "a.h"
28+
export module a;
29+
export using ns::a;
30+
31+
//--- test.cc
32+
import a;
33+
auto m = (a(), 0);
34+
35+
#ifdef TEST_INLINE
36+
// expected-no-diagnostics
37+
#else
38+
// [email protected]:9 {{no matching function for call to 'func'}}
39+
// [email protected]:2 {{in instantiation of function template specialization 'ns::a<long>' requested here}}
40+
#endif
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
// RUN: rm -rf %t
2+
// RUN: mkdir -p %t
3+
// RUN: split-file %s %t
4+
//
5+
// RUN: %clang -std=c++20 %t/a.cppm --precompile -o %t/a.pcm
6+
// RUN: %clang -std=c++20 %t/test.cc -fprebuilt-module-path=%t -fsyntax-only -Xclang -verify
7+
8+
//--- a.h
9+
namespace ns {
10+
namespace {
11+
template <typename G> void func() {}
12+
}
13+
template <typename T = long> void a() { func<T>(); }
14+
}
15+
16+
//--- a.cppm
17+
module;
18+
#include "a.h"
19+
export module a;
20+
export using ns::a;
21+
22+
//--- test.cc
23+
import a;
24+
auto m = (a(), 0);
25+
26+
// expected-no-diagnostics

clang/tools/include-mapping/cppreference_parser.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ def _ParseIndexPage(index_page_html):
139139

140140

141141
def _ReadSymbolPage(path, name, qual_name):
142-
with open(path) as f:
142+
with open(path, encoding="utf-8") as f:
143143
return _ParseSymbolPage(f.read(), name, qual_name)
144144

145145

@@ -156,7 +156,7 @@ def _GetSymbols(pool, root_dir, index_page_name, namespace, variants_to_accept):
156156
# contains the defined header.
157157
# 2. Parse the symbol page to get the defined header.
158158
index_page_path = os.path.join(root_dir, index_page_name)
159-
with open(index_page_path, "r") as f:
159+
with open(index_page_path, "r", encoding="utf-8") as f:
160160
# Read each symbol page in parallel.
161161
results = [] # (symbol_name, promise of [header...])
162162
for symbol_name, symbol_page_path, variant in _ParseIndexPage(f.read()):

libc/utils/hdrgen/yaml_to_classes.py

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,14 @@
1111
import yaml
1212
import argparse
1313
from pathlib import Path
14-
from header import HeaderFile
14+
15+
from enumeration import Enumeration
16+
from function import Function
1517
from gpu_headers import GpuHeaderFile as GpuHeader
16-
from class_implementation.classes.macro import Macro
17-
from class_implementation.classes.type import Type
18-
from class_implementation.classes.function import Function
19-
from class_implementation.classes.enumeration import Enumeration
20-
from class_implementation.classes.object import Object
18+
from header import HeaderFile
19+
from macro import Macro
20+
from object import Object
21+
from type import Type
2122

2223

2324
def yaml_to_classes(yaml_data, header_class, entry_points=None):

llvm/include/llvm/Config/llvm-config.h.cmake

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@
1616

1717
/* Indicate that this is LLVM compiled from the amd-gfx branch. */
1818
#define LLVM_HAVE_BRANCH_AMD_GFX
19-
#define LLVM_MAIN_REVISION 522529
19+
#define LLVM_MAIN_REVISION 522534
2020

2121
/* Define if LLVM_ENABLE_DUMP is enabled */
2222
#cmakedefine LLVM_ENABLE_DUMP

llvm/lib/Target/RISCV/RISCVTargetTransformInfo.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2329,6 +2329,15 @@ unsigned RISCVTTIImpl::getMaximumVF(unsigned ElemWidth, unsigned Opcode) const {
23292329
return std::max<unsigned>(1U, RegWidth.getFixedValue() / ElemWidth);
23302330
}
23312331

2332+
TTI::AddressingModeKind
2333+
RISCVTTIImpl::getPreferredAddressingMode(const Loop *L,
2334+
ScalarEvolution *SE) const {
2335+
if (ST->hasVendorXCVmem() && !ST->is64Bit())
2336+
return TTI::AMK_PostIndexed;
2337+
2338+
return BasicTTIImplBase::getPreferredAddressingMode(L, SE);
2339+
}
2340+
23322341
bool RISCVTTIImpl::isLSRCostLess(const TargetTransformInfo::LSRCost &C1,
23332342
const TargetTransformInfo::LSRCost &C2) {
23342343
// RISC-V specific here are "instruction number 1st priority".

llvm/lib/Target/RISCV/RISCVTargetTransformInfo.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -388,6 +388,9 @@ class RISCVTTIImpl : public BasicTTIImplBase<RISCVTTIImpl> {
388388
llvm_unreachable("unknown register class");
389389
}
390390

391+
TTI::AddressingModeKind getPreferredAddressingMode(const Loop *L,
392+
ScalarEvolution *SE) const;
393+
391394
unsigned getRegisterClassForType(bool Vector, Type *Ty = nullptr) const {
392395
if (Vector)
393396
return RISCVRegisterClass::VRRC;
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2+
; RUN: llc -O3 -mtriple=riscv32 -mattr=+m,+xcvmem -verify-machineinstrs < %s \
3+
; RUN: | FileCheck %s --check-prefixes=CHECK
4+
5+
define i32 @test_heuristic(ptr %b, i32 %e, i1 %0) {
6+
; CHECK-LABEL: test_heuristic:
7+
; CHECK: # %bb.0: # %entry
8+
; CHECK-NEXT: add a3, a0, a1
9+
; CHECK-NEXT: andi a2, a2, 1
10+
; CHECK-NEXT: .LBB0_1: # %loop
11+
; CHECK-NEXT: # =>This Inner Loop Header: Depth=1
12+
; CHECK-NEXT: cv.lbu a1, (a3), 1
13+
; CHECK-NEXT: addi a0, a0, 1
14+
; CHECK-NEXT: beqz a2, .LBB0_1
15+
; CHECK-NEXT: # %bb.2: # %exit
16+
; CHECK-NEXT: mv a0, a1
17+
; CHECK-NEXT: ret
18+
entry:
19+
%1 = getelementptr i8, ptr %b, i32 %e
20+
br label %loop
21+
22+
loop: ; preds = %loop, %entry
23+
%2 = phi ptr [ %b, %entry ], [ %7, %loop ]
24+
%3 = phi ptr [ %1, %entry ], [ %8, %loop ]
25+
%4 = load i8, ptr %2, align 1
26+
%5 = load i8, ptr %3, align 1
27+
%6 = zext i8 %5 to i32
28+
%7 = getelementptr i8, ptr %2, i32 1
29+
%8 = getelementptr i8, ptr %3, i32 1
30+
br i1 %0, label %exit, label %loop
31+
32+
exit: ; preds = %loop
33+
ret i32 %6
34+
}

0 commit comments

Comments
 (0)