Skip to content

Commit

Permalink
Add plc chip reset to ev_slac
Browse files Browse the repository at this point in the history
Signed-off-by: Sebastian Lukas <[email protected]>
  • Loading branch information
SebaLukas committed Aug 2, 2024
1 parent 6f9958e commit 8ee216f
Show file tree
Hide file tree
Showing 7 changed files with 158 additions and 6 deletions.
49 changes: 48 additions & 1 deletion lib/staging/slac/fsm/ev/include/slac/fsm/ev/context.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,23 @@ template <> struct MMTYPE<slac::messages::cm_set_key_req> {
static const uint16_t value = slac::defs::MMTYPE_CM_SET_KEY | slac::defs::MMTYPE_MODE_REQ;
};

template <> struct MMTYPE<slac::messages::qualcomm::cm_reset_device_req> {
static const uint16_t value = slac::defs::qualcomm::MMTYPE_CM_RESET_DEVICE | slac::defs::MMTYPE_MODE_REQ;
};

template <> struct MMTYPE<slac::messages::qualcomm::cm_reset_device_cnf> {
static const uint16_t value = slac::defs::qualcomm::MMTYPE_CM_RESET_DEVICE | slac::defs::MMTYPE_MODE_CNF;
};

// This message has no CNF counterpart
template <> struct MMTYPE<slac::messages::lumissil::nscm_reset_device_req> {
static const uint16_t value = slac::defs::lumissil::MMTYPE_NSCM_RESET_DEVICE | slac::defs::MMTYPE_MODE_REQ;
};

template <> struct MMTYPE<slac::messages::lumissil::nscm_get_version_req> {
static const uint16_t value = slac::defs::lumissil::MMTYPE_NSCM_GET_VERSION | slac::defs::MMTYPE_MODE_REQ;
};

template <typename SlacMessageType> struct MMV {
// this is the default value for homeplug av 2.0 messages, which are
// backward compatible with homeplug av 1.1 messages
Expand All @@ -45,20 +62,48 @@ template <typename SlacMessageType> struct MMV {
// older av 1.0 message need to use AV_1_0
static constexpr auto value = slac::defs::MMV::AV_1_1;
};

template <> struct MMV<slac::messages::qualcomm::cm_reset_device_req> {
static constexpr auto value = slac::defs::MMV::AV_1_0;
};

template <> struct MMV<slac::messages::qualcomm::cm_reset_device_cnf> {
static constexpr auto value = slac::defs::MMV::AV_1_0;
};

template <> struct MMV<slac::messages::lumissil::nscm_reset_device_req> {
static constexpr auto value = slac::defs::MMV::AV_1_0; // FIXME this is unclear
};

} // namespace _context_detail

// FIXME (aw): this should be moved to common headers (in libslac)
enum class ModemVendor {
Unknown,
Qualcomm,
Lumissil,
VertexCom,
};

struct ContextCallbacks {
std::function<void(slac::messages::HomeplugMessage&)> send_raw_slac{nullptr};
std::function<void(const std::string&)> signal_state{nullptr};
std::function<void(const std::string&)> log{nullptr};
};

struct Context {
explicit Context(const ContextCallbacks& callbacks_) : callbacks(callbacks_){};
explicit Context(const ContextCallbacks& callbacks_) : callbacks(callbacks_) {};

// MAC address of our PLC modem (EV side)
uint8_t plc_mac[ETH_ALEN] = {0x00, 0xB0, 0x52, 0x00, 0x00, 0x01};

// Settings CM_DEVICE_RESET.REQ
struct chip_reset_struct {
bool enabled = false;
int timeout_ms = 500;
int delay_ms = 100;
} chip_reset;

Check notice on line 105 in lib/staging/slac/fsm/ev/include/slac/fsm/ev/context.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

lib/staging/slac/fsm/ev/include/slac/fsm/ev/context.hpp#L105

struct member 'Context::chip_reset' is never used.

// event specific payloads
// FIXME (aw): due to the synchroneous nature of the fsm, this could be even a ptr/ref
slac::messages::HomeplugMessage slac_message;
Expand All @@ -79,6 +124,8 @@ struct Context {
// logging util
void log_info(const std::string& text);

ModemVendor modem_vendor{ModemVendor::Unknown};

Check notice on line 127 in lib/staging/slac/fsm/ev/include/slac/fsm/ev/context.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

lib/staging/slac/fsm/ev/include/slac/fsm/ev/context.hpp#L127

struct member 'Context::modem_vendor' is never used.

private:
const ContextCallbacks& callbacks;
};
Expand Down
1 change: 1 addition & 0 deletions lib/staging/slac/fsm/ev/include/slac/fsm/ev/fsm.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ enum class Event {

// internal events
FAILED,
SUCCESS,
};

using FSMReturnType = int;
Expand Down
21 changes: 21 additions & 0 deletions lib/staging/slac/fsm/ev/include/slac/fsm/ev/states/others.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,27 @@ struct ResetState : public FSMSimpleState {
CallbackReturnType callback() final;
};

struct ResetChipState : public FSMSimpleState {
using FSMSimpleState::FSMSimpleState;

HandleEventReturnType handle_event(AllocatorType&, Event) final;

void enter() final;
CallbackReturnType callback() final;

// for now returns true if CM_RESET_CNF is received
bool check_for_valid_reset_conf();

bool reset_delay_done{false};

Check notice on line 32 in lib/staging/slac/fsm/ev/include/slac/fsm/ev/states/others.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

lib/staging/slac/fsm/ev/include/slac/fsm/ev/states/others.hpp#L32

struct member 'ResetChipState::reset_delay_done' is never used.
bool chip_reset_has_been_sent{false};

Check notice on line 33 in lib/staging/slac/fsm/ev/include/slac/fsm/ev/states/others.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

lib/staging/slac/fsm/ev/include/slac/fsm/ev/states/others.hpp#L33

struct member 'ResetChipState::chip_reset_has_been_sent' is never used.

enum class SubState {
DELAY,
SEND_RESET,
DONE,
} sub_state{SubState::DELAY};
};

struct InitSlacState : public FSMSimpleState {
using FSMSimpleState::FSMSimpleState;

Expand Down
70 changes: 69 additions & 1 deletion lib/staging/slac/fsm/ev/src/states/others.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,13 @@ void ResetState::enter() {

FSMSimpleState::HandleEventReturnType ResetState::handle_event(AllocatorType& sa, Event ev) {
if (ev == Event::TRIGGER_MATCHING) {
return sa.create_simple<InitSlacState>(ctx);
if (ctx.chip_reset.enabled) {
// If chip reset is enabled in config, go to ResetChipState and from there to IdleState
return sa.create_simple<ResetChipState>(ctx);
} else {
// If chip reset is disabled, go to IdleState directly
return sa.create_simple<InitSlacState>(ctx);
}
} else {
return sa.PASS_ON;
}
Expand All @@ -32,6 +38,68 @@ FSMSimpleState::CallbackReturnType ResetState::callback() {
return {};
}

void ResetChipState::enter() {
ctx.log_info("Entered HW Chip Reset state");
}

FSMSimpleState::HandleEventReturnType ResetChipState::handle_event(AllocatorType& sa, Event ev) {
if (ev == Event::SLAC_MESSAGE) {
if (check_for_valid_reset_conf()) {
return sa.create_simple<InitSlacState>(ctx);
} else {
return sa.PASS_ON;
}
} else if (ev == Event::SUCCESS) {
return sa.create_simple<InitSlacState>(ctx);
} else {
return sa.PASS_ON;
}
}

FSMSimpleState::CallbackReturnType ResetChipState::callback() {
if (sub_state == SubState::DELAY) {
sub_state = SubState::SEND_RESET;
return ctx.chip_reset.delay_ms;

} else if (sub_state == SubState::SEND_RESET) {

if (ctx.modem_vendor == ModemVendor::Qualcomm) {
slac::messages::qualcomm::cm_reset_device_req reset_req;
ctx.log_info("Resetting HW Chip using RS_DEV.REQ");
ctx.send_slac_message(ctx.plc_mac, reset_req);
sub_state = SubState::DONE;
return ctx.chip_reset.timeout_ms;

} else if (ctx.modem_vendor == ModemVendor::Lumissil) {
slac::messages::lumissil::nscm_reset_device_req reset_req;
ctx.log_info("Resetting HW Chip using NSCM_RESET_DEVICE.REQ");
sub_state = SubState::DONE;
ctx.send_slac_message(ctx.plc_mac, reset_req);
// CG5317 does not reply to the reset packet
return Event::SUCCESS;

} else {
ctx.log_info("Chip reset not supported on this chip");
}
} else {
ctx.log_info("Reset timeout, no response received - failed to reset the chip");
return {};
}
return {};
}

bool ResetChipState::check_for_valid_reset_conf() {
const auto mmtype = ctx.slac_message.get_mmtype();
if (mmtype != (slac::defs::qualcomm::MMTYPE_CM_RESET_DEVICE | slac::defs::MMTYPE_MODE_CNF)) {
// unexpected message
ctx.log_info("Received non-expected SLAC message");
return false;
} else {
ctx.log_info("Received RS_DEV.CNF");
return true;
}
}

FSMSimpleState::HandleEventReturnType InitSlacState::handle_event(AllocatorType& sa, Event ev) {
if (ev == Event::SLAC_MESSAGE) {
if (check_for_valid_parm_conf()) {
Expand Down
7 changes: 3 additions & 4 deletions modules/EvSlac/main/ev_slacImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -56,10 +56,9 @@ void ev_slacImpl::run() {
callbacks.log = [](const std::string& text) { EVLOG_info << "EvSlac: " << text; };

auto fsm_ctx = slac::fsm::ev::Context(callbacks);
// fsm_ctx.slac_config.set_key_timeout_ms = config.set_key_timeout_ms;
// fsm_ctx.slac_config.ac_mode_five_percent = config.ac_mode_five_percent;
// fsm_ctx.slac_config.sounding_atten_adjustment = config.sounding_attenuation_adjustment;
// fsm_ctx.slac_config.generate_nmk();
fsm_ctx.chip_reset.enabled = config.do_chip_reset;
fsm_ctx.chip_reset.delay_ms = config.chip_reset_delay_ms;
fsm_ctx.chip_reset.timeout_ms = config.chip_reset_timeout_ms;

fsm_ctrl = std::make_unique<FSMController>(fsm_ctx);

Expand Down
3 changes: 3 additions & 0 deletions modules/EvSlac/main/ev_slacImpl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@ namespace main {
struct Conf {
std::string device;
int set_key_timeout_ms;
bool do_chip_reset;

Check notice on line 25 in modules/EvSlac/main/ev_slacImpl.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/EvSlac/main/ev_slacImpl.hpp#L25

struct member 'Conf::do_chip_reset' is never used.
int chip_reset_delay_ms;

Check notice on line 26 in modules/EvSlac/main/ev_slacImpl.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/EvSlac/main/ev_slacImpl.hpp#L26

struct member 'Conf::chip_reset_delay_ms' is never used.
int chip_reset_timeout_ms;

Check notice on line 27 in modules/EvSlac/main/ev_slacImpl.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/EvSlac/main/ev_slacImpl.hpp#L27

struct member 'Conf::chip_reset_timeout_ms' is never used.
};

class ev_slacImpl : public ev_slacImplBase {
Expand Down
13 changes: 13 additions & 0 deletions modules/EvSlac/manifest.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,21 @@ provides:
description: Timeout for CM_SET_KEY.REQ. Default works for QCA7000/QCA7005/CG5317.
type: integer
default: 500
do_chip_reset:
description: Perform a chip reset after setting NMK using the RS_DEV.REQ Vendor MME Extension (Only works on Qualcomm chips)
type: boolean
default: false
chip_reset_delay_ms:
description: Delay between SET_KEY.CNF and RS_DEV.REQ
type: integer
default: 100
chip_reset_timeout_ms:
description: Timeout for RS_DEV.REQ (waiting for RS_DEV.CNF)
type: integer
default: 500
metadata:
base_license: https://directory.fsf.org/wiki/License:BSD-3-Clause-Clear
license: https://opensource.org/licenses/Apache-2.0
authors:
- [email protected]
- Sebastian Lukas

0 comments on commit 8ee216f

Please sign in to comment.