嵌入式面试常问题32

指针函数和函数指针的区别:

指针函数本质上是一个函数,只不过该函数的返回值是一个指针类型。函数指针是一种指针,它指向一个函数。

指针的大小怎么算:

char* int* float*:在32位系统中为4位 64位系统是8位

size of 和strlen的区别;

sizeof:它是一个运算符,并非函数。其作用是在编译阶段计算数据类型或者变量所占用的字节数。

strlen:它是一个标准库函数,定义在 <string.h>(C 语言)或者 <cstring>(C++ 语言)头文件中。此函数用于计算以 '\0' 结尾的字符串的实际长度。

c语音中内存分配的方式有几种:

在 C 语言里,主要有三种内存分配方式,分别是静态内存分配、栈内存分配和堆内存分配,

struct 和union的区别:struct

结构体的每个成员都有自己独立的内存空间。结构体的总大小是其所有成员大小之和,同时可能会存在内存对齐的情况,以满足特定硬件平台的要求,提高内存访问效率。

例如,一个包含 int(通常 4 字节)和 char(1 字节)的结构体,考虑内存对齐后,其大小可能是 8 字节(假设按 4 字节对齐)。

union

共用体的所有成员共享同一块内存空间,这块内存空间的大小由共用体中最大的成员决定。

例如,一个包含 int(通常 4 字节)和 char(1 字节)的共用体,其大小为 4 字节,因为 int 是最大的成员。

- STM32启动过程详解?

STM32 的启动过程可以分为以下几个主要阶段:

硬件上电复位:当 STM32 芯片上电或者复位引脚被触发时,硬件会进行复位操作。复位后,CPU 会从特定的地址开始执行代码。

加载向量表:STM32 的向量表存储了一系列中断服务程序的入口地址,位于内存的起始地址(通常为 0x00000000)。复位后,CPU 会从向量表中读取栈顶地址和复位向量地址。栈顶地址用于初始化主栈指针(MSP),复位向量地址则是程序开始执行的起始地址。

初始化堆栈指针:CPU 将读取到的栈顶地址赋值给主栈指针(MSP),为后续的函数调用和局部变量分配内存做好准备。

跳转到复位处理函数:CPU 根据复位向量地址跳转到复位处理函数(通常是Reset_Handler)。在复位处理函数中,会进行一系列的初始化操作,如初始化全局变量、配置系统时钟、初始化外设等。

调用系统初始化函数:在复位处理函数中,通常会调用SystemInit函数来配置系统时钟。该函数会根据用户的配置,设置时钟源、分频系数等参数,使系统时钟达到所需的频率。

跳转到主函数:完成系统初始化后,程序会跳转到main函数,开始执行用户编写的应用程序代码。

- 中断优先级管理及嵌套?

中断优先级管理

STM32 的中断优先级分为抢占优先级和子优先级。

抢占优先级:具有高抢占优先级的中断可以打断正在执行的低抢占优先级的中断,实现中断嵌套。

子优先级:当两个中断的抢占优先级相同时,子优先级高的中断先执行。如果两个中断的抢占优先级和子优先级都相同,则按照中断向量表中的顺序依次执行。

中断嵌套

中断嵌套是指在一个中断服务程序执行过程中,更高优先级的中断可以打断当前的中断服务程序,转而执行更高优先级的中断服务程序。当更高优先级的中断处理完成后,再返回继续执行被打断的中断服务程序。

配置步骤

设置中断分组:通过NVIC_PriorityGroupConfig函数设置中断分组,确定抢占优先级和子优先级的位数。

配置中断优先级:对于每个中断源,使用NVIC_Init函数配置其抢占优先级和子优先级。

- DMA工作原理及应用场景?

工作原理

DMA(Direct Memory Access,直接内存访问)是一种无需 CPU 干预,直接在内存和外设之间进行数据传输的技术。其工作原理如下:

初始化:CPU 配置 DMA 控制器,设置源地址、目标地址、数据长度、传输方向等参数。

请求触发:当外设(如串口、ADC 等)有数据需要传输时,会向 DMA 控制器发送请求信号。

数据传输:DMA 控制器接收到请求信号后,接管总线控制权,直接在内存和外设之间进行数据传输,无需 CPU 干预。

传输完成:当数据传输完成后,DMA 控制器会向 CPU 发送中断信号,通知 CPU 数据传输已经完成。

应用场景

高速数据传输:如音频、视频数据的传输,使用 DMA 可以提高数据z传输效率,减轻 CPU 的负担。

大批量数据搬运:在需要将大量数据从一个内存区域复制到另一个内存区域时,使用 DMA 可以节省 CPU 时间。

外设与内存的数据交互:如 ADC 采集数据、SPI 发送数据等,使用 DMA 可以实现数据的自动传输,提高系统的实时性。

- 定时器的工作模式及配置?

工作模式

STM32 的定时器有多种工作模式,常见的有以下几种:

定时模式:定时器按照设定的时间间隔产生中断,用于实现定时功能。

输入捕获模式:用于测量外部信号的脉冲宽度或频率。定时器可以捕获外部信号的上升沿或下降沿,并记录相应的计数值。

输出比较模式:用于产生特定频率和占空比的 PWM 信号。定时器可以将计数值与比较值进行比较,当计数值等于比较值时,输出引脚的电平会发生变化。

编码器模式:用于测量旋转编码器的位置和速度。定时器可以根据编码器的输出信号,自动更新计数值。

配置步骤

以定时模式为例,配置步骤如下:

使能定时器时钟:使用RCC_APBxPeriphClockCmd函数使能相应的定时器时钟。

初始化定时器:使用TIM_TimeBaseInit函数初始化定时器的基本参数,如预分频系数、自动重装载值等。

配置中断:如果需要使用定时器中断,需要使用NVIC_Init函数配置中断优先级,并使用TIM_ITConfig函数使能定时器中断。

启动定时器:使用TIM_Cmd函数启动定时器

- I2C、SPI、UART的区别及应用场景?

电气特性

I2C(Inter - Integrated Circuit):是一种两线式串行总线,使用 SDA(串行数据线)和 SCL(串行时钟线)两根线进行通信,采用开漏输出,需要外接上拉电阻。

SPI(Serial Peripheral Interface):通常使用四根线,分别是 SCK(时钟线)、MOSI(主出从入)、MISO(主入从出)和 SS(片选线),采用推挽输出。

UART(Universal Asynchronous Receiver - Transmitter):一般使用两根线,TXD(发送端)和 RXD(接收端),用于异步串行通信。

通信方式

I2C:是同步、半双工通信,通过主从模式进行数据传输,每个从设备有唯一的地址。

SPI:是同步、全双工通信,主设备通过片选线选择要通信的从设备。

UART:是异步通信,不需要时钟线,通过约定的波特率进行数据传输。

传输速率

I2C:标准模式下传输速率为 100kbps,快速模式可达 400kbps。

SPI:传输速率较高,可达几十 Mbps 甚至更高。

UART:传输速率范围较广,从几百 bps 到几 Mbps 不等。

通信距离

I2C:通信距离较短,一般在几米以内。

SPI:通信距离也较短,通常在电路板级通信。

UART:在合适的电平转换和抗干扰措施下,通信距离可以达到几十米甚至更远。

应用场景

I2C:常用于连接低速外设,如 EEPROM、传感器(温度传感器、加速度计等)、实时时钟芯片等。

SPI:适用于高速数据传输的场景,如 SD 卡、LCD 显示屏、高速 ADC/DAC 等。

UART:常用于设备之间的异步通信,如计算机与单片机、调制解调器与计算机等。

- CAN总线的特点及应用?

多主通信:CAN 总线是一种多主总线,总线上的任何节点都可以在任意时刻主动向其他节点发送数据。

错误检测和处理:CAN 总线具有完善的错误检测机制,包括位错误、填充错误、CRC 错误等,当检测到错误时,节点会自动重发数据。

高可靠性:采用差分信号传输,抗干扰能力强,适合在恶劣的工业环境中使用。

优先级仲裁:当多个节点同时发送数据时,CAN 总线通过标识符进行优先级仲裁,高优先级的节点优先发送数据。

传输速率:传输速率最高可达 1Mbps,通信距离与传输速率成反比。

应用

汽车电子:CAN 总线在汽车中广泛应用,用于连接发动机控制单元、车身控制模块、仪表盘等,实现各模块之间的通信和数据共享。

工业自动化:在工业控制系统中,CAN 总线用于连接各种传感器、执行器和控制器,实现设备之间的通信和协调控制。

智能建筑:用于智能家居系统中,连接各种智能设备,如灯光控制器、门窗传感器等,实现设备的集中控制和管理。

- Modbus协议的帧格式及异常处理?

帧格式

RTU 模式

起始位:至少 3.5 个字符时间的空闲时间。

地址码:1 个字节,用于标识从站地址。

功能码:1 个字节,指示要执行的操作,如读线圈、读寄存器等。

数据域:可变长度,包含具体的数据信息。

CRC 校验:2 个字节,用于检测数据传输过程中的错误。

结束位:至少 3.5 个字符时间的空闲时间。

ASCII 模式

起始符:“:”(冒号)。

地址码:2 个 ASCII 字符,用于标识从站地址。

功能码:2 个 ASCII 字符,指示要执行的操作。

数据域:可变长度,包含具体的数据信息,以 ASCII 字符表示。

LRC 校验:2 个 ASCII 字符,用于检测数据传输过程中的错误。

结束符:“CR LF”(回车换行)。

异常处理

当主站发送的请求出现错误或从站无法执行请求时,从站会返回异常响应。异常响应的帧格式与正常响应类似,但功能码的最高位会置 1,同时在数据域中包含一个异常码,指示异常的类型,常见的异常码有非法功能码、非法数据地址、非法数据值等。主站收到异常响应后,会根据异常码进行相应的处理,如重新发送请求、提示用户等。

- TCP/IP协议栈在嵌入式系统中的实现?

TCP/IP 协议栈在嵌入式系统中的实现

实现方式

完整协议栈实现:使用专门的 TCP/IP 协议栈软件,如 uIP、LwIP 等,这些协议栈提供了完整的 TCP/IP 协议功能,包括 ARP、IP、TCP、UDP 等。开发者可以根据需求进行配置和裁剪,将其移植到嵌入式系统中。

硬件实现:使用带有 TCP/IP 协议栈硬件支持的网络芯片,如 W5500、ENC28J60 等,这些芯片内部集成了 TCP/IP 协议栈,开发者只需要通过 SPI 或其他接口与芯片进行通信,即可实现网络通信功能。

实现步骤

选择合适的协议栈或硬件:根据嵌入式系统的资源和需求,选择合适的 TCP/IP 协议栈软件或网络芯片。

移植协议栈:如果使用软件协议栈,需要将协议栈移植到嵌入式系统中,包括配置编译环境、修改底层驱动代码等。

配置网络参数:设置嵌入式系统的 IP 地址、子网掩码、网关等网络参数。

编写应用程序:根据实际需求,编写基于 TCP/IP 协议的应用程序,如 HTTP 服务器、TCP 客户端等。

i2c简易时序图

  启动信号:

  SCL为高电平的时候,SDA由高电平向低电平跳变。结束信号:SCL为高电平的时候,SDA由低电平向高电平跳变。

  应答信号:

  I2C总线上的所有数据都是以8位字节传送的,发送器每发送一个字节,就在时钟脉冲9期间释放数据线,由接收器反馈一个应答信号。应答信号为低电平时,规定为有效应答位(ACK简称应答位),表示接收器已经成功地接收了该字节;应答信号为高电平时,规定为非应答位(NACK),一般表示接收器接收该字节没有成功,对于反馈有效应答位ACK的要求是,接收器在第9个时钟脉冲之前的低电平期间将SDA线拉低,并且确保在该时钟的高电平期间为稳定的低电平。如果接收器是主控器,则在它收到最后一个字节后,发送一个NACK信号,以通知被控发送器结束数据发送,并释放SDA线,以便主控接收器发送一个停止信号P。

  写时序:

  开始信号:主机+从设备地址+写命令,从机应答,应答成功,表示有这个设备,然后主机+设备内部寄存器地址,此时不用再加写命令控制字,从机应答,应答成功,表示设备内有这个地址,主机写入数据,从机应答,是否继续发送,不发送的话,发送停止信号P。

  读时序:

  要想读设备,首先要知道将要所读取设备的地址告诉从设备,从设备才能将数据放到(发送)SDA上使主设备读取,从设备将数据放入SDA上的过程,由硬件主动完成,不用人为的写入。所以首先先写入从机地址,然后+写控制命令,从机应答,应答成功,表示有这个设备,然后写入内部寄存器地址,此时不用再加写命令控制字,从机应答,应答成功,表示设备内有这个地址。然后主机继续发出:写入从机地址,然后+读命令,从机应答,应答成功,此时便可以读取数据了,从设备已经将数据放入到SDA上了。地址跟设备已经验证了,不用再进行验证。

SPI通信的四种模式:

SPI通信有4种不同的操作模式,不同的从设备可能在出厂是就是配置为某种模式,这是不能改变的;但我们的通信双方必须是工作在同一模式下,所以我们可以对我们的主设备的SPI模式进行配置,通过CPOL(时钟极性)和CPHA(时钟相位)来

控制我们主设备的通信模式,具体如下:

时钟极性(CPOL)定义了时钟空闲状态电平:

  • CPOL=0,表示当SCLK=0时处于空闲态,所以有效状态就是SCLK处于高电平时
  • CPOL=1,表示当SCLK=1时处于空闲态,所以有效状态就是SCLK处于低电平时

时钟相位(CPHA)定义数据的采集时间。

  • CPHA=0,在时钟的第一个跳变沿(上升沿或下降沿)进行数据采样。,在第2个边沿发送数据
  • CPHA=1,在时钟的第二个跳变沿(上升沿或下降沿)进行数据采样。,在第1个边沿发送数据

SPI的三种模式

SPI工作在3中模式下,分别是运行、等待和停止。

运行模式(Run Mode)

这是基本操作模式

等待模式(Wait Mode)

SPI工作在等待模式是一种可配置的低功耗模式,可以通过SPICR2寄存器的SPISWAI位进行控制。在等待模式下,如果SPISWAI位清0,SPI操作类似于运行模式。如果SPISWAI位置1,SPI进入低功耗状态,并且SPI时钟将关闭。如果SPI配置为主机,所有的传输将停止,但是会在CPU进入运行模式后重新开始。如果SPI配置为从机,会继续接收和传输一个字节,这样就保证从机与主机同步。

停止模式(Stop Mode)

为了降低功耗,SPI在停止模式是不活跃的。如果SPI配置为主机,正在进行的传输会停止,但是在CPU进入运行模式后会重新开始。如果SPI配置为从机,会继续接受和发送一个字节,这样就保证了从机与主机同步。

嵌入式系统的启动流程设计?

嵌入式系统的启动流程通常包含以下几个主要阶段:

硬件上电复位

当系统上电或者复位引脚被触发时,硬件进行复位操作。此时处理器的寄存器被初始化为默认值,程序计数器(PC)被设置为复位向量地址,系统从该地址开始执行代码。

加载向量表

向量表是一系列中断服务程序入口地址的集合,存于内存起始地址。复位后,处理器从向量表读取栈顶地址和复位向量地址。栈顶地址用于初始化主栈指针(MSP),复位向量地址则是程序起始执行地址。

初始化硬件

时钟系统:配置系统时钟源、分频系数等,使系统时钟达到所需频率,为后续硬件和软件运行提供稳定时钟信号。

存储器:初始化片内和片外存储器,如 SRAM、Flash 等,确保存储器正常工作,为程序和数据存储提供支持。

外设:初始化各类外设,如 GPIO、UART、SPI 等,根据需求设置外设工作模式和参数。

初始化软件环境

全局变量:对全局变量进行初始化,确保程序运行时全局变量有正确的初始值。

堆栈:进一步配置堆栈,保证函数调用和局部变量分配内存正常。

中断系统:使能中断控制器,配置中断优先级和中断向量表,为中断处理做好准备。

跳转到应用程序

完成硬件和软件环境初始化后,程序跳转到主函数(main),开始执行用户编写的应用程序代码。

低功耗设计的关键技术?

电源管理技术

动态电压频率调整(DVFS):根据系统负载动态调整处理器的电压和频率。在低负载时降低电压和频率,减少功耗;在高负载时提高电压和频率,保证系统性能。

电源模式切换:嵌入式系统通常具有多种电源模式,如运行模式、睡眠模式、待机模式等。在系统空闲时,切换到低功耗模式,关闭不必要的模块和外设,降低功耗。

外设管理技术

外设时钟控制:只在需要使用外设时开启其时钟,使用完毕后及时关闭,减少外设功耗。

外设低功耗模式:许多外设具有低功耗模式,如 UART 的休眠模式、SPI 的停止模式等。在不使用外设时,将其设置为低功耗模式。

软件优化技术

算法优化:采用高效算法,减少处理器运算量和执行时间,降低功耗。

任务调度优化:合理安排任务执行顺序和时间,避免处理器空转,提高系统效率,降低功耗。

看门狗的工作原理及应用?

工作原理

看门狗(Watchdog)是一种定时器电路,其工作原理如下:

系统启动时,看门狗定时器开始计时。

在程序正常运行过程中,需要在规定时间内对看门狗定时器进行清零操作,即 “喂狗”。

如果程序由于某种原因(如硬件故障、软件死循环等)无法在规定时间内 “喂狗”,看门狗定时器就会溢出,产生复位信号,使系统复位。

应用

防止程序跑飞:当程序受到干扰出现死循环或跑飞时,看门狗能够及时复位系统,使程序重新开始运行,提高系统的稳定性。

监控系统运行状态:可以通过设置不同的 “喂狗” 周期,监控系统的运行状态。如果系统在规定时间内无法完成任务并 “喂狗”,则说明系统可能出现故障。

嵌入式系统的可靠性设计?

硬件可靠性设计

冗余设计:采用冗余电源、冗余处理器等,当一个部件出现故障时,另一个部件能够继续工作,保证系统正常运行。

电磁兼容性(EMC)设计:合理布局电路板,采用屏蔽、滤波等措施,减少电磁干扰,提高系统的抗干扰能力。

热设计:合理设计散热结构,确保系统在高温环境下正常工作,避免因过热导致器件损坏。

软件可靠性设计

容错设计:采用容错算法和数据校验机制,如 CRC 校验、奇偶校验等,检测和纠正数据传输和处理过程中的错误。

异常处理:在程序中添加异常处理代码,对可能出现的异常情况(如除数为零、数组越界等)进行处理,避免程序崩溃。

软件冗余设计:采用软件冗余技术,如 N 版本编程、恢复块等,提高软件的可靠性。

系统可靠性设计

故障诊断和恢复:在系统中添加故障诊断模块,实时监测系统的运行状态,当检测到故障时,能够自动进行恢复操作。

备份和恢复机制:定期对系统数据进行备份,当系统出现故障时,能够快速恢复数据,减少损失。

#嵌入式面试#
全部评论

相关推荐

评论
2
3
分享

创作者周榜

更多
牛客网
牛客企业服务