質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

89.97%

三菱電機製PLCとのソケット通信

受付中

回答 3

投稿

  • 評価
  • クリップ 1
  • VIEW 3,179

moyashi27371

score 4

 前提・実現したいこと

三菱電機製のシーケンサ(Q03UDVCPU)とC#にてソケット通信を行っていますが
うまくいきません。
内臓イーサネットではうまく開通もできなかったのでQJ71E71-100を使用しています。
通信は開通しているのですが、コマンドを送ってもよくわからないのが返ってきてしまいます。
例として
• バイナリコード,3Eフレーム
• アクセス先: 接続局(自局)のQCPU
• コマンド: ワード単位の一括読出し(コマンド: 0401)
• デバイス: M100~M131(2ワード分)
を設定しています

 発生している問題・エラーメッセージ

B5-5B-80-C0-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00

 該当のソースコード

using System;
using System.Text;
using System.Net.Sockets;
using System.Net;

namespace PLCConnect
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("キーを押下で送信処理");
            Console.WriteLine("サーバーがすでに待機していることが条件");
            Console.ReadLine();


            try
            {
                //IPアドレスとポート番号を指定
                IPAddress ipAddress = IPAddress.Parse("192.168.100.4");
                int port = 2000;

                //シーケンサと接続
                TcpClient client = new TcpClient();
                client.Connect(ipAddress, port);

                if (client.Connected) Console.WriteLine("Connented");

                //接続完了確認
                Console.WriteLine("接続完了");

                //ストリームを作成
                NetworkStream stream = client.GetStream();

                string str;
                //データレジスタM0の内容を読みだすコマンド
                str = "5000"    // サブヘッダ(固定値)
                    + "00FF"      // ネットワーク番号(自局なので固定)
                    + "FF"      // PC番号(自局なので固定)
                    + "FF03"    // 要求先ユニットI/O番号(固定値)
                    + "00"      // 要求先ユニット局番号(固定値)
                    + "0C00"    // 要求データ長
                    + "1000"    // CPU監視タイマ
                    + "0104"    // コマンド(データレジスタをワード単位で一括読み出しするコマンド:0401)
                    + "0000"    // サブコマンド
                    + "640000"    // 先頭デバイス(0)
                    + "90"      // デバイスコード(M)
                    + "0200";   // デバイス点数

                Console.WriteLine("str=" + str);

                //byte型に変換
                byte[] tmp = Encoding.UTF8.GetBytes(str);

                //送信
                stream.Write(tmp, 0, tmp.Length);
                Console.WriteLine("送信しました");

                //応答電文の受け取り配列
                byte[] res = new byte[30];
                Console.WriteLine("受信します");


                stream.Read(res, 0, res.Length);
                //受け取り完了確認
                Console.WriteLine("受信完了");

                //受け取ったものの表示
                foreach (int i in res)
                {
                    Console.WriteLine("res=" + i);
                }

                string s = string.Empty;

                s = BitConverter.ToString(res);
                Console.WriteLine("s="+s);

            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message);

            }
            finally
            {
                Console.WriteLine("キーを押下で終了");
                Console.ReadLine();
            }

        }
    }
}
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 3

0

 byte[] tmp = Encoding.UTF8.GetBytes(str);

これでは、単に文字列コードをバイナリにしてるだけなのでダメな気がしますが。
tmpのデータはどうなってるか見てみればどうでしょう


byte[] tmp=new byte[]{
    0x50,0x00,    // サブヘッダ(固定値)
    0x00,0xff,    // ネットワーク番号(自局なので固定)
    0xff,         // PC番号(自局なので固定)
    ...
};


というかんじで

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

0

データ長間違ってませんか?

+ "0C00"    // 要求データ長
↓
+ "1800"    // 要求データ長

 以下追記

あと、文字列の16進数をバイトにしたい場合は以下関数を通してください

public static byte[] StringToBytes(string str)
    {
        var bs = new List<byte>();
        for (int i = 0; i < str.Length / 2; i++)
        {
            bs.Add(Convert.ToByte(str.Substring(i*2, 2), 16));
        }
        // "01-AB-EF" こういう"-"区切りを想定する場合は以下のようにする
        // var bs = str.Split('-').Select(hex => Convert.ToByte(hex, 16));
        return bs.ToArray();
    }

以下変更を行う

byte[] tmp = Encoding.UTF8.GetBytes(str);
↓
byte[] tmp = StringToBytes(str)

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/11/03 21:56

    回答していただいたことを試してみましたがうまくいきませんでした。

    キャンセル

0

実際に実機につないで試してみました。

2点、問題があります。

byte[] tmp = Encoding.UTF8.GetBytes(str); 

このまま変換すると16進数の文字列が正しくバイナリに変換されません。
moonphaseさんの追記にあるように16進数文字列を変換する必要があります。

                    + "00FF"      // ネットワーク番号(自局なので固定)


ネットワーク番号の設定が間違っています。正しくは00ですね。
(多分PC番号を余分につけてしまっているのではと思います)

この2か所を修正したところ、バイナリでD0 00 ~の応答が返ってきました。

ちなみに、最初のエラーメッセージはどこからきているものでしょうか?
そのまま実行したら応答待ちで該当のエラーメッセージは出ませんでした。

内蔵EthernetではOpenできなかったとのことですが、
試せる環境が無いので推測ですが、ネットワークパラメータから設定しているのではないかと思われます。
内蔵Ethernetの設定はPCパラメータに項目があります。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 89.97%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる