第8章S3C2440系统启动

整理文档很辛苦,赏杯茶钱您下走!

免费阅读已结束,点击下载阅读编辑剩下 ...

阅读已结束,您可以下载文档离线阅读编辑

资源描述

ARM体系结构与编程参考资料V1.01英智科技,嵌入式培训专家1第8章S3C2440系统启动1.概述一般情况,嵌入式系统分为两部进行工作,一部份是采用汇编编写的,它的作用是在应用程序运行之前对系统硬件及软件运行环境进行必要的初始化,并在最后使程序跳转到应用程序。汇编代码虽然效率高,但代码可读性和可维护性比较差,因此,这一部份代码要尽量精减,这个阶段主要是给C/C++等高级语言程序准备执行环境;另一部份是采用C/C++编写的应用程序,采用C/C++编写的代码可读性和可维护性更好,因此,是系统大部份是采用它来完成。这两部份虽然是一个连续性整体,但为了更好的理解系统的启动过程,我们将它们分离成两部份,并命名为“启动代码”和“应用程序”以便于分析。启动代码是系统上电或复位以后运行的第一段代码,它直接面对ARM处理器内核及硬件控制器进行编程,所执行的操作与具体的目标系统紧密相关。2.系统启动描述因为启动代码与目标系统紧密相连,所以在分析启动代码之前,先了解一下S3C2440的启动方式。S3C2440支持两种方式的启动:NorFlash启动和NandFlash启动。NorFlash和NandFlash都是非易失性存储器,NorFlash的特点是芯片内执行,程序可以直接在其中运行,而不必将程序读取到RAM中运行。NorFlash虽然具有这个优点,但是它的性价比远低于NandFlash,因而很多系统采用NandFlash启动。NandFlash的特点是采用非线性存储模式,程序无法在其中运行,它只能作为程序或数据的存储载体,存储在其中的程序只能先拷贝到RAM中才能运行。S3C2440的引脚OM[1:0]等于“01”或“10”时,即为NorFlash启动,与nGCS0相连的NorFlash就被映射到nGCS0片选的空间,其地址被映射为0x00000000;当系统上电或复位时,程序会从0地址处开始执行,因此我们编写的启动代码要确保存储在0地址处。当启动方式为NorFlash启动时,没有额外需要考虑的问题,因为这种情况下程序在系统启动前就存储在NorFlash中,我们只要保证将启动代码保存在NorFlash开始的位置即可,系统上电或复位时,0地址处的启动代码就会被执行。S3C2440的引脚OM[1:0]等于“00”时,即为NandFlash启动,S3C2440芯片内部自带的一块容量为4K的被称为“Steppingstone”的BootSRAM被映射到nGCS0片选的空间,其地址被映射为0x00000000。在启动方式为NandFlash启动的情况下,系统启动前所有的程序存储在NandFlash中,系统的启动过程稍微有点复杂:系统上电或复位时,0地址处为S3C2440内部自带的BootSRAM,启动前里面没有任何存储内容,启动后S3C2440先通过硬件机制将NandFlash前4K的内容拷贝至其中,然后再运行里面的程序(从0地址处)。这种情况下我们需要保证将启动代码保存在NandFlash开始的位置,并且启动代码的大小要小于4K。1)如果系统的所有程序在编译链接后的大小小于4K,那在系统的启动代码中无需考ARM体系结构与编程参考资料V1.01英智科技,嵌入式培训专家2虑将程序从NandFlash搬运到SDRAM这个问题,因为所有的程序在启动时即全部由NandFlash拷贝至BootSRAM,程序在BootSRAM中运行即可;2)如果系统的所有程序在编译连接后的大小大于4K,那在系统的启动代码中需要包含一段将系统的全部程序从NandFlash搬运到SDRAM的代码,因为系统启动时只将NandFlash的前4K拷贝到了BootSRAM中,还有部分程序保存在NandFlash中,NandFlash中是无法运行程序的,需要将所有程序拷贝至SDRAM并在其中运行,所以在系统的启动代码中要包含这段有关程序拷贝的代码,并在所有程序拷贝完成后使程序跳转到SDRAM中运行。也就是说在启动方式为NandFlash启动的情况下,因为NandFlash的特性,程序需要涉及到两次的搬移,一次是从NandFlash搬移到BootSRAM,搬运的程序量大小是4K,目的是使系统能够启动;第二次搬运是从NandFlash搬运到系统的SDRAM,如果系统的所有程序量小于4K,这一步可以省略,搬运的程序量大小是系统的所有程序,目的是使程序在SDRAM中运行。第一次搬运是S3C2440通过硬件机制自动实现的,我们无需干预,第二次则需要我们程序员来实现。开发板带有两种FLASH:2M的NorFlash和256M的NandFlash。启动方式可通过拨键开关S2来选择。此处讲解的内容是基于NorFLASH启动的。启动代码主要是在主程序运行之前初始化系统硬件及软件的运行环境,它的主要功能包括以下几个方面:建立异常向量表硬件环境初始化软件环境初始化跳转到应用程序2.1.建立异常向量表异常向量表一般位于启动代码的开始部分,它是用户程序与启动代码之间以及启动代码的各部分之间联系的纽带。它由一个一个的跳转函数组成,它就像一个普通的散转函数,只不过散转的过程中有硬件机制参与,当系统发生异常时,ARM处理器会通过硬件机制强制将PC指针指向异常向量表中对应的异常跳转函数存储的地址,然后程序会跳转到相应的异常中断服务程序去执行。下面我们来逐步了解一下异常向量表。ARM有7种异常,它们分别是:复位异常,当开发板上电或复位时进入;未定义指令异常,当遇到无法识别的指令时进入;软中断异常,当发生软中断时进入;预取中止异常,发生指令预取错误时进入;数据中止异常,对数据访问不能完成时进入;IRQ异常,当发生IRQ中断时进入;FIQ异常,当发生FIQ中断时进入;除了这7种异常之外,异常向量表中还有一个保留位置,所以建立异常向量表需要开辟一块大小为8×4字节的空间,每个异常占据一个字(4个字节)的空间,这一个字的空间包含的是一个跳转指令,通过这条指令使PC指向相应异常处理函数的入口,具体的异常处理函数在别处实现。异常向量表中指令、存储地址等对照表如下表所示:地址指令异常名称进入时处理器模式ARM体系结构与编程参考资料V1.01英智科技,嵌入式培训专家30x00BHandlerReset复位异常管理模式0x04BHandlerUndef未定义指令异常未定义模式0x08BHandlerSWI软中断异常管理模式0x0cBHandlerPabort指令预取异常中止模式0x10BHandlerDabort数据中止异常中止模式0x14B.保留——0x18BHandlerIRQIRQ中断异常中断模式0x1cBHandlerFIQFIQ中断异常快中断模式ARM要求异常向量表必须存储在0地址处,这样当开发板上电或复位时,PC会指向0地址处,进而跳转到复位异常处理函数函数HandlerReset,这个函数负责完成系统的初始化工作,即硬件环境初始化、软件环境初始化、跳转至主函数;发生其他异常时ARM通过硬件机制将PC指向异常向量表对应的位置,进而跳转至相应的异常处理函数。2.2.硬件环境初始化硬件环境初始化是为建立一套基础的应用程序执行环境准备硬件环境,这个初始化过程包括:关闭看门狗,屏蔽FIQ和IRQ中断,初始化系统时钟(PLL),初始化存储系统以及一些必要的其他硬件初始化操作,当然,并不是所有硬件的初始化都要在这里完成,在系统启动过程中一般只初始化一些和应用程序执行环境的建立有密切关系的硬件,其他的硬件可以在应用程序启动后根据需要进行初始化,这样有利于将用汇编写的启动代码精减到最小,而更多的采用C/C++等高级语言来编写代码,增加代码的可读性和可维护性。关闭看门狗在系统启动过程中,没有启动喂狗的任务,不关闭看门狗有可能会导致在系统启动过程中由于看门狗超时导致系统被复位,因此,需要先关闭看门狗,待应用程序执行环境建立好后,再根据需要启动开门狗。屏蔽FIQ和IRQ中断在系统过程中,应用程序执行环境初始化完成前,中断的处理程序的环境也还没有建立好,这个时候如果发生中断将会导致不可预料的后果,因此,需要先将中断屏蔽掉,待应用程序执行环境建立好后,再根据需要开启中断初始化系统时钟(PLL)如果说处理器是整个系统的心脏,那么晶振就是整时系统的心脏,它负责向输送血液(时钟频率)给各个硬件部件,以驱动它们进行工作,系统中的每个硬件的运行都跟时钟频率有密切关系,只有先确定了时钟频率才能够对每个硬件进行正确的初始化。初始化存储系统硬件是驱干,软件是灵魂,存储系统是灵魂的依附,为了能够让应用程序正确的运行起关闭看门狗初始化存储系统设置系统堆栈RO/RW/ZI初始化MMU地址重新映射调用C入口函数配置系统时钟屏蔽FIQ和IRQ中断ARM体系结构与编程参考资料V1.01英智科技,嵌入式培训专家4来,系统启动后中,需要从ROM中加载程序,并在RAM中运行它,因此,只有对存储系统进行正确的初始化才能够让应用程序在系统中正确的执行。2.3.软件环境初始化硬件环境准备完成后,需要对应用程序的软件环境进行初始化工作,这些工作包括系统堆栈初始化,RO/RW/ZI初始化,必要的时候还要进行MMU的初始化工作,在这些初始化完成后,整个系统的应用程序执行环境初始化的工作就准备就绪,可以调用采用C/C++编写的应用程序的主函数,执行应用程序。系统堆栈初始化由于考虑到成本及处理器体积的大小,每一款处理器的寄存器都是相当有限的,但在系统运行过程中却有可能大量的临时数据需要被保存,这不可能全部存到寄存器中,而RAM容量大,成本也比较低,我们需要在RAM中开辟一块空间,专门用于保存这些临数据。每一种处理器模式都有其独享的一个堆栈空间。RO/RW/ZI初始化在程序运行中,我们会涉及到三种类型的数据,RO是代码和常量数据,这是只读的数据,RW具有初始化的变量数量,这些数据变量会被读取并被必写,ZI只是定义了变量,但并未对其进行初始化的,我们系统默认将其初始化为0x00,这此数据在系统运行过程中需要被搬移到相应的存储空间才能保障系统正常运行。MMU地址重映射MMU的主要作用是实现虚拟地址到实际物理地址的映射,即对处理器的地址进行重新映射,它的目的有两个:一是用于将代码从ROM中移到速度较高的RAM中运行时可以将0地址进行重新映射以保证软中断异常的正常执行。二是用于现代高级操作系统对进程地址空间的隔离保护,对每个进程采用不同的虚拟地址映射表,每个进程同一个虚拟地址指向不同的物理地址,减少进程间内存互相破坏的可能性。关于MMU的详细使用在后续会采用专门的章节进行介绍。2.4.跳转到应用程序在所有的准备工作都做好以后,启动代码的最后一步就是跳转到主函数,主函数我们在其他文件中用C语言实现的。从启动代码跳转到主程序有两种方法:1)使用如下指令跳转到自己编写的主函数BMain使用此指令的时候要注意:Main函数是我们自己编写的,为避免和编译器提供的主函数__main发生混淆,最好将其写为Main,而不要写成main。采用这种方法来跳转到主程序时,要自己编写代码来实现应用程序执行环境的初始化。2)使用如下指令跳转到编译器提供的主函数B__main__main是编译器提供的一个函数,它有两个作用,一个作用就是调用__Scatterload函ARM体系结构与编程参考资料V1.01英智科技,嵌入式培训专家5数,将RW和RO段从装载地址复制到运行地址,并完成ZI段的清零工作,这一功能就是上一点讲到的应用程序执行环境初始化,调用__main可以由编译器隐式的完成;另一个功能是库函数调用的初始化,它是通过调用_rt_entry函数来完成的,库函数初始化完成以后就会自动跳转到main函数执行。但是使用__main时,用户需要重新来实现_user_ininial_stackheap函数,这个函数的作用是初始化库函数的堆栈。由于已经自己编写代码实现了软件环境的初始化,所以不要使用第二种方式。3.系统启动流程3.1.关闭看门狗看门狗定时器控制寄存器WTCON的WTCON.5的位是其

1 / 25
下载文档,编辑使用

©2015-2020 m.777doc.com 三七文档.

备案号:鲁ICP备2024069028号-1 客服联系 QQ:2149211541

×
保存成功