Back to page

− Links

 Print 

FUTABA RS Library :: Besttechnology

knowledge:FUTABA RS Library

Table of contents
    • 概要
    • ライブラリおよびサンプルプログラムのダウンロード
    • API
      • RS_OpenPort
      • RS_ClosePort
      • RS_SetBaudrate
      • RS_Active
      • RS_SetTimeOutOffset
      • RS_Ping
      • RS_ReadByteData
      • RS_WriteByteData
      • RS_ReadWordData
      • RS_WriteWordData
      • RS_ReadBlockData
      • RS_WriteBlockData
      • RS_WriteSyncData
      • RS_TxPacket
      • RS_RxPacket
      • RSLIBのオリジナルな定義

概要 anchor.png[1]

ROBO-ONEにおいて各社のアクチュエータで異なる通信方式をDXLIB[2]をベースとしたAPIレベルで標準化する試みが行われました。その成果物として、RS LibraryはFUTABAコマンド式サーボの通信プロトコルをサポートした製品をWindows等のOSから操作するためのライブラリとしてとりまとめました。
本APIを介する事でシリアル通信である事をほとんど意識すること無くアプリケーションの作りこみに専念できます。

なお、PCとRSC-U485[3]BTE061D[4]BTE061E[5]BTE068[6]BTE068B[7]BTE082[8]のいずれかがUSBケーブルで接続され、PC上にWindowsのデバイスとして仮想COMポートが増設された状態で使用するものとします。

Page Top

ライブラリおよびサンプルプログラムのダウンロード anchor.png[9]

以下のリンクよりライブラリ及びサンプルプログラムをアーカイブしたファイルがダウンロードできます。

アーカイブファイルには以下のファイルが同梱されます。必要に応じて解凍してください。なおファイル名のサフィックスが_x32は32ビット、_x64は64ビットのWindowsアプリ用です。

RSLIB1.1rslib_x32.dllライブラリ本体
rslib_x64.dll
librslib_x32.aGCC用ライブラリ(定義のみ)
librslib_x64.a
rslib_x32.llbMSVC用ライブラリ(定義のみ)
rslib_x64.lib
rslib.cライブラリソース
rslib.hライブラリヘッダ
rsmemmap.h仮想メモリマップ定義ヘッダ
makelib.batライブラリ再構築用バッチ
コンパイルにはGCC Developer Lite[12]lib.exe[13]が必要
83.bat
SampleCodetest1.cサンプルプログラム
test2.c
test3.c
test4.c
test5.c
test.viLabVIEWのサンプルとAPIのラッパvi
RS_OpenPort.vi
RS_ClosePort.vi
RS_SetBaudrate.vi
RS_WriteByte.vi
RS_ReadByte.vi
RS_WriteWord.vi
RS_ReadWord.vi
RS_WriteBlock.vi
RS_ReadBlock.vi
ArrayToElement.vi
ErrorCheck.vi
Page Top

API anchor.png[14]

RS Libraryではシリアル通信を直接意識するコードを記述せずに、対象IDのデバイスの仮想メモリマップへの読み書き行うAPIを用意しています。
C言語のソースにrslib.hをインクルードすれば、APIを使用するのに必要なプロトタイプとマクロの定義がなされます。

Page Top

RS_OpenPort anchor.png[15]

ライブラリの内部情報を初期化すると同時に指定されたCOMポートをオープンし、RS_SetBaudrateを使用して通信速度を設定した後、ユニークなTDeviceIDを返す。以後はこのTDeviceIDを使用して各APIを使用する。
複数のCOMポートを使用する場合は、使用するポート毎にRS_OpenPortを行いTDeviceIDを取得しなくてはならない。
なお、Linuxにおけるボーレートの指定に関しては、RS_SetBaudrateの解説に注意の事。

TDeviceID RS_OpenPort (char *name, uint32_t baud);
  • パラメータ
    • char *name

      インターフェースが提供するCOMポート名。
      記述方法はこちら[16]の情報に従う。

    • long baud

      インターフェースとデバイス間の通信速度[bps]。

  • 戻り値
    • TDeviceID

      オープンに成功した場合は0以外の値、失敗した場合は0を返す。

  • 使用例
    TDeviceID dev;
    // COM10を115200bpsでオープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
Page Top

RS_ClosePort anchor.png[17]

RS_OpenPortで開いたCOMポートを閉じる。
RS_ClosePortが実行された以後は指定されたTDeviceIDでの通信が行えなくなる。

bool RS_ClosePort (TDeviceID dvid);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

  • 戻り値
    • bool

      クローズに成功した場合はtrue、失敗した場合はfalseを返す。

  • 使用例
    TDeviceID dev;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      ... (中略)
      // クローズ
      RS_ClosePort (dev);
    }
Page Top

RS_SetBaudrate anchor.png[18]

既にオープンされているTDeviceIDの通信速度の変更を行う。
実行すると強制的に受信バッファがクリアされる。
なお、Linux環境におけるボーレートの設定は、POSIX.1でサポートする値(50, 75, 110, 134, 150, 200, 300, 600, 1200, 1800, 2400, 4800, 9600, 19200, 38400, 57600, 115200, 230400, 460800, 500000, 576000, 921600, 1000000, 1152000, 1500000, 2000000, 2500000, 3000000, 3500000, 4000000)であればtcsetattrを使用して処理するが、これらの値に当てはまらない場合はioctrlを使用する。その際I/Fがこれらのボーレートに対応していなかったり、ioctrlをサポートしない場合、本APIは失敗する。

bool RS_SetBaudrate (TDeviceID dvid, long baud);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • long baud

      新しい通信速度[bps]。

  • 戻り値
    • bool

      通信速度の変更が成功するとtrue、失敗するとfalseを返す。

  • 使用例
    TDeviceID dev;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // 通信速度を1M[bps]に変更
      RS_SetBaudrate (dev, 1000000);
      ... (中略)
      // クローズ
      RS_ClosePort (dev);
    }
Page Top

RS_Active anchor.png[19]

指定されたTDeviceIDのポートが開かれており、使用可能であるかを確認する。
USB接続等によりインターフェース自体が取り外し可能な場合に、実際に使用可能であるかを判断するために使用するが、状況によっては正確に判断できない場合もある。

bool RS_Active (TDeviceID dvid);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

  • 戻り値
    • bool

      指定されたdvidが使用可能な場合はtrue、使用不可の場合はfalseを返す。

  • 使用例
    TDeviceID dev;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      while (RS_Active (dev)) {
        ... (中略)
      }
      // クローズ
      RS_ClosePort (dev);
    }
Page Top

RS_SetTimeOutOffset anchor.png[20]

I/FやOSの都合で生じるであろうタイムラグを予め設定する。
内部で算出している受信タイムアウト時間とタイムアウトオフセット時間を加算した時間を超えた場合に、タイムアウトエラーとして処理する。
デフォルトは20。

void RS_SetTimeOutOffset (TDeviceID dvid, uint32_t offsettime);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint32_t offsettime

      タイムアウトオフセット時間[ms]

  • 戻り値
    • bool

      指定されたdvidが使用可能な場合はtrue、使用不可の場合はfalseを返す。

Page Top

RS_Ping anchor.png[21]

対象IDからの応答を確認する。

bool RS_Ping (TDeviceID dvid, uint8_t id, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (0~31)。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1にPINGを発行
      if (RS_Ping (dev, 1, &err))
        printf ("Found [%08X]\n", err);
      else
        printf ("Not found [%08X]\n", err);
      // クローズ
      RS_ClosePort (dev);
    }
Page Top

RS_ReadByteData anchor.png[22]

対象IDのコントロールテーブルから1バイトのデータを読み出す。

bool RS_ReadByteData(TDeviceID dvid, uint8_t id, uint8_t adr, uint8_t *rdata, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint8_t *rdata

      読み出した値の保存先。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    int8_t     dat;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1の温度を取得
      if (RS_ReadByteData (dev, 1, 50, &dat, &err)) {
        printf ("TEMP=%d\n", dat);
      }
      RS_ClosePort (dev);
    }
Page Top

RS_WriteByteData anchor.png[23]

対象IDのコントロールテーブルへ1バイトのデータを書き込む。

bool RS_WriteByteData(TDeviceID dvid, uint8_t id, uint8_t adr, uint8_t dat, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127, 255)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint8_t dat

      書き込む値。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。
      BROADCASTING ID(255)を指定した場合は応答待ちを行わない。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1のトルクONを指令する
      RS_WriteByteData (dev, 1, 36, 1, &err);
      RS_ClosePort (dev);
    }
Page Top

RS_ReadWordData anchor.png[24]

対象IDのコントロールテーブルから1ワード(2バイト)のデータを読み出す。

bool RS_ReadWordData(TDeviceID dvid, uint8_t id, uint8_t adr, uint16_t *rdata, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint16_t *rdata

      読み出した値の保存先。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    int16_t   dat;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1から現在位置を取得
      if (RS_ReadWordData (dev, 1, 42, &dat, &err)) {
        printf ("PRESENT POS=%d\n", dat);
      }
      RS_ClosePort (dev);
    }
Page Top

RS_WriteWordData anchor.png[25]

対象IDのコントロールテーブルへ1ワード(2バイト)のデータを書き込む。

bool RS_WriteWordData(TDeviceID dvid, uint8_t id, uint8_t adr, uint16_t dat, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127, 255)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint16_t dat

      書き込む値。

    • TErrorCode *errcode

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。
      BROADCASTING ID(255)を指定した場合は応答待ちを行わない。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    // オープン
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1へ位置(0)を指令
      RS_WriteWordData (dev, 1, 30, 0, &err);
      RS_ClosePort (dev);
    }
Page Top

RS_ReadBlockData anchor.png[26]

対象IDのコントロールテーブルから指定サイズのデータを読み出す。

bool RS_ReadBlockData (TDeviceID dvid, uint8_t id, uint8_t adr, uint8_t *rdata, uint32_t len, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint8_t *rdata

      読み出したデータの保存先。

    • uint32_t len

      読み出すデータのサイズ。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    uint8_t    dat[60];
    int        i;
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1から全データ(アドレス0から60バイト)を取得
      if (RS_ReadBlockData (dev, 1, 0, comp, 60, &err) {
        for (i = 0; i < 60; i++) printf ("%02X", dat[i]);
      }
      RS_ClosePort (dev);
    }
Page Top

RS_WriteBlockData anchor.png[27]

対象IDのコントロールテーブルへ指定サイズのデータを書き込む。

bool RS_WriteBlockData(TDeviceID dvid, uint8_t id, uint8_t adr, uint8_t *dat, uint32_t len, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127, 255)。

    • uint8_t adr

      コントロールテーブルのアドレス。

    • uint8_t *dat

      書き込むデータの保存先。

    • uint32_t len

      書き込むデータのサイズ。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      正常な応答が得られた場合はtrue、それ以外はfalseを返す。
      BROADCASTING ID(255)を指定した場合は応答待ちを行わない。

  • 使用例
    TDeviceID  dev;
    TErrorCode err;
    uint8_t    comp[4] = { 1, 1, 10, 10 };
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ID=1のコンプライアンスを変更
      RS_WriteBlockData (dev, 1, 24, comp, 4, &err);
      RS_ClosePort (dev);
    }
Page Top

RS_WriteSyncData anchor.png[28]

ロングパケットを使用して複数IDへブロック書き込みを行う。
書き込まれるデータの構成はユーザに委ねられる。

bool RS_WriteSyncData (TDeviceID dvid, uint8_t *dat, uint32_t size, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t *dat

      書き込むパラメータの保存先。

    • uint32_t size

      パラメータのサイズ。

    • TErrorCode *err

      エラーコード。

  • 戻り値
    • bool

      インターフェースより送信が行われた場合はtrue、それ以外はfalseを返す。

  • 使用例
    #define _POS1 (-1500)
    #define _POS2 (1500)
    
    TDeviceID  dev;
    TErrorCode err;
    uint8_t    param[9] = {
      30,    // 開始アドレス (Goal Position)
      3,     // 1軸あたりのデータバイトサイズ (id + data1 + data2 + ...)
      2,     // 軸数
      1,            // 1軸目ID
      _POS1 & 0xff, // data1
      _POS1 >> 8,   // data2
      2,            // 2軸目ID
      _POS2 & 0xff, // data1
      _POS2 >> 8    // datg2
    };
    
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // 2軸同時に位置を指令
      RS_WriteSyncData (dev, param, 9, &err);
      RS_ClosePort (dev);
    };
Page Top

RS_TxPacket anchor.png[29]

任意のショートないしロングパケットを送信する。

bool RS_TxPacket (TDeviceID dvid, uint8_t id, uint8 cflag, uint8_t *param, uint32_t len, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t id

      対象とするID (1~127, 255)。

    • uint8 cflag

      使用するフラグ。

    • uint8_t *param

      送信するパラメータの保存先。

    • uint32_t len

      送信するパラメータのサイズ。

    • TErrorCode *err

      エラーコード。

  • 戻り値

    インターフェースより送信が行われた場合はtrue、それ以外はfalseを返す。

  • 使用例
TDeviceID  dev;
uint8_t    param[] = {0xff, 0, 0};
dev = RS_OpenPort ("\\\\.\\COM10", 115200);
if (dev) {
  // ID=1のFLASH書込と再起動
  if (RS_TxPacket (dvid, 1, 0x40, param, 3, NULL)) {
    Sleep (100);
    RS_TxPacket (dvid, 1, 0x20, param, 3, NULL);
  }
  RS_ClosePort (dev);
}
Page Top

RS_RxPacket anchor.png[30]

リターンパケットを受信する。
基本的にRS_TxPacketとペアで使用する。リターンパケットが得られない状況で使用するとタイムアウトするまで返らない。
なお、本APIはRS_SetTimeOutOffsetで設定されたオフセット値は使用せず、引数で指定された受信タイムアウトのみが適用される。

bool RS_RxPacket (TDeviceID dvid, uint8_t *rdata, uint32_t rdatasize, uint32_t *rlen, uint32_t timeout, TErrorCode *err);
  • パラメータ
    • TDeviceID dvid

      RS_OpenPortで開いた際のTDeviceID。

    • uint8_t *rdata

      受信バッファ。
      リターンパケットを受信するのに十分なサイズを確保しておく必要がある。

    • uint32_t readsize

      rdataのサイズ。

    • uint32_t *rlen

      実際に受信されたリターンパケットのサイズ。

    • int timeout

      受信タイムアウト[ms]。

    • TErrorCode *err

      エラーコード。

  • 戻り値

    受信成功時はtrue、それ以外はfalseを返す。

  • 使用例
    #define ORGID  1
    #define NEWID  50
    int l;
    TDeviceID  dev;
    uint8_t    param[50], rbuf[50];
    dev = RS_OpenPort ("\\\\.\\COM10", 115200);
    if (dev) {
      // ORGIDのIDをNEWIDに書き換え
      param[0] = 4;     // IDのアドレス
      param[1] = 1;     // データ長
      param[2] = 1;     // カウント
      param[3] = NEWID; // 新しいID
      if (RS_TxPacket (dev, ORGID, 0x03, param, 4, NULL)) {
        // 新しいIDに書き換わった応答を受信
        if (RS_RxPacket (dev, rbuf, sizeof (rbuf), &l, 100, NULL)) {
          // 受信データを確認
          if (rbuf[2] == NEWID && rbuf[11] == NEWID) {
            // FLASHの更新
            param[0] = 0xff;
            param[1] = 0;
            param[2] = 0;
            RS_TxPacket (dev, NEWID, 0x40, param, 3, NULL);
          }
        }
      }
      RS_ClosePort (dev);
    }
Page Top

RSLIBのオリジナルな定義 anchor.png[31]

TDeviceID
(uint32_t|uint64_t)
インターフェース毎に割り当てられるユニークな値。RS_OpenPortにて自動的に生成される。
TErrorCode
(uint16_t)
API内で検出される16ビットのエラーコード。上位8ビットはAPI内部で検出したエラー、下位8ビットはリターンパケットに含まれるフラグが割り当てられている。
bitmacro name
15ERR_INVALID_DEVID使用できないTDeviceID
14ERR_INVALID_ID指定できないID
13ERR_DIFF_ID異なるIDからの応答
12ERR_ILLEGAL_SIZE異常なデータサイズ
11ERR_INVALID_PARAM異常なパラメータ
10ERR_COMMシリアルポートエラー
9ERR_CHECKSUM異常なチェックサム
8ERR_TIMEOUT受信タイムアウト
7ERR_RS_TEMP温度リミットエラー
6
5ERR_RS_TEMPALARM温度リミットアラーム
4
3ERR_RS_FLASHフラッシュROM書き込みエラー
2
1ERR_RS_PACKET受信パケット処理不可能エラー
0


Last-modified: 2014-03-19 (Wed) 15:57:39 (JST) (2264d) by yoshida