Hello everyone, I am using Arduino DUE and Arduino Ethernet Shield 2 for MODBUS TCP/IP communication. Specifically, I have the Arduino DUE acting as a MODBUS Master, while the PC serves as the SLAVE using MODBUS Slave software.
When I set the REQUEST_INTERVAL to 2 seconds, the Response time (microseconds) is 378. When I set the interval to 0.02 seconds, the Response time (microseconds) is 19744. Do you think the slowdown is caused by the Arduino DUE being overloaded or the Arduino Ethernet Shield 2 being overloaded?
Here is my code:
#include <SPI.h>
#include <Ethernet.h>
// Pin Definitions
// Network Configuration
byte mac[] = { 0xA8, 0x61, 0x0A, 0xAE, 0x0A, 0xCC };
IPAddress server(192, 168, 123, 209); // ModbusTCP server address
IPAddress localIP(192, 168, 123, 207); // Local IP address as slave
EthernetClient ethClient;
EthernetServer slaveServer(502); // Modbus slave server
// ModbusTCP Configuration
uint16_t transactionId = 0;
uint16_t holdingRegisters[100]; // Holding registers array
bool isMasterMode = true; // Mode switching flag
unsigned long modeChangeTimer = 0; // Mode change timer
const unsigned long MODE_CHANGE_INTERVAL = 10000; // Mode change interval(ms)
unsigned long requestStartTime = 0; // Request start time
unsigned long lastRequestTime = 0; // Last request time
const unsigned long REQUEST_INTERVAL = 2000000; // 2 seconds = 2000000 microseconds
void sendModbusRequest(byte slaveId, byte functionCode, uint16_t startAddr, uint16_t quantity) {
byte request[12];
// Modbus TCP Frame Header
request[0] = highByte(transactionId);
request[1] = lowByte(transactionId++);
request[2] = 0x00; // Protocol Identifier High Byte
request[3] = 0x00; // Protocol Identifier Low Byte
request[4] = 0x00; // Length High Byte
request[5] = 0x06; // Length Low Byte
request[6] = slaveId;
request[7] = functionCode;
request[8] = highByte(startAddr);
request[9] = lowByte(startAddr);
request[10] = highByte(quantity);
request[11] = lowByte(quantity);
ethClient.write(request, 12);
}
void readModbusResponse() {
byte buffer[256];
int len = 0;
while (ethClient.available() && len < 256) {
buffer[len++] = ethClient.read();
}
if (len > 0) {
// Serial.print("Response received, length: ");
// Serial.println(len);
// Serial.print("Data content: ");
// // Print each byte in hexadecimal format
// for(int i = 0; i < len; i++) {
// if(buffer[i] < 0x10) {
// Serial.print("0"); // Add leading zero
// }
// Serial.print(buffer[i], HEX);
// Serial.print(" ");
// }
// Serial.println(); // New line
// Parse Modbus response
if(len >= 9 && buffer[7] == 0x03) { // Verify read holding register response
byte dataLen = buffer[8]; // Number of data bytes
if(len >= (9 + dataLen)) {
// uint16_t registerValue = (buffer[9] << 8) | buffer[10]; // Combine high and low bytes
// Serial.print("Register value: ");
// Serial.println(registerValue);
unsigned long responseTime = micros() - requestStartTime; // Calculate response time
Serial.print("Response time (microseconds): ");
Serial.println(responseTime);
}
}
}
}
void runMasterMode() {
if (!ethClient.connected()) {
if (ethClient.connect(server, 502)) {
Serial.println("Connected to Modbus server");
} else {
Serial.println("Connection failed");
return;
}
}
requestStartTime = micros(); // Record sending time
sendModbusRequest(0x01, 0x03, 0x0000, 0x0001);
lastRequestTime = micros();
if (ethClient.available()) {
readModbusResponse();
}
}
void setup() {
Serial.begin(9600); // Initialize Serial for debugging
// Initialize Ethernet
Ethernet.begin(mac, localIP);
}
void loop() {
// Check if sending interval has elapsed
if (micros() - lastRequestTime >= REQUEST_INTERVAL) {
runMasterMode();
}
}