M enabled_unittests => enabled_unittests +0 -5
@@ 443,11 443,6 @@ TESTS_LIST["catch2-unittest_ATURCStream"]="
URC AT Stream Parser;
"
#---------
-#---------
-TESTS_LIST["catch2-unittest_CellularResult"]="
- CellularResult
-"
-#---------
M module-bsp/board/linux/cellular/linux_cellular.cpp => module-bsp/board/linux/cellular/linux_cellular.cpp +24 -21
@@ 12,8 12,10 @@
#include <errno.h>
#include <fcntl.h>
#include <map>
+#include <sys/stat.h>
#include <sys/types.h>
#include <ticks.hpp>
+#include <time.h>
#include <unistd.h>
#define _LINUX_UART_DEBUG 0
@@ 66,6 68,8 @@ namespace bsp
LOG_FATAL("Failed to create epoll file descriptor");
}
+ struct epoll_event event;
+
event.events = EPOLLIN;
if (epoll_ctl(epoll_fd, EPOLL_CTL_ADD, fd, &event)) {
@@ 87,23 91,23 @@ namespace bsp
}
}
- void LinuxCellular::powerUp()
+ void LinuxCellular::PowerUp()
{}
- void LinuxCellular::powerDown()
+ void LinuxCellular::PowerDown()
{}
- void LinuxCellular::restart()
+ void LinuxCellular::Restart()
{}
- ssize_t LinuxCellular::read(void *buf, size_t nbytes, std::chrono::milliseconds timeoutMs)
+ ssize_t LinuxCellular::Read(void *buf, size_t nbytes)
{
cpp_freertos::LockGuard lock(serOutMutex);
int ret;
for (;;) {
- ret = ::read(fd, buf, nbytes);
+ ret = read(fd, buf, nbytes);
if (ret != -1 || errno != EINTR)
break;
}
@@ 120,7 124,7 @@ namespace bsp
return ret;
}
- ssize_t LinuxCellular::write(void *buf, size_t nbytes)
+ ssize_t LinuxCellular::Write(void *buf, size_t nbytes)
{
cpp_freertos::LockGuard lock(serOutMutex);
#if _LINUX_UART_DEBUG
@@ 132,31 136,30 @@ namespace bsp
#endif
int ret;
for (;;) {
- ret = ::write(fd, buf, nbytes);
+ ret = write(fd, buf, nbytes);
if (ret != -1 || errno != EINTR)
break;
}
return ret;
}
- void LinuxCellular::informModemHostAsleep(void)
+ void LinuxCellular::InformModemHostAsleep(void)
{}
- void LinuxCellular::informModemHostWakeup(void)
+ void LinuxCellular::InformModemHostWakeup(void)
{}
- void LinuxCellular::enterSleep()
+ void LinuxCellular::EnterSleep()
{}
- void LinuxCellular::exitSleep()
+ void LinuxCellular::ExitSleep()
{}
- uint32_t LinuxCellular::wait(std::chrono::milliseconds timeoutMs)
+ uint32_t LinuxCellular::Wait(uint32_t timeout)
{
- auto timeoutTicks = pdMS_TO_TICKS(timeoutMs.count());
uint32_t currentTime = cpp_freertos::Ticks::GetTicks();
- uint32_t timeoutNeeded = currentTime + timeoutTicks;
+ uint32_t timeoutNeeded = timeout == UINT32_MAX ? UINT32_MAX : currentTime + timeout;
uint32_t timeElapsed = currentTime;
for (;;) {
@@ 179,7 182,7 @@ namespace bsp
}
}
- void LinuxCellular::setSpeed(uint32_t portSpeed)
+ void LinuxCellular::SetSpeed(uint32_t portSpeed)
{
struct termios t;
memset(&t, 0, sizeof(t));
@@ 198,10 201,10 @@ namespace bsp
ioctl(fd, TIOCMBIS, &status);
}
- void LinuxCellular::selectAntenna(bsp::cellular::antenna antenna)
+ void LinuxCellular::SelectAntenna(bsp::cellular::antenna antenna)
{}
- bsp::cellular::antenna LinuxCellular::getAntenna()
+ bsp::cellular::antenna LinuxCellular::GetAntenna()
{
return bsp::cellular::antenna::lowBand;
}
@@ 245,7 248,7 @@ namespace bsp
namespace sim
{
- auto trayIRQHandler() -> BaseType_t
+ auto trayIRQ_handler() -> BaseType_t
{
return BaseType_t();
}
@@ 255,15 258,15 @@ namespace bsp
return Store::GSM::Tray::IN;
}
- void hotSwapTrigger()
+ void hotswap_trigger()
{}
- void simSelect()
+ void sim_sel()
{}
} // namespace sim
namespace ringIndicator
{
- auto riIRQHandler() -> BaseType_t
+ auto riIRQ_handler() -> BaseType_t
{
return BaseType_t();
}
M module-bsp/board/linux/cellular/linux_cellular.hpp => module-bsp/board/linux/cellular/linux_cellular.hpp +18 -16
@@ 4,7 4,6 @@
#ifndef PUREPHONE_LINUX_CELLULAR_HPP
#define PUREPHONE_LINUX_CELLULAR_HPP
-class milliseconds;
#include "bsp/cellular/bsp_cellular.hpp"
#include <cstring>
@@ 15,6 14,7 @@ class milliseconds;
namespace bsp
{
+
class LinuxCellular : public Cellular
{
private:
@@ 24,40 24,40 @@ namespace bsp
LinuxCellular(const char *term, uint32_t portSpeed);
~LinuxCellular();
- void powerUp() override final;
+ void PowerUp() override final;
- void powerDown() override final;
+ void PowerDown() override final;
- void restart() override final;
+ void Restart() override final;
- uint32_t wait(std::chrono::milliseconds timeoutMs) override final;
+ uint32_t Wait(uint32_t timeout) override final;
- ssize_t read(void *buf, size_t nbytes, std::chrono::milliseconds timeoutMs) override final;
+ ssize_t Read(void *buf, size_t nbytes) override final;
- ssize_t write(void *buf, size_t nbytes) override final;
+ ssize_t Write(void *buf, size_t nbytes) override final;
- void informModemHostAsleep() override final;
+ void InformModemHostAsleep() override final;
- void informModemHostWakeup() override final;
+ void InformModemHostWakeup() override final;
- void enterSleep() override final;
+ void EnterSleep() override final;
- void exitSleep() override final;
+ void ExitSleep() override final;
- void setSpeed(uint32_t portSpeed) override final;
+ void SetSpeed(uint32_t portSpeed);
- void setSendingAllowed(bool state) override final
+ void SetSendingAllowed(bool state) override final
{
pv_SendingAllowed = state;
}
- bool getSendingAllowed() override final
+ bool GetSendingAllowed() override final
{
return pv_SendingAllowed;
}
- void selectAntenna(bsp::cellular::antenna antenna) override final;
+ void SelectAntenna(bsp::cellular::antenna antenna) override final;
- bsp::cellular::antenna getAntenna() override final;
+ bsp::cellular::antenna GetAntenna() override final;
private:
static constexpr speed_t baud_bits[] = {0,
@@ 74,6 74,8 @@ namespace bsp
B3000000,
B4000000};
+ static const uint32_t portBaudRate = 115200;
+
static const uint32_t MAX_EVENTS = 1;
int fd = -1;
M module-bsp/board/rt1051/bsp/cellular/rt1051_cellular.cpp => module-bsp/board/rt1051/bsp/cellular/rt1051_cellular.cpp +159 -162
@@ 2,16 2,17 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "rt1051_cellular.hpp"
+#include "FreeRTOS.h"
#include "task.h"
+#include "stream_buffer.h"
+#include "dma_config.h"
#include "fsl_cache.h"
#include <common_data/EventStore.hpp>
#include <ticks.hpp>
#include <algorithm>
-static bsp::cellular::CellularDMAResultStruct RXfer;
-
#if _RT1051_UART_DEBUG == 1
#define logUARTdebug(...) LOG_DEBUG(__VA_ARGS__)
#else
@@ 34,41 35,40 @@ extern "C"
{
void LPUART1_IRQHandler(void)
{
- std::uint32_t isrReg = LPUART_GetStatusFlags(CELLULAR_UART_BASE);
-
- if (bsp::RT1051Cellular::uartRxBuffer != NULL) {
- std::uint32_t count;
+ uint32_t isrReg = LPUART_GetStatusFlags(CELLULAR_UART_BASE);
- auto RxDmaStatus =
- LPUART_TransferGetReceiveCountEDMA(CELLULAR_UART_BASE, &bsp::RT1051Cellular::uartDmaHandle, &count);
-
- if (RxDmaStatus == kStatus_Success) {
- RXfer.dataSize = count;
- }
+ if (bsp::RT1051Cellular::uartRxStreamBuffer != NULL) {
+ auto RxDmaStatus = LPUART_TransferGetReceiveCountEDMA(
+ CELLULAR_UART_BASE,
+ &bsp::RT1051Cellular::uartDmaHandle,
+ reinterpret_cast<uint32_t *>(&bsp::RT1051Cellular::RXdmaReceivedCount));
- if ((isrReg & bsp::RT1051Cellular::startIRQMask) != 0u) {
+ if (isrReg & bsp::RT1051Cellular::startIRQMask) {
if (RxDmaStatus == kStatus_NoTransferInProgress) {
LPUART_DisableInterrupts(CELLULAR_UART_BASE, bsp::RT1051Cellular::startIRQMaskEnable);
- if (not bsp::RT1051Cellular::startReceive(bsp::RT1051Cellular::getMaxBufferDataSize())) {
+ bsp::RT1051Cellular::RXdmaReceivedCount = -1;
+ if (not bsp::RT1051Cellular::StartReceive(bsp::RT1051Cellular::GetFreeStreamBufferSize())) {
bsp::RT1051Cellular::RestartReceivingManually = true;
- bsp::RT1051Cellular::finishReceive();
+ bsp::RT1051Cellular::FinishReceive();
}
logUARTdebug("[RX] on Incoming data");
}
}
- if ((isrReg & bsp::RT1051Cellular::finishIRQMask) != 0u) {
+ if (isrReg & bsp::RT1051Cellular::finishIRQMask) {
if (RxDmaStatus != kStatus_NoTransferInProgress) {
LPUART_TransferAbortReceiveEDMA(CELLULAR_UART_BASE, &bsp::RT1051Cellular::uartDmaHandle);
logUARTdebug("[RX idle] stopped engine");
}
- logUARTdebug("[RX idle], received %d bytes", RXfer.dataSize);
+ logUARTdebug("[RX idle], received %d bytes", bsp::RT1051Cellular::RXdmaReceivedCount);
// the main exit path on transmission done
-
- if (RXfer.dataSize > 0) {
- bsp::RT1051Cellular::sendRxDmAresult(bsp::cellular::CellularResultCode::ReceivedAndIdle);
- }
- if (not bsp::RT1051Cellular::RestartReceivingManually) {
- bsp::RT1051Cellular::finishReceive();
+ if (bsp::RT1051Cellular::RXdmaReceivedCount >= 0) {
+ if (bsp::RT1051Cellular::RXdmaReceivedCount > 0) {
+ bsp::RT1051Cellular::MoveRxDMAtoStreamBuf(bsp::RT1051Cellular::RXdmaReceivedCount);
+ bsp::RT1051Cellular::RXdmaReceivedCount = -1;
+ }
+ if (not bsp::RT1051Cellular::RestartReceivingManually) {
+ bsp::RT1051Cellular::FinishReceive();
+ }
}
}
@@ 79,14 79,16 @@ extern "C"
namespace bsp
{
- std::size_t RT1051Cellular::RXdmaMaxReceivedCount = 0;
- bool RT1051Cellular::RestartReceivingManually = false;
+ uint8_t RT1051Cellular::RXdmaBuffer[RXdmaBufferSize] = {0};
+ ssize_t RT1051Cellular::RXdmaReceivedCount = -1;
+ size_t RT1051Cellular::RXdmaMaxReceivedCount = -1;
+ bool RT1051Cellular::RestartReceivingManually = false;
using namespace drivers;
- lpuart_edma_handle_t RT1051Cellular::uartDmaHandle = {};
- TaskHandle_t RT1051Cellular::untilReceivedNewHandle = nullptr;
- MessageBufferHandle_t RT1051Cellular::uartRxBuffer = nullptr;
+ lpuart_edma_handle_t RT1051Cellular::uartDmaHandle = {};
+ TaskHandle_t RT1051Cellular::untilReceivedNewHandle = nullptr;
+ StreamBufferHandle_t RT1051Cellular::uartRxStreamBuffer = nullptr;
RT1051Cellular::RT1051Cellular()
{
@@ 96,9 98,9 @@ namespace bsp
GPIO_PinRead(GPIO2, BSP_CELLULAR_SIM_TRAY_INSERTED_PIN) == 0 ? Store::GSM::Tray::IN : Store::GSM::Tray::OUT;
DMAInit();
- uartRxBuffer = xMessageBufferCreate(rxMessageBufferLength);
- if (uartRxBuffer == nullptr) {
- LOG_ERROR("Could not create the RX message buffer!");
+ uartRxStreamBuffer = xStreamBufferCreate(rxStreamBufferLength, rxStreamBufferNotifyWatermark);
+ if (uartRxStreamBuffer == NULL) {
+ LOG_ERROR("Could not create the RX stream buffer!");
return;
}
@@ 131,19 133,21 @@ namespace bsp
return;
}
- static_assert(rxMessageBufferLength >= RXfer.getMaxSize() + rxMessageBufferOverheadSize,
- "Minimum buffer size to hold one full DMA rxfer");
+ static_assert(rxStreamBufferLength >= 6, "Minimum buffer size (i.e. sufficient to enable flow control)");
+ static_assert(rxStreamBufferLength >= 1024, "To be able to fit entire response");
+
+ // CANNOT disable FIFO, dma *needs* it :o
+ // CELLULAR_UART_BASE->FIFO &= ~LPUART_FIFO_RXFE_MASK;
LPUART_ClearStatusFlags(CELLULAR_UART_BASE, 0xFFFFFFFF);
NVIC_ClearPendingIRQ(LPUART1_IRQn);
NVIC_SetPriority(LPUART1_IRQn, configLIBRARY_LOWEST_INTERRUPT_PRIORITY);
NVIC_EnableIRQ(LPUART1_IRQn);
- enableRx();
isInitialized = true;
}
- void RT1051Cellular::setSpeed(uint32_t portSpeed)
+ void RT1051Cellular::SetSpeed(uint32_t portSpeed)
{
LOG_DEBUG("[RT1051] Setting %" PRIu32 " baudrate", portSpeed);
LPUART_SetBaudRate(CELLULAR_UART_BASE, portSpeed, GetPerphSourceClock(PerphClock_LPUART));
@@ 151,13 155,14 @@ namespace bsp
RT1051Cellular::~RT1051Cellular()
{
- if (uartRxBuffer) {
- vMessageBufferDelete(uartRxBuffer);
- uartRxBuffer = nullptr;
+
+ if (uartRxStreamBuffer) {
+ vStreamBufferDelete(uartRxStreamBuffer);
+ uartRxStreamBuffer = nullptr;
}
- disableRx();
- disableTx();
+ DisableRx();
+ DisableTx();
NVIC_DisableIRQ(LPUART1_IRQn);
LPUART_DisableInterrupts(CELLULAR_UART_BASE,
@@ 174,66 179,83 @@ namespace bsp
untilReceivedNewHandle = nullptr;
}
- void RT1051Cellular::powerUp()
+ void RT1051Cellular::PowerUp()
{
- constexpr TickType_t POWER_UP_DELAY_MS = 500;
+ const TickType_t POWER_UP_DELAY_MS = 500;
- disableRx();
+ DisableRx();
- exitSleep();
+ ExitSleep();
TickType_t tick = xTaskGetTickCount();
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_POWER_PIN), 1);
vTaskDelayUntil(&tick, POWER_UP_DELAY_MS);
+ // BSP_CellularSetPowerState(CellularPowerStateTurningOn);
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_POWER_PIN), 0);
- enableRx();
+ EnableRx();
}
- void RT1051Cellular::powerDown()
+ void RT1051Cellular::PowerDown()
{
- constexpr std::uint16_t POWER_DOWN_DELAY_MS = 700;
+ const uint16_t POWER_DOWN_DELAY_MS = 700;
- exitSleep();
+ ExitSleep();
TickType_t tick = xTaskGetTickCount();
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_POWER_PIN), 1);
vTaskDelayUntil(&tick, POWER_DOWN_DELAY_MS);
+ // BSP_CellularSetPowerState(CellularPowerStateTurningOff);
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_POWER_PIN), 0);
+ // vTaskDelay(pdMS_TO_TICKS(POWER_DOWN_IN_PROGRESS_DELAY_MS));
+
+ /* while (s_cellularPowerState != CellularPowerStatePoweredDown)
+ {
+ vTaskDelay(pdMS_TO_TICKS(200));
+ }*/
- disableRx();
+ DisableRx();
}
- void RT1051Cellular::restart()
+ void RT1051Cellular::Restart()
{
- constexpr std::uint16_t RESET_DELAY_MS = 460;
+ const uint16_t RESET_DELAY_MS = 460;
- exitSleep();
+ ExitSleep();
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_RESET_PIN), 1);
vTaskDelay(pdMS_TO_TICKS(RESET_DELAY_MS));
gpio_2->WritePin(static_cast<uint32_t>(BoardDefinitions::CELLULAR_GPIO_2_RESET_PIN), 0);
}
- ssize_t RT1051Cellular::write(void *buf, size_t nbytes)
+ ssize_t RT1051Cellular::Write(void *buf, size_t nbytes)
{
lpuart_transfer_t sendXfer;
- //#if _RT1051_UART_DEBUG
- logData("TX", static_cast<uint8_t *>(buf), nbytes);
- //#endif
- sendXfer.data = static_cast<std::uint8_t *>(buf);
+#if _RT1051_UART_DEBUG
+ LOG_PRINTF("[TX: %d]", nbytes);
+ uint8_t *ptr = (uint8_t *)buf;
+ LOG_PRINTF("\n{");
+ for (size_t i = 0; i < nbytes; i++)
+ LOG_PRINTF("%02X ", (uint8_t)*ptr++);
+ LOG_PRINTF("}\n<");
+ ptr = (uint8_t *)buf;
+ for (size_t i = 0; i < nbytes; i++)
+ LOG_PRINTF("%c", (uint8_t)*ptr++);
+ LOG_PRINTF(">");
+ LOG_PRINTF("\n");
+#endif
+ sendXfer.data = static_cast<uint8_t *>(buf);
sendXfer.dataSize = nbytes;
- exitSleep();
+ ExitSleep();
uartDmaHandle.userData = xTaskGetCurrentTaskHandle();
SCB_CleanInvalidateDCache();
- enableTx();
-
+ EnableTx();
if (LPUART_SendEDMA(CELLULAR_UART_BASE, &uartDmaHandle, &sendXfer) != kStatus_Success) {
LOG_ERROR("Cellular: TX Failed!");
- disableTx();
+ DisableTx();
return -1;
}
@@ 242,53 264,44 @@ namespace bsp
if (ulNotificationValue == 0) {
LOG_ERROR("Cellular Uart error: TX Transmission timeout");
- disableTx();
+ DisableTx();
return -1;
}
- disableTx();
+ DisableTx();
return nbytes;
}
- bool RT1051Cellular::sendRxDmAresult(bsp::cellular::CellularResultCode reason)
+ bool RT1051Cellular::MoveRxDMAtoStreamBuf(size_t nbytes)
{
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
- if (RXfer.dataSize > getMaxBufferDataSize()) {
- LOG_ERROR("Cannot dump DMA buffer (%d>%d)", RXfer.dataSize, getMaxBufferDataSize());
- RestartReceivingManually = true;
+ assert(nbytes > 0);
+
+ if (nbytes > GetFreeStreamBufferSize()) {
+ LOG_ERROR("Cannot dump DMA buffer. Data is lost (%d>%d)", nbytes, GetFreeStreamBufferSize());
return false;
}
- RXfer.resultCode = reason;
- logUARTdebug("[RX reason] %d", reason);
-
#if _RT1051_UART_DEBUG
auto ret =
#endif
- xMessageBufferSendFromISR(uartRxBuffer, (void *)&RXfer, RXfer.getSize(), &xHigherPriorityTaskWoken);
+ xStreamBufferSendFromISR(uartRxStreamBuffer, (void *)&RXdmaBuffer, nbytes, &xHigherPriorityTaskWoken);
logUARTdebug("[RX] moved %d bytes to streambuf", ret);
portEND_SWITCHING_ISR(xHigherPriorityTaskWoken);
return true;
}
- size_t RT1051Cellular::getMaxBufferDataSize()
+ size_t RT1051Cellular::GetFreeStreamBufferSize()
{
- const auto messageOverhead =
- rxMessageBufferOverheadSize + bsp::cellular::CellularDMAResultStruct::getEmptySize();
-
- if (const auto bytesFree = xMessageBufferSpaceAvailable(uartRxBuffer); bytesFree > messageOverhead) {
- return bytesFree - messageOverhead;
- }
-
- return 0;
+ return xStreamBufferSpacesAvailable(bsp::RT1051Cellular::uartRxStreamBuffer);
}
- bool RT1051Cellular::startReceive(size_t nbytes)
+ bool RT1051Cellular::StartReceive(size_t nbytes)
{
- if (getMaxBufferDataSize() <= 0) {
+ if (!(GetFreeStreamBufferSize() > 0)) {
logUARTdebug("Not starting RX DMA, stream buffer is full. Be aware");
return false;
}
@@ 298,11 311,11 @@ namespace bsp
RXdmaMaxReceivedCount = std::min(nbytes, static_cast<size_t>(RXdmaBufferSize));
logUARTdebug("Starting DMA RX, max %d bytes", RXdmaMaxReceivedCount);
}
- RXfer.dataSize = 0;
+ assert(RXdmaMaxReceivedCount <= RXdmaBufferSize);
// start RXfer if there is a byte incoming and no pending RXfer
lpuart_transfer_t receiveXfer;
- receiveXfer.data = RXfer.data;
+ receiveXfer.data = RXdmaBuffer;
receiveXfer.dataSize = RXdmaMaxReceivedCount;
// rx config
@@ 320,54 333,50 @@ namespace bsp
return true;
}
- void RT1051Cellular::finishReceive()
+ void RT1051Cellular::FinishReceive()
{
logUARTdebug("[RX] finish");
bsp::cellular::notifyReceivedNew();
}
- ssize_t RT1051Cellular::read(void *buf,
- size_t nbytes,
- std::chrono::milliseconds timeoutMs = std::chrono::milliseconds{0})
+ ssize_t RT1051Cellular::Read(void *buf, size_t nbytes)
{
- logUARTdebug("[RX] Read");
- exitSleep();
-
- auto timeoutTicks = pdMS_TO_TICKS(timeoutMs.count());
- if (timeoutTicks > portMAX_DELAY) {
- timeoutTicks = portMAX_DELAY;
+ ExitSleep();
+ ssize_t ret = xStreamBufferReceive(uartRxStreamBuffer, buf, nbytes, 0);
+#if _RT1051_UART_DEBUG
+ if (ret > 0) {
+ LOG_PRINTF("[RX: %d]", ret);
+ uint8_t *ptr = (uint8_t *)buf;
+ LOG_PRINTF("\n{");
+ for (ssize_t i = 0; i < ret; i++)
+ LOG_PRINTF("%02X ", (uint8_t)*ptr++);
+ LOG_PRINTF("}\n<");
+ ptr = (uint8_t *)buf;
+ for (ssize_t i = 0; i < ret; i++)
+ LOG_PRINTF("%c", (uint8_t)*ptr++);
+ LOG_PRINTF(">");
}
-
- size_t ret = xMessageBufferReceive(uartRxBuffer, buf, nbytes, timeoutTicks);
-
- if (ret > bsp::cellular::CellularDMAResultStruct::getEmptySize()) {
- logData("RX", static_cast<uint8_t *>(buf), nbytes);
-
- if (RestartReceivingManually) {
- if (RXfer.dataSize > 0) {
- // residual data in DMA rx buffer
- logUARTdebug("[RX] Dumping there is residual data in dma buf");
- if (sendRxDmAresult(bsp::cellular::CellularResultCode::ReceivedAfterFull)) {
- return ret;
- }
- }
- logUARTdebug("[RX] resume on Paused");
- // need to start manually, as RegBuf might be already full, therefore no Active Edge Interrupt
- if (startReceive(getMaxBufferDataSize())) {
- RestartReceivingManually = false;
- }
- else {
- // do not lose information as whether manual start needs to be initiated and schedule next poke on
- // Read
- LOG_WARN("Modem is waiting to send data. Stream buffer likely too small");
- finishReceive();
- }
+ else {
+ LOG_PRINTF("[RX] GOT NOTHING (requested %d)", nbytes);
+ }
+ LOG_PRINTF("\n");
+#endif
+ if (RestartReceivingManually) {
+ logUARTdebug("[RX] resume on Paused");
+ // need to start manually, as RegBuf might be already full, therefore no Active Edge Interrupt
+ if (StartReceive(GetFreeStreamBufferSize())) {
+ RestartReceivingManually = false;
+ }
+ else {
+ // do not lose information as whether manual start needs to be initiated and schedule next poke on Read
+ LOG_WARN("Modem is waiting to send data. Stream buffer likely too small");
+ FinishReceive();
}
}
return ret;
}
- uint32_t RT1051Cellular::wait(std::chrono::milliseconds timeoutMs)
+ uint32_t RT1051Cellular::Wait(uint32_t timeout)
{
logUARTdebug("[WAIT]");
if (untilReceivedNewHandle != nullptr) {
@@ 376,32 385,32 @@ namespace bsp
}
// no need to wait: buffer already contains something
- if (!xMessageBufferIsEmpty(uartRxBuffer)) {
+ if (xStreamBufferBytesAvailable(uartRxStreamBuffer)) {
return 1;
}
- enableRx();
+ EnableRx();
// …start waiting for [timeout] until a new xfer from modem is received
untilReceivedNewHandle = xTaskGetCurrentTaskHandle();
- auto ret = ulTaskNotifyTake(pdTRUE, pdMS_TO_TICKS(timeoutMs.count()));
+ auto ret = ulTaskNotifyTake(pdTRUE, timeout);
untilReceivedNewHandle = nullptr;
return ret;
}
- void RT1051Cellular::informModemHostAsleep()
+ void RT1051Cellular::InformModemHostAsleep()
{
gpio_2->WritePin(magic_enum::enum_integer(BoardDefinitions::CELLULAR_GPIO_2_APRDY_PIN),
!CELLULAR_BSP_AP_READY_PIN_ACTIVE_STATE);
}
- void RT1051Cellular::informModemHostWakeup()
+ void RT1051Cellular::InformModemHostWakeup()
{
gpio_2->WritePin(magic_enum::enum_integer(BoardDefinitions::CELLULAR_GPIO_2_APRDY_PIN),
CELLULAR_BSP_AP_READY_PIN_ACTIVE_STATE);
}
- void RT1051Cellular::enterSleep()
+ void RT1051Cellular::EnterSleep()
{
if (!isInSleepMode) {
isInSleepMode = true;
@@ 410,14 419,15 @@ namespace bsp
gpio_2->WritePin(magic_enum::enum_integer(BoardDefinitions::CELLULAR_GPIO_2_WAKEUP_PIN), 1);
// Host sleep information must be before UART disable
- informModemHostAsleep();
+ InformModemHostAsleep();
+
if (driverLPUART) {
driverLPUART->Disable();
}
}
}
- void RT1051Cellular::exitSleep()
+ void RT1051Cellular::ExitSleep()
{
// reset sleep timer countdown
lastCommunicationTimestamp = cpp_freertos::Ticks::TicksToMs(cpp_freertos::Ticks::GetTicks());
@@ 434,7 444,7 @@ namespace bsp
vTaskDelay(pdMS_TO_TICKS(15));
// Host wake up information must be after UART enable
- informModemHostWakeup();
+ InformModemHostWakeup();
}
}
@@ 551,6 561,10 @@ namespace bsp
void RT1051Cellular::DMAInit()
{
+
+ // TODO:M.P add PLL support
+ // pll = DriverInterface<DriverPLL>::Create(static_cast<PLLInstances >(BoardDefinitions
+ // ::AUDIO_PLL),DriverPLLParams{});
dmamux =
DriverDMAMux::Create(static_cast<DMAMuxInstances>(BoardDefinitions::CELLULAR_DMAMUX), DriverDMAMuxParams{});
dma = DriverDMA::Create(static_cast<DMAInstances>(BoardDefinitions::CELLULAR_DMA), DriverDMAParams{});
@@ 594,30 608,29 @@ namespace bsp
}
case kStatus_LPUART_RxIdle:
logUARTdebug("[RX] Chunk done. Flow control must hold the gate from now on");
- RXfer.dataSize = RXdmaMaxReceivedCount;
- if (sendRxDmAresult(cellular::CellularResultCode::ReceivedAndFull) and
- startReceive(getMaxBufferDataSize())) {
+ if (MoveRxDMAtoStreamBuf(RXdmaMaxReceivedCount) and StartReceive(GetFreeStreamBufferSize())) {
// usual mode: append a chunk and wait for line idle to finish receive
}
else {
// the auxiliary exit path on stream buffer full
RestartReceivingManually = true;
- finishReceive();
+ FinishReceive();
}
+ RXdmaReceivedCount = -1;
break;
}
}
- void RT1051Cellular::setSendingAllowed(bool state)
+ void RT1051Cellular::SetSendingAllowed(bool state)
{
pv_SendingAllowed = state;
}
- bool RT1051Cellular::getSendingAllowed()
+ bool RT1051Cellular::GetSendingAllowed()
{
return pv_SendingAllowed;
}
- void RT1051Cellular::selectAntenna(bsp::cellular::antenna antenna)
+ void RT1051Cellular::SelectAntenna(bsp::cellular::antenna antenna)
{
if (antenna == bsp::cellular::antenna::lowBand) {
gpio_2->WritePin(magic_enum::enum_integer(BoardDefinitions::CELLULAR_GPIO_2_ANTSEL_PIN),
@@ 631,7 644,7 @@ namespace bsp
}
}
- bsp::cellular::antenna RT1051Cellular::getAntenna()
+ bsp::cellular::antenna RT1051Cellular::GetAntenna()
{
// make sure ANTSEL pin has Software Input On Field set
bool whichAntenna = gpio_2->ReadPin(magic_enum::enum_integer(BoardDefinitions::CELLULAR_GPIO_2_ANTSEL_PIN));
@@ 639,23 652,6 @@ namespace bsp
: bsp::cellular::antenna::highBand);
}
- void RT1051Cellular::logData(std::string title, uint8_t *buffer, size_t nbytes)
- {
-#if _RT1051_UART_DEBUG == 1
- LOG_PRINTF("[%s: %d]", title.c_str(), nbytes);
- uint8_t *ptr = buffer;
- LOG_PRINTF("\n{");
- for (size_t i = 0; i < nbytes; i++)
- LOG_PRINTF("%02X ", *(ptr++));
- LOG_PRINTF("}\n<");
- ptr = buffer;
- for (size_t i = 0; i < nbytes; i++)
- LOG_PRINTF("%c", *(ptr++));
- LOG_PRINTF(">");
- LOG_PRINTF("\n");
-#endif
- }
-
namespace cellular
{
static xQueueHandle qhandle = nullptr;
@@ 720,7 716,7 @@ namespace bsp
{
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
if (qhandle != NULL) {
- std::uint8_t val = static_cast<std::uint8_t>(IRQsource::statusPin);
+ uint8_t val = static_cast<uint8_t>(IRQsource::statusPin);
xQueueSendFromISR(qhandle, &val, &xHigherPriorityTaskWoken);
}
return xHigherPriorityTaskWoken;
@@ 731,12 727,12 @@ namespace bsp
namespace sim
{
- auto trayIRQHandler() -> BaseType_t
+ auto trayIRQ_handler() -> BaseType_t
{
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
if (qhandle) {
- std::uint8_t val = static_cast<std::uint8_t>(IRQsource::trayPin);
+ uint8_t val = static_cast<uint8_t>(IRQsource::trayPin);
xQueueSendFromISR(qhandle, &val, &xHigherPriorityTaskWoken);
}
return xHigherPriorityTaskWoken;
@@ 749,14 745,14 @@ namespace bsp
return state;
}
- void hotSwapTrigger()
+ void hotswap_trigger()
{
GPIO_PinWrite(BSP_CELLULAR_SIM_CARD_PRESENCE_PORT, BSP_CELLULAR_SIM_CARD_PRESENCE_PIN, 1);
vTaskDelay(100); // sleep for 100 ms...
GPIO_PinWrite(BSP_CELLULAR_SIM_CARD_PRESENCE_PORT, BSP_CELLULAR_SIM_CARD_PRESENCE_PIN, 0);
}
- void simSelect()
+ void sim_sel()
{
if (Store::GSM::get()->selected == Store::GSM::SIM::SIM2) {
GPIO_PinWrite(BSP_CELLULAR_SIM_CARD_PRESENCE_PORT, BSP_CELLULAR_SIMSEL_PIN, 1);
@@ 769,15 765,16 @@ namespace bsp
namespace ringIndicator
{
- auto riIRQHandler() -> BaseType_t
+ auto riIRQ_handler() -> BaseType_t
{
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
if (qhandle != NULL) {
- std::uint8_t val = static_cast<std::uint8_t>(IRQsource::ringIndicatorPin);
+ uint8_t val = static_cast<uint8_t>(IRQsource::ringIndicatorPin);
xQueueSendFromISR(qhandle, &val, &xHigherPriorityTaskWoken);
}
return xHigherPriorityTaskWoken;
}
} // namespace ringIndicator
- } // namespace cellular
+
+ } // namespace cellular
} // namespace bsp
M module-bsp/board/rt1051/bsp/cellular/rt1051_cellular.hpp => module-bsp/board/rt1051/bsp/cellular/rt1051_cellular.hpp +83 -50
@@ 1,18 1,18 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#pragma once
+#ifndef PUREPHONE_RT1501_CELLULAR_HPP
+#define PUREPHONE_RT1501_CELLULAR_HPP
-#include <FreeRTOS.h>
-#include <message_buffer.h>
-#include <timers.h>
+#include "bsp/cellular/bsp_cellular.hpp"
+#include "FreeRTOS.h"
+#include "stream_buffer.h"
+#include "timers.h"
#include "board.h"
#include "fsl_lpuart.h"
#include "fsl_lpuart_edma.h"
-#include "bsp/cellular/bsp_cellular.hpp"
-#include "bsp/cellular/CellularResult.hpp"
#include "bsp/BoardDefinitions.hpp"
#include "drivers/pll/DriverPLL.hpp"
@@ 22,85 22,97 @@
namespace bsp
{
+
class RT1051Cellular : public Cellular
{
private:
bool pv_SendingAllowed = true;
- void logData(std::string title, uint8_t *buffer, size_t nbytes);
-
public:
RT1051Cellular();
~RT1051Cellular();
- void powerUp() override final;
- void powerDown() override final;
- void restart() override final;
- uint32_t wait(std::chrono::milliseconds timeoutMs) override final;
- ssize_t read(void *buf, size_t nbytes, std::chrono::milliseconds timeoutMs) override final;
- ssize_t write(void *buf, size_t nbytes) override final;
- void informModemHostAsleep() override final;
- void informModemHostWakeup() override final;
- void enterSleep() override final;
- void exitSleep() override final;
- void setSpeed(uint32_t portSpeed) override final;
- void setSendingAllowed(bool state) override final;
- bool getSendingAllowed() override final;
- void selectAntenna(bsp::cellular::antenna antenna) override final;
- bsp::cellular::antenna getAntenna() override final;
-
- static MessageBufferHandle_t uartRxBuffer;
- static lpuart_edma_handle_t uartDmaHandle;
- static bool RestartReceivingManually;
- static constexpr std::size_t RXdmaBufferSize = 64;
- static std::size_t RXdmaMaxReceivedCount;
+ void PowerUp() override final;
- static constexpr std::uint32_t startIRQMaskEnable =
- kLPUART_RxActiveEdgeInterruptEnable | kLPUART_RxDataRegFullInterruptEnable;
- static constexpr std::uint32_t finishIRQMaskEnable = kLPUART_IdleLineInterruptEnable;
- static constexpr std::uint32_t startIRQMask = kLPUART_RxActiveEdgeFlag | kLPUART_RxDataRegFullFlag;
- static constexpr std::uint32_t finishIRQMask = kLPUART_IdleLineFlag;
+ void PowerDown() override final;
- static bool sendRxDmAresult(bsp::cellular::CellularResultCode reason);
- static std::size_t getMaxBufferDataSize();
- static bool startReceive(std::size_t nbytes);
- static void finishReceive();
+ void Restart() override final;
- static TaskHandle_t untilReceivedNewHandle;
+ uint32_t Wait(uint32_t timeout) override final;
+
+ ssize_t Read(void *buf, size_t nbytes) override final;
+
+ ssize_t Write(void *buf, size_t nbytes) override final;
+
+ void InformModemHostAsleep() override final;
+
+ void InformModemHostWakeup() override final;
+
+ void EnterSleep() override final;
+
+ void ExitSleep() override final;
+
+ void SetSpeed(uint32_t portSpeed) override final;
+
+ void SetSendingAllowed(bool state) override final;
+ bool GetSendingAllowed() override final;
+
+ static StreamBufferHandle_t uartRxStreamBuffer;
+ static TimerHandle_t rxTimeoutTimer;
+
+ void SelectAntenna(bsp::cellular::antenna antenna) override final;
+ bsp::cellular::antenna GetAntenna() override final;
+
+ static lpuart_edma_handle_t uartDmaHandle;
+
+ static void FinishReceive();
+
+ static bool RestartReceivingManually;
private:
void MSPInit();
+
void MSPDeinit();
+
void DMAInit();
+
void DMADeinit();
- static void uartDMACallback(LPUART_Type *base, lpuart_edma_handle_t *handle, status_t status, void *userData);
+ public:
+ static constexpr uint32_t startIRQMaskEnable =
+ kLPUART_RxActiveEdgeInterruptEnable | kLPUART_RxDataRegFullInterruptEnable;
+ static constexpr uint32_t finishIRQMaskEnable = kLPUART_IdleLineInterruptEnable;
+
+ static constexpr uint32_t startIRQMask = kLPUART_RxActiveEdgeFlag | kLPUART_RxDataRegFullFlag;
+ static constexpr uint32_t finishIRQMask = kLPUART_IdleLineFlag;
- static inline void enableRx(uint32_t irqMask = startIRQMaskEnable | finishIRQMaskEnable)
+ private:
+ static inline void EnableRx(uint32_t irqMask = startIRQMaskEnable | finishIRQMaskEnable)
{
LPUART_ClearStatusFlags(CELLULAR_UART_BASE, 0xFFFFFFFF);
LPUART_EnableInterrupts(CELLULAR_UART_BASE, irqMask);
LPUART_EnableRx(CELLULAR_UART_BASE, true);
}
- static inline void disableRx(uint32_t irqMask = startIRQMaskEnable | finishIRQMaskEnable)
+ static inline void DisableRx(uint32_t irqMask = startIRQMaskEnable | finishIRQMaskEnable)
{
LPUART_DisableInterrupts(CELLULAR_UART_BASE, irqMask);
LPUART_ClearStatusFlags(CELLULAR_UART_BASE, irqMask);
LPUART_EnableRx(CELLULAR_UART_BASE, false);
}
- inline void enableTx()
+ inline void EnableTx()
{
LPUART_EnableTx(CELLULAR_UART_BASE, true);
}
- inline void disableTx()
+ inline void DisableTx()
{
LPUART_EnableTx(CELLULAR_UART_BASE, false);
}
+ // M.P: It is important to destroy these drivers in specific order
std::shared_ptr<drivers::DriverPLL> pll;
std::shared_ptr<drivers::DriverGPIO> gpio_1;
std::shared_ptr<drivers::DriverGPIO> gpio_2;
@@ 110,11 122,32 @@ namespace bsp
std::unique_ptr<drivers::DriverDMAHandle> txDMAHandle;
std::unique_ptr<drivers::DriverDMAHandle> rxDMAHandle;
- static constexpr std::uint32_t baudrate = 115200;
- static constexpr std::uint32_t rxMessageBufferLength = 1024;
- static constexpr std::uint16_t rxMessageBufferOverheadSize = 4;
- static constexpr std::uint32_t CELLULAR_BSP_AP_READY_PIN_ACTIVE_STATE = 1;
- static constexpr std::uint32_t CELLULAR_BSP_ANTSEL_PIN_A_STATE = 0;
- static constexpr std::uint32_t CELLULAR_BSP_ANTSEL_PIN_B_STATE = 1;
+ static void uartDMACallback(LPUART_Type *base, lpuart_edma_handle_t *handle, status_t status, void *userData);
+
+ public:
+ static TaskHandle_t blockedTaskHandle;
+
+ private:
+ // Constants
+ const static uint32_t baudrate = 115200;
+ const static uint32_t rxStreamBufferLength = 1024;
+ const static uint32_t rxStreamBufferNotifyWatermark = 1;
+ const static uint32_t CELLULAR_BSP_AP_READY_PIN_ACTIVE_STATE = 1;
+ const static uint32_t CELLULAR_BSP_ANTSEL_PIN_A_STATE = 0;
+ const static uint32_t CELLULAR_BSP_ANTSEL_PIN_B_STATE = 1;
+
+ public:
+ static constexpr size_t RXdmaBufferSize = 16;
+ static uint8_t RXdmaBuffer[RXdmaBufferSize];
+ static ssize_t RXdmaReceivedCount;
+ static size_t RXdmaMaxReceivedCount;
+ static bool MoveRxDMAtoStreamBuf(size_t nbytes);
+ static size_t GetFreeStreamBufferSize();
+ static bool StartReceive(size_t nbytes);
+
+ static TaskHandle_t untilReceivedNewHandle;
};
+
} // namespace bsp
+
+#endif // PUREPHONE_RT1501_CELLULAR_HPP
M module-bsp/board/rt1051/common/irq/irq_gpio.cpp => module-bsp/board/rt1051/common/irq/irq_gpio.cpp +2 -2
@@ 122,7 122,7 @@ namespace bsp
}
if (irq_mask & (1 << BSP_CELLULAR_SIM_TRAY_INSERTED_PIN)) {
- xHigherPriorityTaskWoken |= bsp::cellular::sim::trayIRQHandler();
+ xHigherPriorityTaskWoken |= bsp::cellular::sim::trayIRQ_handler();
}
if (irq_mask & (1 << static_cast<uint32_t>(BoardDefinitions::LIGHT_SENSOR_IRQ))) {
@@ 154,7 154,7 @@ namespace bsp
}
if (irq_mask & (1 << BSP_CELLULAR_RI_PIN)) {
- bsp::cellular::ringIndicator::riIRQHandler();
+ bsp::cellular::ringIndicator::riIRQ_handler();
}
// Clear all IRQs
D module-bsp/bsp/cellular/CellularResult.hpp => module-bsp/bsp/cellular/CellularResult.hpp +0 -156
@@ 1,156 0,0 @@
-#pragma once
-
-#include <memory>
-#include <module-utils/Utils.hpp>
-#include <utility>
-
-namespace bsp::cellular
-{
- enum class CellularResultCode : std::uint8_t
- {
- Uninitialized,
- ReceivedAndIdle,
- ReceivedAndFull,
- ReceivedAfterFull,
- ReceivingNotStarted,
- ReceivedNoData,
- TransmittingNotStarted,
- CMUXFrameError,
- };
-
- constexpr size_t CellularResultStructMaxDataSize = 128;
-
- struct __attribute__((__packed__)) CellularDMAResultStruct
- {
- CellularResultCode resultCode = CellularResultCode::ReceivedNoData;
- size_t dataSize = 0;
- std::uint8_t data[CellularResultStructMaxDataSize];
-
- constexpr static size_t getEmptySize()
- {
- return sizeof(CellularDMAResultStruct) - CellularResultStructMaxDataSize;
- }
-
- constexpr static size_t getMaxSize()
- {
- return getEmptySize() + sizeof(data);
- }
-
- size_t getSize()
- {
- return getEmptySize() + dataSize;
- }
- };
-
- struct CellularResultStruct
- {
- CellularResultCode resultCode = CellularResultCode::Uninitialized;
- std::vector<uint8_t> data;
-
- [[nodiscard]] auto serialize() const -> std::unique_ptr<uint8_t>
- {
- auto serialized = std::unique_ptr<uint8_t>(new uint8_t[data.size() + sizeof(resultCode)]);
- serialized.get()[0] = static_cast<unsigned char>(resultCode);
-
- if(data.size() > 0) {
- memcpy(serialized.get() + 1, data.data(), data.size());
- }
-
- return serialized;
- }
-
- auto deserialize(const uint8_t *serialized, const size_t size) -> void
- {
- if (size > 0) {
- resultCode = static_cast<CellularResultCode>(*serialized);
- if (size > 1) {
- data = {serialized + 1, serialized + size};
- }
- }
- }
-
- [[nodiscard]] auto getSerializedSize() const -> size_t
- {
- return (sizeof(resultCode) + data.size());
- }
- };
-
- class CellularResult
- {
- CellularResultStruct result;
-
- public:
- CellularResult() : result{CellularResultCode::Uninitialized, {}}
- {}
-
- explicit CellularResult(CellularDMAResultStruct &result)
- : result{result.resultCode, {result.data, result.data + result.dataSize}}
- {}
-
- explicit CellularResult(CellularResultStruct result) : result{std::move(result)}
- {}
-
- explicit CellularResult(const uint8_t *serialized, const size_t size)
- {
- result.deserialize(serialized, size);
- }
-
- auto getResultCode() const noexcept -> CellularResultCode
- {
- return result.resultCode;
- }
-
- auto setResultCode(CellularResultCode code) -> void
- {
- result.resultCode = code;
- }
-
- auto getData() const noexcept -> std::vector<uint8_t> const &
- {
- return result.data;
- }
-
- auto setData(const std::vector<uint8_t> &data) -> void
- {
- result.data = data;
- }
-
- auto getDataAsString() const -> std::string const
- {
- return std::string{result.data.begin(), result.data.end()};
- }
-
- auto getStruct() -> CellularResultStruct const *
- {
- return &result;
- }
-
- auto getSerialized() const -> std::unique_ptr<uint8_t>
- {
- return result.serialize();
- }
-
- auto getSerializedSize() const noexcept -> size_t
- {
- return result.getSerializedSize();
- }
- };
-} // namespace bsp::cellular
-
-inline const char *c_str(bsp::cellular::CellularResultCode result)
-{
- switch (result) {
- case bsp::cellular::CellularResultCode::ReceivedAndIdle:
- return "ReceivedAndIdle";
- case bsp::cellular::CellularResultCode::ReceivedAndFull:
- return "ReceivedAndFull";
- case bsp::cellular::CellularResultCode::ReceivedAfterFull:
- return "ReceivedAfterFull";
- case bsp::cellular::CellularResultCode::ReceivingNotStarted:
- return "ReceivingNotStarted";
- case bsp::cellular::CellularResultCode::TransmittingNotStarted:
- return "TransmittingNotStarted";
- default:
- return "Unknown";
- }
-}
M module-bsp/bsp/cellular/bsp_cellular.cpp => module-bsp/bsp/cellular/bsp_cellular.cpp +10 -9
@@ 8,10 8,11 @@
#error "Unsupported target"
#endif
-namespace bsp
-{
- std::optional<std::unique_ptr<Cellular>> Cellular::create([[maybe_unused]] const char *term, uint32_t portSpeed)
- {
+
+namespace bsp{
+
+ std::optional<std::unique_ptr<Cellular>> Cellular::Create(
+ [[maybe_unused]] const char* term, uint32_t portSpeed) {
std::unique_ptr<Cellular> inst;
@@ 23,26 24,26 @@ namespace bsp
#error "Unsupported target"
#endif
- if (inst->isInitialized) {
+ if(inst->isInitialized){
return inst;
}
return {};
}
- [[nodiscard]] auto Cellular::getCellularDevice() const noexcept -> std::shared_ptr<devices::Device>
+ [[nodiscard]] auto Cellular::GetCellularDevice() const noexcept -> std::shared_ptr<devices::Device>
{
return driverLPUART;
}
- [[nodiscard]] auto Cellular::getLastCommunicationTimestamp() const noexcept -> TickType_t
+ [[nodiscard]] auto Cellular::GetLastCommunicationTimestamp() const noexcept -> TickType_t
{
return lastCommunicationTimestamp;
}
- [[nodiscard]] auto Cellular::isCellularInSleepMode() const noexcept -> bool
+ [[nodiscard]] auto Cellular::IsCellularInSleepMode() const noexcept -> bool
{
return isInSleepMode;
}
-} // namespace bsp
+}
M module-bsp/bsp/cellular/bsp_cellular.hpp => module-bsp/bsp/cellular/bsp_cellular.hpp +51 -61
@@ 5,65 5,61 @@
#include <stdint.h>
#include <stddef.h>
#include <memory>
-#include <chrono>
#include <FreeRTOS.h>
#include <FreeRTOS/include/queue.h>
#include "drivers/lpuart/DriverLPUART.hpp"
#include <common_data/EventStore.hpp>
-namespace bsp
-{
- namespace cellular
+namespace bsp {
+namespace cellular
{
- enum class antenna
- {
- lowBand,
- highBand
- };
+ enum class antenna{
+ lowBand,
+ highBand
+ };
}
- class Cellular
- {
- public:
- static std::optional<std::unique_ptr<Cellular>> create(const char *term = "/dev/ttyUSB0",
- uint32_t portSpeed = 115200);
+ class Cellular {
+ public:
+
+ static std::optional<std::unique_ptr<Cellular>> Create(const char* term = "/dev/ttyUSB0", uint32_t portSpeed = 115200);
- Cellular() = default;
- virtual ~Cellular() = default;
+ Cellular() {}
+ virtual ~Cellular() {}
- virtual void powerUp() = 0;
- virtual void powerDown() = 0;
+ virtual void PowerUp() = 0;
- virtual void restart() = 0;
+ virtual void PowerDown() = 0;
- virtual uint32_t wait(std::chrono::milliseconds timeoutMs) = 0;
+ virtual void Restart() = 0;
- virtual ssize_t read(void *buf, size_t nbytes, std::chrono::milliseconds timeoutMs) = 0;
+ virtual uint32_t Wait(uint32_t timeout) = 0;
- virtual ssize_t write(void *buf, size_t nbytes) = 0;
+ virtual ssize_t Read(void *buf, size_t nbytes) = 0;
- virtual void informModemHostAsleep() = 0;
+ virtual ssize_t Write(void *buf, size_t nbytes) = 0;
- virtual void informModemHostWakeup() = 0;
+ virtual void InformModemHostAsleep() = 0;
- virtual void enterSleep() = 0;
+ virtual void InformModemHostWakeup() = 0;
- virtual void exitSleep() = 0;
+ virtual void EnterSleep() = 0;
- virtual void setSpeed(uint32_t portSpeed) = 0;
+ virtual void ExitSleep() = 0;
- virtual void setSendingAllowed(bool state) = 0;
+ virtual void SetSpeed(uint32_t portSpeed) = 0;
- virtual bool getSendingAllowed() = 0;
+ virtual void SetSendingAllowed(bool state) = 0;
+ virtual bool GetSendingAllowed() = 0;
- virtual void selectAntenna(bsp::cellular::antenna antenna) = 0;
- virtual bsp::cellular::antenna getAntenna() = 0;
+ virtual void SelectAntenna(bsp::cellular::antenna antenna) = 0;
+ virtual bsp::cellular::antenna GetAntenna() = 0;
- [[nodiscard]] auto getCellularDevice() const noexcept -> std::shared_ptr<devices::Device>;
- [[nodiscard]] auto getLastCommunicationTimestamp() const noexcept -> TickType_t;
- [[nodiscard]] auto isCellularInSleepMode() const noexcept -> bool;
+ [[nodiscard]] auto GetCellularDevice() const noexcept -> std::shared_ptr<devices::Device>;
+ [[nodiscard]] auto GetLastCommunicationTimestamp() const noexcept -> TickType_t;
+ [[nodiscard]] auto IsCellularInSleepMode() const noexcept -> bool;
- protected:
+ protected:
bool isInitialized = false;
bool isInSleepMode{false};
TickType_t lastCommunicationTimestamp;
@@ 71,42 67,36 @@ namespace bsp
std::shared_ptr<drivers::DriverLPUART> driverLPUART;
};
namespace cellular
- {
- enum IRQsource
{
+ enum IRQsource{
statusPin,
trayPin,
- ringIndicatorPin,
+ ringIndicatorPin,
};
/// initialize SIM queue directed to EventWorker
int init(xQueueHandle qHandle);
- namespace USB
- {
- enum class PassthroughState
- {
+ namespace USB {
+ enum class PassthroughState {
ENABLED,
DISABLED,
};
- enum class BootPinState
- {
+ enum class BootPinState {
FIRMWARE_UPGRADE,
NORMAL_BOOT,
};
- BootPinState getBootPin();
- PassthroughState getPassthrough();
+ BootPinState getBootPin() ;
+ PassthroughState getPassthrough() ;
void setBootPin(BootPinState bootPin);
void setPassthrough(PassthroughState pass);
- } // namespace USB
+ }
- namespace status
- {
- enum class value
- {
+ namespace status{
+ enum class value {
/// from the docs: When the module is turned on normally, the STATUS will present the low state.
ACTIVE,
INACTIVE,
@@ 114,27 104,27 @@ namespace bsp
/// returns true if status OK. Open drain pulled up; ground is OK.
bsp::cellular::status::value getStatus();
BaseType_t statusIRQhandler();
- } // namespace status
+ }
namespace sim
{
/// handler for SIM tray which is connected to phone, not GSM
- BaseType_t trayIRQHandler();
+ BaseType_t trayIRQ_handler();
Store::GSM::Tray getTray();
/// trigger swap pin on gsm so that it would reload sim card in tray
/// after that +QPIN urc should come
- void hotSwapTrigger();
- void simSelect();
+ void hotswap_trigger();
+ void sim_sel();
} // namespace sim
namespace ringIndicator
- {
- // handling incoming calls and sms - RI pin
- BaseType_t riIRQHandler();
- } // namespace ringIndicator
+ {
+ // handling incoming calls and sms - RI pin
+ BaseType_t riIRQ_handler();
+ } // namespace RingIndicator
- } // namespace cellular
-}; // namespace bsp
+ } // namespace cellular
+}; // namespace bsp
#endif // PUREPHONE_BSP_CELLULAR_HPP
M module-cellular/Modem/ATCommon.cpp => module-cellular/Modem/ATCommon.cpp +22 -45
@@ 8,6 8,7 @@
#include <log/log.hpp>
#include <string>
#include <ticks.hpp>
+#include <vector>
#include <inttypes.h> // for PRIu32
#include <Utils.hpp>
#include "ATStream.hpp"
@@ 26,22 27,22 @@ const std::string Channel::CMS_ERROR = "+CMS ERROR:";
// const std::string Channel::RING = "RING";
// const std::string Channel::NO_DIALTONE = "NO DIALTONE";
-void Channel::cmdLog(std::string cmd, const Result &result, std::chrono::milliseconds timeout)
+void Channel::cmd_log(std::string cmd, const Result &result, uint32_t timeout)
{
cmd.erase(std::remove(cmd.begin(), cmd.end(), '\r'), cmd.end());
cmd.erase(std::remove(cmd.begin(), cmd.end(), '\n'), cmd.end());
switch (result.code) {
case Result::Code::TIMEOUT: {
- LOG_ERROR(
- "[AT]: >%s<, timeout %llu - please check the value with Quectel_EC25&EC21_AT_Commands_Manual_V1.3.pdf",
- cmd.c_str(),
- static_cast<long long unsigned int>(timeout.count()));
+ LOG_INFO("[AT]: >%s<, timeout %" PRIu32
+ " - please check the value with Quectel_EC25&EC21_AT_Commands_Manual_V1.3.pdf",
+ cmd.c_str(),
+ timeout);
} break;
case Result::Code::ERROR: {
- LOG_ERROR("[AT]: >%s<, >%s<", cmd.c_str(), result.response.size() ? result.response.back().c_str() : "");
+ LOG_INFO("[AT]: >%s<, >%s<", cmd.c_str(), result.response.size() ? result.response.back().c_str() : "");
} break;
default:
- LOG_DEBUG("[AT]: >%s<, >%s<", cmd.c_str(), result.response.size() ? result.response.back().c_str() : "");
+ LOG_INFO("[AT]: >%s<, >%s<", cmd.c_str(), result.response.size() ? result.response.back().c_str() : "");
break;
}
#if DEBUG_MODEM_OUTPUT_RESPONSE
@@ 63,31 64,30 @@ std::string Channel::formatCommand(const std::string &cmd) const
Result Channel::cmd(const std::string &cmd, std::chrono::milliseconds timeout, size_t rxCount)
{
Result result;
- ATStream atStream(rxCount);
-
- awaitingResponseFlag.set();
+ blockedTaskHandle = xTaskGetCurrentTaskHandle();
cmd_init();
std::string cmdFixed = formatCommand(cmd);
+
cmd_send(cmdFixed);
- auto startTime = std::chrono::steady_clock::now();
- auto endTime = startTime + timeout;
+ uint32_t currentTime = cpp_freertos::Ticks::GetTicks();
+ uint32_t timeoutNeeded = ((timeout.count() == UINT32_MAX) ? UINT32_MAX : currentTime + timeout.count());
+ uint32_t timeElapsed = currentTime;
+
+ ATStream atStream(rxCount);
while (true) {
- if (std::chrono::steady_clock::now() > endTime) {
+ if (timeoutNeeded != UINT32_MAX && timeElapsed >= timeoutNeeded) {
result.code = Result::Code::TIMEOUT;
break;
}
- if (size_t bytesRead = cmd_receive(receiveBuffer.get(), std::chrono::milliseconds{0}); bytesRead > 0) {
- auto cellularResult = bsp::cellular::CellularResult{receiveBuffer.get(), bytesRead};
+ auto taskUnlocked = ulTaskNotifyTake(pdTRUE, timeoutNeeded - timeElapsed);
+ timeElapsed = cpp_freertos::Ticks::GetTicks();
- if (result = checkResult(cellularResult.getResultCode()); result.code != at::Result::Code::OK) {
- break;
- }
-
- atStream.write(cellularResult.getDataAsString());
+ if (taskUnlocked) {
+ atStream.write(cmd_receive());
if (atStream.isReady()) {
result = atStream.getResult();
@@ 96,10 96,9 @@ Result Channel::cmd(const std::string &cmd, std::chrono::milliseconds timeout, s
}
}
- awaitingResponseFlag.clear();
-
+ blockedTaskHandle = nullptr;
cmd_post();
- cmdLog(cmdFixed, result, timeout);
+ cmd_log(cmdFixed, result, timeout.count());
return result;
}
@@ 116,25 115,3 @@ auto Channel::cmd(const at::AT &at) -> Result
auto time = utils::time::Scoped("Time to run at command" + cmd.getCmd());
return this->cmd(cmd);
}
-
-Result Channel::checkResult(bsp::cellular::CellularResultCode cellularResult)
-{
- Result result;
-
- switch (cellularResult) {
- case bsp::cellular::CellularResultCode::ReceivingNotStarted:
- result.code = Result::Code::RECEIVING_NOT_STARTED;
- break;
- case bsp::cellular::CellularResultCode::TransmittingNotStarted:
- result.code = Result::Code::TRANSMISSION_NOT_STARTED;
- break;
- case bsp::cellular::CellularResultCode::CMUXFrameError:
- result.code = Result::Code::CMUX_FRAME_ERROR;
- break;
- default:
- result.code = Result::Code::OK;
- break;
- }
-
- return result;
-}
M module-cellular/Modem/ATCommon.hpp => module-cellular/Modem/ATCommon.hpp +9 -44
@@ 7,7 7,6 @@
#include <at/ErrorCode.hpp>
#include <mutex.hpp>
#include <task.h>
-#include <message_buffer.h>
#include "BaseChannel.hpp"
namespace sys
@@ 17,37 16,7 @@ namespace sys
namespace at
{
- constexpr auto delimiter = "\r\n"; /// use std::strlen()
- constexpr auto defaultBufferTimeoutMs = std::chrono::milliseconds{50};
- inline constexpr size_t defaultReceiveBufferSize = 128; // receiveBuffer size used for single message processing
- inline constexpr size_t defaultMessageBufferSize =
- defaultReceiveBufferSize * 2; // MessageBuffer size for passing data between tasks
-
- struct AwaitingResponseFlag
- {
- private:
- cpp_freertos::MutexStandard mutex;
- bool isWaiting = false;
-
- public:
- void set()
- {
- cpp_freertos::LockGuard lock{mutex};
- isWaiting = true;
- }
-
- void clear()
- {
- cpp_freertos::LockGuard lock{mutex};
- isWaiting = false;
- }
-
- bool state()
- {
- cpp_freertos::LockGuard lock{mutex};
- return isWaiting;
- }
- };
+ constexpr auto delimiter = "\r\n"; /// use std::strlen()
class Channel : public BaseChannel
{
@@ 56,10 25,8 @@ namespace at
const std::array<char, 3> validTerm = {cmdSeparator, ',', '='};
[[nodiscard]] auto formatCommand(const std::string &cmd) const -> std::string;
- MessageBufferHandle_t responseBuffer = nullptr;
- std::unique_ptr<uint8_t> receiveBuffer;
- AwaitingResponseFlag awaitingResponseFlag;
cpp_freertos::MutexStandard mutex;
+ TaskHandle_t blockedTaskHandle = nullptr;
public:
static const std::string OK;
@@ 74,19 41,17 @@ namespace at
// const std::string Channel::RING = "RING";
// const std::string Channel::NO_DIALTONE = "NO DIALTONE";
- explicit Channel(uint8_t *receiveBuffer)
- : receiveBuffer{receiveBuffer} {
-
- };
-
/// waits till ok or timeout
virtual auto cmd(const std::string &cmd,
std::chrono::milliseconds timeout = at::default_timeout,
size_t rxCount = 0) -> Result final;
virtual auto cmd(const at::AT &at) -> Result final;
virtual auto cmd(const at::Cmd &at) -> Result final;
- virtual void cmdLog(std::string cmd, const Result &result, std::chrono::milliseconds timeout) final;
-
- Result checkResult(bsp::cellular::CellularResultCode cellularResult);
+ virtual void cmd_log(std::string cmd, const Result &result, uint32_t timeout) final;
+ virtual auto ProcessNewData(sys::Service *service) -> int
+ {
+ return 0;
+ }
};
-} // namespace at
+
+}; // namespace at
M module-cellular/Modem/ATParser.cpp => module-cellular/Modem/ATParser.cpp +33 -35
@@ 10,14 10,15 @@
#include <utility>
#include <vector>
-ATParser::ATParser(bsp::Cellular *cellular) : Channel{new uint8_t[at::defaultReceiveBufferSize]}, cellular(cellular)
+ATParser::ATParser(bsp::Cellular *cellular) : cellular(cellular)
{
- responseBuffer = xMessageBufferCreate(at::defaultMessageBufferSize);
+ isInitialized = true;
}
/// plz see 12.7 summary of urc in documentation
std::vector<ATParser::Urc> ATParser::ParseURC()
{
+
std::vector<ATParser::Urc> resp;
size_t maxPos = 0, pos = 0;
@@ 29,7 30,7 @@ std::vector<ATParser::Urc> ATParser::ParseURC()
};
for (const auto &el : vals) {
- pos = urcBuffer.find(el.first);
+ pos = responseBuffer.find(el.first);
if (pos != std::string::npos) {
resp.push_back(el.second);
maxPos = std::max(pos + el.first.length(), maxPos);
@@ 37,50 38,50 @@ std::vector<ATParser::Urc> ATParser::ParseURC()
}
}
- if (urcBuffer.find("+QIND: \"FOTA\"") != std::string::npos) {
- LOG_DEBUG("%s", urcBuffer.c_str());
+ if (responseBuffer.find("+QIND: \"FOTA\"") != std::string::npos) {
+ LOG_DEBUG("%s", responseBuffer.c_str());
resp.push_back(ATParser::Urc::Fota);
return resp;
}
// manage string buffer
if (maxPos == 0) {}
- else if (urcBuffer.size() >= maxPos) {
- urcBuffer.erase();
+ else if (responseBuffer.size() >= maxPos) {
+ responseBuffer.erase();
}
else {
- urcBuffer = urcBuffer.substr(maxPos);
+ responseBuffer = responseBuffer.substr(maxPos);
}
return resp;
}
-at::Result ATParser::ProcessNewData(sys::Service *service, bsp::cellular::CellularResult *cellularResult)
+int ATParser::ProcessNewData(sys::Service *service)
{
- at::Result result;
+ char rawBuffer[256] = {0};
+
+ LOG_DEBUG("Receiving data from ProcessNewData");
+ auto length = cellular->Read(rawBuffer, sizeof(rawBuffer));
{
cpp_freertos::LockGuard lock(mutex);
- urcBuffer.append(cellularResult->getDataAsString());
+ responseBuffer.append(reinterpret_cast<char *>(rawBuffer), length);
+ LOG_DEBUG("Appending %d bytes to responseBuffer[%u]: %s",
+ static_cast<int>(length),
+ static_cast<unsigned int>(responseBuffer.size()),
+ utils::removeNewLines(responseBuffer).c_str());
}
auto ret = ParseURC();
-
- if (awaitingResponseFlag.state()) {
- if (!xMessageBufferSend(responseBuffer,
- (void *)cellularResult->getSerialized().get(),
- cellularResult->getSerializedSize(),
- pdMS_TO_TICKS(at::defaultBufferTimeoutMs.count()))) {
- LOG_DEBUG("[AT] Message buffer full!");
- result.code = at::Result::Code::FULL_MSG_BUFFER;
- }
+ if (blockedTaskHandle) {
+ xTaskNotifyGive(blockedTaskHandle);
}
- else if (!ret.empty()) {
+ else if (ret.size()) {
if (ret.size() == 1 && ret[0] == ATParser::Urc::Fota) {
- std::string fotaData(urcBuffer);
+ std::string fotaData(responseBuffer);
LOG_DEBUG("parsing FOTA:\"%s\"", fotaData.c_str());
FotaService::API::sendRawProgress(service, fotaData);
- urcBuffer.erase();
+ responseBuffer.erase();
}
else {
urcs.insert(std::end(urcs), std::begin(ret), std::end(ret));
@@ 92,36 93,33 @@ at::Result ATParser::ProcessNewData(sys::Service *service, bsp::cellular::Cellul
cpp_freertos::LockGuard lock(mutex);
auto msg = std::make_shared<CellularPowerUpProcedureCompleteNotification>();
service->bus.sendMulticast(msg, sys::BusChannel::ServiceCellularNotifications);
- urcBuffer.erase();
+ LOG_DEBUG("[!!!] Fucking away data");
+ responseBuffer.erase();
urcs.clear();
}
}
- else {
- result.code = at::Result::Code::DATA_NOT_USED;
- }
-
- return result;
+ return 1;
}
void ATParser::cmd_init()
{
cpp_freertos::LockGuard lock(mutex);
- urcBuffer.erase();
+ responseBuffer.erase();
}
void ATParser::cmd_send(std::string cmd)
{
- cellular->write(const_cast<char *>(cmd.c_str()), cmd.size());
+ cellular->Write(const_cast<char *>(cmd.c_str()), cmd.size());
}
-size_t ATParser::cmd_receive(std::uint8_t *buffer, std::chrono::milliseconds timeout = std::chrono::milliseconds{0})
+std::string ATParser::cmd_receive()
{
- return xMessageBufferReceive(responseBuffer, buffer, 256, pdMS_TO_TICKS(timeout.count()));
+ cpp_freertos::LockGuard lock(mutex);
+ return responseBuffer;
}
void ATParser::cmd_post()
{
cpp_freertos::LockGuard lock(mutex);
- urcBuffer.erase();
- xMessageBufferReset(responseBuffer);
+ responseBuffer.erase(); // TODO:M.P is it okay to flush buffer here ?
}
M module-cellular/Modem/ATParser.hpp => module-cellular/Modem/ATParser.hpp +6 -9
@@ 11,9 11,6 @@
#include <optional>
#include <task.h>
#include <vector>
-#include <message_buffer.h>
-
-#include <bsp/cellular/CellularResult.hpp>
namespace bsp
{
@@ 37,19 34,19 @@ class ATParser : public at::Channel
ATParser(bsp::Cellular *cellular);
virtual ~ATParser() = default;
- at::Result ProcessNewData(sys::Service *service, bsp::cellular::CellularResult *cellularResult);
+ int ProcessNewData(sys::Service *service);
virtual void cmd_init() override final;
virtual void cmd_send(std::string cmd) override final;
- virtual size_t cmd_receive(std::uint8_t *buffer, std::chrono::milliseconds timeout) override final;
+ virtual std::string cmd_receive() override final;
virtual void cmd_post() override final;
private:
std::vector<Urc> ParseURC();
- bsp::Cellular *cellular = nullptr;
- MessageBufferHandle_t responseBuffer = nullptr;
- std::string urcBuffer = {};
- std::vector<ATParser::Urc> urcs = {};
+ bsp::Cellular *cellular = nullptr;
+ std::string responseBuffer;
+ std::vector<ATParser::Urc> urcs;
+ bool isInitialized = false;
};
#endif // PUREPHONE_ATPARSER_HPP
M module-cellular/Modem/BaseChannel.hpp => module-cellular/Modem/BaseChannel.hpp +6 -6
@@ 7,7 7,7 @@
#include <vector>
#include <at/Commands.hpp>
#include <at/Result.hpp>
-#include <bsp/cellular/CellularResult.hpp>
+#include <at/Constants.hpp>
namespace at
{
@@ 29,12 29,12 @@ namespace at
/// @defgroup Channel Platform independent methods
/// {
- virtual void cmdLog(std::string cmd, const Result &result, std::chrono::milliseconds timeout)
+ virtual void cmd_log(std::string cmd, const Result &result, uint32_t timeout)
{}
- virtual void cmd_init() = 0;
- virtual void cmd_send(std::string cmd) = 0;
- virtual size_t cmd_receive(std::uint8_t *buffer, std::chrono::milliseconds timeoutMs) = 0;
- virtual void cmd_post() = 0;
+ virtual void cmd_init() = 0;
+ virtual void cmd_send(std::string cmd) = 0;
+ virtual std::string cmd_receive() = 0;
+ virtual void cmd_post() = 0;
/// }
};
} // namespace at
D module-cellular/Modem/README.md => module-cellular/Modem/README.md +0 -98
@@ 1,98 0,0 @@
-
-
-# Cellular Multiplexer
-
-## Table of contents
-1. [History](#history)
-2. [Modes](#modes)
-3. [Single command data flow](#singlecmd)
-5. [Cellular result structures](#result)
-6. [Error codes](#errors)
-
-## History <a name="history"></a>
-| Authors | Change description | Status | Modification date |
-| ----------------- | ------------------------- | ------ | ----------------- |
-| Maciej Janicki | Initial version | Draft | 2021.03.24 |
-
-## Modes <a name="modes"></a>
-Cellular operates in three modes:
- - AT,
- - CMUX setup,
- - CMUX
-
-The AT mode is used for communication setup and modem configuration.
-
-
-
-The CMUX setup is an intermidiate state starting a CMUX communication:
- - It configures CMUX mode's transmission parameters.
- - It creates channels for a frame multiplexing (Commands, Notifications, Data).
-Data flow for both CMUX and CMUX setup in current implementation is identical.
-
-
-
-## Single command data flow <a name="singlecmd"></a>
-
-
-A single command sequence starts with a call from the Service and can end in one of three ways:
- - Command response timeout (timeout depends on command issued).
- - Service receives an error in result and handles it accordingly.
- - Command response is successfully parsed before timeout and passed to service layer.
-
-## Result structs <a name="result"></a>
-
-Currently, there are two types of structs used to pass data between contexts.
-
-DMA result struct is used to directly store data from DMA engine as well as pass these through
-MessageBuffer to Worker. This struct has static data buffer maximum size.
-
-
-
-Cellular Result is used to pass complete frames serialized in vector together with
-result code. This struct has variable size.
-
-
-
-## Error codes <a name="errors"></a>
-
-
-
-
-Currently there are different errors/results codes for different layers.
-
- 1. CellularResultCode
- This code is used to pass information from bsp layer up to channel.
- It can be either used to handle flow control messages from DMA or
- to pass failures to upper layer (transmission/receiving not starter,
- cmux frame error).
-
- ```
- Uninitialized,
- ReceivedAndIdle,
- ReceivedAndFull,
- ReceivedAfterFull,
- ReceivedNoData,
- ReceivingNotStarted,
- TransmittingNotStarted,
- CMUXFrameError,
- ```
-
- 2. AtResult
- This result code is passed to service layer.
-
- ```
- OK, /// at OK
- ERROR, /// at ERROR For compatibility also for CME_ERROR and CMS_ERROR (details in errorCode)
- CME_ERROR, /// In case CME error see errorCode
- CMS_ERROR, /// In case CMS error see errorCode
- TIMEOUT, /// at Timeout
- TOKENS, /// at numbers of tokens needed met
- NONE, /// no code
- UNDEFINED, /// undefined result - usage of Undefined result, define and pin result to use it
- PARSING_ERROR, /// parser error
- FULL_MSG_BUFFER, /// at not enough space left in message buffer for new message
- TRANSMISSION_NOT_STARTED, /// at dma not starting transmission
- RECEIVING_NOT_STARTED, /// at dma not starting requested receiving
- DATA_NOT_USED, /// at received data not being used
- CMUX_FRAME_ERROR, /// at cmux deserialize error
- ```
M module-cellular/Modem/TS0710/DLC_channel.cpp => module-cellular/Modem/TS0710/DLC_channel.cpp +126 -103
@@ 1,42 1,50 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#include "DLC_channel.h"
+/**
+ * Project Untitled
+ */
+#include "DLC_channel.h"
+#include "TS0710.h"
#include "TS0710_DATA.h"
+#include "TS0710_DLC_ESTABL.h"
#include "TS0710_DLC_RELEASE.h"
#include "TS0710_Frame.h"
-
-#include <module-utils/log/log.hpp>
-#include <ticks.hpp>
+#include "log/log.hpp"
+#include "ticks.hpp"
#include <Utils.hpp>
+#include <cstdlib>
-DLC_channel::DLC_channel(DLCI_t DLCI, const std::string &name, bsp::Cellular *cellular, const Callback_t &callback)
- : Channel{new uint8_t[at::defaultReceiveBufferSize]}, pv_name{name}, pv_DLCI{DLCI}, pv_cellular{cellular}
+/**
+ * DLC_channel implementation
+ */
+
+DLC_channel::DLC_channel(DLCI_t DLCI, std::string name, bsp::Cellular *cellular, Callback_t callback)
{
LOG_DEBUG("Creating DLCI %i channel \"%s\"", DLCI, name.c_str());
+ pv_name = name;
+ pv_DLCI = DLCI;
+ pv_cellular = cellular;
- if (callback != nullptr) {
+ if (callback != nullptr)
pv_callback = callback;
- }
-
- chanParams.TypeOfFrame = TypeOfFrame_e::SABM;
- chanParams.ConvergenceLayer = 1;
- chanParams.Priority = 1;
- chanParams.AckTime = 100; // 100ms default
- chanParams.MaxFrameSize = 128;
- chanParams.MaxNumOfRetransmissions = 3; // default 3
- chanParams.ErrRecovWindowSize = 2; // default 2
- responseBuffer = xMessageBufferCreate(at::defaultMessageBufferSize);
-}
-
-bool DLC_channel::init()
-{
- active = establish();
- LOG_INFO("create channel %s: %s", pv_name.c_str(), active ? "TRUE" : "FALSE");
-
- return active;
+ DLC_ESTABL_SystemParameters_t system_parameters;
+ system_parameters.TypeOfFrame = TypeOfFrame_e::SABM;
+ system_parameters.ConvergenceLayer = 1;
+ system_parameters.Priority = 1;
+ system_parameters.AckTime = 100; // 100ms default
+ system_parameters.MaxFrameSize = 128;
+ system_parameters.MaxNumOfRetransmissions = 3; // default 3
+ system_parameters.ErrRecovWindowSize = 2; // default 2
+
+ TS0710_DLC_ESTABL establ = TS0710_DLC_ESTABL(DLCI, system_parameters, cellular);
+ pv_chanParams = establ.getParams();
+
+ // wait for return & set active
+ active = establ.getResponse();
+ LOG_DEBUG("Create channel %s: %s", pv_name.c_str(), active ? "TRUE" : "FALSE");
}
DLC_channel::~DLC_channel()
@@ 46,46 54,41 @@ DLC_channel::~DLC_channel()
void DLC_channel::SendData(std::vector<uint8_t> &data)
{
- TS0710_DATA _data = TS0710_DATA(pv_DLCI, chanParams, data, pv_cellular);
+ TS0710_DATA _data = TS0710_DATA(pv_DLCI, pv_chanParams, data, pv_cellular);
}
-bool DLC_channel::establish()
-{
- LOG_DEBUG("Sending %s frame to DLCI %i", TypeOfFrame_text[chanParams.TypeOfFrame].c_str(), pv_DLCI);
-
- TS0710_Frame frame_c(TS0710_Frame::frame_t(static_cast<uint8_t>(pv_DLCI << 2) | (1 << 1),
- static_cast<uint8_t>(chanParams.TypeOfFrame)));
-
- awaitingResponseFlag.set();
-
- bool result = false;
-
- for (int retries = 0; retries < chanParams.MaxNumOfRetransmissions; ++retries) {
- pv_cellular->write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
-
- auto startTime = std::chrono::steady_clock::now();
- auto endTime = startTime + std::chrono::milliseconds{300};
-
- // Wait for response:
- while (true) {
- if (std::chrono::steady_clock::now() > endTime) {
- break;
- }
-
- if (size_t bytesRead = cmd_receive(receiveBuffer.get(), std::chrono::milliseconds{0}); bytesRead > 0) {
- auto cellularResult = bsp::cellular::CellularResult{receiveBuffer.get(), bytesRead};
- if (evaluateEstablishResponse(cellularResult)) {
- result = true;
- break;
- }
- }
+#if 0 // left here for reference
+ssize_t DLC_channel::ReceiveData(std::vector<uint8_t> &data, uint32_t timeout) {
+ ssize_t ret = -1;
+ static uint8_t *buf = nullptr;
+ buf = reinterpret_cast<uint8_t*>(malloc(pv_chanParams.MaxFrameSize));
+ bool complete = false;
+
+ while((!complete) && (timeout--)) { //TODO: add timeout control
+ ret = pv_cellular->Read(reinterpret_cast<void *>(buf), pv_chanParams.MaxFrameSize);
+ if (ret > 0) {
+ LOG_DEBUG("Received %i bytes", ret);
+ for (int i = 0; i < ret; i++)
+ data.push_back(buf[i]);
+ complete = TS0710_Frame::isComplete(data);
}
+ sleep_ms(1);
+ }
+ if (!complete)
+ LOG_ERROR("Incomplete frame received");
+ if (timeout == 0)
+ LOG_ERROR("Timeout occured");
+
+ free(buf);
+
+ if (!TS0710_Frame::isMyChannel(data, pv_DLCI)) {
+ data.clear();
+ ret = -1;
}
- awaitingResponseFlag.clear();
-
- return result;
+ return ret;
}
+#endif
void DLC_channel::cmd_init()
{}
@@ 96,48 99,78 @@ void DLC_channel::cmd_send(std::string cmd)
SendData(data);
}
-size_t DLC_channel::cmd_receive(uint8_t *result, std::chrono::milliseconds timeout)
+std::string DLC_channel::cmd_receive()
{
- return xMessageBufferReceive(responseBuffer, result, 2 * chanParams.MaxFrameSize, pdMS_TO_TICKS(timeout.count()));
+ cpp_freertos::LockGuard lock(mutex);
+ TS0710_Frame::frame_t frame;
+ std::vector<uint8_t> v(responseBuffer.begin(), responseBuffer.end());
+
+ responseBuffer.clear();
+ std::vector<std::vector<uint8_t>> mFrames;
+ std::vector<uint8_t> rawBuffer;
+
+ // get frames from buffer
+ for (size_t i = 0; i < v.size(); i++) {
+ rawBuffer.push_back(v[i]);
+ if (/*TS0710_Frame::isComplete(rawBuffer)*/ (rawBuffer.size() > 1) && (rawBuffer[0] == 0xF9) &&
+ (rawBuffer[rawBuffer.size() - 1] == 0xF9)) {
+ // LOGrawBufferEBUG("Pushing back FRAME");
+ mFrames.push_back(rawBuffer);
+ rawBuffer.clear();
+ }
+ }
+ // deseriaise data from received frames
+ std::string deserialisedData;
+ for (std::vector<uint8_t> vv : mFrames) {
+ frame.deserialize(vv);
+ std::string str(frame.data.begin(), frame.data.end());
+ // append deserialised buffer
+ deserialisedData += str;
+ }
+ mFrames.clear();
+ return deserialisedData;
}
void DLC_channel::cmd_post()
{}
-std::vector<std::string> DLC_channel::SendCommandPrompt(const char *cmd,
- size_t rxCount,
- std::chrono::milliseconds timeout)
+std::vector<std::string> DLC_channel::SendCommandPrompt(const char *cmd, size_t rxCount, uint32_t timeout)
{
std::vector<std::string> tokens;
- awaitingResponseFlag.set();
-
+ blockedTaskHandle = xTaskGetCurrentTaskHandle();
at::Result result;
cmd_init();
std::string cmdFixed = formatCommand(cmd);
cmd_send(cmdFixed);
- auto startTime = std::chrono::steady_clock::now();
- auto endTime = startTime + timeout;
+ uint32_t currentTime = cpp_freertos::Ticks::GetTicks();
+ uint32_t timeoutNeeded = timeout == UINT32_MAX ? UINT32_MAX : currentTime + timeout;
+ uint32_t timeElapsed = currentTime;
+
+ // wait_for_data:
+ while (1) {
- // Wait for response:
- while (true) {
- if (std::chrono::steady_clock::now() > endTime) {
+ if (timeElapsed >= timeoutNeeded) {
result.code = at::Result::Code::TIMEOUT;
break;
}
- if (size_t bytesRead = cmd_receive(receiveBuffer.get(), std::chrono::milliseconds{0}); bytesRead > 0) {
- auto cellularResult = bsp::cellular::CellularResult{receiveBuffer.get(), bytesRead};
- auto str = cellularResult.getDataAsString();
+ auto ret = ulTaskNotifyTake(pdTRUE, timeoutNeeded - timeElapsed);
+ timeElapsed = cpp_freertos::Ticks::GetTicks();
+ if (ret) {
- if (result = checkResult(cellularResult.getResultCode()); result.code != at::Result::Code::OK) {
- break;
- }
+ std::vector<std::string> strings;
+ cpp_freertos::LockGuard lock(mutex);
+ TS0710_Frame::frame_t frame;
+ std::vector<uint8_t> v(responseBuffer.begin(), responseBuffer.end());
+ responseBuffer.clear();
+ frame.deserialize(v);
+ std::string str(frame.data.begin(), frame.data.end());
// tokenize responseBuffer
- auto pos = str.find('>');
+ auto pos = str.find(">");
if (pos != std::string::npos) {
tokens.push_back(str.substr(pos, strlen(">")));
break;
@@ 148,41 181,31 @@ std::vector<std::string> DLC_channel::SendCommandPrompt(const char *cmd,
}
}
- cmdLog(cmdFixed, result, timeout);
+ cmd_log(cmdFixed, result, timeout);
cmd_post();
-
- awaitingResponseFlag.clear();
+ blockedTaskHandle = nullptr;
return tokens;
}
-at::Result DLC_channel::ParseInputData(bsp::cellular::CellularResult *cellularResult)
+int DLC_channel::ParseInputData(std::vector<uint8_t> &data)
{
- at::Result result;
- if (awaitingResponseFlag.state()) {
- if (!xMessageBufferSend(responseBuffer,
- (void *)cellularResult->getSerialized().get(),
- cellularResult->getSerializedSize(),
- pdMS_TO_TICKS(at::defaultBufferTimeoutMs.count()))) {
- LOG_DEBUG("[DLC] Message buffer full!");
- result.code = at::Result::Code::FULL_MSG_BUFFER;
- }
+ cpp_freertos::LockGuard lock(mutex);
+
+ if (blockedTaskHandle) {
+ responseBuffer.append(reinterpret_cast<char *>(data.data()), data.size());
+ xTaskNotifyGive(blockedTaskHandle);
}
else if (pv_callback != nullptr) {
- std::string receivedData = cellularResult->getDataAsString();
+
+ TS0710_Frame frame(data);
+ auto deserialised = frame.getFrame().data;
+
+ std::string receivedData = std::string(deserialised.begin(), deserialised.end());
+
pv_callback(receivedData);
}
- else {
- result.code = at::Result::Code::DATA_NOT_USED;
- }
- return result;
-}
-
-bool DLC_channel::evaluateEstablishResponse(bsp::cellular::CellularResult &response) const
-{
- auto frame = TS0710_Frame{response.getData()};
- return (frame.getFrameDLCI() == pv_DLCI &&
- (frame.getFrame().Control == (static_cast<uint8_t>(TypeOfFrame_e::UA) & ~(1 << 4))));
+ return 1;
}
M module-cellular/Modem/TS0710/DLC_channel.h => module-cellular/Modem/TS0710/DLC_channel.h +16 -19
@@ 12,12 12,10 @@
#include <vector>
#include <functional>
-#include "module-cellular/Modem/ATCommon.hpp"
+#include "../ATCommon.hpp"
#include "TS0710_types.h"
-#include <bsp/cellular/CellularResult.hpp>
#include <FreeRTOS.h>
#include <task.h>
-#include <message_buffer.h>
class DLC_channel : public at::Channel
{
@@ 28,20 26,23 @@ class DLC_channel : public at::Channel
std::string pv_name;
DLCI_t pv_DLCI;
bool active = false;
- DLC_ESTABL_SystemParameters_t chanParams{};
+ DLC_ESTABL_SystemParameters_t pv_chanParams;
Callback_t pv_callback;
- bsp::Cellular *pv_cellular{};
+
+ std::string responseBuffer;
+ bsp::Cellular *pv_cellular;
public:
- DLC_channel(DLCI_t DLCI, const std::string &name, bsp::Cellular *cellular, const Callback_t &callback = nullptr);
- DLC_channel() : Channel{nullptr}, pv_name{"none"}, pv_DLCI{-1}
- {}
+ // TS0710_DLC_ESTABL ctrlChanEstabl = TS0710_DLC_ESTABL(0); //use default values to create control channel DLCI0
+ DLC_channel(DLCI_t DLCI, std::string name, bsp::Cellular *cellular, Callback_t callback = nullptr);
+ DLC_channel()
+ {
+ pv_DLCI = -1;
+ pv_name = "none";
+ } // default constructor creates empty channel
virtual ~DLC_channel();
- bool init();
- bool establish();
-
void SendData(std::vector<uint8_t> &data);
DLCI_t getDLCI()
@@ 57,6 58,7 @@ class DLC_channel : public at::Channel
return active;
}
+ // ssize_t ReceiveData(std::vector<uint8_t> &data, uint32_t timeout);
void setCallback(Callback_t callback)
{
LOG_DEBUG("[%s] Setting up callback for channel", pv_name.c_str());
@@ 65,17 67,12 @@ class DLC_channel : public at::Channel
virtual void cmd_init() override final;
virtual void cmd_send(std::string cmd) override final;
- virtual size_t cmd_receive(std::uint8_t *result,
- std::chrono::milliseconds timeout = std::chrono::milliseconds{300}) override final;
+ virtual std::string cmd_receive() override final;
virtual void cmd_post() override final;
- std::vector<std::string> SendCommandPrompt(const char *cmd,
- size_t rxCount,
- std::chrono::milliseconds timeout = std::chrono::milliseconds{300});
-
- at::Result ParseInputData(bsp::cellular::CellularResult *cellularResult);
+ std::vector<std::string> SendCommandPrompt(const char *cmd, size_t rxCount, uint32_t timeout = 300);
- bool evaluateEstablishResponse(bsp::cellular::CellularResult &response) const;
+ int ParseInputData(std::vector<uint8_t> &data);
void callback(std::string &data)
{
M module-cellular/Modem/TS0710/TS0710.cpp => module-cellular/Modem/TS0710/TS0710.cpp +147 -180
@@ 5,7 5,6 @@
#include <at/ATFactory.hpp>
#include <at/Cmd.hpp>
#include "bsp/cellular/bsp_cellular.hpp"
-#include "bsp/cellular/CellularResult.hpp"
#include "projdefs.h"
#include <service-cellular/ServiceCellular.hpp>
#include <service-cellular/SignalStrength.hpp>
@@ 45,11 44,39 @@ std::map<PortSpeed_e, int> ATPortSpeeds_text = {{PortSpeed_e::PS9600, 9
#define SERIAL_PORT "/dev/null"
#endif
-static constexpr std::uint16_t threadSizeWords = 2048;
+#define USE_DAEFAULT_BAUDRATE 1
+
+static const std::uint16_t threadSizeWords = 2048;
TS0710::TS0710(PortSpeed_e portSpeed, sys::Service *parent)
{
- Init(portSpeed, parent);
+ LOG_INFO("Serial port: '%s'", SERIAL_PORT);
+ pv_portSpeed = portSpeed;
+ pv_cellular = bsp::Cellular::Create(SERIAL_PORT, 115200).value_or(nullptr);
+ parser = new ATParser(pv_cellular.get());
+ pv_parent = parent;
+
+ // start connection
+ startParams.PortSpeed = pv_portSpeed;
+ startParams.MaxFrameSize = 127; // maximum for Basic mode
+ startParams.AckTimer = 10; // 100ms default
+ startParams.MaxNumOfRetransmissions = 3; // default
+ startParams.MaxCtrlRespTime = 30; // 300ms default
+ startParams.WakeUpRespTime = 10; // 10s default
+ startParams.ErrRecovWindowSize = 2; // 2 default
+
+ if (auto flushed = FlushReceiveData(); flushed > 0) {
+ LOG_INFO("Discarded initial %" PRIu32 " bytes sent by modem",
+ static_cast<uint32_t>(flushed)); // not baud-accurate. Might be 460800÷115200 times more
+ }
+
+ constexpr auto workerName = "TS0710SerialRxWorker";
+ BaseType_t task_error =
+ xTaskCreate(workerTaskFunction, workerName, threadSizeWords, this, taskPriority, &taskHandle);
+ if (task_error != pdPASS) {
+ LOG_ERROR("Failed to start %s task", workerName);
+ return;
+ }
}
TS0710::~TS0710()
@@ 63,47 90,9 @@ TS0710::~TS0710()
if (taskHandle) {
vTaskDelete(taskHandle);
}
-
delete parser;
}
-void TS0710::Init(PortSpeed_e portSpeed, sys::Service *parent)
-{
- pv_cellular = bsp::Cellular::create(SERIAL_PORT, 115200).value_or(nullptr);
- parser = new ATParser(pv_cellular.get());
- pv_parent = parent;
-
- SetStartParams(portSpeed);
-
- if (auto flushed = flushReceiveData(); flushed > 0) {
- LOG_INFO("Discarded initial %lu bytes sent by modem",
- static_cast<unsigned long>(flushed)); // not baud-accurate. Might be 460800÷115200 times more
- }
- else {
- LOG_DEBUG("Nothing to discard");
- }
-
- constexpr auto workerName = "TS0710Worker";
-
- BaseType_t task_error =
- xTaskCreate(workerTaskFunction, workerName, threadSizeWords, this, taskPriority, &taskHandle);
- if (task_error != pdPASS) {
- LOG_ERROR("Failed to start %s task", workerName);
- return;
- }
-}
-
-void TS0710::SetStartParams(PortSpeed_e portSpeed)
-{
- startParams.PortSpeed = portSpeed;
- startParams.MaxFrameSize = 127; // maximum for Basic mode
- startParams.AckTimer = 10; // 100ms default
- startParams.MaxNumOfRetransmissions = 3; // default
- startParams.MaxCtrlRespTime = 30; // 300ms default
- startParams.WakeUpRespTime = 10; // 10s default
- startParams.ErrRecovWindowSize = 2; // 2 default
-}
-
TS0710_Frame::frame_t createCMUXExitFrame()
{
TS0710_Frame::frame_t frame;
@@ 156,7 145,7 @@ void CloseCmux(std::unique_ptr<bsp::Cellular> &pv_cellular)
{
LOG_INFO("Closing mux mode");
TS0710_Frame::frame_t frame = createCMUXExitFrame();
- pv_cellular->write((void *)frame.serialize().data(), frame.serialize().size());
+ pv_cellular->Write((void *)frame.serialize().data(), frame.serialize().size());
vTaskDelay(1000); // GSM module needs some time to close multiplexer
}
@@ 174,7 163,7 @@ TS0710::ConfState TS0710::BaudDetectOnce()
while (!result) {
switch (step) {
case BaudTestStep::baud460800_NoCmux:
- pv_cellular->setSpeed(ATPortSpeeds_text[PortSpeed_e::PS460800]);
+ pv_cellular->SetSpeed(ATPortSpeeds_text[PortSpeed_e::PS460800]);
lastStep = step;
result = BaudDetectTestAT(parser, step, BaudTestStep::baud460800_Cmux);
break;
@@ 184,7 173,7 @@ TS0710::ConfState TS0710::BaudDetectOnce()
result = BaudDetectTestAT(parser, step, BaudTestStep::baud115200_NoCmux);
break;
case BaudTestStep::baud115200_NoCmux:
- pv_cellular->setSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]);
+ pv_cellular->SetSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]);
lastStep = step;
result = BaudDetectTestAT(parser, step, BaudTestStep::baud115200_Cmux);
break;
@@ 194,8 183,8 @@ TS0710::ConfState TS0710::BaudDetectOnce()
result = BaudDetectTestAT(parser, step, BaudTestStep::baud_NotFound);
break;
case BaudTestStep::baud_NotFound:
- pv_cellular->setSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]); // set port speed to default 115200
- LOG_ERROR("No Baud found for modem.");
+ pv_cellular->SetSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]); // set port speed to default 115200
+ LOG_DEBUG("No Baud found for modem.");
return ConfState::Failure;
break;
}
@@ 217,11 206,12 @@ TS0710::ConfState TS0710::BaudDetectProcedure(uint16_t timeout_s)
return ConfState::Success;
}
}
- pv_cellular->setSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]); // set port speed to default 115200
+ pv_cellular->SetSpeed(ATPortSpeeds_text[PortSpeed_e::PS115200]); // set port speed to default 115200
LOG_ERROR("No Baud found.");
return ConfState::Failure;
}
+// TODO:M.P Fetch configuration from JSON/XML file
TS0710::ConfState TS0710::ConfProcedure()
{
LOG_DEBUG("Configuring modem...");
@@ 302,14 292,14 @@ TS0710::ConfState TS0710::AudioConfProcedure()
if (!parser->cmd(at::AT::QMIC)) {
return ConfState::Failure;
}
- return setupEchoCanceller(EchoCancellerStrength::Tuned);
+ return SetupEchoCanceller(EchoCancellerStrength::Tuned);
}
else {
if (!parser->cmd(at::AT::QDAI_INIT)) {
return ConfState::Failure;
}
else {
- pv_cellular->restart();
+ pv_cellular->Restart();
LOG_DEBUG("GSM module first run, performing reset...");
return ConfState::ModemNeedsReset;
}
@@ 369,13 359,13 @@ TS0710::ConfState TS0710::StartMultiplexer()
return ConfState::Failure;
}
- mode = Mode::CMUX_SETUP;
-
- TS0710_START TS0710_Start{TS0710_START::Mode_e::Basic, startParams, pv_cellular.get()};
+ mode = Mode::CMUX_SETUP;
+ TS0710_START *pv_TS0710_Start = new TS0710_START(TS0710_START::Mode_e::Basic, startParams, pv_cellular.get());
// wait for confirmation
- if (TS0710_Start.ConnectionStatus()) {
- channels.push_back(TS0710_Start.getCtrlChannel()); // store control channel
+ if (pv_TS0710_Start->ConnectionStatus()) {
+ channels.push_back(pv_TS0710_Start->getCtrlChannel()); // store control channel
}
+ delete pv_TS0710_Start;
controlCallback = [this](std::string &data) {
auto frameData = data;
@@ 395,10 385,10 @@ TS0710::ConfState TS0710::StartMultiplexer()
LOG_PRINTF("RTR ");
if (frameData[3] & 0x04) {
LOG_PRINTF("RTC ");
- this->getCellular()->setSendingAllowed(true);
+ this->getCellular()->SetSendingAllowed(true);
}
else
- this->getCellular()->setSendingAllowed(false);
+ this->getCellular()->SetSendingAllowed(false);
if (frameData[3] & 0x02)
LOG_PRINTF("FC ");
@@ 407,23 397,24 @@ TS0710::ConfState TS0710::StartMultiplexer()
}
};
+ // channels[0]->setCallback(controlCallback);
+
+ // TODO: Open remaining channels
OpenChannel(Channel::Commands);
OpenChannel(Channel::Notifications);
OpenChannel(Channel::Data);
- LOG_DEBUG("[TS0710] Channels open");
- mode = Mode::CMUX;
- DLC_channel *channel = get(Channel::Commands);
- if (channel != nullptr) {
+ mode = Mode::CMUX;
+ DLC_channel *c = get(Channel::Commands);
+ if (c != nullptr) {
// Route URCs to second (Notifications) MUX channel
- LOG_DEBUG("[TS0710] Setting URC Channel");
- channel->cmd(at::AT::SET_URC_CHANNEL);
+ c->cmd(at::AT::SET_URC_CHANNEL);
LOG_DEBUG("Sending test ATI");
- auto res = channel->cmd(at::AT::SW_INFO);
+ auto res = c->cmd(at::AT::SW_INFO);
if (!res) {
LOG_ERROR("Sending test ATI command failed");
}
- res = channel->cmd(at::AT::CSQ);
+ res = c->cmd(at::AT::CSQ);
if (res) {
auto beg = res.response[0].find(" ");
auto end = res.response[0].find(",", 1);
@@ 452,147 443,123 @@ TS0710::ConfState TS0710::StartMultiplexer()
return ConfState::Failure;
}
- LOG_DEBUG("[TS0710] Mux started");
return ConfState::Success;
}
-void TS0710::sendFrameToChannel(bsp::cellular::CellularResult &resultStruct)
+void workerTaskFunction(void *ptr)
{
- auto frame = TS0710_Frame{resultStruct.getData()};
+ TS0710 *inst = reinterpret_cast<TS0710 *>(ptr);
+
+ while (1) {
+ auto ret = inst->pv_cellular->Wait(UINT32_MAX);
+ if (ret == 0) {
+ continue;
+ }
- for (auto chan : getChannels()) {
- if (frame.getFrameDLCI() == chan->getDLCI()) {
- if (frame.getData().empty()) {
- // Control frame contains no data
- resultStruct.setData(frame.getSerData());
+ // AT mode is used only during initialization phase
+ if (inst->mode == TS0710::Mode::AT) {
+ // inst->atParser->ProcessNewData();
+ // TODO: add AT command processing
+ LOG_DEBUG("[Worker] Processing AT response");
+ inst->parser->ProcessNewData(inst->pv_parent);
+ }
+ // CMUX mode is default operation mode
+ else if (inst->mode == TS0710::Mode::CMUX) {
+ // LOG_DEBUG("[Worker] Processing CMUX response");
+ std::vector<uint8_t> data;
+ inst->ReceiveData(data, static_cast<uint32_t>(inst->startParams.MaxCtrlRespTime));
+ // send data to fifo
+ for (uint8_t c : data) {
+ inst->RXFifo.push(c);
}
- else {
- resultStruct.setData(frame.getData());
+ data.clear();
+ // divide message to different frames as Quectel may send them one after another
+ std::vector<std::vector<uint8_t>> multipleFrames;
+ std::vector<uint8_t> _d;
+ int fifoLen = inst->RXFifo.size();
+ // LOG_DEBUG("[RXFifo] %i elements", fifoLen);
+
+ for (int i = 0; i < fifoLen; i++) {
+ _d.push_back(inst->RXFifo.front());
+ inst->RXFifo.pop();
+ if (/*TS0710_Frame::isComplete(_d)*/ (_d.size() > 1) && (_d[0] == 0xF9) &&
+ (_d[_d.size() - 1] == 0xF9)) {
+ // LOG_DEBUG("Pushing back FRAME");
+ multipleFrames.push_back(_d);
+ _d.clear();
+ }
}
-
- if (frame.getFrameStatus() != TS0710_Frame::OK) {
- resultStruct.setResultCode(bsp::cellular::CellularResultCode::CMUXFrameError);
+ // if some data stored @_d then push it back to queue as incomplete packet
+ if (!_d.empty() && (_d[0] == 0xF9)) {
+ // LOG_DEBUG("Pushing back [%i] incomplete frame", _d.size());
+ for (uint8_t c : _d)
+ inst->RXFifo.push(c);
}
+ _d.clear();
- chan->ParseInputData(&resultStruct);
- return;
- }
- }
-}
-
-void TS0710::parseCellularResultCMUX(bsp::cellular::CellularDMAResultStruct &result)
-{
- static std::vector<uint8_t> currentFrame;
- static bool frameStartDetected = false;
-
- for (auto i = 0U; i < result.dataSize; ++i) {
- uint8_t character = result.data[i];
- if (frameStartDetected || character == TS0710_FLAG) {
-
- currentFrame.push_back(character);
-
- // Check if frame is complete only in case of TS0710_FLAG
- if (frameStartDetected && character == TS0710_FLAG) {
- if (TS0710_Frame::isComplete(currentFrame)) {
- frameStartDetected = false;
- bsp::cellular::CellularResult cellularResult{{result.resultCode, currentFrame}};
- sendFrameToChannel(cellularResult);
- currentFrame.clear();
- continue;
+ // LOG_DEBUG("Received %i frames", multipleFrames.size());
+ for (auto *chan : inst->channels) {
+ for (std::vector<uint8_t> v : multipleFrames) {
+ if (TS0710_Frame::isMyChannel(v, chan->getDLCI()))
+ chan->ParseInputData(v);
}
}
-
- frameStartDetected = true;
+ multipleFrames.clear();
}
}
}
-size_t TS0710::flushReceiveData()
-{
- auto flushed = 0U;
- constexpr auto flushTimeout = std::chrono::milliseconds{20};
- bsp::cellular::CellularDMAResultStruct dummyResult;
- do {
- flushed += pv_cellular->read(&dummyResult, dummyResult.getMaxSize(), flushTimeout);
- } while (dummyResult.resultCode == bsp::cellular::CellularResultCode::ReceivedAndFull);
- return flushed;
-}
-
-void TS0710::processError(bsp::cellular::CellularDMAResultStruct &result)
+size_t TS0710::FlushReceiveData()
{
- bsp::cellular::CellularResult cellularResult{{result.resultCode, {}}};
-
- if (mode == TS0710::Mode::AT) {
- parser->ProcessNewData(pv_parent, &cellularResult);
- }
- else if (mode == TS0710::Mode::CMUX || mode == TS0710::Mode::CMUX_SETUP) {
- sendFrameToChannel(cellularResult);
- }
-}
+ using namespace std::chrono_literals;
-void TS0710::processData(bsp::cellular::CellularDMAResultStruct &result)
-{
- if (mode == TS0710::Mode::AT) {
- bsp::cellular::CellularResult cellularResult{result};
- parser->ProcessNewData(pv_parent, &cellularResult);
- }
- else if (mode == TS0710::Mode::CMUX || mode == TS0710::Mode::CMUX_SETUP) {
- parseCellularResultCMUX(result);
+ auto flushed = 0U;
+ constexpr auto flushInactivityTimeout = 20ms;
+ std::uint8_t dummyRead[50];
+ while (pv_cellular->Wait(flushInactivityTimeout.count())) {
+ flushed += pv_cellular->Read(dummyRead, sizeof(dummyRead));
}
+ return flushed;
}
-[[noreturn]] void workerTaskFunction(void *ptr)
+ssize_t TS0710::ReceiveData(std::vector<uint8_t> &data, uint32_t timeout)
{
- LOG_DEBUG("Worker start");
+ ssize_t ret = -1;
+ std::unique_ptr<uint8_t[]> buf(new uint8_t[startParams.MaxFrameSize]);
+ bool complete = false;
+ uint32_t _timeout = timeout;
- constexpr auto readTimeout = std::chrono::milliseconds{10000};
- TS0710 *inst = static_cast<TS0710 *>(ptr);
- bsp::cellular::CellularDMAResultStruct result{};
-
- while (true) {
- result.resultCode = bsp::cellular::CellularResultCode::ReceivedNoData;
-
- inst->pv_cellular->read(&result, bsp::cellular::CellularDMAResultStruct::getMaxSize(), readTimeout);
-
- switch (result.resultCode) {
- case bsp::cellular::CellularResultCode::ReceivedAndFull:
- LOG_DEBUG("DMA buffer full");
- [[fallthrough]];
- case bsp::cellular::CellularResultCode::ReceivedAfterFull:
- [[fallthrough]];
- case bsp::cellular::CellularResultCode::ReceivedAndIdle:
- inst->processData(result);
- break;
- case bsp::cellular::CellularResultCode::Uninitialized:
- LOG_DEBUG("DMA uninitialized");
- [[fallthrough]];
- case bsp::cellular::CellularResultCode::ReceivingNotStarted:
- [[fallthrough]];
- case bsp::cellular::CellularResultCode::TransmittingNotStarted:
- [[fallthrough]];
- case bsp::cellular::CellularResultCode::CMUXFrameError:
- LOG_DEBUG("CellularResult Error: %s", c_str(result.resultCode));
- inst->processError(result);
- break;
- case bsp::cellular::CellularResultCode::ReceivedNoData:
- break;
+ while ((!complete) && (--_timeout)) {
+ ret = pv_cellular->Read(reinterpret_cast<void *>(buf.get()), startParams.MaxFrameSize);
+ if (ret > 0) {
+ // LOG_DEBUG("Received %i bytes", ret);
+ for (int i = 0; i < ret; i++) {
+ data.push_back(buf[i]);
+ }
+ complete = TS0710_Frame::isComplete(data);
}
+ vTaskDelay(pdMS_TO_TICKS(1));
}
+ if ((!complete) && (_timeout)) {
+ LOG_ERROR("Incomplete frame received");
+ }
+
+ return ret;
}
void TS0710::SelectAntenna(bsp::cellular::antenna antenna)
{
- pv_cellular->selectAntenna(antenna);
+ pv_cellular->SelectAntenna(antenna);
}
bsp::cellular::antenna TS0710::GetAntenna()
{
- return pv_cellular->getAntenna();
+ return pv_cellular->GetAntenna();
}
void TS0710::InformModemHostWakeup(void)
{
- return pv_cellular->informModemHostWakeup();
+ return pv_cellular->InformModemHostWakeup();
}
bool TS0710::IsModemActive(void)
@@ 602,46 569,46 @@ bool TS0710::IsModemActive(void)
void TS0710::TurnOnModem(void)
{
- return pv_cellular->powerUp();
+ return pv_cellular->PowerUp();
}
void TS0710::ResetModem(void)
{
- return pv_cellular->restart();
+ return pv_cellular->Restart();
}
void TS0710::TurnOffModem(void)
{
- return pv_cellular->powerDown();
+ return pv_cellular->PowerDown();
}
void TS0710::EnterSleepMode(void)
{
- return pv_cellular->enterSleep();
+ return pv_cellular->EnterSleep();
}
void TS0710::ExitSleepMode(void)
{
- return pv_cellular->exitSleep();
+ return pv_cellular->ExitSleep();
}
void TS0710::RegisterCellularDevice(void)
{
- auto deviceRegistrationMsg = std::make_shared<sys::DeviceRegistrationMessage>(pv_cellular->getCellularDevice());
+ auto deviceRegistrationMsg = std::make_shared<sys::DeviceRegistrationMessage>(pv_cellular->GetCellularDevice());
pv_parent->bus.sendUnicast(std::move(deviceRegistrationMsg), service::name::system_manager);
}
-[[nodiscard]] auto TS0710::getLastCommunicationTimestamp() const noexcept -> TickType_t
+[[nodiscard]] auto TS0710::GetLastCommunicationTimestamp() const noexcept -> TickType_t
{
- return pv_cellular->getLastCommunicationTimestamp();
+ return pv_cellular->GetLastCommunicationTimestamp();
}
-[[nodiscard]] auto TS0710::isCellularInSleepMode() const noexcept -> bool
+[[nodiscard]] auto TS0710::IsCellularInSleepMode() const noexcept -> bool
{
- return pv_cellular->isCellularInSleepMode();
+ return pv_cellular->IsCellularInSleepMode();
}
-TS0710::ConfState TS0710::setupEchoCanceller(EchoCancellerStrength strength)
+TS0710::ConfState TS0710::SetupEchoCanceller(EchoCancellerStrength strength)
{
switch (strength) {
M module-cellular/Modem/TS0710/TS0710.h => module-cellular/Modem/TS0710/TS0710.h +40 -39
@@ 1,7 1,8 @@
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#pragma once
+#ifndef _TS0710_H
+#define _TS0710_H
/*
5.2.6 Basic Option
@@ 189,9 190,6 @@ repeated until a response is obtained or action is taken by a higher layer.
*/
#include <vector>
-#include <queue>
-#include <string>
-#include <module-bsp/bsp/cellular/bsp_cellular.hpp>
#include "TS0710_START.h"
#include "TS0710_CLOSE.h"
@@ 199,13 197,14 @@ repeated until a response is obtained or action is taken by a higher layer.
#include "TS0710_TEST.h"
#include "TS0710_WAKEUP.h"
#include "TS0710_types.h"
-#include "TS0710_Frame.h"
-
#include "DLC_channel.h"
+#include "TS0710_Frame.h"
#include "Modem/ATParser.hpp"
#include "Service/Service.hpp"
+#include <queue>
+#include <string>
-#include <message_buffer.h>
+#include "module-bsp/bsp/cellular/bsp_cellular.hpp"
#if defined(__cplusplus)
extern "C"
@@ 222,7 221,7 @@ namespace bsp
class Cellular;
}
-[[noreturn]] void workerTaskFunction(void *ptr);
+void workerTaskFunction(void *ptr);
class TS0710
{
@@ 234,7 233,6 @@ class TS0710
Notifications = 2,
Data = 3,
};
-
static std::string name(enum Channel name)
{
switch (name) {
@@ 249,13 247,13 @@ class TS0710
}
return "";
}
-
enum class Mode
{
AT, /// AT raw text mode
CMUX_SETUP, /// Modem is switching from AT to CMUX
CMUX /// multiplexer mode enabled
};
+ void setMode(Mode mode);
enum class ConfState
{
@@ 265,16 263,15 @@ class TS0710
PowerUp
};
- void setMode(Mode mode);
-
private:
Mode mode = Mode::AT;
std::vector<DLC_channel *> channels;
-
- const uint32_t taskPriority = 0;
+ friend void workerTaskFunction(void *ptr);
+ // worker's task handle
xTaskHandle taskHandle = nullptr;
-
+ const uint32_t taskPriority = 0;
std::unique_ptr<bsp::Cellular> pv_cellular;
+ PortSpeed_e pv_portSpeed;
ATParser *parser;
int CloseMultiplexer();
@@ 293,6 290,7 @@ class TS0710
sys::Service *pv_parent;
DLC_channel::Callback_t controlCallback = nullptr;
+ std::queue<uint8_t> RXFifo;
enum class EchoCancellerStrength
{
@@ 301,14 299,7 @@ class TS0710
Aggressive,
Tuned
};
-
- friend void workerTaskFunction(void *ptr);
- ConfState setupEchoCanceller(EchoCancellerStrength strength);
- void parseCellularResultCMUX(bsp::cellular::CellularDMAResultStruct &result);
- size_t flushReceiveData();
- void processData(bsp::cellular::CellularDMAResultStruct &result);
- void processError(bsp::cellular::CellularDMAResultStruct &result);
- void sendFrameToChannel(bsp::cellular::CellularResult &resultStruct);
+ TS0710::ConfState SetupEchoCanceller(EchoCancellerStrength strength);
public:
/// @brief get Channel by index
@@ 325,23 316,31 @@ class TS0710
return nullptr;
}
- std::vector<DLC_channel *> &getChannels()
+ DLC_channel *OpenChannel(Channel chanel_val)
{
- return channels;
+ DLC_channel *channel = new DLC_channel(static_cast<DLCI_t>(chanel_val), name(chanel_val), pv_cellular.get());
+ channels.push_back(channel);
+ return channels.back();
}
- DLC_channel *OpenChannel(Channel channelIndex)
+ void CloseChannel(unsigned index)
{
- DLC_channel *channel =
- new DLC_channel(static_cast<DLCI_t>(channelIndex), name(channelIndex), pv_cellular.get());
- channels.push_back(channel);
-
- if (!channel->init()) {
- channels.pop_back();
- delete channel;
+ if (index >= channels.size()) {
+ LOG_ERROR("Wrong channel index");
+ return;
}
+ delete channels[index];
+ channels.erase(channels.begin() + index);
+ }
- return channels.back();
+ void CloseChannel(const std::string &name)
+ {
+ for (size_t i = 0; i < channels.size(); i++) {
+ if (channels[i]->getName() == name) {
+ delete channels[i];
+ channels.erase(channels.begin() + 1);
+ }
+ }
}
void CloseChannels()
@@ 358,13 357,15 @@ class TS0710
{
return static_cast<DLCI_t>(channels.size() == 0 ? 0 : channels.size() - 1);
}
-
ConfState BaudDetectOnce();
ConfState BaudDetectProcedure(uint16_t timeout_s = 30);
ConfState ConfProcedure();
ConfState AudioConfProcedure();
ConfState StartMultiplexer();
+ size_t FlushReceiveData();
+ ssize_t ReceiveData(std::vector<uint8_t> &data, uint32_t timeout);
+
bsp::Cellular *getCellular()
{
return pv_cellular.get();
@@ 426,8 427,6 @@ class TS0710
TS0710(PortSpeed_e portSpeed, sys::Service *parent);
TS0710() = delete;
~TS0710();
- void Init(PortSpeed_e portSpeed, sys::Service *parent);
- void SetStartParams(PortSpeed_e portSpeed);
void SelectAntenna(bsp::cellular::antenna antenna);
bsp::cellular::antenna GetAntenna();
// Add error handling - only for Advanced mode. Leave for now
@@ 442,6 441,8 @@ class TS0710
void EnterSleepMode(void);
void ExitSleepMode(void);
void RegisterCellularDevice(void);
- [[nodiscard]] auto getLastCommunicationTimestamp() const noexcept -> TickType_t;
- [[nodiscard]] auto isCellularInSleepMode() const noexcept -> bool;
+ [[nodiscard]] auto GetLastCommunicationTimestamp() const noexcept -> TickType_t;
+ [[nodiscard]] auto IsCellularInSleepMode() const noexcept -> bool;
};
+
+#endif //_TS0710_H
M module-cellular/Modem/TS0710/TS0710_DATA.cpp => module-cellular/Modem/TS0710/TS0710_DATA.cpp +3 -3
@@ 61,7 61,7 @@ void TS0710_DATA::request(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t sysParams,
frame.data = User_data;
TS0710_Frame frame_c(frame);
// UartSend(frame_c.getSerData().data(), frame_c.getSerData().size());
- pv_cellular->write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
+ pv_cellular->Write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
}
else { // if data size > max frame size
int dataLeft = User_data.size();
@@ 76,7 76,7 @@ void TS0710_DATA::request(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t sysParams,
TS0710_Frame frame_c(frame);
// UartSend(frame_c.getSerData().data(), frame_c.getSerData().size());
// while(!pv_cellular->GetSendingAllowed());
- pv_cellular->write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
+ pv_cellular->Write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
// vTaskDelay(1);
dataLeft -= (dataLeft <= maximumFrameLength ? dataLeft : maximumFrameLength);
}
@@ 88,4 88,4 @@ void TS0710_DATA::request(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t sysParams,
* @param User_data
*/
void TS0710_DATA::indication(DLCI_t DLCI, std::vector<uint8_t> User_data)
-{}
+{}<
\ No newline at end of file
M module-cellular/Modem/TS0710/TS0710_DLC_ESTABL.cpp => module-cellular/Modem/TS0710/TS0710_DLC_ESTABL.cpp +6 -7
@@ 21,8 21,6 @@ extern "C"
#include "log/log.hpp"
#include "FreeRTOS.h"
-#include <bsp/cellular/CellularResult.hpp>
-
/**
* TS0710_DLC_ESTABL implementation
*/
@@ 83,12 81,12 @@ bool TS0710_DLC_ESTABL::request(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t syste
frame.Address = static_cast<uint8_t>(DLCI << 2) | (1 << 1); // set C/R = 1 - command
frame.Control = static_cast<uint8_t>(system_parameters.TypeOfFrame);
TS0710_Frame frame_c(frame);
- pv_cellular->write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
+ pv_cellular->Write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
// return true;
int retries = system_parameters.MaxNumOfRetransmissions;
while (retries--) {
// UartSend(frame_c.getSerData().data(), frame_c.getSerData().size());
- pv_cellular->write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
+ pv_cellular->Write(static_cast<void *>(frame_c.getSerData().data()), frame_c.getSerData().size());
vTaskDelay(system_parameters.AckTime);
if (response(DLCI, system_parameters)) {
LOG_DEBUG("Got response");
@@ 115,13 113,14 @@ void TS0710_DLC_ESTABL::indication(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t sy
bool TS0710_DLC_ESTABL::response(DLCI_t DLCI, DLC_ESTABL_SystemParameters_t system_parameters)
{
constexpr size_t size = 256;
- bsp::cellular::CellularDMAResultStruct result{};
+ std::unique_ptr<uint8_t[]> data(new uint8_t[size]);
- ssize_t len = pv_cellular->read(&result, size, std::chrono::milliseconds{0});
+ // uint32_t len = UartReceive(data);
+ ssize_t len = pv_cellular->Read(reinterpret_cast<void *>(data.get()), size);
LOG_DEBUG("RX length = %d", static_cast<int>(len));
if (len > 0) {
- std::vector<uint8_t> v(result.data, result.data + result.dataSize);
+ std::vector<uint8_t> v(data.get(), data.get() + len);
TS0710_Frame frame_c(v);
TS0710_Frame::frame_t frame = frame_c.getFrame();
M module-cellular/Modem/TS0710/TS0710_Frame.h => module-cellular/Modem/TS0710/TS0710_Frame.h +19 -59
@@ 34,26 34,12 @@ class TS0710_Frame
0xBD, 0x2C, 0x5E, 0xCF};
public:
- enum TS0710FrameStatus : std::uint8_t
- {
- OK,
- EmptyFrame,
- IncorrectStartStopFlags,
- CRCError,
- };
-
struct frame_t
{
- TS0710FrameStatus frameStatus = OK;
uint8_t Address;
uint8_t Control;
std::vector<uint8_t> data;
- frame_t() = default;
-
- explicit frame_t(uint8_t address, uint8_t control) : frameStatus{OK}, Address{address}, Control{control}
- {}
-
std::vector<uint8_t> serialize()
{
std::vector<uint8_t> ret;
@@ 79,7 65,7 @@ class TS0710_Frame
unsigned char i = 1;
if (Control == static_cast<uint8_t>(TypeOfFrame_e::UIH)) {
len = 3; // par. 5.3.6 of GSM0710 document states that for UIH frames, the FCS shall be calculated over
- // only the address, control and length fields TODO: include 2-byte address
+ // only the address, control and length fields TODO: include 2-byte address
// if (Length > 127)
// len += 1;
}
@@ 99,9 85,8 @@ class TS0710_Frame
{
if (serData.size() < 4) {
LOG_ERROR("Trying to deserialize empty frame");
- Address = 0;
- Control = 0;
- frameStatus = EmptyFrame;
+ Address = 0;
+ Control = 0;
return;
}
// iterate through frame to get correct trailing flag. In case multiple-frame stream provided
@@ 119,9 104,8 @@ class TS0710_Frame
}
if ((serData[0] != TS0710_FLAG) || (serData[myLen - 1] != TS0710_FLAG)) {
- Address = 0;
- Control = 0;
- frameStatus = IncorrectStartStopFlags;
+ Address = 0;
+ Control = 0;
LOG_ERROR("Received frame has incorrect leading/trailing flags. Dropping.");
return; // return empty frame. Discard frame witout proper leading & trailing flag
}
@@ 151,7 135,7 @@ class TS0710_Frame
unsigned char i = 1;
if (Control == static_cast<uint8_t>(TypeOfFrame_e::UIH)) {
len = 3; // par. 5.3.6 of GSM0710 document states that for UIH frames, the FCS shall be calculated over
- // only the address, control and length fields
+ // only the address, control and length fields: include 2-byte address
// if (Length > 127)
// len += 1;
}
@@ 166,9 150,8 @@ class TS0710_Frame
(Control !=
static_cast<uint8_t>(
TypeOfFrame_e::UA))) { // error - but fuck FCS check if it's faulty Quectel UIH frame or UA frame
- Address = 0;
- Control = 0;
- frameStatus = CRCError;
+ Address = 0;
+ Control = 0;
data.clear();
LOG_ERROR("Received frame FCS [0x%02X] != 0xCF error. Dropping.", FCS);
return; // return empty frame. Discard frame witout proper leading & trailing flag
@@ 181,42 164,33 @@ class TS0710_Frame
std::vector<uint8_t> pv_serData;
public:
- explicit TS0710_Frame(frame_t frame)
+ TS0710_Frame(frame_t frame)
{
// LOG_DEBUG("Serializing given frame");
pv_serData = frame.serialize();
pv_frame = frame;
}
-
- explicit TS0710_Frame(const std::vector<uint8_t> &serData)
+ TS0710_Frame(std::vector<uint8_t> &serData)
{
// LOG_DEBUG("Deserializing serData");
pv_frame.deserialize(serData);
pv_serData = serData;
}
-
TS0710_Frame()
{
LOG_DEBUG("Deserializing pv_serData");
pv_frame.deserialize(pv_serData);
}
-
~TS0710_Frame()
{
pv_serData.clear();
pv_frame.data.clear();
}
- frame_t &getFrame()
+ frame_t getFrame()
{
return pv_frame;
}
-
- const std::vector<uint8_t> &getData() const noexcept
- {
- return pv_frame.data;
- }
-
std::vector<uint8_t> getSerData()
{
return pv_serData;
@@ 225,13 199,11 @@ class TS0710_Frame
/* F9 03 3F 01 1C F9 */
static bool isComplete(const std::vector<uint8_t> &serData)
{
- if (serData.size() < 4) {
+ if (serData.size() < 4)
return false; // check if buffer has enough data to get length
- }
- if ((serData[0] != TS0710_FLAG) || (serData[serData.size() - 1] != TS0710_FLAG)) {
+ if ((serData[0] != TS0710_FLAG) || (serData[serData.size() - 1] != TS0710_FLAG))
return false;
- }
int Length = 0;
if (serData[3] & 0x01) { // short length
@@ 240,22 212,22 @@ class TS0710_Frame
else if (serData.size() > 4) { // long length - another check if enough bytes in buffer
Length = static_cast<uint16_t>(serData[3] >> 1) + (static_cast<uint16_t>(serData[4]) << 7);
}
- else {
+ else
return false;
- }
if (serData.size() >=
static_cast<size_t>(TS0710_FRAME_HDR_LEN + Length +
- (serData[3] & 0x01 ? 0 : 1))) { // include extended address byte if present
+ (serData[3] & 0x01 ? 0 : 1))) // include extended address byte if present
return true;
- }
return false;
}
- bool isMyChannel(DLCI_t DLCI) const
+ static bool isMyChannel(const std::vector<uint8_t> &serData, DLCI_t DLCI)
{
- return (pv_serData.size() > 1) && ((pv_serData[1] >> 2) == DLCI);
+ if ((serData.size() > 1) && ((serData[1] >> 2) == DLCI))
+ return true;
+ return false;
}
static DLCI_t getFrameDLCI(const std::vector<uint8_t> &serData)
@@ 264,18 236,6 @@ class TS0710_Frame
return (serData[1] >> 2);
return -1;
}
-
- DLCI_t getFrameDLCI() const
- {
- if (pv_serData.size() > 1)
- return (pv_serData[1] >> 2);
- return -1;
- }
-
- TS0710FrameStatus getFrameStatus() const
- {
- return pv_frame.frameStatus;
- }
};
#endif /*_TS0710_FRAME_H*/
D module-cellular/Modem/doc/Images/at_mode.svg => module-cellular/Modem/doc/Images/at_mode.svg +0 -72
@@ 1,72 0,0 @@
-<?xml version="1.0" encoding="UTF-8" standalone="no"?><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" contentScriptType="application/ecmascript" contentStyleType="text/css" height="1324px" preserveAspectRatio="none" style="width:405px;height:1324px;" version="1.1" viewBox="0 0 405 1324" width="405px" zoomAndPan="magnify"><defs><filter height="300%" id="f1cg90pa4di60m" width="300%" x="-1" y="-1"><feGaussianBlur result="blurOut" stdDeviation="2.0"/><feColorMatrix in="blurOut" result="blurOut2" type="matrix" values="0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 .4 0"/><feOffset dx="4.0" dy="4.0" in="blurOut2" result="blurOut3"/><feBlend in="SourceGraphic" in2="blurOut3" mode="normal"/></filter></defs><g><text fill="#000000" font-family="sans-serif" font-size="18" lengthAdjust="spacing" textLength="78" x="157" y="16.708">AT Mode</text><!--MD5=[36105e52843f3f28080f43ce369346ca]
-cluster CellularBSP--><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="277" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="350" x="7" y="27.9531"/><rect fill="#FFFFFF" height="244.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="344" x="10" y="57.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="7" x2="357" y1="54.25" y2="54.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="81" x="141.5" y="45.9482">CellularBSP</text><!--MD5=[4feec3315c2ae8fe0f31fdbe0936cbea]
-cluster CellularWorker--><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="554" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="295" x="29" y="377.9531"/><rect fill="#FFFFFF" height="521.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="289" x="32" y="407.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="29" x2="324" y1="404.25" y2="404.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="106" x="123.5" y="395.9482">CellularWorker</text><!--MD5=[df0b49b3bcea4a1034e7e56a9608b471]
-cluster Channel--><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="189" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="174" x="219" y="1004.9531"/><rect fill="#FFFFFF" height="156.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="168" x="222" y="1034.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="219" x2="393" y1="1031.25" y2="1031.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="58" x="277" y="1022.9482">Channel</text><g id="CellularBSP.UartIrq"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="64.2344" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="284" x="40" y="62.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="40" x2="324" y1="89.25" y2="89.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="49" x="157.5" y="80.9482">UartIrq</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="218" x="45" y="105.3887">Reads data with DMA to static buffer</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="264" x="45" y="119.3574">and packs them into struct with result code.</text></g><g id="CellularBSP.SendToWorker"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50.2656" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="318" x="23" y="187.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="23" x2="341" y1="214.25" y2="214.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="107" x="128.5" y="205.9482">SendToWorker</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="298" x="28" y="230.3887">Puts structured data into workers MessageBuffer.</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="49" x="157.5" y="323.9482">output</text><ellipse cx="182" cy="304.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="186.3891" x2="178.6109" y1="309.3422" y2="301.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="186.3891" x2="178.6109" y1="301.564" y2="309.3422"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="139" x="94.5" y="356.6514">DMAMessageBuffer</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="158" y="371.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="170" x2="170" y1="371.9531" y2="383.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="182" x2="182" y1="371.9531" y2="383.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="194" x2="194" y1="371.9531" y2="383.9531"/><g id="CellularWorker.ATParser"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50.2656" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="154" x="105" y="449.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="105" x2="259" y1="476.25" y2="476.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="64" x="150" y="467.9482">ATParser</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="134" x="110" y="492.3887">Parses URC packages.</text></g><g id="CellularWorker.CmdAwaitingResponse"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="185" x="89.5" y="560.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="89.5" x2="274.5" y1="587.25" y2="587.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="165" x="99.5" y="578.9482">CmdAwaitingResponse</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="102" x="255" y="950.9482">outputWorker</text><ellipse cx="306" cy="931.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="310.3891" x2="302.6109" y1="936.3422" y2="928.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="310.3891" x2="302.6109" y1="928.564" y2="936.3422"/><g id="CellularWorker.CheckIfFOTA"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="113" x="125.5" y="687.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="125.5" x2="238.5" y1="714.25" y2="714.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="93" x="135.5" y="705.9482">CheckIfFOTA</text></g><g id="CellularWorker.StoreURC"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="89" x="45.5" y="814.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="45.5" x2="134.5" y1="841.25" y2="841.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="69" x="55.5" y="832.9482">StoreURC</text></g><g id="CellularWorker.FotaService"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="105" x="169.5" y="814.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="169.5" x2="274.5" y1="841.25" y2="841.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="85" x="179.5" y="832.9482">FotaService</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="64" x="256" y="983.6514">ATBuffer</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="282" y="998.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="294" x2="294" y1="998.9531" y2="1010.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="306" x2="306" y1="998.9531" y2="1010.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="318" x2="318" y1="998.9531" y2="1010.9531"/><g id="Channel.ATStream"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50.2656" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="141" x="235.5" y="1076.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="235.5" x2="376.5" y1="1103.25" y2="1103.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="72" x="270" y="1094.9482">ATStream</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="121" x="240.5" y="1119.3887">parses AT message</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="107" x="252.5" y="1212.9482">channelOutput</text><ellipse cx="306" cy="1193.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="310.3891" x2="302.6109" y1="1198.3422" y2="1190.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="310.3891" x2="302.6109" y1="1190.564" y2="1198.3422"/><g id="ServiceCellular"><rect fill="#FEFECE" filter="url(#f1cg90pa4di60m)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="126" x="243" y="1260.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="243" x2="369" y1="1287.25" y2="1287.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="106" x="253" y="1278.9482">ServiceCellular</text></g><!--MD5=[a57b3170d04d2bd212a327163f4c8137]
-link UartIrq to SendToWorker--><path d="M182,127.0431 C182,144.3131 182,165.6731 182,182.6531 " fill="none" id="UartIrq-to-SendToWorker" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="182,187.7731,186,178.7731,182,182.7731,178,178.7731,182,187.7731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[12c5ee31291134eacafef3eedf3c1f48]
-link SendToWorker to output--><path d="M182,238.0731 C182,256.2931 182,280.3931 182,293.8131 " fill="none" id="SendToWorker-to-output" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="182,298.8631,186,289.8631,182,293.8631,178,289.8631,182,298.8631" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[e932264d0d3e1dc4eecdd1ce9c7fd236]
-link DMAMessageBuffer to ATParser--><path d="M182,384.0611 C182,395.3351 182,423.0731 182,444.7801 " fill="none" id="DMAMessageBuffer-to-ATParser" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="182,449.8731,186,440.8731,182,444.8731,178,440.8731,182,449.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[13a40670c7eb8b170560bd331fd78e1e]
-link ATParser to CmdAwaitingResponse--><path d="M182,500.1441 C182,516.5131 182,538.2321 182,555.5931 " fill="none" id="ATParser-to-CmdAwaitingResponse" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="182,560.8301,186,551.8301,182,555.8301,178,551.8301,182,560.8301" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[777abd894339136b04c29cf487b6773b]
-link CmdAwaitingResponse to outputWorker--><path d="M203.533,611.0751 C219.963,630.5941 242.074,659.4351 256,687.9531 C296.557,771.0041 304.253,885.5621 305.682,920.4531 " fill="none" id="CmdAwaitingResponse-to-outputWorker" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="305.872,925.6871,309.5401,916.5468,305.6891,920.6905,301.5455,916.8395,305.872,925.6871" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="29" x="289" y="781.02">True</text><!--MD5=[8a7a058cbacea9da7579bb2851695ae5]
-link CmdAwaitingResponse to CheckIfFOTA--><path d="M168.072,611.1631 C163.609,620.2081 159.244,630.7631 157,640.9531 C153.871,655.1611 158.191,670.4391 164.073,683.1691 " fill="none" id="CmdAwaitingResponse-to-CheckIfFOTA" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="166.3,687.7371,165.9509,677.8945,164.1086,683.2429,158.7601,681.4007,166.3,687.7371" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="33" x="158" y="654.02">False</text><!--MD5=[fd94f81ce2f3862349c63c5a12cf90a3]
-link CheckIfFOTA to StoreURC--><path d="M155.402,738.1951 C146.442,747.0751 136.758,757.5161 129,767.9531 C119.287,781.0221 110.382,796.7921 103.541,810.1471 " fill="none" id="CheckIfFOTA-to-StoreURC" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="101.117,814.9491,108.7436,808.7173,103.3702,810.4856,101.6019,805.1122,101.117,814.9491" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="33" x="130" y="781.02">False</text><!--MD5=[2bf7f23f6b2f1fdfd1cbf2b79eff56c5]
-link CheckIfFOTA to FotaService--><path d="M174.406,737.9881 C171.221,752.0771 169.4,769.9881 175,784.9531 C178.492,794.2831 184.405,803.0651 190.88,810.7271 " fill="none" id="CheckIfFOTA-to-FotaService" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="194.524,814.8641,191.5787,805.466,191.2199,811.1114,185.5744,810.7526,194.524,814.8641" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="29" x="176" y="781.02">True</text><!--MD5=[460a876a9029e334c616b58fb8501c7e]
-link output to DMAMessageBuffer--><path d="M182,311.0591 C182,322.7261 182,351.5151 182,366.8911 " fill="none" id="output-to-DMAMessageBuffer" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="182,371.8931,186,362.8931,182,366.8931,178,362.8931,182,371.8931" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[f66c76729024c907a3d48f760668579d]
-link ATBuffer to ATStream--><path d="M306,1011.0611 C306,1022.3351 306,1050.0731 306,1071.7801 " fill="none" id="ATBuffer-to-ATStream" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="306,1076.8731,310,1067.8731,306,1071.8731,302,1067.8731,306,1076.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[dd80df3ee72f240316d7675a269eb8c4]
-link ATStream to channelOutput--><path d="M306,1127.0711 C306,1145.2951 306,1169.3901 306,1182.8131 " fill="none" id="ATStream-to-channelOutput" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="306,1187.8641,310,1178.8641,306,1182.8641,302,1178.8641,306,1187.8641" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[8fe72049e9716dbce24d7677e0dd4d3e]
-link outputWorker to ATBuffer--><path d="M306,938.0591 C306,949.7261 306,978.5151 306,993.8911 " fill="none" id="outputWorker-to-ATBuffer" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="306,998.8931,310,989.8931,306,993.8931,302,989.8931,306,998.8931" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[4663c35d14db62ee482ccec530d01964]
-link channelOutput to ServiceCellular--><path d="M306,1200.0501 C306,1210.6081 306,1235.5673 306,1255.7077 " fill="none" id="channelOutput-to-ServiceCellular" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="306,1260.7127,310,1251.7127,306,1255.7127,302,1251.7127,306,1260.7127" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[8213d0f92b754f55ac336ef108bd4edb]
-@startuml
-Title AT Mode
-
-state CellularBSP {
- UartIrq: Reads data with DMA to static buffer
- UartIrq: and packs them into struct with result code.
- UartIrq - -> SendToWorker
- SendToWorker: Puts structured data into workers MessageBuffer.
- SendToWorker - -> output
-
- state output <<exitPoint>>
-}
-
-state CellularWorker{
- state DMAMessageBuffer <<expansionInput>>
-
- DMAMessageBuffer - -> ATParser
- ATParser: Parses URC packages.
- ATParser - -> CmdAwaitingResponse
-
- state CmdAwaitingResponse <<choice>>
- CmdAwaitingResponse - - - -> outputWorker : True
- CmdAwaitingResponse - -> CheckIfFOTA : False
-
- CheckIfFOTA - -> StoreURC : False
- CheckIfFOTA - -> FotaService : True
-
- state outputWorker <<exitPoint>>
-}
-
-output - -> DMAMessageBuffer
-
-state Channel {
- state ATBuffer <<expansionInput>>
-
- ATBuffer - -> ATStream
- ATStream: parses AT message
-
- ATStream - -> channelOutput
-
- state channelOutput <<exitPoint>>
-}
-
-outputWorker - -> ATBuffer
-channelOutput - -> ServiceCellular
-@enduml
-
-PlantUML version 1.2021.4beta1(Unknown compile time)
-(GPL source distribution)
-Java Runtime: Java(TM) SE Runtime Environment
-JVM: Java HotSpot(TM) 64-Bit Server VM
-Default Encoding: UTF-8
-Language: en
-Country: US
---></g></svg>>
\ No newline at end of file
D module-cellular/Modem/doc/Images/at_mode.uml => module-cellular/Modem/doc/Images/at_mode.uml +0 -46
@@ 1,46 0,0 @@
-@startuml
-Title AT Mode
-
-state CellularBSP {
- UartIrq: Reads data with DMA to static buffer
- UartIrq: and packs them into struct with result code.
- UartIrq --> SendToWorker
- SendToWorker: Puts structured data into workers MessageBuffer.
- SendToWorker --> output
-
- state output <<exitPoint>>
-}
-
-state CellularWorker{
- state DMAMessageBuffer <<expansionInput>>
-
- DMAMessageBuffer --> ATParser
- ATParser: Parses URC packages.
- ATParser --> CmdAwaitingResponse
-
- state CmdAwaitingResponse <<choice>>
- CmdAwaitingResponse ----> outputWorker : True
- CmdAwaitingResponse --> CheckIfFOTA : False
-
- CheckIfFOTA --> StoreURC : False
- CheckIfFOTA --> FotaService : True
-
- state outputWorker <<exitPoint>>
-}
-
-output --> DMAMessageBuffer
-
-state Channel {
- state ATBuffer <<expansionInput>>
-
- ATBuffer --> ATStream
- ATStream: parses AT message
-
- ATStream --> channelOutput
-
- state channelOutput <<exitPoint>>
-}
-
-outputWorker --> ATBuffer
-channelOutput --> ServiceCellular
-@enduml
D module-cellular/Modem/doc/Images/cellular_mux_read.png => module-cellular/Modem/doc/Images/cellular_mux_read.png +0 -0
D module-cellular/Modem/doc/Images/cellular_result_struct.png => module-cellular/Modem/doc/Images/cellular_result_struct.png +0 -0
D module-cellular/Modem/doc/Images/cellular_result_struct.uml => module-cellular/Modem/doc/Images/cellular_result_struct.uml +0 -9
@@ 1,9 0,0 @@
-@startuml
-object CellularResultStruct {
- CellularResultCode resultCode
- vector<uint8_t> data
-
- +std::shared_ptr<uint8_t> serialize()
- +void deserialize(serialized, size)
-}
-@enduml
D module-cellular/Modem/doc/Images/cmx_mode.uml => module-cellular/Modem/doc/Images/cmx_mode.uml +0 -70
@@ 1,70 0,0 @@
-@startuml
-Title CMUX Mode
-
-state CellularBSP {
- UartIrq: Reads data with DMA to static buffer
- UartIrq: and packs them into struct with result code.
- UartIrq --> SendToWorker
- SendToWorker: Puts structured data into workers MessageBuffer.
- SendToWorker --> output
-
- state output <<exitPoint>>
-}
-
-state CellularWorker{
- state DMAMessageBuffer <<expansionInput>>
-
- DMAMessageBuffer --> ATParser
- ATParser: Parses URC packages.
- ATParser --> CmdAwaitingResponse
-
- state CmdAwaitingResponse <<choice>>
- CmdAwaitingResponse ----> workerOutput : True
- CmdAwaitingResponse --> callback : False
-
- state workerOutput <<exitPoint>>
-}
-
-state Notifications {
- state input1 <<expansionInput>>
-
- input1 --> ATStream1
-
- ATStream1 --> output1
-
- state output1 <<exitPoint>>
-}
-
-state Commands {
- state input2 <<expansionInput>>
-
- input2 --> ATStream2
-
- ATStream2 --> output2
-
- state output2 <<exitPoint>>
-}
-
-state Data {
- state input3 <<expansionInput>>
-
- input3 --> ATStream3
-
- ATStream3 --> output3
-
- state output3 <<exitPoint>>
-}
-
-state channelsFork <<fork>>
-state channelsJoin <<join>>
-
-output --> DMAMessageBuffer : Result{data,resultCode}
-workerOutput --> channelsFork
-channelsFork --> input1
-channelsFork --> input2
-channelsFork --> input3
-output1 --> channelsJoin
-output2 --> channelsJoin
-output3 --> channelsJoin
-channelsJoin --> ServiceCellular : Result{parsedData,resultCode}
-@enduml
D module-cellular/Modem/doc/Images/dma_result_struct.png => module-cellular/Modem/doc/Images/dma_result_struct.png +0 -0
D module-cellular/Modem/doc/Images/dma_result_struct.uml => module-cellular/Modem/doc/Images/dma_result_struct.uml +0 -7
@@ 1,7 0,0 @@
-@startuml
-object CellularDMAResultStruct {
- CellularResultCode resultCode
- size_t dataSize
- uint8_t data[CellularResultStructMaxDataSize]
-}
-@enduml
D module-cellular/Modem/doc/Images/mux_mode.svg => module-cellular/Modem/doc/Images/mux_mode.svg +0 -106
@@ 1,106 0,0 @@
-<?xml version="1.0" encoding="UTF-8" standalone="no"?><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" contentScriptType="application/ecmascript" contentStyleType="text/css" height="1445px" preserveAspectRatio="none" style="width:435px;height:1445px;" version="1.1" viewBox="0 0 435 1445" width="435px" zoomAndPan="magnify"><defs><filter height="300%" id="f342a3rt0b12s" width="300%" x="-1" y="-1"><feGaussianBlur result="blurOut" stdDeviation="2.0"/><feColorMatrix in="blurOut" result="blurOut2" type="matrix" values="0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 .4 0"/><feOffset dx="4.0" dy="4.0" in="blurOut2" result="blurOut3"/><feBlend in="SourceGraphic" in2="blurOut3" mode="normal"/></filter></defs><g><text fill="#000000" font-family="sans-serif" font-size="18" lengthAdjust="spacing" textLength="109" x="156.5" y="16.708">CMUX Mode</text><!--MD5=[36105e52843f3f28080f43ce369346ca]
-cluster CellularBSP--><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="277" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="350" x="12" y="27.9531"/><rect fill="#FFFFFF" height="244.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="344" x="15" y="57.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="12" x2="362" y1="54.25" y2="54.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="81" x="146.5" y="45.9482">CellularBSP</text><!--MD5=[4feec3315c2ae8fe0f31fdbe0936cbea]
-cluster CellularWorker--><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="505" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="218" x="78" y="393.9531"/><rect fill="#FFFFFF" height="472.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="212" x="81" y="423.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="78" x2="296" y1="420.25" y2="420.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="106" x="134" y="411.9482">CellularWorker</text><!--MD5=[a878dacc166bb130104221e452026b76]
-cluster Notifications--><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="189" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="134" x="7" y="1040.9531"/><rect fill="#FFFFFF" height="156.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="128" x="10" y="1070.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="7" x2="141" y1="1067.25" y2="1067.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="92" x="28" y="1058.9482">Notifications</text><!--MD5=[7c76d2c3a8a2b6b7f38b9d3310256c36]
-cluster Commands--><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="189" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="132" x="149" y="1040.9531"/><rect fill="#FFFFFF" height="156.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="126" x="152" y="1070.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="149" x2="281" y1="1067.25" y2="1067.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="80" x="175" y="1058.9482">Commands</text><!--MD5=[f21b1f164e99c6b37934f23ad048ad54]
-cluster Data--><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="189" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="134" x="289" y="1040.9531"/><rect fill="#FFFFFF" height="156.7031" rx="12.5" ry="12.5" style="stroke:#FFFFFF;stroke-width:1.0;" width="128" x="292" y="1070.25"/><line style="stroke:#A80036;stroke-width:1.5;" x1="289" x2="423" y1="1067.25" y2="1067.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="34" x="339" y="1058.9482">Data</text><g id="CellularBSP.UartIrq"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="64.2344" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="284" x="45" y="62.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="45" x2="329" y1="89.25" y2="89.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="49" x="162.5" y="80.9482">UartIrq</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="218" x="50" y="105.3887">Reads data with DMA to static buffer</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="264" x="50" y="119.3574">and packs them into struct with result code.</text></g><g id="CellularBSP.SendToWorker"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50.2656" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="318" x="28" y="187.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="28" x2="346" y1="214.25" y2="214.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="107" x="133.5" y="205.9482">SendToWorker</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="298" x="33" y="230.3887">Puts structured data into workers MessageBuffer.</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="49" x="162.5" y="323.9482">output</text><ellipse cx="187" cy="304.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="191.3891" x2="183.6109" y1="309.3422" y2="301.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="191.3891" x2="183.6109" y1="301.564" y2="309.3422"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="139" x="99.5" y="372.6514">DMAMessageBuffer</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="163" y="387.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="175" x2="175" y1="387.9531" y2="399.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="187" x2="187" y1="387.9531" y2="399.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="199" x2="199" y1="387.9531" y2="399.9531"/><g id="CellularWorker.ATParser"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50.2656" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="154" x="110" y="465.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="110" x2="264" y1="492.25" y2="492.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="64" x="155" y="483.9482">ATParser</text><text fill="#000000" font-family="sans-serif" font-size="12" lengthAdjust="spacing" textLength="134" x="115" y="508.3887">Parses URC packages.</text></g><g id="CellularWorker.CmdAwaitingResponse"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="185" x="94.5" y="576.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="94.5" x2="279.5" y1="603.25" y2="603.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="165" x="104.5" y="594.9482">CmdAwaitingResponse</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="101" x="164.5" y="917.9482">workerOutput</text><ellipse cx="215" cy="898.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="219.3891" x2="211.6109" y1="903.3422" y2="895.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="219.3891" x2="211.6109" y1="895.564" y2="903.3422"/><g id="CellularWorker.callback"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="79" x="99.5" y="703.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="99.5" x2="178.5" y1="730.25" y2="730.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="59" x="109.5" y="721.9482">callback</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="47" x="50.5" y="1019.6514">input1</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="68" y="1034.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="80" x2="80" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="92" x2="92" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="104" x2="104" y1="1034.9531" y2="1046.9531"/><g id="Notifications.ATStream1"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="101" x="23.5" y="1112.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="23.5" x2="124.5" y1="1139.25" y2="1139.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="81" x="33.5" y="1130.9482">ATStream1</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="58" x="72" y="1248.9482">output1</text><ellipse cx="101" cy="1229.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="105.3891" x2="97.6109" y1="1234.3422" y2="1226.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="105.3891" x2="97.6109" y1="1226.564" y2="1234.3422"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="46" x="174" y="1019.6514">input2</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="191" y="1034.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="203" x2="203" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="215" x2="215" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="227" x2="227" y1="1034.9531" y2="1046.9531"/><g id="Commands.ATStream2"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="100" x="165" y="1112.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="165" x2="265" y1="1139.25" y2="1139.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="80" x="175" y="1130.9482">ATStream2</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="57" x="186.5" y="1248.9482">output2</text><ellipse cx="215" cy="1229.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="219.3891" x2="211.6109" y1="1234.3422" y2="1226.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="219.3891" x2="211.6109" y1="1226.564" y2="1234.3422"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="47" x="296.5" y="1019.6514">input3</text><rect fill="#FEFECE" height="12" style="stroke:#A80036;stroke-width:1.5;" width="48" x="314" y="1034.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="326" x2="326" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="338" x2="338" y1="1034.9531" y2="1046.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="350" x2="350" y1="1034.9531" y2="1046.9531"/><g id="Data.ATStream3"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="101" x="305.5" y="1112.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="305.5" x2="406.5" y1="1139.25" y2="1139.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="81" x="315.5" y="1130.9482">ATStream3</text></g><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="58" x="287" y="1248.9482">output3</text><ellipse cx="316" cy="1229.9531" fill="#FEFECE" rx="6" ry="6" style="stroke:#A80036;stroke-width:1.5;"/><line style="stroke:#A80036;stroke-width:1.5;" x1="320.3891" x2="312.6109" y1="1234.3422" y2="1226.564"/><line style="stroke:#A80036;stroke-width:1.5;" x1="320.3891" x2="312.6109" y1="1226.564" y2="1234.3422"/><rect fill="#000000" filter="url(#f342a3rt0b12s)" height="8" style="stroke:none;stroke-width:1.0;" width="80" x="175" y="965.9531"/><rect fill="#000000" filter="url(#f342a3rt0b12s)" height="8" style="stroke:none;stroke-width:1.0;" width="80" x="175" y="1296.9531"/><g id="ServiceCellular"><rect fill="#FEFECE" filter="url(#f342a3rt0b12s)" height="50" rx="12.5" ry="12.5" style="stroke:#A80036;stroke-width:1.5;" width="126" x="152" y="1381.9531"/><line style="stroke:#A80036;stroke-width:1.5;" x1="152" x2="278" y1="1408.25" y2="1408.25"/><text fill="#000000" font-family="sans-serif" font-size="14" lengthAdjust="spacing" textLength="106" x="162" y="1399.9482">ServiceCellular</text></g><!--MD5=[a57b3170d04d2bd212a327163f4c8137]
-link UartIrq to SendToWorker--><path d="M187,127.0431 C187,144.3131 187,165.6731 187,182.6531 " fill="none" id="UartIrq-to-SendToWorker" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="187,187.7731,191,178.7731,187,182.7731,183,178.7731,187,187.7731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[12c5ee31291134eacafef3eedf3c1f48]
-link SendToWorker to output--><path d="M187,238.0731 C187,256.2931 187,280.3931 187,293.8131 " fill="none" id="SendToWorker-to-output" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="187,298.8631,191,289.8631,187,293.8631,183,289.8631,187,298.8631" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[e932264d0d3e1dc4eecdd1ce9c7fd236]
-link DMAMessageBuffer to ATParser--><path d="M187,400.0631 C187,411.3331 187,439.0731 187,460.7801 " fill="none" id="DMAMessageBuffer-to-ATParser" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="187,465.8731,191,456.8731,187,460.8731,183,456.8731,187,465.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[13a40670c7eb8b170560bd331fd78e1e]
-link ATParser to CmdAwaitingResponse--><path d="M187,516.1441 C187,532.5131 187,554.2321 187,571.5931 " fill="none" id="ATParser-to-CmdAwaitingResponse" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="187,576.8301,191,567.8301,187,571.8301,183,567.8301,187,576.8301" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[9a2733e9d3d9be03a03451908a1ba3d9]
-link CmdAwaitingResponse to workerOutput--><path d="M189.291,627.0941 C195.068,687.9511 210.046,845.7621 214.02,887.6301 " fill="none" id="CmdAwaitingResponse-to-workerOutput" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="214.524,892.9411,217.6549,883.6032,214.0511,887.9635,209.6907,884.3598,214.524,892.9411" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="29" x="207" y="797.02">True</text><!--MD5=[d46098a13406a974ef8f13d074dfa6c4]
-link CmdAwaitingResponse to callback--><path d="M153.482,626.9631 C144.458,635.3271 135.859,645.5171 131,656.9531 C125.476,669.9541 126.45,685.4391 129.233,698.6241 " fill="none" id="CmdAwaitingResponse-to-callback" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="130.427,703.7431,132.2785,694.0699,129.2914,698.8738,124.4875,695.8868,130.427,703.7431" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="33" x="132" y="670.02">False</text><!--MD5=[5af6ce0d04d61de9b9e76368ba5a826e]
-link input1 to ATStream1--><path d="M91.0322,1047.0611 C88.896,1058.3351 83.6403,1086.0731 79.5275,1107.7801 " fill="none" id="input1-to-ATStream1" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="78.5625,1112.8731,84.1668,1104.7742,79.4925,1107.9604,76.3064,1103.2862,78.5625,1112.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[8f490082540074d4ee2ef1a6e118265e]
-link ATStream1 to output1--><path d="M81.2355,1163.0711 C86.7027,1181.2951 93.9312,1205.3901 97.9581,1218.8131 " fill="none" id="ATStream1-to-output1" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="99.473,1223.8641,100.7176,1214.0942,98.036,1219.0751,93.0551,1216.3935,99.473,1223.8641" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[0988824bf8ec7c59907bef1cbce29abd]
-link input2 to ATStream2--><path d="M215,1047.0611 C215,1058.3351 215,1086.0731 215,1107.7801 " fill="none" id="input2-to-ATStream2" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,1112.8731,219,1103.8731,215,1107.8731,211,1103.8731,215,1112.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[6ea5f7ac2ff21e3e6e6f599ed58b1881]
-link ATStream2 to output2--><path d="M215,1163.0711 C215,1181.2951 215,1205.3901 215,1218.8131 " fill="none" id="ATStream2-to-output2" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,1223.8641,219,1214.8641,215,1218.8641,211,1214.8641,215,1223.8641" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[c8610ed9c90908ab582e2197c703e61b]
-link input3 to ATStream3--><path d="M338.968,1047.0611 C341.104,1058.3351 346.36,1086.0731 350.473,1107.7801 " fill="none" id="input3-to-ATStream3" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="351.437,1112.8731,353.6932,1103.2862,350.507,1107.9604,345.8328,1104.7742,351.437,1112.8731" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[d41c41dd4852fd322b9dd1ba5228125c]
-link ATStream3 to output3--><path d="M345.281,1163.0711 C337.027,1181.6421 326.064,1206.3091 320.171,1219.5671 " fill="none" id="ATStream3-to-output3" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="318.111,1224.2031,325.4202,1217.6019,320.1408,1219.6337,318.109,1214.3543,318.111,1224.2031" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[460a876a9029e334c616b58fb8501c7e]
-link output to DMAMessageBuffer--><path d="M187,311.1331 C187,325.1931 187,364.2331 187,382.8431 " fill="none" id="output-to-DMAMessageBuffer" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="187,387.9031,191,378.9031,187,382.9031,183,378.9031,187,387.9031" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="160" x="188" y="354.02">Result{data,resultCode}</text><!--MD5=[613d73f2a6b0064d130614cb72f0ee69]
-link workerOutput to channelsFork--><path d="M215,905.3671 C215,917.3761 215,946.3111 215,960.6341 " fill="none" id="workerOutput-to-channelsFork" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,965.7861,219,956.7861,215,960.7861,211,956.7861,215,965.7861" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[2d19209ccd932d018b2d06ef9fb86c8f]
-link channelsFork to input1--><path d="M209.395,974.0971 C191.079,984.3721 132.623,1017.1641 105.751,1032.2391 " fill="none" id="channelsFork-to-input1" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="101.118,1034.8381,110.9241,1033.9212,105.4782,1032.3909,107.0085,1026.945,101.118,1034.8381" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[5fac8884c6f6b68b192a3cbb904f8716]
-link channelsFork to input2--><path d="M215,974.2811 C215,984.1591 215,1013.6091 215,1029.5041 " fill="none" id="channelsFork-to-input2" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,1034.6851,219,1025.6851,215,1029.6851,211,1025.6851,215,1034.6851" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[3c5d7806c110bbdbc69ac9b51157b004]
-link channelsFork to input3--><path d="M220.605,974.0971 C238.921,984.3721 297.377,1017.1641 324.249,1032.2391 " fill="none" id="channelsFork-to-input3" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="328.882,1034.8381,322.9915,1026.945,324.5218,1032.3909,319.0759,1033.9212,328.882,1034.8381" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[11b55a60e505a1d49558f29f7757b5a7]
-link output1 to channelsJoin--><path d="M105.898,1233.9181 C123.325,1244.4661 182.507,1280.2861 205.632,1294.2831 " fill="none" id="output1-to-channelsJoin" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="209.991,1296.9211,204.3612,1288.84,205.713,1294.3329,200.2201,1295.6847,209.991,1296.9211" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[920d51171ddf142c6b023bfa2e85b080]
-link output2 to channelsJoin--><path d="M215,1236.3671 C215,1248.3761 215,1277.3111 215,1291.6341 " fill="none" id="output2-to-channelsJoin" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,1296.7861,219,1287.7861,215,1291.7861,211,1287.7861,215,1296.7861" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[78d2c976a325450ffc8758782f6c5ecd]
-link output3 to channelsJoin--><path d="M311.398,1234.0971 C295.755,1244.7841 244.462,1279.8261 223.77,1293.9621 " fill="none" id="output3-to-channelsJoin" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="219.629,1296.7901,229.3169,1295.0169,223.7578,1293.97,224.8047,1288.4108,219.629,1296.7901" style="stroke:#A80036;stroke-width:1.0;"/><!--MD5=[a54a1b5c1c5e133ff80d5fe379df8844]
-link channelsJoin to ServiceCellular--><path d="M215,1304.9531 C215,1315.3821 215,1350.8308 215,1376.7961 " fill="none" id="channelsJoin-to-ServiceCellular" style="stroke:#A80036;stroke-width:1.0;"/><polygon fill="#A80036" points="215,1381.8525,219,1372.8525,215,1376.8525,211,1372.8525,215,1381.8525" style="stroke:#A80036;stroke-width:1.0;"/><text fill="#000000" font-family="sans-serif" font-size="13" lengthAdjust="spacing" textLength="206" x="216" y="1348.02">Result{parsedData,resultCode}</text><!--MD5=[1ca860d6e5dd9ee4bdeadd232ce293fa]
-@startuml
-Title CMUX Mode
-
-state CellularBSP {
- UartIrq: Reads data with DMA to static buffer
- UartIrq: and packs them into struct with result code.
- UartIrq - -> SendToWorker
- SendToWorker: Puts structured data into workers MessageBuffer.
- SendToWorker - -> output
-
- state output <<exitPoint>>
-}
-
-state CellularWorker{
- state DMAMessageBuffer <<expansionInput>>
-
- DMAMessageBuffer - -> ATParser
- ATParser: Parses URC packages.
- ATParser - -> CmdAwaitingResponse
-
- state CmdAwaitingResponse <<choice>>
- CmdAwaitingResponse - - - -> workerOutput : True
- CmdAwaitingResponse - -> callback : False
-
- state workerOutput <<exitPoint>>
-}
-
-state Notifications {
- state input1 <<expansionInput>>
-
- input1 - -> ATStream1
-
- ATStream1 - -> output1
-
- state output1 <<exitPoint>>
-}
-
-state Commands {
- state input2 <<expansionInput>>
-
- input2 - -> ATStream2
-
- ATStream2 - -> output2
-
- state output2 <<exitPoint>>
-}
-
-state Data {
- state input3 <<expansionInput>>
-
- input3 - -> ATStream3
-
- ATStream3 - -> output3
-
- state output3 <<exitPoint>>
-}
-
-state channelsFork <<fork>>
-state channelsJoin <<join>>
-
-output - -> DMAMessageBuffer : Result{data,resultCode}
-workerOutput - -> channelsFork
-channelsFork - -> input1
-channelsFork - -> input2
-channelsFork - -> input3
-output1 - -> channelsJoin
-output2 - -> channelsJoin
-output3 - -> channelsJoin
-channelsJoin - -> ServiceCellular : Result{parsedData,resultCode}
-@enduml
-
-PlantUML version 1.2021.4beta1(Unknown compile time)
-(GPL source distribution)
-Java Runtime: Java(TM) SE Runtime Environment
-JVM: Java HotSpot(TM) 64-Bit Server VM
-Default Encoding: UTF-8
-Language: en
-Country: US
---></g></svg>>
\ No newline at end of file
D module-cellular/Modem/doc/Images/single_cmd.uml => module-cellular/Modem/doc/Images/single_cmd.uml +0 -24
@@ 1,24 0,0 @@
-@startuml
-title Single cmd processing
-
-participant IRQ order 1
-participant BSP order 2
-participant CellularWorker order 3
-participant Channel order 4
-participant Service order 5
-
-CellularWorker -> BSP: Read()
-rnote over CellularWorker: Wait for data in MessageBuffer
-Service -> Channel: cmd()
-activate CellularWorker
-Channel -> BSP : Write()
-rnote over Channel: Wait for cmd response in MessageBuffer
-activate Channel
-rnote over IRQ: DMA received data
-IRQ -> CellularWorker: MessageBufferSendFromISR()
-rnote over CellularWorker: processData()
-CellularWorker -> Channel: MessageBufferSend()
-rnote over Channel: Parse response
-deactivate Channel
-Channel -> Service: Result
-@enduml
D module-cellular/Modem/doc/Images/single_cmd_transmission.png => module-cellular/Modem/doc/Images/single_cmd_transmission.png +0 -0
M module-cellular/at/Result.hpp => module-cellular/at/Result.hpp +9 -14
@@ 16,20 16,15 @@ namespace at
/// result class for AT send -> receive command, could return promise :p
enum class Code
{
- OK, /// at OK
- ERROR, /// at ERROR For compatibility also for CME_ERROR and CMS_ERROR (details in errorCode)
- CME_ERROR, /// In case CME error see errorCode
- CMS_ERROR, /// In case CMS error see errorCode
- TIMEOUT, /// at Timeout
- TOKENS, /// at numbers of tokens needed met
- NONE, /// no code
- UNDEFINED, /// undefined result - usage of Undefined result, define and pin result to use it
- PARSING_ERROR, /// parser error
- FULL_MSG_BUFFER, /// at not enough space left in message buffer for new message
- TRANSMISSION_NOT_STARTED, /// at dma not starting transmission
- RECEIVING_NOT_STARTED, /// at dma not starting requested receiving
- DATA_NOT_USED, /// at received data not being used
- CMUX_FRAME_ERROR, /// at cmux deserialize error
+ OK, /// at OK
+ ERROR, /// at ERROR For compatibility also for CME_ERROR and CMS_ERROR (details in errorCode)
+ CME_ERROR, /// In case CME error see errorCode
+ CMS_ERROR, /// In case CMS error see errorCode
+ TIMEOUT, /// at Timeout
+ TOKENS, /// at numbers of tokens needed met
+ NONE, /// no code
+ UNDEFINED, /// undefined result - usage of Undefined result, define and pin result to use it
+ PARSING_ERROR, /// parser error
} code = Code::UNDEFINED;
Result() = default;
M module-cellular/test/CMakeLists.txt => module-cellular/test/CMakeLists.txt +1 -10
@@ 46,6 46,7 @@ add_catch2_executable(
module-cellular
)
+
add_catch2_executable(
NAME
unittest_ATURCStream
@@ 54,13 55,3 @@ add_catch2_executable(
LIBS
module-cellular
)
-
-add_catch2_executable(
- NAME
- unittest_CellularResult
- SRCS
- unittest_CellularResult.cpp
- LIBS
- module-cellular
- module-bsp
-)
M module-cellular/test/mock/AtCommon_channel.hpp => module-cellular/test/mock/AtCommon_channel.hpp +4 -4
@@ 41,7 41,7 @@ namespace at
void cmd_post() override
{}
- size_t cmd_receive(std::uint8_t *buffer, std::chrono::milliseconds timeoutMs) override
+ std::string cmd_receive() override
{
return {};
}
@@ 49,7 49,7 @@ namespace at
class FailingChannel : public ChannelMock
{
- auto ResultMock() -> Result override
+ virtual Result ResultMock()
{
auto r = Result();
r.code = Result::Code::ERROR;
@@ 75,7 75,7 @@ namespace at
/// provides CSCS bad response
class CSCS_badChannel : public ChannelMock
{
- auto ResultMock() -> Result override
+ virtual Result ResultMock()
{
auto r = Result();
r.code = Result::Code::ERROR;
@@ 87,7 87,7 @@ namespace at
/// standard bad CSCA values I get from modem (with result OK)
class CSCA_emptyData : public ChannelMock
{
- auto ResultMock() -> Result override
+ virtual Result ResultMock()
{
auto r = Result();
r.code = Result::Code::OK;
D module-cellular/test/unittest_CellularResult.cpp => module-cellular/test/unittest_CellularResult.cpp +0 -71
@@ 1,71 0,0 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
-// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-
-#define CATCH_CONFIG_MAIN
-
-#include <catch2/catch.hpp>
-#include <module-bsp/bsp/cellular/CellularResult.hpp>
-
-TEST_CASE("CellularResult")
-{
- SECTION("CellularDMAResultStruct")
- {
- bsp::cellular::CellularDMAResultStruct cellularDmaResultStruct;
-
- auto maxSize = bsp::cellular::CellularResultStructMaxDataSize + sizeof(cellularDmaResultStruct.resultCode) +
- sizeof(cellularDmaResultStruct.dataSize);
-
- REQUIRE(cellularDmaResultStruct.getMaxSize() == maxSize);
- REQUIRE(cellularDmaResultStruct.resultCode == bsp::cellular::CellularResultCode::ReceivedNoData);
- REQUIRE(cellularDmaResultStruct.getEmptySize() == maxSize - bsp::cellular::CellularResultStructMaxDataSize);
- REQUIRE(cellularDmaResultStruct.getSize() == cellularDmaResultStruct.getEmptySize());
- }
-
- SECTION("Create CellularResultStruct")
- {
- bsp::cellular::CellularResultStruct cellularResultStruct;
-
- REQUIRE(cellularResultStruct.resultCode == bsp::cellular::CellularResultCode::Uninitialized);
- REQUIRE(cellularResultStruct.data.empty());
- }
-
- SECTION("Serialize empty CellularResultStruct")
- {
- bsp::cellular::CellularResultStruct cellularResultStruct;
-
- auto serialized = cellularResultStruct.serialize();
- auto serializedResult = serialized.get()[0];
- serialized.release();
-
- REQUIRE(cellularResultStruct.getSerializedSize() == sizeof(cellularResultStruct.resultCode));
- REQUIRE(serializedResult == static_cast<unsigned char>(bsp::cellular::CellularResultCode::Uninitialized));
- }
-
- SECTION("Deserialize empty buffer")
- {
- bsp::cellular::CellularResultStruct cellularResultStruct;
-
- uint8_t serialized[0] = {};
- cellularResultStruct.deserialize(serialized, 0);
-
- REQUIRE(cellularResultStruct.resultCode == bsp::cellular::CellularResultCode::Uninitialized);
- REQUIRE(cellularResultStruct.data.empty());
- }
-
- SECTION("Serialize and deserialize CellularResultStruct")
- {
- bsp::cellular::CellularResultStruct cellularResultStruct;
- cellularResultStruct.resultCode = bsp::cellular::CellularResultCode::ReceivedAndFull;
- cellularResultStruct.data = {1, 2, 3, 4, 5, 10};
-
- auto serialized = cellularResultStruct.serialize();
-
- bsp::cellular::CellularResultStruct cellularResultStructDeserialized;
- cellularResultStructDeserialized.deserialize(serialized.get(), cellularResultStruct.getSerializedSize());
-
- serialized.release();
-
- REQUIRE(cellularResultStructDeserialized.resultCode == cellularResultStruct.resultCode);
- REQUIRE(cellularResultStructDeserialized.data == cellularResultStruct.data);
- }
-}
M module-cellular/test/unittest_cmux.cpp => module-cellular/test/unittest_cmux.cpp +1 -1
@@ 27,7 27,7 @@ TEST_CASE("TS0170 frame")
TS0710_Frame frame(tempFrame);
REQUIRE(frame.isComplete(frame.getSerData()) == true);
- REQUIRE(frame.isMyChannel(DLCI) == true);
+ REQUIRE(frame.isMyChannel(frame.getSerData(), DLCI) == true);
REQUIRE(frame.getFrameDLCI(frame.getSerData()) == DLCI);
REQUIRE(frame.getSerData().size() == cmuxMinimumFrameLength + command.length());
}
M module-services/service-cellular/ServiceCellular.cpp => module-services/service-cellular/ServiceCellular.cpp +12 -10
@@ 248,7 248,7 @@ static bool isSettingsAutomaticTimeSyncEnabled()
void ServiceCellular::SleepTimerHandler()
{
auto currentTime = cpp_freertos::Ticks::TicksToMs(cpp_freertos::Ticks::GetTicks());
- auto lastCommunicationTimestamp = cmux->getLastCommunicationTimestamp();
+ auto lastCommunicationTimestamp = cmux->GetLastCommunicationTimestamp();
auto timeOfInactivity = currentTime >= lastCommunicationTimestamp
? currentTime - lastCommunicationTimestamp
: std::numeric_limits<TickType_t>::max() - lastCommunicationTimestamp + currentTime;
@@ 358,8 358,8 @@ void ServiceCellular::registerMessageHandlers()
connect(typeid(CellularChangeSimDataMessage), [&](sys::Message *request) -> sys::MessagePointer {
auto msg = static_cast<CellularChangeSimDataMessage *>(request);
Store::GSM::get()->selected = msg->getSim();
- bsp::cellular::sim::simSelect();
- bsp::cellular::sim::hotSwapTrigger();
+ bsp::cellular::sim::sim_sel();
+ bsp::cellular::sim::hotswap_trigger();
return std::make_shared<CellularResponseMessage>(true);
});
@@ 456,7 456,7 @@ void ServiceCellular::registerMessageHandlers()
}
if (typeid(*msg->event.get()) == typeid(sdesktop::developerMode::CellularSleepModeInfoRequestEvent)) {
auto event = std::make_unique<sdesktop::developerMode::CellularSleepModeInfoRequestEvent>(
- cmux->isCellularInSleepMode());
+ cmux->IsCellularInSleepMode());
auto message = std::make_shared<sdesktop::developerMode::DeveloperModeRequest>(std::move(event));
bus.sendUnicast(std::move(message), service::name::service_desktop);
}
@@ 929,7 929,7 @@ bool ServiceCellular::handle_audio_conf_procedure()
state.set(this, State::ST::Failed);
return false;
}
- cmux->getCellular()->setSpeed(ATPortSpeeds_text[cmux->getStartParams().PortSpeed]);
+ cmux->getCellular()->SetSpeed(ATPortSpeeds_text[cmux->getStartParams().PortSpeed]);
vTaskDelay(1000);
if (cmux->StartMultiplexer() == TS0710::ConfState::Success) {
@@ 1303,7 1303,8 @@ auto ServiceCellular::sendSMS(SMSRecord record) -> bool
std::string body = UCS2(UTF8(receiver)).str();
std::string suffix = "\"";
std::string command_data = command + body + suffix;
- if (cmux->CheckATCommandPrompt(channel->SendCommandPrompt(command_data.c_str(), 1, commandTimeout))) {
+ if (cmux->CheckATCommandPrompt(
+ channel->SendCommandPrompt(command_data.c_str(), 1, commandTimeout.count()))) {
if (channel->cmd((UCS2(record.body).str() + "\032").c_str(), commandTimeout)) {
result = true;
@@ 1341,7 1342,8 @@ auto ServiceCellular::sendSMS(SMSRecord record) -> bool
std::string command(at::factory(at::AT::QCMGS) + UCS2(UTF8(receiver)).str() + "\",120," +
std::to_string(i + 1) + "," + std::to_string(messagePartsCount));
- if (cmux->CheckATCommandPrompt(channel->SendCommandPrompt(command.c_str(), 1, commandTimeout))) {
+ if (cmux->CheckATCommandPrompt(
+ channel->SendCommandPrompt(command.c_str(), 1, commandTimeout.count()))) {
// prompt sign received, send data ended by "Ctrl+Z"
if (channel->cmd(UCS2(messagePart).str() + "\032", commandTimeout, 2)) {
result = true;
@@ 1691,7 1693,7 @@ bool ServiceCellular::handle_sim_sanity_check()
auto ret = sim_check_hot_swap(cmux->get(TS0710::Channel::Commands));
if (ret) {
state.set(this, State::ST::ModemOn);
- bsp::cellular::sim::simSelect();
+ bsp::cellular::sim::sim_sel();
}
else {
LOG_ERROR("Sanity check failure - user will be promped about full shutdown");
@@ 1703,8 1705,8 @@ bool ServiceCellular::handle_sim_sanity_check()
bool ServiceCellular::handle_select_sim()
{
- bsp::cellular::sim::simSelect();
- bsp::cellular::sim::hotSwapTrigger();
+ bsp::cellular::sim::sim_sel();
+ bsp::cellular::sim::hotswap_trigger();
#if defined(TARGET_Linux)
DLC_channel *channel = cmux->get(TS0710::Channel::Commands);
auto ret = channel->cmd(at::AT::QSIMSTAT);
M module-services/service-evtmgr/WorkerEvent.cpp => module-services/service-evtmgr/WorkerEvent.cpp +1 -1
@@ 163,7 163,7 @@ bool WorkerEvent::handleMessage(uint32_t queueID)
if (notification == bsp::cellular::trayPin) {
Store::GSM::Tray pinstate = bsp::cellular::sim::getTray();
LOG_DEBUG("SIM state change: %d", static_cast<int>(pinstate));
- bsp::cellular::sim::hotSwapTrigger();
+ bsp::cellular::sim::hotswap_trigger();
}
if (notification == bsp::cellular::ringIndicatorPin) {