Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update rvc mode cluters with new mode restrictions #31560

Merged
Show file tree
Hide file tree
Changes from 9 commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
62ecf35
Updated step 3 in TC 1.1 for RvcRunMode and RvcCleanMode
hicklin Jan 19, 2024
2c00c99
Updated TC 1.2 for RvcRunMode and RvcCleanMode cluters.
hicklin Jan 19, 2024
7227a80
Added TC 2.2 for the RvcCleanMode cluster.
hicklin Jan 19, 2024
76cbde1
Restyled by autopep8
restyled-commits Jan 19, 2024
d3ffb58
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 22, 2024
cc5e3ed
Added TC 2.2 for the RvcRunMode cluster.
hicklin Jan 22, 2024
5dde47b
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 22, 2024
647d4f7
Removed unused imports.
hicklin Jan 22, 2024
423daf4
Regenerated zap files.
hicklin Jan 22, 2024
754d8de
Added the PICS provider methods to the new python tests.
hicklin Jan 22, 2024
a97b2c5
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 22, 2024
cf781ab
Changed the features supported by the RVC mode cluters in the all-clu…
hicklin Jan 23, 2024
41a67ae
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 23, 2024
d508cbc
Added the mapping mode tag to the all-clusters-app example
hicklin Jan 23, 2024
e08330c
Changed the response returned by the RVC clean mode's handler of the …
hicklin Jan 24, 2024
48ace96
Updated TC_RVCCLEAN_2_2 to remove incorrect type checks.
hicklin Jan 24, 2024
18f5040
Apply suggestions from code review
hicklin Jan 24, 2024
9cd3186
Updated the RVC run ChangeToMode handler in the all-clusters-app to m…
hicklin Jan 24, 2024
8a122a1
Updated the cl-pics-values for the RVC Run and Clean clusters.
hicklin Jan 24, 2024
1a89bae
Future proofed the enum to text function and change to using the --en…
hicklin Jan 24, 2024
ddd30b6
Fixed retrival of the endpoint setting.
hicklin Jan 24, 2024
1d066c4
Simplified some of the test code following review.
hicklin Jan 24, 2024
45505e4
Removed test steps to match the test plan.
hicklin Jan 24, 2024
7f2861c
Changed the capture of the endpoint for the RVC run and RVC clean tes…
hicklin Jan 24, 2024
4e49153
Restyled by clang-format
restyled-commits Jan 24, 2024
a8f10e6
Restyled by autopep8
restyled-commits Jan 24, 2024
d77738f
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 24, 2024
dc2f6ef
Regenerated zap files.
hicklin Jan 24, 2024
e46137d
Removed duplicate RVCRUNM PICS from the ci-pics-values.
hicklin Jan 25, 2024
f7ea7f5
Updated PICS.yaml to reflect the new PICS requirements for the RvcRun…
hicklin Jan 25, 2024
861434b
Made all RVC python tests consistent regarding the capture of the end…
hicklin Jan 25, 2024
98b544f
Apply typo suggestions from code review
hicklin Jan 25, 2024
31b6df2
Fixed the RVC clean handle change to mode in the all-clusters-app.
hicklin Jan 25, 2024
421186b
Merge branch 'update_rvc_mode_cluters_with_new_mode_restrictions' of …
hicklin Jan 25, 2024
7b08a3a
Restyled by clang-format
restyled-commits Jan 25, 2024
8329b67
Merge branch 'master' into update_rvc_mode_cluters_with_new_mode_rest…
hicklin Jan 25, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 0 additions & 12 deletions src/app/tests/suites/certification/Test_TC_RVCCLEANM_1_1.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -42,25 +42,13 @@ tests:
type: int16u

- label: "Step 3: TH reads from the DUT the FeatureMap attribute."
PICS: " !RVCCLEANM.S.F00 "
command: "readAttribute"
attribute: "FeatureMap"
response:
value: 0
constraints:
type: bitmap32

- label:
"Step 3: Given RVCCLEANM.S.F00(DEPONOFF) ensure featuremap has the
correct bit set"
PICS: RVCCLEANM.S.F00
command: "readAttribute"
attribute: "FeatureMap"
response:
constraints:
type: bitmap32
hasMasksSet: [0x1]

plauric marked this conversation as resolved.
Show resolved Hide resolved
- label: "Step 4a: TH reads from the DUT the AttributeList attribute."
PICS: PICS_EVENT_LIST_ENABLED
command: "readAttribute"
Expand Down
14 changes: 1 addition & 13 deletions src/app/tests/suites/certification/Test_TC_RVCRUNM_1_1.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -41,26 +41,14 @@ tests:
constraints:
type: int16u

- label: "Step 3a: TH reads from the DUT the FeatureMap attribute."
PICS: " !RVCRUNM.S.F00 "
- label: "Step 3: TH reads from the DUT the FeatureMap attribute."
command: "readAttribute"
attribute: "FeatureMap"
response:
value: 0
constraints:
type: bitmap32

- label:
"Step 3b: Given RVCRUNM.S.F00(DEPONOFF) ensure featuremap has the
correct bit set"
PICS: RVCRUNM.S.F00
command: "readAttribute"
attribute: "FeatureMap"
response:
constraints:
type: bitmap32
hasMasksSet: [0x1]

plauric marked this conversation as resolved.
Show resolved Hide resolved
- label: "Step 4a: TH reads from the DUT the AttributeList attribute."
PICS: PICS_EVENT_LIST_ENABLED
command: "readAttribute"
Expand Down
96 changes: 60 additions & 36 deletions src/python_testing/TC_RVCCLEANM_1_2.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@
import logging

import chip.clusters as Clusters
from chip.clusters.Types import NullValue
from matter_testing_support import MatterBaseTest, async_test_body, default_matter_test_main
from mobly import asserts

Expand All @@ -28,6 +27,21 @@


class TC_RVCCLEANM_1_2(MatterBaseTest):
def __init__(self, *args):
super().__init__(args)
self.commonTags = {0x0: 'Auto',
0x1: 'Quick',
0x2: 'Quiet',
0x3: 'LowNoise',
0x4: 'LowEnergy',
0x5: 'Vacation',
0x6: 'Min',
0x7: 'Max',
0x8: 'Night',
0x9: 'Day'}
self.cleanTags = [tag.value for tag in Clusters.RvcCleanMode.Enums.ModeTag
if tag is not Clusters.RvcCleanMode.Enums.ModeTag.kUnknownEnumValue]
self.supported_modes_dut = []

async def read_mod_attribute_expect_success(self, endpoint, attribute):
cluster = Clusters.Objects.RvcCleanMode
Expand Down Expand Up @@ -55,64 +69,74 @@ async def test_TC_RVCCLEANM_1_2(self):

logging.info("SupportedModes: %s" % (supported_modes))

# Verify that the list has at least 2 and at most 255 entries
asserts.assert_greater_equal(len(supported_modes), 2, "SupportedModes must have at least 2 entries!")
asserts.assert_less_equal(len(supported_modes), 255, "SupportedModes must have at most 255 entries!")

modes = []
# Verify that each ModeOptionsStruct entry has a unique Mode field value
hicklin marked this conversation as resolved.
Show resolved Hide resolved
for m in supported_modes:
if m.mode in modes:
if m.mode in self.supported_modes_dut:
asserts.fail("SupportedModes must have unique mode values!")
else:
modes.append(m.mode)
self.supported_modes_dut.append(m.mode)

# Verify that each ModeOptionsStruct entry has a unique Label field value
labels = []
for m in supported_modes:
if m.label in labels:
asserts.fail("SupportedModes must have unique mode label values!")
else:
labels.append(m.label)

# common mode tags
commonTags = {0x0: 'Auto',
0x1: 'Quick',
0x2: 'Quiet',
0x3: 'LowNoise',
0x4: 'LowEnergy',
0x5: 'Vacation',
0x6: 'Min',
0x7: 'Max',
0x8: 'Night',
0x9: 'Day'}

cleanTags = [tag.value for tag in Clusters.RvcCleanMode.Enums.ModeTag
if tag is not Clusters.RvcCleanMode.Enums.ModeTag.kUnknownEnumValue]
# Verify that each ModeOptionsStruct entry's ModeTags field has:
for m in supported_modes:
# * at least one entry
if len(m.modeTags) == 0:
asserts.fail("SupportedModes must have at least one mode tag!")

at_least_one_common_or_clean_tag = False
for t in m.modeTags:
# * the values of the Value fields that are not larger than 16 bits
if t.value > 0xFFFF or t.value < 0:
asserts.fail("Mode tage values must not be lager tha 16 bits!")
hicklin marked this conversation as resolved.
Show resolved Hide resolved

# * for each Value field: {isCommonOrDerivedOrMfgTagsVal}
is_mfg = (0x8000 <= t.value <= 0xBFFF)
if (t.value not in self.commonTags and
t.value not in self.cleanTags and
not is_mfg):
asserts.fail("Mode tag value is not a common tag, clean tag or vendor tag!")

# * for at least one Value field: {isCommonOrDerivedTagsVal}
if not is_mfg:
at_least_one_common_or_clean_tag = True

if not at_least_one_common_or_clean_tag:
asserts.fail("At least one mode tag must be a common tag or clean tag!")

# Verify that at least one ModeOptionsStruct entry includes either the
# Vacuum(0x4001) mode tag or the Mop(0x4002)mode tag in the ModeTags field
has_vacuum_or_mop_mode_tag = False
cecille marked this conversation as resolved.
Show resolved Hide resolved
for m in supported_modes:
if has_vacuum_or_mop_mode_tag:
break

for t in m.modeTags:
is_mfg = (0x8000 <= t.value and t.value <= 0xBFFF)
asserts.assert_true(t.value in commonTags.keys() or t.value in cleanTags or is_mfg,
"Found a SupportedModes entry with invalid mode tag value!")
if t.value in [Clusters.RvcCleanMode.Enums.ModeTag.kVacuum,
Clusters.RvcCleanMode.Enums.ModeTag.kMop]:
has_vacuum_or_mop_mode_tag = True
break

if not has_vacuum_or_mop_mode_tag:
asserts.fail("At least one ModeOptionsStruct entry must include either the "
"Vacuum(0x4001) mode tag or the Mop(0x4002)mode tag in the ModeTags field")
hicklin marked this conversation as resolved.
Show resolved Hide resolved

if self.check_pics("RVCCLEANM.S.A0001"):
self.print_step(3, "Read CurrentMode attribute")
current_mode = await self.read_mod_attribute_expect_success(endpoint=self.endpoint, attribute=attributes.CurrentMode)

logging.info("CurrentMode: %s" % (current_mode))
asserts.assert_true(current_mode in modes, "CurrentMode is not a supported mode!")

if self.check_pics("RVCCLEANM.S.A0003"):
self.print_step(4, "Read OnMode attribute")
on_mode = await self.read_mod_attribute_expect_success(endpoint=self.endpoint, attribute=attributes.OnMode)

logging.info("OnMode: %s" % (on_mode))
asserts.assert_true(on_mode in modes or on_mode == NullValue, "OnMode is not a supported mode!")

if self.check_pics("RVCCLEANM.S.A0002"):
self.print_step(5, "Read StartUpMode attribute")
startup_mode = await self.read_mod_attribute_expect_success(endpoint=self.endpoint, attribute=attributes.StartUpMode)

logging.info("StartUpMode: %s" % (startup_mode))
asserts.assert_true(startup_mode in modes or startup_mode == NullValue, "StartUpMode is not a supported mode!")
asserts.assert_true(current_mode in self.supported_modes_dut, "CurrentMode is not a supported mode!")


if __name__ == "__main__":
Expand Down
146 changes: 146 additions & 0 deletions src/python_testing/TC_RVCCLEANM_2_2.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
#
# Copyright (c) 2023 Project CHIP Authors
hicklin marked this conversation as resolved.
Show resolved Hide resolved
# All rights reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#

import chip.clusters as Clusters
from matter_testing_support import MatterBaseTest, async_test_body, default_matter_test_main, type_matches
from mobly import asserts

# This test requires several additional command line arguments
hicklin marked this conversation as resolved.
Show resolved Hide resolved
# run with
# --int-arg PIXIT_ENDPOINT:<endpoint> PIXIT.RVCCLEANM.MODE_CHANGE_OK:<mode id> PIXIT.RVCCLEANM.MODE_CHANGE_FAIL:<mode id>
hicklin marked this conversation as resolved.
Show resolved Hide resolved


class TC_RVCCLEANM_2_2(MatterBaseTest):

def __init__(self, *args):
super().__init__(args)
self.endpoint = 0
self.supported_run_modes = {} # these are the ModeOptionStructs
self.supported_run_modes_dut = []
self.supported_clean_modes_dut = []
self.run_mode_dut = 0
self.old_clean_mode_dut = 0
self.new_clean_mode_th = 0

async def read_mod_attribute_expect_success(self, cluster, attribute):
return await self.read_single_attribute_check_success(
endpoint=self.endpoint, cluster=cluster, attribute=attribute)

async def read_run_supported_modes(self) -> Clusters.Objects.RvcRunMode.Attributes.SupportedModes:
ret = await self.read_mod_attribute_expect_success(
Clusters.RvcRunMode,
Clusters.RvcRunMode.Attributes.SupportedModes)
asserts.assert_true(type_matches(ret, Clusters.Objects.RvcRunMode.Attributes.SupportedModes), "")
return ret

async def read_clean_supported_modes(self) -> Clusters.Objects.RvcCleanMode.Attributes.SupportedModes:
ret = await self.read_mod_attribute_expect_success(
Clusters.RvcCleanMode,
Clusters.RvcCleanMode.Attributes.SupportedModes)
asserts.assert_true(type_matches(ret, Clusters.Objects.RvcCleanMode.Attributes.SupportedModes), "")
return ret

async def send_change_to_mode_cmd(self, newMode) -> Clusters.Objects.RvcCleanMode.Commands.ChangeToModeResponse:
ret = await self.send_single_cmd(cmd=Clusters.Objects.RvcCleanMode.Commands.ChangeToMode(newMode=newMode), endpoint=self.endpoint)
asserts.assert_true(type_matches(ret, Clusters.Objects.RvcCleanMode.Commands.ChangeToModeResponse),
"Unexpected return type for ChangeToMode")
return ret

# Prints the instruction and waits for a user input to continue
def print_instruction(self, step_number, instruction):
self.print_step(step_number, instruction)
input("Press Enter when done.\n")

@async_test_body
async def test_TC_RVCCLEANM_2_2(self):

asserts.assert_true('PIXIT_ENDPOINT' in self.matter_test_config.global_test_params,
cecille marked this conversation as resolved.
Show resolved Hide resolved
"PIXIT_ENDPOINT must be included on the command line in "
"the --int-arg flag as PIXIT_ENDPOINT:<endpoint>")

self.endpoint = self.matter_test_config.global_test_params['PIXIT_ENDPOINT']

asserts.assert_true(self.check_pics("RVCCLEANM.S"), "RVCCLEANM.S must be supported")
asserts.assert_true(self.check_pics("RVCRUNM.S.A0000"), "RVCRUNM.S.A0000 must be supported")
asserts.assert_true(self.check_pics("RVCRUNM.S.A0001"), "RVCRUNM.S.A0001 must be supported")

self.print_step(1, "Commissioning, already done")

self.print_instruction(2, "Manually put the device in a state in which the RVC Run Mode "
"cluster’s CurrentMode attribute is set to a mode without the Idle mode tag.")

self.print_step(3, "Read the RvcRunMode SupportedModes attribute")
supported_run_modes = await self.read_run_supported_modes()
for mode in supported_run_modes:
cecille marked this conversation as resolved.
Show resolved Hide resolved
self.supported_run_modes[mode.mode] = mode
# Save the Mode field values as supported_run_modes_dut
self.supported_run_modes_dut.append(mode.mode)

self.print_step(4, "Read the RvcRunMode CurrentMode attribute")
current_run_mode = await self.read_mod_attribute_expect_success(
Clusters.RvcRunMode,
Clusters.RvcRunMode.Attributes.CurrentMode)

# Verify that the DUT response contains an integer value
asserts.assert_true(type_matches(current_run_mode, Clusters.RvcRunMode.Attributes.CurrentMode),
"CurrentMode must be an integer")

# Save the value as run_mode_dut
self.run_mode_dut = current_run_mode

# Verify that the supported_run_modes_dut entry matching run_mode_dut does not have the Idle (0x4000) mode tag.
for t in self.supported_run_modes[current_run_mode].modeTags:
if t.value == Clusters.RvcRunMode.Enums.ModeTag.kIdle:
asserts.fail("The device must be is a mode with the Idle (0x4000) mode tag.")
hicklin marked this conversation as resolved.
Show resolved Hide resolved

self.print_step(5, "Read the RvcCleanMode SupportedModes attribute")
supported_clean_modes = await self.read_clean_supported_modes()
for mode in supported_clean_modes:
# Verify that the DUT response contains a list of ModeOptionsStruct entries
asserts.assert_true(type_matches(mode, Clusters.RvcCleanMode.Attributes.SupportedModes),
"Supported modes must be of type ModeOptionsStruct!")
# Save the Mode field values as supported_run_modes_dut
self.supported_clean_modes_dut.append(mode.mode)

self.print_step(6, "Read the RvcCleanMode CurrentMode attribute")
current_clean_mode = await self.read_mod_attribute_expect_success(
Clusters.RvcCleanMode,
Clusters.RvcCleanMode.Attributes.CurrentMode)

# Verify that the DUT response contains an integer value
asserts.assert_true(type_matches(current_clean_mode, Clusters.RvcCleanMode.Attributes.CurrentMode),
"CurrentMode must be an integer")

# Save the value as old_clean_mode_dut
self.old_clean_mode_dut = current_clean_mode

# Select from supported_clean_modes_dut a value which is different from old_clean_mode_dut,
# and save it as new_clean_mode_th
for mode in self.supported_clean_modes_dut:
if mode != self.old_clean_mode_dut:
self.new_clean_mode_th = mode
break

self.print_step(7, "Send ChangeToMode command")
response = await self.send_change_to_mode_cmd(self.new_clean_mode_th)
asserts.assert_equal(response.status, 3,
"The response should contain a ChangeToModeResponse command "
"with the Status set to InvalidInMode(0x03).")


if __name__ == "__main__":
default_matter_test_main()
Loading
Loading