diff --git a/Cyphal/cyphal.cpp b/Cyphal/cyphal.cpp index c2ce1c8..982cf54 100644 --- a/Cyphal/cyphal.cpp +++ b/Cyphal/cyphal.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "cyphal.hpp" -#include "main.h" #include "cyphal_subscribers.hpp" #include "cyphal_registers.hpp" #include "uavcan/node/Heartbeat_1_0.h" @@ -18,7 +17,6 @@ static const constexpr size_t TX_QUEUE_FRAME_SIZE = 320; ///< we need 314 bytes ///< wrappers static void* memAllocate(CanardInstance* const canard, const size_t amount); static void memFree(CanardInstance* const canard, void* const pointer); -static uint32_t getCurrentMicroseconds(); O1HeapInstance* Cyphal::my_allocator; @@ -58,7 +56,7 @@ int Cyphal::init(uint8_t id) { void Cyphal::process() { // 1. spin recv - uint32_t crnt_time_ms = HAL_GetTick(); + uint32_t crnt_time_ms = platformSpecificGetTimeMs(); for (uint_fast8_t frame_idx = 0; frame_idx < transport.get_rx_queue_size(); frame_idx++) { CanardFrame rx_frame; if (transport.receive(&rx_frame)) { @@ -132,7 +130,7 @@ void Cyphal::processReceivedTransfer([[maybe_unused]] const uint8_t redundant_in } bool Cyphal::isTxQueueItemFresh(const CanardTxQueueItem* ti) const { - return (0U == ti->tx_deadline_usec) || (ti->tx_deadline_usec > getCurrentMicroseconds()); + return (0U == ti->tx_deadline_usec) || (ti->tx_deadline_usec > platformSpecificGetTimeMs()); } void Cyphal::spinTransmit() { @@ -201,8 +199,5 @@ static void memFree(CanardInstance* const canard, void* const pointer) { (void) canard; o1heapFree(Cyphal::my_allocator, pointer); } -static uint32_t getCurrentMicroseconds() { - return HAL_GetTick(); -} } // namespace cyphal diff --git a/Cyphal/cyphal.hpp b/Cyphal/cyphal.hpp index accfdbd..f772b10 100644 --- a/Cyphal/cyphal.hpp +++ b/Cyphal/cyphal.hpp @@ -9,6 +9,7 @@ #include "cyphal_subscribers.hpp" #include "cyphal_registers.hpp" #include "cyphal_publishers.hpp" +#include "platform_specific.h" #include "canard.h" #include "o1heap.h" #include "uavcan/node/GetInfo_1_0.h" diff --git a/Cyphal/cyphal_publishers.cpp b/Cyphal/cyphal_publishers.cpp index f19c511..279ca8d 100644 --- a/Cyphal/cyphal_publishers.cpp +++ b/Cyphal/cyphal_publishers.cpp @@ -4,7 +4,6 @@ #include "cyphal_publishers.hpp" #include "cyphal.hpp" -#include "main.h" #include "storage.h" namespace cyphal { @@ -101,7 +100,7 @@ size_t PortListPublisher::uavcan_node_port_List_1_0_create() { } void PortListPublisher::publish() { - auto crnt_time_ms = HAL_GetTick(); + auto crnt_time_ms = platformSpecificGetTimeMs(); if (crnt_time_ms < next_pub_time_ms && !driver->ports_updated) { return; } diff --git a/Cyphal/cyphal_subscribers.cpp b/Cyphal/cyphal_subscribers.cpp index 9a70ca0..33fa72d 100644 --- a/Cyphal/cyphal_subscribers.cpp +++ b/Cyphal/cyphal_subscribers.cpp @@ -4,10 +4,10 @@ #include "cyphal_subscribers.hpp" #include "cyphal.hpp" -#include "main.h" #include "params.hpp" #include "algorithms.hpp" #include "storage.h" +#include "platform_specific.h" #ifndef GIT_HASH #define GIT_HASH 0xBADC0FFEE000 @@ -56,24 +56,7 @@ void NodeGetInfoSubscriber::init() { get_info_response.hardware_version.minor = hw_version.minor; get_info_response.certificate_of_authenticity.count = 0; - auto uid_u32 = HAL_GetUIDw0(); - get_info_response.unique_id[0] = uid_u32 & 0xFF; - get_info_response.unique_id[1] = (uid_u32 >> 8) & 0xFF; - get_info_response.unique_id[2] = (uid_u32 >> 16) & 0xFF; - get_info_response.unique_id[3] = (uid_u32 >> 24) & 0xFF; - - uid_u32 = HAL_GetUIDw1(); - get_info_response.unique_id[4] = uid_u32 & 0xFF; - get_info_response.unique_id[5] = (uid_u32 >> 8) & 0xFF; - get_info_response.unique_id[6] = (uid_u32 >> 16) & 0xFF; - get_info_response.unique_id[7] = (uid_u32 >> 24) & 0xFF; - - uid_u32 = HAL_GetUIDw2(); - get_info_response.unique_id[8] = uid_u32 & 0xFF; - get_info_response.unique_id[9] = (uid_u32 >> 8) & 0xFF; - get_info_response.unique_id[10] = (uid_u32 >> 16) & 0xFF; - get_info_response.unique_id[11] = (uid_u32 >> 24) & 0xFF; - + platformSpecificReadUniqueID(get_info_response.unique_id); updateNodeName(); } @@ -135,8 +118,7 @@ void ExecuteCommandSubscriber::callback(const CanardRxTransfer& transfer) { switch (msg.command) { case uavcan_node_ExecuteCommand_Request_1_0_COMMAND_RESTART: - HAL_NVIC_SystemReset(); - cmd_response.status = uavcan_node_ExecuteCommand_Response_1_0_STATUS_SUCCESS; + cmd_response.status = platformSpecificRequestRestart() ? 0 : 1; break; case uavcan_node_ExecuteCommand_Request_1_0_COMMAND_STORE_PERSISTENT_STATES: diff --git a/Cyphal/platform_specific.h b/Cyphal/platform_specific.h new file mode 100644 index 0000000..2e7e74e --- /dev/null +++ b/Cyphal/platform_specific.h @@ -0,0 +1,41 @@ +/* + * Copyright (C) 2024 Dmitry Ponomarev + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. + */ + +#ifndef CYPHAL_PLATFORM_SPECIFIC_H_ +#define CYPHAL_PLATFORM_SPECIFIC_H_ + +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @return the time in milliseconds since the application started. + * @note This function must be provided by a user! + */ +uint32_t platformSpecificGetTimeMs(); + +/** + * @return whether the request will be processed + * True - the application will be restarted soon. + * False - the restarted is not supported or can't be handled at the moment. + * @note Implementation is recommended, but optional. + */ +bool platformSpecificRequestRestart(); + +/** + * @param[out] out_id - hardware Unique ID + * @note Implementation is recommended, but optional. + */ +void platformSpecificReadUniqueID(uint8_t out_uid[16]); + +#ifdef __cplusplus +} +#endif + +#endif // CYPHAL_PLATFORM_SPECIFIC_H_ diff --git a/Cyphal/weak.cpp b/Cyphal/weak.cpp index 6b68f87..6eeba40 100644 --- a/Cyphal/weak.cpp +++ b/Cyphal/weak.cpp @@ -2,11 +2,13 @@ /// Copyright (c) 2022 Dmitry Ponomarev. /// Author: Dmitry Ponomarev -#include +#include "platform_specific.h" +#include -/// Functions below are auxiliary. -/// You may provide their implementation outside if you need. -__attribute__ ((weak)) uint32_t HAL_GetUIDw0() { return 0; } -__attribute__ ((weak)) uint32_t HAL_GetUIDw1() { return 0; } -__attribute__ ((weak)) uint32_t HAL_GetUIDw2() { return 0; } -__attribute__ ((weak)) void HAL_NVIC_SystemReset() { } +__attribute__((weak)) bool platformSpecificRequestRestart() { + return false; // because not implemented +} + +__attribute__((weak)) void platformSpecificReadUniqueID(uint8_t out_uid[16]) { + memset(out_uid, 0x00, 16); +} diff --git a/Makefile b/Makefile index d7fe87c..c6d0145 100644 --- a/Makefile +++ b/Makefile @@ -2,6 +2,9 @@ # Distributed under the MIT License, available in the file LICENSE. # Author: Dmitry Ponomarev +ROOT_DIR:=$(shell dirname $(realpath $(firstword $(MAKEFILE_LIST)))) +LIBPARAMS_DIR:=${ROOT_DIR}/Libs/libparams + all: ubuntu_minimal ubuntu_publisher_example define build_example @@ -22,6 +25,10 @@ generage_dsdl: mkdir -p build/nunavut_out ./scripts/nnvg_generate_c_headers.sh build/nunavut_out +clone_dependencies: + mkdir -p build + if [ ! -d "${LIBPARAMS_DIR}" ]; then git clone --depth 1 --branch v0.8.4 https://github.com/PonomarevDA/libparams.git ${LIBPARAMS_DIR}; fi + clean: rm -rf build/examples/ diff --git a/Udral/actuator.cpp b/Udral/actuator.cpp index ae3fb60..d3e0b5b 100644 --- a/Udral/actuator.cpp +++ b/Udral/actuator.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "actuator.hpp" -#include "main.h" #include "params.hpp" namespace cyphal { @@ -61,7 +60,7 @@ int8_t ReadinessSubscriber::init() { } uint8_t ReadinessSubscriber::get_readiness() { - if (_last_recv_time_ms == 0 || HAL_GetTick() > _last_recv_time_ms + 500) { + if (_last_recv_time_ms == 0 || platformSpecificGetTimeMs() > _last_recv_time_ms + 500) { return reg_udral_service_common_Readiness_0_1_SLEEP; } @@ -72,7 +71,7 @@ void ReadinessSubscriber::callback(const CanardRxTransfer& transfer) { auto payload = static_cast(transfer.payload); size_t payload_len = transfer.payload_size; reg_udral_service_common_Readiness_0_1_deserialize_(&msg, payload, &payload_len); - _last_recv_time_ms = HAL_GetTick(); + _last_recv_time_ms = platformSpecificGetTimeMs(); } } // namespace cyphal diff --git a/Udral/airspeed.cpp b/Udral/airspeed.cpp index 5068051..c6a50b6 100644 --- a/Udral/airspeed.cpp +++ b/Udral/airspeed.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "airspeed.hpp" -#include "main.h" #include "params.hpp" namespace cyphal { diff --git a/Udral/barometer.cpp b/Udral/barometer.cpp index e54f849..95971d3 100644 --- a/Udral/barometer.cpp +++ b/Udral/barometer.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "barometer.hpp" -#include "main.h" #include "cyphal.hpp" #include "params.hpp" diff --git a/Udral/battery.cpp b/Udral/battery.cpp index a91a466..ea02db7 100644 --- a/Udral/battery.cpp +++ b/Udral/battery.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "battery.hpp" -#include "main.h" #include "params.hpp" #define WH_TO_JOULE 3600 @@ -16,7 +15,7 @@ void UdralBatteryPublisher::set_nominal_data(float design_capacity_ah, uint64_t } void UdralBatteryPublisher::publish(float voltage, float current, float temperature_kelvin, float full_capacity_ah, float remaining_capacity_ah) { - uint32_t crnt_time_ms = HAL_GetTick(); + uint32_t crnt_time_ms = platformSpecificGetTimeMs(); if (crnt_time_ms > _next_source_pub_time_ms) { _next_source_pub_time_ms = crnt_time_ms + 10; diff --git a/Udral/imu.cpp b/Udral/imu.cpp index 82a5620..b7683de 100644 --- a/Udral/imu.cpp +++ b/Udral/imu.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "imu.hpp" -#include "main.h" #include "params.hpp" namespace cyphal { diff --git a/Udral/rangefinder.cpp b/Udral/rangefinder.cpp index 3e28c6a..c6536d5 100644 --- a/Udral/rangefinder.cpp +++ b/Udral/rangefinder.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "rangefinder.hpp" -#include "main.h" namespace cyphal { diff --git a/Udral/rgbled.cpp b/Udral/rgbled.cpp index 7ce9faf..4c89cd4 100644 --- a/Udral/rgbled.cpp +++ b/Udral/rgbled.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "rgbled.hpp" -#include "main.h" #include "params.hpp" namespace cyphal { @@ -35,7 +34,7 @@ void HighColorSubscriber::callback(const CanardRxTransfer& transfer) { auto payload = static_cast(transfer.payload); size_t payload_len = transfer.payload_size; reg_udral_physics_optics_HighColor_0_1_deserialize_(&_msg, payload, &payload_len); - _last_recv_ts_ms = HAL_GetTick(); + _last_recv_ts_ms = platformSpecificGetTimeMs(); } } // namespace cyphal diff --git a/examples/main.h b/examples/_main.h similarity index 66% rename from examples/main.h rename to examples/_main.h index 204a3b4..c354ebc 100644 --- a/examples/main.h +++ b/examples/_main.h @@ -7,10 +7,4 @@ #include -uint32_t HAL_GetTick(); -uint32_t HAL_GetUIDw0(); -uint32_t HAL_GetUIDw1(); -uint32_t HAL_GetUIDw2(); -void HAL_NVIC_SystemReset(); - #endif // UBUNTU_MAIN_H_ diff --git a/examples/ubuntu_minimal/main.cpp b/examples/ubuntu_minimal/main.cpp index c2ae15d..27aab8b 100644 --- a/examples/ubuntu_minimal/main.cpp +++ b/examples/ubuntu_minimal/main.cpp @@ -7,7 +7,7 @@ #include #include -uint32_t HAL_GetTick() { +uint32_t platformSpecificGetTimeMs() { static auto time_start = std::chrono::steady_clock::now(); auto time_now = std::chrono::steady_clock::now(); auto elapsed_time_ms = std::chrono::duration_cast(time_now - time_start).count(); diff --git a/examples/ubuntu_minimal/main.h b/examples/ubuntu_minimal/main.h index 7a3af63..e97c0d0 100644 --- a/examples/ubuntu_minimal/main.h +++ b/examples/ubuntu_minimal/main.h @@ -5,11 +5,8 @@ #ifndef UBUNTU_MAIN_H_ #define UBUNTU_MAIN_H_ - -uint32_t HAL_GetTick(); uint32_t HAL_GetUIDw0(); uint32_t HAL_GetUIDw1(); uint32_t HAL_GetUIDw2(); -void HAL_NVIC_SystemReset(); #endif // UBUNTU_MAIN_H_ diff --git a/examples/ubuntu_publisher_example/application.cpp b/examples/ubuntu_publisher_example/application.cpp index 2c980fe..061997e 100644 --- a/examples/ubuntu_publisher_example/application.cpp +++ b/examples/ubuntu_publisher_example/application.cpp @@ -7,12 +7,11 @@ #include #include #include "reg/udral/service/actuator/common/Feedback_0_1.h" -#include "main.h" #include "params.hpp" void FeedbackPublisher::process() { static uint32_t prev_pub_time_ms = 1000; - uint32_t crnt_time_ms = HAL_GetTick(); + uint32_t crnt_time_ms = platformSpecificGetTimeMs(); if (crnt_time_ms < prev_pub_time_ms + 1000) { return; } diff --git a/examples/ubuntu_publisher_example/main.cpp b/examples/ubuntu_publisher_example/main.cpp index b09ea2d..3388161 100644 --- a/examples/ubuntu_publisher_example/main.cpp +++ b/examples/ubuntu_publisher_example/main.cpp @@ -7,7 +7,7 @@ #include #include -uint32_t HAL_GetTick() { +uint32_t platformSpecificGetTimeMs() { static auto time_start = std::chrono::steady_clock::now(); auto time_now = std::chrono::steady_clock::now(); auto elapsed_time_ms = std::chrono::duration_cast(time_now - time_start).count(); diff --git a/platform_specific/bxcan/cyphal_transport_can.cpp b/platform_specific/bxcan/cyphal_transport_can.cpp index d6b2d6c..4dee746 100644 --- a/platform_specific/bxcan/cyphal_transport_can.cpp +++ b/platform_specific/bxcan/cyphal_transport_can.cpp @@ -6,6 +6,7 @@ #include #include "bxcan.h" #include "main.h" +#include "platform_specific.h" namespace cyphal { @@ -42,7 +43,7 @@ bool CyphalTransportCan::transmit(const CanardTxQueueItem* transfer) { return false; } - const uint64_t current_time = HAL_GetTick() * 1000; + const uint64_t current_time = platformSpecificGetTimeMs() * 1000; const uint64_t deadline = current_time + 100 * 1000; const uint8_t iface_index = 0; diff --git a/platform_specific/socketcan/cyphal_transport_can.cpp b/platform_specific/socketcan/cyphal_transport_can.cpp index 6d2cb55..226c8d3 100644 --- a/platform_specific/socketcan/cyphal_transport_can.cpp +++ b/platform_specific/socketcan/cyphal_transport_can.cpp @@ -5,7 +5,7 @@ #include "cyphal_transport_can.hpp" #include #include "socketcan.h" -#include "main.h" +#include "platform_specific.h" namespace cyphal { @@ -47,7 +47,7 @@ bool CyphalTransportCan::transmit(const CanardTxQueueItem* transfer) { return false; } - const uint64_t current_time_us = HAL_GetTick() * 1000; + const uint64_t current_time_us = platformSpecificGetTimeMs() * 1000; int16_t res = socketcanPush(_instance, &transfer->frame, current_time_us); return (res > 0) ? true : false; } diff --git a/zubax/compact_feedback.cpp b/zubax/compact_feedback.cpp index 557b6c0..8578c2c 100644 --- a/zubax/compact_feedback.cpp +++ b/zubax/compact_feedback.cpp @@ -3,7 +3,6 @@ /// Author: Dmitry Ponomarev #include "compact_feedback.hpp" -#include "main.h" #include "params.hpp" namespace zubax::telega {