Fading Coder

One Final Commit for the Last Sprint

Home > Tech > Content

Implementing Serial Communication Between a Host Computer and Mitsubishi FX3U PLC via FX-232-BD

Tech 3

This article details the implementation of serial communication between a host computer (PC) and a Mitsubishi FX3U Programmable Logic Controller (PLC) using the FX-232-BD communication board. The communication protocol used is the Mitsubishi computer link protocol with checksum (Sum Check) and protocol format 4.

PLC Configuraton

On the PLC side, the communication parameters must be configured to use the Sum Check + Protocol 4 format.

Reading Data from the PLC

To read a single word (16-bit) from data register D200, the host sends the following command frame:

Command: 05 30 30 46 46 57 52 30 44 30 32 30 30 30 31

Response (value 0x201): 02 30 30 46 46 30 30 43 39 03

Below is a C# method that constructs this read command. The method builds a byte array representing the ASCII characters of the command frame, calculates the checksum, and appends the required terminators.

private void SendReadCommand(string registerAddress)
{
    byte[] commandFrame = new byte[20];
    commandFrame[0] = 0x05; // ENQ (Start of transmission)
    commandFrame[1] = 0x30; // Station Number (ASCII '0')
    commandFrame[2] = 0x30; // Station Number (ASCII '0')
    commandFrame[3] = 0x46; // PC Number (ASCII 'F')
    commandFrame[4] = 0x46; // PC Number (ASCII 'F')
    commandFrame[5] = 0x57; // Command Code 'WR' for Read (ASCII 'W')
    commandFrame[6] = 0x52; // Command Code 'WR' for Read (ASCII 'R')
    commandFrame[7] = 0x30; // Message Wait Time (ASCII '0')
    // Register Address (e.g., "D0200")
    commandFrame[8] = (byte)registerAddress[0];
    commandFrame[9] = (byte)registerAddress[1];
    commandFrame[10] = (byte)registerAddress[2];
    commandFrame[11] = (byte)registerAddress[3];
    commandFrame[12] = (byte)registerAddress[4];
    commandFrame[13] = 0x30; // Number of Points (ASCII '0')
    commandFrame[14] = 0x31; // Number of Points (ASCII '1')

    // Calculate checksum (Sum of bytes 1-14)
    int checksumValue = 0;
    for (int index = 1; index <= 14; index++)
    {
        checksumValue += commandFrame[index];
    }
    string checksumHex = checksumValue.ToString("X");
    // Append checksum as ASCII characters
    commandFrame[15] = (byte)checksumHex[checksumHex.Length - 2];
    commandFrame[16] = (byte)checksumHex[checksumHex.Length - 1];

    commandFrame[17] = 0x0D; // CR (Carriage Return)
    commandFrame[18] = 0x0A; // LF (Line Feed)

    SendToPLC(commandFrame); // Method to send the byte array via serial port
}

Writing Data to the PLC

To write the value 1 (hex 0001) to data register D100, the host sends the following command frame:

Command: 05 30 30 46 46 57 57 30 44 30 31 30 30 30 31 30 30 30 31

Response (ACK): 06 30 30 46 46

The following C# method constructs this write command. It includes the data to be written in the frame before calculating the checksum.

private void SendWriteCommand(string registerAddress, string dataValue)
{
    byte[] commandFrame = new byte[24];
    commandFrame[0] = 0x05; // ENQ
    commandFrame[1] = 0x30; // Station Number
    commandFrame[2] = 0x30;
    commandFrame[3] = 0x46; // PC Number
    commandFrame[4] = 0x46;
    commandFrame[5] = 0x57; // Command Code 'WW' for Write (ASCII 'W')
    commandFrame[6] = 0x57; // Command Code 'WW' for Write (ASCII 'W')
    commandFrame[7] = 0x30; // Message Wait Time
    // Register Address (e.g., "D0100")
    commandFrame[8] = (byte)registerAddress[0];
    commandFrame[9] = (byte)registerAddress[1];
    commandFrame[10] = (byte)registerAddress[2];
    commandFrame[11] = (byte)registerAddress[3];
    commandFrame[12] = (byte)registerAddress[4];
    commandFrame[13] = 0x30; // Number of Points
    commandFrame[14] = 0x31;
    // Data to Write (e.g., "0001")
    commandFrame[15] = (byte)dataValue[0];
    commandFrame[16] = (byte)dataValue[1];
    commandFrame[17] = (byte)dataValue[2];
    commandFrame[18] = (byte)dataValue[3];

    // Calculate checksum (Sum of bytes 1-18)
    int checksumValue = 0;
    for (int index = 1; index <= 18; index++)
    {
        checksumValue += commandFrame[index];
    }
    string checksumHex = checksumValue.ToString("X");
    // Append checksum as ASCII characters
    commandFrame[19] = (byte)checksumHex[checksumHex.Length - 2];
    commandFrame[20] = (byte)checksumHex[checksumHex.Length - 1];

    commandFrame[21] = 0x0D; // CR
    commandFrame[22] = 0x0A; // LF

    SendToPLC(commandFrame); // Method to send the byte array via serial port
}

Related Articles

Understanding Strong and Weak References in Java

Strong References Strong reference are the most prevalent type of object referencing in Java. When an object has a strong reference pointing to it, the garbage collector will not reclaim its memory. F...

Comprehensive Guide to SSTI Explained with Payload Bypass Techniques

Introduction Server-Side Template Injection (SSTI) is a vulnerability in web applications where user input is improper handled within the template engine and executed on the server. This exploit can r...

Implement Image Upload Functionality for Django Integrated TinyMCE Editor

Django’s Admin panel is highly user-friendly, and pairing it with TinyMCE, an effective rich text editor, simplifies content management significantly. Combining the two is particular useful for bloggi...

Leave a Comment

Anonymous

◎Feel free to join the discussion and share your thoughts.