、M/C/U/简单加/密方法、

、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、

一.STM32Flash组织

STM32的Flash包括主存储器(HD版本,512KB)+信息块。信息块包括2KB的系统存储器(用于系统自举启动代码)和16字节的选项字节(8个字节数据+8个字节数据的反码)。

 二、STM32读保护

STM32读保护是通过设置RDP选项字节,然后在系统重新复位加载了新的RDP选项字节后启动的。当保护字节被写入相应的值以后:

●通过从内置SRAM或FSMC执行代码访问主闪存存储器的操作,通过DMA1、DMA2、JTAG、SWV(串行线观察器)、SWD(串行线调试)、ETM和边界扫描方式对闪存的访问都将被禁止。

●只允许从用户代码中对主闪存存储器的读操作(以非调试方式从主闪存存储器启动)。

●第0~3页(小容量和中容量产品),或第0~1页(大容量和互联型产品)被自动加上了写保护,其它部分的存储器可以通过在主闪存存储器中执行的代码进行编程(实现IAP或数据存储等功能),但不允许在调试模式下或在从内部SRAM启动后执行写或擦除操作(整片擦除除外)。

●所有通过JTAG/SWD向内置SRAM装载代码并执行代码的功能依然有效,亦可以通过JTAG/SWD从内置SRAM启动,这个功能可以用来解除读保护。当读保护的选项字节转变为存储器未保护的数值时,将会执行整片擦除过程。

●可以使用系统启动程序解除读保护(此时只需执行系统复位即可重新加载选项字节),芯片自动擦除Flash所有内容。

 三.STM32的加密

1.使用系统启动程序STM32 Flash Loader demonstrator将Flash设置为读保护。

所有以调试工具、内置SRAM或FSMC执行代码等方式对主存储器访问的操作将被禁止,只允许用户代码对主Flash存储器的读操作和编程操作(除了Flash开始的4KB区域不能编程)。用户代码允许自主编程可以实现IAP或者数据存储等功能。

这样破解者将不能用调试工具、内置SRAM或者FSMC执行代码等方式读出Flash中的代码。破解者也不能使用系统启动程序读取代码,因为要解除读保护,将执行整个芯片的擦除操作。

2.主程序中使用设备ID保护

    即使将Flash设置为读保护,破解者也可以通过IAP下载自己的一段小程序,从而读出Flash中的内容。因此,还需要利用设备的唯一ID进行加密保护。在主程序中,加入对设备唯一ID的检测,这样即使破解者读出了芯片中的二进制码,也不能用这个二进制码去复制新的器件。具体实现方法:

    (1)在应用程序中定义1个(32位甚至更多)const变量,变量值全为0xFF。每次启动程序时,检查const变量值如果全为0xFF,就读器件的唯一ID,通过Flash编程写入该const变量中(因为全是0xFF,所以可以编程写入)。

    (2)在程序中多个地方检查const变量,如果变量值不为0xFF并且与设备ID不一致,就执行与功能无关代码(比如自擦除)。

    这样,即使破解者读出了芯片中的二进制码,因为这份二进制码包含了设备唯一ID,具有唯一性,所以不能复制到其他芯片中。

    为了避免破解者利用反汇编,根据芯片ID数据在二进制文件中查找对应相同数据的位置从而破解,可以将ID拆散成不同的组合,并且写到不同且不连续的地方。更进一步,可在程序中检测多份这样的分散ID,以增加反汇编的难度。或者将CPUID进行加密,Flash中存储加密后的结果。

 四.程序加密的实现

 

[cpp] view plaincopy
01.//加密后的CPUID  
02.volatile const static uint32 CPUIDEncrypt = 0xFFFFFFFF;  
03.  
04.//写入加密数据  
05.void WriteEncrypt(void)  
06.{   
07.    //第一次烧写:将UID写入到Flash中  
08.    if(CPUIDEncrypt==0xFFFFFFFF)  
09.   {  
10.        uint32_t CpuID[3];         
11.        //获取CPU唯一的ID  
12.        CpuID[0]=*(vu32*)(UID_BASE);  
13.        CpuID[1]=*(vu32*)(UID_BASE+4);  
14.        CpuID[2]=*(vu32*)(UID_BASE+8);          
15.  
16.        //加密算法,很简单的加密算法  
17.        uint32_t EncryptCode=(CpuID[0]>>3)+(CpuID[1]>>1)+(CpuID[2]>>2);     
18.        FLASH_Unlock();  
19.        FLASH_ClearFlag(FLASH_FLAG_BSY|FLASH_FLAG_EOP|FLASH_FLAG_PGERR|FLASH_FLAG_WRPRTERR);  
20.        FLASH_ProgramWord((uint32_t)&CPUIDEncrypt, EncryptCode);  
21.        FLASH_Lock();  
22.    }  
23.}  

======================================================================================================
24.//判断加密  
25.bool JudgeEncrypt(void)  
26.{         
27.    uint32_t CpuID[4];         
28.    //获取CPU唯一的ID  
29.    CpuID[0]=*(vu32*)(UID_BASE);  
30.    CpuID[1]=*(vu32*)(UID_BASE+4);  
31.    CpuID[2]=*(vu32*)(UID_BASE+8);      
32.    //加密算法,很简单的加密算法  
33.    CpuID[3]=(CpuID[0]>>3)+(CpuID[1]>>1)+(CpuID[2]>>2);     
34.    //检查Flash中的UID是否合法   
35.    return (CPUIDEncrypt == CpuID[3]);  
36.} 


1、将写入加密数据和判断加密两个功能分开。写入加密在PrsCtrlTask开始的地方;而判断加密分布到程序的各个角落。

2、非常重要的是CPUID加密值的定义一定要加“volatile”类型:

volatile const static uint32 CPUIDEncrypt = 0xFFFFFFFF;

否则按速度优化编译,在判断加密值,不会重新读取加密值,导致判断出错。

3、在工程选项Options->Debugger->Download中选择: use flash loader

否则主程序中对Flash编程将不成功。

参考资料:

STM32F10x微控制器参考手册(2009年12月第10版).pdf

 

 

-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

STM32 读写保护功能及设置

功能::
读保护设置后将不能读出flash 的内容;当解除读保护的时候stm32 会自动擦出
整篇flash;
设置:
读保护设置:在程序的开头加入“读保护”代码,即实现了读保护功能;(每次程序

运行先
开保护)
解除读保护:解除读保护可以设置在按键里面,方便实现解锁,也不可不设;
(1)设置读保护:
if(FLASH_GetReadOutProtectionStatus() != SET)
{
//FLASH_Unlock();不解锁FALSH 也可设置读保护???
FLASH_ReadOutProtection(ENABLE);
}
(2)解除读保护
if(FLASH_GetReadOutProtectionStatus() != RESET)
{
FLASH_Unlock();
FLASH_ReadOutProtection(DISABLE);
}
这些函数在stm32f10x_flash 里面;
注意:调用上面这个库的时候需在#include "stm32f10x_flash.h"前加#define

_FLASH_PROG;
否则报(没有定义)错;

 

 

************************************************************************

/* Flash读保护使能 */ 
if (FLASH_GetReadOutProtectionStatus() == RESET) 
{
FLASH_Unlock();
FLASH_ReadOutProtection(ENABLE); 
}


/* 清除Flash读保护 */ 
if (FLASH_GetReadOutProtectionStatus() == SET) 

/* 会擦除Flash */
FLASH_Unlock();
FLASH_ReadOutProtection(DISABLE); 
}

CPU Flash读保护使能后,仿真器调试会失败。J-LINK有个解锁菜单,需要解锁才能正常再次烧写程序。当然解锁会导致Flash内容被全部擦出。

 

启动"J-Flash ARM"工具,Target->unsercure chip 就解除了芯片的读保护。
Target->unsercure chip 后一定要上电复位,系统复位是不行的。

一定要上电复位,系统复位是不行的!

 

 

 

STM32对内部Flash的保护措施

1、STM32对内部Flash的保护措施 
所有STM32的芯片都提供对Flash的保护,防止对Flash的非法访问 - 写保护和读保护。 
1)、读保护即大家通常说的“加密”,是作用于整个Flash存储区域。一旦设置了Flash的读保护,内置的Flash存储区只能通过程序的正常执行才能读出,而不能通过下述任何一种方式读出: 通过调试器(JTAG或SWD);
从RAM中启动并执行的程序; 
2)、写保护是以四页(1KB/页) Flash存储区为单位提供写保护,对被保护的页实施编程或擦除操作将不被执行,同时产生操作错误标志。 
读与写设置的效果见下表: 
读保护 写保护 对Flash的操作功能 
有效 有效 CPU只能读,禁止调试和非法访问。 
有效 无效 CPU可以读写,禁止调试和非法访问,页0~3为写保护。 
无效 有效 CPU可读,允许调试和非法访问。 
无效 无效 CPU可以读写,允许调试和非法访问。


2、当Flash读保护生效时,http://tiyubisai.com/video_news/news_135620.html CPU执行程序可以读受保护的Flash区,但存在两个例外情况: 
1)、调试执行程序时; 
2)、从RAM启动并执行程序时 
STM32还提供了一个特别的保护,即对Flash存储区施加读保护后,即使没有启用写保护,Flash的第 0 ~ 3 页也将处于写保护状态,这是为了防止修改复位或中断向量而跳转到RAM区执行非法程序代码。
3、Flash保护相关函数 
FLASH_Unlock(); //Flash解锁 
FLASH_ReadOutProtection(DISABLE); //Flash读保护禁止 
FLASH_ReadOutProtection(ENABLE); //Flash读保护允许

 

 

现在总结一下FLASH读保护和解除读保护的步骤:
(1)设置读保护
int main(void)
{
....
if(FLASH_GetReadOutProtectionStatus() != SET)
{
//FLASH_Unlock();
FLASH_ReadOutProtection(ENABLE); 
}
......
while(1)
{
.....
}
}
(2)解除读保护:在程序中的某个操作中(如按键等)加入如下代码,执行后
代码自己杀死了自己,哈哈!!!
if(FLASH_GetReadOutProtectionStatus() != RESET)
{
FLASH_Unlock();
FLASH_ReadOutProtection(DISABLE); 


如果没有在程序中加入解除读保护代码,也不要紧,可以写段RAM中运行的程序
用于解除读保护,执行后,FLASH会自动全部擦除。代码如下:
int main(void)
{
Chinp_Init();
FLASH_Unlock();
FLASH_ReadOutProtection(DISABLE); 
}

※对于在RAM中运行程序,说明如下:
(1)我使用IAR + J-Link,不用把Boot0和boot1脚设置成从RAM启动也可在RAM中调试(我是设置成从FLASH启动)。
(2)在IAR环境中设置Link文件为lnkarm_ram.xcl
(3)Debuger选项Download tab中勾全部去掉。
按上面设置完成后,按Debug按钮,执行上面程序,读保护可解除。

http://blog.csdn.net/chengfeng135/article/details/49638181

http://blog.csdn.net/chengfeng135/

 

--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- 

程序加密的最高手法 是加明锁+暗锁 首先 有明锁 让你copy了hex 要花钱找人破解加密方法 也就是上文说的注册码, 
如果注册码被绕过,程序不要功能异常,要功能正常 ,给出破解成功的假象 
其次,外加一段验证程序,如果注册码被破解或者失效,那么 运行一段时间后 自杀! 这个时间设置长一点 例如机器激活3个月或者更久。 
再来一段程序,验证上面的验证程序,自杀日期定位机器激活后6个月 

以上3道防线 1明2暗 

然后通过特殊参数 按键 设置隐藏的版权声明, 版权声明不要用文字,用图片的形式存储。最好和你的固定数组,字库等混在一起。 
例如定义一个数组,前面 后面是字库或者重要信息 中间是图的数据 之类的。 

这个是用来起诉的直接证据 呵呵。 

最后理想的结果是 抄袭者花钱抄你的硬件 软件,发现不能用,找人破解验证。后测试正常,投入资金生产,销售。 
销售一段时间,他的机器集中死亡,你再去采集证据 把他告上法庭 再赔一笔。

——————————————————写在我的机器被抄后 抄袭者被我整得很惨之后-------------------



--小偷不怕复杂的锁 就怕锁找不到........................

 


我现在是通过一张SD卡来激活的 SD里面存了一个文件 那个文件的特殊字节 是用SD卡的id号+剩余字节数+文件数目+某镞的32个字节+N9条公式 组成一个128字节的加密码。 
这样做 sd卡的文件复制到另一张 也不可以用。 sd卡就一张 我自己保存。 

机器判断sd卡的特殊字节 是否符合运算规则 ,然后在用某个特殊组合键 呼出激活页面后插入sd卡 认证。 

我的机器无需远程通信 所以没有通信口 呵 

关键是认证不成功 也不要影响功能 也不要做出提示 。开启计数就是,计数要设置足够大起码能用3个月以上 或者半年的。计数够了直接黑屏!!(外面收钱破解的是不会花时间去解这些暗锁的) 


然后再机器的某个菜单 用一个字 显示是否已经成功激活 例如某个字 激活是 “住”  没激活是 “往” 这个只有你自己知道就行。

 

 --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

ST 的唯一ID 可能就是在备用的 FLASH 区!  出厂之前做的了个动作而已!

---

不是可能,就是在备用的FLASH区,呵呵。
同BootLoader代码放一起的。
我估计是DIE上面有个特殊的测试用pad,没引出到封装片管脚上。
或者是有不公开的寄存器,用于烧录系统区FLASH。

---

STM32 破解 : 1、STM32 程序没办法读出来(他们直接把 IC 芯片开盖,这边要 13.5W)
                    2、要是使用了 ID 加密的 (提供修改 ID 的烧写工具 另外付费5W-10W)
                    ID 既然可以被修改???? 
这样一来破解就没有任何障碍了!!!
---

 只要思路一传播开来,恐怕1,2w就可以了

---

只要破解成本维持在10W以上,那仍然是有意义的。
银行专用的MCU破解成本也不过百万美金的级别

----

具体是怎么做的我就不知道了!! 我給了几个 IC 給他们!! 他们就把 ID 給改成一样的了!!  具体怎么实现的我现在还不清除!! 别人也不会说!!!

几个 IC 我读ID 出来真的就一样的了!!

posted @ 2019-06-12 17:29  yuanhuang  阅读(431)  评论(0编辑  收藏  举报