Skip to content

Commit bab66f5

Browse files
PeterC1965restyled-commitsjamesharrowhasty
authored
Address various DEM testing issues (project-chip#35067)
* Add checks for correct DEM feature map for test * Add checks for a nominalPower having a value and get slotIndex check correct * Allow a little tolerance checking the duration returned in the event as CI tests can run slower * Restyled by clang-format * Restyled by autopep8 * Add check DEM feature map step + add event registration step if necessary and renumber test cases * Fix issue project-chip#4415 Fails randomly on CI when checking pause duration * Test an illegal slot index == number of slots in a forecast * Add a test in PFR when ModifyForecastRequest does not specify NominalPower * Set ClusterRevision to 4 * First versionof DEM 1-1 * Regenerate files * Get DEM 1.1 test passing * Update test step definitions * Get featureSet option correct * Restyled by autopep8 * First cut of a Q quality test * Regenerate files following a re-bootstrap * Fix typo in comment * Cancel subscriptions at the end of the test * Add a cancel subscription method * Ensure MatterReportingAttributeChangeCallback is called after forecast is changed * Restyled by autopep8 * Restyled by isort * Fix ruff detected errors * Restyled by autopep8 * Fix the cancelling of subscriptions * Used .name instead of needing a feature string mapping. * Removed TC_DEM_1_1 now that the test plan has removed this test case. * Corrected Featuremap -> FeatureMap in test steps * Aligned verification step 2 on TC_DEM_2.3 to actual code and syncd test plan. * Aligned verification step 2 on TC_DEM_2.4 to actual code and syncd test plan. * Added in missing text in step 18 in TC_DEM_2.4 * TC_DEM_2.5 minor update to step 2 and aligning to updated test plan. * TC_DEM_2.5 - slight change to call to name args in validate_feature_map() call * TC_DEM_2.6,2.7,2.8 step 2 alignment with tweaked test plan * TC_DEM_2.6/2.7/2.8 - slight change to call to name args in validate_feature_map() call * Corrected log message in TC_DEM_2.9 step 4b * Updated TC_DEM_2.10 (Q Quality) Basic structure is there - steps need tidying up and fails due to powerAdjustmentCapability not being updated as expected. * Fixed bug where PowerAdjustReason wasn't calling MatterReportingAttributeChangeCallback when reason was changing. * Restyled by clang-format * Restyled by autopep8 * Restyled by isort * Autogen'd the TestSteps from latest test plan * Changed featureSet to 0x7b to enable PA, PFR, FA (plus other) features --------- Co-authored-by: Restyled.io <commits@restyled.io> Co-authored-by: James Harrow <james.harrow@gmail.com> Co-authored-by: Hasty Granbery <hasty@granbery.org>
1 parent ac5dfee commit bab66f5

16 files changed

+1177
-821
lines changed

examples/energy-management-app/energy-management-common/device-energy-management/include/DeviceEnergyManagementDelegateImpl.h

+1
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,7 @@ class DeviceEnergyManagementDelegate : public DeviceEnergyManagement::Delegate
189189
CHIP_ERROR SetAbsMinPower(int64_t);
190190
CHIP_ERROR SetAbsMaxPower(int64_t);
191191
CHIP_ERROR SetPowerAdjustmentCapability(const DataModel::Nullable<Structs::PowerAdjustCapabilityStruct::Type> &);
192+
CHIP_ERROR SetPowerAdjustmentCapabilityPowerAdjustReason(const PowerAdjustReasonEnum);
192193

193194
// The DeviceEnergyManagementDelegate owns the master copy of the ForecastStruct object which is accessed via GetForecast and
194195
// SetForecast. The slots field of forecast is owned and managed by the object that implements the DEMManufacturerDelegate

examples/energy-management-app/energy-management-common/device-energy-management/src/DeviceEnergyManagementDelegateImpl.cpp

+19-8
Original file line numberDiff line numberDiff line change
@@ -120,11 +120,11 @@ Status DeviceEnergyManagementDelegate::PowerAdjustRequest(const int64_t powerMw,
120120
switch (cause)
121121
{
122122
case AdjustmentCauseEnum::kLocalOptimization:
123-
mPowerAdjustCapabilityStruct.Value().cause = PowerAdjustReasonEnum::kLocalOptimizationAdjustment;
123+
SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum::kLocalOptimizationAdjustment);
124124
break;
125125

126126
case AdjustmentCauseEnum::kGridOptimization:
127-
mPowerAdjustCapabilityStruct.Value().cause = PowerAdjustReasonEnum::kGridOptimizationAdjustment;
127+
SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum::kGridOptimizationAdjustment);
128128
break;
129129

130130
default:
@@ -175,7 +175,7 @@ void DeviceEnergyManagementDelegate::HandlePowerAdjustRequestFailure()
175175

176176
mPowerAdjustmentInProgress = false;
177177

178-
mPowerAdjustCapabilityStruct.Value().cause = PowerAdjustReasonEnum::kNoAdjustment;
178+
SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum::kNoAdjustment);
179179

180180
// TODO
181181
// Should we inform the mpDEMManufacturerDelegate that PowerAdjustRequest has failed?
@@ -210,7 +210,7 @@ void DeviceEnergyManagementDelegate::HandlePowerAdjustTimerExpiry()
210210

211211
SetESAState(ESAStateEnum::kOnline);
212212

213-
mPowerAdjustCapabilityStruct.Value().cause = PowerAdjustReasonEnum::kNoAdjustment;
213+
SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum::kNoAdjustment);
214214

215215
// Generate a PowerAdjustEnd event
216216
GeneratePowerAdjustEndEvent(CauseEnum::kNormalCompletion);
@@ -264,8 +264,7 @@ CHIP_ERROR DeviceEnergyManagementDelegate::CancelPowerAdjustRequestAndGenerateEv
264264
SetESAState(ESAStateEnum::kOnline);
265265

266266
mPowerAdjustmentInProgress = false;
267-
268-
mPowerAdjustCapabilityStruct.Value().cause = PowerAdjustReasonEnum::kNoAdjustment;
267+
SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum::kNoAdjustment);
269268

270269
CHIP_ERROR err = GeneratePowerAdjustEndEvent(cause);
271270

@@ -922,6 +921,18 @@ DeviceEnergyManagementDelegate::SetPowerAdjustmentCapability(
922921
return CHIP_NO_ERROR;
923922
}
924923

924+
CHIP_ERROR
925+
DeviceEnergyManagementDelegate::SetPowerAdjustmentCapabilityPowerAdjustReason(PowerAdjustReasonEnum powerAdjustReason)
926+
{
927+
assertChipStackLockedByCurrentThread();
928+
929+
mPowerAdjustCapabilityStruct.Value().cause = powerAdjustReason;
930+
931+
MatterReportingAttributeChangeCallback(mEndpointId, DeviceEnergyManagement::Id, PowerAdjustmentCapability::Id);
932+
933+
return CHIP_NO_ERROR;
934+
}
935+
925936
CHIP_ERROR DeviceEnergyManagementDelegate::SetForecast(const DataModel::Nullable<Structs::ForecastStruct::Type> & forecast)
926937
{
927938
assertChipStackLockedByCurrentThread();
@@ -962,9 +973,9 @@ CHIP_ERROR DeviceEnergyManagementDelegate::SetOptOutState(OptOutStateEnum newVal
962973
if (mPowerAdjustmentInProgress)
963974
{
964975
if ((newValue == OptOutStateEnum::kLocalOptOut &&
965-
mPowerAdjustCapabilityStruct.Value().cause == PowerAdjustReasonEnum::kLocalOptimizationAdjustment) ||
976+
GetPowerAdjustmentCapability().Value().cause == PowerAdjustReasonEnum::kLocalOptimizationAdjustment) ||
966977
(newValue == OptOutStateEnum::kGridOptOut &&
967-
mPowerAdjustCapabilityStruct.Value().cause == PowerAdjustReasonEnum::kGridOptimizationAdjustment) ||
978+
GetPowerAdjustmentCapability().Value().cause == PowerAdjustReasonEnum::kGridOptimizationAdjustment) ||
968979
newValue == OptOutStateEnum::kOptOut)
969980
{
970981
err = CancelPowerAdjustRequestAndGenerateEvent(DeviceEnergyManagement::CauseEnum::kUserOptOut);

examples/energy-management-app/energy-management-common/energy-management-app.matter

+1-1
Original file line numberDiff line numberDiff line change
@@ -2704,7 +2704,7 @@ endpoint 1 {
27042704
callback attribute eventList;
27052705
callback attribute attributeList;
27062706
callback attribute featureMap;
2707-
ram attribute clusterRevision default = 3;
2707+
ram attribute clusterRevision default = 4;
27082708

27092709
handle command PowerAdjustRequest;
27102710
handle command CancelPowerAdjustRequest;

examples/energy-management-app/energy-management-common/energy-management-app.zap

+1-1
Original file line numberDiff line numberDiff line change
@@ -4210,7 +4210,7 @@
42104210
"storageOption": "RAM",
42114211
"singleton": 0,
42124212
"bounded": 0,
4213-
"defaultValue": "3",
4213+
"defaultValue": "4",
42144214
"reportable": 1,
42154215
"minInterval": 1,
42164216
"maxInterval": 65534,

src/app/clusters/device-energy-management-server/device-energy-management-server.cpp

+3-3
Original file line numberDiff line numberDiff line change
@@ -676,7 +676,7 @@ void Instance::HandleModifyForecastRequest(HandlerContext & ctx, const Commands:
676676
const Structs::SlotAdjustmentStruct::Type & slotAdjustment = iterator.GetValue();
677677

678678
// Check for an invalid slotIndex
679-
if (slotAdjustment.slotIndex > forecast.Value().slots.size())
679+
if (slotAdjustment.slotIndex >= forecast.Value().slots.size())
680680
{
681681
ChipLogError(Zcl, "DEM: Bad slot index %d", slotAdjustment.slotIndex);
682682
ctx.mCommandHandler.AddStatus(ctx.mRequestPath, Status::Failure);
@@ -696,8 +696,8 @@ void Instance::HandleModifyForecastRequest(HandlerContext & ctx, const Commands:
696696
// NominalPower is only relevant if PFR is supported
697697
if (HasFeature(Feature::kPowerForecastReporting))
698698
{
699-
if (!slot.minPowerAdjustment.HasValue() || !slot.maxPowerAdjustment.HasValue() ||
700-
slotAdjustment.nominalPower.Value() < slot.minPowerAdjustment.Value() ||
699+
if (!slotAdjustment.nominalPower.HasValue() || !slot.minPowerAdjustment.HasValue() ||
700+
!slot.maxPowerAdjustment.HasValue() || slotAdjustment.nominalPower.Value() < slot.minPowerAdjustment.Value() ||
701701
slotAdjustment.nominalPower.Value() > slot.maxPowerAdjustment.Value())
702702
{
703703
ChipLogError(Zcl, "DEM: Bad nominalPower");

src/python_testing/TC_DEMTestBase.py

+20
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,26 @@ async def check_dem_attribute(self, attribute, expected_value, endpoint: int = N
3838
asserts.assert_equal(value, expected_value,
3939
f"Unexpected '{attribute}' value - expected {expected_value}, was {value}")
4040

41+
async def validate_feature_map(self, must_have_features, must_not_have_features):
42+
feature_map = await self.read_dem_attribute_expect_success(attribute="FeatureMap")
43+
for must_have_feature in must_have_features:
44+
asserts.assert_true(feature_map & must_have_feature,
45+
f"{must_have_feature.name} must be set but is not. feature_map 0x{feature_map:x}")
46+
47+
for must_not_have_feature in must_not_have_features:
48+
asserts.assert_false(feature_map & must_not_have_feature,
49+
f"{must_not_have_feature.name} is not allowed to be set. feature_map 0x{feature_map:x}")
50+
51+
async def validate_pfr_or_sfr_in_feature_map(self):
52+
feature_map = await self.read_dem_attribute_expect_success(attribute="FeatureMap")
53+
54+
illegal_combination = Clusters.DeviceEnergyManagement.Bitmaps.Feature.kPowerForecastReporting | Clusters.DeviceEnergyManagement.Bitmaps.Feature.kStateForecastReporting
55+
asserts.assert_not_equal(feature_map & illegal_combination, illegal_combination,
56+
f"Cannot have kPowerForecastReporting and kStateForecastReporting both set. feature_map 0x{feature_map:x}")
57+
58+
asserts.assert_not_equal(feature_map & illegal_combination, 0,
59+
f"Must have one of kPowerForecastReporting and kStateForecastReporting set. feature_map 0x{feature_map:x}")
60+
4161
async def send_power_adjustment_command(self, power: int, duration: int,
4262
cause: Clusters.Objects.DeviceEnergyManagement.Enums.CauseEnum,
4363
endpoint: int = None, timedRequestTimeoutMs: int = 3000,

0 commit comments

Comments
 (0)