Skip to content

Commit 6722693

Browse files
Add std::source_location to ChipError for C++20 builds (#32935)
* Add std::source_location to ChipError for C++20 builds * Fix errors due to CHIP_ERROR default constructor no longer being trivial * Restyled by clang-format * A few more fixes * Replace semicolon with comma * Add enum->int cast * Add tests and simplify constructor * Convert to gtest * Restyled by clang-format * Restyled by gn --------- Co-authored-by: Restyled.io <commits@restyled.io>
1 parent 1174bdc commit 6722693

14 files changed

+200
-127
lines changed

src/app/FailSafeContext.cpp

+5-6
Original file line numberDiff line numberDiff line change
@@ -85,12 +85,11 @@ void FailSafeContext::ScheduleFailSafeCleanup(FabricIndex fabricIndex, bool addN
8585

8686
SetFailSafeArmed(false);
8787

88-
ChipDeviceEvent event;
89-
event.Type = DeviceEventType::kFailSafeTimerExpired;
90-
event.FailSafeTimerExpired.fabricIndex = fabricIndex;
91-
event.FailSafeTimerExpired.addNocCommandHasBeenInvoked = addNocCommandInvoked;
92-
event.FailSafeTimerExpired.updateNocCommandHasBeenInvoked = updateNocCommandInvoked;
93-
CHIP_ERROR status = PlatformMgr().PostEvent(&event);
88+
ChipDeviceEvent event{ .Type = DeviceEventType::kFailSafeTimerExpired,
89+
.FailSafeTimerExpired = { .fabricIndex = fabricIndex,
90+
.addNocCommandHasBeenInvoked = addNocCommandInvoked,
91+
.updateNocCommandHasBeenInvoked = updateNocCommandInvoked } };
92+
CHIP_ERROR status = PlatformMgr().PostEvent(&event);
9493

9594
if (status != CHIP_NO_ERROR)
9695
{

src/app/clusters/bindings/bindings.cpp

+2-3
Original file line numberDiff line numberDiff line change
@@ -259,9 +259,8 @@ CHIP_ERROR BindingTableAccess::WriteBindingTable(const ConcreteDataAttributePath
259259

260260
CHIP_ERROR BindingTableAccess::NotifyBindingsChanged()
261261
{
262-
DeviceLayer::ChipDeviceEvent event;
263-
event.Type = DeviceLayer::DeviceEventType::kBindingsChangedViaCluster;
264-
event.BindingsChanged.fabricIndex = mAccessingFabricIndex;
262+
DeviceLayer::ChipDeviceEvent event{ .Type = DeviceLayer::DeviceEventType::kBindingsChangedViaCluster,
263+
.BindingsChanged = { .fabricIndex = mAccessingFabricIndex } };
265264
return chip::DeviceLayer::PlatformMgr().PostEvent(&event);
266265
}
267266

src/include/platform/CHIPDeviceEvent.h

-1
Original file line numberDiff line numberDiff line change
@@ -530,7 +530,6 @@ struct ChipDeviceEvent final
530530
} OtaStateChanged;
531531
};
532532

533-
void Clear() { memset(this, 0, sizeof(*this)); }
534533
bool IsPublic() const { return DeviceEventType::IsPublic(Type); }
535534
bool IsInternal() const { return DeviceEventType::IsInternal(Type); }
536535
bool IsPlatformSpecific() const { return DeviceEventType::IsPlatformSpecific(Type); }

src/include/platform/internal/GenericConnectivityManagerImpl_Thread.ipp

+4-5
Original file line numberDiff line numberDiff line change
@@ -70,11 +70,10 @@ void GenericConnectivityManagerImpl_Thread<ImplClass>::UpdateServiceConnectivity
7070
mFlags.Set(Flags::kHaveServiceConnectivity, haveServiceConnectivity);
7171

7272
{
73-
ChipDeviceEvent event;
74-
event.Clear();
75-
event.Type = DeviceEventType::kServiceConnectivityChange;
76-
event.ServiceConnectivityChange.ViaThread.Result =
77-
(haveServiceConnectivity) ? kConnectivity_Established : kConnectivity_Lost;
73+
ChipDeviceEvent event{ .Type = DeviceEventType::kServiceConnectivityChange,
74+
.ServiceConnectivityChange = { .ViaThread = { .Result = (haveServiceConnectivity)
75+
? kConnectivity_Established
76+
: kConnectivity_Lost } } };
7877
event.ServiceConnectivityChange.Overall.Result = event.ServiceConnectivityChange.ViaThread.Result;
7978
CHIP_ERROR status = PlatformMgr().PostEvent(&event);
8079
if (status != CHIP_NO_ERROR)

src/lib/core/CHIPError.h

+46-10
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,10 @@
3535
#include <limits>
3636
#include <type_traits>
3737

38+
#if __cplusplus >= 202002L
39+
#include <source_location>
40+
#endif // __cplusplus >= 202002L
41+
3842
namespace chip {
3943

4044
/**
@@ -112,9 +116,13 @@ class ChipError
112116

113117
// Helper for declaring constructors without too much repetition.
114118
#if CHIP_CONFIG_ERROR_SOURCE
115-
#define CHIP_INITIALIZE_ERROR_SOURCE(f, l) , mFile((f)), mLine((l))
116-
#else // CHIP_CONFIG_ERROR_SOURCE
117-
#define CHIP_INITIALIZE_ERROR_SOURCE(f, l)
119+
#if __cplusplus >= 202002L
120+
#define CHIP_INITIALIZE_ERROR_SOURCE(f, l, loc) , mFile((f)), mLine((l)), mSourceLocation((loc))
121+
#else
122+
#define CHIP_INITIALIZE_ERROR_SOURCE(f, l, loc) , mFile((f)), mLine((l))
123+
#endif // __cplusplus >= 202002L
124+
#else // CHIP_CONFIG_ERROR_SOURCE
125+
#define CHIP_INITIALIZE_ERROR_SOURCE(f, l, loc)
118126
#endif // CHIP_CONFIG_ERROR_SOURCE
119127

120128
/**
@@ -123,23 +131,35 @@ class ChipError
123131
* @note
124132
* The result is valid only if CanEncapsulate() is true.
125133
*/
126-
constexpr ChipError(Range range, ValueType value) :
127-
mError(MakeInteger(range, (value & MakeMask(0, kValueLength)))) CHIP_INITIALIZE_ERROR_SOURCE(nullptr, 0)
134+
constexpr ChipError(Range range, ValueType value) : ChipError(range, value, /*file=*/nullptr, /*line=*/0) {}
135+
#if __cplusplus >= 202002L
136+
constexpr ChipError(Range range, ValueType value, const char * file, unsigned int line,
137+
std::source_location location = std::source_location::current()) :
138+
mError(MakeInteger(range, (value & MakeMask(0, kValueLength)))) CHIP_INITIALIZE_ERROR_SOURCE(file, line, location)
128139
{}
140+
#else
129141
constexpr ChipError(Range range, ValueType value, const char * file, unsigned int line) :
130-
mError(MakeInteger(range, (value & MakeMask(0, kValueLength)))) CHIP_INITIALIZE_ERROR_SOURCE(file, line)
142+
mError(MakeInteger(range, (value & MakeMask(0, kValueLength)))) CHIP_INITIALIZE_ERROR_SOURCE(file, line, /*loc=*/nullptr)
131143
{}
144+
#endif // __cplusplus >= 202002L
132145

133146
/**
134147
* Construct a CHIP_ERROR for SdkPart @a part with @a code.
135148
*
136149
* @note
137150
* The macro version CHIP_SDK_ERROR checks that the numeric value is constant and well-formed.
138151
*/
139-
constexpr ChipError(SdkPart part, uint8_t code) : mError(MakeInteger(part, code)) CHIP_INITIALIZE_ERROR_SOURCE(nullptr, 0) {}
152+
constexpr ChipError(SdkPart part, uint8_t code) : ChipError(part, code, /*file=*/nullptr, /*line=*/0) {}
153+
#if __cplusplus >= 202002L
154+
constexpr ChipError(SdkPart part, uint8_t code, const char * file, unsigned int line,
155+
std::source_location location = std::source_location::current()) :
156+
mError(MakeInteger(part, code)) CHIP_INITIALIZE_ERROR_SOURCE(file, line, location)
157+
{}
158+
#else
140159
constexpr ChipError(SdkPart part, uint8_t code, const char * file, unsigned int line) :
141-
mError(MakeInteger(part, code)) CHIP_INITIALIZE_ERROR_SOURCE(file, line)
160+
mError(MakeInteger(part, code)) CHIP_INITIALIZE_ERROR_SOURCE(file, line, /*loc=*/nullptr)
142161
{}
162+
#endif // __cplusplus >= 202002L
143163

144164
/**
145165
* Construct a CHIP_ERROR constant for SdkPart @a part with @a code at the current source line.
@@ -159,10 +179,17 @@ class ChipError
159179
* @note
160180
* This is intended to be used only in foreign function interfaces.
161181
*/
162-
explicit constexpr ChipError(StorageType error) : mError(error) CHIP_INITIALIZE_ERROR_SOURCE(nullptr, 0) {}
182+
explicit constexpr ChipError(StorageType error) : ChipError(error, /*file=*/nullptr, /*line=*/0) {}
183+
#if __cplusplus >= 202002L
184+
explicit constexpr ChipError(StorageType error, const char * file, unsigned int line,
185+
std::source_location location = std::source_location::current()) :
186+
mError(error) CHIP_INITIALIZE_ERROR_SOURCE(file, line, location)
187+
{}
188+
#else
163189
explicit constexpr ChipError(StorageType error, const char * file, unsigned int line) :
164-
mError(error) CHIP_INITIALIZE_ERROR_SOURCE(file, line)
190+
mError(error) CHIP_INITIALIZE_ERROR_SOURCE(file, line, /*loc=*/nullptr)
165191
{}
192+
#endif // __cplusplus >= 202002L
166193

167194
#undef CHIP_INITIALIZE_ERROR_SOURCE
168195

@@ -299,6 +326,12 @@ class ChipError
299326
*/
300327
unsigned int GetLine() const { return mLine; }
301328

329+
#if __cplusplus >= 202002L
330+
/**
331+
* Get the source_location of the point where the error occurred.
332+
*/
333+
const std::source_location & GetSourceLocation() { return mSourceLocation; }
334+
#endif // __cplusplus >= 202002L
302335
#endif // CHIP_CONFIG_ERROR_SOURCE
303336

304337
private:
@@ -365,6 +398,9 @@ class ChipError
365398
#if CHIP_CONFIG_ERROR_SOURCE
366399
const char * mFile;
367400
unsigned int mLine;
401+
#if __cplusplus >= 202002L
402+
std::source_location mSourceLocation;
403+
#endif // __cplusplus >= 202002L
368404
#endif // CHIP_CONFIG_ERROR_SOURCE
369405

370406
public:

src/lib/core/tests/BUILD.gn

+1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ chip_test_suite("tests") {
2424
test_sources = [
2525
"TestCATValues.cpp",
2626
"TestCHIPCallback.cpp",
27+
"TestCHIPError.cpp",
2728
"TestCHIPErrorStr.cpp",
2829
"TestOTAImageHeader.cpp",
2930
"TestOptional.cpp",

src/lib/core/tests/TestCHIPError.cpp

+72
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
/*
2+
*
3+
* Copyright (c) 2024 Project CHIP Authors
4+
* All rights reserved.
5+
*
6+
* Licensed under the Apache License, Version 2.0 (the "License");
7+
* you may not use this file except in compliance with the License.
8+
* You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing, software
13+
* distributed under the License is distributed on an "AS IS" BASIS,
14+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
* See the License for the specific language governing permissions and
16+
* limitations under the License.
17+
*/
18+
19+
#include <string>
20+
21+
#include <lib/core/CHIPError.h>
22+
23+
#include <gtest/gtest.h>
24+
25+
namespace chip {
26+
namespace {
27+
28+
TEST(ChipErrorTest, RangeConstructor)
29+
{
30+
ChipError error(ChipError::Range::kSDK, /*value=*/1, __FILE__, __LINE__);
31+
#if CHIP_CONFIG_ERROR_SOURCE
32+
EXPECT_EQ(error.GetFile(), __FILE__);
33+
EXPECT_EQ(error.GetLine(), 30u);
34+
#if __cplusplus >= 202002L
35+
std::source_location location = error.GetSourceLocation();
36+
EXPECT_EQ(location.line(), 30u);
37+
EXPECT_EQ(location.file_name(), __FILE__);
38+
#endif // __cplusplus >= 202002L
39+
#endif // CHIP_CONFIG_ERROR_SOURCE
40+
}
41+
42+
TEST(ChipErrorTest, SdkPartConstructor)
43+
{
44+
ChipError error(ChipError::SdkPart::kCore, /*code=*/1, __FILE__, __LINE__);
45+
#if CHIP_CONFIG_ERROR_SOURCE
46+
EXPECT_EQ(error.GetFile(), __FILE__);
47+
EXPECT_EQ(error.GetLine(), 44u);
48+
#if __cplusplus >= 202002L
49+
std::source_location location = error.GetSourceLocation();
50+
EXPECT_EQ(location.line(), 44u);
51+
EXPECT_EQ(location.file_name(), __FILE__);
52+
#endif // __cplusplus >= 202002L
53+
#endif // CHIP_CONFIG_ERROR_SOURCE
54+
}
55+
56+
TEST(ChipErrorTest, StorageTypeConstructor)
57+
{
58+
ChipError error(/*error=*/1, __FILE__, __LINE__);
59+
EXPECT_EQ(error.AsInteger(), 1u);
60+
#if CHIP_CONFIG_ERROR_SOURCE
61+
EXPECT_EQ(error.GetFile(), __FILE__);
62+
EXPECT_EQ(error.GetLine(), 58u);
63+
#if __cplusplus >= 202002L
64+
std::source_location location = error.GetSourceLocation();
65+
EXPECT_EQ(location.line(), 58u);
66+
EXPECT_EQ(location.file_name(), __FILE__);
67+
#endif // __cplusplus >= 202002L
68+
#endif // CHIP_CONFIG_ERROR_SOURCE
69+
}
70+
71+
} // namespace
72+
} // namespace chip

src/platform/DeviceControlServer.cpp

+10-14
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,11 @@ DeviceControlServer & DeviceControlServer::DeviceControlSvr()
3636

3737
CHIP_ERROR DeviceControlServer::PostCommissioningCompleteEvent(NodeId peerNodeId, FabricIndex accessingFabricIndex)
3838
{
39-
ChipDeviceEvent event;
39+
ChipDeviceEvent event{
4040

41-
event.Type = DeviceEventType::kCommissioningComplete;
42-
event.CommissioningComplete.nodeId = peerNodeId;
43-
event.CommissioningComplete.fabricIndex = accessingFabricIndex;
41+
.Type = DeviceEventType::kCommissioningComplete,
42+
.CommissioningComplete = { .nodeId = peerNodeId, .fabricIndex = accessingFabricIndex }
43+
};
4444

4545
return PlatformMgr().PostEvent(&event);
4646
}
@@ -66,31 +66,27 @@ CHIP_ERROR DeviceControlServer::SetRegulatoryConfig(uint8_t location, const Char
6666

6767
CHIP_ERROR DeviceControlServer::PostConnectedToOperationalNetworkEvent(ByteSpan networkID)
6868
{
69-
ChipDeviceEvent event;
70-
event.Type = DeviceEventType::kOperationalNetworkEnabled;
71-
// TODO(cecille): This should be some way to specify thread or wifi.
72-
event.OperationalNetwork.network = 0;
69+
ChipDeviceEvent event{ .Type = DeviceEventType::kOperationalNetworkEnabled,
70+
// TODO(cecille): This should be some way to specify thread or wifi.
71+
.OperationalNetwork = { .network = 0 } };
7372
return PlatformMgr().PostEvent(&event);
7473
}
7574

7675
CHIP_ERROR DeviceControlServer::PostCloseAllBLEConnectionsToOperationalNetworkEvent()
7776
{
78-
ChipDeviceEvent event;
79-
event.Type = DeviceEventType::kCloseAllBleConnections;
77+
ChipDeviceEvent event{ .Type = DeviceEventType::kCloseAllBleConnections };
8078
return PlatformMgr().PostEvent(&event);
8179
}
8280

8381
CHIP_ERROR DeviceControlServer::PostWiFiDeviceAvailableNetworkEvent()
8482
{
85-
ChipDeviceEvent event;
86-
event.Type = DeviceEventType::kWiFiDeviceAvailable;
83+
ChipDeviceEvent event{ .Type = DeviceEventType::kWiFiDeviceAvailable };
8784
return PlatformMgr().PostEvent(&event);
8885
}
8986

9087
CHIP_ERROR DeviceControlServer::PostOperationalNetworkStartedEvent()
9188
{
92-
ChipDeviceEvent event;
93-
event.Type = DeviceEventType::kOperationalNetworkStarted;
89+
ChipDeviceEvent event{ .Type = DeviceEventType::kOperationalNetworkStarted };
9490
return PlatformMgr().PostEvent(&event);
9591
}
9692

0 commit comments

Comments
 (0)