Android NDK 未定义对 `std::ios_base::Init::Init()' 的引用

Android NDK undefined reference to `std::ios_base::Init::Init()'

我正在从 cocos2d-x 3.9 迁移到 cocos2d-x 3.17.2,当我构建 android studio 项目时,链接 Wwise libAuroPannerMixer.a 时出现错误。 NDK 版本 19.2,用 clang 编译,wwise 版本 2017.1.3.6377。也许有人有同样的问题?

Application.mk

APP_STL := c++_static

APP_CPPFLAGS := -frtti -DCC_ENABLE_CHIPMUNK_INTEGRATION=1 -std=c++11 - 
fsigned-char -Wno-extern-c-compat
APP_LDFLAGS := -latomic -stdlib=libc++ -lstdc++

APP_ABI := arm64-v8a
APP_SHORT_COMMANDS := true

ifeq ($(NDK_DEBUG),1)
  APP_CPPFLAGS += -DCOCOS2D_DEBUG=1
  APP_OPTIM := debug
else
  APP_CPPFLAGS += -DNDEBUG
  APP_OPTIM := release
endif

build.gradle:

import org.gradle.internal.os.OperatingSystem

apply plugin: 'com.android.application'

android {
    compileSdkVersion PROP_COMPILE_SDK_VERSION.toInteger()

    defaultConfig {
        applicationId "org.bio.brick.breaker"
        minSdkVersion PROP_MIN_SDK_VERSION
        targetSdkVersion PROP_TARGET_SDK_VERSION
        versionCode 55
        versionName "1.55"
        multiDexEnabled true

        externalNativeBuild {
            if (PROP_BUILD_TYPE == 'ndk-build') {
                ndkBuild {
                    targets 'BioBrickBreaker'
                    arguments 'NDK_TOOLCHAIN_VERSION=clang'
                    arguments '-j' + Runtime.runtime.availableProcessors()

                    def module_paths =     [project.file("../../cocos2d").absolutePath,
                                    project.file("../../cocos2d/cocos").absolutePath,
                                    project.file("../../cocos2d/external").absolutePath]
                    if (OperatingSystem.current().isWindows()) {
                        module_paths = module_paths.collect {it.replaceAll('\\', '/')}
                        arguments 'NDK_MODULE_PATH=' + module_paths.join(";")
                    }
                    else {
                        arguments 'NDK_MODULE_PATH=' + module_paths.join(':')
                    }
                }
            }
            else if (PROP_BUILD_TYPE == 'cmake') {
                cmake {
                    targets 'BioBrickBreaker'
                    arguments "-DCMAKE_FIND_ROOT_PATH=", "-DANDROID_STL=c++_static", "-DANDROID_TOOLCHAIN=clang", "-DANDROID_ARM_NEON=TRUE"
                    cppFlags "-frtti -fexceptions -fsigned-char"
                }
            }
        }

        ndk {
            abiFilters = []
            abiFilters.addAll(PROP_APP_ABI.split(':').collect{it as String})
        }
    }

    sourceSets.main {
        java.srcDir "src"
        res.srcDir "res"
        jniLibs.srcDir "libs"
        manifest.srcFile "AndroidManifest.xml"
        assets.srcDir "../../Resources"
    }

    externalNativeBuild {
        if (PROP_BUILD_TYPE == 'ndk-build') {
            ndkBuild {
                path "jni/Android.mk"
            }
        }
        else if (PROP_BUILD_TYPE == 'cmake') {
            cmake {
                path "../../CMakeLists.txt"
            }
        }
    }

    buildTypes {
        release {
            debuggable false
            jniDebuggable false
            renderscriptDebuggable false
            minifyEnabled true
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
            if (project.hasProperty("RELEASE_STORE_FILE")) {
                signingConfig signingConfigs.release
            }

            externalNativeBuild {
                ndkBuild {
                   arguments 'NDK_DEBUG=0'
                }
            }
       }

        debug {
            debuggable true
            jniDebuggable true
            renderscriptDebuggable true
            externalNativeBuild {
                ndkBuild {
                    arguments 'NDK_DEBUG=1'
                }
            }
        }
    }
}

buildscript {
    repositories {
        mavenCentral()
    }
}

repositories {
    maven {
        url "https://maven.google.com"
    }

    maven {
        url "http://maven.gameanalytics.com/release"
    }

    flatDir {
        dirs 'libs-aar'
    }
}

android.applicationVariants.all { variant ->
    delete "${buildDir}/intermediates/assets/${variant.dirName}"

    variant.mergeAssets.doLast {
        copy {
            from "${buildDir}/../../../Resources"
            into "${buildDir}/intermediates/assets/${variant.dirName}"
            exclude "**/*.gz"
        }
    }
}

dependencies {
    implementation fileTree(include: ['*.jar'], dir: 'libs')
    implementation project(':libcocos2dx')
    implementation project(':downloader_library')
    implementation project(':license_library')
    implementation project(':zip_library')
}

输出日志:

D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(AuroPannerMixer.o): In function `__static_initialization_and_destruction_0':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `LssAuroPannerEncoder::setSourceParameter(char const*, float)':
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:627: undefined reference to `std::basic_string<char, std::char_traits<char>, std::allocator<char> >::basic_string(char const*, std::allocator<char> const&)'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:628: undefined reference to `std::string::compare(char const*) const'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `std::string::_Rep::_M_dispose(std::allocator<char> const&)':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:249: undefined reference to `std::string::_Rep::_M_destroy(std::allocator<char> const&)'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `LssAuroPannerEncoder::setSourceParameter(char const*, float)':
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:632: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:636: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:640: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:644: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:648: undefined reference to `std::string::compare(char const*) const'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o):C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:652: more undefined references to `std::string::compare(char const*) const' follow
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `__static_initialization_and_destruction_0':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
clang++.exe: error: linker command failed with exit code 1 (use -v to see invocation)D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(AuroPannerMixer.o): In function `__static_initialization_and_destruction_0':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `LssAuroPannerEncoder::setSourceParameter(char const*, float)':
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:627: undefined reference to `std::basic_string<char, std::char_traits<char>, std::allocator<char> >::basic_string(char const*, std::allocator<char> const&)'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:628: undefined reference to `std::string::compare(char const*) const'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `std::string::_Rep::_M_dispose(std::allocator<char> const&)':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:240: undefined reference to `std::string::_Rep::_S_empty_rep_storage'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x\bits/basic_string.h:249: undefined reference to `std::string::_Rep::_M_destroy(std::allocator<char> const&)'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `LssAuroPannerEncoder::setSourceParameter(char const*, float)':
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:632: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:636: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:640: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:644: undefined reference to `std::string::compare(char const*) const'
C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:648: undefined reference to `std::string::compare(char const*) const'
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o):C:\jenkins\ws\wwise_v2017.1\wwise\Partners\Auro\AuroPanner\SoundEnginePlugin\Android/../../../auro-commons/audio/LSSAuroPanner/Src/LSSAuroPanner.cpp:652: more undefined references to `std::string::compare(char const*) const' follow
D:/dev/biobrickbreaker/proj.android/app/jni/../../../WwiseLib/android-21_arm64-v8a/Release/lib/libAuroPannerMixer.a(LSSAuroPanner.o): In function `__static_initialization_and_destruction_0':
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::~Init()'
clang++.exe: error: linker command failed with exit code 1 (use -v to see invocation)

我认为 libAuroPannerMixer.a 构建不正确。在接下来的 wwise 版本中没有 Auro 库。结果,我只是从项目中删除了那个库,它对我有用,没有任何声音问题。我在 wwise 论坛上创建了一个主题 topic

我至少看到三个问题。

APP_LDFLAGS := -latomic -stdlib=libc++ -lstdc++

删除整行。第一个标志是多余的(ndk-build 是自动的),后两个是错误的。

ndk-build 手动 link 将标准库放在 link 命令的正确位置,并使用 -nostdlib++ 来禁止编译器的默认行为。添加 -stdlib=libc++ 会破坏它,所以现在它被 link 编辑了两次,而且在错误的位置。

-lstdc++ link 库错误。

c:\jenkins\ws\wwise_v2017.1\wwise\sdk\source\build\android\android-21_arm64-v8a\include\c++.9.x/iostream:74: undefined reference to `std::ios_base::Init::Init()'

请特别注意此处 std 命名空间的路径和名称。 include\c++.9.x 是 gnustl header 的路径,std 是 gnustl 命名空间的名称。 libc++ 使用不同的 header 路径,命名空间为 std::__ndk1(第二部分是内联命名空间,因此这是一个实现细节,您在编码时无需担心,但它在构建时中断以保护您免受这些问题的影响)。您的 wwise 库是使用 gnustl 构建的,而您使用的是 libc++。这两个库不兼容,不能在同一个应用程序中使用。

您需要使用 libc++ 重建 wwise 才能将其与 libc++ 一起使用。如果您无法这样做,则需要恢复到 NDK r17(支持 gnustl 的最后一个版本)。请注意,如果这样做,您也会失去对 C++14 和 C++11 的某些部分的访问权限(以及重新引入我们从那时起修复的任何错误),因此强烈建议重建 wwise 而不是使用一个旧的 NDK。