feat: add option to disable radio calibration and update status error handling
This commit is contained in:
@ -3,7 +3,8 @@
|
||||
#include <array>
|
||||
#include <tuple>
|
||||
|
||||
#define APP_ERR_TBL_IT(err) {err, #err}
|
||||
#define APP_ERR_TBL_IT(err) \
|
||||
{ err, #err }
|
||||
|
||||
namespace app::driver::hal::error {
|
||||
using t = int;
|
||||
@ -40,7 +41,8 @@ constexpr t SPI_TIMEOUT = SPI_ERR_BASE + 2;
|
||||
constexpr t SPI_CMD_INVALID = SPI_ERR_BASE + 3;
|
||||
// The command was successfully processed, however the chip could not execute the command;
|
||||
// for instance it was unable to enter the specified device mode or send the requested data
|
||||
constexpr t SPI_CMD_FAILED = SPI_ERR_BASE + 4;
|
||||
constexpr t SPI_CMD_FAILED = SPI_ERR_BASE + 4;
|
||||
constexpr t SPI_INVALID_RADIO_STATE = SPI_ERR_BASE + 5; /*!< Radio is in an invalid state for the requested operation */
|
||||
|
||||
constexpr t RADIO_ERR_BASE = 0x1'3000;
|
||||
constexpr t RADIO_CHIP_NOT_FOUND = RADIO_ERR_BASE + 1;
|
||||
@ -76,6 +78,7 @@ constexpr auto error_table = std::to_array<std::tuple<t, const char *>>(
|
||||
APP_ERR_TBL_IT(SPI_TIMEOUT),
|
||||
APP_ERR_TBL_IT(SPI_CMD_INVALID),
|
||||
APP_ERR_TBL_IT(SPI_CMD_FAILED),
|
||||
APP_ERR_TBL_IT(SPI_INVALID_RADIO_STATE),
|
||||
|
||||
APP_ERR_TBL_IT(RADIO_CHIP_NOT_FOUND),
|
||||
APP_ERR_TBL_IT(RADIO_INVALID_TCXO_VOLTAGE),
|
||||
|
||||
@ -47,21 +47,37 @@ void init(spi_config_t config = {SPI2_HOST, 4'000'000});
|
||||
|
||||
|
||||
inline error_t status_to_err(const uint8_t status) {
|
||||
const auto st = *reinterpret_cast<const llcc68::status_t *>(&status);
|
||||
switch (st.command_status) {
|
||||
case llcc68::CommandStatus::COMMAND_TIMEOUT:
|
||||
return error::SPI_TIMEOUT;
|
||||
case llcc68::CommandStatus::FAILURE_TO_EXECUTE_COMMAND:
|
||||
return error::SPI_CMD_FAILED;
|
||||
case llcc68::CommandStatus::COMMAND_PROCESSING_ERROR:
|
||||
const auto st = *reinterpret_cast<const llcc68::status_t *>(&status);
|
||||
error_t status_ok = [](llcc68::CommandStatus st) {
|
||||
switch (st) {
|
||||
case llcc68::CommandStatus::COMMAND_TIMEOUT:
|
||||
return error::SPI_TIMEOUT;
|
||||
case llcc68::CommandStatus::FAILURE_TO_EXECUTE_COMMAND:
|
||||
return error::SPI_CMD_FAILED;
|
||||
case llcc68::CommandStatus::COMMAND_PROCESSING_ERROR:
|
||||
#ifdef APP_SPI_DISABLE_INVALID_STATUS_CHECK
|
||||
return error::OK;
|
||||
return error::OK;
|
||||
#else
|
||||
return error::SPI_CMD_INVALID;
|
||||
return error::SPI_CMD_INVALID;
|
||||
#endif
|
||||
default:
|
||||
return error::OK;
|
||||
default:
|
||||
return error::OK;
|
||||
}
|
||||
}(st.command_status);
|
||||
if (status_ok != error::OK) {
|
||||
return status_ok;
|
||||
}
|
||||
error_t chip_mode_usual = [](llcc68::ChipMode mode) {
|
||||
switch (mode) {
|
||||
case llcc68::ChipMode::TX:
|
||||
case llcc68::ChipMode::RX:
|
||||
case llcc68::ChipMode::STBY_RC:
|
||||
return error::OK;
|
||||
default:
|
||||
return error::SPI_INVALID_RADIO_STATE;
|
||||
}
|
||||
}(st.chip_mode);
|
||||
return chip_mode_usual;
|
||||
}
|
||||
|
||||
/*!
|
||||
|
||||
@ -494,16 +494,17 @@ inline Result<Unit, error_t> config_packet_type(uint8_t sf) {
|
||||
res = set_dio_irq_params(irq_params);
|
||||
APP_RADIO_RETURN_ERR(res);
|
||||
|
||||
#ifndef APP_RADIO_DISABLE_CALIBRATION
|
||||
data[0] = RADIOLIB_SX126X_CALIBRATE_ALL;
|
||||
res = spi::write_stream(RADIOLIB_SX126X_CMD_CALIBRATE, std::span<const uint8_t>{data, 1});
|
||||
APP_RADIO_RETURN_ERR(res);
|
||||
|
||||
// The total calibration time if all blocks are calibrated is 3.5 ms. The
|
||||
// calibration must be launched in STDBY_RC mode and the BUSY pins will be
|
||||
// high during the calibration process. A falling edge of BUSY indicates the
|
||||
// end of the procedure.
|
||||
delay_ms(5);
|
||||
while (gpio::digital_read(BUSY_PIN) == gpio::HIGH) {}
|
||||
#endif /** APP_RADIO_DISABLE_CALIBRATION */
|
||||
return {};
|
||||
}
|
||||
|
||||
@ -1130,19 +1131,19 @@ async_transmit(const std::span<const uint8_t> data,
|
||||
|
||||
Result<Unit, error_t> res;
|
||||
res = standby();
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to standby");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "standby");
|
||||
|
||||
res = set_packet_params(packet_params.preamble_len, data.size(), packet_params.crc_type, packet_params.hdr_type);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to set packet params");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "set packet params");
|
||||
|
||||
res = set_buffer_base_address();
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to set buffer base address");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "set buffer base address");
|
||||
|
||||
res = write_buffer(data);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to write buffer");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "write buffer");
|
||||
|
||||
res = fix_sensitivity(mod_params.bw);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to fix sensitivity");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "fix sensitivity");
|
||||
|
||||
constexpr auto irq_mask = RADIOLIB_SX126X_IRQ_TX_DONE | RADIOLIB_SX126X_IRQ_TIMEOUT;
|
||||
constexpr auto irq_params = irq_params_t{
|
||||
@ -1152,12 +1153,12 @@ async_transmit(const std::span<const uint8_t> data,
|
||||
DIO3_PIN == NC_PIN ? RADIOLIB_SX126X_IRQ_NONE : irq_mask,
|
||||
};
|
||||
res = set_dio_irq_params(irq_params);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to set dio irq params");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "set dio irq params");
|
||||
clear_irq_status(irq_mask);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to clear irq status");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "clear irq status");
|
||||
|
||||
res = tx();
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "failed to transmit");
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "tx");
|
||||
|
||||
constexpr auto TIMEOUT_FACTOR = 11u / 10u;
|
||||
const auto timeout_us = calc_time_on_air(data.size(),
|
||||
@ -1310,7 +1311,12 @@ static constexpr auto begin = [](const lora_parameters_t ¶ms) -> Result<Unit
|
||||
res = set_dio2_as_rf_switch(false);
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "set dio2 as rf switch");
|
||||
|
||||
res = set_frequency(params.frequency);
|
||||
#ifdef APP_RADIO_DISABLE_CALIBRATION
|
||||
res = set_frequency(params.frequency, false);
|
||||
#else
|
||||
res = set_frequency(params.frequency, true);
|
||||
#endif /* APP_RADIO_DISABLE_CALIBRATION */
|
||||
|
||||
APP_RADIO_RETURN_ERR_CTX(res, "set frequency");
|
||||
|
||||
// SetPacketParams
|
||||
|
||||
@ -284,10 +284,12 @@ inline const char *to_str(const ChipMode &mode) {
|
||||
|
||||
|
||||
struct __attribute__((packed)) status_t {
|
||||
// LSB
|
||||
uint8_t reserved_1 : 1;
|
||||
CommandStatus command_status : 3;
|
||||
ChipMode chip_mode : 3;
|
||||
uint8_t reserved_2 : 1;
|
||||
// MSB
|
||||
};
|
||||
static_assert(sizeof(status_t) == 1);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user