This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] CC2652R:ti_compatibility.h 中的_restore_interrupts ()会导致"instruction&quot 的无效操作数;

Guru**** 2589280 points
Other Parts Discussed in Thread: CC1354P10, CC2674R10, CC2652R

请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/wireless-connectivity/bluetooth-group/bluetooth/f/bluetooth-forum/1371809/cc2652r-_restore_interrupts-in-ti_compatibility-h-causes-invalid-operand-for-instruction

器件型号:CC2652R
主题中讨论的其他器件:CC2674R10、CC1354P10、

工具与软件:

大家好!

我使用的是 TI Arm Clang 编译器 v3.2.LTS、 CCS v12.4、 CC2674R10 (Cortex M33、Armv8-M)

基于 project_zero 示例构建一个项目

尝试使用最初为 armcl 编写的代码

此代码使用 _disable_interrupts()和 _restore_interrupts()内在函数来保护关键段:

    uint32_t savevar;
    savevar = _disable_interrupts(); // get current interrupt state and disable interrupts (TI ARM Compiler intrinsic)
    // critical code...
    _restore_interrupts(savevar);    // restore interrupt state (TI ARM Compiler intrinsic)

tiarmclang 不支持这些内在函数、但提供了 ti_compatibility.h 头文件、该文件应将它们转换为与 tiarmclang 兼容的形式:

/******************************************************************************/
/* Disable interrupts                                                         */
/******************************************************************************/
static __inline__ uint32_t __attribute__((always_inline))
_disable_interrupts(void)
{
#if __ARM_ARCH_PROFILE == 'M' && __ARM_ARCH == 6
    return _disable_IRQ();
#elif __ARM_ARCH_PROFILE == 'M' && __ARM_ARCH == 7
    uint32_t res = 0;
    __asm volatile ("MRS %0, FAULTMASK" : "=r" (res) : : );
    __asm volatile ("CPSID F" : : : );
    return res;
#elif __ARM_ARCH >= 7
    uint32_t res = _get_CPSR();
     __asm volatile ("CPSID IF" : : : );
    return res;
#else
    return 0
#endif
}

/******************************************************************************/
/* Restore interrupts                                                         */
/******************************************************************************/
static __inline__ void __attribute__((always_inline))
_restore_interrupts(uint32_t x)
{
#if __ARM_ARCH_PROFILE == 'M' && __ARM_ARCH == 6
    __asm volatile ("MSR PRIMASK, %0" : : "r" (x) : );
#elif __ARM_ARCH_PROFILE == 'M' && __ARM_ARCH == 7
    __asm volatile ("MSR FAULTMASK, %0" : : "r" (x) : );
#elif __ARM_ARCH >= 7
    __asm volatile ("MSR CPSR_fc, %0" : : "r" (x) : );
#endif
}

编译器采用路径"#elif _arm_arch >= 7"、并在 _restore_interrupts ()上以"指令的无效操作数"失败:

C:\ti\ccs1240\ccs\tools\compiler\ti-cgt-armllvm_3.2.2.LTS\include\c\ti_compatibility.h:1529:21: error: invalid operand for instruction
    __asm volatile ("MSR CPSR_fc, %0" : : "r" (x) : );
                    ^
<inline asm>:1:5: note: instantiated into assembly here
MSR CPSR_fc, r0
    ^

 《Armv8-M 架构参考手册》甚至没有提及 CPSR 寄存器、更不用说 CPSR_fc。

这个代码(及其整个头文件)适用于 Arm v8- M  到底?

是否已有解决此问题的方法?

或者是否有具有相同功能的替代方案?
我在 driverlib 的 cpu.h 中找到 CPUcpsid():它也 返回原始中断启用状态、但没有函数可将其恢复到该状态。


此致、

沃尔夫冈

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    对于编译器发出此诊断时生成的源文件...

    错误:指令的操作数无效

    ... 请遵循在文章 如何提交编译器测试案例中的指示

    谢谢。此致、

    -George.

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    源极少的测试用例:

    #include <ti_compatibility.h>
    int main()
    {
        uint32_t savevar;
        savevar = _disable_interrupts(); // get current interrupt state and disable interrupts (TI ARM Compiler intrinsic)
        // critical code...
        _restore_interrupts(savevar);    // restore interrupt state (TI ARM Compiler intrinsic)
    
        return 0;
    }
    

    编译器版本: TI-CGT-ARMLLVM_3.2.LTS

    从 CCS 控制台中复制的编译命令:
    "c:/ti/ccs1240/ccs/tools/compiler/ti-cgt-armllvm_3.2.2.LTS/bin/tiarmclang.exe cmp"-c @"C:/ti/simplelink_cc13xx_cc26xx_sdk_7_40_00_77/source/ti/ble5stack_flash/config/build_components.opt /ti/simplelink_cc13xx_cc26xx_sdk_7_40_00_77/source/ti/ble5stack_flash/config/factory_config.opt /Startup/problem.c @"C:ti"-mcpu=cortex-m33 -mfloat-abi=hard -mfpu=fpv5-sp-D16 -mlittle-endian -Oz -i"C /ti/ccs1240/ccs/tools/compiler/ti-cgt-armllvm_3.2.2.LTS/include/c @

    预处理的测试用例文件:
    e2e.ti.com/.../problem.pp.txt

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    感谢您提供测试用例。  我可以重现相同的行为。  我提交了 EXT_EP-11787条目 以对其进行调查。  我们欢迎您通过这个链接来了解。

    谢谢。此致、

    -George.

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    好的、感谢您 提交此文档。

    所以、我可以 假设答案是这样的  

    这个代码(及其整个头文件)是否适用于 Arm v8- M  到底?

    是否已有解决此问题的方法?

    如果  armllvm_3.2.2.LTS 的信息为"否"、会怎么样?

    BTW:查找解决方法时、我偶然发现了另一个潜在错误、请参阅相关问题:
    https://e2e.ti.com/support/wireless-connectivity/bluetooth-group/bluetooth/f/bluetooth-forum/1372162/cc2652r-is-hal_enter_critical_section-in-hal_mcu-h-correctly-implemented

    此致、
    沃尔夫冈

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

      有关编译器行为的说明、请参阅 EXT_EP-11787。

    谢谢。此致、

    -George.

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我刚注意到我在错误的器件号下提交了此文件(混淆了2个并发项目)

    CC2674R10 是正确的(Cortex M33)
    CC2652R 错误(Cortex M4F)

    但是、测试用例文件是正确的。

    抱歉

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    谢谢、我明白、TI 不会修复。 因此、ti_compatibilty.h 无法用于 M33。

    除了与中断相关的函数外、还有许多其他函数对于从 CC26xx M4F armcl 移植到 CC26xx M33 armllvm 的项目非常有用(如我们的函数)。

    目前、与中断相关的函数假设__arm_arch > 7是 Armv8、但对于 Armv8M (Cortex M33)、这会失败。
    它们可以简单地检查 _arm_arch_profile、就像对 v6和 v7所做的那样。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您实际上是在要求测试和支持的范围 ti_compatibility.h 扩展。  假设我们开始展开它。  这种扩展在哪里结束?  我们不让它发生、而是限制的范围 ti_compatibility.h 响应 armcl 配置。  遗憾的是、这不包括对 Cortex-M33的支持。

    谢谢。此致、

    -George.

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    是的、我看到了。

    我们从 CC2652切换到了 CC2674、即从 M4切换到 M33 (从而从 armcl 切换到 armllvm)、前提是它们兼容并且可以轻松进行切换。 现在、我们看到情况并非 如此、并且 ti_compatibility.h 不支持此迁移路径。

    我们可以处理这种情况、没问题、这只是一种不愉快的客户体验。