Skip to content

Commit

Permalink
Chip tool interactive (#16135)
Browse files Browse the repository at this point in the history
* [chip-tool] Add chip-tool interactive mode

* Update generated content

* Allow interactive mode to be disabled for some build variants
  • Loading branch information
vivien-apple authored and pull[bot] committed Oct 16, 2023
1 parent a6ff951 commit 1030462
Show file tree
Hide file tree
Showing 20 changed files with 454 additions and 65 deletions.
6 changes: 3 additions & 3 deletions .github/workflows/examples-linux-arm.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ jobs:
./scripts/run_in_build_env.sh \
"./scripts/build/build_examples.py \
--target linux-arm64-all-clusters \
--target linux-arm64-chip-tool-ipv6only \
--target linux-arm64-chip-tool-no-interactive-ipv6only \
--target linux-arm64-door-lock \
--target linux-arm64-minmdns \
--target linux-arm64-thermostat-no-ble \
Expand All @@ -79,8 +79,8 @@ jobs:
timeout-minutes: 5
run: |
.environment/pigweed-venv/bin/python3 scripts/tools/memory/gh_sizes.py \
linux arm64 chip-tool-ipv6only \
out/linux-arm64-chip-tool-ipv6only/chip-tool \
linux arm64 chip-tool-no-interactive-ipv6only \
out/linux-arm64-chip-tool-no-interactive-ipv6only/chip-tool \
/tmp/bloat_reports/
- name: Bloat report - thermostat
timeout-minutes: 5
Expand Down
14 changes: 13 additions & 1 deletion examples/chip-tool/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ assert(chip_build_tools)
declare_args() {
# Use a separate eventloop for CHIP tasks
config_use_separate_eventloop = true
config_use_interactive_mode = true
}

config("config") {
Expand All @@ -32,9 +33,16 @@ config("config") {
"${chip_root}/src/lib",
]

defines = [ "CONFIG_USE_SEPARATE_EVENTLOOP=${config_use_separate_eventloop}" ]
defines = [
"CONFIG_USE_SEPARATE_EVENTLOOP=${config_use_separate_eventloop}",
"CONFIG_USE_INTERACTIVE_MODE=${config_use_interactive_mode}",
]

cflags = [ "-Wconversion" ]

if (config_use_interactive_mode) {
libs = [ "readline" ]
}
}

static_library("chip-tool-utils") {
Expand Down Expand Up @@ -67,6 +75,10 @@ static_library("chip-tool-utils") {
"config/PersistentStorage.cpp",
]

if (config_use_interactive_mode) {
sources += [ "commands/interactive/InteractiveCommands.cpp" ]
}

public_deps = [
"${chip_root}/src/app/server",
"${chip_root}/src/app/tests/suites/commands/commissioner",
Expand Down
7 changes: 7 additions & 0 deletions examples/chip-tool/commands/clusters/ModelCommand.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -56,3 +56,10 @@ void ModelCommand::OnDeviceConnectionFailureFn(void * context, PeerId peerId, CH
VerifyOrReturn(command != nullptr, ChipLogError(chipTool, "OnDeviceConnectionFailureFn: context is null"));
command->SetCommandExitStatus(err);
}

void ModelCommand::Shutdown()
{
ResetArguments();
mOnDeviceConnectedCallback.Cancel();
mOnDeviceConnectionFailureCallback.Cancel();
}
6 changes: 1 addition & 5 deletions examples/chip-tool/commands/clusters/ModelCommand.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,11 +47,7 @@ class ModelCommand : public CHIPCommand

virtual CHIP_ERROR SendGroupCommand(chip::GroupId groupId, chip::FabricIndex fabricIndex) { return CHIP_ERROR_BAD_REQUEST; };

void Shutdown() override
{
mOnDeviceConnectedCallback.Cancel();
mOnDeviceConnectionFailureCallback.Cancel();
}
void Shutdown() override;

protected:
chip::Optional<uint16_t> mTimeout;
Expand Down
66 changes: 26 additions & 40 deletions examples/chip-tool/commands/clusters/ReportCommand.h
Original file line number Diff line number Diff line change
Expand Up @@ -376,7 +376,6 @@ class SubscribeAttribute : public ReportCommand
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("data-version", 0, UINT32_MAX, &mDataVersion);
AddArgument("wait", 0, 1, &mWait);
AddArgument("fabric-filtered", 0, 1, &mFabricFiltered);
ReportCommand::AddArguments();
}
Expand All @@ -388,7 +387,6 @@ class SubscribeAttribute : public ReportCommand
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("data-version", 0, UINT32_MAX, &mDataVersion);
AddArgument("wait", 0, 1, &mWait);
AddArgument("fabric-filtered", 0, 1, &mFabricFiltered);
ReportCommand::AddArguments();
}
Expand All @@ -402,7 +400,6 @@ class SubscribeAttribute : public ReportCommand
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("data-version", 0, UINT32_MAX, &mDataVersion);
AddArgument("wait", 0, 1, &mWait);
AddArgument("fabric-filtered", 0, 1, &mFabricFiltered);
ReportCommand::AddArguments();
}
Expand All @@ -416,26 +413,23 @@ class SubscribeAttribute : public ReportCommand
mDataVersion);
}

chip::System::Clock::Timeout GetWaitDuration() const override
{
return mWait ? chip::System::Clock::Seconds16(UINT16_MAX) : ReportCommand::GetWaitDuration();
}
chip::System::Clock::Timeout GetWaitDuration() const override { return ReportCommand::GetWaitDuration(); }

void OnAttributeSubscription() override
{
if (!mWait)
{
// The ReadClient instance can not be released directly into the OnAttributeSubscription
// callback since it happens to be called by ReadClient itself which is doing additional
// work after that.
chip::DeviceLayer::PlatformMgr().ScheduleWork(
[](intptr_t arg) {
auto * command = reinterpret_cast<SubscribeAttribute *>(arg);
// The ReadClient instance can not be released directly into the OnAttributeSubscription
// callback since it happens to be called by ReadClient itself which is doing additional
// work after that.
chip::DeviceLayer::PlatformMgr().ScheduleWork(
[](intptr_t arg) {
auto * command = reinterpret_cast<SubscribeAttribute *>(arg);
if (!command->IsInteractive())
{
command->mReadClient.reset();
command->SetCommandExitStatus(CHIP_NO_ERROR);
},
reinterpret_cast<intptr_t>(this));
}
}
command->SetCommandExitStatus(CHIP_NO_ERROR);
},
reinterpret_cast<intptr_t>(this));
}

private:
Expand All @@ -445,7 +439,6 @@ class SubscribeAttribute : public ReportCommand
uint16_t mMinInterval;
uint16_t mMaxInterval;
chip::Optional<std::vector<chip::DataVersion>> mDataVersion;
bool mWait;
};

class ReadEvent : public ReportCommand
Expand Down Expand Up @@ -496,7 +489,6 @@ class SubscribeEvent : public ReportCommand
AddArgument("event-id", 0, UINT32_MAX, &mEventIds);
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("wait", 0, 1, &mWait);
ReportCommand::AddArguments();
}

Expand All @@ -506,7 +498,6 @@ class SubscribeEvent : public ReportCommand
AddArgument("event-id", 0, UINT32_MAX, &mEventIds);
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("wait", 0, 1, &mWait);
ReportCommand::AddArguments();
}

Expand All @@ -518,7 +509,6 @@ class SubscribeEvent : public ReportCommand
AddArgument("attr-name", eventName);
AddArgument("min-interval", 0, UINT16_MAX, &mMinInterval);
AddArgument("max-interval", 0, UINT16_MAX, &mMaxInterval);
AddArgument("wait", 0, 1, &mWait);
ReportCommand::AddArguments();
}

Expand All @@ -530,26 +520,23 @@ class SubscribeEvent : public ReportCommand
chip::app::ReadClient::InteractionType::Subscribe, mMinInterval, mMaxInterval);
}

chip::System::Clock::Timeout GetWaitDuration() const override
{
return mWait ? chip::System::Clock::Seconds16(UINT16_MAX) : ReportCommand::GetWaitDuration();
}
chip::System::Clock::Timeout GetWaitDuration() const override { return ReportCommand::GetWaitDuration(); }

void OnEventSubscription() override
{
if (!mWait)
{
// The ReadClient instance can not be released directly into the OnEventSubscription
// callback since it happens to be called by ReadClient itself which is doing additional
// work after that.
chip::DeviceLayer::PlatformMgr().ScheduleWork(
[](intptr_t arg) {
auto * command = reinterpret_cast<SubscribeEvent *>(arg);
// The ReadClient instance can not be released directly into the OnEventSubscription
// callback since it happens to be called by ReadClient itself which is doing additional
// work after that.
chip::DeviceLayer::PlatformMgr().ScheduleWork(
[](intptr_t arg) {
auto * command = reinterpret_cast<SubscribeEvent *>(arg);
if (!command->IsInteractive())
{
command->mReadClient.reset();
command->SetCommandExitStatus(CHIP_NO_ERROR);
},
reinterpret_cast<intptr_t>(this));
}
}
command->SetCommandExitStatus(CHIP_NO_ERROR);
},
reinterpret_cast<intptr_t>(this));
}

private:
Expand All @@ -558,5 +545,4 @@ class SubscribeEvent : public ReportCommand

uint16_t mMinInterval;
uint16_t mMaxInterval;
bool mWait;
};
75 changes: 75 additions & 0 deletions examples/chip-tool/commands/clusters/SubscriptionsCommands.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
/*
* Copyright (c) 2022 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.
*
*/

#pragma once

class ShutdownSubscription : public CHIPCommand
{
public:
ShutdownSubscription(CredentialIssuerCommands * credsIssuerConfig) : CHIPCommand("shutdown-subscription", credsIssuerConfig)
{
AddArgument("subscription-id", 0, UINT64_MAX, &mSubscriptionId);
}

/////////// CHIPCommand Interface /////////
CHIP_ERROR RunCommand() override
{
CHIP_ERROR err = chip::app::InteractionModelEngine::GetInstance()->ShutdownSubscription(mSubscriptionId);
SetCommandExitStatus(err);
return CHIP_NO_ERROR;
}
chip::System::Clock::Timeout GetWaitDuration() const override { return chip::System::Clock::Seconds16(10); }

private:
uint64_t mSubscriptionId;
};

class ShutdownSubscriptions : public CHIPCommand
{
public:
ShutdownSubscriptions(CredentialIssuerCommands * credsIssuerConfig) : CHIPCommand("shutdown-subscriptions", credsIssuerConfig)
{
AddArgument("fabric-index", 0, UINT64_MAX, &mFabricIndex);
AddArgument("node-id", 0, UINT64_MAX, &mNodeId);
}

/////////// CHIPCommand Interface /////////
CHIP_ERROR RunCommand() override
{
CHIP_ERROR err = chip::app::InteractionModelEngine::GetInstance()->ShutdownSubscriptions(mFabricIndex, mNodeId);
SetCommandExitStatus(err);
return CHIP_NO_ERROR;
}
chip::System::Clock::Timeout GetWaitDuration() const override { return chip::System::Clock::Seconds16(10); }

private:
chip::FabricIndex mFabricIndex;
chip::NodeId mNodeId;
};

void registerClusterSubscriptions(Commands & commands, CredentialIssuerCommands * credsIssuerConfig)
{
const char * clusterName = "Subscriptions";

commands_list clusterCommands = {
make_unique<ShutdownSubscription>(credsIssuerConfig), //
make_unique<ShutdownSubscriptions>(credsIssuerConfig), //
};

commands.Register(clusterName, clusterCommands);
}
Loading

0 comments on commit 1030462

Please sign in to comment.