这是我的小文章,描述了(几乎)我了解的有关Apple Lightning接口和相关技术的所有信息:Tristar,Hydra,HiFive,SDQ,IDBUS等。但是,首先要提个警告……
请自担风险阅读本文!该信息基于我对角阅读的许多内部Apple内部材料(数据泄漏,示意图,源代码)。而且,当然,根据我自己的研究。我必须警告您,我从未做过此类研究。因此,本文可能使用了不正确或简单的奇怪术语,而部分或完全不正确!
在深入探讨之前,让我们简要了解一下这些术语:
什么是闪电?
自2012年底以来,Lightning是大多数Apple iOS设备中使用的数字接口。它取代了旧的30针连接器。
上图是连接器插座,下图是其引脚排列:
请注意,在连接器中,连接器两侧的插针未按相同顺序连接。因此,主机设备必须在执行任何操作之前确定电缆的方向。
尽管并非总是如此。我遇到的许多Lightning配件在连接器中都有镜像的引脚排列。
什么是Tristar和Hydra?
Tristar是每个带有Lightning连接器的设备中内置的集成电路。它本质上是一个多路复用器:
除其他事项外,其主要目的是在插入插头后立即连接到Lightning公连接器-确定方向,配件ID并正确布线内部接口(如USB,UART和SWD)。
Hydra是Tristar的新变种,自iPhone 8 / X起就使用。可能最重大的变化是对无线充电的支持,但这仍有待验证:
我知道Tristar / Hydra的五个主要变体:
- TI THS7383 -iPad mini 1和iPad 4中的第一代Tristar
- 恩智浦CBTL1608A1 -iPhone 5和iPod touch 5中的第一代Tristar
- NXP CBTL1609A1 -iPod nano 7中神秘的第一代Tristar- 来源
- 恩智浦CBTL1610Ax- 第二代TriStar,自iPhone 5C / 5S起使用,并且显然在不支持无线充电的所有其他产品中使用。存在多个世代(x是世代数)
- 恩智浦CBTL1612Ax -Hydra与iPhone 8 / X以及显然支持无线充电的所有其他产品一起使用。存在多个世代(x是世代数)
从现在开始,我将仅使用术语TriStar,但请记住,它也代表Hydra,因为它们在本文中涵盖的大多数方面都非常相似。
什么是HiFive?
HiFive是Lightning的子代,即插头连接器。它还包含一个逻辑门-该芯片被称为SN2025 / BQ2025。
什么是SDQ和IDBUS?
这两个术语通常被认为是各种同义词。为了方便起见,我将仅使用术语IDBUS,因为它对我来说似乎更正确(这就是THS7383规范中所称的技术)。
因此,IDBUS是用于Tristar和HiFive之间通信的数字协议。非常类似于Onewire协议。
现在我们可以开始
让我们听听Tristar和HiFive的交流。获取一个逻辑分析仪,一个带插孔和公连接器的Lightning转接卡,一个附件(常规的Lightning-to-USB电缆非常有用),当然还有一个带Lightning端口的设备。
首先,将逻辑分析仪通道连接到提升板的两个ID线(引脚4和8),然后将板连接到设备,但仍不连接附件:
此后立即开始采样(2 MHz或更高的任何频率都可以)。您将看到如下内容:
如您所见,Tristar依次轮询每个ID行。但是由于我们没有插入任何附件,所以调查显然失败了。在某个时候,设备会厌倦无休止的故障流并将其停止。现在,让我们看一下轮询过程中到底发生了什么:
首先,我们看到一个很长的间隔(大约1.1毫秒),当该级别很高时,却什么也没发生:
显然,该时间用于为内部HiFive电容器充电-然后,来自其的能量将用于为内部逻辑芯片供电。
接下来会发生更多有趣的事情:
显然,这是一些数据的流。但是如何解释呢?如何解密?让我们实际上将其划分为最小的重要部分-我所说的单词:
实际上,一个单词是由下降到上升,下降到下降的组合:
- 内容阶段 -确定单词含义的时间间隔
- 恢复阶段 -在接收方处理内容阶段和/或在发送阶段准备下一个字显然需要的时间间隔
这是一张上面我们讨论过的两个阶段的著名单词及其间距的表(所有单位以微秒为单位):
内容 | 复苏 | ||||
---|---|---|---|---|---|
字 | 敏 | 典型值 | 最高 | 敏 | 典型值 |
打破 | 12 | 十四 | 十六 | 2.5 | 4.5 |
唤醒 | 22 | 24 | 27 | 1100? | |
零 | 6 | 7 | 8 | 3 | |
之一 | 1个 | 1.7 | 2.5 | 8.5 | |
零和停止* | 6 | 7 | 8 | 十六 | |
一站式* | 1个 | 1.7 | 2.5 | 21 |
上面的表,我们现在可以构建一个简单的协议解码器:
如您所见,主机首先发送一个BREAK-当Tristar要发送新请求时,主机始终以该字开头。然后进入数据传输阶段。请注意,字节的最后(第8个)位具有更长的恢复阶段。数据传输阶段结束后,主机将发送另一个BREAK。然后,孩子必须发送响应(在至少2.5微秒的延迟后-参见表)。 Tristar将等待约2.2毫秒以做出响应。如果在此时间段内未给出响应,Tristar将尝试询问另一个ID行。
现在让我们使用上面的示例-在数据阶段
0x74 0x00 0x02 0x1f
:
0x74
-请求/响应的类型。对于请求始终为偶数,对于响应始终为奇数(请求类型+1)
0x00 0x02
-事实数据。可能是空的
0x1f
-这是请求类型字节和所有数据的CRC8(多项式-0x31,初始值-0xff)
让我们将一些附件连接到我们的钻机上,看看会发生什么。我将使用Apple原来的Lightning-to-USB电缆:
这是0x74请求后IDBUS上显示的内容:
HiFive回答了!如果进一步滚动,则会看到许多其他请求/响应对:
某些请求不需要响应:
解释IDBUS请求和响应
最重要的IDBUS请求是0x74,它用于两个目的:告诉HiFive打开全电压和安培数(如果附件支持),询问电缆支持的插针配置以及其他一些元数据。
对于0x75响应数据的编码方式知之甚少。但是旧的Tristar规范中有一些可用的位:
第一个响应数据字节0x75
7 | 6 | 五 | 4 | 3 | 2 | 1个 | 0 |
---|---|---|---|---|---|---|---|
ACCx | Dx | 数据[43:40] |
在ID0上找到ID时的ACCx配置
ACCx [1:0] | ACC1 | ACC2 | HOST_RESET |
---|---|---|---|
00 | Hi-Z(IDBUS) | 高Z | 高Z |
01 | UART1_RX | UART1_TX | 高Z |
十 | JTAG_DIO | JTAG_CLK | 高Z |
十一 | 高Z | 高Z | 高 |
在ID1上找到ID时的ACCx配置
ACCx [1:0] | ACC1 | ACC2 | HOST_RESET |
---|---|---|---|
00 | 高Z | Hi-Z(IDBUS) | 高Z |
01 | UART1_RX | UART1_TX | 高Z |
十 | JTAG_DIO | JTAG_CLK | 高Z |
十一 | 高Z | 高Z | 高 |
在ID0上找到ID时的Dx配置
Dx [1:0] | DP1 | DN1 | DP2 | DN2 |
---|---|---|---|---|
00 | 高Z | 高Z | 高Z | 高Z |
01 | USB0_DP | USB0_DN | 高Z | 高Z |
十 | USB0_DP | USB0_DN | UART1_TX | UART1_RX |
十一 | 高Z | 高Z | 高Z | 高Z |
在ID1上找到ID时的Dx配置
Dx [1:0] | DP1 | DN1 | DP2 | DN2 |
---|---|---|---|---|
00 | 高Z | 高Z | 高Z | 高Z |
01 | 高Z | 高Z | USB0_DP | USB0_DN |
十 | USB0_DP | USB0_DN | UART1_TX | UART1_RX |
十一 | 高Z | 高Z | 高Z | 高Z |
使用这些表,
10 0C 00 00 00 00
考虑到ID线位于ID0引脚上的事实,我们来解密电缆的ID():
0x75电缆响应的第一个字节
7 | 6 | 五 | 4 | 3 | 2 | 1个 | 0 |
---|---|---|---|---|---|---|---|
ACCx | Dx | 数据[43:40] | |||||
0 | 0 | 0 | 1个 | 0 | 0 | 0 | 0 |
因此,ACCx为00,这意味着ID0引脚仅与IDBUS相连,而Dx = 01意味着DP1 / DN1引脚被配置为USB0_DP / USB0_DN。正是我们对标准USB电缆的期望。
现在让我们截取一些更有趣的东西:
附件 | ID(主机ID = 1) |
---|---|
DCSD | 20 00 00 00 00 00 |
KongSWD(无Astris运行) | 20 02 00 00 00 00 |
KongSWD(运行Astris) | A0 00 00 00 00 00 |
KanziSWD(不运行Astris) | 20 0E 00 00 00 00 |
KanziSWD(运行Astris) | A0 0C 00 00 00 00 |
Haywire(HDMI) | 0B F0 00 00 00 00 |
充电UART | 20 00 10 00 00 00 |
闪电到3.5毫米/带有闪电的EarPods | 04 F1 00 00 00 00 |
这是来自@spbdimka的IDBUS请求的完整(?)列表:
提示1:您可以使用accctl轻松获取附件的属性,包括其ID:
这是NonUI / InternalUI程序集附带的内部Apple实用程序。但是您可以在越狱后在任何设备上轻松运行它。
提示2:您可以使用诊断轻松获得电缆的引脚配置:
tristar -p
请注意,此命令仅在iOS 7+上可用。
提示3:通过将
debug
env var 设置为3,您可以轻松跟踪SWD探针生成的0x74 / 0x75请求/响应。
astrisctl setenv debug 3
然后在电缆上的虚拟COM上,您将看到以下内容:
主机名
在上面的表之一中,您可以看到提到的某个HOSTID。这是在0x74请求中传递的16位值。看起来它也影响了HiFive的答案。至少如果将其设置为无效值(是的,可能是通过诊断),HiFive将停止使用它:
但是,KongSWD / KanziSWD固件具有环境变量disableIdCheck,您可以将其配置为忽略无效的HOSTID。
重要说明: Kong和Kanzi没有HiFive作为专用的非可编程芯片。这些配件可通过微控制器和/或FPGA对其进行仿真,从而易于更新/重新编程。
唤醒
在上面的附件ID表中,您可以看到Kong和Kanzi根据Astris是否正在运行发送不同的响应,这是Apple的内部软件,用于使用SWD探针(或多个探针)进行调试。如果使用上表对这些答案进行解密,则会发现当Astris无法启动时,探针的行为将与DCSD-D1线上的USB和D2线上的UART完全相同。但是,在运行调试软件时,ACCID线会切换到SWD。
但是,如果我们想在探针已连接到设备后启动Astris,该怎么办?电缆会做什么?如何在ACC到SWD线之间切换?这是WAKE发挥作用的地方! HiFive(或模拟它的设备)可以启动唤醒 -IDBUS枚举过程将再次开始:Tristar将发送请求0x74,Kong / Kanzi将使用新ID进行响应,Tristar将进行确认并将ACC线路发送到SWD扩展(当然,SoC必须在物理级别支持此功能)。
电源握手
我要看的最后一件事是电源握手。这是Tristar内核驱动程序在允许附件充电之前使用的IDBUS请求/响应算法。
当Lightning电缆仅位于某个地方,已连接至充电器/计算机,但未连接至设备时,HiFive会将PWR上的电流限制为一个很小的值(根据我的测量,约为10-15 mA)。要启用全电流,必须由Tristar发出请求0x74,并由HiFive处理。对于SecureROM / iBoot,这已足够,但是在加载内核时必须采取其他步骤:
- TriStar发出两个0x70请求
- HiFive处理完第二个请求并发送响应后,它将立即关闭当前的所有内容约20毫秒
- Tristar 0x70, 0x80 . HiFive
- , Tristar,
: , . , . ,
ESN Tristar I2C
我想谈谈Tristar的另一个功能是ESN。这是Tristar在其EEPROM(在CBTL1610A2及更高版本中)存储的EEPROM中的一个小斑点。可以使用序列号读取器电缆通过IDBUS(或Kanzi,它们基本相同,除了不同的USB-PID和略有不同的外壳)可以
获取。简单地说,将这个Blob发送到ttrs.apple.com,您可以获得设备的序列号... Apple Store / Apple Premium Reseller员工使用此机制从死机中检索SN(如果Tristar仍然存在):
收到ESN时IDBUS在IDBUS上发生的情况,@ spbdimka记录如下:
训练
“固件»ESN的过程要求进行Tristar 培训(配置)。它通过接收方的EzLink分三步在设备端进行诊断。
您可以使用诊断来检查状态:
tristar --prov_stat
...并获得ESN:
tristar --esn
顺便说一句,诊断程序通常具有丰富的Tristar命令集(自iOS 7起可用):
三星I2C
Tristar在I2C总线上可用(地址0x34用于写入,0x35用于读取)。这就是diag和内核驱动程序与之交互的方式。
有关注册表的公开信息并不多。可以从泄漏的iBoot源代码(仅适用于THS7383-似乎与CBTL1608-和CBTL1610向后兼容)中获取有关寄存器映射本身的很多信息,但是要获得任何有趣的结果,在那里需要写的内容并不多。
另一个知识来源是来自诊断程序的Tristar模块(运行时可通过SWD轻松检索)。例如,我能够撤销配置和ESN读取算法。然后,我将其实现为iBoot负载Lina的补充:
我也尝试更改ESN写入算法,但失败了-该机制对我来说太复杂了。但是,此处提供Lina的代码段。
Tristar的电气特性
Tristar本身由1.8V电源供电,根据我的示波器,IDBUS的线路可承受3.0V的电压:
因此,如果没有电平转换电路,最好不要尝试使用5V耐压的设备(例如某些Arduino模型)与IDBUS进行通信...