連載
» 2013年07月12日 10時00分 公開

Android USBマスストレージクラスのパケットを理解しよう!実践しながら学ぶ Android USBガジェットの仕組み(12)(3/3 ページ)

[村上雅彦、舟元拓斗、森崇(永和システムマネジメント 組込み技術センター),MONOist]
前のページへ 1|2|3       

5.SCSIコマンドを追い掛けよう

 それでは、前回解析したSCSIコマンドの解析を始めましょう。解析のポイントは以下の2点です。

  • ポイント1:ホストはどうやってAndroidをリムーバブルディスクとして認識するのか
  • ポイント2:AndroidをCD-ROMドライブとして認識させるにはどうすればよいのか

 というわけで、早速、SCSIコマンドを1つずつコツコツと見ていきましょう……と、言いたいところですが、大量のパケットを1つ1つ見ていくのは現実的ではありません。そこで、筆者の方で、上から下までざっと眺めて、当たりを付けてみましたので、本稿ではポイントを絞って解説していきます。

 SCSIコマンドの流れは、ユーザー操作と連動して、大きく分けて下図のように2つのフェーズに分類することができました。まずは、各フェーズのコマンドの流れの概要を把握してみましょう。

図 【※画像クリックで拡大表示】

5.1.USB接続直後のコマンドの流れを把握する

 まず、PC上での操作として、USB接続直後、PCはAndroidをリムーバブルディスクとして認識していました。しかし、ディスクへアクセスするとエラーとなりました。

 このときのSCSIコマンドの流れは、INQUIRYというコマンドが1回だけ発行され、その後、「TEST UNIT READY」「REQUEST SENSE」「READ CAPACITY」が繰り返し発行され続けていました(注2)。

※注2:実際には、その他のコマンドも発行されていましたが本質的ではなさそうでしたので省略しています。


 詳細は、コマンドの応答データを実際に見てみる必要がありますが、この流れから推測をめぐらすと、ホストがAndroidをリムーバブルディスクとして認識した原因としては、最初に1回だけ発行されたINQUIRYが大変怪しいですね。その後に繰り返し発行され続けているコマンドは、Android側でマウント操作が行われるのを監視しているからではないか? と考えると筋が通りそうです。

5.2.マウント直後のコマンドの流れを把握する

 マウント直後は、PCからAndroid内のSDカードにアクセスできるようになりました。

 このときのSCSIコマンドの流れはどうかというと、繰り返し発行されていた、TEST UNIT READY、REQUEST SENSE、READ CAPACITYコマンドが止まり、「READ10」が連続して発行されるようになりました。この流れから推測すると、Androidをマウントすることで、ホスト側のマウント監視が終わり、SDカードのデータをREAD10コマンドで取得し始めたと考えられます。

5.3.SCSIコマンドの応答データを解析する

 以上が大まかなコマンドの流れと推測です。それでは、次にコマンド応答データとSCSIコマンド仕様を参照しながら、裏付け調査を行っていきましょう。

(1)INQUIRY応答データ

図

 INQUIRY応答データを参照すると上図の通りでした。ポイントは、「PDT(Peripheral Device Type)」と「RMB(Removable Medium Bit)」です。PDTは、デバイスがその種類を宣言するためのメンバです。“PDT=0x0”の意味を仕様書で参照すると、「フロッピーディスクなどの直接アクセス可能なデバイス」と記載があります。RMBは、メディアを抜き差しできるかどうかのフラグであり、7bit目が1であると抜き差し可能という意味になります。以上より、AndroidはPCに対して、INQUIRYコマンド応答で「ボクは直接アクセス可能で、メディアを抜き差しされるデバイスです」と宣言していることになります。明らかに、これがリムーバブルディスクとして認識させる要因といえますよね!

 ということは、INQUIRY応答で「ボクはCD-ROMドライブです」と宣言すれば、CD-ROMドライブになりそうな気がしませんか? 実際、仕様書を参照してみると、“PDT=0x5”はCD-ROMデバイスという記載がありました。ここがAndroidの最初の改造ポイントとなります。

(2)REQUESET SENSEの応答データ

図 【※画像クリックで拡大表示】

 REQUEST SENSE応答データを参照すると上図の通りでした。ポイントは、「SENSE KEY」と「ADDITIONAL SENSE CODE」です。これらの値は、マウント前後で値が変わっていました。仕様書の記載を確認した結果を以下に示します。

フェーズ SENSE KEY ADDITIONAL SENSE CODE 説明
USB接続直後 0x2 0x3A MEDIUM NOT PRESENT
マウント直後 0x6 0x28 NOT READY TO READY TRANSITION - MEDIA CHANGED

 Androidは、REQUEST SENSEの応答で現在のデバイスの状態を返しており、USB接続直後は「メディアなし状態」と通知し、マウント後はSDカードへのアクセスが可能になったため、「メディア状態がREADYへ変化した」と通知したと解釈できます。つまり、ホストはREQUEST SENSEコマンドで、リムーバブルディスクにメディアが挿入されるかどうかを確認していたのですね。

(3)READ CAPACITYの応答データ

図 【※画像クリックで拡大表示】

 READ CAPACITYの変化は一目瞭然であり、マウント後にメディアの容量情報(ブロックサイズ=512バイト、最終ブロック番号=0x2edfff)を返すようになっています。この情報を基に、後続のREAD10コマンドでデータの読み込みを開始し、SDカードへのアクセスが可能になったといえます。

6.まとめ

 今回は、UMSクラスのパケットを解析する上で前提となる基礎知識を概説した上で、前回積み残していた疑問点を調査しました。その結果、AndroidをCD-ROMドライブとして認識させるには、SCSIコマンドのINQUIRY応答データを改造すれば対応できそうであることが見えてきました。

 とはいえ、INQUIRY応答データを変えると、ホストが送信するSCSIコマンドの種類や内容も変わってくることは容易に想像ができます。最終回となる次回では、AndroidのUMSクラスのドライバを改造し、CD-ROMドライブとして認識させたいと思います。お楽しみに! (次回に続く)


Android コーナー

Androidコーナー
「Android(アンドロイド)」の組み込み機器への適用からアプリ開発、レポート、ニュースなどさまざまな技術情報・最新動向をお届けする!!

>>コーナーTOPはこちらから


前のページへ 1|2|3       

Copyright © ITmedia, Inc. All Rights Reserved.