嵌入式工程师去面试可能被问到的问题集锦

大家好,很高兴和各位一起分享我的文章,喜欢和支持我的工程师,一定记得给我点赞、收藏、分享。

加微信[xyzn3333]与作者沟通交流,免费获取更多单片机与嵌入式的海量电子资料。

Q:什么是ISR?

A:ISR 是指中断服务程序。 这些是存储在特定内存地址的函数,当发生某种类型的中断时会调用这些函数。 Cortex-M 处理器系列具有管理中断执行的 NVIC

Q:我们可以给ISP传递参数或从ISR返回一个值吗?为什么?

A:ISR 不返回任何内容并且不允许传递任何参数。 

当硬件或软件中断发生时会调用 ISR,它不会被任何代码调用,所以这就是没有参数传递到 ISR 的原因。因为它不会被任何代码调用,所以它不会有返回值。

Q:什么是 volatile 关键字?

A:volatile 关键字是一个类型限定符,可防止对象进行编译器优化。根据 C 标准,具有 volatile 限定类型的对象可能会以实现未知的方式进行修改或具有其他未知的副作用。您也可以说 volatile 限定对象的值可以随时更改,而无需代码采取任何操作。如果对象由 volatile 限定符限定,则每次程序访问该对象时,编译器都会从内存中重新加载该值,这意味着它可以防止将变量缓存到寄存器中。从内存中读取值是检查值不可预测变化的唯一方法。

Q:标准C语言和嵌入式C语言有什么区别?

A:C语言:是一种通用编程语言,广泛用于设计任何类型的基于桌面的应用程序。 它是一种用于开发操作系统的系统编程语言。 C 语言的主要特点包括对内存的低级访问、一组简单的关键字和干净的风格,这些特点使 C 语言适用于操作系统或编译器开发等系统编程。 本质上它采用原生平台开发方案,即它开发的应用程序是平台相关的,只能在单一平台上使用。嵌入式 C:是标准C的扩展,而不能说是标准C的一部分。嵌入式C语言用于开发基于微控制器的应用程序。 嵌入式C语言对标准C的扩展是I/O硬件寻址、定点算术运算、访问地址空间等。

Q:C 中的 const 和 volatile 限定符有什么区别?

A:const 关键字是编译器强制执行的,它表示程序无法更改对象的值,这意味着它使对象成为不可修改的类型。 让我们看一个例子,

const int a = 0;

如果我们尝试修改“a”的值,我们将得到编译器错误,因为“a”用 const 关键字限定,防止更改“a”(整数变量)的值。

volatile 会阻止任何编译器优化,并表示对象的值可以被程序控制之外的东西更改,因此编译器不会对对象做出任何假设。 看个例子,

    volatile int a;

    当编译器看到上面的声明时,它会避免对“a”做出任何假设,并在每次迭代中从分配给“a”的地址读取值。

    Q:C中的变量可以既是const又是volatile吗?

    A:是的,可以同时使用 const 和 volatile。

    将 volatile 和 const 关键字一起使用的一个重要用途是在访问 GPIO 寄存器时。在 GPIO被配置为输入的情况下,读取到的值将取决于外部因素(如开关或其他设备的输出信号)的改变。在这种情况下, volatile 发挥着重要作用,并确保编译器始终从 GPIO 地址读取值并避免做出任何优化。使用 volatile 关键字后,无论何时访问端口,您都会获得正确的值,但仍然存在另一个问题,因为指针不是 const 类型,当您的程序更改了指针的指向地址时,所获取的数值就是错误的,这样我们就必须创建一个带有 volatile 关键字的常量指针。

    定义的用法为:

    int volatile * const PortRegister;

    理解:

    Q:常用的使用volatile的场合?

    A:1、访问内存映射外设寄存器或硬件状态寄存器。

    #define COM_STATUS_BIT  0x00000006
    
    uint32_t const volatile * const pStatusReg = (uint32_t*)0x00020000;
    
    unit32_t GetRecvData()
    {
        unit32_t RecvData;
        
        //Code to receive data
        while (((*pStatusReg)  & COM_STATUS_BIT) == 0)
        {
            // Wait until flag does not set
            //Received data in RecvData
    
        }
        return RecvData;
    }

    2、在多个线程之间共享全局变量或缓冲区

    3、在中断例程或信号处理程序中访问全局变量

    volatile int giFlag = 0;
    
    ISR(void)
    {
        giFlag = 1;
    }
    
    int main(void)
    {
    
        while (!giFlag)
        {
            //do some work
        }
    
        return 0;
    }

    Q:什么是中断延迟?

    A:中断延迟是处理器响应中断请求所用的时钟周期数。 这个时钟周期数是在中断请求的发生和中断处理程序的第一条指令之间计数。

    Cortex-M 处理器的中断延迟非常低。 在下表中列出了 Cortex-M 处理器的中断延迟。

    Q:如何减少中断延迟?

    A:中断延迟取决于许多因素,我在下面的陈述中提到了一些因素。

    • 平台和中断控制器。
    • CPU 时钟速度。
    • 定时器频率
    • 缓存配置。
    • 应用程序。

    因此,通过正确选择平台和处理器,我们可以轻松减少中断延迟。 我们还可以通过缩短 ISR 并避免在 ISR 内调用函数来减少中断延迟。

    Q:在中断服务程序(ISR) 中调用printf() 是否安全?

    A:不建议在接ISR中调用printf()

    Q:可以在 ISR 中放置断点吗?

    A:可以设置断点,但是不建议这么做。

    Q:在ISR中可以调用任何函数吗?

    A:是的,但是不建议在中断中直接调用函数;建议在中断中先设置相关标志或执行数据准备,在主循环中进行数据处理。

    Q:什么是中断嵌套?

    A:在嵌套中断系统中,即使正在执行中断服务函数,也可以随时随地进行中断。 但是,只有最高优先级的 ISR 会立即执行。 优先级次高的 ISR 将在最高优先级的 ISR 完成后执行。

    嵌套中断系统的规则是:

    • 所有中断都必须被设定中断优先级。
    • 初始化后,任何中断都可以随时随地发生。
    • 如果低优先级 ISR 被高优先级中断中断,则执行高优先级 ISR。
    • 如果高优先级 ISR 被低优先级中断中断,则高优先级 ISR 继续执行。
    • 必须按时间顺序执行相同优先级的 ISR

    Q:ARM Cortex 中的NVIC是什么?

    A:Cortex-M 处理器系列中的嵌套向量中断控制器 (NVIC) 是具有极其灵活的中断优先级管理的中断控制器的一个示例。 它支持可编程优先级、自动嵌套中断支持以及对多个中断屏蔽的支持,同时仍然非常易于程序员使用。NVIC 的 Cortex-M3 和 Cortex-M4 处理器支持多达 240 个中断输入,具有 8 个多达 256 个可编程优先级。

    Q:可以更改 Cortex-M 处理器系列的中断优先级吗?

    A:可以。

    Q:什么是启动代码,在进入main函数前芯片都做了什么工作?

    A:芯片上电后,进入 main 函数之前调用的代码是启动代码,一般是用汇编语言编写的一小段代码。启动代码至少包括以下部分

    • 堆栈区的声明
    • 堆区的声明
    • 矢量表
    • 重置处理程序代码
    • 其他异常处理程序代码

    Q:如何访问内存的固定地址?

    A:

    //Memory address, you want to access
    #define RW_FLAG 0x1FFF7800
    
    //Pointer to access the Memory address
    volatile uint32_t *flagAddress = NULL;
    
    //variable to stored the read value
    uint32_t readData = 0;
    
    //Assign addres to the pointer
    flagAddress = (volatile uint32_t *)RW_FLAG;
    
    //Read value from memory
    * flagAddress = 12; // Write
    
    //Write value to the memory
    readData = * flagAddress;

    Q:什么是堆栈溢出?

    A:如果您的程序尝试访问超出可用堆栈内存的限制,则会发生堆栈溢出。换句话说,如果调用堆栈指针超出堆栈边界,则可以说发生堆栈溢出。如果发生堆栈溢出,程序可能会崩溃,或者可以说是堆栈溢出导致的分段错误。

    Q:I2C和SPI的区别是什么?

    A:在嵌入式系统中,I2C和SPI都扮演着重要的角色。这两种通信协议都是同步通信的例子,但仍然有一些重要的区别。I2C 和 SPI 通信协议之间的重要区别。

    • I2C 支持半双工,而 SPI 是全双工通信。
    • I2C 只需要两线进行通信,而 SPI 需要三线或四线进行通信(取决于要求)。
    • 与 SPI 通信相比,I2C 速度较慢。
    • I2C 比 SPI 消耗更多功率。
    • I2C 比 SPI 更不易受噪声影响。
    • 与 SPI 通信协议相比,I2C 的实现成本更低。
    • I2C 工作在线路和逻辑上,它有一个上拉电阻,而在 SPI 的情况下不需要上拉电阻。
    • 在 I2C 通信中,我们在每个字节后获得确认位,SPI 通信协议不需要。
    • I2C 确保从设备接收发送的数据,而 SPI 不验证数据是否正确接收。
    • I2C 支持多主机通信,而 SPI 不支持多主机通信。
    • I2C 和 SPI 之间的一大区别在于,I2C 支持同一总线上的多个设备,而无需任何额外的选择线(基于设备地址工作),而 SPI 需要额外的信号(从选择线)线来管理同一总线上的多个设备。
    • I2C 支持仲裁,而 SPI 不支持仲裁。
    • I2C 支持时钟延长,而 SPI 不支持时钟延长。
    • I2C 可以被一个未能释放通信总线的设备锁定。
    • 由于起始位和停止位,I2C 有一些额外的开销。
    • I2C 更适合长距离,而 SPI 更适合短距离。

    Q:RS232和RS485有什么区别?

    A:RS232 和 RS485 之间的一些重要区别

    声明:本内容为作者独立观点,不代表电子星球立场。未经允许不得转载。授权事宜与稿件投诉,请联系:editor@netbroad.com
    觉得内容不错的朋友,别忘了一键三连哦!
    赞 3
    收藏 4
    关注 49
    成为作者 赚取收益
    全部留言
    0/200
    成为第一个和作者交流的人吧