/* * * Copyright (c) 2021 Project CHIP Authors * 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. */ #include "SubDevice.h" #include "SubDeviceManager.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace ::chip; using namespace ::chip::Credentials; using namespace ::chip::DeviceLayer; using namespace ::chip::System; using namespace ::chip::Platform; using namespace ::chip::app::Clusters; #ifdef ENABLE_ASR_BRIDGE_SUBDEVICE_TEST static const int kNodeLabelSize = 32; // Current ZCL implementation of Struct uses a max-size array of 254 bytes static const int kDescriptorAttributeArraySize = 254; // 4 Bridged devices static SubDevice gLight1("Light 1", "Office"); static SubDevice gLight2("Light 2", "Office"); static SubDevice gLight3("Light 3", "Kitchen"); static SubDevice gLight4("Light 4", "Den"); /* BRIDGED DEVICE ENDPOINT: contains the following clusters: - On/Off - Descriptor - Bridged Device Basic */ // Declare On/Off cluster attributes DECLARE_DYNAMIC_ATTRIBUTE_LIST_BEGIN(onOffAttrs) DECLARE_DYNAMIC_ATTRIBUTE(OnOff::Attributes::OnOff::Id, BOOLEAN, 1, 0), /* on/off */ DECLARE_DYNAMIC_ATTRIBUTE_LIST_END(); // Declare Descriptor cluster attributes DECLARE_DYNAMIC_ATTRIBUTE_LIST_BEGIN(descriptorAttrs) DECLARE_DYNAMIC_ATTRIBUTE(Descriptor::Attributes::DeviceTypeList::Id, ARRAY, kDescriptorAttributeArraySize, 0), /* device list */ DECLARE_DYNAMIC_ATTRIBUTE(Descriptor::Attributes::ServerList::Id, ARRAY, kDescriptorAttributeArraySize, 0), /* server list */ DECLARE_DYNAMIC_ATTRIBUTE(Descriptor::Attributes::ClientList::Id, ARRAY, kDescriptorAttributeArraySize, 0), /* client list */ DECLARE_DYNAMIC_ATTRIBUTE(Descriptor::Attributes::PartsList::Id, ARRAY, kDescriptorAttributeArraySize, 0), /* parts list */ DECLARE_DYNAMIC_ATTRIBUTE_LIST_END(); // Declare Bridged Device Basic information cluster attributes DECLARE_DYNAMIC_ATTRIBUTE_LIST_BEGIN(bridgedDeviceBasicAttrs) DECLARE_DYNAMIC_ATTRIBUTE(BridgedDeviceBasicInformation::Attributes::NodeLabel::Id, CHAR_STRING, kNodeLabelSize, 0), /* NodeLabel */ DECLARE_DYNAMIC_ATTRIBUTE(BridgedDeviceBasicInformation::Attributes::Reachable::Id, BOOLEAN, 1, 0), /* Reachable */ DECLARE_DYNAMIC_ATTRIBUTE_LIST_END(); // Declare Cluster List for Bridged Light endpoint // TODO: It's not clear whether it would be better to get the command lists from // the ZAP config on our last fixed endpoint instead. constexpr CommandId onOffIncomingCommands[] = { app::Clusters::OnOff::Commands::Off::Id, app::Clusters::OnOff::Commands::On::Id, app::Clusters::OnOff::Commands::Toggle::Id, app::Clusters::OnOff::Commands::OffWithEffect::Id, app::Clusters::OnOff::Commands::OnWithRecallGlobalScene::Id, app::Clusters::OnOff::Commands::OnWithTimedOff::Id, kInvalidCommandId, }; DECLARE_DYNAMIC_CLUSTER_LIST_BEGIN(bridgedLightClusters) DECLARE_DYNAMIC_CLUSTER(OnOff::Id, onOffAttrs, ZAP_CLUSTER_MASK(SERVER), onOffIncomingCommands, nullptr), DECLARE_DYNAMIC_CLUSTER(Descriptor::Id, descriptorAttrs, ZAP_CLUSTER_MASK(SERVER), nullptr, nullptr), // DECLARE_DYNAMIC_CLUSTER(BridgedDeviceBasic::Id, bridgedDeviceBasicAttrs, ZAP_CLUSTER_MASK(SERVER), nullptr, nullptr) DECLARE_DYNAMIC_CLUSTER(BridgedDeviceBasicInformation::Id, bridgedDeviceBasicAttrs, ZAP_CLUSTER_MASK(SERVER), nullptr, nullptr) DECLARE_DYNAMIC_CLUSTER_LIST_END; // Declare Bridged Light endpoint DECLARE_DYNAMIC_ENDPOINT(bridgedLightEndpoint, bridgedLightClusters); DataVersion gLight1DataVersions[ArraySize(bridgedLightClusters)]; DataVersion gLight2DataVersions[ArraySize(bridgedLightClusters)]; DataVersion gLight3DataVersions[ArraySize(bridgedLightClusters)]; DataVersion gLight4DataVersions[ArraySize(bridgedLightClusters)]; const EmberAfDeviceType gRootDeviceTypes[] = { { DEVICE_TYPE_ROOT_NODE, DEVICE_VERSION_DEFAULT } }; const EmberAfDeviceType gAggregateNodeDeviceTypes[] = { { DEVICE_TYPE_BRIDGE, DEVICE_VERSION_DEFAULT } }; const EmberAfDeviceType gBridgedOnOffDeviceTypes[] = { { DEVICE_TYPE_LO_ON_OFF_LIGHT, DEVICE_VERSION_DEFAULT }, { DEVICE_TYPE_BRIDGED_NODE, DEVICE_VERSION_DEFAULT } }; extern "C" void Sync_SubDevice_test(void); extern "C" void Add_SubDevice_test(void); extern "C" void Remove_SubDevice_test(void); void Sync_SubDevice_test() { gLight1.SetReachable(true); gLight2.SetReachable(true); gLight3.SetReachable(true); gLight4.SetReachable(true); // Whenever bridged device changes its state gLight1.SetChangeCallback(&HandleDeviceStatusChanged); gLight2.SetChangeCallback(&HandleDeviceStatusChanged); gLight3.SetChangeCallback(&HandleDeviceStatusChanged); gLight4.SetChangeCallback(&HandleDeviceStatusChanged); // Add lights 1..4 --> will be mapped to ZCL endpoints 3..6 AddDeviceEndpoint(&gLight1, &bridgedLightEndpoint, Span(gBridgedOnOffDeviceTypes), Span(gLight1DataVersions), 1); AddDeviceEndpoint(&gLight2, &bridgedLightEndpoint, Span(gBridgedOnOffDeviceTypes), Span(gLight2DataVersions), 1); AddDeviceEndpoint(&gLight3, &bridgedLightEndpoint, Span(gBridgedOnOffDeviceTypes), Span(gLight3DataVersions), 1); AddDeviceEndpoint(&gLight4, &bridgedLightEndpoint, Span(gBridgedOnOffDeviceTypes), Span(gLight4DataVersions), 1); } void Add_SubDevice_test() { gLight2.SetReachable(true); gLight2.SetChangeCallback(&HandleDeviceStatusChanged); // Re-add Light 2 -- > will be mapped to ZCL endpoint 7 AddDeviceEndpoint(&gLight2, &bridgedLightEndpoint, Span(gBridgedOnOffDeviceTypes), Span(gLight2DataVersions), 1); } void Remove_SubDevice_test() { gLight2.SetChangeCallback(NULL); gLight2.SetReachable(false); // Remove Light 2 -- Others Lights remain RemoveDeviceEndpoint(&gLight2); } #endif // ENABLE_ASR_BRIDGE_SUBDEVICE_TEST