Skip to content

Commit

Permalink
Merge pull request #3 from ofthedove/bitty-bean
Browse files Browse the repository at this point in the history
Add Bean Features
  • Loading branch information
ryanplusplus authored Nov 20, 2024
2 parents d027e50 + 060d894 commit 467a649
Show file tree
Hide file tree
Showing 9 changed files with 206 additions and 27 deletions.
6 changes: 3 additions & 3 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,11 @@
"type": "cppdbg",
"request": "launch",
"preLaunchTask": "Build",
"program": "${workspaceFolder}/build/home-assistant-bridge_tests",
"args": [],
"program": "${workspaceFolder}/build/arduino-gea3-api_tests",
"args": [ ],
"stopAtEntry": true,
"cwd": "${workspaceFolder}",
"environment": [],
"environment": [ ],
"externalConsole": false,
"linux": {
"MIMode": "gdb"
Expand Down
2 changes: 1 addition & 1 deletion .vscode/tasks.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
{
"label": "Build",
"type": "shell",
"command": "make build/home-assistant-bridge_tests"
"command": "make build/arduino-gea3-api_tests"
}
]
}
16 changes: 16 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,19 @@ Provides a simple interface for sending and receiving GEA3 serial packets.

### `tiny_erd_client`
Provides a simple interface for reading and writing addressable data (ERDs) over a GEA3 serial interface.

## Dev Environment
1. Clone the repo
2. Install Cpputest
3. Run tests with `make test`

### Installing Cpputest on Linux
1. Run `sudo apt install cpputest`.

### Installing Cpputest on MacOS
1. Run `brew install cpputest`
2. Add these lines to `~/.bash_profile` after `eval "$(/opt/homebrew/bin/brew shellenv)"` on macOS:
```
export CPATH="$CPATH:$(brew --prefix)/include"
export LIBRARY_PATH="$LIBRARY_PATH:$(brew --prefix)/lib"
```
29 changes: 25 additions & 4 deletions include/i_tiny_gea3_interface.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,14 @@ typedef struct {
} i_tiny_gea3_interface_t;

typedef struct i_tiny_gea3_interface_api_t {
void (*send)(
bool (*send)(
i_tiny_gea3_interface_t* self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context);

bool (*forward)(
i_tiny_gea3_interface_t* self,
uint8_t destination,
uint8_t payload_length,
Expand All @@ -40,16 +47,30 @@ typedef struct i_tiny_gea3_interface_api_t {
* Send a packet by getting direct access to the internal send buffer (given to
* the client via the provided callback). Sets the source and destination addresses
* of the packet automatically. If the requested payload size is too large then the
* callback will not be invoked.
* callback will not be invoked. Returns false if packet is dropped due to size
* or activity.
*/
static inline bool tiny_gea3_interface_send(
i_tiny_gea3_interface_t* self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context)
{
return self->api->send(self, destination, payload_length, callback, context);
}

/*!
* Send a packet without setting source address
*/
static inline void tiny_gea3_interface_send(
static inline bool tiny_gea3_interface_forward(
i_tiny_gea3_interface_t* self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context)
{
self->api->send(self, destination, payload_length, callback, context);
return self->api->forward(self, destination, payload_length, callback, context);
}

/*!
Expand Down
7 changes: 5 additions & 2 deletions include/tiny_gea3_interface.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ typedef struct {
i_tiny_gea3_interface_t interface;

tiny_event_t on_receive;
tiny_event_subscription_t byte_received_subscfription;
tiny_event_subscription_t byte_received_subscription;
tiny_event_subscription_t byte_sent_subscription;
i_tiny_uart_t* uart;
uint8_t* send_buffer;
Expand All @@ -50,6 +50,8 @@ typedef struct {
bool send_escaped;
bool receive_escaped;
bool stx_received;

bool ignore_destination_address;
} tiny_gea3_interface_t;

/*!
Expand All @@ -64,7 +66,8 @@ void tiny_gea3_interface_init(
uint8_t* receive_buffer,
uint8_t receive_buffer_size,
uint8_t* send_queue_buffer,
size_t send_queue_buffer_size);
size_t send_queue_buffer_size,
bool ignore_destination_address);

/*!
* Run the interface and publish received packets.
Expand Down
2 changes: 1 addition & 1 deletion library.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
"maintainer": true
}
],
"version": "2.0.0",
"version": "3.0.0",
"frameworks": "*",
"platforms": "*",
"export": {
Expand Down
39 changes: 29 additions & 10 deletions src/tiny_gea3_interface.c
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,9 @@ static bool received_packet_has_valid_length(self_t* self)
static bool received_packet_is_addressed_to_me(self_t* self)
{
reinterpret(packet, self->receive_buffer, tiny_gea3_packet_t*);
return (packet->destination == self->address) || (packet->destination == tiny_gea3_broadcast_address);
return (packet->destination == self->address) ||
(packet->destination == tiny_gea3_broadcast_address) ||
(self->ignore_destination_address);
}

static void buffer_received_byte(self_t* self, uint8_t byte)
Expand Down Expand Up @@ -212,7 +214,7 @@ static void populate_send_packet(
packet->destination = destination;
}

static void send_worker(
static bool send_worker(
i_tiny_gea3_interface_t* _self,
uint8_t destination,
uint8_t payload_length,
Expand All @@ -223,13 +225,16 @@ static void send_worker(
reinterpret(self, _self, self_t*);

if(payload_length + send_packet_header_size > self->send_buffer_size) {
return;
return false;
}

if(self->send_in_progress) {
uint8_t buffer[255];
populate_send_packet(self, (tiny_gea3_packet_t*)buffer, destination, payload_length, callback, context, setSourceAddress);
tiny_queue_enqueue(&self->send_queue, buffer, tiny_gea3_packet_overhead + payload_length);
if(!tiny_queue_enqueue(&self->send_queue, buffer, tiny_gea3_packet_overhead + payload_length))
{
return false;
}
}
else {
reinterpret(sendPacket, self->send_buffer, tiny_gea3_packet_t*);
Expand All @@ -238,16 +243,28 @@ static void send_worker(
self->send_in_progress = true;
tiny_uart_send(self->uart, tiny_gea3_stx);
}

return true;
}

static bool send(
i_tiny_gea3_interface_t* _self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context)
{
return send_worker(_self, destination, payload_length, callback, context, true);
}

static void send(
static bool forward(
i_tiny_gea3_interface_t* _self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context)
{
send_worker(_self, destination, payload_length, callback, context, true);
return send_worker(_self, destination, payload_length, callback, context, false);
}

static i_tiny_event_t* on_receive(i_tiny_gea3_interface_t* _self)
Expand All @@ -256,7 +273,7 @@ static i_tiny_event_t* on_receive(i_tiny_gea3_interface_t* _self)
return &self->on_receive.interface;
}

static const i_tiny_gea3_interface_api_t api = { send, on_receive };
static const i_tiny_gea3_interface_api_t api = { send, forward, on_receive };

void tiny_gea3_interface_init(
tiny_gea3_interface_t* self,
Expand All @@ -267,7 +284,8 @@ void tiny_gea3_interface_init(
uint8_t* receive_buffer,
uint8_t receive_buffer_size,
uint8_t* send_queue_buffer,
size_t send_queue_buffer_size)
size_t send_queue_buffer_size,
bool ignore_destination_address)
{
self->interface.api = &api;

Expand All @@ -277,6 +295,7 @@ void tiny_gea3_interface_init(
self->send_buffer_size = send_buffer_size;
self->receive_buffer = receive_buffer;
self->receive_buffer_size = receive_buffer_size;
self->ignore_destination_address = ignore_destination_address;
self->receive_escaped = false;
self->send_in_progress = false;
self->send_escaped = false;
Expand All @@ -288,10 +307,10 @@ void tiny_gea3_interface_init(

tiny_queue_init(&self->send_queue, send_queue_buffer, send_queue_buffer_size);

tiny_event_subscription_init(&self->byte_received_subscfription, self, byte_received);
tiny_event_subscription_init(&self->byte_received_subscription, self, byte_received);
tiny_event_subscription_init(&self->byte_sent_subscription, self, byte_sent);

tiny_event_subscribe(tiny_uart_on_receive(uart), &self->byte_received_subscfription);
tiny_event_subscribe(tiny_uart_on_receive(uart), &self->byte_received_subscription);
tiny_event_subscribe(tiny_uart_on_send_complete(uart), &self->byte_sent_subscription);
}

Expand Down
28 changes: 26 additions & 2 deletions test/src/tiny_gea3_interface_double.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
#include "double/tiny_gea3_interface_double.hpp"
#include "tiny_utils.h"

static void send(
static bool send(
i_tiny_gea3_interface_t* _self,
uint8_t destination,
uint8_t payload_length,
Expand All @@ -26,6 +26,30 @@ static void send(
.withParameter("source", self->packet.source)
.withParameter("destination", self->packet.destination)
.withMemoryBufferParameter("payload", self->packet.payload, payload_length);

return true;
}

static bool forward(
i_tiny_gea3_interface_t* _self,
uint8_t destination,
uint8_t payload_length,
tiny_gea3_interface_send_callback_t callback,
void* context)
{
reinterpret(self, _self, tiny_gea3_interface_double_t*);
self->packet.destination = destination;
self->packet.payload_length = payload_length;
callback(context, &self->packet);

mock()
.actualCall("forward")
.onObject(self)
.withParameter("source", self->packet.source)
.withParameter("destination", self->packet.destination)
.withMemoryBufferParameter("payload", self->packet.payload, payload_length);

return true;
}

static i_tiny_event_t* on_receive(i_tiny_gea3_interface_t* _self)
Expand All @@ -34,7 +58,7 @@ static i_tiny_event_t* on_receive(i_tiny_gea3_interface_t* _self)
return &self->on_receive.interface;
}

static const i_tiny_gea3_interface_api_t api = { send, on_receive };
static const i_tiny_gea3_interface_api_t api = { send, forward, on_receive };

void tiny_gea3_interface_double_init(tiny_gea3_interface_double_t* self, uint8_t address)
{
Expand Down
Loading

0 comments on commit 467a649

Please sign in to comment.