Skip to content
Closed
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
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -39,3 +39,8 @@ _build
# Coverage info file
lcov.info
test_coverage/

# cmake cache.
.cache/
build/
build-*/
49 changes: 49 additions & 0 deletions .vscode/tasks.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
{
"version": "2.0.0",
"tasks": [
{
"label": "CMake Configure Tests (Debug)",
"type": "shell",
"command": "cmake",
"args": [
"-S",
".",
"-B",
"build-cmake-tests-debug",
"-DCMAKE_BUILD_TYPE=Debug",
"-DDCCEX_BUILD_TESTS=ON"
],
"group": "build"
},
{
"label": "CMake Build Tests (Debug)",
"type": "shell",
"command": "cmake",
"args": [
"--build",
"build-cmake-tests-debug",
"-j"
],
"dependsOn": "CMake Configure Tests (Debug)",
"group": {
"kind": "build",
"isDefault": true
}
},
{
"label": "CMake Run Tests (Debug)",
"type": "shell",
"command": "ctest",
"args": [
"--test-dir",
"build-cmake-tests-debug",
"--output-on-failure"
],
"dependsOn": "CMake Build Tests (Debug)",
"group": {
"kind": "test",
"isDefault": true
}
}
]
}
68 changes: 68 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
cmake_minimum_required(VERSION 3.11)

# Detect ESP-IDF build
if(DEFINED ENV{IDF_PATH})
file(GLOB_RECURSE SRC src/*.cpp)
set(COMPONENT_SRCS ${SRC}) # Add all your source files here
set(COMPONENT_ADD_INCLUDEDIRS src)
set(COMPONENT_PRIV_INCLUDEDIRS "")
set(COMPONENT_REQUIRES "")
set(COMPONENT_PRIV_REQUIRES "")
register_component()
else()
include(FetchContent)
list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/cmake)

project(DCCEXProtocol LANGUAGES CXX)

option(DCCEX_BUILD_TESTS "Build native GoogleTest test target" ON)

file(GLOB_RECURSE SRC src/*.cpp)
add_library(DCCEXProtocol STATIC ${SRC})
add_library(DCCEX::Protocol ALIAS DCCEXProtocol)

# Stuck at C++11
target_compile_options(DCCEXProtocol PRIVATE -std=c++11)

# Don't bother users with warnings by setting 'SYSTEM'
if(CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME)
target_include_directories(DCCEXProtocol PUBLIC src)
else()
target_include_directories(DCCEXProtocol SYSTEM PUBLIC src)
endif()

foreach(FILE ${SRC})
message(${FILE})
endforeach()

source_group(TREE ${CMAKE_CURRENT_SOURCE_DIR} FILES ${SRC})

if(DCCEX_BUILD_TESTS)
include(CTest)
enable_testing()

FetchContent_Declare(
googletest
URL https://github.com/google/googletest/archive/refs/tags/v1.17.0.zip
)
FetchContent_MakeAvailable(googletest)

file(GLOB_RECURSE TEST_SOURCES CONFIGURE_DEPENDS test/*.cpp)
add_executable(DCCEXProtocolTests ${TEST_SOURCES})

target_compile_definitions(DCCEXProtocolTests PRIVATE NATIVE_TESTING)
target_include_directories(DCCEXProtocolTests PRIVATE test/mocks test/setup)
target_link_libraries(DCCEXProtocolTests PRIVATE DCCEXProtocol GTest::gtest GTest::gmock)

include(GoogleTest)
gtest_discover_tests(DCCEXProtocolTests)

add_custom_target(check
COMMAND ${CMAKE_CTEST_COMMAND} --output-on-failure
DEPENDS DCCEXProtocolTests
USES_TERMINAL
)

add_custom_target(run-tests DEPENDS check)
endif()
endif()
59 changes: 56 additions & 3 deletions examples/DCCEXProtocol_Basic/DCCEXProtocol_Basic.ino
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,11 @@
// Peter Akers (Flash62au), Peter Cole (PeteGSX) and Chris Harlow (UKBloke), 2023
// Luca Dentella, 2020

#include <Arduino.h>
#include <DCCEXProtocol.h>
#include <WiFi.h>
#include <stdarg.h>
#include <stdio.h>


// If we haven't got a custom config.h, use the example
Expand All @@ -19,9 +22,59 @@
#include "config.example.h"
#endif

using namespace DCCExController;

class ArduinoDCCMillis : public DCCMillis {
public:
unsigned long millis() const override { return ::millis(); }
};

class ArduinoDCCStream : public DCCStream {
public:
explicit ArduinoDCCStream(Stream &stream) : _stream(stream) {}

int available() const override {
return const_cast<Stream &>(_stream).available();
}

int read() override { return _stream.read(); }

size_t write(const uint8_t *buffer, size_t size) override {
return _stream.write(buffer, size);
}

void flush() override { _stream.flush(); }

void println(const char *format, ...) override {
char message[160];
va_list args;
va_start(args, format);
vsnprintf(message, sizeof(message), format, args);
va_end(args);
_stream.println(message);
}

void print(const char *format, ...) override {
char message[160];
va_list args;
va_start(args, format);
vsnprintf(message, sizeof(message), format, args);
va_end(args);
_stream.print(message);
}

private:
Stream &_stream;
};



// Global objects
WiFiClient client;
DCCEXProtocol dccexProtocol;
ArduinoDCCMillis dccMillis;
ArduinoDCCStream dccTransport(client);
ArduinoDCCStream dccLog(Serial);
DCCEXProtocol dccexProtocol(&dccMillis);

void setup() {

Expand All @@ -46,12 +99,12 @@ void setup() {
}
Serial.println("Connected to the server");

dccexProtocol.setLogStream(&Serial);
dccexProtocol.setLogStream(&dccLog);

dccexProtocol.enableHeartbeat();

// Pass the communication to wiThrottleProtocol
dccexProtocol.connect(&client);
dccexProtocol.connect(&dccTransport);
Serial.println("DCC-EX connected");
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
//
// Peter Cole (PeteGSX), 2026

#include <Arduino.h>
#include <DCCEXProtocol.h>
#include <WiFi.h>

Expand All @@ -16,6 +17,52 @@
#include "config.example.h"
#endif

using namespace DCCExController;

class ArduinoDCCMillis : public DCCMillis {
public:
unsigned long millis() const override { return ::millis(); }
};

class ArduinoDCCStream : public DCCStream {
public:
explicit ArduinoDCCStream(Stream &stream) : _stream(stream) {}

int available() const override {
return const_cast<Stream &>(_stream).available();
}

int read() override { return _stream.read(); }

size_t write(const uint8_t *buffer, size_t size) override {
return _stream.write(buffer, size);
}

void flush() override { _stream.flush(); }

void println(const char *format, ...) override {
char message[160];
va_list args;
va_start(args, format);
vsnprintf(message, sizeof(message), format, args);
va_end(args);
_stream.println(message);
}

void print(const char *format, ...) override {
char message[160];
va_list args;
va_start(args, format);
vsnprintf(message, sizeof(message), format, args);
va_end(args);
_stream.print(message);
}

private:
Stream &_stream;
};


// Delegate class
class MyDelegate : public DCCEXProtocolDelegate {

Expand Down Expand Up @@ -47,7 +94,10 @@ CSConsist *csConsist = nullptr;

// Global objects
WiFiClient client;
DCCEXProtocol dccexProtocol;
ArduinoDCCMillis dccMillis;
ArduinoDCCStream dccTransport(client);
ArduinoDCCStream dccLog(Serial);
DCCEXProtocol dccexProtocol(&dccMillis);
MyDelegate myDelegate;

void setup() {
Expand All @@ -74,15 +124,15 @@ void setup() {
Serial.println("Connected to the server");

// Logging on Serial
dccexProtocol.setLogStream(&Serial);
dccexProtocol.setLogStream(&dccLog);

// Pass the delegate instance to wiThrottleProtocol
dccexProtocol.setDelegate(&myDelegate);

dccexProtocol.enableHeartbeat();

// Pass the communication to wiThrottleProtocol
dccexProtocol.connect(&client);
dccexProtocol.connect(&dccTransport);
Serial.println("DCC-EX connected");

// Turn track power on for locos to move
Expand All @@ -95,7 +145,7 @@ void loop() {
// parse incoming messages
dccexProtocol.check();

if (!consist) {
if (!csConsist) {
// Create a new CSConsist for loco address 11 in the normal direction of travel, and replicate functions across the
// consist.
// By default, functions will only affect the lead loco
Expand Down
Loading
Loading