知识点记录持续更新2、ARM系列ARM7一般没有MMUARM9一般有ARM的A系列和R系列一般有MMU。需要有MMU才能跑Linux系统。一般ARM的M系列是跑RTOS系统。3、ELF文件Executable and Linkable Format可执行与可链接格式也算是一种程序文件相比binhexaxf等可执行文件这种文件包含信息更多、更复杂。addressline原理把elf文件通过objdump反汇编生成lst文件在lst文件中拿到输出信息。参数-e:指定需要转换地址的可执行文件名-a指定需要查询的地址-f显示函数名-i如果需要转换的地址是一个内联函数则还将打印返回第一个非内联函数的信息。不仅会显示内联函数的名称还会显示调用该内联函数的函数名。例如addr2line -e rtthread.elf -a -f 1806d33a 1806f884ELF文件除机器码外还有一些额外信息– 段的加载地址、运行地址– 符号表、重定位表等ELF文件运行需要OS环境和加载器(loader、ld-linux.so)Bin文件– 只包含机器码纯粹的程序文件即镜像文件– 类似的还有HEX文件BIN文件运行只需要将其加载到链接地址即可ELF和map文件的区别- **编译过程**在程序的编译和链接过程中ELF文件和map文件都是由链接器生成的。ELF文件是主要的输出文件包含了可执行的程序代码和数据而map文件则是辅助性的输出提供了程序的内存映射信息。- **信息共享**两者都包含了程序的符号信息例如变量和函数的地址这些信息对于调试和分析程序非常重要。- **文件格式**ELF文件是一种二进制文件格式用于存储可执行代码、对象代码、共享库以及它们的调试信息等数据。它是可执行与可链接格式Executable and Linkable Format的缩写通常用于嵌入式系统中的程序文件。- **可读性**与ELF文件不同map文件是一种文本文件它以人类可读的格式提供了程序的内存使用情况、变量和函数的地址等信息。它通常用于调试目的帮助开发者理解程序的内存布局。- **目的**ELF文件的主要目的是作为可执行文件它包含了程序的机器代码和数据对象。而map文件的主要目的是提供程序的内存映射信息帮助开发者进行调试和优化内存使用。- **内容**ELF文件包含了程序的完整二进制内容可能包含符号信息用于调试以及将机器代码与源代码相关联的元数据。MAP文件则主要包含代码和数据对象的位置和大小信息以及内存使用情况的摘要。addressline -e -f的原理**ELF文件结构解析**- **节头表作用**ELF文件中的节头表为文件中的各个节提供了必要的信息如节的大小、偏移量以及节的类型等。这些信息是定位特定数据或代码段的关键。- **符号表索引**ELF文件通过符号表来映射人类可读的函数和变量名称到它们的地址。符号表为程序中的每一个符号分配了一个唯一的索引这个索引被用于间接地址的解析。- **程序链接表**程序链接表在ELF文件中扮演着重要的角色它描述了程序在运行时候的内存布局。程序头表中的每一项都对应一个内存段包含了该段的地址、大小以及与其他段的关系等信息。**命令行工具的作用**- **解析ELF文件**addressline工具通过解析ELF文件的结构能够提取出文件中的符号、节头和程序头等信息。这些信息是进一步分析和处理地址映射的基础。- **符号地址映射**使用addressline工具时可以通过提供的符号名查找其在ELF文件中的位置。工具内部会解析符号表并将符号名映射到相应的地址。- **地址转换机制**addressline工具还能够解析程序链接表从而理解程序加载到内存时的地址转换机制。这对于动态链接的符号尤为重要因为其地址可能在程序加载时才确定。**指定选项的作用**- **-e选项**这个选项允许用户指定要查询的特定节。通过这种方式用户可以针对ELF文件中的任意部分进行地址查询而不仅限于默认的文本段或数据段。- **-f选项**这个选项用于指定输出的格式。用户可以根据需要选择不同的输出格式以便更好地分析和使用查询结果。- **组合使用**当-e和-f选项组合使用时它们可以提供更灵活的控制方式使用户能够以自定义的方式查看ELF文件中特定节的地址信息并以所需的格式呈现。**实际应用场景**- **故障诊断**在软件开发和故障诊断过程中开发者可能需要查看特定函数或数据的地址。addressline工具可以帮助快速定位问题所在的代码段。- **性能优化**性能优化时常需查看特定函数的地址和大小以分析其性能瓶颈。addressline工具提供的详细信息有助于性能调优。- **安全分析**在进行安全分析时了解程序的内存布局和函数地址是关键。addressline工具能够帮助安全研究人员快速获取这些信息。综上所述addressline -e -f的原理基于对ELF文件结构的深入理解通过解析文件中的节头表、符号表和程序链接表等信息实现对特定符号地址的查询和格式化输出。这种机制不仅对于程序的加载和执行分析至关重要也对于软件的开发、调试和安全分析等领域有着广泛的应用。4、串口通信一帧数据发送8个bit数据位每帧数据都有开始位和停止位。5、当使用fseek函数在文件中偏移100字节而文件长度不足100字节时fseek会将文件指针定位到文件末尾并返回成功状态。通过fseek和ftell组合可以获取文件大小。如果fseek的超过了文件大小会扩展文件。6、LittleFS采用日志结构来存储元数据这意味着它会在块中顺序写入数据并在必要时进行合并和压缩以减少存储空间的浪费。7、ARM寄存器### 特殊寄存器- **零寄存器**当用作目标寄存器时写操作被忽略读操作返回0。在很多指令中可以使用但不是全部- **栈指针SP**ARMv8体系结构中栈指针的选择与异常级别有关。每个异常级别都有自己的栈指针如SP_EL0、SP_EL1等。在AArch64状态下EL0只能访问SP_EL0而其他异常级别可以使用专用的64位栈指针或SP_EL0- **程序计数器PC**在ARMv8中PC寄存器不再作为直接访问的寄存器而是隐式地用于某些指令中如PC相对加载和地址生成。PC不能被指定为数据处理或加载指令的目的操作数- **异常链接寄存器ELR**保存异常返回地址- **程序状态保存寄存器SPSR**保存异常发生前的PSTATE值用于异常返回时恢复PSTATE的值### 系统控制寄存器系统控制寄存器SCTLR用于控制内存、配置系统能力以及提供处理器核状态信息。不同的异常级别可能拥有独立的SCTLR副本例如ACTLR_EL1、ACTLR_EL2和ACTLR_EL3### 影子寄存器Banked RegistersARM体系结构通过影子寄存器的设计允许在不同工作模式下重复使用相同的寄存器编码但对应不同的物理寄存器。例如Abort模式下的R13与用户模式下的R13不同尽管它们编码相同实际上却对应不同的物理寄存器### CPSR和SPSRCPSR当前程序状态寄存器可以在任何处理器模式下访问包含条件码标志、中断禁止位、当前处理器模式以及其他状态和控制信息。每种异常模式下都有一个对应的SPSR备份程序状态寄存器用于保存CPSR的状态以便在异常返回后恢复### 寄存器的用途- R0-R3通常用于子程序间传递参数或作为返回值。- R4-R11主要用于保存局部变量。- R12用作子程序间的临时寄存器scratch register也称为IP。- R13通常用作栈指针sp。- R14链接寄存器lr用于保存子程序和中断的返回地址。- R15程序计数器PC指向当前执行的指令8、在嵌入式系统中同步通信和异步通信是两种基本的数据传输方式它们各自具有不同的特性和应用场景。下面是这两种通信方式的优缺点### 同步通信Synchronous Communication比如IICSPIUSB**优点****高效率**由于数据传输是连续的没有额外的同步开销因此传输效率高。**高数据速率**适合高速数据传输因为可以在短时间内传输大量数据。**简单性**在发送和接收端使用相同的时钟简化了数据同步的复杂性。**缺点****时钟依赖性**需要发送和接收设备共享相同的时钟信号这可能限制了系统的灵活性。**时钟偏差**时钟信号的不稳定或偏差可能导致数据同步问题。**功耗**在某些情况下维持时钟信号可能需要较高的功耗。### 异步通信Asynchronous Communication比如串口通信**优点****灵活性**不需要共享时钟信号适用于不同速率的设备或长距离通信。**独立性**每个数据包都有起始位和停止位使得数据包可以独立传输。**容错性**由于数据包独立即使数据传输中断也可以重新同步。**缺点****效率较低**每个数据包都需要额外的起始位和停止位增加了数据传输的开销。**数据速率受限**由于需要处理每个数据包的同步位数据传输速率相对较低。**复杂性**发送和接收端需要更复杂的逻辑来处理数据包的同步。9、GPIO通用输入输出是一种常见的硬件接口用于嵌入式系统中的数字信号处理。GPIO端口可以配置为不同的模式以适应不同的应用需求。以下是一些常见的GPIO模式及其详解**输入模式Input Mode**- GPIO端口被配置为接收外部信号。- 可以进一步细分为上拉输入、下拉输入等。**输出模式Output Mode**- GPIO端口被配置为输出信号到外部设备。- 可以控制LED、继电器等设备的开关状态。**上拉输入模式Pull-Up Input Mode**- 当GPIO端口配置为输入模式时内部上拉电阻被激活将输入信号拉高到高电平。- 适用于外部设备通过下拉电阻将信号拉低的情况。**下拉输入模式Pull-Down Input Mode**- 类似于上拉输入但内部激活的是下拉电阻将输入信号拉低到低电平。- 适用于外部设备通过上拉电阻将信号拉高的情况。**开漏输出模式Open-Drain Output Mode**- GPIO端口可以输出低电平但高电平由外部上拉电阻决定。- 常用于多个设备共享同一信号线的情况如I2C通信。**开集输出模式Open-Collector Output Mode**- 类似于开漏输出但通常用于双极性晶体管而不是MOSFET。- 同样适用于多个设备共享信号线的情况。**模拟输入模式Analog Input Mode**- GPIO端口被配置为模拟信号输入可以读取模拟信号的电压值。- 通常需要ADC模拟数字转换器来转换模拟信号为数字信号。**特殊功能模式Alternate Function Mode**- GPIO端口可以配置为特定的特殊功能如PWM脉冲宽度调制、定时器输入/输出等。- 这通常需要根据微控制器的特定功能来设置。**中断模式Interrupt Mode**- GPIO端口可以配置为中断输入当外部信号变化时可以触发中断请求。- 适用于需要快速响应外部事件的应用。**三态逻辑模式Tri-State Logic Mode**- GPIO端口可以被配置为高阻态既不输出也不输入常用于总线通信。10、推挽模式Push-Pull Mode是一种常见的GPIO通用输入输出配置方式主要用于微控制器或数字逻辑电路中。在推挽模式下GPIO端口既可以作为输出也可以作为输入具有以下特点**双向驱动能力**- 推挽模式允许GPIO端口在输出时具有较强的驱动能力可以驱动外部负载。**输出状态清晰**- 在推挽模式下GPIO端口可以清晰地输出高电平或低电平信号没有中间状态。**无需外部上拉或下拉电阻**- 与开漏或开集模式不同推挽模式不需要外部上拉或下拉电阻来确定输出电平。**内部结构**- 推挽模式的GPIO端口内部通常包含两个互补的晶体管或MOSFET一个用于输出高电平另一个用于输出低电平。**应用场景**- 适用于需要直接驱动LED、继电器、小型电机等负载的场景。- 也适用于简单的数字信号传输如控制其他数字电路的输入。**功耗**- 在推挽模式下当GPIO端口输出高电平时内部的低电平输出晶体管关闭减少了功耗。- 同样当输出低电平时高电平输出晶体管关闭。**噪声抑制**- 由于推挽模式具有较好的驱动能力它可以减少信号线上的噪声和抖动。**冲突保护**- 在某些微控制器中推挽模式的GPIO端口可能具有内部保护机制以防止在输出和输入之间发生冲突。**配置方式**- 推挽模式通常可以通过编程配置设置GPIO端口的控制寄存器来实现。**与开漏模式的比较**- 与开漏模式相比推挽模式不需要外部上拉电阻来确定高电平因此在设计上更为简单。推挽模式是GPIO端口最基本和最常用的配置之一适用于大多数需要直接输出数字信号的场景。然而在设计时仍需考虑GPIO端口的最大输出电流和电压以确保不会超出其规格限制。11、编译优化是编译器在编译过程中对源代码进行的改进以提高程序的执行效率、减少资源消耗或缩短编译时间等。不同的编译优化等级对应不同的优化策略和强度。以下是一些常见的编译优化等级及其区别**-O0**无优化- 不进行任何优化编译速度最快生成的代码体积小但执行效率最低。- 适用于调试阶段便于分析程序行为和性能问题。**-O1**启用基本优化- 启用基本的优化措施如循环展开、公共子表达式消除等。- 优化程度适中编译速度和执行效率之间取得平衡。**-O2**优化速度- 进一步优化程序的执行速度可能包括更激进的优化措施。- 编译时间可能增加但生成的代码执行效率更高。**-O3**优化速度和空间- 在-O2的基础上进一步优化内存使用和执行速度。- 可能包括更激进的优化如内联函数、更深层次的循环优化等。**-Os**优化大小- 优化生成代码的体积适用于对存储空间有限制的环境。- 可能牺牲一些执行速度以减少代码大小。**-Ofast**- 启用更多的优化选项包括那些可能违反严格标准的优化。- 生成的代码可能执行更快但可能不符合某些语言标准。**-Og**- 优化的同时尽量保持调试信息的完整性便于调试优化后的程序。- 适用于需要优化但又需要保持调试信息的情况。**-flto**Link Time Optimization链接时优化- 在链接阶段进行优化可以跨编译单元进行优化。- 可以提高程序的执行效率但会增加编译和链接的时间。**-finline-functions**- 内联所有的函数包括递归函数。- 可以减少函数调用的开销但可能导致生成的代码体积增大。**-fno-omit-frame-pointer**- 保留帧指针便于调试但可能会略微影响性能。不同的编译优化等级会影响程序的性能、大小和调试的便利性。开发者应根据项目的具体需求选择合适的优化等级。例如开发阶段可能使用-O0或-Og以便于调试而在发布产品时使用-O2或-O3以提高性能。使用链接时优化LTO可以在不牺牲太多编译时间的情况下进一步提高性能。12、核间通信共享物理内存方式避免竞态的方式同一个核可以通过互斥锁自旋锁的方式防止同时访问不同的核可以通过硬件信号中断来同步或者硬件消息机制。内存屏障可以解决内存一致性问题。13、具体来说当IO口配置为低电平时IO口通过内部或外部的下拉电阻连接到地使得IO口输出低电平信号此时IO口不会向外部电路提供电流因此不会漏电。同样地当IO口配置为高电平时IO口通过内部或外部的上拉电阻连接到电源使得IO口输出高电平信号此时虽然IO口与电源相连但由于上拉电阻的存在电流被限制在很小的范围内因此也不会造成显著的漏电。相比之下浮空模式Floating Mode是容易漏电的一种模式。在浮空模式下IO口既不上拉也不下拉其电平状态完全由外部电路决定。由于外部电路可能受到各种干扰和噪声的影响因此IO口的电平状态可能会频繁变化导致电流在IO口与外部电路之间来回流动从而造成漏电。此外如果外部电路中存在高阻抗路径或漏电通道也可能导致IO口在浮空模式下漏电。14、malloc0官方解释可能返回NULL也有可能返回非NULL。返回的地址是不可存储的。常见的一般返回非NULL。15、编译构建工具嵌入式编译构建工具的选择非常多样它们各自具有不同的特点和优势。以下是一些常见的嵌入式编译构建工具及其区别1 Keil MDKKeil MDK 是一款集成开发环境IDE广泛用于ARM Cortex微控制器的开发。它提供了全面的开发工具包括编辑器、编译器、调试器和仿真器2 IAR Embedded WorkbenchIAR 是一款跨平台的IDE支持多种编程语言和多种仿真器及调试器。它以其优化编译器和丰富的库支持而闻名3 STM32CubeIDE这是STMicroelectronics提供的一款基于Eclipse的IDE专门用于STM32微控制器的开发。它集成了STM32CubeMX一个图形化配置工具用于快速生成STM32的初始化代码和配置文件4 LLVM/ClangLLVM是一个编译器基础设施项目提供了丰富的库用于构建编译器和工具链。Clang是LLVM项目的一部分作为前端处理C、C和Objective-C等语言的编译而LLVM作为后端进行代码优化和生成5 GCCGNU Compiler Collection是一个开源编译器套装支持多种编程语言和平台。它以广泛的社区支持和平台兼容性著称6 CMakeCMake是一个跨平台的自动化构建系统它使用配置文件来生成标准的构建文件如Makefile或IDE工程文件。CMake广泛用于项目中因为它可以简化编译过程并且可以很好地与多种编译器和构建工具集成7还有MinGW每种工具都有其特定的应用场景和优势。例如Keil和IAR提供了针对特定微控制器的优化和支持而LLVM/Clang和GCC则提供了更广泛的语言和平台支持。CMake作为一个构建系统可以与这些编译器配合使用简化构建过程。开发者可以根据项目需求、目标平台和个人偏好来选择最合适的工具。16、a和a--是被拆分成3条汇编指令1--从内存中读a的值保存在CPU的R0假设是R02--计算a的新值3--把a的新值写在内存中变量a的位置加载-计算-保存17、SPIIIC1SPI是全双工IIC是半双工SPI支持更高的传输速率2IIC是两线通常SPI四线3IIC支持多个主从机IIC也可以支持需要通过片选来操作支持的数量很有限。18、fatfs32有MBR区FAT表区数据区。BR区用于引导记录磁盘参数剩余容量簇大小等FAT表区记录数据区存储情况文件信息也可以通过遍历fat表区查询剩余容量信息。数据区存储文件数据以簇的方式管理19、gcc的目标文件的依赖的.h文件也要加上不然头文件的更改检测不到依然是最新的main.omain.c hello.h如果目标文件和gcc编译后的文件名不一样生成的文件名是gcc的但是makefile检查的是目标文件main如果文件有改动也检查不到20、malloc不能在中断中调用分配时间不确定会调用到互斥锁互斥锁基于任务调度器和优先级反转。有可能造成任务获取到了锁中断获取不到会卡死。21、printf数据一般放到缓冲区不建议中断使用执行时间较长。线程不安全一般是没有锁机制sprintf等接口是有锁机制线程安全中断调用可能输出发生错误。22、C语言中int a[10] {1};数组的第一个元素初始化为1如果是全局变量或者静态变量其余元素a[1] 到 a[9]则肯定是初始化为0如果是局部变量一般也会初始化为0也有少数编译器不会对后面9个元素做初始化。如果定义局部变量数组不初始化栈空间可能会是随机值。23、32位的CPU数据总线也是32位每次读取四个字节。因为读取效率的原因CPU一般都会四字节对齐。数据总线读取时地址一般都是4的倍数。如果全局变量定义的是1字节实际占用的内存大小可能是14字节。编译器可能会进行优化例如将多个小的全局变量打包到一个更大的内存块中以减少内存碎片和提高访问效率。24、文件打开1读模式在大多数情况下如果一个文件以读模式被打开且未被关闭再次以读模式打开该文件通常是允许的。每次打开都会获得一个新的文件描述符file descriptor这些描述符各自独立维护着各自的文件状态信息如文件偏移量。2写模式写模式通常是独占的这意味着如果一个文件以写模式被打开且未被关闭再次尝试以写模式或读写模式打开该文件可能会失败具体取决于操作系统的实现。然而在某些操作系统和配置下可能允许以追加模式append mode同时打开文件进行写入而不会相互干扰。3其中一个地方关闭close文件不影响其他地方的打开文件描述符都是独立的。25、ARM 架构的中断处理流程当中断请求IRQ发生时会首先停止当前任务执行中断ARM 架构的中断处理流程如下1硬件中断请求外设如网卡、定时器等向中断控制器如 GIC发送中断信号可能是高低电平或者下降沿等信号2中断控制器处理GIC 接收中断信号进行优先级仲裁并将中断信号路由到目标 CPU3CPU 响应中断CPU 收到中断信号后保存当前程序状态如 PC、PSTATE 等并将处理器状态切换到中断模式如 IRQ 模式4跳转到中断向量表CPU 根据中断向量表存储在 VBAR_EL1 指定的地址找到对应的中断处理入口地址5执行中断处理程序中断处理程序ISR开始执行通常由内核提供的通用中断处理框架如gic_handle_irq读取中断号并调用具体的设备驱动中断处理函数6中断处理完成中断处理程序执行完毕后通过 ERET 指令恢复中断前的状态继续执行被中断的任务示例网卡中断处理以下是一个典型的网卡中断处理流程1硬件触发网卡接收数据包后向 GIC 发送中断信号。2中断处理GIC 路由中断到 CPUCPU 跳转到中断处理程序执行网卡驱动的 ISR。3下半部处理ISR 读取网卡状态清除中断标志并触发 SoftIRQ 或 Tasklet。4数据传递SoftIRQ 或 Tasklet 处理数据包并通过 sk_buff 将数据传递到网络协议栈。5用户空间回调协议栈将数据包传递到用户空间应用层通过套接字接口接收数据26、在单CPU上多线程执行不存在运行时内存乱序访问但是可能存在缓存一致问题内存屏障是一种硬件指令用于确保特定的内存操作在执行时的顺序性和可见性。它用于防止编译器和处理器对内存访问指令进行重排序确保某些操作在内存屏障之前完成之后的操作不会被提前执行。volatile是C语言关键字用于告诉编译器被修饰的变量可能会被程序之外的其他因素如硬件、中断、其他线程等修改。因此编译器在优化时不能假设该变量的值不会改变必须每次直接从内存中读取或写入该变量。27、AMP与SMP的区别AMPAsymmetric Multi-Processing非对称多处理SMPSymmetric Multi-Processing对称多处理AMP的各处理器可能是不同的架构比如ARMRISC-V一般每个核有自己的操作系统。SMP一般是一个操作系统来调度。28、文件系统元数据元数据的组成• 文件属性包括文件名、大小、类型、创建时间、修改时间等基本信息。• 文件位置信息记录文件在存储设备上的物理位置如文件起始块号、块分布等。• 文件系统结构信息包括文件系统的超级块、inode表、块位图等关键数据结构。• 访问权限和所有权信息文件和目录的访问权限、所属用户和用户组等。• 其他相关信息如文件的扩展属性、安全标签等。29、adb forward实现TCP三次握手ADB协议在 USB 协议之上定义命令格式如OPEN、OKAY、WRTE模拟 Socket 通信。ADB 的三次握手并非严格遵循 TCP 的三次握手而是通过 ADB 协议命令的交换 实现连接的建立和同步。以下是具体步骤1. 客户端发起连接请求类似 SYN动作客户端通过 adb 命令如 adb shell向本地 adb server 发送连接请求。 协议交互客户端通过 USB 发送 OPEN 命令到设备端携带目标服务标识如 shell: 表示 Shell 服务。OPEN 命令包含本地生成的唯一连接 ID如 0000模拟 TCP 的初始序列号。 状态变化客户端进入等待确认状态。 2. 服务端响应确认类似 SYN-ACK 动作设备端 adbd 收到 OPEN 命令后验证服务可用性。协议交互若服务可用adbd 返回 OKAY 命令携带与客户端相同的连接 ID0000并分配设备端资源。若不可用返回 FAIL 命令终止连接。 状态变化服务端进入连接就绪状态。 3. 客户端最终确认类似 ACK 动作客户端收到 OKAY 后发送初始化数据如 Shell 命令。协议交互客户端通过 WRTE 命令发送首个数据包如 ls\n携带连接 ID 和数据载荷。服务端返回 OKAY 确认接收完成握手。 状态变化双方进入 ESTABLISHED 状态开始数据传输。30、中断上文直接处理硬件中断快速、不可睡眠。中断下文处理延迟任务根据机制不同可能运行在原子或进程上下文。关键选择需要极高性能且不睡眠 → Softirq/Tasklet。需要睡眠或复杂操作 → Workqueue中断上文硬件中断打断当前CPU执行状态保存CPU寄存器、程序计数器、堆栈指针等称为“中断现场”中断下文保存完上文后CPU跳转执行 ISR即中断处理程序• 中断上文hard-IRQ未完成时更高优先级的中断可以打断它• 中断下文soft-IRQ/tasklet/workqueue未完成时任何新的硬件中断都可以打断它。31、lfs和fat32的区别lfs文件系统换成fat32的主要原因是a、lfs遍历文件速度慢文件数量多开机首次遍历时间长。因为lfs是日志的方式保存数据需要遍历磁盘fat32有一个分区来记录文件信息不需要遍历磁盘b、需要U盘模式读写速率fat32和lfs的写速率大概200~300kb/s读速率大概是600kb/s主要受限于SPI的速率SPI的由主频分频决定非U盘模式文件系统读写是16M。U盘模式用的64M写速率有1M/S左右1单个文件最大分区/卷都是LFS更大fat32单个文件最大4G2LFS支持可读可写配置fat32不支持所有都是可读可写3LFS可靠性高支持掉电保护日志保障崩溃后可恢复fat32不支持掉电保护易导致数据损坏4LFS读写速率更快但是一般不用做U盘U盘选择fat32或者fat64exfat。32、由于物理组成与设计原因FLASH只能写0不能写1RAM可以写0也可以写1不需要先擦除来变成1。33、串口的软件流控和硬件流控硬件流控RTS/CTS1额外两根信号线RTSReady To Send、CTSClear To Send。2接收端 FIFO 快满 → 拉高 CTS → 发送端看见后 立刻停止发数据3FIFO 腾空 → 拉低 CTS → 继续发送。4响应快、不占用数据带宽但需要 多两根物理线 。软件流控XON/XOFF1不增加引线利用 数据通道本身 传控制字符2– XOFF0x13Ctrl-S10 进制 19 → “暂停”3– XON0x11Ctrl-Q10 进制 17 → “继续”4接收端 FIFO 达到警戒线 → 回送 XOFF腾空后回送 XON。5成本低但 不能用于二进制传输控制字符可能出现在用户数据里且会 额外消耗 1~2 字节带宽34、代码控制硬件流程1以读取内存为例假设CPU要读取内存地址0x1000处的数据1CPU发出地址CPU将地址0x1000二进制形式放到地址总线上2CPU发出读命令CPU通过控制总线另一组信号线发出读信号3内存响应所有内存和外设都看到了这个地址但只有地址0x1000对应的内存芯片会响应4内存提供数据该内存芯片将0x1000处的数据放到数据总线上5CPU接收数据CPU从数据总线上读取数据完成一次读取操作例如芯片设计时可能这样划分地址空间0x00000000-0x3FFFFFFF主内存1GB0x40000000-0x4001FFFFGPIO控制器0x40020000-0x4003FFFFUART控制器当CPU访问0x40010000时地址解码器会激活GPIO控制器的片选信号。2实际示例点亮LED的完整总线操作假设LED连接在GPIO端口A的第5脚GPIO端口A的数据寄存器地址是0x40020014我们要让该引脚输出高电平1C代码*(volatile uint32_t*)0x40020014 0x20; // 0x20 0010 0000第5位为1硬件执行过程1CPU执行存储指令将地址0x40020014放到地址总线上2CPU准备数据将数据0x00000020放到数据总线上3CPU发出写信号通过控制总线发出写命令4地址解码地址解码器识别0x4002xxxx范围属于GPIO5设备响应GPIO控制器被激活接收写命令6寄存器写入GPIO控制器将数据总线上的0x20写入其数据寄存器7物理输出GPIO硬件电路将第5个引脚的电压拉高到3.3V8LED点亮如果LED电路正确LED就会亮起35、自旋锁一般用多核多个CPU持有者会一直处于空转状态等其他cpu释放。一个好处就是等待释放的cpu不会引起上下文切换别的cpu释放后马上得到执行如果使用互斥锁的话引起上下文切换可能会等待时间较久才能得到执行。自旋锁不能嵌套使用不可重入
嵌入式知识点
知识点记录持续更新2、ARM系列ARM7一般没有MMUARM9一般有ARM的A系列和R系列一般有MMU。需要有MMU才能跑Linux系统。一般ARM的M系列是跑RTOS系统。3、ELF文件Executable and Linkable Format可执行与可链接格式也算是一种程序文件相比binhexaxf等可执行文件这种文件包含信息更多、更复杂。addressline原理把elf文件通过objdump反汇编生成lst文件在lst文件中拿到输出信息。参数-e:指定需要转换地址的可执行文件名-a指定需要查询的地址-f显示函数名-i如果需要转换的地址是一个内联函数则还将打印返回第一个非内联函数的信息。不仅会显示内联函数的名称还会显示调用该内联函数的函数名。例如addr2line -e rtthread.elf -a -f 1806d33a 1806f884ELF文件除机器码外还有一些额外信息– 段的加载地址、运行地址– 符号表、重定位表等ELF文件运行需要OS环境和加载器(loader、ld-linux.so)Bin文件– 只包含机器码纯粹的程序文件即镜像文件– 类似的还有HEX文件BIN文件运行只需要将其加载到链接地址即可ELF和map文件的区别- **编译过程**在程序的编译和链接过程中ELF文件和map文件都是由链接器生成的。ELF文件是主要的输出文件包含了可执行的程序代码和数据而map文件则是辅助性的输出提供了程序的内存映射信息。- **信息共享**两者都包含了程序的符号信息例如变量和函数的地址这些信息对于调试和分析程序非常重要。- **文件格式**ELF文件是一种二进制文件格式用于存储可执行代码、对象代码、共享库以及它们的调试信息等数据。它是可执行与可链接格式Executable and Linkable Format的缩写通常用于嵌入式系统中的程序文件。- **可读性**与ELF文件不同map文件是一种文本文件它以人类可读的格式提供了程序的内存使用情况、变量和函数的地址等信息。它通常用于调试目的帮助开发者理解程序的内存布局。- **目的**ELF文件的主要目的是作为可执行文件它包含了程序的机器代码和数据对象。而map文件的主要目的是提供程序的内存映射信息帮助开发者进行调试和优化内存使用。- **内容**ELF文件包含了程序的完整二进制内容可能包含符号信息用于调试以及将机器代码与源代码相关联的元数据。MAP文件则主要包含代码和数据对象的位置和大小信息以及内存使用情况的摘要。addressline -e -f的原理**ELF文件结构解析**- **节头表作用**ELF文件中的节头表为文件中的各个节提供了必要的信息如节的大小、偏移量以及节的类型等。这些信息是定位特定数据或代码段的关键。- **符号表索引**ELF文件通过符号表来映射人类可读的函数和变量名称到它们的地址。符号表为程序中的每一个符号分配了一个唯一的索引这个索引被用于间接地址的解析。- **程序链接表**程序链接表在ELF文件中扮演着重要的角色它描述了程序在运行时候的内存布局。程序头表中的每一项都对应一个内存段包含了该段的地址、大小以及与其他段的关系等信息。**命令行工具的作用**- **解析ELF文件**addressline工具通过解析ELF文件的结构能够提取出文件中的符号、节头和程序头等信息。这些信息是进一步分析和处理地址映射的基础。- **符号地址映射**使用addressline工具时可以通过提供的符号名查找其在ELF文件中的位置。工具内部会解析符号表并将符号名映射到相应的地址。- **地址转换机制**addressline工具还能够解析程序链接表从而理解程序加载到内存时的地址转换机制。这对于动态链接的符号尤为重要因为其地址可能在程序加载时才确定。**指定选项的作用**- **-e选项**这个选项允许用户指定要查询的特定节。通过这种方式用户可以针对ELF文件中的任意部分进行地址查询而不仅限于默认的文本段或数据段。- **-f选项**这个选项用于指定输出的格式。用户可以根据需要选择不同的输出格式以便更好地分析和使用查询结果。- **组合使用**当-e和-f选项组合使用时它们可以提供更灵活的控制方式使用户能够以自定义的方式查看ELF文件中特定节的地址信息并以所需的格式呈现。**实际应用场景**- **故障诊断**在软件开发和故障诊断过程中开发者可能需要查看特定函数或数据的地址。addressline工具可以帮助快速定位问题所在的代码段。- **性能优化**性能优化时常需查看特定函数的地址和大小以分析其性能瓶颈。addressline工具提供的详细信息有助于性能调优。- **安全分析**在进行安全分析时了解程序的内存布局和函数地址是关键。addressline工具能够帮助安全研究人员快速获取这些信息。综上所述addressline -e -f的原理基于对ELF文件结构的深入理解通过解析文件中的节头表、符号表和程序链接表等信息实现对特定符号地址的查询和格式化输出。这种机制不仅对于程序的加载和执行分析至关重要也对于软件的开发、调试和安全分析等领域有着广泛的应用。4、串口通信一帧数据发送8个bit数据位每帧数据都有开始位和停止位。5、当使用fseek函数在文件中偏移100字节而文件长度不足100字节时fseek会将文件指针定位到文件末尾并返回成功状态。通过fseek和ftell组合可以获取文件大小。如果fseek的超过了文件大小会扩展文件。6、LittleFS采用日志结构来存储元数据这意味着它会在块中顺序写入数据并在必要时进行合并和压缩以减少存储空间的浪费。7、ARM寄存器### 特殊寄存器- **零寄存器**当用作目标寄存器时写操作被忽略读操作返回0。在很多指令中可以使用但不是全部- **栈指针SP**ARMv8体系结构中栈指针的选择与异常级别有关。每个异常级别都有自己的栈指针如SP_EL0、SP_EL1等。在AArch64状态下EL0只能访问SP_EL0而其他异常级别可以使用专用的64位栈指针或SP_EL0- **程序计数器PC**在ARMv8中PC寄存器不再作为直接访问的寄存器而是隐式地用于某些指令中如PC相对加载和地址生成。PC不能被指定为数据处理或加载指令的目的操作数- **异常链接寄存器ELR**保存异常返回地址- **程序状态保存寄存器SPSR**保存异常发生前的PSTATE值用于异常返回时恢复PSTATE的值### 系统控制寄存器系统控制寄存器SCTLR用于控制内存、配置系统能力以及提供处理器核状态信息。不同的异常级别可能拥有独立的SCTLR副本例如ACTLR_EL1、ACTLR_EL2和ACTLR_EL3### 影子寄存器Banked RegistersARM体系结构通过影子寄存器的设计允许在不同工作模式下重复使用相同的寄存器编码但对应不同的物理寄存器。例如Abort模式下的R13与用户模式下的R13不同尽管它们编码相同实际上却对应不同的物理寄存器### CPSR和SPSRCPSR当前程序状态寄存器可以在任何处理器模式下访问包含条件码标志、中断禁止位、当前处理器模式以及其他状态和控制信息。每种异常模式下都有一个对应的SPSR备份程序状态寄存器用于保存CPSR的状态以便在异常返回后恢复### 寄存器的用途- R0-R3通常用于子程序间传递参数或作为返回值。- R4-R11主要用于保存局部变量。- R12用作子程序间的临时寄存器scratch register也称为IP。- R13通常用作栈指针sp。- R14链接寄存器lr用于保存子程序和中断的返回地址。- R15程序计数器PC指向当前执行的指令8、在嵌入式系统中同步通信和异步通信是两种基本的数据传输方式它们各自具有不同的特性和应用场景。下面是这两种通信方式的优缺点### 同步通信Synchronous Communication比如IICSPIUSB**优点****高效率**由于数据传输是连续的没有额外的同步开销因此传输效率高。**高数据速率**适合高速数据传输因为可以在短时间内传输大量数据。**简单性**在发送和接收端使用相同的时钟简化了数据同步的复杂性。**缺点****时钟依赖性**需要发送和接收设备共享相同的时钟信号这可能限制了系统的灵活性。**时钟偏差**时钟信号的不稳定或偏差可能导致数据同步问题。**功耗**在某些情况下维持时钟信号可能需要较高的功耗。### 异步通信Asynchronous Communication比如串口通信**优点****灵活性**不需要共享时钟信号适用于不同速率的设备或长距离通信。**独立性**每个数据包都有起始位和停止位使得数据包可以独立传输。**容错性**由于数据包独立即使数据传输中断也可以重新同步。**缺点****效率较低**每个数据包都需要额外的起始位和停止位增加了数据传输的开销。**数据速率受限**由于需要处理每个数据包的同步位数据传输速率相对较低。**复杂性**发送和接收端需要更复杂的逻辑来处理数据包的同步。9、GPIO通用输入输出是一种常见的硬件接口用于嵌入式系统中的数字信号处理。GPIO端口可以配置为不同的模式以适应不同的应用需求。以下是一些常见的GPIO模式及其详解**输入模式Input Mode**- GPIO端口被配置为接收外部信号。- 可以进一步细分为上拉输入、下拉输入等。**输出模式Output Mode**- GPIO端口被配置为输出信号到外部设备。- 可以控制LED、继电器等设备的开关状态。**上拉输入模式Pull-Up Input Mode**- 当GPIO端口配置为输入模式时内部上拉电阻被激活将输入信号拉高到高电平。- 适用于外部设备通过下拉电阻将信号拉低的情况。**下拉输入模式Pull-Down Input Mode**- 类似于上拉输入但内部激活的是下拉电阻将输入信号拉低到低电平。- 适用于外部设备通过上拉电阻将信号拉高的情况。**开漏输出模式Open-Drain Output Mode**- GPIO端口可以输出低电平但高电平由外部上拉电阻决定。- 常用于多个设备共享同一信号线的情况如I2C通信。**开集输出模式Open-Collector Output Mode**- 类似于开漏输出但通常用于双极性晶体管而不是MOSFET。- 同样适用于多个设备共享信号线的情况。**模拟输入模式Analog Input Mode**- GPIO端口被配置为模拟信号输入可以读取模拟信号的电压值。- 通常需要ADC模拟数字转换器来转换模拟信号为数字信号。**特殊功能模式Alternate Function Mode**- GPIO端口可以配置为特定的特殊功能如PWM脉冲宽度调制、定时器输入/输出等。- 这通常需要根据微控制器的特定功能来设置。**中断模式Interrupt Mode**- GPIO端口可以配置为中断输入当外部信号变化时可以触发中断请求。- 适用于需要快速响应外部事件的应用。**三态逻辑模式Tri-State Logic Mode**- GPIO端口可以被配置为高阻态既不输出也不输入常用于总线通信。10、推挽模式Push-Pull Mode是一种常见的GPIO通用输入输出配置方式主要用于微控制器或数字逻辑电路中。在推挽模式下GPIO端口既可以作为输出也可以作为输入具有以下特点**双向驱动能力**- 推挽模式允许GPIO端口在输出时具有较强的驱动能力可以驱动外部负载。**输出状态清晰**- 在推挽模式下GPIO端口可以清晰地输出高电平或低电平信号没有中间状态。**无需外部上拉或下拉电阻**- 与开漏或开集模式不同推挽模式不需要外部上拉或下拉电阻来确定输出电平。**内部结构**- 推挽模式的GPIO端口内部通常包含两个互补的晶体管或MOSFET一个用于输出高电平另一个用于输出低电平。**应用场景**- 适用于需要直接驱动LED、继电器、小型电机等负载的场景。- 也适用于简单的数字信号传输如控制其他数字电路的输入。**功耗**- 在推挽模式下当GPIO端口输出高电平时内部的低电平输出晶体管关闭减少了功耗。- 同样当输出低电平时高电平输出晶体管关闭。**噪声抑制**- 由于推挽模式具有较好的驱动能力它可以减少信号线上的噪声和抖动。**冲突保护**- 在某些微控制器中推挽模式的GPIO端口可能具有内部保护机制以防止在输出和输入之间发生冲突。**配置方式**- 推挽模式通常可以通过编程配置设置GPIO端口的控制寄存器来实现。**与开漏模式的比较**- 与开漏模式相比推挽模式不需要外部上拉电阻来确定高电平因此在设计上更为简单。推挽模式是GPIO端口最基本和最常用的配置之一适用于大多数需要直接输出数字信号的场景。然而在设计时仍需考虑GPIO端口的最大输出电流和电压以确保不会超出其规格限制。11、编译优化是编译器在编译过程中对源代码进行的改进以提高程序的执行效率、减少资源消耗或缩短编译时间等。不同的编译优化等级对应不同的优化策略和强度。以下是一些常见的编译优化等级及其区别**-O0**无优化- 不进行任何优化编译速度最快生成的代码体积小但执行效率最低。- 适用于调试阶段便于分析程序行为和性能问题。**-O1**启用基本优化- 启用基本的优化措施如循环展开、公共子表达式消除等。- 优化程度适中编译速度和执行效率之间取得平衡。**-O2**优化速度- 进一步优化程序的执行速度可能包括更激进的优化措施。- 编译时间可能增加但生成的代码执行效率更高。**-O3**优化速度和空间- 在-O2的基础上进一步优化内存使用和执行速度。- 可能包括更激进的优化如内联函数、更深层次的循环优化等。**-Os**优化大小- 优化生成代码的体积适用于对存储空间有限制的环境。- 可能牺牲一些执行速度以减少代码大小。**-Ofast**- 启用更多的优化选项包括那些可能违反严格标准的优化。- 生成的代码可能执行更快但可能不符合某些语言标准。**-Og**- 优化的同时尽量保持调试信息的完整性便于调试优化后的程序。- 适用于需要优化但又需要保持调试信息的情况。**-flto**Link Time Optimization链接时优化- 在链接阶段进行优化可以跨编译单元进行优化。- 可以提高程序的执行效率但会增加编译和链接的时间。**-finline-functions**- 内联所有的函数包括递归函数。- 可以减少函数调用的开销但可能导致生成的代码体积增大。**-fno-omit-frame-pointer**- 保留帧指针便于调试但可能会略微影响性能。不同的编译优化等级会影响程序的性能、大小和调试的便利性。开发者应根据项目的具体需求选择合适的优化等级。例如开发阶段可能使用-O0或-Og以便于调试而在发布产品时使用-O2或-O3以提高性能。使用链接时优化LTO可以在不牺牲太多编译时间的情况下进一步提高性能。12、核间通信共享物理内存方式避免竞态的方式同一个核可以通过互斥锁自旋锁的方式防止同时访问不同的核可以通过硬件信号中断来同步或者硬件消息机制。内存屏障可以解决内存一致性问题。13、具体来说当IO口配置为低电平时IO口通过内部或外部的下拉电阻连接到地使得IO口输出低电平信号此时IO口不会向外部电路提供电流因此不会漏电。同样地当IO口配置为高电平时IO口通过内部或外部的上拉电阻连接到电源使得IO口输出高电平信号此时虽然IO口与电源相连但由于上拉电阻的存在电流被限制在很小的范围内因此也不会造成显著的漏电。相比之下浮空模式Floating Mode是容易漏电的一种模式。在浮空模式下IO口既不上拉也不下拉其电平状态完全由外部电路决定。由于外部电路可能受到各种干扰和噪声的影响因此IO口的电平状态可能会频繁变化导致电流在IO口与外部电路之间来回流动从而造成漏电。此外如果外部电路中存在高阻抗路径或漏电通道也可能导致IO口在浮空模式下漏电。14、malloc0官方解释可能返回NULL也有可能返回非NULL。返回的地址是不可存储的。常见的一般返回非NULL。15、编译构建工具嵌入式编译构建工具的选择非常多样它们各自具有不同的特点和优势。以下是一些常见的嵌入式编译构建工具及其区别1 Keil MDKKeil MDK 是一款集成开发环境IDE广泛用于ARM Cortex微控制器的开发。它提供了全面的开发工具包括编辑器、编译器、调试器和仿真器2 IAR Embedded WorkbenchIAR 是一款跨平台的IDE支持多种编程语言和多种仿真器及调试器。它以其优化编译器和丰富的库支持而闻名3 STM32CubeIDE这是STMicroelectronics提供的一款基于Eclipse的IDE专门用于STM32微控制器的开发。它集成了STM32CubeMX一个图形化配置工具用于快速生成STM32的初始化代码和配置文件4 LLVM/ClangLLVM是一个编译器基础设施项目提供了丰富的库用于构建编译器和工具链。Clang是LLVM项目的一部分作为前端处理C、C和Objective-C等语言的编译而LLVM作为后端进行代码优化和生成5 GCCGNU Compiler Collection是一个开源编译器套装支持多种编程语言和平台。它以广泛的社区支持和平台兼容性著称6 CMakeCMake是一个跨平台的自动化构建系统它使用配置文件来生成标准的构建文件如Makefile或IDE工程文件。CMake广泛用于项目中因为它可以简化编译过程并且可以很好地与多种编译器和构建工具集成7还有MinGW每种工具都有其特定的应用场景和优势。例如Keil和IAR提供了针对特定微控制器的优化和支持而LLVM/Clang和GCC则提供了更广泛的语言和平台支持。CMake作为一个构建系统可以与这些编译器配合使用简化构建过程。开发者可以根据项目需求、目标平台和个人偏好来选择最合适的工具。16、a和a--是被拆分成3条汇编指令1--从内存中读a的值保存在CPU的R0假设是R02--计算a的新值3--把a的新值写在内存中变量a的位置加载-计算-保存17、SPIIIC1SPI是全双工IIC是半双工SPI支持更高的传输速率2IIC是两线通常SPI四线3IIC支持多个主从机IIC也可以支持需要通过片选来操作支持的数量很有限。18、fatfs32有MBR区FAT表区数据区。BR区用于引导记录磁盘参数剩余容量簇大小等FAT表区记录数据区存储情况文件信息也可以通过遍历fat表区查询剩余容量信息。数据区存储文件数据以簇的方式管理19、gcc的目标文件的依赖的.h文件也要加上不然头文件的更改检测不到依然是最新的main.omain.c hello.h如果目标文件和gcc编译后的文件名不一样生成的文件名是gcc的但是makefile检查的是目标文件main如果文件有改动也检查不到20、malloc不能在中断中调用分配时间不确定会调用到互斥锁互斥锁基于任务调度器和优先级反转。有可能造成任务获取到了锁中断获取不到会卡死。21、printf数据一般放到缓冲区不建议中断使用执行时间较长。线程不安全一般是没有锁机制sprintf等接口是有锁机制线程安全中断调用可能输出发生错误。22、C语言中int a[10] {1};数组的第一个元素初始化为1如果是全局变量或者静态变量其余元素a[1] 到 a[9]则肯定是初始化为0如果是局部变量一般也会初始化为0也有少数编译器不会对后面9个元素做初始化。如果定义局部变量数组不初始化栈空间可能会是随机值。23、32位的CPU数据总线也是32位每次读取四个字节。因为读取效率的原因CPU一般都会四字节对齐。数据总线读取时地址一般都是4的倍数。如果全局变量定义的是1字节实际占用的内存大小可能是14字节。编译器可能会进行优化例如将多个小的全局变量打包到一个更大的内存块中以减少内存碎片和提高访问效率。24、文件打开1读模式在大多数情况下如果一个文件以读模式被打开且未被关闭再次以读模式打开该文件通常是允许的。每次打开都会获得一个新的文件描述符file descriptor这些描述符各自独立维护着各自的文件状态信息如文件偏移量。2写模式写模式通常是独占的这意味着如果一个文件以写模式被打开且未被关闭再次尝试以写模式或读写模式打开该文件可能会失败具体取决于操作系统的实现。然而在某些操作系统和配置下可能允许以追加模式append mode同时打开文件进行写入而不会相互干扰。3其中一个地方关闭close文件不影响其他地方的打开文件描述符都是独立的。25、ARM 架构的中断处理流程当中断请求IRQ发生时会首先停止当前任务执行中断ARM 架构的中断处理流程如下1硬件中断请求外设如网卡、定时器等向中断控制器如 GIC发送中断信号可能是高低电平或者下降沿等信号2中断控制器处理GIC 接收中断信号进行优先级仲裁并将中断信号路由到目标 CPU3CPU 响应中断CPU 收到中断信号后保存当前程序状态如 PC、PSTATE 等并将处理器状态切换到中断模式如 IRQ 模式4跳转到中断向量表CPU 根据中断向量表存储在 VBAR_EL1 指定的地址找到对应的中断处理入口地址5执行中断处理程序中断处理程序ISR开始执行通常由内核提供的通用中断处理框架如gic_handle_irq读取中断号并调用具体的设备驱动中断处理函数6中断处理完成中断处理程序执行完毕后通过 ERET 指令恢复中断前的状态继续执行被中断的任务示例网卡中断处理以下是一个典型的网卡中断处理流程1硬件触发网卡接收数据包后向 GIC 发送中断信号。2中断处理GIC 路由中断到 CPUCPU 跳转到中断处理程序执行网卡驱动的 ISR。3下半部处理ISR 读取网卡状态清除中断标志并触发 SoftIRQ 或 Tasklet。4数据传递SoftIRQ 或 Tasklet 处理数据包并通过 sk_buff 将数据传递到网络协议栈。5用户空间回调协议栈将数据包传递到用户空间应用层通过套接字接口接收数据26、在单CPU上多线程执行不存在运行时内存乱序访问但是可能存在缓存一致问题内存屏障是一种硬件指令用于确保特定的内存操作在执行时的顺序性和可见性。它用于防止编译器和处理器对内存访问指令进行重排序确保某些操作在内存屏障之前完成之后的操作不会被提前执行。volatile是C语言关键字用于告诉编译器被修饰的变量可能会被程序之外的其他因素如硬件、中断、其他线程等修改。因此编译器在优化时不能假设该变量的值不会改变必须每次直接从内存中读取或写入该变量。27、AMP与SMP的区别AMPAsymmetric Multi-Processing非对称多处理SMPSymmetric Multi-Processing对称多处理AMP的各处理器可能是不同的架构比如ARMRISC-V一般每个核有自己的操作系统。SMP一般是一个操作系统来调度。28、文件系统元数据元数据的组成• 文件属性包括文件名、大小、类型、创建时间、修改时间等基本信息。• 文件位置信息记录文件在存储设备上的物理位置如文件起始块号、块分布等。• 文件系统结构信息包括文件系统的超级块、inode表、块位图等关键数据结构。• 访问权限和所有权信息文件和目录的访问权限、所属用户和用户组等。• 其他相关信息如文件的扩展属性、安全标签等。29、adb forward实现TCP三次握手ADB协议在 USB 协议之上定义命令格式如OPEN、OKAY、WRTE模拟 Socket 通信。ADB 的三次握手并非严格遵循 TCP 的三次握手而是通过 ADB 协议命令的交换 实现连接的建立和同步。以下是具体步骤1. 客户端发起连接请求类似 SYN动作客户端通过 adb 命令如 adb shell向本地 adb server 发送连接请求。 协议交互客户端通过 USB 发送 OPEN 命令到设备端携带目标服务标识如 shell: 表示 Shell 服务。OPEN 命令包含本地生成的唯一连接 ID如 0000模拟 TCP 的初始序列号。 状态变化客户端进入等待确认状态。 2. 服务端响应确认类似 SYN-ACK 动作设备端 adbd 收到 OPEN 命令后验证服务可用性。协议交互若服务可用adbd 返回 OKAY 命令携带与客户端相同的连接 ID0000并分配设备端资源。若不可用返回 FAIL 命令终止连接。 状态变化服务端进入连接就绪状态。 3. 客户端最终确认类似 ACK 动作客户端收到 OKAY 后发送初始化数据如 Shell 命令。协议交互客户端通过 WRTE 命令发送首个数据包如 ls\n携带连接 ID 和数据载荷。服务端返回 OKAY 确认接收完成握手。 状态变化双方进入 ESTABLISHED 状态开始数据传输。30、中断上文直接处理硬件中断快速、不可睡眠。中断下文处理延迟任务根据机制不同可能运行在原子或进程上下文。关键选择需要极高性能且不睡眠 → Softirq/Tasklet。需要睡眠或复杂操作 → Workqueue中断上文硬件中断打断当前CPU执行状态保存CPU寄存器、程序计数器、堆栈指针等称为“中断现场”中断下文保存完上文后CPU跳转执行 ISR即中断处理程序• 中断上文hard-IRQ未完成时更高优先级的中断可以打断它• 中断下文soft-IRQ/tasklet/workqueue未完成时任何新的硬件中断都可以打断它。31、lfs和fat32的区别lfs文件系统换成fat32的主要原因是a、lfs遍历文件速度慢文件数量多开机首次遍历时间长。因为lfs是日志的方式保存数据需要遍历磁盘fat32有一个分区来记录文件信息不需要遍历磁盘b、需要U盘模式读写速率fat32和lfs的写速率大概200~300kb/s读速率大概是600kb/s主要受限于SPI的速率SPI的由主频分频决定非U盘模式文件系统读写是16M。U盘模式用的64M写速率有1M/S左右1单个文件最大分区/卷都是LFS更大fat32单个文件最大4G2LFS支持可读可写配置fat32不支持所有都是可读可写3LFS可靠性高支持掉电保护日志保障崩溃后可恢复fat32不支持掉电保护易导致数据损坏4LFS读写速率更快但是一般不用做U盘U盘选择fat32或者fat64exfat。32、由于物理组成与设计原因FLASH只能写0不能写1RAM可以写0也可以写1不需要先擦除来变成1。33、串口的软件流控和硬件流控硬件流控RTS/CTS1额外两根信号线RTSReady To Send、CTSClear To Send。2接收端 FIFO 快满 → 拉高 CTS → 发送端看见后 立刻停止发数据3FIFO 腾空 → 拉低 CTS → 继续发送。4响应快、不占用数据带宽但需要 多两根物理线 。软件流控XON/XOFF1不增加引线利用 数据通道本身 传控制字符2– XOFF0x13Ctrl-S10 进制 19 → “暂停”3– XON0x11Ctrl-Q10 进制 17 → “继续”4接收端 FIFO 达到警戒线 → 回送 XOFF腾空后回送 XON。5成本低但 不能用于二进制传输控制字符可能出现在用户数据里且会 额外消耗 1~2 字节带宽34、代码控制硬件流程1以读取内存为例假设CPU要读取内存地址0x1000处的数据1CPU发出地址CPU将地址0x1000二进制形式放到地址总线上2CPU发出读命令CPU通过控制总线另一组信号线发出读信号3内存响应所有内存和外设都看到了这个地址但只有地址0x1000对应的内存芯片会响应4内存提供数据该内存芯片将0x1000处的数据放到数据总线上5CPU接收数据CPU从数据总线上读取数据完成一次读取操作例如芯片设计时可能这样划分地址空间0x00000000-0x3FFFFFFF主内存1GB0x40000000-0x4001FFFFGPIO控制器0x40020000-0x4003FFFFUART控制器当CPU访问0x40010000时地址解码器会激活GPIO控制器的片选信号。2实际示例点亮LED的完整总线操作假设LED连接在GPIO端口A的第5脚GPIO端口A的数据寄存器地址是0x40020014我们要让该引脚输出高电平1C代码*(volatile uint32_t*)0x40020014 0x20; // 0x20 0010 0000第5位为1硬件执行过程1CPU执行存储指令将地址0x40020014放到地址总线上2CPU准备数据将数据0x00000020放到数据总线上3CPU发出写信号通过控制总线发出写命令4地址解码地址解码器识别0x4002xxxx范围属于GPIO5设备响应GPIO控制器被激活接收写命令6寄存器写入GPIO控制器将数据总线上的0x20写入其数据寄存器7物理输出GPIO硬件电路将第5个引脚的电压拉高到3.3V8LED点亮如果LED电路正确LED就会亮起35、自旋锁一般用多核多个CPU持有者会一直处于空转状态等其他cpu释放。一个好处就是等待释放的cpu不会引起上下文切换别的cpu释放后马上得到执行如果使用互斥锁的话引起上下文切换可能会等待时间较久才能得到执行。自旋锁不能嵌套使用不可重入