Skip to content

Commit

Permalink
Add single write command to serial hub
Browse files Browse the repository at this point in the history
Signed-off-by: Evgeny Petrov <[email protected]>
  • Loading branch information
golovasteek committed Feb 9, 2024
1 parent 14d26f4 commit 5c97bbb
Show file tree
Hide file tree
Showing 6 changed files with 75 additions and 12 deletions.
24 changes: 24 additions & 0 deletions interfaces/serial_communication_hub.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,30 @@ cmds:
description: Status code of the transfer
type: string
$ref: /serial_comm_hub_requests#/StatusCodeEnum
modbus_write_signle_register:
description: >-
Send a Modbus RTU 'write single register' command via serial interface
to the target hardware. (return value: response)
arguments:
target_device_id:
description: ID (1 byte) of the device to send the commands to
type: integer
minimum: 0
maximum: 255
register_address:
description: Address of the register to write to (16 bit address)
type: integer
minimum: 0
maximum: 65535
data:
description: Data content to be written to the above selected register
type: integer
minimum: 0
maximum: 65535
result:
description: Status code of the transfer
type: string
$ref: /serial_comm_hub_requests#/StatusCodeEnum
nonstd_write:
description: >-
Non standard mode to write registers in read discrete input mode
Expand Down
2 changes: 1 addition & 1 deletion modules/SerialCommHub/SerialCommHub.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,8 @@ class SerialCommHub : public Everest::ModuleBase {
SerialCommHub(const ModuleInfo& info, std::unique_ptr<serial_communication_hubImplBase> p_main, Conf& config) :
ModuleBase(info), p_main(std::move(p_main)), config(config){};

const Conf& config;
const std::unique_ptr<serial_communication_hubImplBase> p_main;
const Conf& config;

// ev@1fce4c5e-0ab8-41bb-90f7-14277703d2ac:v1
// insert your public definitions here
Expand Down
44 changes: 38 additions & 6 deletions modules/SerialCommHub/main/serial_communication_hubImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,9 @@ serial_communication_hubImpl::handle_modbus_read_holding_registers(int& target_d
auto retry_counter = this->num_resends_on_error;
while (retry_counter > 0) {

EVLOG_debug << fmt::format("Try {} Call modbus_client->read_holding_register(id {} addr {} len {})",
(int)retry_counter, (uint8_t)target_device_id, (uint16_t)first_register_address,
(uint16_t)num_registers_to_read);
// EVLOG_info << fmt::format("Try {} Call modbus_client->read_holding_register(id {} addr {} len {})",
// (int)retry_counter, (uint8_t)target_device_id,
// (uint16_t)first_register_address, (uint16_t)num_registers_to_read);

response = modbus.txrx(target_device_id, tiny_modbus::FunctionCode::READ_MULTIPLE_HOLDING_REGISTERS,
first_register_address, num_registers_to_read, config.max_packet_size);
Expand Down Expand Up @@ -99,9 +99,9 @@ serial_communication_hubImpl::handle_modbus_read_input_registers(int& target_dev
uint8_t retry_counter{this->num_resends_on_error};
while (retry_counter-- > 0) {

EVLOG_debug << fmt::format("Try {} Call modbus_client->read_input_register(id {} addr {} len {})",
(int)retry_counter, (uint8_t)target_device_id, (uint16_t)first_register_address,
(uint16_t)num_registers_to_read);
// EVLOG_info << fmt::format("Try {} Call modbus_client->read_input_register(id {} addr {} len {})",
// (int)retry_counter, (uint8_t)target_device_id,
// (uint16_t)first_register_address, (uint16_t)num_registers_to_read);

response = modbus.txrx(target_device_id, tiny_modbus::FunctionCode::READ_INPUT_REGISTERS,
first_register_address, num_registers_to_read, config.max_packet_size);
Expand Down Expand Up @@ -158,6 +158,38 @@ types::serial_comm_hub_requests::StatusCodeEnum serial_communication_hubImpl::ha
}
}

types::serial_comm_hub_requests::StatusCodeEnum
serial_communication_hubImpl::handle_modbus_write_signle_register(int& target_device_id, int& register_address,
int& data) {
types::serial_comm_hub_requests::Result result;
std::vector<uint16_t> response;

{
std::scoped_lock lock(serial_mutex);

uint8_t retry_counter{this->num_resends_on_error};
while (retry_counter-- > 0) {

EVLOG_debug << fmt::format("Try {} Call modbus_client->write_single_register(id {} addr {} data {})",
(int)retry_counter, (uint8_t)target_device_id, (uint16_t)register_address,
(uint16_t)data);

response = modbus.txrx(target_device_id, tiny_modbus::FunctionCode::WRITE_SINGLE_HOLDING_REGISTER,
register_address, 1, true, {static_cast<uint16_t>(data)});
if (response.size() > 0) {
break;
}
}
}
EVLOG_debug << fmt::format("Done writing");
// process response
if (response.size() > 0) {
return types::serial_comm_hub_requests::StatusCodeEnum::Success;
} else {
return types::serial_comm_hub_requests::StatusCodeEnum::Error;
}
}

void serial_communication_hubImpl::handle_nonstd_write(int& target_device_id, int& first_register_address,
int& num_registers_to_read) {
}
Expand Down
3 changes: 2 additions & 1 deletion modules/SerialCommHub/main/serial_communication_hubImpl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@ struct Conf {
std::string serial_port;
int baudrate;
int parity;
int rs485_direction_gpio;
bool ignore_echo;
std::string rxtx_gpio_chip;
int rxtx_gpio_line;
Expand Down Expand Up @@ -60,6 +59,8 @@ class serial_communication_hubImpl : public serial_communication_hubImplBase {
virtual types::serial_comm_hub_requests::StatusCodeEnum
handle_modbus_write_multiple_registers(int& target_device_id, int& first_register_address,
types::serial_comm_hub_requests::VectorUint16& data_raw) override;
virtual types::serial_comm_hub_requests::StatusCodeEnum
handle_modbus_write_signle_register(int& target_device_id, int& register_address, int& data) override;
virtual void handle_nonstd_write(int& target_device_id, int& first_register_address,
int& num_registers_to_read) override;
virtual types::serial_comm_hub_requests::Result
Expand Down
13 changes: 9 additions & 4 deletions modules/SerialCommHub/tiny_modbus_rtu.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -307,7 +307,6 @@ int TinyModbusRTU::read_reply(uint8_t* rxbuf, int rxbuf_len) {
int bytes_read = read(fd, rxbuf + bytes_read_total, rxbuf_len - bytes_read_total);
if (bytes_read > 0) {
bytes_read_total += bytes_read;
EVLOG_debug << "RECVD: " << hexdump(rxbuf, bytes_read_total);
}
}
}
Expand Down Expand Up @@ -370,7 +369,10 @@ std::vector<uint16_t> TinyModbusRTU::txrx_impl(uint8_t device_address, FunctionC
first_register_address = htobe16(first_register_address);
register_quantity = htobe16(register_quantity);
memcpy(req.get() + REQ_TX_FIRST_REGISTER_ADDR_POS, &first_register_address, 2);
memcpy(req.get() + REQ_TX_QUANTITY_POS, &register_quantity, 2);
if (function != FunctionCode::WRITE_SINGLE_HOLDING_REGISTER) {
// For functioncode 6 we do not transmit quantity
memcpy(req.get() + REQ_TX_QUANTITY_POS, &register_quantity, 2);
}

if (function == FunctionCode::WRITE_MULTIPLE_HOLDING_REGISTERS) {
// write byte count
Expand All @@ -383,11 +385,14 @@ std::vector<uint16_t> TinyModbusRTU::txrx_impl(uint8_t device_address, FunctionC
i += 2;
}
}

if (function == FunctionCode::WRITE_SINGLE_HOLDING_REGISTER) {
memcmp(req.get() + REQ_TX_SINGLE_REG_PAYLOAD_POS, &request[0], 2);

Check warning on line 390 in modules/SerialCommHub/tiny_modbus_rtu.cpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/SerialCommHub/tiny_modbus_rtu.cpp#L390

'req.get()' is of type 'void *'. When using void pointers in calculations, the behaviour is undefined.

Check warning on line 390 in modules/SerialCommHub/tiny_modbus_rtu.cpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/SerialCommHub/tiny_modbus_rtu.cpp#L390

Return value of function memcmp() is not used.
}

// set checksum in the last 2 bytes
append_checksum(req.get(), req_len);

EVLOG_debug << "SEND: " << hexdump(req.get(), req_len);

// clear input and output buffer
tcflush(fd, TCIOFLUSH);

Expand Down
1 change: 1 addition & 0 deletions modules/SerialCommHub/tiny_modbus_rtu.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ constexpr int FUNCTION_CODE_POS = 0x01;

constexpr int REQ_TX_FIRST_REGISTER_ADDR_POS = 0x02;
constexpr int REQ_TX_QUANTITY_POS = 0x04;
constexpr int REQ_TX_SINGLE_REG_PAYLOAD_POS = 0x04;

constexpr int REQ_TX_MULTIPLE_REG_BYTE_COUNT_POS = 0x06;

Expand Down

0 comments on commit 5c97bbb

Please sign in to comment.