Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 6 additions & 4 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
cmake_minimum_required(VERSION 3.16)
project("AOG-TaskController")
set(PROJECT_VERSION_MAJOR 1)
set(PROJECT_VERSION_MINOR 3)
set(PROJECT_VERSION_PATCH 3)
set(PROJECT_VERSION_MINOR 5)
set(PROJECT_VERSION_PATCH 0)
set(PROJECT_VERSION
"${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}.${PROJECT_VERSION_PATCH}"
)
Expand Down Expand Up @@ -61,8 +61,8 @@ FetchContent_MakeAvailable(Boost)

FetchContent_Declare(
isobus
GIT_REPOSITORY https://github.com/Open-Agriculture/AgIsoStack-plus-plus.git
GIT_TAG 869430f0347188e0f8dc0740d6c6a1cfcce37706
GIT_REPOSITORY https://github.com/gunicsba/AgIsoStack-plus-plus.git
Comment thread
gunicsba marked this conversation as resolved.
GIT_TAG d4d36dd6f15af6c6f6218317572025a1ffec6883
DOWNLOAD_EXTRACT_TIMESTAMP TRUE)
Comment thread
gunicsba marked this conversation as resolved.
FetchContent_MakeAvailable(isobus)

Expand All @@ -73,11 +73,13 @@ FetchContent_Declare(
FetchContent_MakeAvailable(json)

include(FetchContent)
set(CMAKE_POLICY_VERSION_MINIMUM 3.5)
FetchContent_Declare(
git_version
GIT_REPOSITORY https://github.com/andrew-hardin/cmake-git-version-tracking.git
GIT_TAG 904dbda1336ba4b9a1415a68d5f203f576b696bb)
FetchContent_MakeAvailable(git_version)
unset(CMAKE_POLICY_VERSION_MINIMUM)

find_package(Threads REQUIRED)

Expand Down
1 change: 1 addition & 0 deletions include/task_controller.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ class MyTCServer : public isobus::TaskControllerServer
bool get_is_enough_memory_available(std::uint32_t) override;
void identify_task_controller(std::uint8_t) override;
void on_client_timeout(std::shared_ptr<isobus::ControlFunction> partner) override;
void on_client_version_received(std::shared_ptr<isobus::ControlFunction> clientControlFunction, std::uint8_t version) override;
void on_process_data_acknowledge(std::shared_ptr<isobus::ControlFunction> partner, std::uint16_t dataDescriptionIndex, std::uint16_t elementNumber, std::uint8_t errorCodesFromClient, ProcessDataCommands processDataCommand) override;
bool on_value_command(std::shared_ptr<isobus::ControlFunction> partner,
std::uint16_t dataDescriptionIndex,
Expand Down
31 changes: 27 additions & 4 deletions src/task_controller.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,22 @@
#include <fstream>
#include <iostream>

// Sanitize a string for use as a filename by replacing invalid characters with underscores
static std::string sanitize_filename(const std::string &input)
{
std::string result = input;
// Characters invalid on Windows (and / is invalid on POSIX too)
const std::string invalid_chars = "\\/*:?\"<>|";
for (char &c : result)
{
if (invalid_chars.find(c) != std::string::npos)
{
c = '_';
}
}
return result;
}

void ClientState::set_number_of_sections(std::uint8_t number)
{
numberOfSections = number;
Expand Down Expand Up @@ -295,11 +311,11 @@ bool MyTCServer::activate_object_pool(std::shared_ptr<isobus::ControlFunction> p

auto labelBytes = deviceObject->get_localization_label();
std::string label(reinterpret_cast<const char *>(labelBytes.data()), labelBytes.size());
// trim at first occurrence of null or ETX (0x03)
auto it = std::find_if(label.begin(), label.end(), [](char c) { return c == '\0' || static_cast<unsigned char>(c) == 0x03; });
// trim at first non-printable character (control chars, DEL, etc.)
auto it = std::find_if(label.begin(), label.end(), [](unsigned char c) { return c < 0x20 || c >= 0x7F; });
label.erase(it, label.end());

auto fileName = std::to_string(partnerCF->get_NAME().get_full_name()) + "\\" + label + ".ddop";
auto fileName = std::to_string(partnerCF->get_NAME().get_full_name()) + "/" + sanitize_filename(label) + ".ddop";
std::vector<std::uint8_t> binaryPool;
if (state.get_pool().generate_binary_object_pool(binaryPool))
{
Expand Down Expand Up @@ -420,6 +436,12 @@ void MyTCServer::on_client_timeout(std::shared_ptr<isobus::ControlFunction> part
clients.erase(partner);
}

void MyTCServer::on_client_version_received(std::shared_ptr<isobus::ControlFunction> clientControlFunction, std::uint8_t version)
{
std::cout << "[" << get_timestamp() << "] [TC Server] Client " << clientControlFunction->get_NAME().get_full_name()
<< " reported TC version " << static_cast<int>(version) << std::endl;
}

void MyTCServer::on_process_data_acknowledge(std::shared_ptr<isobus::ControlFunction> partner,
std::uint16_t dataDescriptionIndex,
std::uint16_t elementNumber,
Expand Down Expand Up @@ -502,7 +524,8 @@ void MyTCServer::request_measurement_commands()
{
for (auto &client : clients)
{
if (!client.second.are_measurement_commands_sent())
// Skip clients with 0 sections (e.g. tractors) - sending measurement commands to a tractor ECU can cause unexpected behavior
if (!client.second.are_measurement_commands_sent() && client.second.get_number_of_sections() > 0)
{
// Find all actual (condensed) work state DDIs and request them to trigger "On Change" and "Time Interval"
for (std::uint32_t i = 0; i < client.second.get_pool().size(); i++)
Expand Down
Loading