“第001课 不要再用老方法学习单片机和ARM”的版本间的差异

来自百问网嵌入式Linux wiki
 
(未显示3个用户的63个中间版本)
第1行: 第1行:
 +
<div body style="width:800px;">
 +
= 单片机程序员发展的必选之路: Linux =
 +
我们的第一期是教大家如何将ARM开发板当作单片机来用,但在这期视频的第一节,我告诉你们,'''学习单片机是没有前途的'''。
  
<categorytree mode=all style="float:right; clear:right; margin-left:1ex; border:1px solid gray; padding:0.7ex; background-color:white;">ARM裸机加强版</categorytree>
+
话说得非常狠,因为不这样说,没法警醒你们。我说这句话,是冒着生命危险的,因为很多人依靠单片机来生活,淘宝上有一大堆售卖单片机开发板的,像51、STM32等。
  
= 第001节_LCD硬件原理 =
+
== 工资方面 ==
 +
我们学习这些不就是为了赚钱吗?在51job上,搜索“单片机”,工资平均下来是几千块钱。然后搜搜“Linux系统工程师”,平均工资是上万左右。
  
先简单介绍下LCD的操作原理。
+
== 职业发展 ==
如下图的LCD示意图,里面的每个点就是一个像素点。
+
这里我有切实的体会,我2003年毕业,2005年进入一个小公司,当时做的是车载电话,我们先是用51单片机来做的。当时我的李姓同事,用两个3000多行的C文件,实现了车载电话的功能。
 +
另一个魏姓同事,将功能拆分成各种模块,使用了50多个C文件,以操作系统的思想,重新写了这个程序。这两个牛人,都跳槽了,都不做单片机了。
 +
李姓同事去了美国,深造了机器人视觉,现在是百度的搜索专家,魏姓同事和我一起去了中兴,现在在厦门联想公司负责手机的开发,而我给你们录视频,但我们都不玩单片机了。
 +
我在2005发表了一个2440开发板上仿照ucos写了一个操作系统,10年前,我们已经把单片机玩得登峰造极了。但是我们还需要升级,为什么?
 +
因为单片机非常简单,稍微认真学习2-3个月就可以达到中等的水平,你工作十年和工作两年技能差别不大,对一个公司,现实一点,他肯定喜欢使用工资更低还更愿意加班的新人,所以说,我们必须升级。
  
[[File:lesson1_001.jpg|500px]]
+
== 应用方面 ==
 +
在嵌入式领域,单片机位于哪个位置。我们看看一个自动化的机床,在这条生产线上面,比如说在这传输带上,会有一些单片机来检测物品传输的位置,触发某些信号。
 +
但其总控肯定运行操作系统,以处理更加复杂的事情。
 +
[[File:chapter1_lesson1_001.png|800px]]
  
想象有一个电子枪,一边移动,一边发出各种颜色的光。这里有很多细节问题,我们一个一个的梳理。
+
再看看Google的机器人,他的手臂、脚趾,也许有些单片机来控制其动作,但他的核心大脑,肯定运行操作系统,才能处理各种复杂的事情。
# 1. 电子枪是如何移动的?
+
也就是说,在一个复杂的系统,操作系统是大脑,单片机是可以实现手指的功能。那么你想去做大脑还是想去做手指?
答:有一条CLK时钟线与LCD相连,每发出一次CLK(高低电平),电子枪就移动一个像素。
+
[[File:chapter1_lesson1_002.png|800px]]
#2. 颜色如何确定?
 
答:由连接LCD的三组线:R(Red)、G(Green)、B(Blue)确定。
 
#3. 电子枪如何得知应跳到下一行?
 
答:有一条HSYNC信号线与LCD相连,每发出一次脉冲(高低电平),电子枪就跳到下一行。
 
#4. 电子枪如何得知应跳到原点?
 
答:有一条VSYNC信号线与LCD相连,每发出一次脉冲(高低电平),电子枪就跳到原点。
 
#5. RGB线上的数据从何而来?
 
答:内存里面划分一块显存(FrameBuffer),里面存放了要显示的数据,LCD控制器从里面将数据读出来,通过RGB三组线传给电子枪,电子枪再依次打到显示屏上。
 
#6. 前面的信号由谁发给LCD?
 
答:有S3C2440里面的LCD控制器来控制发出信号。
 
  
通过JZ2440原理图对上面进行验证,下图的LCD控制器接口图。
+
并且单片机的产品升级换代比较慢,一个产品使用单片机的话,他追求的是稳定与成本,那显然,日常的工作的活少,并且也不需要你有太新的技能,既然如此,公司干嘛要花2~3万来请人做单片机,直接花几千元请个新人不就完了吗?
  
[[File:lesson1_002.jpg|500px]]
+
并且单片机的价格优势正在逐渐消失,我们在淘宝搜索一下,STM32开发板的基本都是1-200元,而一个能够运行Linux系统的板子,nanopi的价格却在100元左右。
 +
一个能够运行Linux操作系统,有512M DDR内存,有四核处理的的ARM开发板,他只需要99元。所以说,现在单片机的价格优势正逐渐消失,他只能保持微弱的优势就是稳定性这一特点。
  
①是时钟信号,每来一个CLK,电子枪就移动一个像素;
+
下面来看看使用的单片机和使用操作系统开发的产品,比如闹钟、自动售货机就是单片机做的。<br>
②是用来传输颜色数据;
+
但自动售卖机,他一旦需要连接网络,需要WiFi,他很可能就需要操作系统。现在的新型自动售卖机,上面有微信支付,就必须要操作系统。<br>
③是垂直方向同步信号,FRAME(帧);
+
像无人机,既用单片机也用Linux操作系统。单片机可以更加及时的处理一些信息。看这些产品,你更想做哪些产品?
④是水平方向同步信号,LINE(行);
+
[[File:chapter1_lesson1_003.png|800px]]
再来看看LCD的芯片手册。
 
  
[[File:lesson1_003.jpg|500px]]
+
== 技术方面 ==
先是VLED+、VLED-背光灯电源。VDD、VDD是LCD电源。
+
我们的操作系统Linux,他需要一个Bootloader,这个Bootloader就是一个单片机裸板程序的大全,只要掌握了Linux的Bootloader,对单片机是轻而易举。
R0-R7、G0-G7、B0-B7是红绿蓝颜色信号。
+
在后面视频,我会讲解这点。所以说,我告诉你们,学单片机没前途了。
PCLK是像素时钟信号。DISP是像素开关。
 
HSYNC、VSYNC分别是水平方向、垂直方向信号。
 
DE数据使能。X1、Y1、X2、Y2是触摸屏信号。
 
  
可以看出LCD有很多信号,这些信号要根据时序图传输才能正确显示。参考JZ2440_4.3寸LCD手册_AT043TN24的时序如下:
+
当然我说的是一般情况,你说特例我就完蛋了,周立功做单片机的,年收入几亿,这没办法说。'''注意''',我说的是学习,在学习上,你不需要用单片机来学习,但是在工作中,我们设计产品的时候,如果单片机的性能更好,我们就要选择单片机。
 +
就比如说小米的智能插座,他就是使用单片机来做的,如果同一个功能,用单片机可以省成本,我干嘛不用单片机呢?卖出几百万台设备,每一个省一毛钱,就可以省几十万。我只告诉你,在技术方面,一旦我们掌握了Linux的bootloader,反过来,对单片机来说,他是小菜一碟。
  
[[File:lesson1_004.png|500px]]
+
=单片机知识是Linux驱动开发的基础之一 =
  
从最小的像素开始分析,电子枪每次在CLK下降沿(本开发板是下降沿)从数据线Dn0-Dn7上得到数据,发射到显示屏上,然后移动到下一个位置。Dn0-Dn7上的数据来源就是前面介绍的FrameBuffer。就这样从一行的最左边,一直移动到一行的最右边,完成了一行的显示,假设为x。
+
为什么没前途也要学习单片机?
  
当打完一行的最后一个数据后,就会收到Hsync行同步信号,根据时序图,一个Hsync周期可以大致分为五部分组成:thp、thb、1/tc、thd、thf。thp称为脉冲宽度,这个时间不能太短,太短电子枪可能识别不到。电子枪正确识别到thp后,会从最右端移动最左端,这个移动的时间就是thb,称之为移动时间。thf表示显示完最右像素,再过多久Hsync才来。
+
'''因为它是个很好的入口。'''
同理,当电子枪一行一行的从上面移动到最下面时,Vsync垂直同步信号就让电子枪移动回最上边。Vsync中的tvp是脉冲宽度,tvb是移动时间,tvf表示显示完最下一行像素,再过多久Vsync才来。
 
假设一共有y行,则LCD的分辨率就是x*y。
 
  
关于显示原理,可以参考这篇博客:http://www.cnblogs.com/shangdawei/p/4760933.html
+
单片机的学习可以让我们抛开复杂的软件结构,先'''掌握硬件操作''',如:看原理图、芯片手册、写程序操作寄存器等。
里面有一个LCD显示配置示意图如下:
+
在上一节视频里,我刚把单片机贬得一无是处,说单片机没前途了,这节视频,我又要告诉你们,没有前途,也要学习单片机。为什么?
  
[[File:lesson1_005.jpg|500px]]
+
首先,我说不用学习单片机,是指不要使用老一套得学习方法学习单片机。什么叫老一套的方法?
 +
*硬件上:不要使用C51、STM32这些专用的单片机开发板。如果以后,你不打算从事单片机开发,你用这些芯片干嘛,研究了两三个月,把这些寄存器都用清楚了,你又用不上,没必要啊。
 +
*软件上:不要使用Keil、MDK等集成度太高的软件。你用这些软件,你写个main()就可以了,然后调用各种库,进行傻瓜式操作。这些好用的工具,封装了很多技术细节,使得我们没法了解裸机、单片机的本质。
  
当发出一个HSYNC信号后,电子枪就会从最右边花费HBP时长移动到最左边,等到了最右边后,等待HFP时长HSYNC信号才回来。因此,HBP和HFP分别决定了左边和右边的黑框。
+
以后我们会使用新一套的方法来进行单片机的开发。新一套的方法,我们后面再介绍。
同理,当发出一个VSYNC信号后,电子枪就会从最下边花费VBP时长移动到最上边,等到了最下边后,等待VFP时长VSYNC信号才回来。因此,VBP和VFP分别决定了上边和下边的黑框。
+
[[File:chapter1_lesson2_001.png|800px]]
中间灰色区域才是有效显示区域。
 
  
再来解决最后一个问题:每个像素再FrameBuffer中,占据多少位BPP(Bits Per Pixels)?
+
我们之所以还要学习单片机,是因为他里面的知识,对我们后续学习Linux还是有用的。我们首先来看看,一个Linux系统是怎么一回事。
前面的LCD引脚功能图里,R0-R7、G0-G7、B0-B7,每个像素是占据3*8=24位的,即硬件上LCD的BPP是确定的。
+
一个嵌入式Linux系统的软件组成:
虽然LCD上的引脚是固定的,但我们使用的时候,可以根据实际情况进行取舍,比如我们的JZ2440使用的是16BPP,因此LCD只需要R0-R4、G0-G5、B0-B4与SOC相连,5+6+6=16BPP,每个像素就只占据16位数据。
 
  
我们写程序的思路如下:
+
'''单片机大全Bootloader-->Linux驱动-->Linux APP-->Linux GUI(Android/QT)'''
1. 查看LCD芯片手册,查看相关的时间参数、分辨率、引脚极性;
 
2. 根据以上信息设置LCD控制器寄存器,让其发出正确信号;
 
3. 在内存里面分配一个FrameBuffer,在里面用若干位表示一个像素,再把首地址告诉LCD控制器;
 
之后LCD控制器就能周而复始取出FrameBuffer里面的像素数据,配合其它控制信号,发送给电子枪,电子枪再让在LCD上显示出来。以后我们想显示图像,只需要编写程序向FrameBuffer填入相应数据即可,硬件会自动的完成显示操作。
 
  
 +
我们PC机一上电的时候,黑色屏幕上会显示BIOS,这个BIOS目的是去启动Windows内核。Windows内核再挂载C盘(系统盘)、D盘(应用盘),最后再去启动应用程序,像QQ、网游等。
  
 +
同样的道理,我们的Android手机或者工控设备,也有BIOS,但嵌入式Linux系统里面不叫BIOS,叫Bootloader,他的目的是去启动Linux内核。
 +
他首先也是识别应用程序所在的存储设备,挂载根文件系统(在Windows系统里面的C盘、D盘,在Linux里面称为根文件系统)。最后去启动应用程序。
 +
[[File:chapter1_lesson2_002.png|800px]]
  
 +
仔细的分析下Bootloader,他去启动内核,他去哪里启动内核呢?
 +
显然是去某个地方读出内核,就比如说BIOS是去C盘上读出Windows内核,我们的Bootloader是去Flash或者SD卡读取内核。
 +
因此Bootloader要拥有读取Flash或者SD卡的能力。有些Bootloader还要显示logo,因此还要具有操作LCD的能力。Bootloader还要设置开发板的环境,比如,初始化时钟、初始化内存、还要设置网卡等。
 +
这么多事情,都是在Bootloader里面实现的,太复杂了,如果你一来就分析整个Bootloader是非常困难的。
  
 +
那我们怎么学习呢?
 +
把他拆开,写出单独的程序,比如:LED点灯、时钟、网卡、Flash都单独写个程序来练习,这些不就是单片机程序吗?所以说,Bootloader是单片机程序的大全。我们为了更好的学习Bootloader,我们应该事先一个一个练习硬件,当我们熟悉每个硬件后,再组合起来,就是一个Bootloader。
 +
[[File:chapter1_lesson2_003.png|800px]]
  
 +
我们再来看看Bootloader启动内核之后,内核再去挂载根文件系统,意味着内核也要有操作硬件的能力,这就是驱动程序。我们首先来看看一个简单的驱动程序是什么样子。
 +
首先我们的应用程序是调用open()、read()、write()这些标准的接口去访问硬件。那么就进入驱动程序里面,驱动程序里面有对应的drive_open()、drive_read()、drive_write()。最后在驱动程序里面,去配置硬件。
 +
这里以如果是一个LED点灯驱动,那么drive_open()要把GPIO设置为输出引脚,drive_read(),返回GPIO状态,driver_write()则写GPIO,让引脚输出高电平或者低电平。
 +
[[File:chapter1_lesson2_004.png|800px]]
  
 +
对于我们的LED驱动程序,你需要提供drive_open()、drive_read()、drive_write()这些接口,这就是他的框架。具体的怎么操作硬件,就是硬件操作。
 +
所以说,我们事先在单片机里面,熟悉熟练的掌握硬件操作。即驱动程序的组成:
  
 +
'''驱动程序=软件框架+硬件操作'''
  
 +
你需要学会看原理图、看硬件怎么连接、看芯片手册、知道怎么读写寄存器。这一切都可以先在单片机里面学习,去掌握。以后学习Linux驱动时,把重点放在软件框架就行了。
  
[[File:lesson2_001.png|500px]]
+
我们可以事先学习单片机,单片机的学习可以让我们先抛开复杂的软件结构,先掌握硬件的操作,如:看原理图、芯片手册、写程序操作寄存器等。
 +
这就是为什么单片机没有前途,我们也要学习。是因为他里面涉及的硬件操作,对我们后续的学习,非常有用处。
  
[[File:lesson2_002.jpg|500px]]
+
现在我们知道了,'''我们学习单片机,不是为了掌握单片机的开发技能,而是为了掌握Bootloader,掌握硬件操作'''。
 +
[[File:chapter1_lesson2_005.png|800px]]
  
[[File:lesson3_001.jpg|500px]]
+
=单片机和Linux都想学_换个两全的方法学习单片机 =
  
[[File:lesson3_002.jpg|500px]]
+
本节教你如何学习单片机,如何选择合适的'''开发板'''和'''开发工具'''。
  
[[File:lesson5_001.png|500px]]
+
现在我们知道单片机是要学习的,那么怎么去学习单片机?在上一课我们说不要使用老一套的方法学习,实际上是指的两个问题。
  
[[File:lesson5_002.png|500px]]
+
'''第一:选择什么开发板;'''
  
[[File:lesson5_003.png|500px]]
+
'''第二:使用什么开发工具;'''
  
[[File:lesson5_004.png|500px]]
+
我们学习单片机的目的是干嘛?'''目的是为后续嵌入式Linux学习服务'''。
 +
在这条学习线路上:
  
[[File:lesson5_005.png|500px]]
+
单片机->bootloader->Linux系统/驱动->APP(QT) '''可以使用同一套开发板'''。
  
[[File:lesson5_006.png|500px]]
+
我们选择开发板的原则是:'''资料丰富'''。
  
[[File:lesson5_007.png|500px]]
+
[[File:chapter1_lesson3_001.png|800px]]
  
[[File:lesson5_008.png|500px]]
+
开发板首推'''三星 (SAMSUNG)'''系列的,资料最开放,
 +
* 有S3C2440、S3C6410、S5PV210、Exynos4412;
 +
* 然后是'''德州仪器 (TI)'''的,TI开始不开放资料,现在逐渐公开了,有AM437X、AM335X;
 +
* 然后是'''飞思卡尔(freescale)''',有iMX6;
 +
* 还有其它国产芯片:'''全志'''、'''瑞芯微''';
  
[[File:bak.png|500px]]
+
我们用百度进行搜索,看哪个资料最丰富。结果如下:
  
[[File:lesson6_001.png|500px]]
+
[[File:chapter1_lesson3_002.png|800px]]
  
[[File:bak.png|500px]]
+
再在搜索关键词中加入“教程”后,S3C2440的搜索结果比AM335X更多,因此S3C2440的资料仍是最多的,TI的营销更好,当然,TI作为工控板,其用户也是很多的。
  
[[File:lesson6_001.png|500px]]
+
所以,'''从教程的丰富程度来看,S3C2440为首选开发板''';
  
[[File:lesson8_001.jpg|500px]]
+
我们后面会考虑使用TI的芯片重新录制一套视频,但需要2-3年的功夫,所以,现在还是使用S3C2440吧。
  
[[File:lesson8_002.jpg|500px]]
+
现在普遍有个错误观点:S3C2440过时了,它还是ARM9内核,现在Cortex-A7、 Cortex-A8、 Cortex-A9、 Cortex-A15都出来了,它的性能太差了。
 +
性能差没错,但它是否过时了呢?
  
 +
'''那要看学到的知识是否过时。'''
 +
 +
我们首先来看看一个芯片是怎么组成的,里面有CPU、外设串口、I2C、SPI、LCD等。
 +
 +
[[File:chapter1_lesson3_003.png|800px]]
 +
我们写程序的时候,是去操作这些模块的寄存器,访问这些模块,并不是去操作CPU。
 +
等你工作的时候,你使用不同的芯片,那么差别在于这些模块,这些硬件的操作,差别不在CPU操作,你写程序的时候,根本不涉及CPU的内部机制。
 +
 +
'''不同芯片的差别:
 +
在于外设操作,不在于CPU,写程序几乎不涉及CPU,只有涉及中断时,才会跟CPU的机制有点关系,但是不同CPU的架构差异很小,并且我们后面开发Linux驱动时,内核已经帮我们做好了这些处理,根本不需要去关心。'''
 +
 +
从上一课我们知道,驱动=软件框架+硬件操作。这个软件框架对于所有的芯片都是一样的,因为都是用Linux内核。
 +
而这个硬件操作,你在2440上掌握了串口操作,I2C操作、SPI操作,掌握了这些硬件的语言,你换一种芯片,是完全类似的。
 +
 +
[[File:chapter1_lesson3_004.png|800px]]
 +
 +
我假设你选择了2440开发板,那么怎么使用2440开发板来学习单片机的开发呢?又使用什么开发工具呢?
 +
以前在Windows开发的时候,我们使用ADS、Keil、MDK等,你直接写个main()函数,所有的细节都帮你实现了,谁来调用main()函数,有他帮你做了。这main()所生成出来的代码,怎么放入到内存里面,这工具也帮你做了,我们基本上只需要写main()函数,只需要写C语言就行了。但是这里掩盖了太多的技术细节,你看看我们[官网->学习路线](http://www.100ask.net/a/howtostudy/) 的这篇文章,里面有个比较:
 +
 +
① Windows下的单片机学习,深度不够
 +
 +
* Windows下有很好的图形界面单片机开发软件,比如keil、MDK等。
 +
* 它们封装了很多技术细节,比如:
 +
* 你只会从main函数开始编写代码,却不知道上电后第1条代码是怎么执行的;
 +
* 你可以编写中断处理函数,但是却不知道它是怎么被调用的;
 +
* 你不知道程序怎么从Flash上被读入内存;
 +
* 也不知道内存是怎么划分使用的,不知道栈在哪、堆在哪;
 +
* 当你想裁剪程序降低对Flash、内存的使用时,你无从下手;
 +
* 当你新建一个文件时,它被自动加入到工程里,但是其中的机理你完全不懂;
 +
* 等等等。
 +
 +
② 基于ARM+Linux裸机学习,可以学得更深,并且更贴合后续的Linux学习。
 +
 +
* 实际上它就是Linux下的单片机学习,只是一切更加原始:所有的代码需要你自己来编写;哪些文件加入工程,需要你自己来管理。
 +
* 在工作中,我们当然倾向于使用Windows下更便利的工具,但是在学习阶段,我们更想学习到程序的本质。
 +
* 一切从零编写代码、管理代码,可以让我们学习到更多知识:
 +
* 你需要了解芯片的上电启动过程,知道第1条代码如何运行;
 +
* 你需要掌握怎么把程序从Flash上读入内存;
 +
* 需要理解内存怎么规划使用,比如栈在哪,堆在哪;
 +
* 需要理解代码重定位;
 +
* 需要知道中断发生后,软硬件怎么保护现场、跳到中断入口、调用中断程序、恢复现场;
 +
* 你会知道,main函数不是我们编写的第1个函数;
 +
* 你会知道,芯片从上电开始,程序是怎么被搬运执行的;
 +
* 你会知道,函数调用过程中,参数是如何传递的;
 +
* 你会知道,中断发生时,每一个寄存器的值都要小心对待;
 +
* 等等等。
 +
* 你掌握了ARM+Linux的裸机开发,再回去看Windows下的单片机开发,会惊呼:怎么那么简单!并且你会完全明白这些工具没有向你展示的技术细节。
 +
 +
 +
如果我们基于ARM+Linux,不使用这些Windows工具,你可以学得更深,并且单片机的大全Bootloader,他就是ARM+Linux开发的,他并不使用Windows下的工具。
 +
你基于ARM+Linux学裸板、学单片机,你可以学得更多,因为我们一切都从零开始的。我们既管理这些代码,也可以知道芯片上电的时候做了什么事情,知道程序自己怎么把自己读到内存,且知道怎么去规划内存,知道怎么代码重定位……
 +
 +
我说的这些概念,你可能听都没听过,这是因为Windows下这些好用的工具把这些统统都给屏蔽了。
 +
我们使用ARM+Linux进行裸板开发,一旦掌握了ARM+Linux开发这套机制,再回过头去看这些Windows工具、看STM32的话,你只需要几分钟就可以搞定。
 +
并且你可以无缝进入后续的学习,因为你已经熟练掌握了Linux的操作环境,后面的Bootloader是在Linux下开发的,后面的Linux驱动也是在Linux下开发的。
 +
 +
[[File:chapter1_lesson3_005.png|800px]]
 +
 +
所以我们怎么去学习单片机的开发呢?
 +
 +
'''使用S3C2440开发板,在Linux环境(Ubuntu)下使用arm-Linux-gcc工具来编译程序。'''
 +
 +
你编写代码的时候,可以使用Windows下各种好用的工具,文本工具等,但便宜的时候,使用arm-Linux-gcc来编译。
 +
</div>
 +
='''查看《《所有章节目录》》'''=
 +
 +
<categorytree mode=all background-color:white;">ARM裸机加强版</categorytree>
 
[[Category:ARM裸机加强版 ]]
 
[[Category:ARM裸机加强版 ]]
 +
[[Category:Jz2440]]

2018年4月23日 (一) 11:00的最新版本

单片机程序员发展的必选之路: Linux

我们的第一期是教大家如何将ARM开发板当作单片机来用,但在这期视频的第一节,我告诉你们,学习单片机是没有前途的

话说得非常狠,因为不这样说,没法警醒你们。我说这句话,是冒着生命危险的,因为很多人依靠单片机来生活,淘宝上有一大堆售卖单片机开发板的,像51、STM32等。

工资方面

我们学习这些不就是为了赚钱吗?在51job上,搜索“单片机”,工资平均下来是几千块钱。然后搜搜“Linux系统工程师”,平均工资是上万左右。

职业发展

这里我有切实的体会,我2003年毕业,2005年进入一个小公司,当时做的是车载电话,我们先是用51单片机来做的。当时我的李姓同事,用两个3000多行的C文件,实现了车载电话的功能。 另一个魏姓同事,将功能拆分成各种模块,使用了50多个C文件,以操作系统的思想,重新写了这个程序。这两个牛人,都跳槽了,都不做单片机了。 李姓同事去了美国,深造了机器人视觉,现在是百度的搜索专家,魏姓同事和我一起去了中兴,现在在厦门联想公司负责手机的开发,而我给你们录视频,但我们都不玩单片机了。 我在2005发表了一个2440开发板上仿照ucos写了一个操作系统,10年前,我们已经把单片机玩得登峰造极了。但是我们还需要升级,为什么? 因为单片机非常简单,稍微认真学习2-3个月就可以达到中等的水平,你工作十年和工作两年技能差别不大,对一个公司,现实一点,他肯定喜欢使用工资更低还更愿意加班的新人,所以说,我们必须升级。

应用方面

在嵌入式领域,单片机位于哪个位置。我们看看一个自动化的机床,在这条生产线上面,比如说在这传输带上,会有一些单片机来检测物品传输的位置,触发某些信号。 但其总控肯定运行操作系统,以处理更加复杂的事情。 Chapter1 lesson1 001.png

再看看Google的机器人,他的手臂、脚趾,也许有些单片机来控制其动作,但他的核心大脑,肯定运行操作系统,才能处理各种复杂的事情。 也就是说,在一个复杂的系统,操作系统是大脑,单片机是可以实现手指的功能。那么你想去做大脑还是想去做手指? Chapter1 lesson1 002.png

并且单片机的产品升级换代比较慢,一个产品使用单片机的话,他追求的是稳定与成本,那显然,日常的工作的活少,并且也不需要你有太新的技能,既然如此,公司干嘛要花2~3万来请人做单片机,直接花几千元请个新人不就完了吗?

并且单片机的价格优势正在逐渐消失,我们在淘宝搜索一下,STM32开发板的基本都是1-200元,而一个能够运行Linux系统的板子,nanopi的价格却在100元左右。 一个能够运行Linux操作系统,有512M DDR内存,有四核处理的的ARM开发板,他只需要99元。所以说,现在单片机的价格优势正逐渐消失,他只能保持微弱的优势就是稳定性这一特点。

下面来看看使用的单片机和使用操作系统开发的产品,比如闹钟、自动售货机就是单片机做的。
但自动售卖机,他一旦需要连接网络,需要WiFi,他很可能就需要操作系统。现在的新型自动售卖机,上面有微信支付,就必须要操作系统。
像无人机,既用单片机也用Linux操作系统。单片机可以更加及时的处理一些信息。看这些产品,你更想做哪些产品? Chapter1 lesson1 003.png

技术方面

我们的操作系统Linux,他需要一个Bootloader,这个Bootloader就是一个单片机裸板程序的大全,只要掌握了Linux的Bootloader,对单片机是轻而易举。 在后面视频,我会讲解这点。所以说,我告诉你们,学单片机没前途了。

当然我说的是一般情况,你说特例我就完蛋了,周立功做单片机的,年收入几亿,这没办法说。注意,我说的是学习,在学习上,你不需要用单片机来学习,但是在工作中,我们设计产品的时候,如果单片机的性能更好,我们就要选择单片机。 就比如说小米的智能插座,他就是使用单片机来做的,如果同一个功能,用单片机可以省成本,我干嘛不用单片机呢?卖出几百万台设备,每一个省一毛钱,就可以省几十万。我只告诉你,在技术方面,一旦我们掌握了Linux的bootloader,反过来,对单片机来说,他是小菜一碟。

单片机知识是Linux驱动开发的基础之一

为什么没前途也要学习单片机?

因为它是个很好的入口。

单片机的学习可以让我们抛开复杂的软件结构,先掌握硬件操作,如:看原理图、芯片手册、写程序操作寄存器等。 在上一节视频里,我刚把单片机贬得一无是处,说单片机没前途了,这节视频,我又要告诉你们,没有前途,也要学习单片机。为什么?

首先,我说不用学习单片机,是指不要使用老一套得学习方法学习单片机。什么叫老一套的方法?

  • 硬件上:不要使用C51、STM32这些专用的单片机开发板。如果以后,你不打算从事单片机开发,你用这些芯片干嘛,研究了两三个月,把这些寄存器都用清楚了,你又用不上,没必要啊。
  • 软件上:不要使用Keil、MDK等集成度太高的软件。你用这些软件,你写个main()就可以了,然后调用各种库,进行傻瓜式操作。这些好用的工具,封装了很多技术细节,使得我们没法了解裸机、单片机的本质。

以后我们会使用新一套的方法来进行单片机的开发。新一套的方法,我们后面再介绍。 Chapter1 lesson2 001.png

我们之所以还要学习单片机,是因为他里面的知识,对我们后续学习Linux还是有用的。我们首先来看看,一个Linux系统是怎么一回事。 一个嵌入式Linux系统的软件组成:

单片机大全Bootloader-->Linux驱动-->Linux APP-->Linux GUI(Android/QT)

我们PC机一上电的时候,黑色屏幕上会显示BIOS,这个BIOS目的是去启动Windows内核。Windows内核再挂载C盘(系统盘)、D盘(应用盘),最后再去启动应用程序,像QQ、网游等。

同样的道理,我们的Android手机或者工控设备,也有BIOS,但嵌入式Linux系统里面不叫BIOS,叫Bootloader,他的目的是去启动Linux内核。 他首先也是识别应用程序所在的存储设备,挂载根文件系统(在Windows系统里面的C盘、D盘,在Linux里面称为根文件系统)。最后去启动应用程序。 Chapter1 lesson2 002.png

仔细的分析下Bootloader,他去启动内核,他去哪里启动内核呢? 显然是去某个地方读出内核,就比如说BIOS是去C盘上读出Windows内核,我们的Bootloader是去Flash或者SD卡读取内核。 因此Bootloader要拥有读取Flash或者SD卡的能力。有些Bootloader还要显示logo,因此还要具有操作LCD的能力。Bootloader还要设置开发板的环境,比如,初始化时钟、初始化内存、还要设置网卡等。 这么多事情,都是在Bootloader里面实现的,太复杂了,如果你一来就分析整个Bootloader是非常困难的。

那我们怎么学习呢? 把他拆开,写出单独的程序,比如:LED点灯、时钟、网卡、Flash都单独写个程序来练习,这些不就是单片机程序吗?所以说,Bootloader是单片机程序的大全。我们为了更好的学习Bootloader,我们应该事先一个一个练习硬件,当我们熟悉每个硬件后,再组合起来,就是一个Bootloader。 Chapter1 lesson2 003.png

我们再来看看Bootloader启动内核之后,内核再去挂载根文件系统,意味着内核也要有操作硬件的能力,这就是驱动程序。我们首先来看看一个简单的驱动程序是什么样子。 首先我们的应用程序是调用open()、read()、write()这些标准的接口去访问硬件。那么就进入驱动程序里面,驱动程序里面有对应的drive_open()、drive_read()、drive_write()。最后在驱动程序里面,去配置硬件。 这里以如果是一个LED点灯驱动,那么drive_open()要把GPIO设置为输出引脚,drive_read(),返回GPIO状态,driver_write()则写GPIO,让引脚输出高电平或者低电平。 Chapter1 lesson2 004.png

对于我们的LED驱动程序,你需要提供drive_open()、drive_read()、drive_write()这些接口,这就是他的框架。具体的怎么操作硬件,就是硬件操作。 所以说,我们事先在单片机里面,熟悉熟练的掌握硬件操作。即驱动程序的组成:

驱动程序=软件框架+硬件操作

你需要学会看原理图、看硬件怎么连接、看芯片手册、知道怎么读写寄存器。这一切都可以先在单片机里面学习,去掌握。以后学习Linux驱动时,把重点放在软件框架就行了。

我们可以事先学习单片机,单片机的学习可以让我们先抛开复杂的软件结构,先掌握硬件的操作,如:看原理图、芯片手册、写程序操作寄存器等。 这就是为什么单片机没有前途,我们也要学习。是因为他里面涉及的硬件操作,对我们后续的学习,非常有用处。

现在我们知道了,我们学习单片机,不是为了掌握单片机的开发技能,而是为了掌握Bootloader,掌握硬件操作Chapter1 lesson2 005.png

单片机和Linux都想学_换个两全的方法学习单片机

本节教你如何学习单片机,如何选择合适的开发板开发工具

现在我们知道单片机是要学习的,那么怎么去学习单片机?在上一课我们说不要使用老一套的方法学习,实际上是指的两个问题。

第一:选择什么开发板;

第二:使用什么开发工具;

我们学习单片机的目的是干嘛?目的是为后续嵌入式Linux学习服务。 在这条学习线路上:

单片机->bootloader->Linux系统/驱动->APP(QT) 可以使用同一套开发板

我们选择开发板的原则是:资料丰富

Chapter1 lesson3 001.png

开发板首推三星 (SAMSUNG)系列的,资料最开放,

  • 有S3C2440、S3C6410、S5PV210、Exynos4412;
  • 然后是德州仪器 (TI)的,TI开始不开放资料,现在逐渐公开了,有AM437X、AM335X;
  • 然后是飞思卡尔(freescale),有iMX6;
  • 还有其它国产芯片:全志瑞芯微

我们用百度进行搜索,看哪个资料最丰富。结果如下:

Chapter1 lesson3 002.png

再在搜索关键词中加入“教程”后,S3C2440的搜索结果比AM335X更多,因此S3C2440的资料仍是最多的,TI的营销更好,当然,TI作为工控板,其用户也是很多的。

所以,从教程的丰富程度来看,S3C2440为首选开发板

我们后面会考虑使用TI的芯片重新录制一套视频,但需要2-3年的功夫,所以,现在还是使用S3C2440吧。

现在普遍有个错误观点:S3C2440过时了,它还是ARM9内核,现在Cortex-A7、 Cortex-A8、 Cortex-A9、 Cortex-A15都出来了,它的性能太差了。 性能差没错,但它是否过时了呢?

那要看学到的知识是否过时。

我们首先来看看一个芯片是怎么组成的,里面有CPU、外设串口、I2C、SPI、LCD等。

Chapter1 lesson3 003.png 我们写程序的时候,是去操作这些模块的寄存器,访问这些模块,并不是去操作CPU。 等你工作的时候,你使用不同的芯片,那么差别在于这些模块,这些硬件的操作,差别不在CPU操作,你写程序的时候,根本不涉及CPU的内部机制。

不同芯片的差别: 在于外设操作,不在于CPU,写程序几乎不涉及CPU,只有涉及中断时,才会跟CPU的机制有点关系,但是不同CPU的架构差异很小,并且我们后面开发Linux驱动时,内核已经帮我们做好了这些处理,根本不需要去关心。

从上一课我们知道,驱动=软件框架+硬件操作。这个软件框架对于所有的芯片都是一样的,因为都是用Linux内核。 而这个硬件操作,你在2440上掌握了串口操作,I2C操作、SPI操作,掌握了这些硬件的语言,你换一种芯片,是完全类似的。

Chapter1 lesson3 004.png

我假设你选择了2440开发板,那么怎么使用2440开发板来学习单片机的开发呢?又使用什么开发工具呢? 以前在Windows开发的时候,我们使用ADS、Keil、MDK等,你直接写个main()函数,所有的细节都帮你实现了,谁来调用main()函数,有他帮你做了。这main()所生成出来的代码,怎么放入到内存里面,这工具也帮你做了,我们基本上只需要写main()函数,只需要写C语言就行了。但是这里掩盖了太多的技术细节,你看看我们[官网->学习路线](http://www.100ask.net/a/howtostudy/) 的这篇文章,里面有个比较:

① Windows下的单片机学习,深度不够
  • Windows下有很好的图形界面单片机开发软件,比如keil、MDK等。
  • 它们封装了很多技术细节,比如:
  • 你只会从main函数开始编写代码,却不知道上电后第1条代码是怎么执行的;
  • 你可以编写中断处理函数,但是却不知道它是怎么被调用的;
  • 你不知道程序怎么从Flash上被读入内存;
  • 也不知道内存是怎么划分使用的,不知道栈在哪、堆在哪;
  • 当你想裁剪程序降低对Flash、内存的使用时,你无从下手;
  • 当你新建一个文件时,它被自动加入到工程里,但是其中的机理你完全不懂;
  • 等等等。
② 基于ARM+Linux裸机学习,可以学得更深,并且更贴合后续的Linux学习。
  • 实际上它就是Linux下的单片机学习,只是一切更加原始:所有的代码需要你自己来编写;哪些文件加入工程,需要你自己来管理。
  • 在工作中,我们当然倾向于使用Windows下更便利的工具,但是在学习阶段,我们更想学习到程序的本质。
  • 一切从零编写代码、管理代码,可以让我们学习到更多知识:
  • 你需要了解芯片的上电启动过程,知道第1条代码如何运行;
  • 你需要掌握怎么把程序从Flash上读入内存;
  • 需要理解内存怎么规划使用,比如栈在哪,堆在哪;
  • 需要理解代码重定位;
  • 需要知道中断发生后,软硬件怎么保护现场、跳到中断入口、调用中断程序、恢复现场;
  • 你会知道,main函数不是我们编写的第1个函数;
  • 你会知道,芯片从上电开始,程序是怎么被搬运执行的;
  • 你会知道,函数调用过程中,参数是如何传递的;
  • 你会知道,中断发生时,每一个寄存器的值都要小心对待;
  • 等等等。
  • 你掌握了ARM+Linux的裸机开发,再回去看Windows下的单片机开发,会惊呼:怎么那么简单!并且你会完全明白这些工具没有向你展示的技术细节。


如果我们基于ARM+Linux,不使用这些Windows工具,你可以学得更深,并且单片机的大全Bootloader,他就是ARM+Linux开发的,他并不使用Windows下的工具。 你基于ARM+Linux学裸板、学单片机,你可以学得更多,因为我们一切都从零开始的。我们既管理这些代码,也可以知道芯片上电的时候做了什么事情,知道程序自己怎么把自己读到内存,且知道怎么去规划内存,知道怎么代码重定位……

我说的这些概念,你可能听都没听过,这是因为Windows下这些好用的工具把这些统统都给屏蔽了。 我们使用ARM+Linux进行裸板开发,一旦掌握了ARM+Linux开发这套机制,再回过头去看这些Windows工具、看STM32的话,你只需要几分钟就可以搞定。 并且你可以无缝进入后续的学习,因为你已经熟练掌握了Linux的操作环境,后面的Bootloader是在Linux下开发的,后面的Linux驱动也是在Linux下开发的。

Chapter1 lesson3 005.png

所以我们怎么去学习单片机的开发呢?

使用S3C2440开发板,在Linux环境(Ubuntu)下使用arm-Linux-gcc工具来编译程序。

你编写代码的时候,可以使用Windows下各种好用的工具,文本工具等,但便宜的时候,使用arm-Linux-gcc来编译。