基于OHCI的USB主机 —— OHCI(传输描述符)

传输描述符(TD
传输描述符( TD )是系统内存的数据结构,被 HC 用于定义从端点收发数据的缓冲区。 TD 分为 2 个类型:通用 TD 和同步 TD 。通用 TD 用于中断、控制和批量端点,同步 TD 用于同步传输。使用两种不同的 TD 类型是因为缓冲区类型的不同。对于 U 盘主机控制器来说,不使用同步传输。
 
若干个传输描述符组成队列链接到 ED 上。 ED 提供传输 TD 数据所需要的端点地址。 HCD TD 增加到队列中,而 HC TD 从队列中删除。 HC TD 从队列删除后,将其链接到已完成队列,这个过程叫做“释放”。 TD 的释放原因包括正常释放和错误释放。当 TD 释放后,释放情况代码被写到 TD 中,以便 HCD 确定释放原因。
 
TD 是按照顺序进行处理的。它们被链接到 ED 上。 TD 队列的第一个 TD 指针放在 ED NextTransferDescriptor 字段, HC 从该 TD 开始处理队列。当 TD 被释放,就会从队列中删除,该 TD NextTransferDescriptor 字段所指向的下一个 TD 被转移到队列头。当 HC 处理 ED 的时候,只会产生一个事务。 HC 只有在当前 ED 的所有 TD 都处理完毕后才会产生下一个事务。
 
在每一个事务完成以后就会更新通用 TD 。有 4 个字段会被更新: CompletionCode DataToggleControl CurrentBufferPointer ErrorCount
 
DataToggleControl 字段反映了下一次传输所需要的数据分组 PID 。如果当前包成功传输, HC 就会设置 DataToggleControl 字段最高位,并切换最低位以反映下一次传输所需要的新的数据分组 PID 。如果当前包没有收到 ACK NAK ,则该字段不会被修改。
 
CurrentBufferPointer 表示当前包传输后是否收到 ACK 或者是否有错误。如果 HC 收到 ACK 或带有不正确切换标记的 NAK CurrentBufferPointer 字段就不会更新,因为 HC 需要重试当前包。如果 CurrentBufferPointer 字段需要更新,包内传输的字节数将会加到当前的 CurrentBufferPointer 字段。如果当前包跨越了页边界,则 CurrentBufferPointer 字段的高 20 比特位将会更新为 BufferEnd 字段的高 20 比特位,以反映页基地址的变化。 CurrentBufferPointer 的低 12 位将会滚动到正确的值以代表新的包地址。
 
如果包传输发生错误, ErrorCount 字段会加 1 。如果 ErrorCount 的值为 2 ,同时有其它的错误发生, TD 就会被释放,并且在 CompletionCode 字段设置错误代码。
 
CompletionCode 字段表示通用 TD 是否传输成功。如果事务成功,则该字段被设置为“无错误”,否则设置为相应的错误代码。对于通用 TD ConditionCode 字段的值只有在 TD 在已完成队列中的时候才有意义。对于 CRC 、位填充错和设备没响应错误, TD 在错误发生 3 次以后才会被释放到已完成队列。对于拖延、数据溢出、数据不足等错误, TD 在第一次发生错误的时候就会被释放到已完成队列。通用 TD 没有用到缓冲区溢出和缓冲区不足的错误。
 
当通用 TD 带着错误被转移到已完成队列时, ED Halted 字段被设置为 1 ,以暂停处理 TD 队列,直到软件清除了错误状态。

你可能感兴趣的:(基于OHCI的USB主机 —— OHCI(传输描述符))