【linux】正点原子linux教程学习

  最近看了正点原子的linux教学视频,感觉讲的挺不错,简单来整理一下,对此有个印象。

一、裸机代码

  视频教程中讲了nxp的imx6ull的soc(原来的freescale下面的产品,后来被nxp收购了,该soc使用的时arm内核,arm v7架构,最高主频800mhz,目前公司使用的nova的cpu也是完全相同的架构,最高主频900mhz,感觉相差不多)。
  这个系列的视频教程讲的比较详细,讲了芯片如何跑起来的很多相关的知识:

  • 链接地址:gcc链接时可以选择链接地址,链接地址可以在gcc的命令中给出,也可以在链接脚本.lds文件中给出。这样就可以在编译时设置,入口代码的地址。这让我会想起以前看编译原理的.o文件时可重定向的文件(应该就是地址无关代码),而链接好之后就是地址有关的代码了,应该必须放在链接时规定好的地址区域才能运行。正点原子在imx6ull裸机中设置的代码入口地址是0x87800000,说是因为u-boot的链接起始地址也是这个。
  • c语言环境的配置:使用c语言函数时,需要使用堆栈,使用cpu的sp寄存器。所以在执行c语言函数时,是需要设置sp寄存器(堆栈指针)的值,这样也就设置了栈底的地址,就可以使用c的堆栈了。因为c语言跑起来需要sp寄存器被设置。所以cpu跑的第一段代码肯定是汇编写的。所以上面的代码入口地址的代码时汇编代码。
  • bootrom:soc开发商有时候没有内部flash,不像stm32那样,从内部flash启动代码。这个imx6ull就是最先得启动nxp厂商在内部rom放置得代码,这块rom区域用户无法使用。rom中得代码就做了一些初始化得工作,比如:初始化ddr(这些soc的代码在ddr中运行,而不是像stm32那样)。(原子教程说不是所有得soc厂商都会在bootrom里面初始化ddr,如果厂商没有在bootrom中做初始化,就需要自己在汇编代码中做相关得初始化工作)
  • 选择启动设备: imx6ull可以设置从什么地方启动,可以让用户选择 从哪个设备启动:sd卡,emmc,nand等,这个好像stm32也可以设置。这里首先设置从内部rom启动,这也就是执行bootrom里面的代码,然后bootrom会从sd卡,emmc等设备获取头部信息,做一些初始化工作:初始化ddr等,并将bin文件拷贝到指定的地方:链接起始地址。
  • 汇编代码: 汇编代码就是从bootrom里面跑完的第一段代码,正点原子的是放置在0x87800000。里面主要定义了中断向量表中断处理函数等。这里面的内容跟stm32项目里面的汇编启动代码是很像的。只不过stm32的是soc厂商st帮着写了启动汇编文件,imx6ull的需要自己写启动汇编文件(bootrom里面并没有写中断向量表相关的内容)。中断向量表的第一个中断向量是reset复位中断,执行到这个就会转到复位中断处理函数,复位中断处理函数也在启动汇编文件中实现,里面会做一些初始化配置工作,可能还会调用类似c函数systeminit函数去做一些系统配置工作,最后该函数会调用主函数main。但是这里在主函数中才调用一些函数做中断相关的配置:使能中断,配置中断优先级等。这里就是在配置中断之前就已经使用了复位中断的函数,这里感觉是因为复位中断向量放在向量表的第一个,所以会最先走到这块,然后会跳转到复位中断处理函数。(处理器里面有硬件逻辑会使发生中断后跳转的对应的中断表,然后跳转到对应的中断处理函数,这就需要看cortex架构相关东西了),在Ubuntu下编译arm的工程,要使用交叉编译器。
      小结: 看了这系列的裸机视频之后,更理解cpu的运行流程了,感觉stm32的启动汇编代码也不是完全看不懂了。尤其是看了imx6ull的复杂,感觉stm32真是相对简单许多,即使使用寄存器函数,不使用库函数也行了。

二、嵌入式linux

linux移植三大部分

  • uboot
  • linux内核(包含设备树)
  • 根文件系统

u-boot

  • 要熟悉整个u-boot的工程目录,怎么编译,配置, 查看顶层的Makefile,但是这好像非常复杂,所以怎么配置,编译,移植u-boot也是比较有难度。
  • u-boot是开源的,可以从官网获得最原始的u-boot,但是一般soc厂家会对最原始的u-boot进行修改以适配自己的芯片和板子,然后使用soc的开发板厂商会进一步进行修改以适配自己的外设。所以是:原始u-boot–》soc厂商的u-boot–》板子厂商的u-boot。
  • 用于启动linux,可以烧写在板子上直接跑起来。相当于一个大型的裸机程序。
  • 里面驱动什么也都很全,网络驱动等都有,u-boot的命令非常多,且很全面,各种内存操作,网络操作,启动内核操作等都有,据说掌握u-boot的命令对linux的开发非常重要。
  • 正点原子通常利用u-boot的网络功能:nfs功能(网络文件系统),将系统镜像zImge什么的从利用u-boot的网络功能拷贝到内存中启动。

linux内核

  • 要熟悉整个linux内核的工程目录,怎么编译,配置, 查看顶层的Makefile,但是这好像更加复杂(据说u-boot的工程项目很多都参考了linux的项目,所以两者的的makefile,配置什么的都很相似),所以怎么配置,编译,移植linux内核也是比较有难度。
  • 设备树:貌似是为了方便驱动开发而整出来的东西,也需要编译设备树什么的,现在不太懂。
  • 只有linux内核,系统跑不起来,需要根文件系统。通常系统的内核并不大,zImage,或者uImage也就几M,根文件系统就大得多。
    【linux】正点原子linux教程学习_第1张图片
  • 上图中的nove的项目中的linux内核镜像uImage就只有11M,而根文件系统rootfs.img 就有80M。
  • 并且内核的大半还都是驱动。

根文件系统

  • 根文件系统就是linux里面根目录里面的那些文件,那些文件在移植linux系统的时候也要配置移植的,包含各种bin文件(编译好的软件),库文件,配置文件等等。是linux运行的基础。
  • 配置根文件系统也有很多种工具,用于生产那些可用的bin文件:ls,cat等常用的命令的实现文件等。
  • 由于根文件系统比较大,也可以利用Ubuntu做nfs服务器,将板子的根文件系统不放在板子中,直接放在ubuntu下,免得调试的时候老要反复烧写,方便开发。
  • busybox,用于编译生成根文件系统,

BusyBox 是一个集成了三百多个最常用Linux命令和工具的软件。BusyBox
包含了一些简单的工具,例如ls、cat和echo等等,还包含了一些更大、更复杂的工具,例grep、find、mount以及telnet。有些人将
BusyBox 称为 Linux 工具里的瑞士军刀。简单的说BusyBox就好像是个大工具箱,它集成压缩了 Linux
的许多工具和命令,也包含了 Android 系统的自带的shell。

根据以上百度内容可以知道,busybox应该是拥有许多linux小程序源码的工程,可以编译成linux所需的小工具的可执行文件,根据正点原子的后面还有添加库文件的操作,busybox应该不包括linux系统里面的库文件。

三、linux驱动开发

  • Linux驱动分三类:字符设备,块设备,网络设备。

  • linux的用户空间(用户态)和内核空间(内核态)
    kernel和驱动程序再内核空间跑,应用程序在用户空间跑。为了安全性的设置,用户空间程序会受限,暂时不去深究,要了解详细的内容可以百度去看。
    应用程序要访问内核资源怎么办?三种方法:系统调用,异常(中断)和陷入。
    系统调用:
    应用程序不直接调用系统调用,而是通过库API函数来间接调用系统调用,比如POSIX,API和c库,printf就是c库里面的函数,它里面实现的细节就调用了系统调用。

  • linux驱动可以编译到内核中,zImage;也可以编译成模块,.ko文件。

你可能感兴趣的:(Liunx学习)