【VB.NET】MCプロトコルで三菱PLCと通信

パソコン

どうも、もももです。

今回はVB.NETで三菱社PLCとMCプロトコルで通信を行う方法について紹介します。

MCプロトコル 読書きコマンド

MCプロトコルのコマンドについては下記で紹介しているので参照下さい。

構成イメージ

PCとPLCをEthernetケーブルで接続します。

サンプルプログラム

Imports System.Net.Sockets

Public Class Form1

    Dim _socket As Socket =
        New Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp)

    Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        Dim ipAddress As String = "192.168.3.39"
        Dim portNo As Integer = 1100

        _socket.Connect(ipAddress, portNo)
    End Sub

    Private Sub Form1_FormClosed(sender As Object, e As FormClosedEventArgs) Handles MyBase.FormClosed
        _socket.Close()
    End Sub

    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click

        '送信メッセージ作成
        Dim sendMessage(20) As String
        'サブヘッダ
        sendMessage(0) = "50" '50で固定
        sendMessage(1) = "00" '00で固定
        'アクセス経路
        sendMessage(2) = "00" 'ネットワーク番号
        sendMessage(3) = "FF" 'PC番号
        sendMessage(4) = "FF" '要求先ユニットI/O番号
        sendMessage(5) = "03" '要求先ユニットI/O番号
        sendMessage(6) = "00" '要求先ユニット局番号
        '要求データ長(2Byte)
        sendMessage(7) = "0C" '要求データ長34 12点⇒000C
        sendMessage(8) = "00" '要求データ長12 12点⇒000C
        '監視タイマ(2Byte)
        sendMessage(9) = "10"
        sendMessage(10) = "00"
        '要求データ
        sendMessage(11) = "01" 'コマンド 読取0401⇒04"01"
        sendMessage(12) = "04" 'コマンド 読取0401⇒"04"01
        sendMessage(13) = "01" 'サブコマンド ビット読取0001⇒00"01"
        sendMessage(14) = "00" 'サブコマンド ビット読取0001⇒"00"01
        sendMessage(15) = "00" 'デバイス番号56 0⇒0000"00"
        sendMessage(16) = "00" 'デバイス番号34 0⇒00"00"00
        sendMessage(17) = "00" 'デバイス番号12 0⇒"00"0000
        sendMessage(18) = "90" 'デバイスコード M⇒90
        sendMessage(19) = "01" '読取点数34 1点⇒00"01"
        sendMessage(20) = "00" '読取点数12 1点⇒"00"01

        'メッセージ送信&受信
        Dim byteReciveMessage = SendAndRecieve(sendMessage)

        Me.TextBox1.Text = Hex(byteReciveMessage(11)).PadLeft(2, "0").Substring(0, 1)

    End Sub

    Private Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click
        '送信メッセージ作成
        Dim sendMessage(21) As String
        'サブヘッダ(3Eフレーム:5000)
        sendMessage(0) = "50"
        sendMessage(1) = "00"
        'アクセス経路
        sendMessage(2) = "00" 'ネットワーク番号
        sendMessage(3) = "FF" 'PC番号
        sendMessage(4) = "FF" '要求先ユニットI/O番号
        sendMessage(5) = "03" '要求先ユニットI/O番号
        sendMessage(6) = "00" '要求先ユニット局番号
        '要求データ長(監視タイマ+要求データの要素数:13)
        sendMessage(7) = "0D"
        sendMessage(8) = "00"
        '監視タイマ(2Byte)
        sendMessage(9) = "10"
        sendMessage(10) = "00"
        '要求データ
        sendMessage(11) = "01" 'コマンド 書込(1401)
        sendMessage(12) = "14" 'コマンド 書込(1401)
        sendMessage(13) = "01" 'サブコマンド ビット(0001)
        sendMessage(14) = "00" 'サブコマンド ビット(0001)
        sendMessage(15) = "00" 'デバイス番号56 0⇒0000"00"
        sendMessage(16) = "00" 'デバイス番号34 0⇒00"00"00
        sendMessage(17) = "00" 'デバイス番号12 0⇒"00"0000
        sendMessage(18) = "90" 'デバイスコード
        sendMessage(19) = "01" '書込点数34 1⇒00"01"
        sendMessage(20) = "00" '書込点数12 1⇒"00"01
        If Me.RadioButton1.Checked Then
            sendMessage(21) = "10" '書込内容 1点目:"1", 2点目:"0"
        Else
            sendMessage(21) = "00" '書込内容 1点目:"0", 2点目:"0"
        End If

        'メッセージ送信&受信
        Dim byteReciveMessage = SendAndRecieve(sendMessage)

    End Sub

    Private Function SendAndRecieve(sendMessage As String()) As Byte()

        '送信メッセージを変換 String⇒Byte
        Dim byteSendMessage As Byte() = StringsToBytes(sendMessage)

        'メッセージ送信
        _socket.Send(byteSendMessage, byteSendMessage.GetLength(0), SocketFlags.None)

        '応答メッセージを受信
        Dim byteReciveMessage As Byte()
        Dim reciveSize As Integer = 0
        Do
            byteReciveMessage = New Byte(_socket.Available - 1) {}
            reciveSize =
                _socket.Receive(byteReciveMessage, byteReciveMessage.GetLength(0), SocketFlags.None)
        Loop While reciveSize = 0
        Return byteReciveMessage
    End Function

    Private Function StringsToBytes(src() As String) As Byte()
        Dim returnBytes(src.Length - 1) As Byte

        '1要素ずつ変換
        Dim i As Integer
        For i = 0 To src.Length - 1
            returnBytes(i) = Convert.ToByte(src(i), 16)
        Next
        Return returnBytes

    End Function

End Class

コード解説

上記は「Bit読み取り」ボタンを押下すると、「M0」の内容を「Bit読み取り」 テキストに表示(ON=1/OFF=0)し、「Bit書き込み」ボタンを押下するとラジオボタンの状態に応じて 「M0」 をON/OFFするサンプルプログラムです

・フォーム ロードイベント(8~13行)

画面起動時にソケット通信を確立します。

GX WorksでPLCのIPアドレスやオープン設定(MCプロトコルのポート番号, RUN中書込みの許可など)を確認し、設定して下さい。

下記ではIPアドレスやオープン設定の確認方法を紹介しています。

・フォーム クローズドイベント(15~17行)

画面終了時にソケット通信をクローズします。

・Bit読み取りボタン クリックイベント(19~55行)

Bit読み取りの要求メッセージ(M0)をString配列で作成⇒送信し、応答メッセージの内容をテキストボックスに反映します。(ONの場合は1、OFFの場合は0)

応答メッセージはByte配列の11番目以降が取得値になります。

Bit読み取りの場合は1つの要素には2Bit分の情報が格納されています。

  • ONの場合:byteReciveMessage(11)=16 バイナリコード⇒文字列変換で”10”
  • OFFの場合:byteReciveMessage(11)=0 バイナリコード⇒文字列変換で”00”

1文字目が読み取り1Bit目の値、2文字目が読み取り2Bit目の値になります。

・Bit書き込みボタン クリックイベント(57~95行)

Bit書き込みの要求メッセージをString配列で作成⇒送信しています。

・メッセージの送受信処理(97~126行)

引数のString配列をByte配列(バイナリコード)に変換して要求メッセージとして送信し、応答メッセージを戻り値として返します。

三菱PLCでは交信方法をバイナリコードとASCIIコードで選択できますが、今回はバイナリコード交信を前提としてサンプルプログラムを作成しました。

また、ソケット通信の詳細については下記でも紹介しています。

まとめ

VB.NETで三菱社PLCとMCプロトコルで通信を行う方法についてまとめました。

MX Componentを用いたPLC通信に比べて難易度はこちらの方が高いですが、一度作ってしまえばある程度使いまわしができるので便利です。

下記では MX Componentを用いた通信方法を紹介しています。

コメント

タイトルとURLをコピーしました