Files
esp_llcc68_driver/inc/hal_spi.hpp

123 lines
3.3 KiB
C++

//
// Created by Kurosu Chan on 2024/1/17.
//
#ifndef B7431E31_4075_4B09_B4B3_EAD0234EFB40
#define B7431E31_4075_4B09_B4B3_EAD0234EFB40
#include <cstdint>
#include <span>
#include "hal/spi_types.h"
#include "radiolib_definitions.hpp"
#include "llcc68_definitions.hpp"
#include "utils/app_result.hpp"
#include "hal_error.hpp"
#include "app_const_llcc68.hpp"
namespace app::driver::hal::spi {
template <typename T, typename E>
using Result = app::utils::Result<T, E>;
using Unit = app::utils::Unit;
constexpr auto TAG = "spi";
constexpr auto MOSI_PIN = llcc68::MOSI_PIN;
constexpr auto MISO_PIN = llcc68::MISO_PIN;
constexpr auto SCLK_PIN = llcc68::SCLK_PIN;
constexpr auto BUSY_PIN = llcc68::BUSY_PIN;
constexpr auto CS_PIN = llcc68::CS_PIN;
using error_t = error::t;
using ue_t = app::utils::unexpected<error_t>;
constexpr uint8_t SPI_READ_COMMAND = RADIOLIB_SX126X_CMD_READ_REGISTER;
constexpr uint8_t SPI_WRITE_COMMAND = RADIOLIB_SX126X_CMD_WRITE_REGISTER;
constexpr uint8_t SPI_NOP_COMMAND = RADIOLIB_SX126X_CMD_NOP;
constexpr uint8_t SPI_WRITE_BUFFER_CMD = RADIOLIB_SX126X_CMD_WRITE_BUFFER;
constexpr uint8_t SPI_READ_BUFFER_CMD = RADIOLIB_SX126X_CMD_READ_BUFFER;
constexpr size_t DEFAULT_TIMEOUT_MS = 1000;
struct spi_config_t {
spi_host_device_t host_id;
int clock_speed_hz;
};
/*!
\brief Initialize the SPI interface.
*/
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:
#ifdef APP_SPI_DISABLE_INVALID_STATUS_CHECK
return error::OK;
#else
return error::SPI_CMD_INVALID;
#endif
default:
return error::OK;
}
}
/*!
See also LLCC68 chapter 10 Host Controller Interface
*/
/*! Common API patterns */
/*!
READ (no parameters, only OPCODE, but has data and status)
OPCODE() -> (status, data)
*/
Result<Unit, error_t>
read_stream(uint8_t cmd, std::span<uint8_t> data, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
/*!
WRITE (having parameters, no excessive return values but status)
OPCODE(parameters) -> status
*/
Result<Unit, error_t>
write_stream(uint8_t cmd, std::span<const uint8_t> data, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
/*!
READ REGISTER
READ_REGISTER(register, offset) -> (status, data)
*/
Result<Unit, error_t>
read_register(uint16_t reg, std::span<uint8_t> data, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
/*!
WRITE REGISTER
WRITE_REGISTER(register, offset, data) -> status
*/
Result<Unit, error_t>
write_register(uint16_t offset, std::span<const uint8_t> data, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
/*!
WRITE BUFFER
WRITE_BUFFER(offset, data) -> status
*/
Result<Unit, error_t>
write_buffer(uint8_t offset, std::span<const uint8_t> data_from_host, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
/*!
READ BUFFER
READ_BUFFER(offset) -> (status, data)
*/
Result<std::span<const uint8_t>, error_t>
read_buffer(uint8_t offset, uint8_t size, const size_t timeout_ms = DEFAULT_TIMEOUT_MS);
}
#endif /* B7431E31_4075_4B09_B4B3_EAD0234EFB40 */