当前嵌入式的门槛分工及重难点
一、从科学技术发展史看技术门槛的降低
以前总是听有经验的工程师或者学长学姐告诉我们,嵌入式有多难学,门槛有多高,既要懂软件,也要懂硬件,还要懂各种xx原理,xx协议,xx算法。在学习嵌入式的过程中也走了不少弯路,无的放矢地学了各种杂七杂八的知识,尽管现在有一份还凑合的工作。但是面试应届生以及和群里一些还在校的学生交流的时候,发现他们能学习和掌握一些我们有2-3年工作经验才懂的知识,明显这一代的佼佼者可以花更少的时间学习到我们在不断踩坑和弯路中才得到的知识。
正因如此,我对以前老工程师总结的那套嵌入式Linux门槛很高,需要很多的经验,长期积累才能培养出合格的工程师,越老越吃香的说辞产生了怀疑,进而联系科学发展史和唯物辩证的思维,发现那些老工程师的意识和观念由于受他们成长的环境和时代的影响,由于他们技术成长过程中所经历的困难使他们的主观意识对嵌入式技术的认知上产生了一些偏见(就像是物质匮乏时代给老一辈人带来的偏见,使得他们在小康的新时代还要省吃俭用,舍不得浪费一粒米一样),这些主观偏见有一些时代局限性,和当前社会普通学生能接触的信息和资源是有差异的(这也是所谓代沟),但是他们却意识不到自己的主观偏见,也很少能以客观的态度看待这种意识差异,他们把带有主观偏见的经验传授给新一代的工程师,也使得新一代工程师发现其中与当前实际情况不符的地方,产生很多困惑。
嵌入式相关的技术,说到底也只是电子信息与计算机交叉的一种应用性的技术,其本身的地位远远不如了人类发展史上的几大科学进步的里程碑,比如:牛顿力学体系,欧姆定律,法拉第电磁感应,洛伦兹力,麦克斯韦方程,布,微积分等等……
像牛顿力学,元素周期表,欧姆定律,高斯分布等这些科学理论知识,是人类中杰出的精英探索研究了几百上千年才得到。这些知识在200-300年前,只有人类社会中*杰出的精英才能掌握。可如今,我们从一无所知的婴儿到掌握这些200-300年前精英科学家的前沿理论,只需要18岁读到高中毕业就行,不需要我们再沿着前人的老路再探索上百年了。上一段提到的其它几个近100多年的科学里程碑,我们也只要读到大二也能学懂。这要是在200年前,那些伟大科学家可能会说,你们高中和大学基础知识是他们穷尽了毕生心血才弄懂的。
所以从科学技术的发展史可以明显看出,踩在巨人的肩膀上,学习过去已有的知识,我们已经不用跨过那么高的门槛,不用在黑暗中摸索,走那么多的弯路。
同理,在嵌入式领域,相比于20年前入门的嵌入式工程师,我们有了X宝,可以购买到各种各样的开发板以及价格相对便宜的低频示波器,万用表,有了更多专业领域的中文资料,能够使用各种方便的IDE环境直接采用C语言编程(他们入门用汇编),相比于10年前入门的嵌入式工程师,我们有了更多专业方面的网络视频培训资料,能有人手把手带你做项目,调试,我们有了Github,在上面能获取Linux内核源码,看到全球公司提交的产品级的驱动代码,我们有了更多的开源应用软件和生态,有更多的人在网络论坛上回答你的专业问题,教你一步一步配置环境,遇到很难的专业领域算法(比如使用小波变换做得视频有损编解码算法),我们一时半会写不出来的时候,往往可以找到别人写好的开源库,稍微修改移植过来。
这个移动互联网时代带来的这一切,不知不觉中侵蚀了嵌入式所谓的高门槛,让那些老工程师在信息相对匮乏年代所经历的很多困难,在当下,都算不上困难和门槛。
所以网上那些复制粘贴的文章中所谓的嵌入式高门槛,放到当下的时代环境,可能并不是什么难事。我们应该学会用发展的眼光看待技术的进步,而不该被嵌入式高门槛的教条所束缚,以正常的心态,把它看成是一种普通的技术活,和应用软件开发,硬件开发,结构设计同等对待,技术本身并没有啥鄙视链和优劣之分。
二、嵌入式领域分工的变化
有很多所谓有经验的人认为,嵌入式底层软件和硬件技术是不怎么变化的,经验越多越值钱,越老越吃香。其实这是一种主观机械而又狭隘的经验主义,缺乏全局视野,只看到自己所在领域的一些基础性技术,看不到整个行业和相关领域的变化,一叶障目。
其实就拿现代足球和篮球运动作为类比,也是同样的道理。现代足球和篮球的发展历史比什么嵌入式软件,硬件等高科技的发展史还要长久,那种机械经验主义狭隘的观点肯定会认为,打篮球就是学运球,突破,传球,投篮,踢足球就是学传球,停球,带球,铲球,射门,跑位,这都是50年前甚至100年前就有的东西,和现在一样是不变的。然后他们没有看到的是,篮球和足球的战术和位置分工,每隔5-10年就会发生很大的变化。
比如篮球领域从之前的强内线,肌肉棒子的中锋时代演变成小球三分射手时代,内线球员对中远投和三分球能力要求越来越高,以前那种没有射程的大个内线越来越不吃香。
足球领域的分工和战术变化就更多了,从远古一点巴西群星的424 WM阵型个人技术流到意大利链式防守,从经典442阵型,双前锋一高一快或者双高的英式长传冲吊,到第*代433全攻全守的踢法。从4231传统的边锋加经典10号位前腰和扫荡防守型后腰再到西班牙式Tiki-Taka传控足球短传渗透的盛行,再到现在高位逼抢,经典前腰和防守型后腰的消失,全能型B2B中场的吃香。其它位置的球员,例如,逆足边锋内切踢法,伪9号无锋阵,边后卫对助攻能力要求越来越高,而不只是防守对方边锋,中后卫对出球能力要求越高,不只是会防守抢断。而过去那些有了很多*和荣誉但是位置单一,不符合现代高位逼抢,灵活换位要求的球员,越来越没有市场。
像现代足球,篮球这种发展了50年到100年的体育运动,看似不变,实际上都经历了如此多的战术和位置分工变化,不同时代对不同位置球员的要求都不一样,更何况近二三十年经历了高速发展的电子信息和嵌入式技术呢?回到正题,分析一下硬件工程师和嵌入式软件工程师的分工和技能要求变迁。
1. 硬件工程师
一开始没有集成电路和数字芯片,要设计一个系统需要用三极管,电阻,电容,电感等分立器件来搭,那时候硬件工程师对模拟电路设计的要求是非常高的,既要精通应用业务逻辑,也要精通模拟电路设计,大家可以看看模电书上经典uC741放大器里面的模拟电路图的复杂程度。
后来有了小规模的模拟和数字芯片(比如uc741放大器,74LS04数字门电路,ne555时钟发生器),硬件工程师就可以使用这些芯片加上一些外围电路来搭建自己的系统,硬件设计门槛有所降低,做出的产品也更加丰富,但是自己还是要精通应用业务逻辑。
再到后来,ASIC和大规模集成电路以及嵌入式编程芯片的出现,很多算法和逻辑控制功能都集成在ASIC芯片里面或者在嵌入式处理器中用编程软件实现。硬件工程师对业务应用业务逻辑的要求大大降低,同时所做的外围电路设计也越来越少,比如电源方面,可以买TI的开关电源芯片加上少量的外围电路,就能实现自己高性能开关电源,无需精通里面各种复杂的控制算法和功率因素补偿等技术。这个时候,有些硬件工程师开始往单片机编程技能方面发展,还有一些硬件工程师往EMC,PCIE,WIFI,USB,DDR等数字和模拟等接口标准认证方面发展,硬件的分工开始细化专业化。
再到当前,芯片原厂提供的不再仅仅提供单独的芯片让硬件工程师设计电路,而是提供现成的基于芯片设计的模块或者turn key解决方案,即插即用,不需要自走PCB打板的流程,就能快速验证自己想法和产品方案。并且原厂提供的这些模块和解决方案,已经做好了安规,车规与EMC等标准认证,更加降低了硬件开发的门槛,提高了开发效率,很多硬件工程师的工作也变成在原厂方案板上修改,验证,抠掉一些冗余器件节约成本,或者剩余的时间要负责供应链和生产管理相关的工作。而从前那些高深的数字,模拟混合电路,分立器件电路设计技术和经验显得无太大用武之地(除了少数芯片设计场合)。
2. 嵌入式软件工程师
20多年前的嵌入式工程师大部分都是用C语言和汇编在8位单片机上开发驱动程序和相对简单的控制和通信系统。那时候单片机功能没有现在这么高级,里面甚至没有ADC, PWM等常用模块,需要搭建很多外围或者电路来丰富产品的功能。那时候的单片机嵌入式开发除了要会编程,对硬件也相对较高,要自己设计通用的硬件原理图,甚至画2层左右的PCB板,只有碰到电源,射频,EMC专业硬件问题的时候,才会需要雇佣专门的硬件工程师来处理。
后来使用复杂一些的32位MCU开发,MCU功能开始变得强大,系统需求也开始复杂化,嵌入式工程师需要开发多个平台驱动乃至上位机应用程序,这个时候,公司一般会雇佣专门的硬件工程师做PCB layout和部分原理图设计工作。嵌入式软件工程师只需要设计硬件原理图的核心功能I/O部分,看懂芯片手册,对嵌入式工程师硬件能力的要求开始降低,大部分精力用于软件开发上。
再后来的嵌入式开发使用DSP处理器和RTOS实时操作系统,硬件部分也变得集成度更高更复杂,嵌入式工程师对硬件方面的掌控和要求也越来越低,仅限于看原理图,配置一些I/O引脚和寄存器,原理图设计基本都交给专门的硬件工程师。但是嵌入式软件这块,做DSP的需要熟悉一些业务算法,做RTOS的要懂得数据结构,操作系统、计算机网络方面的知识。驱动开发也开始变得框架化,模块化而不仅仅限于裸机开发,配置寄存器和简单的业务逻辑。
再到当前,嵌入式大规模使用SOC,跑Linux/Android等复杂操作系统,DSP等专用CPU核也可以集成在SOC中,通过驱动进行调用。嵌入式工程师基本不用参与硬件原理图设计,硬件能力基本不是啥门槛,只要学过电路,模电,数电等教科书知识,看得懂别人I/O部分的原理图就行了。读数据手册配置修改寄存器的活也只有偶尔会用上,因为芯片原厂和Linux开源社区为了推广生态,已经将很多产品级的芯片的驱动程序集成到Linux内核,配置好了寄存器,降低了系统底层软件的使用门槛(这其中有少数嵌入式工程师在原厂从事门槛较高的专业领域驱动开发,比如音视频,GPU,Display,Security等),使得嵌入式工程师把更多的精力集中在具体应用和业务逻辑开发上。
通过上述的一次次技术领域分工的变化,使得嵌入式工程师入行门槛和工作重点也发生了变化,从硬件到原理图I/O设计,到驱动开发到应用业务逻辑。可以说每个部分都有它的技术难点,没有哪个技术比其它技术高尚,我们应该关注当下的重点,善于从各种矛盾中抓主要矛盾,有的放矢地学习提高自己,善于思考主流技术的发展趋势和变化,千万不要被过去的教条所束缚。
三、当前阶段嵌入式技术的重难点
当前阶段嵌入式技术的重难点小编认为有三个方面:
1. 以C/C++语言为主的编程能力。
原本C语言编程也不是啥门槛性的大问题,但是因为国内大部分电子信息专业都是以C语言入门,然后选用的国产教材质量参差不齐,代码风格不规范,这就人为地给入门菜鸟创造了门槛。但是只要肯花时间下功夫,学习豆瓣上推荐的几本国外经典的C语言教材,进而学习数据结构,面向对象等计算机基础知识,多练习多写代码来熟练编程技巧,小编相信这个不会是大问题。
C++方面,以前做单片机,做RTOS的老嵌入式工程师可能基本上都是写C程序,用不上C++。但是现在基于Linux系统的嵌入式开发,重点将会聚焦在复杂业务逻辑应用编程上。在大规模复杂业务逻辑和GUI编程中,使用纯C语言已经力不从心,使用C++开发的嵌入式应用程序的地方将会越来越多。但是C++这个语言本身比较复杂,不能强求像C语言那样掌握95%以上的特性,C++总会有很多语言特性用不上或者不熟练,需要找到合适的项目,在实践中反复练习再回头看书巩固,循序渐进。熟练掌握C++会需要较长的时间,目前一般的要求是掌握基本的面向过程,面向对象编程的编程方法,多用智能指针,复杂的模板编程能看懂就行,不要求掌握所有奇巧淫技。
2. 对计算机体系结构和操作系统相关问题的掌控能力
这一块知识算是计算机基础理论上的难点,虽然相关书籍资料已经汗牛充栋,商业级的Linux内核源代码也能从网上下载,但是要啃下它还是需要耐心。很多做单片机裸机,RTOS开发的嵌入式工程师无法进入Linux开发的世界,多半也是因为Linux操作系统确实有一定难度。对这一块知识,其实并不要求你掌握Linux内核每行源码(这是不可能的),也不要求你能够独立写出一个复杂的产品化的操作系统(也不现实),但是操作系统底层和计算机体系结构基本的工作原理和机制还是要搞清楚,要知道操作系统大概做了什么,是如何处理你的API调用的。
小编知道这是一块硬骨头,但事在人为,有了这么多资料和实验资料的今天,肯花时间,有耐心,也不应该是大问题。
3. 业务应用能力
为什么我们需要做嵌入式计算机系统,因为嵌入式计算机系统可以根据不同业务场景需求进行裁剪和定制。说到底,业务才是嵌入式系统真正的命根子,不同业务方向嵌入式工程师薪资差异可能会比较大(当然在少数公司,开发操作系统也属于他们的业务)。在企业有话语权有地位的嵌入式工程师所掌握的业务技能一定和企业当前盈利的业务方向高度匹配,充分满足企业的业务需求。
当前嵌入式软件工程师要想提高收入,一定要跟着主流有盈利能力的业务走,提升相关的业务应用技能。当然很多细分业务,不去相关的企业是根本没有机会接触的,热门业务相关的高级资料也不是能够通过网络和入门培训视频轻易获得。所以说当前阶段的业务门槛才是嵌入式在不同领域的真正门槛。学会自己分析,把握当前主流前沿的业务方向,有的放矢地学习提升自己,让自己掌握的知识发挥*大的“钱”力。
四、如何调整自己的学习和职业发展方向
分析了嵌入式领域的现状和重难点之后,那么嵌入式工程师调整自己的学习和职业方向,小编认为有以下三点:
1. 不用过于纠结硬件门槛与寄存器配置
毛选《矛盾论》告诉我们事物的背后要搞清楚哪些是主要矛盾,哪些是次要矛盾,处理问题要善于抓主要矛盾。
同理,在当前的嵌入式学习和开发中,硬件门槛与寄存器配置已经不再是主要矛盾,而是影响你解决问题众多次要矛盾之一。真正的主要矛盾是应用业务开发,是对操作系统工作流程的掌控,让操作系统能够很好地支持和配合应用业务实现系统的功能。
那么对待硬件和寄存器配置,固然还是要以客观严谨的态度分析和解决相关的问题,但是不要把太多时间花在硬件原理和数据手册寄存器的学习上,否则这将是一个高投入,低产出的工作。小编认为硬件相关问题,嵌入式工程师能把大概定位出来,交给专业的硬件工程师处理就行。这点对硬件知识的要求只需要懂得教科书上基本模拟和数字电路知识就行,相对于自己独立设计硬件电路,通过各种标准认证的要求完全不是一个层次的。
2. 不能把编程仅限于嵌入式端
目前的嵌入式复杂业务应用编程和PC端,服务器应用编程的界限其实越来越模糊。嵌入式端应用编程除了某些时候需要利用一些平台特有的硬件和驱动特性,来提升和优化程序性能之外,大部分的工作也是堆业务逻辑代码,只是在不同平台上堆业务代码,用不同的编译器编译而已。
从编程的角度考虑,就不要把编程范围仅仅限制在嵌入式端,在以应用业务为中心的前提下,可以主动尝试开发PC端,服务器端甚至web端的应用程序,还可以把在PC端,服务器端编程用到的新技术因地制宜地移植部署到嵌入式端,做到取长补短的作用,同时也把自己的职业道路越走越宽。
目前,嵌入式端也引入了python编程搭建整套自动化测试系统,很多嵌入式端的测试用例也是用python编写的。很多做STM32, RTOS开发的嵌入式工程师,也不仅限于嵌入式端编程了,因为他们开发的产品很多需要通过物联网接入到云端服务器,有时候他们也要兼顾一些云服务器的应用业务逻辑以及云端和嵌入式端通信协议开发的工作,不再是以前传统意义上的嵌入式开发工程师。
按照这个发展潮流和趋势,小编可以预言,未来的对嵌入式工程师的技能要求将会弱化硬件技能,在有扎实的操作系统基本功前提下,以业务导向的应用编程为核心,有云端服务器到嵌入式终端的端到端垂直开发能力。
3. 跳槽的时候要有业务升级意识
最后就是要有目的地跳槽,不只是考虑薪资问题,更要考虑下一份工作能接触到的业务知识是不是主流赚钱的业务,未来有没有赚钱的盈利模式,能不能让自己的路越走越宽?平时多关注招聘网站的需要,看看什么样的公司,什么样的业务提供的招聘需求是*多的,要敢于和打价格战,不赚钱的业务和公司说再见,及时跳坑。不要把时间耗在了重复性基础性工作(比如小编鄙视的万年嵌入式点灯,spi,i2c开发)和不盈利的业务上。
*文章内容和图片均来源于网络,如有侵权,请联系删除。