私は何をする必要がありますか:
- レスポンダー (Android を実行している Beaglebone Black) からカスタム ベンダー拡張イベントを生成し、イニシエーターでイベント通知を取得します。
私が使用しているもの:
- Initiator - Portabledeviceapilib.dll (COM 相互運用) ライブラリのマネージ ラッパーを使用する Windows 7 上の C# .Net アプリケーション。
- テスト レスポンダー 1 - Microsoft による MTP シミュレーター 3.0
- Test Responder 2 - Android Jelly Bean 4.1.1 を実行する Beaglebone Black
私がこれまで取り組んできたこと:
イニシエータとレスポンダの間でエンド ツー エンドの通信が正常に行われています。MTP コマンドを送信し、MTP 応答を取得できます。また、レスポンダーから標準イベント通知を正常に取得できます。
問題
イニシエーターがイベントを正常に起動して受信した場合でも、Android からの USB パケットに MTP イベント コードが表示されません。Android の標準イベント コードをカスタム イベント コードに変更しても、適切なイベント メッセージが表示されます (詳細は後述)。
これまでに行ったこと
レスポンダー側で Android ソース コードを参照すると、 /frameworks/av/media/mtp/mtp.hで定義されている MTP イベント コードが見つかりました。
以下は、オブジェクトの追加/削除用に定義されたイベント ID です。
#define MTP_EVENT_OBJECT_ADDED 0x4002
#define MTP_EVENT_OBJECT_REMOVED 0x4003
これらのイベント コードは、MTP 仕様で定義されています。
イニシエーター側でイベントをサブスクライブするために、私はDarene Lewisの記事 (こちら) のガイドラインに従っています。ここで定義された定数のイベントの GUID を使用しています。
ファイルがデバイスに追加されるか、デバイスからファイルが削除されると、MTP イベント通知が起動され、イニシエーターは eventID を定数の 1 つにマップする通知を取得します。私が理解しているように、GUID の最初の 4 バイトはイベント ID に対応しています。
以下は、ファイルの追加および削除イベントの GUID です。
public static Guid WPD_EVENT_OBJECT_ADDED = new Guid( 0xA726DA95, 0xE207, 0x4B02, 0x8D, 0x44, 0xBE, 0xF2, 0xE8, 0x6C, 0xBF, 0xFC );
public static Guid WPD_EVENT_OBJECT_REMOVED = new Guid( 0xBE82AB88, 0xA52C, 0x4823, 0x96, 0xE5, 0xD0, 0x27, 0x26, 0x71, 0xFC, 0x38 );
私のテストは、デバイスからのファイルの追加/削除で構成されていました。
シミュレーターを使用すると、イニシエーターは 2 つのイベント通知を正常に取得し、上記で定義した正しい WPD イベントにマップされます。また、これらのイベントコードが USB パケットに表示されることを確認しました。
Android デバイスを使用している場合、イニシエーターは 2 つのイベント通知を正常に取得し、上記で定義した正しい WPD イベントにマップします。ただし、USB パケットのどこにもイベント コードが表示されません。
パケットに MTP イベント コードが表示されていないにもかかわらず、COM 相互運用ライブラリがイベントの通知を正常に取得する方法がわかりません。
パケット内のイベント コードを確認できないため、デバイスからイニシエーターへのカスタム イベント コードの送信をテストできません。
上記の Android MTP イベント コードをベンダー拡張イベント コード用に変更し (MTP 仕様で 0xC000 - 0xC7FF と記述されているように)、デバイスの libmtp を更新して何が起こるかを確認する実験を行いました。
イニシエータがイベントを取得しないことを期待していましたが、驚くべきことに、イベント コードを変更した後でも、COM 相互運用ライブラリはイベントを受信し、正しい GUID にマップしました。
要約すると、Android を使用している場合、USB メッセージに MTP イベント コードが表示されませんが、イニシエータは何らかの方法で通知を正常に取得します。MTP Simulator を使用すると、USB メッセージに MTP イベント コードが表示されます。