【发布时间】:2018-08-10 04:49:49
【问题描述】:
我也在 STM32 社区论坛上发布了相同的question,但没有收到回复。
我在启用 C++14 的项目中使用 stm32 HAL 库。它向我发出以下警告,我无法摆脱。
../platform/stm32/l4/STM32L4xx_HAL_Driver/Inc/stm32l4xx_hal_rcc.h:735:57:
警告:转换为 void 不会访问 'volatile 类型的对象 uint32_t {aka volatile long unsigned int}' UNUSED(tmpreg); \
当调用 __GPIOX_CLK_ENABLE() 或 __HAL_RCC_GPIOX_CLK_ENABLE 时会发生这种情况。
有没有人能够摆脱上述警告而保持 HAL 源代码完好无损。
或者任何可以做的想法。
当前警告级别为 -Wall。
我在 l4 和 f4 系列代码中都遇到过上述问题。
示例代码:
int main(void)
{
HAL_Init();
__GPIOB_CLK_ENABLE();
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.Pin = GPIO_PIN_7;
GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStructure.Speed = GPIO_SPEED_HIGH;
GPIO_InitStructure.Pull = GPIO_NOPULL;
HAL_GPIO_Init(GPIOB, &GPIO_InitStructure);
for (;;)
{
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_7, GPIO_PIN_SET);
HAL_Delay(500);
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_7, GPIO_PIN_RESET);
HAL_Delay(500);
}
}
罪魁祸首是__GPIOB_CLK_ENABLE(),它被扩展为以下内容(在 ST 驱动程序中)。
#define __HAL_RCC_GPIOB_CLK_ENABLE() do { \
__IO uint32_t tmpreg; \
SET_BIT(RCC->AHB2ENR, RCC_AHB2ENR_GPIOBEN); \
/* Delay after an RCC peripheral clock enabling */ \
tmpreg = READ_BIT(RCC->AHB2ENR, RCC_AHB2ENR_GPIOBEN); \
UNUSED(tmpreg); \
} while(0)
我最初的问题旨在找出解决方案,使底层 ST 驱动程序保持不变。 一种可能的解决方案是使用直接寄存器访问而不通过库提供的方便宏。
提前谢谢你。
【问题讨论】:
-
我做了一些研究,这个警告的原因是
UNUSED宏,它是上述宏的一部分,对void进行了不稳定的引用。它与 C++14 和 -Wall 无关,但所有 g++ 版本都提供相同的诊断。原因可以在链接的副本中找到。解决方案是不使用 volatile 引用,这在编写与硬件相关的代码时是一种可疑的做法——改用 volatile 指针。也许您不小心使用了引用? -
C++11 中不会发出警告。我可以使用 C++11 成功编译相同的代码,而不会收到
-Wall的任何警告。绝对不是all g++编译器版本。这就是这个问题背后的原因。 -
绝对不是
duplicate。我强烈建议您下载 STM32 CubeMX HAL 源代码并在 C++11 和 C++14 中编译它。该警告在 C++14 中变得明显,但在 C++11 中从未出现。 -
我能够通过简单地将任何 volatile 引用转换为 void 来将其复制到 C++03。所以这与编译器版本无关。你的调用者代码中一定有一些在 C++14 中表现不同的东西。请使用包含发出警告的调用者代码的MCVE 编辑您的问题。
-
我现在重新打开这个问题,但我不相信没有例子就可以回答。很可能问题出在 ST 驱动程序上,尽管据我了解,这些驱动程序是用纯 C 编写的?参考来自哪里?