I want to use herumi / bls library in my application. I've successfully compiled libraries following his documentation and get a file armeabi-v7a/libbls384_256.a.
As I guess this is not the same with *.so library and I cannot use this library directly in JNI. I guess instead of this I have to create my own native code to import libbls384_256.a. Is it correct way?
There is no problem to use my own C++ code in my project and this part is already pretty described in different manuals. But I have no idea how to import libbls384_256.a to my native code using Android Studio, Gradle and JNI.
How to include *.a library in native code in Android?
Like you say, you should write a shared library that links against the prebuilt static library. The shared library should contain the exported functions that you want to call from Java, and these can in turn call functions in the static library.
If you're using nkdBuild you'd use the PREBUILT_STATIC_LIBRARY rule, and then add the library to the LOCAL_STATIC_LIBRARIES for your shared library. See https://developer.android.com/ndk/guides/prebuilts
If you're using CMake you'd do something like:
add_library(bls384_256 STATIC IMPORTED GLOBAL)
set_target_properties(bls384_256
PROPERTIES
IMPORTED_LOCATION the/path/to/libbls384_256.a
INTERFACE_INCLUDE_DIRECTORIES the/path/to/the/bls384_256/api/headers
)
Related
I am sorry maybe this is stupid what I am asking, but I have a question about linking static/shared libraries in android.
I am creating a new C++ Native android studio project. After build, I open the apk file, and inside lib the folder there are placed libraries libnative-lib.so for every ABI. Size of APK is 3.580 KB.
But if I change inside CMakeLists.txt to build the native lib like Static lib, so now I got this:
add_library(native-lib
STATIC
native-lib.cpp)
When APK is built, I can not find the static library (libnative-lib.a). There is no lib folder in the apk. Also, the size is 2.836 KB.
Can someone please explain(or give me link for more info about this) where is the library placed in the STATIC build?
And on run I got error if I link static:
No implementation found for java.lang.String com.example.myapplication.MainActivity.stringFromJNI()
You can't use native static libraries directly in Android apps.
Android user space is basically a Java (or more precisely Dalvik VM).
So all user-facing applications must be written in Java or Kotlin (which both compile to Dalvik bytecode).
Static C/C++ libraries must be link in to a C/C++ executable or dynamic library to be used. They can not be loaded directly by Linux or Android.
Since Android app does not have a C/C++ executable in it, the only way to use a static library with an Android app is to link it with a dynamic library (*.so) that can be loaded via Java Native Interface.
Since JNI uses the system loader to load the library, it can only load dynamic libraries, and of those, only ones that export functions with proper naming conventions so they can be matched to a Java class that will be used to call the native code.
How can I use '.a' static library built with NDK.
Where do I attach header files( include file ) to call a function.
My Android studio version is 2.23.
Thanks in advance.
A good place to start is the formal documentation, if you haven't tried it already. Here is the general page showing how to add a prebuilt library: Using Prebuilt Libraries
I need to change pitch and time stretching of an audio. For this I am using prebuild static library. Currently I am having libZtxAndroid.a static library and corresponding header file which contains function declaration. But I don't know how to load this library in my android studio app and call native function from java code. I explored many links and tried to load this library. But all attempts are failed. This is the one link which I have tried last time https://tariqzubairy.wordpress.com/2012/03/12/use-of-prebuild-static-library-compiled-with-android-toolchain/
Also I am using FFMPEG shared library and MP4Parser (https://github.com/sannies/mp4parser) library in this app for adding water mark to video and merging audio respectively. Can any one help from basics.
How to load static library?
Where I need to place that static library?
Where I need to create jni folder (folder structure)?
How to call function available in that static library with the help of header file from java code?
You need to do several things:
Compile a dynamic library. This is a .so file in Android.
You can do this with the android ndk.
There is a directory in every android project, I am saying from the top of my head, but I think it is in a jni subdirectory where you must put your library.
You should wrap your library in JNI. Place them as the advice in this other question: JNI folder in Android Studio
If you have something like this in android:
Java_com_example_hellojni_HelloJni_stringFromJNI( JNIEnv* env,
jobject thiz )
where Java_comp_example_hellojni_HelloJni is your project name, you have to do from Java, assuming the name of your lib is libmylib.so:
public class HelloJni {
static {
System.LoadLibrary('mylib');
}
public native stringFromJni();
}
Note that the native library name does not need the lib prefix and the .so suffix. Note also that you do not need any header file from C++, you just load the library from Java and declare a native function. The library should be already compiled and in the right directory before the Java project uses it.
Be careful at loading: if you use the shared version of the standard library, you will also need to add it to your static { section in Java for loading it, before your library.
i want to use C++ Code in in my Android Project and I find out that Android Studio 2.2 support this much better than the old Version(debugging...).
I created a Folder for each Library so I can add all the C++ Files in the Folder to the Library.
Everything works fine, but there is a little Problem. I want to inlcude a Header File from library A into library B.
I know in can simply use:
#include"../libraryB/someHeader.h"
in the cpp File in Library A.
But is there a way that I can write
#include"somerHeader.h"
Here´s a part of my CMakeListsFile:
file(GLOB SOURCESLIB-A src/main/cpp/lib-A/*cpp)
file(GLOB SOURCESLIB-B src/main/cpp/lib-B/*cpp)
add_library(lib-A SHARED ${SOURCESLIB-A}
add_library(lib-B STATIC ${SOURCESLIB-B}
target_link_libraries(lib-A lib-B)
I'am using one CMakeLists.txt File.
I am writing an Android application. I am implementing some of the app in C++ using JNI. Is there a way to actually separate completely the JNI (C++) code from the Java Android code? Like creating a JNI project or something ? Because my C++ code will become a little library that I will use in another app. I tried to create a C++ project but I can't compile with ndk-build.
In actuality, the tie-in between the Java and native code is fairly loose, in that it is done by the names of the methods at runtime.
The NDK is just a special environment and libraries for a C compiler. A suitable dynamic library file must be produced, but this can be done using the ndk script, using an ndk generated "stand alone tool chain" or even done before (or after, see later) the java project build, done on another machine, etc.
Normally the .so dynamic library gets copied into the appropriate place in the application project tree such that it will end up packaged in the .apk and installed on the device where it can be automatically found by the System.loadLibrary() method. But you could just insert it into the otherwise finished .apk (which is a zip file with special alignment and jarsigner signatures). But even the .pak is not actually not the only way to deliver it to the device (though it is the only recommended way)- a library can also be stored in a place such as the app's private folder and loaded using System.load() which takes a full pathname instead of a library name.
hotverspicy does have a point that the java code needs a native method "declaration" for what is implemented in the jni library, and that this needs to match the actual package name as encoded in the name of the native function implementation. However, that package name does not have to be the same as the rest of the java code - it could be something generic for the re-usable C/C++ library, which would require only one brief matching java class file in the matching java package name.
But in addition to Neevek's idea of using one native lib to interface to another, it is also likely possible to use an object factory mechanism to hook up arbitrary native functions at runtime, given just one association set up at compile time - see the relevant answer to C/C++ Reflection and JNI - A method for invoking native code which hasn't been written yet
If you use JNI in your C++ code, then it's bound to Android, and it must be an Android project with properly defined Android.mk, Application.mk(optional).
If you don't use JNI API in your code, say you want to create a generic library, you can just write your C++ code, compile it, test it as usual, no ndk-build is needed. When you finish coding with the library, build the code as a static library, and when you want to use this static library in your Android project, write some JNI wrappers around functionalities in the static library that you want to use, link against the static library in your Android.mk, something like this:
include $(CLEAR_VARS)
LOCAL_MODULE := libgeneric
LOCAL_SRC_FILES := prebuilt/libgeneric.a
include $(PREBUILT_STATIC_LIBRARY)