Skip to content

Commit 16ecc19

Browse files
SC llvm teamSC llvm team
authored andcommitted
Merged origin/amd-debug:458a46b5916f into origin/amd-gfx:1547ed8a9c4b
Local branch origin/amd-gfx 1547ed8 Merged origin/amd-debug:e434301ce4eb into origin/amd-gfx:377906eee23e Remote branch origin/amd-debug 458a46b Merge llvm/main into amd-debug
2 parents 1547ed8 + 458a46b commit 16ecc19

File tree

33 files changed

+1820
-73
lines changed

33 files changed

+1820
-73
lines changed

bolt/runtime/CMakeLists.txt

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,12 @@ set(BOLT_RT_FLAGS
3535
-fno-exceptions
3636
-fno-rtti
3737
-fno-stack-protector
38-
-fPIC)
38+
-fPIC
39+
# Runtime currently assumes omitted frame pointers for functions marked __attribute((naked)).
40+
# Protect against distros adding -fno-omit-frame-pointer and compiling with GCC.
41+
# Refs: llvm/llvm-project#148595 https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77882
42+
-fomit-frame-pointer
43+
)
3944
if (CMAKE_SYSTEM_PROCESSOR MATCHES "x86_64")
4045
set(BOLT_RT_FLAGS ${BOLT_RT_FLAGS}
4146
-mno-sse

clang/docs/ReleaseNotes.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -376,6 +376,8 @@ New Compiler Flags
376376

377377
- New option ``-ignore-pch`` added to disable precompiled headers. It overrides ``-emit-pch`` and ``-include-pch``. (#GH142409, `PCHDocs <https://clang.llvm.org/docs/UsersManual.html#ignoring-a-pch-file>`_).
378378

379+
- New options ``-g[no-]key-instructions`` added, disabled by default. Reduces jumpiness of debug stepping for optimized code in some debuggers (not LLDB at this time). Not recommended for use without optimizations. DWARF only. Note both the positive and negative flags imply ``-g``.
380+
379381
Deprecated Compiler Flags
380382
-------------------------
381383

clang/include/clang/Driver/Options.td

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4737,9 +4737,9 @@ def gno_embed_source : Flag<["-"], "gno-embed-source">, Group<g_flags_Group>,
47374737
defm key_instructions : BoolGOption<"key-instructions",
47384738
CodeGenOpts<"DebugKeyInstructions">, DefaultFalse,
47394739
NegFlag<SetFalse>, PosFlag<SetTrue, [], [],
4740-
"Enable Key Instructions, which reduces the jumpiness of optimized code stepping (DWARF only)."
4741-
" Requires LLVM built with LLVM_EXPERIMENTAL_KEY_INSTRUCTIONS.">,
4742-
BothFlags<[HelpHidden], [ClangOption, CLOption, CC1Option]>>;
4740+
"Enable Key Instructions, which reduces the jumpiness of debug stepping in optimized C/C++ code"
4741+
" in some debuggers. DWARF only. Implies -g.">,
4742+
BothFlags<[], [ClangOption, CLOption, CC1Option]>>;
47434743
def headerpad__max__install__names : Joined<["-"], "headerpad_max_install_names">;
47444744
def help : Flag<["-", "--"], "help">,
47454745
Visibility<[ClangOption, CC1Option, CC1AsOption,

clang/lib/CodeGen/CGDebugInfo.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4683,6 +4683,7 @@ void CGDebugInfo::emitFunctionStart(GlobalDecl GD, SourceLocation Loc,
46834683
llvm::DIFile *Unit = getOrCreateFile(Loc);
46844684
llvm::DIScope *FDContext = Unit;
46854685
llvm::DINodeArray TParamsArray;
4686+
bool KeyInstructions = CGM.getCodeGenOpts().DebugKeyInstructions;
46864687
if (!HasDecl) {
46874688
// Use llvm function name.
46884689
LinkageName = Fn->getName();
@@ -4699,6 +4700,9 @@ void CGDebugInfo::emitFunctionStart(GlobalDecl GD, SourceLocation Loc,
46994700
}
47004701
collectFunctionDeclProps(GD, Unit, Name, LinkageName, FDContext,
47014702
TParamsArray, Flags);
4703+
// Disable KIs if this is a coroutine.
4704+
KeyInstructions =
4705+
KeyInstructions && !isa_and_present<CoroutineBodyStmt>(FD->getBody());
47024706
} else if (const auto *OMD = dyn_cast<ObjCMethodDecl>(D)) {
47034707
Name = getObjCMethodName(OMD);
47044708
Flags |= llvm::DINode::FlagPrototyped;
@@ -4760,7 +4764,7 @@ void CGDebugInfo::emitFunctionStart(GlobalDecl GD, SourceLocation Loc,
47604764
llvm::DISubprogram *SP = DBuilder.createFunction(
47614765
FDContext, Name, LinkageName, Unit, LineNo, DIFnType, ScopeLine,
47624766
FlagsForDef, SPFlagsForDef, TParamsArray.get(), Decl, nullptr,
4763-
Annotations, "", CGM.getCodeGenOpts().DebugKeyInstructions);
4767+
Annotations, "", KeyInstructions);
47644768
Fn->setSubprogram(SP);
47654769

47664770
// We might get here with a VarDecl in the case we're generating
Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
// RUN: %clang_cc1 -disable-llvm-optzns -std=c++20 \
2+
// RUN: -triple=x86_64 -dwarf-version=4 -debug-info-kind=limited \
3+
// RUN: -emit-llvm -o - %s -gkey-instructions | \
4+
// RUN: FileCheck %s
5+
6+
// Check that for the coroutine below, we mark the created DISubprogram as
7+
// not having key instructions. This will prevent AsmPrinter from trying to
8+
// instrument the linetable with key-instructions for source-locations in
9+
// the coroutine scope.
10+
//
11+
// This is a temporary workaround for key instructions: we can instrument
12+
// coroutine code in the future, but it hasn't been done yet.
13+
//
14+
// File contents copied from coro-dwarf.cpp.
15+
16+
namespace std {
17+
template <typename... T> struct coroutine_traits;
18+
19+
template <class Promise = void> struct coroutine_handle {
20+
coroutine_handle() = default;
21+
static coroutine_handle from_address(void *) noexcept;
22+
};
23+
template <> struct coroutine_handle<void> {
24+
static coroutine_handle from_address(void *) noexcept;
25+
coroutine_handle() = default;
26+
template <class PromiseType>
27+
coroutine_handle(coroutine_handle<PromiseType>) noexcept;
28+
};
29+
} // namespace std
30+
31+
struct suspend_always {
32+
bool await_ready() noexcept;
33+
void await_suspend(std::coroutine_handle<>) noexcept;
34+
void await_resume() noexcept;
35+
};
36+
37+
template <typename... Args> struct std::coroutine_traits<void, Args...> {
38+
struct promise_type {
39+
void get_return_object() noexcept;
40+
suspend_always initial_suspend() noexcept;
41+
suspend_always final_suspend() noexcept;
42+
void return_void() noexcept;
43+
promise_type();
44+
~promise_type() noexcept;
45+
void unhandled_exception() noexcept;
46+
};
47+
};
48+
49+
// TODO: Not supported yet
50+
struct CopyOnly {
51+
int val;
52+
CopyOnly(const CopyOnly &) noexcept;
53+
CopyOnly(CopyOnly &&) = delete;
54+
~CopyOnly();
55+
};
56+
57+
struct MoveOnly {
58+
int val;
59+
MoveOnly(const MoveOnly &) = delete;
60+
MoveOnly(MoveOnly &&) noexcept;
61+
~MoveOnly();
62+
};
63+
64+
struct MoveAndCopy {
65+
int val;
66+
MoveAndCopy(const MoveAndCopy &) noexcept;
67+
MoveAndCopy(MoveAndCopy &&) noexcept;
68+
~MoveAndCopy();
69+
};
70+
71+
void consume(int, int, int) noexcept;
72+
73+
void f_coro(int val, MoveOnly moParam, MoveAndCopy mcParam) {
74+
consume(val, moParam.val, mcParam.val);
75+
co_return;
76+
}
77+
78+
// CHECK: ![[SP:[0-9]+]] = distinct !DISubprogram(name: "f_coro", linkageName: "_Z6f_coroi8MoveOnly11MoveAndCopy"
79+
// CHECK-NOT: keyInstructions:
80+
// CHECK: !DIFil
81+

clang/test/DebugInfo/KeyInstructions/flag.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@
33
//// Default: Off.
44
// RUN: %clang -### -target x86_64 -c -gdwarf %s 2>&1 | FileCheck %s --check-prefixes=NO-KEY-INSTRUCTIONS
55

6+
//// Help.
7+
// RUN %clang --help | FileCheck %s --check-prefix=HELP
8+
// HELP: -gkey-instructions Enable Key Instructions, which reduces the jumpiness of debug stepping in optimized C/C++ code in some debuggers. DWARF only. Implies -g.
9+
610
// KEY-INSTRUCTIONS: "-gkey-instructions"
711
// NO-KEY-INSTRUCTIONS-NOT: key-instructions
812

flang/include/flang/Common/format.h

Lines changed: 73 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
#include "Fortran-consts.h"
1313
#include "enum-set.h"
1414
#include <cstring>
15+
#include <limits>
1516

1617
// Define a FormatValidator class template to validate a format expression
1718
// of a given CHAR type. To enable use in runtime library code as well as
@@ -28,6 +29,71 @@
2829

2930
namespace Fortran::common {
3031

32+
// AddOverflow and MulOverflow are copied from
33+
// llvm/include/llvm/Support/MathExtras.h and specialised to int64_t.
34+
35+
/// Add two signed integers, computing the two's complement truncated result,
36+
/// returning true if overflow occurred.
37+
static inline bool AddOverflow(int64_t X, int64_t Y, int64_t &Result) {
38+
#if __has_builtin(__builtin_add_overflow)
39+
return __builtin_add_overflow(X, Y, &Result);
40+
#else
41+
// Perform the unsigned addition.
42+
const uint64_t UX = static_cast<uint64_t>(X);
43+
const uint64_t UY = static_cast<uint64_t>(Y);
44+
const uint64_t UResult = UX + UY;
45+
46+
// Convert to signed.
47+
Result = static_cast<int64_t>(UResult);
48+
49+
// Adding two positive numbers should result in a positive number.
50+
if (X > 0 && Y > 0) {
51+
return Result <= 0;
52+
}
53+
// Adding two negatives should result in a negative number.
54+
if (X < 0 && Y < 0) {
55+
return Result >= 0;
56+
}
57+
return false;
58+
#endif
59+
}
60+
61+
/// Multiply two signed integers, computing the two's complement truncated
62+
/// result, returning true if an overflow occurred.
63+
static inline bool MulOverflow(int64_t X, int64_t Y, int64_t &Result) {
64+
#if __has_builtin(__builtin_mul_overflow)
65+
return __builtin_mul_overflow(X, Y, &Result);
66+
#else
67+
// Perform the unsigned multiplication on absolute values.
68+
const uint64_t UX =
69+
X < 0 ? (0 - static_cast<uint64_t>(X)) : static_cast<uint64_t>(X);
70+
const uint64_t UY =
71+
Y < 0 ? (0 - static_cast<uint64_t>(Y)) : static_cast<uint64_t>(Y);
72+
const uint64_t UResult = UX * UY;
73+
74+
// Convert to signed.
75+
const bool IsNegative = (X < 0) ^ (Y < 0);
76+
Result = IsNegative ? (0 - UResult) : UResult;
77+
78+
// If any of the args was 0, result is 0 and no overflow occurs.
79+
if (UX == 0 || UY == 0) {
80+
return false;
81+
}
82+
83+
// UX and UY are in [1, 2^n], where n is the number of digits.
84+
// Check how the max allowed absolute value (2^n for negative, 2^(n-1) for
85+
// positive) divided by an argument compares to the other.
86+
if (IsNegative) {
87+
return UX > (static_cast<uint64_t>(std::numeric_limits<int64_t>::max()) +
88+
uint64_t(1)) /
89+
UY;
90+
} else {
91+
return UX >
92+
(static_cast<uint64_t>(std::numeric_limits<int64_t>::max())) / UY;
93+
}
94+
#endif
95+
}
96+
3197
struct FormatMessage {
3298
const char *text; // message text; may have one %s argument
3399
const char *arg; // optional %s argument value
@@ -214,16 +280,18 @@ template <typename CHAR> void FormatValidator<CHAR>::NextToken() {
214280
case '7':
215281
case '8':
216282
case '9': {
217-
int64_t lastValue;
218283
const CHAR *lastCursor;
219284
integerValue_ = 0;
220285
bool overflow{false};
221286
do {
222-
lastValue = integerValue_;
223287
lastCursor = cursor_;
224-
integerValue_ = 10 * integerValue_ + c - '0';
225-
if (lastValue > integerValue_) {
226-
overflow = true;
288+
if (!overflow) {
289+
overflow =
290+
MulOverflow(static_cast<int64_t>(10), integerValue_, integerValue_);
291+
}
292+
if (!overflow) {
293+
overflow = AddOverflow(
294+
integerValue_, static_cast<int64_t>(c - '0'), integerValue_);
227295
}
228296
c = NextChar();
229297
} while (c >= '0' && c <= '9');

flang/lib/Lower/Support/ReductionProcessor.cpp

Lines changed: 22 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -633,13 +633,25 @@ void ReductionProcessor::processReductionArguments(
633633
}
634634
}
635635

636-
fir::FirOpBuilder &firOpBuilder = converter.getFirOpBuilder();
637-
638636
// Reduction variable processing common to both intrinsic operators and
639637
// procedure designators
640638
fir::FirOpBuilder &builder = converter.getFirOpBuilder();
639+
mlir::OpBuilder::InsertPoint dcIP;
640+
constexpr bool isDoConcurrent =
641+
std::is_same_v<OpType, fir::DeclareReductionOp>;
642+
643+
if (isDoConcurrent) {
644+
dcIP = builder.saveInsertionPoint();
645+
builder.setInsertionPoint(
646+
builder.getRegion().getParentOfType<fir::DoConcurrentOp>());
647+
}
648+
641649
for (const semantics::Symbol *symbol : reductionSymbols) {
642650
mlir::Value symVal = converter.getSymbolAddress(*symbol);
651+
652+
if (auto declOp = symVal.getDefiningOp<hlfir::DeclareOp>())
653+
symVal = declOp.getBase();
654+
643655
mlir::Type eleType;
644656
auto refType = mlir::dyn_cast_or_null<fir::ReferenceType>(symVal.getType());
645657
if (refType)
@@ -667,13 +679,13 @@ void ReductionProcessor::processReductionArguments(
667679
// boxed arrays are passed as values not by reference. Unfortunately,
668680
// we can't pass a box by value to omp.redution_declare, so turn it
669681
// into a reference
670-
682+
auto oldIP = builder.saveInsertionPoint();
683+
builder.setInsertionPointToStart(builder.getAllocaBlock());
671684
auto alloca =
672685
builder.create<fir::AllocaOp>(currentLocation, symVal.getType());
686+
builder.restoreInsertionPoint(oldIP);
673687
builder.create<fir::StoreOp>(currentLocation, symVal, alloca);
674688
symVal = alloca;
675-
} else if (auto declOp = symVal.getDefiningOp<hlfir::DeclareOp>()) {
676-
symVal = declOp.getBase();
677689
}
678690

679691
// this isn't the same as the by-val and by-ref passing later in the
@@ -693,7 +705,7 @@ void ReductionProcessor::processReductionArguments(
693705
unsigned idx = 0;
694706
for (auto [symVal, isByRef] : llvm::zip(reductionVars, reduceVarByRef)) {
695707
auto redType = mlir::cast<fir::ReferenceType>(symVal.getType());
696-
const auto &kindMap = firOpBuilder.getKindMap();
708+
const auto &kindMap = builder.getKindMap();
697709
std::string reductionName;
698710
ReductionIdentifier redId;
699711

@@ -745,9 +757,12 @@ void ReductionProcessor::processReductionArguments(
745757
OpType decl = createDeclareReduction<OpType>(
746758
converter, reductionName, redId, redType, currentLocation, isByRef);
747759
reductionDeclSymbols.push_back(
748-
mlir::SymbolRefAttr::get(firOpBuilder.getContext(), decl.getSymName()));
760+
mlir::SymbolRefAttr::get(builder.getContext(), decl.getSymName()));
749761
++idx;
750762
}
763+
764+
if (isDoConcurrent)
765+
builder.restoreInsertionPoint(dcIP);
751766
}
752767

753768
const semantics::SourceName

0 commit comments

Comments
 (0)