この方式は、要するにTime Shareingなどの方式に近い。Host上で動くApplication(実際にはClass Driverの可能性が大だろう)やEndpointのDeviceからみれば、あくまでStream PIPEは1つしか見えないが、実際はこのPIPEは仮想化されて、複数のPIPEを適当に帯域を割り振って通すという仕組みだ。これはPCI ExpressのVirtual Channelに近い機能ではあるが、具体的な帯域の割り振り方などはインプリメント次第とされている。

面白いのは、このStreamIDとHost Buffer(Endpoint Buffer)が1:1の関係で割り当てられ、IDが1~65533(FFFDh。ID:0とかID:FFFDh/FFFEhはSystem Reservedとされている)があることで、これは要するにHost側は最大65533個のEndpoint Bufferを用意しなければいけない事になる。まぁ実際には愚直に65533個ものバッファを実装するケースはないとは思うが、このあたりはプロトコル側で実装までかなり考えていろいろな細工を施したPCI Expressと、プロトコルレベルではあまり実装の事を考えていないUSB 3.0の違いが目立つ感じがする。ちなみにEndpointがStream転送のRequestを出したときに、Host側でBufferが準備できない場合、Host側はそのRequestをRejectできる。

次はInterrupt Transferである。Interrupt Transferに関しては、基本的にUSB 2.0とは大きな違いが無い。最大Data Packet Sizeも1024Bytesで、これはUSB 2.0のHigh-speedと一緒(Full-Speedの場合は64Bytes)。ただしBurst Transferが許される(最大3Packetまで)関係で、トータルでは3072Bytesになるのがちょっとした違いだろうか。

一方Isochronous Transferに関しては、基本的な構造はUSB 2.0と同じである。ただし違いとして、

  • Start of frameを送出しない。ただしTiming Informationを、ITP(Isochronous Timestamp Packets)を使って送信する。
  • Power Managementにより省電力モードに入る際には、転送が阻害される。これを防ぐため、新たにPING/PING_RESPONSEというメカニズムを採用した。Isochronous transferの初期化を開始する前に、Host側からDeviceに対してPINK Packetを送出し、これをDeviceが受けてPING_RESPONCE packetが返された場合は、以後そのDeviceは常にActiveと見なされ、省電力化の対象から外す様に配慮される。

といった事が挙げられる。また転送サイズは、USB 2.0がHigh-Speedの場合、Data Paylordは最大1KB(1024Bytes)、Micro-Frameあたり最大3 Transactionが可能なので、3Micro-Frameあたり3KBytesとなる。対してUSB 3.0ではこの3 Transactionを16回連続して実行できるので、合計48KBが転送可能になるという次第だ。このあたりは、その7に出てきた数字そのままである。

さて、このあたりまではほぼUSB 2.0と同じであるが、USB 3.0で新しく追加されたのがDevice Notificationである。279回でもちょっと触れたが、USB 2.0ではDeviceの状態取得をHost ControllerからのPollingで行っていた。たとえばUSBマウスの場合、これまでだとMouseが動いた場合は、「動いた」という情報と、さらにその動いた変量(とりあえずはMouse本体のX/Y軸の移動量とボタンの状態、最近だとさらにスクロールダイアルの変量やら追加のボタン情報やらが加わるだろう)をまとめてData Packetにしておき、Isochronous Transferの転送待ち状態で(Mouse内部の)USB DeviceのBufferに蓄えておく。一方Hostは定期的に(USB 2.0で、ほかに何のデバイスも無い状態ならば理論上8000回/秒の頻度で)HostがDevice→HostのIsochronous Transferを掛ける事で、Mouseが動いたという情報がHost側に送られることになる。

これに対し、USB 3.0ではMouseが動いた事を内部のコントローラが感知したら、その変量などをまとめてData Packet化し、Isochronous Transfer PacketとしてUSB DeviceのBufferに蓄える所までは一緒だが、この後にDevice Notification Packetを送り出す「事が出来る」。というのは、これは必須ではないからだ。Isochronous Transferである以上、一定頻度で必ず転送が掛かるので、これを待てば十分といった用途(例えばUSBマウスだと、普通は毎秒8000回も状況が更新されていれば十分だろう)であれば、無理にNotificationを使う必要はない。ところがもっとデータ量が多く、かつ煩雑に割り込みを掛けたいなんて用途のデバイスを繋ぐ場合(Flash Memoryをファイルシステムだのキャッシュの一部にしているケースがまさしくこれだ)に、このDevice Notificationが活躍することになる。

(続く)