本帖最后由 酱哒哒 于 2017-1-17 19:50 编辑
1.初识STM32
还记得那是大四的时候!
因为大学里课程一塌糊涂,大四的时候,我突然发觉自己不能再这样颓废下去。
于是顶着学渣的身份不好意思地找了大学里的一位本科老师(一位老教授),本以为自己那渣渣成绩,会被鄙视。可那一下午,和老教授的深谈,他一丁点儿都没谈成绩的事情,反而是问我关乎未来的一些考量。那时候,我才意识到,一直因为成绩而抬不起头的人,仅仅是自己心中的魔障而已!
老教授答应,只要我考上学校的研究生,就收我。
大四上学期那半年,我废寝忘食,全部课程重新学习(大学的课程一点儿没学,高数英语这些全是靠高中的底子过的,那段时间真是感觉回到了高三)。索性结果不错,我以成绩第一的身份顺利进入了复试(进入复试,我基本就定了,当然我也觉得对其他人不公平,不过这社会就是这样,有点小黑幕也可以理解)。
大四下学期,老教授(这时该叫导师了)开始给我安排了一个毕业设计,他说本校的应该更早进入研究领域,要不然这点资源就浪费了。所以,下学期开始我就与研二的师兄们开始一起开组会。导师还分配给我一个师兄,全力负责引领我的方向。
导师是做磁敏传感器的,就算考上了研究生,我当时也根本不知道自己能做什么,会做什么!
当时,师兄给我看了一个他曾经做过的项目,是一个基于STM32的角度编码器,我当时感觉好厉害。他问我想不想深入单片机领域?(导师手下三个师兄,一个做理论仿真,一个做硬件方面的工作,一个做单片机开发)
其实,当时我并没有什么想法,就随性说自己愿意进入单片机领域(那时,我丝毫没有意识到这个决定将会影响我这以后的方方面面)。
后来,我也经历了许多人初学STM32的基本过程,先学51,再来弄STM32。
初步接触单片机的时候,初步进入这个领域的时候,有各种各样的怪想法,怪问题,因为那时候自己什么都不懂,而师兄正好就替补了搜索引擎这个作用,悉心地解答了我的所有问题!在这儿,我很想提醒后面的初学者,最好找一个真正熟悉STM32的人,来带自己,这比看什么书有用多了。
所以,我一直以来都很感谢导师,很感谢师兄!
2.九尺高台,起于毫末
后来,在我的勤奋努力下,STM32的基本外设都大致会使用(我相信很多人如今也仅仅限于“会使用”而已)了。
这时候,我开始想为什么用STM32给的函数就能实现这些功能?
我干了一件很变态的事情了,读STM32的固件库代码,还是打印出来那种(如果只是想做单片机应用开发的同学,看这个真的用处不是很大,不过看完之后我对STM32的理解开始加深了)。
有了大致浏览源码的基础,我开始明白了STM32更加深刻的一些东西(以前只是知道how to do,但是现在有一丢丢知道why to do了,但是我依旧是那个菜鸟)。
也是在这个期间,我开始渐渐步入这个圈子了,加了一些论坛,进了一些QQ群。
这些群和论坛,是继导师和师兄之后,给我帮助最大、最多的地方了。虽然我不是很喜欢说话,但是群和论坛的交流中,我可以看到大家的一些想法,了解一些新的东西(毕竟那时候自己什么都不懂,对整个单片机圈子没有一个概念,不知道生态圈)。正是在各位的交流中,我才发现原来还有OS这个概念(原来我一直在做前后台编程)。
这时候,我开始学习基于STM32的uC/osII。(这是我干过最有意义的一件事情)
学完这个RTOS,我明白了更多深层的东西,知道了CM3的堆栈概念、CPU寄存器的一些东西。后来我也把源码看了一遍,明白了任务切换的实现手段,当时真的觉得第一个诞生这种想法的人,好腻害!
后来我模仿CPU寄存器操作,去实现了一个模拟while(1)功能的无限循环:(基于IAR的,MDK没有内链,不能这么用汇编)
asm("MRS R12,PSP"); //存储当前进程堆栈地址
......
asm("MOV SP,R12 ");//将记录的堆栈地址导入SP寄存器
第一次完成这个功能的时候,我感觉到心情十分舒畅。我第一次感受到了CPU的工作机制,CPU的运行动作!
不过,上述的操作,一旦引入更多程序环境,就会出错,因为我保存的东西太少了。RTOS切换任务的时候,保存了和程序运行有关的基本所有环境。(想要深入了解的同学,可以随便找个RTOS的源码,读一读)
3.天高任鸟飞
经过了这么多东西的沉淀,我发现自己好像越走越底层了。不过,我是个理性的人,对于往这方面的发展,我很开心,因为这是我想要做的!
然后一次与同学的讨论中,我发现自己还不知道程序运行时FLASH,SRAM的使用情况。为了解决这个问题,我开始在一些论坛中搜寻信息,在群里问人,最后总算基本弄懂了基于IAR的STM32启动流程(这一步,我真的感觉很重要,很多人可能都没有去了解过)。有了上一步的积淀,可以了解到STM32程序运行中PC指针跳转的情况,以及各种全局变量、局部变量存储的地址,这对于更深入的程序调试,有着极其重要的意义。
学到这个地步,我才感觉自己略微明白了些STM32。
一开始学习的时候,自己只是知道遵循库函数,拿来单纯地开发应用。但是至于why?根本不懂。而如今,从堆栈——中断向量表——main()——其他,这一连串的启动流程,在我脑子里清晰无比。自己不再是混沌一团了。、
从我初识STM32到如今,不过也才一年多时光,我感谢所有给与我帮助我的人、感谢导师、感谢师兄、感谢QQ群的大神、感谢论坛的技术帖子(希望各位大神有空多写写帖子,说来忏愧,自己好像还没发过什么技术帖子,一直受用于前辈们的经验,却没有留下一丢一毫的东西回馈)。
4.我想谈谈的一个项目——基于IAP的芯片安全加密技术探究
这个问题的引出是在我刚入门时,导师与师兄们交流时的一个东西,就是导师自己开发了单片机程序,要和别人一起合作,对方也有程序,现在双方都不想给别人看到,也不想别人能无限使用这个程序。那时候,师兄们并没有想到解决的办法,所以我就留了点心思。
可惜,刚入门那时候,自己实力不够,完全不懂!!也没有任何的想法。
后来在了解了RTOS的任务切换机制,明白了CM3 CPU运行情况后(这是理论基础,不然根本不知道我后面在说什么),一次在论坛中闲逛时,我看到了一个术语IAP。秉承着不懂就问的态度,当时我就去百度了一下IAP。正是这次百度,让我发现了解决当初导师那个问题的一丝曙光。
至于为什么要谈这个项目?
虽然我也做了许多基于STM32的应用开发,但是我个人内心并不想谈那些,因为我感觉我做过的这些应用开发,只要学过C学过C++,懂单片机,接触一段时间,最后都能做到这一地步。我感觉不到谈它们的任何意义!(我承认这些东西对于初学者很有意义,但我内心并不想谈论这些内容)
这个项目我暂时还没能完成所有的工作,但是我更想谈这个东西。因为大部分做嵌入式开发的,很可能根本不会接触到这个东西。
IAP就是在应用内编程,平时大家用STLINK或者其他的烧写程序那种叫ICP。IAP可以实现用外设接口(USART/CAN/IIC等)烧写更新程序。表面上看不出什么区别,但是实际上程序运行的时候有很大区别。
具体可以搜寻一些帖子看看,在这儿我推荐这个人的帖子: http://www.techbulo.com/592.html 另外,本网站也能搜到一些好的帖子,关于IAP处理过程中中断的一些建议,例如: https://www.stmcu.org.cn/article/id-317094
衷心企望STM中文网,越来越好,更多的大神留下自己独到的见解,更多的学习者在这儿找到自己需要的东西。
之所以会用到IAP是因为:
1.利用IAP,可以更新内部程序,而且加入FLASH保护的话,还能实现防止外部读写。
2.当然,近年来芯片解密技术也提高了,仅靠FLASH保护,有时候不一定能防住。所以有人又提出了基于IAP的CPUID加解密保护。
就是每一块stm32都有唯一的一个ID号,先用这个ID号作为密钥对烧录的文件进行加密,然后每次运行的时候再利用ID号解密,这样就能更大范围地防止程序被读出。(用外部方法把程序读出去,别人没密钥,也没用)
3.至于老师的程序如何和对方的程序实现衔接,构思了下,有点类似下图。
甚至可以利用和IAP跳转相同的手段,实现用户程序之间的相互跳转,这样就能把两个程序融合在一起,而又互不干涉。
4.我把上述的想法,改成PPT拿给导师和师兄看后,他们表示这个方法能满足要求,后来就交给我去做了。
不过,因为着手时间比较晚,今年还未能完成。目前只是实现了bootloader的设计,加解密的过程有待明年。
(相关的实现手段,有一些论文,可以去搜索一下)
毕竟人不是什么都知道的,有的时候一些想法,可能就是周围的人给的。
再次,感谢所有给予过我帮助的人。
上述文字,大致地记录了我一点点步入STM32领域的经历,可能和很多人初学的经历都相似,希望能对大家有点帮助。
|