2013年5月20日月曜日

YubiKey Personalization Library (COM/ActiveX)


誰も解説してなさそうなものを触ったほうが面白いと思うので、試しに開発者向けの YubiKey Personalization Library の Windows COM/ActiveX v2.3 を叩いてみます。



名前から Personalization Tool と同じような設定機能をプログラムから叩くときに使うものと推測できると思います。

YubiKey Personalization Library
http://www.yubico.com/develop/open-source-software/personalization-libraries/

ここでは、Windows の OLE / COM / ActiveX などの技術体系に対する最低限の基礎知識を持っている前提で話を進めます。知らない場合は他の解説している所で補完して頂けると幸いです。

私の場合は Win7 64bit 環境なのですが、32bit版を叩きたいため、先ほどのページから次のをダウンロード

>> Binary installer 32-bit / x86 (Digitally signed)

とりあえず、デフォルトの設定でインストールしてみました。
スタートメニューに Yubico - Yubikey Configuration API が追加されてます。

その中に、Yubikey Configuration COM API という PDF ファイルへのショートカットがあるのですが、ウェブで公開されている User guide と比べてみると、ウェブの方が新しいようです。

開発資料の場合、必ずしも新しい方が正確である保証はありませんが、書かれている履歴を見ると "Changed document templete" という事から、文書の体裁を変えただけのようです。とりあえずは、ドキュメントのバージョンがそれぞれ違う事を念頭に、私は最新の資料を見ながら進めることにしました。


まず、Windows 上で COM を使う場合はファイルを配置するだけのインストールではダメで、regsvr32 を使った登録が必要となります。これはインストーラーで実行される場合もありますが、YubiKey の COM モジュールは手動でのインストールが必要です。注意点として Windows Vista 以降は UAC の関係から管理権限を持ったコンソール上で実行しなければなりません。通常のコマンドプロンプトで実行した場合、必ず COM 登録は失敗してしまいます。

Win7 64bit 上で 32bit版の設定手順を書いておきます。bit が違う環境であれば、フォルダが異なるので注意してください。

私の環境では以下に COM の実体となる dll がインストールされていましたので、
C:\Program Files (x86)\Yubico\Yubikey Configuration COM API\Bin\x86\YubiKcom.dll

スタートメニューからコマンドプロンプト(cmd)を Ctrl + Shift + Enter で(管理権限を持たせて)起動し、一般的な COM 登録と同じように進めます。

> cd C:\Program Files (x86)\Yubico\Yubikey Configuration COM API\Bin\x86\
> regsvr32 YubiKcom.dll

次のダイアログが出れば登録成功です。



ちなみに、アンインストールする際には、regsvr32 /u で登録の解除設定が必要となります。


個人的に手っ取り早く、COM の確認を行うために、手元にインストールしてある 32bit版 Excel の VBA から叩いてみることにします。

Excel を起動し、Alt + F11 で VBA を起動、ツール - 参照設定 でダイアログを開きます。
ここに Excel VBA から利用可能な COM/ActiveX の一覧が出るわけですが、32bit版 Excel から叩けるのは、32bit でコンパイルされた COM/ActiveX のみです。

※ このような理由があるために、64bit版ではなく 32bit版を選択しました

私の環境では、この一覧の中に『Yubico YubiKcom 2.3 Type Library』が追加されていたため、これにチェックを付けて [OK] を押下し、ダイアログを閉じます。これで VBA からタイプライブラリが参照できているため、YubiKcom で定義されている型や公開情報が全て使えるようになります。要は、面倒なことをしなくても、コード補完が効くようになる。ということです。


下手に YubiKey の設定を変える API を叩いてしまうと厄介なので、試しに YubiKey が刺さっているかどうか?を確認してみます。


YubiKeyConfig がクラスの定義みたいですね。使用する言語によっては IYubiKeyConfig 等になったりするかもしれません。

ドキュメントからそれらしい機能を探してみると、YubiKey が PC に刺さっているかどうかは ykIsInserted プロパティで調べられるらしく、結果は接続時 1 / 未接続 0 という感じの数値で返すようです。ということで、以下のようなコードで確認してみます。

Option Explicit

Sub hoge()
  Dim yk As New YubiKeyConfig
  Debug.Print IIf(yk.ykIsInserted, "Inserted", "Not inserted")
End Sub

IIF() を知らない人のために解説しておくと、第1引数を BOOL っぽく比較し、True だと第2引数を返す。False だと第3引数を返します。要は3項演算子のようなものです。比較は 0 以外 / True / 長さが1以上の文字列などを True として扱うようです。流石 VB という感じの適当な判定ですが、これを実行すると、私の環境ではイミディエイトウィンドウに意図した結果が報告されました。

Excel などの環境が無い状態でも手軽に確認したい場合、API の Samples\HTML に含まれる yksample.htm が IE の JavaScript(JS) 上で COM を生成して動かすサンプルコードになっています。これにも ykIsInserted のテストが含まれているので確認できるはずです。ただ、JS 上では、当然タイプライブラリが使えないため、他の環境の方が純粋に叩きやすいでしょう。

なお、ykProgram は Slot の書き換え処理の実行だったりするため、下手に叩くと設定が消えることになります。特に注意しましょう。

Personalization Library に含まれる機能については、実際に pdf の User guide を見てもらったほうが早いかもしれませんが、ざっくり機能を見渡すと(当然ではありますが)設定周りに限定した Low-level の機能が公開されている感じですね。

接続確認 ykIsInserted
設定確認 ykIsConfigured
デバッグモード設定 ykEnableDebug
※ メッセージダイアログを介しての設定内容表示など、ちょっと特殊かな?
Slot の設定関連 ykProgram 他

あと、コールバック関連として、ykInserted と ykRemoved があり、ykEnableNotifications を使ってコールバック自体を有効化するみたい。なので、YubiKey の接続や切断をトリガーにした軽めの制御も可能。



なお、今回叩いているのは Personalization Library であるため、個人で使うには面白く無いかもしれませんが、YubiKey の接続と同時に Slot に特定の設定を行うような、特定環境向けの設定ツールなど、組織的な運用環境を整える用途で部品として使う場合に良いでしょう。


最後に、 Personalization Tool の設定で確認した RFC 4226 HOTP の設定を実際にコードで行ってみましょう。以下の様な感じで作りました。

Sub setupSampleHOTP()
  const KEY = "3132333435363738393031323334353637383930"
  Dim yk As New YubiKeyConfig
  
  If (0 = yk.ykIsInserted) Then Exit Sub
  
  yk.ykFlagProperty(ykFLAG_SECOND_CONFIG) = True
  yk.ykFlagProperty(ykFLAG_APPEND_CR) = True
  yk.ykFlagProperty(ykFLAG_OATH_HOTP6) = True
  yk.ykKey = key
  
  Debug.Print yk.ykProgram
End Sub

これで YubiKey を挿して実行すると、ykOK(0) がデバッグ出力され、実際にパスワードを発行してみると Slot2 に意図した HOTP が設定されている事を確認しました。YubiKeyConfig での設定の注意点として、秘密鍵の設定はスペースを含めず16進の文字列をそのまま詰めて渡せば良いようです。もし、更に細かい設定を行ったり、他の認証方式を設定する場合、事前に Personalization Tool で設定の確認と検証用の出力結果を数パターン取っておき、あとはドキュメントを読みつつコードを書きながら試していくと、細かい設定も制御できるのではないでしょうか?

他、本論ではないコードの注意点として、個人的には Not yk.ykIsInserted と書きたいのですが、ykIsInserted の結果は厳密な BOOL や (0, -1) ではないため、Not なんて使うと残念ながら意図した結果にはなりません。Exit せずブロックの中で処理しても良いのですが、極力インデントせず不要なロジックからはすぐ抜ける方が好きな書き方なのでこうしています。


さて、設定できることは解ったんで、次回は同じ COM つながりで、開発者向け Low-level library の Client COM API を叩いてみます。




完全に余談にはなりますが、Windows の COM/ActiveX に対して、初期調査を行う場合や、この程度の小規模テストを行う場合、VBA は非常に強力なツールに成り得ます。ツールそのものが極めて軽いこともあり、限定的な環境における生産性は侮れません。ただし、ポインタでデータを渡す等、VBA から扱いにくい領域が出てきた場合や、少し規模が大きくなり、まともなロジックを書く必要が出てきた場合、また、アプリケーションとして完結させたい要望が出てきた場合には .NET 等の他言語への移行を真剣に考え、さっさと移行すべきです。保守性や拡張性は所詮旧来の VB 程度なので、ある規模を超えるとプログラマへの負担も大きく使うメリットは薄れるでしょう。適用範囲を割り切るのが賢い使い方だと私は考えます。

また、COM/ActiveX に限れば Windows 固有のやや悪しき歴史も持つ技術ではありますが、OS を Windows に限ればサーバ上でも経路さえ整備すれば叩けますし、少し仕掛けが大きくなりますが、COM を動かす部分が Windows 限定なだけなので、ウェブ向けの Wrapper API を整備して、HTTP GET/POST で外部から繋いだりすれば、OS 環境も問わず利用することも可能です。今後の事を考えると、あまり使うべきではない技術なのかもしれませんが、泥臭い業務だとかのビジネス用途では、まだ現役で連携する必要がある所も見かけるため、コストが見合う場合は一考の余地があるかもしれませんね。この辺の内容は世の中に興味ある人って限られるとは思うけど。

以上、余談でした。

0 件のコメント:

コメントを投稿