Modbus RTU su RS232 con Arduino

Materiale occorrente:

  • Arduino UNO
  • Modulo MAX RS 232 (MAX3232)
  • Prolific PL2303GT USB / Serial (DB9)
  • opzionale: Weintek Easy Builder

Implementiamo una comunicazione Modbus RTU con Arduino.

Occorre importare in IDE la libreria ModbusRTUSlave.

Ecco lo sketch:

/*
  Arduino UNO + MAX3232 + RS232 + Modbus RTU SLAVE (ModbusRTUSlave v3.x)

  CABLAGGIO (TTL lato MAX3232):
    MAX3232 VCC  -> UNO 5V
    MAX3232 GND  -> UNO GND
    MAX3232 TX   -> UNO D10 (RX SoftwareSerial)
    MAX3232 RX   -> UNO D11 (TX SoftwareSerial)

  Modbus Poll:
    RTU, 9600, 8N1, Slave ID = 1
    (Con SoftwareSerial: usa Parity NONE)
*/

#include <SoftwareSerial.h>
#include <ModbusRTUSlave.h>

static const uint8_t  SLAVE_ID = 1;
static const uint32_t BAUD     = 9600;

SoftwareSerial rs232(10, 11);     // RX, TX (Modbus su RS232)
ModbusRTUSlave modbus(rs232);     // <-- FIX: costruttore con Stream

uint16_t holding[10];             // Holding Registers 0..9

void setup() {
  Serial.begin(115200);           // debug USB
  rs232.begin(BAUD);              // linea Modbus

  modbus.configureHoldingRegisters(holding, 10);
  modbus.begin(SLAVE_ID, BAUD, SERIAL_8N1);

  holding[0] = 1234;
  holding[1] = 5678;
}

void loop() {
  // valori "live" (esempio)
  holding[0] = analogRead(A0);
  holding[1] = (uint16_t)(millis() & 0xFFFF);

  modbus.poll();

  // debug leggero (opzionale)
  static uint32_t t = 0;
  if (millis() - t >= 1000) {
    t = millis();
    Serial.print("HR0=");
    Serial.print(holding[0]);
    Serial.print(" HR1=");
    Serial.print(holding[1]);
    Serial.print(" HR2=");
    Serial.println(holding[2]);
  }
}

Il serial monitor di Arduino espone i dati degli Holding Register.

Ora è possibile interagire via Modbus con Arduino. Su Modbus Poll (o qualsiasi altro programma Modbus client) impostiamo questi parametri di comunicazione:

  • 9600 Baud
  • 8 Data Bit
  • Parity None
  • 1 Stop Bit

Una volta collegati si possono visualizzare i valori degli Holding Register.

Si può impostare il valore dello Holding Register 2.

Il monitor serial di IDE conferma l’avvenuta scrittura.

Ora proviamo a visualizzare questi valori su un HMI Weintek. Creiamo un nuovo progetto in Weintek Easy Builder. Va bene il modello MT8050iE.

Aggiungiamo il dispositivo Arduino (HOME > Parametri di sistema > Nuovo dispositivo / Server > Modbus RTU Adjustable)

Nota: dato che proveremo il progetto in simulazione on-line dobbiamo mappare il nostro cavo seriale usb / RS-232 sulla porta COM1. Fare attenzione anche qui a impostare correttamente i parametri di comunicazione (COM1 9600, N, 8, 1).

Nella Window_010 creiamo degli oggetti numerici con i seguenti indirizzi (4x-0, 4x-1, 4x-2), nell’ultimo oggetto possiamo mettere anche la spunta a “consenti ingresso” per modificarne i valori.

NOTA: Attenzione a non confondere indirizzo 4x la funzione Modbus 04 (0x04) – Read Input Registers. Quest’ultima è un function code per leggere gli input register, invece in Indirizzo 4x <n> mettiamo l’indirizzo dell’Holding register che vogliamo leggere, non la funzione.

Cliccando su Progetto > Simulatore Online possiamo ora interagire con Arduino via Modbus RTU su tramite RS232.

Buon divertimento 🙂