Skip to content

Commit 4d45052

Browse files
SC llvm teamSC llvm team
authored andcommitted
Merge llvm/main into amd-debug
2 parents 9bdd483 + 6d98f67 commit 4d45052

File tree

13 files changed

+220
-11
lines changed

13 files changed

+220
-11
lines changed

clang-tools-extra/clang-tidy/llvm/PreferStaticOverAnonymousNamespaceCheck.cpp

Lines changed: 14 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,17 @@ AST_MATCHER(NamedDecl, isInMacro) {
2121

2222
AST_MATCHER(VarDecl, isLocalVariable) { return Node.isLocalVarDecl(); }
2323

24+
AST_MATCHER(Decl, isLexicallyInAnonymousNamespace) {
25+
for (const DeclContext *DC = Node.getLexicalDeclContext(); DC != nullptr;
26+
DC = DC->getLexicalParent()) {
27+
if (const auto *ND = dyn_cast<NamespaceDecl>(DC))
28+
if (ND->isAnonymousNamespace())
29+
return true;
30+
}
31+
32+
return false;
33+
}
34+
2435
} // namespace
2536

2637
PreferStaticOverAnonymousNamespaceCheck::
@@ -40,9 +51,9 @@ void PreferStaticOverAnonymousNamespaceCheck::storeOptions(
4051

4152
void PreferStaticOverAnonymousNamespaceCheck::registerMatchers(
4253
MatchFinder *Finder) {
43-
const auto IsDefinitionInAnonymousNamespace =
44-
allOf(unless(isExpansionInSystemHeader()), isInAnonymousNamespace(),
45-
unless(isInMacro()), isDefinition());
54+
const auto IsDefinitionInAnonymousNamespace = allOf(
55+
unless(isExpansionInSystemHeader()), isLexicallyInAnonymousNamespace(),
56+
unless(isInMacro()), isDefinition());
4657

4758
if (AllowMemberFunctionsInClass) {
4859
Finder->addMatcher(

clang-tools-extra/test/clang-tidy/checkers/llvm/prefer-static-over-anonymous-namespace.cpp

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -178,6 +178,95 @@ void OuterClass::NestedClass::nestedMemberFunc() {}
178178

179179
} // namespace
180180

181+
namespace {
182+
183+
class MyClassOutOfAnon {
184+
public:
185+
MyClassOutOfAnon();
186+
MyClassOutOfAnon(const MyClassOutOfAnon&) {}
187+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:3: warning: place definition of method 'MyClassOutOfAnon' outside of an anonymous namespace
188+
MyClassOutOfAnon(MyClassOutOfAnon&&) = default;
189+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:3: warning: place definition of method 'MyClassOutOfAnon' outside of an anonymous namespace
190+
MyClassOutOfAnon& operator=(const MyClassOutOfAnon&);
191+
MyClassOutOfAnon& operator=(MyClassOutOfAnon&&);
192+
bool operator<(const MyClassOutOfAnon&) const;
193+
void memberFunction();
194+
static void staticMemberFunction();
195+
void memberDefinedInClass() {}
196+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:8: warning: place definition of method 'memberDefinedInClass' outside of an anonymous namespace
197+
static void staticMemberDefinedInClass() {}
198+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:15: warning: place definition of method 'staticMemberDefinedInClass' outside of an anonymous namespace
199+
template <typename T>
200+
void templateFunction();
201+
template <typename T>
202+
void templateFunctionInClass() {}
203+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:8: warning: place definition of method 'templateFunctionInClass' outside of an anonymous namespace
204+
};
205+
206+
} // namespace
207+
208+
MyClassOutOfAnon::MyClassOutOfAnon() {}
209+
210+
MyClassOutOfAnon& MyClassOutOfAnon::operator=(const MyClassOutOfAnon&) { return *this; }
211+
212+
MyClassOutOfAnon& MyClassOutOfAnon::operator=(MyClassOutOfAnon&&) = default;
213+
214+
bool MyClassOutOfAnon::operator<(const MyClassOutOfAnon&) const { return true; }
215+
216+
void MyClassOutOfAnon::memberFunction() {}
217+
218+
void MyClassOutOfAnon::staticMemberFunction() {}
219+
220+
template <typename T>
221+
void MyClassOutOfAnon::templateFunction() {}
222+
223+
namespace {
224+
225+
template<typename T>
226+
class TemplateClassOutOfAnon {
227+
public:
228+
TemplateClassOutOfAnon();
229+
TemplateClassOutOfAnon(const TemplateClassOutOfAnon&) {}
230+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:3: warning: place definition of method 'TemplateClassOutOfAnon<T>' outside of an anonymous namespace
231+
TemplateClassOutOfAnon(TemplateClassOutOfAnon&&) = default;
232+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:3: warning: place definition of method 'TemplateClassOutOfAnon<T>' outside of an anonymous namespace
233+
TemplateClassOutOfAnon& operator=(const TemplateClassOutOfAnon&);
234+
TemplateClassOutOfAnon& operator=(TemplateClassOutOfAnon&&);
235+
bool operator<(const TemplateClassOutOfAnon&) const;
236+
void memberFunc();
237+
T getValue() const;
238+
void memberDefinedInClass() {}
239+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:8: warning: place definition of method 'memberDefinedInClass' outside of an anonymous namespace
240+
static void staticMemberDefinedInClass() {}
241+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:15: warning: place definition of method 'staticMemberDefinedInClass' outside of an anonymous namespace
242+
template <typename U>
243+
void templateMethodInTemplateClass() {}
244+
// CHECK-MESSAGES-MEM: :[[@LINE-1]]:8: warning: place definition of method 'templateMethodInTemplateClass' outside of an anonymous namespace
245+
private:
246+
T Value;
247+
};
248+
249+
} // namespace
250+
251+
template<typename T>
252+
TemplateClassOutOfAnon<T>::TemplateClassOutOfAnon() {}
253+
254+
template<typename T>
255+
TemplateClassOutOfAnon<T>& TemplateClassOutOfAnon<T>::operator=(const TemplateClassOutOfAnon&) { return *this; }
256+
257+
template<typename T>
258+
TemplateClassOutOfAnon<T>& TemplateClassOutOfAnon<T>::operator=(TemplateClassOutOfAnon&&) = default;
259+
260+
template<typename T>
261+
bool TemplateClassOutOfAnon<T>::operator<(const TemplateClassOutOfAnon&) const { return true; }
262+
263+
template<typename T>
264+
void TemplateClassOutOfAnon<T>::memberFunc() {}
265+
266+
template<typename T>
267+
T TemplateClassOutOfAnon<T>::getValue() const { return Value; }
268+
269+
181270
#define DEFINE_FUNCTION(name) \
182271
namespace { \
183272
void name() {} \

libc/config/baremetal/aarch64/entrypoints.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,7 @@ set(TARGET_LIBC_ENTRYPOINTS
262262
# time.h entrypoints
263263
libc.src.time.asctime
264264
libc.src.time.asctime_r
265+
libc.src.time.clock
265266
libc.src.time.ctime
266267
libc.src.time.ctime_r
267268
libc.src.time.difftime

libc/config/baremetal/arm/entrypoints.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,7 @@ set(TARGET_LIBC_ENTRYPOINTS
262262
# time.h entrypoints
263263
libc.src.time.asctime
264264
libc.src.time.asctime_r
265+
libc.src.time.clock
265266
libc.src.time.ctime
266267
libc.src.time.ctime_r
267268
libc.src.time.difftime

libc/config/baremetal/riscv/entrypoints.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,7 @@ set(TARGET_LIBC_ENTRYPOINTS
262262
# time.h entrypoints
263263
libc.src.time.asctime
264264
libc.src.time.asctime_r
265+
libc.src.time.clock
265266
libc.src.time.ctime
266267
libc.src.time.ctime_r
267268
libc.src.time.difftime

libc/src/time/baremetal/CMakeLists.txt

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,14 @@
1+
add_entrypoint_object(
2+
clock
3+
SRCS
4+
clock.cpp
5+
HDRS
6+
../clock.h
7+
DEPENDS
8+
libc.hdr.time_macros
9+
libc.hdr.types.struct_timespec
10+
)
11+
112
add_entrypoint_object(
213
timespec_get
314
SRCS

libc/src/time/baremetal/clock.cpp

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
//===-- Baremetal implementation of the clock function --------------------===//
2+
//
3+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
9+
#include "src/time/clock.h"
10+
#include "hdr/time_macros.h"
11+
#include "hdr/types/struct_timespec.h"
12+
#include "src/__support/CPP/limits.h"
13+
#include "src/__support/common.h"
14+
#include "src/__support/macros/config.h"
15+
#include "src/__support/time/units.h"
16+
17+
namespace LIBC_NAMESPACE_DECL {
18+
19+
extern "C" bool __llvm_libc_timespec_get_active(struct timespec *ts);
20+
21+
LLVM_LIBC_FUNCTION(clock_t, clock, ()) {
22+
using namespace time_units;
23+
struct timespec ts;
24+
if (!__llvm_libc_timespec_get_active(&ts))
25+
return clock_t(-1);
26+
27+
// The above call gets the CPU time in seconds plus nanoseconds.
28+
// The standard requires that we return clock_t(-1) if we cannot represent
29+
// clocks as a clock_t value.
30+
constexpr clock_t CLOCK_SECS_MAX =
31+
cpp::numeric_limits<clock_t>::max() / CLOCKS_PER_SEC;
32+
if (ts.tv_sec > CLOCK_SECS_MAX)
33+
return clock_t(-1);
34+
if (ts.tv_nsec / 1_s_ns > CLOCK_SECS_MAX - ts.tv_sec)
35+
return clock_t(-1);
36+
37+
// For the integer computation converting tv_nsec to clocks to work
38+
// correctly, we want CLOCKS_PER_SEC to be less than 1000000000.
39+
static_assert(1_s_ns > CLOCKS_PER_SEC,
40+
"Expected CLOCKS_PER_SEC to be less than 1'000'000'000.");
41+
return clock_t(ts.tv_sec * CLOCKS_PER_SEC +
42+
ts.tv_nsec / (1_s_ns / CLOCKS_PER_SEC));
43+
}
44+
45+
} // namespace LIBC_NAMESPACE_DECL

libc/test/src/math/exhaustive/tanf_test.cpp

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
1-
//===-- Exhaustive test for tanf
2-
//--------------------------------------std::cout----===//
1+
//===-- Exhaustive test for tanf ------------------------------------------===//
32
//
43
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
54
// See https://llvm.org/LICENSE.txt for license information.

lldb/include/lldb/Expression/DWARFExpressionList.h

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#ifndef LLDB_EXPRESSION_DWARFEXPRESSIONLIST_H
1010
#define LLDB_EXPRESSION_DWARFEXPRESSIONLIST_H
1111

12+
#include "lldb/Core/AddressRange.h"
1213
#include "lldb/Core/Value.h"
1314
#include "lldb/Expression/DWARFExpression.h"
1415
#include "lldb/Utility/RangeMap.h"
@@ -59,6 +60,21 @@ class DWARFExpressionList {
5960

6061
lldb::addr_t GetFuncFileAddress() { return m_func_file_addr; }
6162

63+
/// Represents an entry in the DWARFExpressionList with all needed metadata.
64+
struct DWARFExpressionEntry {
65+
/// Represents a DWARF location range in the DWARF unit’s file‐address space
66+
std::optional<AddressRange> file_range; ///< None = always-valid single expr
67+
const DWARFExpression *expr;
68+
};
69+
70+
/// Returns a DWARFExpressionEntry whose file_range contains the given
71+
/// load‐address. `func_load_addr` is the load‐address of the function
72+
/// start; `load_addr` is the full runtime PC. On success, `expr` is
73+
/// non-null.
74+
std::optional<DWARFExpressionEntry>
75+
GetExpressionEntryAtAddress(lldb::addr_t func_load_addr,
76+
lldb::addr_t load_addr) const;
77+
6278
const DWARFExpression *GetExpressionAtAddress(lldb::addr_t func_load_addr,
6379
lldb::addr_t load_addr) const;
6480

lldb/source/Expression/DWARFExpressionList.cpp

Lines changed: 34 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
//===----------------------------------------------------------------------===//
88

99
#include "lldb/Expression/DWARFExpressionList.h"
10+
#include "lldb/Core/AddressRange.h"
1011
#include "lldb/Symbol/Function.h"
1112
#include "lldb/Target/RegisterContext.h"
1213
#include "lldb/Target/StackFrame.h"
@@ -20,7 +21,7 @@ bool DWARFExpressionList::IsAlwaysValidSingleExpr() const {
2021
return GetAlwaysValidExpr() != nullptr;
2122
}
2223

23-
const DWARFExpression * DWARFExpressionList::GetAlwaysValidExpr() const {
24+
const DWARFExpression *DWARFExpressionList::GetAlwaysValidExpr() const {
2425
if (m_exprs.GetSize() != 1)
2526
return nullptr;
2627
const auto *expr = m_exprs.GetEntryAtIndex(0);
@@ -53,6 +54,38 @@ bool DWARFExpressionList::ContainsAddress(lldb::addr_t func_load_addr,
5354
return GetExpressionAtAddress(func_load_addr, addr) != nullptr;
5455
}
5556

57+
std::optional<DWARFExpressionList::DWARFExpressionEntry>
58+
DWARFExpressionList::GetExpressionEntryAtAddress(lldb::addr_t func_load_addr,
59+
lldb::addr_t load_addr) const {
60+
if (const DWARFExpression *always = GetAlwaysValidExpr()) {
61+
return DWARFExpressionEntry{std::nullopt, always};
62+
}
63+
64+
if (func_load_addr == LLDB_INVALID_ADDRESS)
65+
func_load_addr = m_func_file_addr;
66+
67+
// Guard against underflow when translating a load address back into file
68+
// space.
69+
if (load_addr < func_load_addr)
70+
return std::nullopt;
71+
72+
// Guard against overflow.
73+
lldb::addr_t delta = load_addr - func_load_addr;
74+
if (delta > std::numeric_limits<lldb::addr_t>::max() - m_func_file_addr)
75+
return std::nullopt;
76+
77+
lldb::addr_t file_pc = (load_addr - func_load_addr) + m_func_file_addr;
78+
79+
if (const auto *entry = m_exprs.FindEntryThatContains(file_pc)) {
80+
AddressRange range_in_file(entry->GetRangeBase(),
81+
entry->GetRangeEnd() - entry->GetRangeBase());
82+
return DWARFExpressionEntry{range_in_file, &entry->data};
83+
}
84+
85+
// No entry covers this PC:
86+
return std::nullopt;
87+
}
88+
5689
const DWARFExpression *
5790
DWARFExpressionList::GetExpressionAtAddress(lldb::addr_t func_load_addr,
5891
lldb::addr_t load_addr) const {

0 commit comments

Comments
 (0)