求教:sw4stm32编译C++工程 Link的时候出错,请大神帮忙看看
是用STM32CubeMX生成的sw4stm32工程。然后在sw4中转换为C++工程
建立了一个Source Folder 叫做user_libs,在该目录下添加了自定义的类。
该类中有一个public的function定义如下
void HW_SteerEngine::init(TIM_HandleTypeDef *htim, uint32_t tim_channel, int angle)
C和C++编译设置中都已经把user_libs目录添加到include路径中。
代码编译都过了,最后在link的时候出现下列错误。
Building target: SteerEngine.elf
Invoking: MCU G++ Linker
arm-none-eabi-g++ -mcpu=cortex-m3 -mthumb -mfloat-abi=soft -specs=nosys.specs -specs=nano.specs -T"../STM32F103C8Tx_FLASH.ld" -Wl,-Map=output.map -Wl,--gc-sections -fno-exceptions -fno-rtti -o "SteerEngine.elf" @"objects.list" -lm
Src/user_main.o: In function `user_setup':
D:\jinbin\单片机\MyProject\STM32\AC6 WorkSpace\SteerEngine\Debug/../Src/user_main.cpp:18: undefined reference to `HWSteerEngine::HW_SteerEngine::init(TIM_HandleTypeDef*, unsigned long, int)'
collect2.exe: error: ld returned 1 exit status
make: *** Error 1
makefile:51: recipe for target 'SteerEngine.elf' failed
问题是,如果将该方法中的第一个参数类型改为 void *htim的话,link就不出错,能正常生成.bin文件。
类似的问题已经遇到好几次了,一旦在自定义类的函数定义中使用到hal库的变量类型就会出现连接错误。但是使用普通的变量类型就完全OK。
是不是那里设置上遗漏了什么?
这个应该是 HAL 的暗病,头文件没做 C++ 兼容。试试看往 HAL 的头文件里面加上 __BEGIN_DECLS 和 __END_DECLS 能不能解决。 maxtch 发表于 2018-3-12 15:34
这个应该是 HAL 的暗病,头文件没做 C++ 兼容。试试看往 HAL 的头文件里面加上 __BEGIN_DECLS 和 __END_DEC ...
看过头文件。
HAL的头文件中都有
#ifdef __cplusplus
extern "C" {
#endif
#ifdef __cplusplus
}
#endif
__BEGIN_DECLS是一个意思吗?
编译的时候也没出错啊!
__BEGIN_DECLS
和
#ifdef __cplusplus
extern "C" {
#endif
是一回事。 本帖最后由 jjbboox 于 2018-3-20 16:22 编辑
问题原因找到了
不是__cplusplus的问题。
之所以编译出错是HAL的头文件存在bug。
经过仔细调查,发现 TIM_HandleTypeDef是不会出错的,只有SPI_HandelTypeDef类型会出错。
跑到头文件中去查看,发现该类型结构的定义存在问题。定义代码如下:
/**
* @briefSPI handle Structure definition
*/
typedef struct __SPI_HandleTypeDef
{
SPI_TypeDef *Instance; /*!< SPI registers base address */
SPI_InitTypeDef Init; /*!< SPI communication parameters */
uint8_t *pTxBuffPtr;/*!< Pointer to SPI Tx transfer Buffer */
uint16_t TxXferSize; /*!< SPI Tx Transfer size */
__IO uint16_t TxXferCount;/*!< SPI Tx Transfer Counter */
uint8_t *pRxBuffPtr;/*!< Pointer to SPI Rx transfer Buffer */
uint16_t RxXferSize; /*!< SPI Rx Transfer size */
__IO uint16_t RxXferCount;/*!< SPI Rx Transfer Counter */
void (*RxISR)(struct __SPI_HandleTypeDef * hspi); /*!< function pointer on Rx ISR */
void (*TxISR)(struct __SPI_HandleTypeDef * hspi); /*!< function pointer on Tx ISR */
DMA_HandleTypeDef *hdmatx; /*!< SPI Tx DMA Handle parameters */
DMA_HandleTypeDef *hdmarx; /*!< SPI Rx DMA Handle parameters */
HAL_LockTypeDef Lock; /*!< Locking object */
__IO HAL_SPI_StateTypeDefState; /*!< SPI communication state */
__IO uint32_t ErrorCode; /*!< SPI Error code */
}SPI_HandleTypeDef;
通常我们在用typedef定义一个类型的时候 typedef struct后面是不带名称的,只会在结构体最后起名,
但是该类型定义却在typedef struct 后定义为 ,而在结构体定义最后又起名为,导致编译器无法将识别为一个有效的变量类型。
现在通过将参数类型更改为 struct __SPI_HandleTypeDef后问题解决。
该问题在编译器中貌似不会出问题,但是如果是C++编译器就会出错了。
可能是HAL库的bug。
页:
[1]