Could not find method cppFlags() arguments() for arguments - android

I am trying to use
std::function
But the compiler throws an error
Error:(50, 10) error: no type named 'function' in namespace 'std'
I have tried to modify the build.gradle file
externalNativeBuild {
ndkBuild {
path "src/main/jni/Android.mk"
}
cmake {
cppFlags "-std=c++11"
arguments "-DANDROID_STL=gnustl_static"
path 'src/main/jni/CMakeLists.txt'
}
}
But it doesn't accept arguments other than path and throws the following errors
Error:(28, 0) Could not find method arguments() for arguments [-DANDROID_STL=gnustl_static] on object of type com.android.build.gradle.internal.dsl.CmakeOptions.
Please help me to be able to use
std::function
UPDATE
Thanks to #Alex Cohn I was able to configure flags and arguments, and now my file looks like that
apply plugin: 'com.android.library'
android {
compileSdkVersion 25
buildToolsVersion '26.0.2'
defaultConfig {
minSdkVersion 15
targetSdkVersion 25
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
externalNativeBuild {
cmake {
cppFlags "-std=c++11"
arguments "-DANDROID_STL=gnustl_static"
}
}
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
externalNativeBuild {
/* ndkBuild {
path "src/main/jni/Android.mk"
}*/
cmake {
// cppFlags "-std=c++11"
//arguments "-DANDROID_STL=gnustl_static"
path 'src/main/jni/CMakeLists.txt'
}
}
}
dependencies {
compile 'com.android.support:support-annotations:25.0.1'
}

There are two entirely different blocks in build.gradle that are named externalNativeBuild (thanks, Google).
One is under android top-level block, and it specifies the path to native build script, cmake or ndkBuild (but not both).
The other can be used to specify, from gradle, some parameters for the native build. This block is usually a child of the defaultConfig block, but can also appear for flavors (see an example).
These externalNativeBuild blocks can also have cmake or ndkBuild children, but only the child that matches the path setting (see above) is relevant, the other is silently ignored.
The bottom line, split your block in two, and put each one in correct place in build.gradle hierarchy.

Related

CMAKE not obeying flags from gradle for NDK building on Android

I have an Android NDK project which I am trying to build through Gradle+CMake.
build.gradle:
apply plugin: 'com.android.library'
allprojects {
repositories {
jcenter()
google()
}
}
android {
compileSdkVersion 27
defaultConfig {
minSdkVersion 16
targetSdkVersion 27
versionCode 1
versionName "1.0"
externalNativeBuild {
cmake {
cppFlags "-std=c++11"
arguments "-DANDROID_ABI=armeabi-v7a",
"-DANDROID_PLATFORM=android-16",
"-DANDROID_STL=gnustl_static",
"-DANDROID_CPP_FEATURES=rtti exceptions",
"-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=libs"
}
}
}
buildTypes {
release {
ndk {
abiFilters "armeabi-v7a"
}
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
debug {
ndk {
abiFilters "armeabi-v7a"
}
}
}
externalNativeBuild {
cmake {
path 'CMakeLists.txt'
}
}
}
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
}
CMAKE Command Output:
Executable : /Users/ssk/Library/Android/sdk/cmake/3.6.3155560/bin/cmake
arguments :
-H/Users/ssk/MyProject
-B/Users/ssk/MyProject/.externalNativeBuild/cmake/debug/armeabi-v7a
-DANDROID_ABI=armeabi-v7a
-DANDROID_PLATFORM=android-16
------> -DCMAKE_LIBRARY_OUTPUT_DIRECTORY=/Users/ssk/MyProject/build/intermediates/cmake/debug/obj/armeabi-v7a
-DCMAKE_BUILD_TYPE=Debug
-DANDROID_NDK=/Users/ssk/Library/Android/sdk/ndk-bundle
-DCMAKE_CXX_FLAGS=-std=c++11
-DCMAKE_TOOLCHAIN_FILE=/Users/ssk/Library/Android/sdk/ndk-bundle/build/cmake/android.toolchain.cmake
-DCMAKE_MAKE_PROGRAM=/Users/ssk/Library/Android/sdk/cmake/3.6.3155560/bin/ninja
-GAndroid Gradle - Ninja
-DANDROID_STL=gnustl_static
-DANDROID_ABI=armeabi-v7a
-DANDROID_PLATFORM=android-16
-DANDROID_CPP_FEATURES=rtti exceptions
------> -DCMAKE_LIBRARY_OUTPUT_DIRECTORY=libs
jvmArgs :
I am trying to configure the output directory using DCMAKE_LIBRARY_OUTPUT_DIRECTORY, but it's not obeying.
Gradle prefixes a default one before my option as highlighted (------> in cmake command output).
Question:
How should I configure the output directory?
Below snippet will configure your output directory:
For static lib output directory, try below:
# copy out the static lib binary
set_target_properties(${STATIC_LIBRARY_NAME}
PROPERTIES
ARCHIVE_OUTPUT_DIRECTORY "libs/${ANDROID_ABI}")
For shared lib output directory, try below:
# copy out the shared lib binary
set_target_properties(${SHARED_LIBRARY_NAME}
PROPERTIES
LIBRARY_OUTPUT_DIRECTORY "libs/${ANDROID_ABI}")
Explanation:
ANDROID_ABI is a variable defining the Android ABI, e.g. armeabi-v7a
Reference about the CMake variables definition:
Android NDK path variable for "strip" command in CMake build tool chain
Probably you need to set the buildStagingDirectory option. In the next link you will find how to manage paths for CMake in gradle:
CMakeOptions
And as a side note unrelated to the question. In your gradle script seems you are still using gnustl_static which is no longer supported and will be removed in the next NDK versions. You should switch to either c++_static or c++_shared. Take into account that gcc has been deprecated and you should use clang. Next an example:
externalNativeBuild {
cmake {
arguments "-DANDROID_PLATFORM=android-16", "-DANDROID_STL=c++_static", "-DANDROID_TOOLCHAIN=clang"
abiFilters "armeabi-v7a", "arm64-v8a", "x86"
}
}

How to resolve this issue Error while executing c:\Users\user\...\cmake.exe with arguments {-HF:\My Project\app\sr.......-DANDROID_TOOLCHAIN=clang}

I am not so much familiar with Cmake of the android studio. Recently I decided to use it for the native interface. Every time I build the project from build tool, I am getting the aforesaid error in gradle sync message.
My CMakeLists.txt file
cmake_minimum_required(VERSION 3.4.1)
add_library(native-lib
SHARED
src/main/cpp/native-lib.cpp)
My build.gradle (app level)
apply plugin: 'com.android.application'
android {
compileSdkVersion 24
buildToolsVersion "25.0.2"
defaultConfig {
applicationId="com.example.user.MyProject"
minSdkVersion 17
targetSdkVersion 24
multiDexEnabled true
versionCode 1
versionName "1.0"
vectorDrawables.useSupportLibrary true
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
externalNativeBuild {
cmake {
cppFlags '-frtti'
arguments '-DANDROID_TOOLCHAIN=clang'
abiFilters 'armeabi-v7a'
}
}
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
// proguardFiles.add(file("proguard-rules.txt"))
}
}
externalNativeBuild {
cmake {
path 'src/main/cpp/CMakeLists.txt'
}
}
}
dependencies {
What am I doing wrong here?? Any help will be appreciated.

Gradle seems to overrwrite ndk build arguments while adding product flavors

I have an android project where the build.gradle looks like this:
android {
compileSdkVersion 25
buildToolsVersion "25.0.0"
defaultConfig {
applicationId "com.example.test"
minSdkVersion 24
targetSdkVersion 25
versionCode 1
versionName "1.0"
ndk {
// Specifies the ABI configurations of your native
// libraries Gradle should build and package with your APK.
abiFilters 'armeabi-v7a'
}
externalNativeBuild {
ndkBuild {
targets "test_app"
}
}
}
buildTypes {
release {
minifyEnabled false
useProguard false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
productFlavors {
general {
externalNativeBuild {
ndkBuild {
arguments "LOCAL_CFLAGS+=-std=c++11"
arguments "LOCAL_CFLAGS+=-DMODE_GENERAL"
}
}
}
full {
externalNativeBuild {
ndkBuild {
arguments "LOCAL_CFLAGS+=-std=c++11"
arguments "LOCAL_CFLAGS+=-DMODE_FULL"
}
}
}
}
externalNativeBuild {
ndkBuild {
path 'src/main/cpp/Android.mk'
}
}
}
My Android.mk in path 'src/main/cpp/Android.mk' already includes LOCAL_CFLAGS += -std=c++11 and it builds fine if I don't have any product flavors. However, if I do have the product flavors then I have to include arguments "LOCAL_CFLAGS+=-std=c++11" to make it build. I am wondering if there is any way to avoid this as I feel I should only need to include extra args which are not mentioned in the Android.mk.
The root cause of the problematic behavior is not gradle, but that you set LOCAL_CFLAGS (a make variable) on make's command line. The rules of gnu make which runs under the hood of ndk-build, state that this "locks" the variable, and whatever you set in makefile has no effect. Make introduces a special override directive, but it cannot be used in ndk-build for LOCAL_CFLAGS.
You are not supposed to override LOCAL_CFLAGS from outside a local module; you should use APP_CFLAGS in Application.mk or as ndk-build command line arguments.
It is not a good idea to set (whatever)_CFLAGS=-std=c++11 because these flags will be passed both to C++ and C compilers. This setting belongs to LOCAL_CPPFLAGS and her kin.
With gradle plugin, you can use cFlags and cppFlags, as shown in the official doc - better than general-purpose arguments, e.g.:
productFlavors {
full {
externalNativeBuild {
ndkBuild {
cFlags "-DMODE_FULL"
cppFlags "-fexceptions"
}
}
}
}

In Android Studio what is the equivalent of CMAKE_VERBOSE_MAKEFILE under ndk-build?

I am trying to push some existing Android.mk-based native code into a new Android Studio app. There are some linking errors that give the message "Error:error: linker command failed with exit code 1 (use -v to see invocation)". When using CMake, one can set the variable CMAKE_VERBOSE_MAKEFILE to make this the default behavior. Is there a way to do something similar under ndk-build? Trying to run ndk-build from the command line with -v or V=1 (not sure which is best) in an Android Studio context seems awkward.
Edit:
As noted in the response below, this should be possible from Gradle using the "arguments" keyword. My interpretation of this is this version of the Module: app build.gradle file:
apply plugin: 'com.android.application'
android {
compileSdkVersion 24
buildToolsVersion "25.0.2"
defaultConfig {
applicationId "com.adth.jwc.testproj4"
minSdkVersion 16
targetSdkVersion 24
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
externalNativeBuild {
cmake {
cppFlags ""
}
}
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
externalNativeBuild {
ndkBuild {
path "$projectDir/jni/Android.mk"
arguments "V=1"
}
}
}
dependencies {
compile fileTree(dir: 'libs', include: ['*.jar'])
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compile 'com.android.support:appcompat-v7:24.2.1'
testCompile 'junit:junit:4.12'
}
This generates the error message "Error:(16, 0) Could not find method ndkBuild() for arguments [build_95llvy1tc979yxena3spokoe8$_run_closure1$_closure3#34646897] on root project 'TestProj4' of type org.gradle.api.Project."
I have also tried some variations, all of which generate essentially the same error. What is the correct placement of the "arguments" keyword in the build.gradle file?
From the DSL reference, it looks like you need to put the exernalNativeBuild block in a product flavor or build type block to add arguments, so
defaultConfig {
applicationId "com.adth.jwc.testproj4"
minSdkVersion 16
targetSdkVersion 24
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
externalNativeBuild {
ndkBuild {
arguments "V=1"
}
}
}
should work. Confusingly, BaseExtension (the android block) can also have an externalNativeBuild block, but its ndkBuild property is an NdkBuildOptions object, which only has a path property. The ndkBuild blocks for flavors and build types are ExternalNativeNdkBuildOptions objects, which have arguments etc.
ndkBuild { arguments "V=1" } in your build.gradle, and then run gradle with --info (Settings->Build, Execution, Deployment->Compiler->Command-line Options).
For command line ndk-build usage, run ndk-build V=1.
https://developer.android.com/studio/projects/add-native-code.html#link-gradle

How to set NDK lib path in Gradle?

I'm working on a PDF viewer application using ebookdroid & MuPDF CPP files. I am having lots of problem with NDK integration in Gradle. I've gone through many answers but they have not fixed my problem.
Gradle is giving me the following error message:
Error:Execution failed for task ':app:compileDebugNdk'.
Error: Your project contains C++ files but it is not using a supported native build system.
Consider using CMake or ndk-build integration with the stable Android Gradle plugin:
https://developer.android.com/studio/projects/add-native-code.html
or use the experimental plugin:
http://tools.android.com/tech-docs/new-build-system/gradle-experimental.
Edit your build.gradle, add defaultConfig.externalNativeBuild.ndkBuild, externalNativeBuild.ndkBuild and sourceSet.main.jni.srcDir options. See the comments below.
android {
compileSdkVersion 22
buildToolsVersion "27.0.0"
defaultConfig {
minSdkVersion 18
targetSdkVersion 22
versionCode 1
versionName "1.0"
//add arguments passed to ndkBuild
externalNativeBuild {
ndkBuild {
arguments "NDK_TOOLCHAIN_VERSION=clang", "APP_SHORT_COMMANDS=true", "APP_ALLOW_MISSING_DEPS=true"
arguments "-j" + Runtime.runtime.availableProcessors()
cFlags "-fexceptions"
}
}
ndk {
abiFilters "armeabi-v7a"
}
}
//specify jni source file path
sourceSets.main {
java.srcDir "src"
res.srcDir "res"
jni.srcDir "jni"
}
buildTypes {
debug {
debuggable true
jniDebuggable true
}
}
//specify makefile / CMake file
externalNativeBuild {
ndkBuild {
path 'jni/Android.mk'
}
}
}

Categories

Resources