处理ARM芯片的保留寄存器位

我正在使用ARM Cortex M3的寄存器。 在文档中,一些位可能是“保留的”。 在寄存器上写入时,我不清楚如何处理这些保留位。

这些保留位是否可写? 我不小心不接触它们吗? 如果我触摸它们会发生什么不好的事吗?

对于如何处理保留位,这是一个经典的嵌入式世界问题! 首先,你不应该随意写入它,以免你的代码变得无法移植。 当架构在未来为保留位分配新含义时会发生什么? 你的代码会破裂。 因此,处理具有保留位的寄存器时最好的咒语是Read-Modify-Write 。 即读取寄存器内容, 仅修改所需的位 ,然后回写该值,使保留位不受影响(未触及,并不意味着我们不写入它们,但从某种意义上说,我们写的是之前的那些)

例如,假设有一个寄存器,其中只有LSBit具有含义而所有其他都被保留。 我会这样做的

 ldr r0,=memoryAddress ldr r1,[r0] orr r1,r1,#1 str r1,[r0] 

如果文档中没有其他线索,请写入零。 你不能避免写入在32位寄存器中传播的一些保留位。

Read-Modify-Write应该在大多数情况下工作, 但是有些情况下保留位在读取时未定义,但必须使用特定值写入。 请参阅LPC2000小组的这篇文章 (整个post也很有趣)。 因此,请务必仔细检查文档,以及任何可用的勘误表。 如有疑问或文档不清楚,请不要犹豫写信给制造商。

理想情况下,您应该阅读 – 修改 – 写入,不能保证成功,当您更换为具有不同位的较新芯片时,无论如何都要更改代码。 我见过供应商,当他们加速芯片并且必须触及代码时,将零写入保留位失败。 所以没有保证。 最大的线索是,如果在供应商代码中,您会看到一个明确读取 – 修改 – 写入或明显只是写入的寄存器或集合。 这可能是不同的开发人员编写示例的不同部分,或者该外设中的寄存器是敏感的,具有未记录的位,并且需要读取 – 修改 – 写入。

在我工作的芯片上,我确保无证(对客户),但未使用的位以某种方式标记,以突出其他未使用的位。 我们通常将未使用/保留位标记为零,这些其他位得到一个名称,并且必须写入此值标记。 并非所有供应商都这样做。

底线是没有保证,假设所有文档和示例程序都有错误,你必须破解你的方法来弄清楚什么是对的,什么是错的。 无论你采取什么样的路径(读取 – 修改 – 写入,写入零等),你都会不时地做错,并且必须重新执行代码以匹配硬件更改。 我强烈建议,如果某个供应商拥有某种类型的芯片ID,那么您的软件会读取该ID,如果它是您没有测试过代码的ID,则声明失败而不编程该部分。 在客户看到产品之前很久的生产测试中,将检测到零件更改,并且软件将参与了解零件更改的原因,作为备用零件的分辨率不兼容和拒绝或软件更改等。

保留大部分时间意味着它们不在此芯片中使用,但它们可能用于特征设备(其他产品系列)。 (大多数芯片制造商生产一个外设驱动程序,并将它用于所有芯片。这种方式主要是复制过去的工作,并且错误的变化较少)大多数情况下,如果写入外设寄存器中的保留位并不重要,这是因为没有附加任何逻辑。

如果你写了一些东西,它就不会被存储,下次你试图读取寄存器/位时,它的接缝就不会改变。