Skip to content

Commit

Permalink
[NXP] Adapt CLI to be used both for Zephyr and FreeRTOS (project-chip…
Browse files Browse the repository at this point in the history
…#33844)

* [NXP] Adapt CLI to be used both for Zephyr and FreeRTOS

Adapt CLI + update opstate subcommands required by opstate tests

* Restyled by clang-format

---------

Co-authored-by: Restyled.io <[email protected]>
  • Loading branch information
yeaissa and restyled-commits authored Jun 24, 2024
1 parent 6e9053b commit 66e0663
Show file tree
Hide file tree
Showing 20 changed files with 556 additions and 357 deletions.
5 changes: 4 additions & 1 deletion examples/all-clusters-app/nxp/rt/rw61x/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,6 @@ rt_executable("all_cluster_app") {
"${common_example_dir}/device_manager/source/CHIPDeviceManager.cpp",
"${common_example_dir}/icd/source/ICDUtil.cpp",
"${common_example_dir}/matter_button/source/AppMatterButtonEmpty.cpp",
"${common_example_dir}/matter_cli/source/AppMatterCli.cpp",
]

deps = [ "${chip_root}/examples/${app_common_folder}" ]
Expand All @@ -185,6 +184,10 @@ rt_executable("all_cluster_app") {
"${chip_root}/examples/shell/shell_common:shell_common",
"${chip_root}/src/lib/shell:shell",
]
sources += [
"${common_example_dir}/matter_cli/source/AppCLIBase.cpp",
"${common_example_dir}/matter_cli/source/AppCLIFreeRTOS.cpp",
]
}

if (chip_enable_ota_requestor) {
Expand Down
107 changes: 58 additions & 49 deletions examples/laundry-washer-app/nxp/common/main/AppTask.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -29,80 +29,87 @@

#ifdef ENABLE_CHIP_SHELL
#include <lib/shell/Engine.h>

#include <map>
using namespace chip::Shell;
#define MATTER_CLI_LOG(message) (streamer_printf(streamer_get(), message))
#endif /* ENABLE_CHIP_SHELL */

using namespace chip;
using namespace chip::app::Clusters;

app::Clusters::TemperatureControl::AppSupportedTemperatureLevelsDelegate sAppSupportedTemperatureLevelsDelegate;

CHIP_ERROR cliOpState(int argc, char * argv[])
#ifdef ENABLE_CHIP_SHELL
const static std::map<std::string, uint8_t> map_cmd_errstate{
{ "no_error", (uint8_t) OperationalState::ErrorStateEnum::kNoError },
{ "unable_to_start_or_resume", (uint8_t) OperationalState::ErrorStateEnum::kUnableToStartOrResume },
{ "unable_to_complete_operation", (uint8_t) OperationalState::ErrorStateEnum::kUnableToCompleteOperation },
{ "command_invalid_in_state", (uint8_t) OperationalState::ErrorStateEnum::kCommandInvalidInState }
};

const static std::map<std::string, uint8_t> map_cmd_opstate{ { "stop", (uint8_t) OperationalState::OperationalStateEnum::kStopped },
{ "run", (uint8_t) OperationalState::OperationalStateEnum::kRunning },
{ "pause", (uint8_t) OperationalState::OperationalStateEnum::kPaused },
{ "error",
(uint8_t) OperationalState::OperationalStateEnum::kError } };

static void InvalidStateHandler(void)
{
if ((argc != 1) && (argc != 2))
{
ChipLogError(Shell, "Target State is missing");
return CHIP_ERROR_INVALID_ARGUMENT;
}
if (!strcmp(argv[0], "stop"))
ChipLogError(Shell, "Invalid State/Error to set");
MATTER_CLI_LOG("Invalid. Supported commands are:\n");
for (auto const & it : map_cmd_opstate)
{
ChipLogDetail(Shell, "OpSState : Set to %s state", argv[0]);
OperationalState::GetOperationalStateInstance()->SetOperationalState(
to_underlying(OperationalState::OperationalStateEnum::kStopped));
MATTER_CLI_LOG(("\t opstate " + it.first + "\n").c_str());
}
else if (!strcmp(argv[0], "run"))
for (auto const & it : map_cmd_errstate)
{
ChipLogDetail(Shell, "OpSState : Set to %s state", argv[0]);
OperationalState::GetOperationalStateInstance()->SetOperationalState(
to_underlying(OperationalState::OperationalStateEnum::kRunning));
MATTER_CLI_LOG(("\t opstate error " + it.first + "\n").c_str());
}
else if (!strcmp(argv[0], "pause"))
}

static CHIP_ERROR cliOpState(int argc, char * argv[])
{
bool inputErr = false;
if ((argc != 1) && (argc != 2))
{
ChipLogDetail(Shell, "OpSState : Set to %s state", argv[0]);
OperationalState::GetOperationalStateInstance()->SetOperationalState(
to_underlying(OperationalState::OperationalStateEnum::kPaused));
inputErr = true;
goto exit;
}
else if (!strcmp(argv[0], "error"))

if (map_cmd_opstate.find(argv[0]) != map_cmd_opstate.end())
{
OperationalState::Structs::ErrorStateStruct::Type err;
OperationalState::GetOperationalStateInstance()->SetOperationalState(map_cmd_opstate.at(argv[0]));
ChipLogDetail(Shell, "OpSState : Set to %s state", argv[0]);
if (!strcmp(argv[1], "no_error"))
{
ChipLogDetail(Shell, "OpSState_error : Error: %s state", argv[1]);
err.errorStateID = (uint8_t) OperationalState::ErrorStateEnum::kNoError;
}
else if (!strcmp(argv[1], "unable_to_start_or_resume"))
{
ChipLogDetail(Shell, "OpSState_error : Error: %s state", argv[1]);
err.errorStateID = (uint8_t) OperationalState::ErrorStateEnum::kUnableToStartOrResume;
}
else if (!strcmp(argv[1], "unable_to_complete_operation"))
{
ChipLogDetail(Shell, "OpSState_error : Error: %s state", argv[1]);
err.errorStateID = (uint8_t) OperationalState::ErrorStateEnum::kUnableToCompleteOperation;
}
else if (!strcmp(argv[1], "command_invalid_in_state"))
{
ChipLogDetail(Shell, "OpSState_error : Error: %s state", argv[1]);
err.errorStateID = (uint8_t) OperationalState::ErrorStateEnum::kCommandInvalidInState;
}
else
if (!strcmp(argv[0], "error") && argc == 2)
{
ChipLogError(Shell, "Invalid Error State to set");
return CHIP_ERROR_INVALID_ARGUMENT;
OperationalState::Structs::ErrorStateStruct::Type err;
if (map_cmd_errstate.find(argv[1]) != map_cmd_errstate.end())
{
ChipLogDetail(Shell, "OpSState_error : Set to %s state", argv[1]);
err.errorStateID = map_cmd_errstate.at(argv[1]);
OperationalState::GetOperationalStateInstance()->OnOperationalErrorDetected(err);
}
else
{
inputErr = true;
goto exit;
}
}
OperationalState::GetOperationalStateInstance()->OnOperationalErrorDetected(err);
OperationalState::GetOperationalStateInstance()->SetOperationalState(
to_underlying(OperationalState::OperationalStateEnum::kError));
}
else
{
ChipLogError(Shell, "Invalid State to set");
inputErr = true;
}
exit:
if (inputErr)
{
InvalidStateHandler();
return CHIP_ERROR_INVALID_ARGUMENT;
}

return CHIP_NO_ERROR;
}
#endif /* ENABLE_CHIP_SHELL */

void LaundryWasherApp::AppTask::PreInitMatterStack()
{
Expand All @@ -121,7 +128,9 @@ void LaundryWasherApp::AppTask::AppMatter_RegisterCustomCliCommands()
#ifdef ENABLE_CHIP_SHELL
/* Register application commands */
static const shell_command_t kCommands[] = {
{ .cmd_func = cliOpState, .cmd_name = "opstate", .cmd_help = "Set the Operational State" },
{ .cmd_func = cliOpState,
.cmd_name = "opstate",
.cmd_help = "Set the Operational State. Usage:[stop|run|pause|dock|error 'state'] " },
};
Engine::Root().RegisterCommands(kCommands, sizeof(kCommands) / sizeof(kCommands[0]));
#endif
Expand Down
5 changes: 4 additions & 1 deletion examples/laundry-washer-app/nxp/rt/rw61x/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,6 @@ rt_executable("laundry-washer") {
"${common_example_dir}/device_manager/source/CHIPDeviceManager.cpp",
"${common_example_dir}/icd/source/ICDUtil.cpp",
"${common_example_dir}/matter_button/source/AppMatterButtonEmpty.cpp",
"${common_example_dir}/matter_cli/source/AppMatterCli.cpp",
]

deps = [ "${chip_root}/examples/${app_common_folder}" ]
Expand All @@ -190,6 +189,10 @@ rt_executable("laundry-washer") {
"${chip_root}/examples/shell/shell_common:shell_common",
"${chip_root}/src/lib/shell:shell",
]
sources += [
"${common_example_dir}/matter_cli/source/AppCLIBase.cpp",
"${common_example_dir}/matter_cli/source/AppCLIFreeRTOS.cpp",
]
}

if (chip_enable_ota_requestor) {
Expand Down
18 changes: 13 additions & 5 deletions examples/platform/nxp/common/app_task/include/AppTaskBase.h
Original file line number Diff line number Diff line change
Expand Up @@ -130,14 +130,22 @@ class AppTaskBase
*/
static void InitServer(intptr_t arg);

/* Commissioning handlers */
virtual void StartCommissioningHandler(void){};
virtual void StopCommissioningHandler(void){};
virtual void SwitchCommissioningStateHandler(void){};
virtual void FactoryResetHandler(void){};
/**
* Commissioning handlers
* Generic implementation is provided within this class
* Can be overridden by a child class
*/
virtual void StartCommissioningHandler(void);
virtual void StopCommissioningHandler(void);
virtual void SwitchCommissioningStateHandler(void);
virtual void FactoryResetHandler(void);

private:
inline static chip::CommonCaseDeviceServerInitParams initParams;
/* Functions used by the public commisioning handlers */
static void StartCommissioning(intptr_t arg);
static void StopCommissioning(intptr_t arg);
static void SwitchCommissioningState(intptr_t arg);
};

/**
Expand Down
15 changes: 1 addition & 14 deletions examples/platform/nxp/common/app_task/include/AppTaskFreeRTOS.h
Original file line number Diff line number Diff line change
Expand Up @@ -65,26 +65,13 @@ class AppTaskFreeRTOS : public AppTaskBase
#endif

/**
* \brief This function register matter CLI and button features.
* \brief This function registers custom matter CLI and button features.
*
* \return CHIP_ERROR
*
*/
virtual CHIP_ERROR AppMatter_Register(void) override;

/* Functions that would be called in the Matter task context */
static void StartCommissioning(intptr_t arg);
static void StopCommissioning(intptr_t arg);
static void SwitchCommissioningState(intptr_t arg);

/* Commissioning handlers */
virtual void StartCommissioningHandler(void) override;
virtual void StopCommissioningHandler(void) override;
virtual void SwitchCommissioningStateHandler(void) override;

/* FactoryResetHandler */
virtual void FactoryResetHandler(void) override;

private:
void DispatchEvent(const AppEvent & event);
};
Expand Down
8 changes: 8 additions & 0 deletions examples/platform/nxp/common/app_task/include/AppTaskZephyr.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,14 @@ class AppTaskZephyr : public AppTaskBase
virtual chip::DeviceLayer::NetworkCommissioning::WiFiDriver * GetWifiDriverInstance(void) override;
#endif

/**
* \brief This function registers applicative features such as custom CLI commands
*
* \return CHIP_ERROR
*
*/
virtual CHIP_ERROR AppMatter_Register(void) override;

private:
void DispatchEvent(const AppEvent & event);
};
Expand Down
88 changes: 82 additions & 6 deletions examples/platform/nxp/common/app_task/source/AppTaskBase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -172,6 +172,12 @@ CHIP_ERROR chip::NXP::App::AppTaskBase::Init()
ChipLogError(DeviceLayer, "CHIPDeviceManager.Init() failed: %s", ErrorStr(err));
goto exit;
}
/* Make sure to initialize the Matter CLI which will include the ot-cli first.
* In fact it is mandatory to enable first the ot-cli before initializing the Matter openthread layer
* which would modify some contexts of the openthread instance.
*/
err = AppMatter_Register();
VerifyOrExit(err == CHIP_NO_ERROR, ChipLogError(DeviceLayer, "Error during APP features registration"));

#if CONFIG_NET_L2_OPENTHREAD
err = ThreadStackMgr().InitThreadStack();
Expand Down Expand Up @@ -218,12 +224,6 @@ CHIP_ERROR chip::NXP::App::AppTaskBase::Init()
}
#endif

err = AppMatter_Register();
if (err != CHIP_NO_ERROR)
{
goto exit;
}

ConfigurationMgr().LogDeviceConfig();

// QR code will be used with CHIP Tool
Expand Down Expand Up @@ -257,3 +257,79 @@ CHIP_ERROR chip::NXP::App::AppTaskBase::Init()
exit:
return err;
}

void chip::NXP::App::AppTaskBase::StartCommissioning(intptr_t arg)
{
/* Check the status of the commissioning */
if (ConfigurationMgr().IsFullyProvisioned())
{
ChipLogProgress(DeviceLayer, "Device already commissioned");
}
else if (chip::Server::GetInstance().GetCommissioningWindowManager().IsCommissioningWindowOpen())
{
ChipLogProgress(DeviceLayer, "Commissioning window already opened");
}
else
{
chip::Server::GetInstance().GetCommissioningWindowManager().OpenBasicCommissioningWindow();
}
}

void chip::NXP::App::AppTaskBase::StopCommissioning(intptr_t arg)
{
/* Check the status of the commissioning */
if (ConfigurationMgr().IsFullyProvisioned())
{
ChipLogProgress(DeviceLayer, "Device already commissioned");
}
else if (!chip::Server::GetInstance().GetCommissioningWindowManager().IsCommissioningWindowOpen())
{
ChipLogProgress(DeviceLayer, "Commissioning window not opened");
}
else
{
chip::Server::GetInstance().GetCommissioningWindowManager().CloseCommissioningWindow();
}
}

void chip::NXP::App::AppTaskBase::SwitchCommissioningState(intptr_t arg)
{
/* Check the status of the commissioning */
if (ConfigurationMgr().IsFullyProvisioned())
{
ChipLogProgress(DeviceLayer, "Device already commissioned");
}
else if (!chip::Server::GetInstance().GetCommissioningWindowManager().IsCommissioningWindowOpen())
{
chip::Server::GetInstance().GetCommissioningWindowManager().OpenBasicCommissioningWindow();
}
else
{
chip::Server::GetInstance().GetCommissioningWindowManager().CloseCommissioningWindow();
}
}

void chip::NXP::App::AppTaskBase::StartCommissioningHandler(void)
{
/* Publish an event to the Matter task to always set the commissioning state in the Matter task context */
PlatformMgr().ScheduleWork(StartCommissioning, 0);
}

void chip::NXP::App::AppTaskBase::StopCommissioningHandler(void)
{
/* Publish an event to the Matter task to always set the commissioning state in the Matter task context */
PlatformMgr().ScheduleWork(StopCommissioning, 0);
}

void chip::NXP::App::AppTaskBase::SwitchCommissioningStateHandler(void)
{
/* Publish an event to the Matter task to always set the commissioning state in the Matter task context */
PlatformMgr().ScheduleWork(SwitchCommissioningState, 0);
}

void chip::NXP::App::AppTaskBase::FactoryResetHandler(void)
{
/* Emit the ShutDown event before factory reset */
chip::Server::GetInstance().GenerateShutDownEvent();
chip::Server::GetInstance().ScheduleFactoryReset();
}
Loading

0 comments on commit 66e0663

Please sign in to comment.