Sequence Makerのバイナリ送信する「#SENDBIN」コマンドについて

## はじめに
Sequence MakerはExcelから測定器を制御可能にするアドインです。Sequence Makerは様々なシーケンスを自由に組むことができますが、Sequence Maker専用コマンドを組み合わせるとより複雑な処理を行うことができます。この記事ではバイナリデータを送信することができる「#SENDBIN」コマンドについて解説していきます。なお、Sequence Makerについての詳細は以下の記事を参照ください。

https://qiita.com/sequencemaker/items/8e6a370ab0a793a06a3b

:::note warn
***お断り***
本記事の内容はSequence Maker開発元の公式見解ではなく、あくまでも個人が趣味の範囲内で執筆しているものです。記事の内容について開発元へ問い合わせることはお控えください。ご質問・要望などは各記事のコメント欄へお願いいたします。
:::

## 「#SENDBIN」コマンド
| 専用コマンド | 機能 |
|:-|:-|
| #SENDBIN(コマンド)	| バイナリ形式のコマンドの送信のみ行います。受信動作は行いません。<br>コマンドは16進数形式で1バイトずつコンマで区切って指定します。|

（https://sequencemaker.hioki.com/manual/ja/#command より引用）

「#SENDBIN」コマンドは、マニュアルにあるように、バイナリデータを送信することができるコマンドです。Sequence Makerの通常の送信ではASCIIデータとしてしか送信できません。測定器を制御する通信コマンド（SCPI準拠）の場合はASCIIで困ることはありませんが、一部の特殊な機器とかではバイナリでデータを送信する必要がある場合があり、そんなときにこのコマンドを使用します。

## バイナリ送信が必要な例
今まで見たことがあるケースとしては、送信データの前後を **「STX」** と **「ETX」** で囲む必要があるパターンです。Wikipediaによると制御文字の項目に以下の表が掲載されています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3821782/f164031e-abf2-ca21-b84e-a17b6fb6f685.png)

（https://ja.wikipedia.org/wiki/%E5%88%B6%E5%BE%A1%E6%96%87%E5%AD%97 より引用）

「STX」は16進数で表記すると「0x02」、「ETX」は「0x03」となります。例えば送信データが「HELLO」の場合は以下のようになります。

```
「STX」HELLO「ETX」
```

すべて16進数で表記すると、

```
02 48 45 4C 4C 4F 03
```

となります。

## 使い方
送信したいバイナリデータを16進でコンマで区切って書くだけです。こんな感じ。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3821782/a5963f36-024f-3126-b17c-c774608ad68f.png)

::: note warn
CR＋LFなどの送信ターミネーターは自動的に付加されないので、必要なら自分で付ける必要があります。上記の例ではLF（0A）を付加しています。
:::

## 試してみる…その前に実験の準備
本当にバイナリデータの送信ができているのか確認してみます。ちょっと手元にバイナリで動く機器が無いので、今回はArduinoでバイナリデータを受信して、そのままオウム返しする適当なスケッチを用意しました。

``` C
// 定義
#define LED_PIN (13)                        // LEDのピン番号

// 初期化
void setup() {
  Serial.begin(9600);                       // シリアルポートを9600bpsで初期化
  pinMode(LED_PIN, OUTPUT);                 // LEDのピンを出力に設定

}

// ループ処理
void loop() {
  if ( Serial.available() ) {               // シリアルデータを受信したら…
    digitalWrite(LED_PIN, HIGH);            // 処理中はLED点灯

    int data = Serial.read();               // 1バイト読み取り

    char buf[5];                            // 送信データ格納用バッファ
    if ( data == '\n' ) {                   // LF受信したときは、
      sprintf(buf, "%02X\r\n", data);       // 受信データにCRLFを付加する
    } else {
      sprintf(buf, "%02X,", data);          // それ以外の時はコンマを付加する
    }

    Serial.print(buf);                      // 受信データを応答

    digitalWrite(LED_PIN, LOW);             // 処理が終わったのでLED消灯
  }

}
```

データ処理中はLEDが点灯します。バイナリデータを受信すると、sprintfで文字列に変換してそのまま応答します。ターミネーターのLFを受信したら、CRLFを付加するようにしています。それ以外の場合はコンマを付加します。
なお、Sequence MakerとArduinoを組み合わせて使う場合はフロー制御の設定で注意点がありますので、以下の記事を参照ください。

https://qiita.com/sequencemaker/items/e68cf7d242e01de62f97

::: note alert
Sequence Makerは「DSR/DTR」にチェックが入っているとArduinoがリセットしてしまうので、チェックを外す。
:::

## Sequence Makerから送受信してみる

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3821782/dae59ae1-16fd-d9ee-e8a5-097107d70dd2.png)

ちゃんとバイナリデータとして送信できていて、応答も正しく返ってきていることが確認できました。ちなみに#SENDBINは送信専門で、受信動作などを行わないので、今回はその後に#READ?を使用して受信だけしています。


## まとめ
今回はバイナリデータ送信時に使う「#SENDBIN」コマンドについて紹介し、実際の動作確認をArduinoを使って行いました。バイナリ送信が必要な機器に対して、どれだけ使えるのは若干謎です（実際はチェックサムを計算したりしないといけない機器なんかもあって、複雑なのだ）。もし、実際にうまくいったようなケースがあれば、コメントをいただきたいです。