OpenWRT交叉编译C++程序遇std::to_string报错,需启用C++11
解决OpenWRT交叉编译C++时std::to_string未定义的问题
嘿,我之前帮朋友排查过一模一样的OpenWRT交叉编译坑,你的问题确实是C++11特性没被正确启用导致的,而且直接加TARGET_CXXFLAGS没用是因为OpenWRT的Makefile有自己的变量优先级规则,给你几个亲测有效的解决办法:
方法1:用OpenWRT专属的PKG_CXXFLAGS设置C++11
OpenWRT里针对单个包的编译选项,应该用PKG_CXXFLAGS而不是全局的TARGET_CXXFLAGS,而且要放在正确的位置。修改你的Makefile如下:
include $(TOPDIR)/rules.mk PKG_NAME:=gateway PKG_VERSION:=1.0 PKG_RELEASE:=2 INIT_SCRIPT_NAME:=$(PKG_NAME) PKG_SOURCE:=... # 你的源码定义 # 关键:添加C++11编译选项,放在include package.mk之前 PKG_CXXFLAGS += -std=c++11 # 部分老版本交叉工具链还需要加这个宏才能支持std::to_string PKG_CXXFLAGS += -D_GLIBCXX_USE_C99 include $(INCLUDE_DIR)/package.mk # 下面是你的包定义和编译规则 define Package/gateway SECTION:=utils CATEGORY:=Utilities TITLE:=Your Gateway Application endef # 如果你自定义了编译命令,一定要把PKG_CXXFLAGS传递进去 define Build/Compile $(MAKE) -C $(PKG_BUILD_DIR) \ CC="$(TARGET_CC)" \ CXX="$(TARGET_CXX)" \ CFLAGS="$(TARGET_CFLAGS) $(PKG_CFLAGS)" \ CXXFLAGS="$(TARGET_CXXFLAGS) $(PKG_CXXFLAGS)" \ LDFLAGS="$(TARGET_LDFLAGS) $(PKG_LDFLAGS)" endef $(eval $(call BuildPackage,gateway))
为什么TARGET_CXXFLAGS没用?因为OpenWRT的package.mk会优先使用PKG_CXXFLAGS来覆盖全局设置,而且如果你的自定义编译命令没把这个变量传进去,编译器根本拿不到C++11的开关。
方法2:手动实现to_string应急
如果工具链版本太老(比如某些老款OpenWRT的mips工具链),即使开了C++11也没有std::to_string,可以自己写一个替代函数放进代码里:
#include <string> #include <sstream> // 自定义to_string,支持常见的数值类型 template <typename T> std::string to_string(T value) { std::ostringstream oss; oss << value; return oss.str(); }
然后把代码里的std::to_string换成这个自定义的to_string就行,不用改Makefile也能解决问题。
最后检查点
- 确认你的交叉工具链支持C++11(大部分OpenWRT 18.06及以后的版本都支持)
- 确保
PKG_CXXFLAGS的添加位置在include $(INCLUDE_DIR)/package.mk之前,不然不会生效
内容的提问来源于stack exchange,提问作者Jakub J.
相关产品推荐
相关产品推荐

