添加链接
link管理
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接
Zenn
📌

libusb-1.0のざっくりとした使い方

2021/04/03 に公開

libusb は、USBデバイスを扱うプログラムをOSを意識せずに書けるCのライブラリ。現在はバージョン1.0系の開発が続いているが、バージョン0.1系とは互換性がない。しかし、ネット上で公開されているプログラムやチュートリアルにはバージョン0.1系のものも多く、また、たとえばDebianのように 「libusb-dev」という名前でインストールできるパッケージが0.1系 のプラットフォームもあるので、2021年4月現在はちょっと混乱しやすい状況にある気がする。

なお、2021年4月現在、 libusb-1.0のDebianにおけるパッケージ名は「libusb-1.0-0-dev」 である。

libusb-1.0の使い方は、いきなりAPIを見てもよくわからない。USBの仕様を片手に "Modules" のセクションからドキュメントを読んでいくとなんとなくわかってくる。

  • http://libusb.sourceforge.net/api-1.0/structlibusb__device__descriptor.html
  • libusb_device_descriptor のフィールドうち、デバイスを特定するのに使えそうなのは下記の4つ。なお、USB-IFというのは “USB Implementers Forum” のことで、要するにUSBの規格を策定している団体。

    フィールド

    デバイスを特定するには、取得したデバイス一覧に含まれている各デバイスについてデスクリプタを取り出し、上記のフィールドの値を読み出して、それを調べればよい。デスクリプタの取り出しには libusb_get_device_descriptor という関数が用意されているので、だいたい以下のような流れでやっていく。

    struct libusb_device_descriptor desc;
    libusb_device_handle *handle;
    for (i = 0; i < cnt; i++) {
      libusb_device *dev = list[i];
      libusb_get_device_descriptor(device, &desc);
      libusb_open(devive, &handle)
      /* handle と desc を使って何かする */
      ...
    

    上記には、libusb_device_handle 型の handle という変数へのポインタが出てくるが、これはデバイスハンドラと呼ばれており、デバイスに対する実際のI/O操作などの対象になる。デバイス一覧として得られるのが libusb_device 型の変数へのポインタたちで、これを直接いじれそうな気がするかもしれないが、こちらは内部構造を参照できない。デスクリプタを参照する際も、libusb_device 型の変数へのポインタを libusb_open() して得られる libusb_device_handle 型の変数が必要になる。

    じゃあ、libusb_device 型の変数は何のためにあるかというと、これにはデバイスの参照カウンタという役割がある。参照カウンタは、デバイス一覧を取得した時点で「1」が割り当てられ、そのあとはプログラマーが増やしたり減らしたりできる。参照カウンタがゼロになったデバイスはそのセッションで破棄される。

    ちなみに、Vendor IDとProduct IDを指定して一気にデバイスハンドラを得られる libusb_open_device_with_vid_pid() という関数もある。これにコンテキストとVendor IDとProduct IDを引数に指定して実行すれば、返り値として libusb_device_handle 型の変数へのポインタが得られる。

    int vendorId, productId;
    libusb_device_handle *handle;
    handle = libusb_open_device_with_vid_pid(NULL, vendorId, productId)