Firebase C++ SDK与WebRTC SDK集成报ssl_lib.cc函数多重定义错误
- 使用官方渠道获取的Firebase C++预构建SDK
- Firebase C++ SDK版本:9.0.0
- 涉及核心Firebase组件:App(Auth、Database等)
- 其他接入的Firebase组件:Database(Auth、Database等)
- SDK运行环境:Ubuntu 18.04.6 LTS(兼容Mac、Windows、Linux平台)
- 目标编译平台:桌面端(支持iOS、Android、桌面端多端目标)
项目中同时集成Firebase SDK与WebRTC SDK时,只要引入Firebase App相关类就会触发编译错误,ssl_st类的所有成员函数均提示多重定义,典型报错输出如下:
home/webrtc/lib_webrtc/src/third_party/boringssl/src/ssl/ssl_lib.cc.o first defined here ../firebase/libs/linux/x86_64/legacy/libfirebase_app.a(93f69bbf5771d4a5b72056dec59d993b_ssl_lib.cc.o): In function ssl_st::~ssl_st()': /home/runner/work/firebase-cpp-sdk/firebase-cpp-sdk/out-sdk/external/src/boringssl/src/ssl/ssl_lib.cc:655: multiple definition of ssl_st::~ssl_st()'
经单独测试验证:Firebase SDK、WebRTC SDK单独接入时均可正常编译运行,仅在二者同时集成时才会触发上述冲突。
该冲突属于典型的静态库依赖重复问题:Firebase官方预编译SDK默认将内置的BoringSSL静态库打包进libfirebase_app.a中,而WebRTC同样内置了自行编译的BoringSSL库。两个静态库中存在大量同名的BoringSSL符号(比如报错提到的ssl_st类相关函数),链接阶段链接器同时加载两份同名符号,就会触发多重定义错误。
按稳定性从高到低排序,可选择以下方案解决:
方案1:源码编译Firebase SDK,统一依赖SSL库(生产环境推荐)
放弃使用官方提供的legacy预编译包,拉取Firebase C++ SDK源码自行编译,编译时通过构建参数关闭SDK内置BoringSSL的静态打包,配置为链接项目中WebRTC使用的同一份BoringSSL库,从根源上消除重复符号。
该方案不存在版本兼容问题,运行稳定性最高,适合正式生产环境使用。
方案2:链接阶段隐藏Firebase库中的BoringSSL符号(快速验证用)
如果暂时不想重新编译SDK,可在链接参数中添加配置,将Firebase静态库中的内部BoringSSL符号设置为局部可见,避免和WebRTC导出的BoringSSL符号冲突,示例GCC/Clang链接参数:
-Wl,--exclude-libs,libfirebase_app.a
注意:该方案存在版本兼容风险,如果Firebase内置的BoringSSL和WebRTC使用的BoringSSL版本差异过大,可能触发运行时崩溃,仅适合临时调试、快速验证场景使用。
方案3:调整链接顺序(不推荐)
可尝试调整链接顺序,将WebRTC相关库的链接顺序放在Firebase SDK之前,让链接器优先加载WebRTC提供的BoringSSL符号,自动跳过Firebase库中重复的符号定义。但该方法受编译器版本、构建系统逻辑影响较大,稳定性差,不建议在正式环境使用。
内容的提问来源于stack exchange,提问作者Muhammad Zaid Ali

