嵌入式系统设计

时间:2020-12-16 22:34:02

2012年下学期嵌入式系统设计课程大作业

1、叙述下列相关名词的含义

ARM、xscale、PXA255、RISC、体系结构

ARM:一种技术、一个公司的名称、一种处理器。

Xscale:Xscale是ARM体系结构的一种内核,基于ARMv5TE,由Intel公司开发,在架构扩展的基础上同时也保留了对于以往产品的向下兼容。

PXA255XScale的内核版本,采用ARMV5TE7级超流水线,32K数据缓存/32K指令缓存。

RISC:英文全称为:ReducedInstructionSetComputing,中文即精简指令集一种CPU的设计概念;与之相对的是CISC,即复杂指令集

体系结构:嵌入式系统硬件与软件的衔接;它确定嵌入式系统设计的部件、部件功能、部件间借口的设计,并集中于嵌入式系统的核心部分——处理器的运算与内存的存取。

 

2、画出嵌入式硬件系统组成的模块结构图

嵌入式系统设计 

3、叙述基于linux的嵌入式平台的搭建过程

答:Linux嵌入式平台的搭建符合嵌入式平台搭建的一般过程,但是具体到Linux嵌入式平台,又有些许不同,其搭建过程如下:

1)处理器以及硬件开发平台的选择

以处理器为主,结合考虑硬件平台的情况。处理器考虑的问题包括应用类型及I/O接口、主频和功耗、对不同类型存储器的支持、封装等;硬件平台的选择和设计包括内存和外围存储器、输入输出接口以及设备等几项主要内容。

2)操作系统的选择

由于已经选取了Linux操作系统,因此此处主要是内核版本的选取以及对内核功能的裁剪。

3)开发环境的选取

即开发工具的选取,主要是指开发软件的选取,比如常用的minicom。

4)开发实施

首先,Bootloader的烧制。目的是对硬件系统基本功能的支持,比如串口通信。其次,内核文件的制作。接下来,内核文件的拷贝。此时,可以通过串口或者网口实施传输,能够大幅度提高传输速度。最后,在主机使用开发软件,完成对硬件系统的开发工作。包括硬件驱动程序、上层的应用程序、系统的集成与调试等。

 

4、判断题

(×)1.嵌入式系统调试通常可以分为硬件级调试和在线仿真器调试。
(√)2.在ARM处理器中,快速中断(FIQ)的优先级高于外部中断(IRQ)。
(×)3.ROM能够永久或半永久地保存数据,ROM内的数据永远不会丢失。
(√)4.内建测试系统(BIST)是SoC片上系统的重要结构之一,JTAG测试接口是IC芯片测试方法的标准。
(×)5.VHDL的基本单元描述不包括库。
(×)6.嵌入式ARM架构的嵌入式处理器同时支持大端、小端(Big/Little-Endian)数据类型。
(×)7.嵌入式操作系统通常采用整体式内核或层次式内核的结构。
(×)8.ARM7TDMI中的T代表增强型乘法器。
(×)9.看门狗(Watch Dog)实际是一个简单的定时器,在固定时间内若正常清零,则自动复位处理器。
(√)10.ARM-CPU由多家不同制造商生产,芯片外部提供的总线是不一致的。
(√)11.Linux 内核稳定、功能强大并且可以裁减,因为非常适合嵌入式应用。
(√)12.Linux 内核的中断服务程序运行于与所有进程都无关的中断上下文中。
(√)13.Linux遵循POSIX标准,意味着绝大多数UNIX应用程序不需要任何改动就可以在Linux系统上编译且运行。
(×)14.Linux内核支持可以裁减的功能,因此它属于微内核架构。
(√)15.Linux在fork()时采用了写时拷贝(简称COW)技术,允许父进程和子进程同时共享相同的物理页面。
(√)16.任何一个Linux应用程序都需要调用exit()函数。
(×)17.当前的Linux调度算法非常高效,但是查找当前最高优先级的可运行程序时,开销会随着可运行程序的多少而变化。
(√)18.Linux的系统调用是作为C库的一部分提供的。
(×)19.为了对硬件做出迅速的响应并完成对时间严格的操作,中断处理下半部必须在关中断状态下执行。
(×)20.Linux的内存管理采用了分页的机制,因此即使是内核本身也全部是分页的。
(√)21.嵌入式系统由上到下主要分为3个层次:应用软件层,系统软件层,硬件层。
(×)22.嵌入式系统的软硬件是独立设计的。
(√)23.嵌入式系统设计需要建立交叉开发环境。
(√)24.通用系统程序开发不需要建立和使用交叉编译环境。
(√)25.对于C++代码,gcc命令只能编译其源文件,而不能自动和C++程序使用的库链接。
(√)26.嵌入式系统可以没有操作系统。
(√)27.JTAG测试允许多个器件通过JTAG接口串联在一起形成一个JTAG链,能实现对各个器件分别测试。
(×)28.GDB调试器只支持本地调试应用程序。
(√)29.KGDB程序是一个专门用于调试Linux内核的GDB调试桩。
(×)30.片上调试器是存在重叠RAM。

 

5、基于嵌入式的智能家居系统设计,重点在于完成智能家居控制平台的结构、功能和设计分析,画出相应的结构功能框图。

(1) 硬件总体设计框图

根据上文的功能需要,设计出由ARM为控制核心,单片机控制的家电控制模块和传感器报警模块,并且包含GSM通信模块的智能家居系统,硬件结构框图如下图所示。

                                                        嵌入式系统设计

(2) 控制核心选择

智能家居控制系统采用XScale作为开发平台,该平台基于Intel®高性能的XScale处理器,支持Windows CE和Linux等嵌入式操作系统,是针对教学和实验的多功能实验平台。XScale处理器的最高主频可达400MHz,且该处理器被加入了WirelessMXX技术,大大的提高了多媒体处理能力,而且加入了Intel SpeedStep动态电源管理技术,在保证CPU性能的前提下,最大限度的降低设备功耗。

XScale配备了触摸屏、以太网、USB、串口、CF/MMC、PCMCIA等接口。满足了智能家居系统控制中心的硬件要求

(3)家电控制板

家电控制板采用AT89C51为控制核心。扩展板的元件布局,其上有四盏LED分别模拟四种家电,三个按钮模拟三种传感器。其中四盏LED分别连接单片机的P1.0、P1.1、P1.2、P1.3;三个按钮分别连接P2.0、P2.1、P2.2。

(3.1)串行端口电路

家电控制板采用串口与XScale实验箱进行通信,其采用了经典的兼容RS-232标准的MAX232芯片作为串口的电平转换芯片。家电扩展板采用的是常用的DB9头作为串口接口, 其中2脚RxD为接收引脚,3脚TxD为发送引脚,GND为信号地引脚。一般情况下普通串口只接这几个引脚;特殊的串口,如蓝牙串口除接上述的三个脚之外,还接了DSR引脚和CTS引脚,是因为蓝牙串口的数据流输出采用这两个脚的信号控制;而其他引脚是跟MODEM相关的。在智能家居系统中,家电控制板接普通串口,GSM模块接蓝牙串口。

RS-232信号相对于信号地而言,在正负电平之间摆动。发送数据时,发送端输出的正电平在+5V到+15V之间,负电平在-5V和-15V之间。无数据传输时,线上为TTL电平。接收器典型的工作电平在+3V~+12V与-3V~-12V。由于发送电平和接收电平的差仅为2~3V左右,所以其共模抑制能力差,加上双绞线的分布电容,信号传输距离最大为15m,最高速率为20kb/s。

MAX232包含2个驱动器、2个接收器和一个电压发生器电路,提供TIA/EIA-232-F电平。该器件符合TIA/EIA-232-F标准,每一个接收器将TIA/EIA-232-F电平转换成5V TTL/CMOS电平。每一个发送器将TTL/CMOS电平转换成TIA/EIA-232-F电平。

(3.2)家电控制电路

家用电器控制的接口中K1~K4 为继电器,分别控制四路家电的闭合和断开,Q1~Q4 为继电器线圈电流驱动,电路由单片机的P1口进行控制,DD1~DD4 发光二极管用于显示某路控制电路的工作情况,主要为了调试电路而设置。

(3.3) 传感器接口电路

在传感器没有报警信号时,光电耦合芯片处于截止状态,与之相接的单片机端口为低电平;当传感器有报警,传感器输出高电平,此时光电耦合芯片导通,与之相接的单片机端口为高电平,由单片机对报警信号进行采集并做出相应处理。

(4) GSM通信模块

GSM通信部分采用西门子MC35GSM/GPRS无线模块作为通信工具。它支持EGSM900和GSM1800双频,支持数字、语音、短消息和传真,使用AT指令控制发送短消息。它采用9V直流电源供电,通过RS-232串行端口与XSBase270试验箱连接进行通信。

(5) 视频监控模块

视频采集模块采用使用中星微(Vimicro)公司的ZC0301P芯片的摄像头, ZC0301P芯片可支持USB 1.1接口,硬件最高支持VGA分辨率(640×480)。在VGA模式下可达到15帧/秒速率,在CIF(352×288)和 SIF(320×240)模式下可达到30帧/秒速率。它通过USB接口连接到XScale试验箱。

 

6、下面是linux下的一个简单的设备驱动程序,写出linux设备驱动常用的数据结构,同时阅读下面代码,请给出测试程序中的每条语句加以注释。

设备驱动程序Keypad.c的源代码:

#include <linux/module.h>

#include <linux/fs.h>

#include <linux/init.h>

#include <linux/poll.h>

#include <linux/types.h>

#include <linux/fs.h>

#include <linux/rtc.h>

#include <linux/delay.h>

#include <asm/hardware.h>

#include <asm/delay.h>

#include <asm/uaccess.h>

#define LEDnKEY_MAJOR   251

#define KEYPAD_NAME    "X-Hyper250 Keypad"

#define KEYPAD_VERSION "Version 0.1"

#define EXT_KEY_CS  EXT_PORT2

#define EXT_LED_CS  EXT_PORT3

#define LED_SHOW    10

/*EXT_KEY_CS 为向外部LED进行数值设定,它定义在其它头文件里*/

void led_off_on() /**/

{

    int i;

    EXT_LED_CS = 0xff;

   

    for(i =0 ; i<8;++i)

    {

        EXT_LED_CS = ~((1 << i)& 0xff);   

        udelay(30000);

    }

    EXT_LED_CS = 0xff;

}

 

int lednkey_open(struct inode *inode, struct file *filp)

{

    MOD_INC_USE_COUNT;

    return (0);          /* success */      

}

int lednkey_release(struct inode *inode, struct file *filp)

{

    led_off_on();

    MOD_DEC_USE_COUNT;

    return (0);

}

ssize_t lednkey_read(struct file *filp, char *Putbuf, size_t length,loff_t *f_pos)

{

    unsigned short BottonStatus;

   unsignedchar Bottontmp = 0;

    int i;

    BottonStatus = ( EXT_KEY_CS &0xff );

    for(i = 0 ; i < 8; ++i)

    {

        if( ((BottonStatus >>i) & 1) == 0 )

            Bottontmp = (i+1);

    }

    copy_to_user( Putbuf,&Bottontmp, length);

    return length;

}

 

ssize_t lednkey_write(struct file *filp, const char *Getbuf, size_tlength, loff_t *f_pos)

{

    int num;

    unsigned char UsrWantLed;

     

    copy_from_user(&UsrWantLed, Getbuf, length);

   

    num =  ( (UsrWantLed) & 0xff );

    EXT_LED_CS = ~(1 <<(num-1));

    return (0);

}

 

int lednkey_ioctl(struct inode *inode, struct file *filp, unsigned intcmd,unsigned long arg)

{

    switch(cmd)

    {

        case LED_SHOW:

            {

                if(arg)

                    led_off_on();

                break;

            }

    }

    return 0;

}

struct file_operations lednkey_fops = {

    open:       lednkey_open,

    read:       lednkey_read,

    write:      lednkey_write,

    ioctl:      lednkey_ioctl,

    release:    lednkey_release,

};

static int _init xhyper250_keypad_init(void)

 

{

    int result;

    result =register_chrdev(LEDnKEY_MAJOR, "lednkey", &lednkey_fops);

   

printf("%s %s initialized.\n",KEYPAD_NAME,KEYPAD_VERSION);

    led_off_on();

    return 0;

}

static void _exit xhyper250_keypad_exit(void)

    unregister_chrdev( LEDnKEY_MAJOR,"lednkey" );          

    led_off_on();

}

module_init(xhyper250_keypad_init);

module_exit(xhyper250_keypad_exit);

 

 

测试文件的源代码如下:

 

#include<stdio.h>

#include<stdlib.h>

#include<unistd.h>

#include<sys/types.h>

#include<sys/stat.h>

#include<fcntl.h>

 

#define LED_SHOW 10

int fd;//定义文件描述符

 

static char *dev_name = "/dev/keypad";//设备文件地址

 

int main(int argc, char **argv)

{

    int data = 0, pre_data;

 

    fd = open( dev_name , O_RDWR );//打开字符设备文件,返回该文件的描述符

 

    if( !(fd >=0) )

    {

        printf("%s file openfailed\n", dev_name );//如果打开失败,打印

        exit(-1);

    }

    printf("\nkeypad App : pressthe push button see show led - Exit Ctrl-C \n",dev_name);

 

    ioctl(fd,LED_SHOW,1);//利用ioctl来控制设备,命令是LED_SHOW

 

    while(1)   

    {

        do

        {

            pre_data = data;

            read( fd, (char *)&data, sizeof(data) );//从fd所代表的设备中读取sizeof(data)字节数的数据到data所指向的区域中。

            data = (data & 0xff);

        }while(data == 0);

 

        if( pre_data == 0)

        {

            printf("Write %dLED\n",data);

            write( fd, (const char*)&data, sizeof((const char )data) ); //将data所指向的区域写入sizeof(data)字节数的数据中到fd所代表的设备。

 

        }              

    }

 

    close( fd );//关闭文件

    return 0;

}