Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Revision 3:b8d920737d9e, committed 2021-09-02
- Comitter:
- ascheeren
- Date:
- Thu Sep 02 14:30:39 2021 +0000
- Parent:
- 1:35fdc7056f66
- Commit message:
- 01
Changed in this revision
| ModbusSlave232.cpp | Show annotated file Show diff for this revision Revisions of this file |
diff -r 35fdc7056f66 -r b8d920737d9e ModbusSlave232.cpp
--- a/ModbusSlave232.cpp Fri Jul 22 09:44:55 2016 +0000
+++ b/ModbusSlave232.cpp Thu Sep 02 14:30:39 2021 +0000
@@ -1,50 +1,50 @@
-/*
+/*
Modified by Afdhal: arduino library so that it can be used on mbed.
-
+
Original message:
- Modbus over serial line - RTU Slave Arduino Sketch
-
+ Modbus over serial line - RTU Slave Arduino Sketch
+
By Juan Pablo Zometa : jpmzometa@gmail.com
http://sites.google.com/site/jpmzometa/
Samuel Marco: sammarcoarmengol@gmail.com
and Andras Tucsni.
-
+
These functions implement functions 3, 6, and 16 (read holding registers,
- preset single register and preset multiple registers) of the
+ preset single register and preset multiple registers) of the
Modbus RTU Protocol, to be used over the Arduino serial connection.
-
+
This implementation DOES NOT fully comply with the Modbus specifications.
-
+
This Arduino adaptation is derived from the work
By P.Costigan email: phil@pcscada.com.au http://pcscada.com.au
-
+
These library of functions are designed to enable a program send and
receive data from a device that communicates using the Modbus protocol.
-
+
Copyright (C) 2000 Philip Costigan P.C. SCADA LINK PTY. LTD.
-
+
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
-
+
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
-
+
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-
- The functions included here have been derived from the
+
+ The functions included here have been derived from the
Modicon Modbus Protocol Reference Guide
which can be obtained from Schneider at www.schneiderautomation.com.
-
- This code has its origins with
+
+ This code has its origins with
paul@pmcrae.freeserve.co.uk (http://www.pmcrae.freeserve.co.uk)
who wrote a small program to read 100 registers from a modbus slave.
-
+
I have used his code as a catalist to produce this more functional set
of functions. Thanks paul.
*/
@@ -57,7 +57,7 @@
MODSERIAL pc(USBTX, USBRX); // tx, rx //afdhal
#ifndef ModbusSlave232_h
- #include "ModbusSlave232.h"
+#include "ModbusSlave232.h"
#endif
@@ -66,45 +66,45 @@
****************************************************************************/
/* constants */
-enum {
- MAX_READ_REGS = 0x7D,
- MAX_WRITE_REGS = 0x7B,
- MAX_MESSAGE_LENGTH = 256
+enum {
+ MAX_READ_REGS = 0x7D,
+ MAX_WRITE_REGS = 0x7B,
+ MAX_MESSAGE_LENGTH = 256
};
-enum {
- RESPONSE_SIZE = 6,
- EXCEPTION_SIZE = 3,
- CHECKSUM_SIZE = 2
+enum {
+ RESPONSE_SIZE = 6,
+ EXCEPTION_SIZE = 3,
+ CHECKSUM_SIZE = 2
};
/* exceptions code */
-enum {
- NO_REPLY = -1,
- EXC_FUNC_CODE = 1,
- EXC_ADDR_RANGE = 2,
- EXC_REGS_QUANT = 3,
- EXC_EXECUTE = 4
+enum {
+ NO_REPLY = -1,
+ EXC_FUNC_CODE = 1,
+ EXC_ADDR_RANGE = 2,
+ EXC_REGS_QUANT = 3,
+ EXC_EXECUTE = 4
};
/* positions inside the query/response array */
-enum {
- SLAVE = 0,
- FUNC,
- START_H,
- START_L,
- REGS_H,
- REGS_L,
- BYTE_CNT
+enum {
+ SLAVE = 0,
+ FUNC,
+ START_H,
+ START_L,
+ REGS_H,
+ REGS_L,
+ BYTE_CNT
};
/* enum of supported modbus function codes. If you implement a new one, put its function code here ! */
-enum {
- FC_READ_REGS = 0x03, //Read contiguous block of holding register
- FC_WRITE_REG = 0x06, //Write single holding register
- FC_WRITE_REGS = 0x10 //Write block of contiguous registers
+enum {
+ FC_READ_REGS = 0x03, //Read contiguous block of holding register
+ FC_WRITE_REG = 0x06, //Write single holding register
+ FC_WRITE_REGS = 0x10 //Write block of contiguous registers
};
/* supported functions. If you implement a new one, put its function code into this array! */
@@ -113,418 +113,418 @@
/*
CRC
-
+
INPUTS:
- buf -> Array containing message to be sent to controller.
+ buf -> Array containing message to be sent to controller.
start -> Start of loop in crc counter, usually 0.
cnt -> Amount of bytes in message being sent to controller/
OUTPUTS:
temp -> Returns crc byte for message.
COMMENTS:
This routine calculates the crc high and low byte of a message.
- Note that this crc is only used for Modbus, not Modbus+ etc.
+ Note that this crc is only used for Modbus, not Modbus+ etc.
****************************************************************************/
unsigned int ModbusSlave232::crc(unsigned char *buf, unsigned char start,
-unsigned char cnt)
+ unsigned char cnt)
{
- unsigned char i, j;
- unsigned temp, temp2, flag;
+ unsigned char i, j;
+ unsigned temp, temp2, flag;
- temp = 0xFFFF;
+ temp = 0xFFFF;
- for (i = start; i < cnt; i++) {
- temp = temp ^ buf[i];
+ for (i = start; i < cnt; i++) {
+ temp = temp ^ buf[i];
- for (j = 1; j <= 8; j++) {
- flag = temp & 0x0001;
- temp = temp >> 1;
- if (flag)
- temp = temp ^ 0xA001;
- }
+ for (j = 1; j <= 8; j++) {
+ flag = temp & 0x0001;
+ temp = temp >> 1;
+ if (flag)
+ temp = temp ^ 0xA001;
}
+ }
- /* Reverse byte order. */
- temp2 = temp >> 8;
- temp = (temp << 8) | temp2;
- temp &= 0xFFFF;
+ /* Reverse byte order. */
+ temp2 = temp >> 8;
+ temp = (temp << 8) | temp2;
+ temp &= 0xFFFF;
- return (temp);
+ return (temp);
}
/***********************************************************************
- *
+ *
* The following functions construct the required query into
* a modbus query packet.
- *
+ *
***********************************************************************/
-/*
- * Start of the packet of a read_holding_register response
+/*
+ * Start of the packet of a read_holding_register response
*/
void ModbusSlave232::build_read_packet(unsigned char function,
-unsigned char count, unsigned char *packet)
+ unsigned char count, unsigned char *packet)
{
- packet[SLAVE] = slave;
- packet[FUNC] = function;
- packet[2] = count * 2;
-}
+ packet[SLAVE] = slave;
+ packet[FUNC] = function;
+ packet[2] = count * 2;
+}
-/*
- * Start of the packet of a preset_multiple_register response
+/*
+ * Start of the packet of a preset_multiple_register response
*/
void ModbusSlave232::build_write_packet(unsigned char function,
-unsigned int start_addr,
-unsigned char count,
-unsigned char *packet)
+ unsigned int start_addr,
+ unsigned char count,
+ unsigned char *packet)
{
- packet[SLAVE] = slave;
- packet[FUNC] = function;
- packet[START_H] = start_addr >> 8;
- packet[START_L] = start_addr & 0x00ff;
- packet[REGS_H] = 0x00;
- packet[REGS_L] = count;
-}
+ packet[SLAVE] = slave;
+ packet[FUNC] = function;
+ packet[START_H] = start_addr >> 8;
+ packet[START_L] = start_addr & 0x00ff;
+ packet[REGS_H] = 0x00;
+ packet[REGS_L] = count;
+}
-/*
- * Start of the packet of a write_single_register response
+/*
+ * Start of the packet of a write_single_register response
*/
void ModbusSlave232::build_write_single_packet(unsigned char function,
- unsigned int write_addr, unsigned int reg_val, unsigned char* packet)
+ unsigned int write_addr, unsigned int reg_val, unsigned char* packet)
{
- packet[SLAVE] = slave;
- packet[FUNC] = function;
- packet[START_H] = write_addr >> 8;
- packet[START_L] = write_addr & 0x00ff;
- packet[REGS_H] = reg_val >> 8;
- packet[REGS_L] = reg_val & 0x00ff;
-}
+ packet[SLAVE] = slave;
+ packet[FUNC] = function;
+ packet[START_H] = write_addr >> 8;
+ packet[START_L] = write_addr & 0x00ff;
+ packet[REGS_H] = reg_val >> 8;
+ packet[REGS_L] = reg_val & 0x00ff;
+}
-/*
- * Start of the packet of an exception response
+/*
+ * Start of the packet of an exception response
*/
void ModbusSlave232::build_error_packet( unsigned char function,
-unsigned char exception, unsigned char *packet)
+ unsigned char exception, unsigned char *packet)
{
- packet[SLAVE] = slave;
- packet[FUNC] = function + 0x80;
- packet[2] = exception;
-}
+ packet[SLAVE] = slave;
+ packet[FUNC] = function + 0x80;
+ packet[2] = exception;
+}
/*************************************************************************
- *
+ *
* modbus_query( packet, length)
- *
+ *
* Function to add a checksum to the end of a packet.
* Please note that the packet array must be at least 2 fields longer than
* string_length.
**************************************************************************/
-void ModbusSlave232::modbus_reply(unsigned char *packet, unsigned char string_length)
+void ModbusSlave232::modbus_reply(unsigned char *packet, unsigned char string_length)
{
- int temp_crc;
+ int temp_crc;
- temp_crc = crc(packet, 0, string_length);
- packet[string_length] = temp_crc >> 8;
- string_length++;
- packet[string_length] = temp_crc & 0x00FF;
-}
+ temp_crc = crc(packet, 0, string_length);
+ packet[string_length] = temp_crc >> 8;
+ string_length++;
+ packet[string_length] = temp_crc & 0x00FF;
+}
/***********************************************************************
- *
+ *
* send_reply( query_string, query_length )
- *
+ *
* Function to send a reply to a modbus master.
* Returns: total number of characters sent
************************************************************************/
-int ModbusSlave232::send_reply(unsigned char *query, unsigned char string_length)
+int ModbusSlave232::send_reply(unsigned char *query, unsigned char string_length)
{
- unsigned char i;
+ unsigned char i;
- /*if (txenpin > 1) { // set MAX485 to speak mode //afdhal
- UCSR0A=UCSR0A |(1 << TXC0);
- digitalWrite( txenpin, HIGH);
- delay(1);
- }*/
+ /*if (txenpin > 1) { // set MAX485 to speak mode //afdhal
+ UCSR0A=UCSR0A |(1 << TXC0);
+ digitalWrite( txenpin, HIGH);
+ delay(1);
+ }*/
- modbus_reply(query, string_length);
- string_length += 2;
+ modbus_reply(query, string_length);
+ string_length += 2;
- for (i = 0; i < string_length; i++) {
- //Serial.print(char(query[i])); //afdhal
- pc.putc(char(query[i])); //afdhal
-
- }
+ for (i = 0; i < string_length; i++) {
+ //Serial.print(char(query[i])); //afdhal
+ pc.putc(char(query[i])); //afdhal
- return i; /* it does not mean that the write was succesful, though */
+ }
+
+ return i; /* it does not mean that the write was succesful, though */
}
/***********************************************************************
- *
+ *
* receive_request( array_for_data )
- *
+ *
* Function to monitor for a request from the modbus master.
- *
+ *
* Returns: Total number of characters received if OK
- * 0 if there is no request
+ * 0 if there is no request
* A negative error code on failure
***********************************************************************/
-int ModbusSlave232::receive_request(unsigned char *received_string)
+int ModbusSlave232::receive_request(unsigned char *received_string)
{
- int bytes_received = 0;
+ int bytes_received = 0;
- /* FIXME: does Serial.available wait 1.5T or 3.5T before exiting the loop? */
- //while (Serial.available()) { //afdhal
- while (pc.readable()) { //afdhal
- received_string[bytes_received] = pc.getc(); //Serial.read(); //afdhal
- //Serial.print(received_string[bytes_received], DEC);
- bytes_received++;
- if (bytes_received >= MAX_MESSAGE_LENGTH)
- return NO_REPLY; /* port error */
- }
+ /* FIXME: does Serial.available wait 1.5T or 3.5T before exiting the loop? */
+ //while (Serial.available()) { //afdhal
+ while (pc.readable()) { //afdhal
+ received_string[bytes_received] = pc.getc(); //Serial.read(); //afdhal
+ //Serial.print(received_string[bytes_received], DEC);
+ bytes_received++;
+ if (bytes_received >= MAX_MESSAGE_LENGTH)
+ return NO_REPLY; /* port error */
+ }
- return (bytes_received);
+ return (bytes_received);
}
/*********************************************************************
- *
+ *
* modbus_request(request_data_array)
- *
+ *
* Function to the correct request is returned and that the checksum
* is correct.
- *
+ *
* Returns: string_length if OK
* 0 if failed
* Less than 0 for exception errors
- *
+ *
* Note: All functions used for sending or receiving data via
* modbus return these return values.
- *
+ *
**********************************************************************/
-int ModbusSlave232::modbus_request(unsigned char *data)
+int ModbusSlave232::modbus_request(unsigned char *data)
{
- int response_length;
- unsigned int crc_calc = 0;
- unsigned int crc_received = 0;
- unsigned char recv_crc_hi;
- unsigned char recv_crc_lo;
+ int response_length;
+ unsigned int crc_calc = 0;
+ unsigned int crc_received = 0;
+ unsigned char recv_crc_hi;
+ unsigned char recv_crc_lo;
- response_length = receive_request(data);
+ response_length = receive_request(data);
- if (response_length > 0) {
- crc_calc = crc(data, 0, response_length - 2);
- recv_crc_hi = (unsigned) data[response_length - 2];
- recv_crc_lo = (unsigned) data[response_length - 1];
- crc_received = data[response_length - 2];
- crc_received = (unsigned) crc_received << 8;
- crc_received =
- crc_received | (unsigned) data[response_length - 1];
+ if (response_length > 0) {
+ crc_calc = crc(data, 0, response_length - 2);
+ recv_crc_hi = (unsigned) data[response_length - 2];
+ recv_crc_lo = (unsigned) data[response_length - 1];
+ crc_received = data[response_length - 2];
+ crc_received = (unsigned) crc_received << 8;
+ crc_received =
+ crc_received | (unsigned) data[response_length - 1];
- /*********** check CRC of response ************/
- if (crc_calc != crc_received) {
- return NO_REPLY;
- }
+ /*********** check CRC of response ************/
+ if (crc_calc != crc_received) {
+ return NO_REPLY;
+ }
- /* check for slave id */
- if (slave != data[SLAVE]) {
- return NO_REPLY;
- }
+ /* check for slave id */
+ if (slave != data[SLAVE]) {
+ return NO_REPLY;
}
- return (response_length);
+ }
+ return (response_length);
}
/*********************************************************************
- *
+ *
* validate_request(request_data_array, request_length, available_regs)
- *
+ *
* Function to check that the request can be processed by the slave.
- *
+ *
* Returns: 0 if OK
* A negative exception code on error
- *
+ *
**********************************************************************/
int ModbusSlave232::validate_request(unsigned char *data, unsigned char length,
-unsigned int regs_size)
+ unsigned int regs_size)
{
- int i, fcnt = 0;
- unsigned int regs_num = 0;
- unsigned int start_addr = 0;
- unsigned char max_regs_num;
+ int i, fcnt = 0;
+ unsigned int regs_num = 0;
+ unsigned int start_addr = 0;
+ unsigned char max_regs_num;
- /* check function code */
- for (i = 0; i < sizeof(fsupported); i++) {
- if (fsupported[i] == data[FUNC]) {
- fcnt = 1;
- break;
- }
+ /* check function code */
+ for (i = 0; i < sizeof(fsupported); i++) {
+ if (fsupported[i] == data[FUNC]) {
+ fcnt = 1;
+ break;
}
- if (0 == fcnt)
- return EXC_FUNC_CODE;
-
- if (FC_WRITE_REG == data[FUNC]) {
- /* For function write single reg, this is the target reg.*/
- regs_num = ((int) data[START_H] << 8) + (int) data[START_L];
- if (regs_num >= regs_size)
- return EXC_ADDR_RANGE;
- return 0;
- }
+ }
+ if (0 == fcnt)
+ return EXC_FUNC_CODE;
- /* For functions read/write regs, this is the range. */
- regs_num = ((int) data[REGS_H] << 8) + (int) data[REGS_L];
+ if (FC_WRITE_REG == data[FUNC]) {
+ /* For function write single reg, this is the target reg.*/
+ regs_num = ((int) data[START_H] << 8) + (int) data[START_L];
+ if (regs_num >= regs_size)
+ return EXC_ADDR_RANGE;
+ return 0;
+ }
+
+ /* For functions read/write regs, this is the range. */
+ regs_num = ((int) data[REGS_H] << 8) + (int) data[REGS_L];
- /* check quantity of registers */
- if (FC_READ_REGS == data[FUNC])
- max_regs_num = MAX_READ_REGS;
- else if (FC_WRITE_REGS == data[FUNC])
- max_regs_num = MAX_WRITE_REGS;
+ /* check quantity of registers */
+ if (FC_READ_REGS == data[FUNC])
+ max_regs_num = MAX_READ_REGS;
+ else if (FC_WRITE_REGS == data[FUNC])
+ max_regs_num = MAX_WRITE_REGS;
- if ((regs_num < 1) || (regs_num > max_regs_num))
- return EXC_REGS_QUANT;
+ if ((regs_num < 1) || (regs_num > max_regs_num))
+ return EXC_REGS_QUANT;
- /* check registers range, start address is 0 */
- start_addr = ((int) data[START_H] << 8) + (int) data[START_L];
- if ((start_addr + regs_num) > regs_size)
- return EXC_ADDR_RANGE;
+ /* check registers range, start address is 0 */
+ start_addr = ((int) data[START_H] << 8) + (int) data[START_L];
+ if ((start_addr + regs_num) > regs_size)
+ return EXC_ADDR_RANGE;
- return 0; /* OK, no exception */
+ return 0; /* OK, no exception */
}
/************************************************************************
- *
+ *
* write_regs(first_register, data_array, registers_array)
- *
- * writes into the slave's holding registers the data in query,
+ *
+ * writes into the slave's holding registers the data in query,
* starting at start_addr.
- *
+ *
* Returns: the number of registers written
************************************************************************/
-int ModbusSlave232::write_regs(unsigned int start_addr, unsigned char *query, int *regs)
+int ModbusSlave232::write_regs(unsigned int start_addr, unsigned char *query, int *regs)
{
- int temp;
- unsigned int i;
+ int temp;
+ unsigned int i;
- for (i = 0; i < query[REGS_L]; i++) {
- /* shift reg hi_byte to temp */
- temp = (int) query[(BYTE_CNT + 1) + i * 2] << 8;
- /* OR with lo_byte */
- temp = temp | (int) query[(BYTE_CNT + 2) + i * 2];
+ for (i = 0; i < query[REGS_L]; i++) {
+ /* shift reg hi_byte to temp */
+ temp = (int) query[(BYTE_CNT + 1) + i * 2] << 8;
+ /* OR with lo_byte */
+ temp = temp | (int) query[(BYTE_CNT + 2) + i * 2];
- regs[start_addr + i] = temp;
- }
- return i;
+ regs[start_addr + i] = temp;
+ }
+ return i;
}
/************************************************************************
- *
+ *
* preset_multiple_registers(first_register, number_of_registers,
* data_array, registers_array)
- *
- * Write the data from an array into the holding registers of the slave.
- *
+ *
+ * Write the data from an array into the holding registers of the slave.
+ *
*************************************************************************/
int ModbusSlave232::preset_multiple_registers(unsigned int start_addr,
-unsigned char count,
-unsigned char *query,
-int *regs)
+ unsigned char count,
+ unsigned char *query,
+ int *regs)
{
- unsigned char function = FC_WRITE_REGS; /* Preset Multiple Registers */
- int status = 0;
- unsigned char packet[RESPONSE_SIZE + CHECKSUM_SIZE];
+ unsigned char function = FC_WRITE_REGS; /* Preset Multiple Registers */
+ int status = 0;
+ unsigned char packet[RESPONSE_SIZE + CHECKSUM_SIZE];
- build_write_packet(function, start_addr, count, packet);
+ build_write_packet(function, start_addr, count, packet);
- if (write_regs(start_addr, query, regs)) {
- status = send_reply(packet, RESPONSE_SIZE);
- }
+ if (write_regs(start_addr, query, regs)) {
+ status = send_reply(packet, RESPONSE_SIZE);
+ }
- return (status);
+ return (status);
}
/************************************************************************
- *
+ *
* write_single_register(slave_id, write_addr, data_array, registers_array)
- *
- * Write a single int val into a single holding register of the slave.
- *
+ *
+ * Write a single int val into a single holding register of the slave.
+ *
*************************************************************************/
-int ModbusSlave232::write_single_register(unsigned int write_addr, unsigned char *query, int *regs)
+int ModbusSlave232::write_single_register(unsigned int write_addr, unsigned char *query, int *regs)
{
- unsigned char function = FC_WRITE_REG; /* Function: Write Single Register */
- int status = 0;
- unsigned int reg_val;
- unsigned char packet[RESPONSE_SIZE + CHECKSUM_SIZE];
+ unsigned char function = FC_WRITE_REG; /* Function: Write Single Register */
+ int status = 0;
+ unsigned int reg_val;
+ unsigned char packet[RESPONSE_SIZE + CHECKSUM_SIZE];
- reg_val = query[REGS_H] << 8 | query[REGS_L];
- build_write_single_packet(function, write_addr, reg_val, packet);
- regs[write_addr] = (int) reg_val;
-/*
- written.start_addr=write_addr;
- written.num_regs=1;
-*/
- status = send_reply(packet, RESPONSE_SIZE);
+ reg_val = query[REGS_H] << 8 | query[REGS_L];
+ build_write_single_packet(function, write_addr, reg_val, packet);
+ regs[write_addr] = (int) reg_val;
+ /*
+ written.start_addr=write_addr;
+ written.num_regs=1;
+ */
+ status = send_reply(packet, RESPONSE_SIZE);
- return (status);
+ return (status);
}
/************************************************************************
- *
+ *
* read_holding_registers(first_register, number_of_registers,
* registers_array)
- *
+ *
* reads the slave's holdings registers and sends them to the Modbus master
- *
+ *
*************************************************************************/
int ModbusSlave232::read_holding_registers( unsigned int start_addr,
-unsigned char reg_count, int *regs)
+ unsigned char reg_count, int *regs)
{
- unsigned char function = FC_READ_REGS; /* Read Holding Registers */
- int packet_size = 3;
- int status;
- unsigned int i;
- unsigned char packet[MAX_MESSAGE_LENGTH];
+ unsigned char function = FC_READ_REGS; /* Read Holding Registers */
+ int packet_size = 3;
+ int status;
+ unsigned int i;
+ unsigned char packet[MAX_MESSAGE_LENGTH];
- build_read_packet(function, reg_count, packet);
+ build_read_packet(function, reg_count, packet);
- for (i = start_addr; i < (start_addr + (unsigned int) reg_count);
- i++) {
- packet[packet_size] = regs[i] >> 8;
- packet_size++;
- packet[packet_size] = regs[i] & 0x00FF;
- packet_size++;
- }
+ for (i = start_addr; i < (start_addr + (unsigned int) reg_count);
+ i++) {
+ packet[packet_size] = regs[i] >> 8;
+ packet_size++;
+ packet[packet_size] = regs[i] & 0x00FF;
+ packet_size++;
+ }
- status = send_reply(packet, packet_size);
+ status = send_reply(packet, packet_size);
- return (status);
+ return (status);
}
-/*
+/*
* configure(slave, baud, parity, txenpin)
*
* sets the communication parameters for of the serial line.
*
* slave: identification number of the slave in the Modbus network (1 to 127)
* baud: baudrate in bps (typical values 9600, 19200... 115200)
- * parity: a single character sets the parity mode (character frame format):
+ * parity: a single character sets the parity mode (character frame format):
* 'n' no parity (8N1); 'e' even parity (8E1), 'o' for odd parity (8O1).
* txenpin: arduino pin number that controls transmision/reception
* of an external half-duplex device (e.g. a RS485 interface chip).
@@ -534,50 +534,50 @@
void ModbusSlave232::configure(unsigned char slave, long baud, char parity)
{
- this->slave = slave;
- //this->txenpin = 2; //afdhal
+ this->slave = slave;
+ //this->txenpin = 2; //afdhal
+
-
- //Serial.begin(baud); //afdhal
- pc.baud(baud); //afdhal
+ //Serial.begin(baud); //afdhal
+ pc.baud(baud); //afdhal
- switch (parity) {
+ switch (parity) {
case 'e': // 8E1
- //UCSR0C |= ((1<<UPM01) | (1<<UCSZ01) | (1<<UCSZ00)); //afdhal
- pc.format(8, SerialBase::Even, 1); //afdhal
- // UCSR0C &= ~((1<<UPM00) | (1<<UCSZ02) | (1<<USBS0));
- break;
+ //UCSR0C |= ((1<<UPM01) | (1<<UCSZ01) | (1<<UCSZ00)); //afdhal
+ pc.format(8, SerialBase::Even, 1); //afdhal
+ // UCSR0C &= ~((1<<UPM00) | (1<<UCSZ02) | (1<<USBS0));
+ break;
case 'o': // 8O1
- //UCSR0C |= ((1<<UPM01) | (1<<UPM00) | (1<<UCSZ01) | (1<<UCSZ00)); //afdhal
- pc.format(8, SerialBase::Odd, 1); //afdhal
- // UCSR0C &= ~((1<<UCSZ02) | (1<<USBS0));
- break;
+ //UCSR0C |= ((1<<UPM01) | (1<<UPM00) | (1<<UCSZ01) | (1<<UCSZ00)); //afdhal
+ pc.format(8, SerialBase::Odd, 1); //afdhal
+ // UCSR0C &= ~((1<<UCSZ02) | (1<<USBS0));
+ break;
case 'n': // 8N1
- //UCSR0C |= ((1<<UCSZ01) | (1<<UCSZ00)); //afdhal
- pc.format(8, SerialBase::None, 1); //afdhal
- // UCSR0C &= ~((1<<UPM01) | (1<<UPM00) | (1<<UCSZ02) | (1<<USBS0));
- break;
+ //UCSR0C |= ((1<<UCSZ01) | (1<<UCSZ00)); //afdhal
+ pc.format(8, SerialBase::None, 1); //afdhal
+ // UCSR0C &= ~((1<<UPM01) | (1<<UPM00) | (1<<UCSZ02) | (1<<USBS0));
+ break;
default:
- break;
- }
-
- /*
- if (txenpin > 1) { // pin 0 & pin 1 are reserved for RX/TX
- pinMode(txenpin, OUTPUT);
- digitalWrite(txenpin, LOW);
- }*/
+ break;
+ }
- return;
-}
+ /*
+ if (txenpin > 1) { // pin 0 & pin 1 are reserved for RX/TX
+ pinMode(txenpin, OUTPUT);
+ digitalWrite(txenpin, LOW);
+ }*/
+
+ return;
+}
/*
* update(regs, regs_size)
- *
+ *
* checks if there is any valid request from the modbus master. If there is,
* performs the requested action
- *
+ *
* regs: an array with the holding registers. They start at address 1 (master point of view)
* regs_size: total number of holding registers.
* returns: 0 if no request from master,
@@ -590,68 +590,68 @@
const unsigned long T35 = 5;
int ModbusSlave232::update(int *regs,
-unsigned int regs_size)
-{
- unsigned char query[MAX_MESSAGE_LENGTH];
- unsigned char errpacket[EXCEPTION_SIZE + CHECKSUM_SIZE];
- unsigned int start_addr;
- int exception;
- int length = pc.rxBufferGetCount(); //Serial.available(); //afdhal
- unsigned long now = millis();
-
+ unsigned int regs_size)
+{
+ unsigned char query[MAX_MESSAGE_LENGTH];
+ unsigned char errpacket[EXCEPTION_SIZE + CHECKSUM_SIZE];
+ unsigned int start_addr;
+ int exception;
+ int length = pc.rxBufferGetCount(); //Serial.available(); //afdhal
+ unsigned long now = millis();
+
- if (length == 0) {
- lastBytesReceived = 0;
- return 0;
- }
+ if (length == 0) {
+ lastBytesReceived = 0;
+ return 0;
+ }
- if (lastBytesReceived != length) {
- lastBytesReceived = length;
- Nowdt = now + T35;
- return 0;
- }
- if (now < Nowdt)
- return 0;
+ if (lastBytesReceived != length) {
+ lastBytesReceived = length;
+ Nowdt = now + T35;
+ return 0;
+ }
+ if (now < Nowdt)
+ return 0;
- lastBytesReceived = 0;
+ lastBytesReceived = 0;
+
+ length = modbus_request(query);
+ if (length < 1)
+ return length;
- length = modbus_request(query);
- if (length < 1)
- return length;
-
- exception = validate_request(query, length, regs_size);
- if (exception) {
- build_error_packet( query[FUNC], exception,
- errpacket);
- send_reply(errpacket, EXCEPTION_SIZE);
- return (exception);
- }
+ exception = validate_request(query, length, regs_size);
+ if (exception) {
+ build_error_packet( query[FUNC], exception,
+ errpacket);
+ send_reply(errpacket, EXCEPTION_SIZE);
+ return (exception);
+ }
- start_addr =
- ((int) query[START_H] << 8) +
- (int) query[START_L];
+ start_addr =
+ ((int) query[START_H] << 8) +
+ (int) query[START_L];
- switch (query[FUNC]) {
- case FC_READ_REGS:
- return read_holding_registers(
- start_addr,
- query[REGS_L],
- regs);
- break;
- case FC_WRITE_REGS:
- return preset_multiple_registers(
- start_addr,
- query[REGS_L],
- query,
- regs);
- break;
- case FC_WRITE_REG:
- write_single_register(
- start_addr,
- query,
- regs);
- break;
- }
-
+ switch (query[FUNC]) {
+ case FC_READ_REGS:
+ return read_holding_registers(
+ start_addr,
+ query[REGS_L],
+ regs);
+ break;
+ case FC_WRITE_REGS:
+ return preset_multiple_registers(
+ start_addr,
+ query[REGS_L],
+ query,
+ regs);
+ break;
+ case FC_WRITE_REG:
+ write_single_register(
+ start_addr,
+ query,
+ regs);
+ break;
+ }
+
}
\ No newline at end of file