USB2.0设备的休眠挂起及远程唤醒

news/2024/11/18 4:32:19/文章来源:https://www.cnblogs.com/linhaostudy/p/18425855

USB可见设备状态,分为连接(Attached),上电(Powered),默认(Default),地址(Address),配置(Configured)和挂起(Suspended)6个状态。所谓可见,即USB系统和主机可见的状态,其他状态属于USB设备内部而不可见。其中有关电源的,大致可分下面三类:

  • 连接状态(Attached):设备连接,但未提供电源。

  • 上电状态(Powered):设备被复位(Reset),或者说处于地址、配置状态。

  • 挂起状态(Suspended):3 ms未见总线活动而处于省电状态,设备不可用,但仍然保持原有的USB地址和配置。

USB设备的挂起

我们知道,在USB系统中,正常状态下hub或root hub会一直周期性地发送SOF包(Start Of Frame,全速USB每1ms发送一个,高速USB则是125µs发送一个)。根据USB协议,如果USB线上一直处于空闲(Idle)状态超过3ms,设备应该把它当作一个挂起(Suspended)信号,要求设备在10ms内进入挂起状态,并把设备所需的电流大小降到规定的值(对于low-power设备,要求是500 µA,而对于high-power或支持远程唤醒(remote wakeup)功能的设备是2.5mA。

  • 所在USB设备都应该支持挂起状态(Suspending State)。

  • USB设备可以从任意供电状态进入挂起状态。

  • USB设备从上游主机端口接收到持续的IDLE信号超过3.0ms时,USB设备应当认为这是一个挂起的信号,然后开始进入挂起状态。当所有端口无总线活动时,要求设备在10ms内进入挂起状态,并把设备所需的电流大小降到规定的值,即挂起电流值(对于low-power设备,要求是500 µA,而对于high-power或支持远程唤醒(remote wakeup)功能的设备是2.5mA。

  • USB设备面向上游的端口上的任何总线活动都将使其退出挂起状态。

  • 在没有任何其他总线流量的情况下,SOF令牌每(微)帧将发生一次,以防止全速/高速设备挂起。 在没有任何低速流量的情况下,低速设备将在每一帧中看到至少一个保持活动状态发生 SOF,使它们无法挂起。

  • 当处于挂起状态时,设备必须继续为其 D+(全速/高速)或 D-(低速)上拉电阻供电,以保持IDLE状态,以便上游集线器可以保持正确的设备连接状态 。

  • USB设备挂起时,可以停止设备的时钟,以进入低功耗模式。而当USB设备可以通过外部中断唤醒自身,然后再由USB设备唤醒主机。

在挂起状态中,设备必须继续向数据项D+/D-的上拉电阻提供电压以维持Idle状态。而对于USB2.0高速设备,还有些额外的要求:

  • 高速设备在收到挂起信号(3ms空闲)后,应在0.125ms内切换到全速状态,也就是说要把终端电阻移除,并在D+数据线上重新挂上1.5k上拉电阻。

  • 设备在随后的100-875µs内检测数据线上的状态。如果该状态是一个Full speed J,那么说明host发下来的是一个挂起信号;如果此时该状态是SE0,说明是host drive数据线D+到0,这是一个复位信号(复位信号会持续至少10ms时间)。

  • 要注意的是高速设备在挂起状态时处于高速模式,只是所用的是全速信号。一旦从挂起状态恢复回来,会马上进入高速工作状态而无需进行复位操作。

  • 当处于挂起状态时,设备必须继续为其 D+(全速/高速)或 D-(低速)上拉电阻供电,以保持IDLE状态,以便上游集线器可以保持正确的设备连接状态 。

  • USB设备挂起时,可以停止设备的时钟,以进入低功耗模式。而当USB设备可以通过外部中断唤醒自身,然后再由USB设备唤醒主机。

在挂起状态中,设备必须继续向数据项D+/D-的上拉电阻提供电压以维持Idle状态。而对于USB2.0高速设备,还有些额外的要求:

  • 高速设备在收到挂起信号(3ms空闲)后,应在0.125ms内切换到全速状态,也就是说要把终端电阻移除,并在D+数据线上重新挂上1.5k上拉电阻。

  • 设备在随后的100-875µs内检测数据线上的状态。如果该状态是一个Full speed J,那么说明host发下来的是一个挂起信号;如果此时该状态是SE0,说明是host drive数据线D+到0,这是一个复位信号(复位信号会持续至少10ms时间)。
    要注意的是高速设备在挂起状态时处于高速模式,只是所用的是全速信号。一旦从挂起状态恢复回来,会马上进入高速工作状态而无需进行复位操作。

  • USB主机使使用周期性的SOF或Keep alive(低速)阻止设备进入挂起状态。

    • For High-speed, SOF is sent every micro-frame 125us +/- 65ns
    • For Full-speed, SOF is sent every frame 1ms +/- 500ns
    • For Low-speed, Keep Alive (End of Packet) is sent every 1ms in absence of low-speed data
  • USB设备要退出【挂起模式】 可以由Host唤醒,或者自己唤醒。

  • 如果设备配置为高功率(高达 500 mA),并启用了远程唤醒功能,则在挂起期间允许消耗高达 2.5 mA 的电流。

设备的唤醒

设备处于挂起状态时,任何总线上的活动(非空闲信号)都可以把设备唤醒/恢复,从而退出低功耗模式。
因为设备挂起时处于全速信号,在当host需要把将设备退出suspend状态时,需要先发送一个持续时间超过20ms的Fulll Speed K状态。设备看到K状态结束的1.3us内醒过来,而host需要在3ms内发送uSOF信号以维持正常的高速信号模式,否则设备又将进入suspend。

当主机想要在挂起后唤醒设备时,它通过将数据线上的信号极性反转至少 20ms 来实现。该信号以分组信号的低速端完成。

具有远程唤醒功能集的设备也可以自行启动恢复。它必须处于空闲状态至少 5ms,并且必须在 1 到 15ms 之间应用唤醒 K 条件。主机在 1 ms 内接管恢复信号的驱动。

设备的远程唤醒

同样,设备也可以换醒host,比如电脑待机时通过USB键盘来换醒主机,这种功能称之为“远程唤醒”(remote wakeup)
在配置描述符中,USB设备会将是否支持远程唤醒的能力报告给主机。

GetStatus返回请求

GetStatus()设备请求返回的信息,包含是否允许远程唤醒的信息。
详见:USB读取状态GET_STATUS

在配置描述符中,偏移第7个字节的描述属性项,包含了设备是否支持远程的功能位。Bit5代表是否支持远程唤醒。

    ------------------ Configuration Descriptor -------------------
bLength                  : 0x09 (9 bytes)
bDescriptorType          : 0x02 (Configuration Descriptor)
wTotalLength             : 0x010B (267 bytes)
bNumInterfaces           : 0x04 (4 Interfaces)
bConfigurationValue      : 0x01 (Configuration 1)
iConfiguration           : 0x00 (No String Descriptor)
bmAttributes             : 0xA0D7: Reserved, set 1     : 0x01D6: Self Powered        : 0x00 (no)D5: Remote Wakeup       : 0x01 (yes)D4..0: Reserved, set 0  : 0x00
MaxPower                 : 0x32 (100 mA)

禁用USB设备的远程唤醒

当然,也可通过 USB清除特性请求CLEAR_FEATURE 来禁止USB的远程唤醒功能。

USB远程唤醒的编程

如我们有一个STM32做的USB设备,通过外接GPIO按键触发实现远程唤醒PC主机。

Resume的代码其实是一个状态机,是将STM32远程唤醒的寄存器置高10ms,即10个EOF,然后再置低,以使USB设备通过D+/D-的电信号进行远程唤醒。

STM32寄存器定义将此位置高1-15ms,将进行远程唤醒操作。

USB远程唤醒的编程

当然,支持远程唤醒也是需要PC机的配合的,一般情况下是在BIOS中的电源管理进行配置。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/801703.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

CSP-S 2024 提高组初赛解析(更新至单项选择)

单项选择 1在 Linux 系统中,如果你想显示当前工作目录的路径,应该使用哪个命令? A pwd B cd C ls D echopwd : print working directory cd : 跳转到指定目录 ls : 列出当前目录的所有子文件和子文件夹 echo : 输出指定内容 2假设一个长度为n的整数数组中每个元索值互不相同…

[CVPR2024]DeiT-LT Distillation Strikes Back for Vision Transformer Training on Long-Tailed Datasets

在长尾数据集上,本文引入强增强(文中也称为OOD)实现对DeiT的知识蒸馏的改进,实现尾部类分类性能的提升。 动机ViT相较于CNN缺少归纳偏置,如局部性(一个像素与周围的区域关系更紧密)、平移不变性(图像的主体在图像的任意位置都应该一样重要)。因此需要大型数据集进行预…

MobaXterm24.2 分析

MobaXterm 目录MobaXterm0、启动窗口 TForm11、TForm1_FormCreatedecrypt_9FDA481)xxBase64Decode_9FD80C2)DecryptBytes_9FD9DC2、许可结构1) Type2) version_info_3A83) user_limit4) Version5) unuse6)NoGames7)NoPlugins解析函数parse_9FEB5Cothersub_A03F80TFormAbout…

ABC372 F 题解

ABC372 F 题解F - Teleporting Takahashi 2 先把问题转化一下:把环断开成链,复制 \((K + 1)\) 层,每走一步就相当于前进一层:可以想到一个简单的 dp:设 \(f(i, j)\) 表示走到第 \(i\) 层第 \(j\) 个位置的方案数。初始化:\(f(0, 1) = 1\),其它均为 \(0\),表示 Takahash…

【做题笔记】收集邮票 做题笔记

水。P4550 收集邮票展开目录 目录P4550 收集邮票ReadingStep 1Step 2Code彩蛋Reading \(k\ge 1\) 时,可以通过支付 \(k\) 元钱获得一张 \(n\) 种邮票中的某种邮票。这 \(n\) 种邮票等概率出现,求买到全部 \(n\) 种邮票的花费期望。 Step 1 \(k\) 次 \(k\) 元太难搞了,干脆直…

单机版 ClickHouse 部署和 SpringBoot 程序访问

ClickHouse 是俄罗斯的 Yandex 于 2016 年开源的列式存储数据库(DBMS),使用C++语言编写,主要用于在线分析处理查询(OLAP),能够使用SQL查询实时生成分析数据报告。 OLAP 为联机分析处理,专注于统计查询;OLTP 为联机事务处理,专注于增删改。 ClickHouse 的优势在于单表…

self supervised learning

self supervised learning 自监督学习,按照机器学习中传统分类方法,监督学习,无监督学习,强化学习,有些还会有半监督学习等。 监督学习,以计算机视觉领域中最简单的任务为例,给你一张只有一只狗的图,让你说这图是什么,你肯定说是狗。那么在计算机视觉任务重,给这图打…

用户验收测试指南8实施测试

8 实施测试 到目前为止,我们已经规划了我们的 UAT 演习,并制定了测试的总体战略,然后设计了所有测试并编写了测试脚本。现在,我们已准备好实施计划和进行测试。 在本章中,我们将介绍如何安排所有测试,以实现我们的测试策略,并根据验收标准评估系统。为此,我们需要记录所…

Linux中删除文本中所有的重复的字符保持唯一

001、[root@PC1 test]# ls a.txt [root@PC1 test]# cat a.txt ## 测试文本 abk akkkkccc 8777 ,,, aaaf 333444 --- uukk22 [root@PC1 test]# cat a.txt | tr -s [:alnum:] ## 删除连续的重复字符 abk akc 87 ,,, af 34 --- uk2 [root@PC1 test]# …

ConcurrentLinkedQueue详解(图文并茂)

前言 ConcurrentLinkedQueue是基于链接节点的无界线程安全队列。此队列按照FIFO(先进先出)原则对元素进行排序。队列的头部是队列中存在时间最长的元素,而队列的尾部则是最近添加的元素。新的元素总是被插入到队列的尾部,而队列的获取操作(例如poll或peek)则是从队列头部…

Linux 中实现文本中所有的单词的第一个字符大写,其余字符小写

001、[root@PC1 test]# ls a.txt [root@PC1 test]# cat a.txt ## 测试数据 afdf eDET FDSS FFde fexk mxnd [root@PC1 test]# cat a.txt | awk {for(i = 1; i <= NF; i++) {$i = toupper(subst…