The Android app I am working on is completely written in C++. I need to integrate it with a static library that also is written in C++. There is no dependency on STL in any of the projects.
The static library uses cmake to build. Unfortunately, the app is based on an old AOSP version of Android NDK and has no support for cmake.
I also have a newer version of Android NDK in a different directory. This version does support cmake toolchains.
I am thinking I will build the static library against the new NDK and use it in my main project. The ABI is the same for both the projects - armv7a.
I have tested this logic with a sample code. It seems to work. I am able to invoke methods in the static library from my main app.
Also, there are no name-mangling issues.
The question I have is if there is any issue I am overlooking.
I am thinking it should not matter that the compilers used to build the sources are different. As long as they are producing arm-compatible code, I should be able to able to integrate them.
As a matter of fact, another library that I am using, gstreamer, is available for download as pre-built binaries at https://gstreamer.freedesktop.org/data/pkg/android.
Please advice.
For those interested, mixing NDKs doesn't seem to be an issue as long as you follow certain guidelines. Some of them are listed at https://developer.android.com/ndk/guides/cpp-support.
Essentially, there is no problem if your project is 'C' based. However, if you are using C++, you must not use STL.
I have managed to build part of my code with two NDKs and I am not seeing any link time or runtime errors.
Related
I am currently working on a wearOS app written in Kotlin that needs to consume a native library.
I have cloned the library from github and built it. The output consists of a libs folder with 4 different subfolders containing .so files for the different ABIs and a java folder with two java classes to interact with the library.
I have been reading the android docs but I still can't figure out how I need to import these files in my project to actually use the library. I don't have a lot of experience in android development, could anybody explain to me wat to do or just point me to the right docs/integration guide?
Windows SDK 7.1 was the last version that included the baseclasses direct show sample. But later Windows SDK have strmbase.lib with the compiled library. What use is the library without the headers?
It might be included without good reason waiting for its cleanup time, or there is unobvious reason such as reference to this static library when linking other legacy libraries.
Either way you are correct in the part that DirectShow bases classes are no longer in Windows SDK. Those interested in DirectShow development would typically get DirectShow BaseClasses and samples from Windows-classic-samples/Win7Samples and build the code including strmbase.lib themselves.
For a cross-platform software project that builds on Linux and Windows we have distinct ways to handle third-party libraries. On Linux we build and link against the versions distributed with the CentOS/RHEL distribution, which means we link against release builds, whereas on Windows we maintain our own third-party library "packages" and on Windows we build two versions of every library - a release version that links msvcr100 and msvcp100 and a debug version that links msvcr100d and msvcp100d.
My question is simply whether it is necessary to build the debug version of the third-party dependencies on Windows or can we simply use /nodefaultlib:msvcr100 when building debug builds of our own software.
A follow up question: Where can I learn about good practices in this regard. I've read the MSDN pages about the msvc runtime, but there is very little there in terms of recommendations.
EDIT:
Let me rephrase the question more concisely. With VS2010, what is the problem with using /nodefaultlib:msvcr100 to link an executable build with /MDd when linking with libraries that are compiled with /MD.
My motivation for this is to avoid to have to build both release and debug version of third party libraries that I use. Also I want my debug build to run faster.
From the document for /MD, /MT, /LD (Use Run-Time Library):
MD: Causes your application to use the multithread- and DLL-specific version of the run-time library. Defines _MT and _DLL and causes the compiler to place the library name MSVCRT.lib into the .obj file.
Applications compiled with this option are statically linked to MSVCRT.lib. This library provides a layer of code that allows the linker to resolve external references. The actual working code is contained in MSVCR100.DLL, which must be available at run time to applications linked with MSVCRT.lib
/MDd: Defines _DEBUG, _MT, and _DLL and causes your application to use the debug multithread- and DLL-specific version of the run-time library. It also causes the compiler to place the library name MSVCRTD.lib into the .obj file.
So there is no documentation for any difference done to the generated code other than _DEBUG being defined.
You only use the Debug build of the CRT to debug your app. It contains lots of asserts to help you catch mistakes in your code. You never ship the debug build of your project, always the Release build. Nor can you, the license forbids shipping msvcr100d.dll. So building your project correctly automatically avoids the dependency on the debug version of the CRT.
The /nodefaultlib linker option was intended to allow linking your program with a custom CRT implementation. Quite rare but some programmers care a lot about building small programs and the standard CRT isn't exactly small.
Some programmers use the /nodefaultlib has a hack around a link problem. Induced when they link code that was built with Debug configuration settings with code built with Release configuration settings. Or link code that has incompatible CRT choices, /MD vs /MT. This can work, no guarantee, but of course only sweeps the real problem under the floor mat.
So no, it is not the proper choice, fixing the core problem should be your goal. Ensure that all your .obj and .lib files are built with the same compiler options and you won't have this problem. If that means that you have to pester a library owner for a proper build then pester first, hack around it only when you've discovered that you don't want to have a dependency on that .lib anymore but don't yet have the time to find an alternative.
I'm working on WinRt version of my class library dll. Finally, after the huge "code cleanup" my project is on building step and I have two ways. To build the solution with Release|AnyCPU as usually or build it with Release|ARM (Which unclear for me). Which dependencies my dll will get or avoid in process of building, what will be different, will there a specific IL optimizations on a second way?
If you're only using managed code, there's no reason not to use Release|AnyCPU. This way the same package will be used for all three platforms (ARM, x86 and x64).
On the other hand, if your project references natively compiled library, you'll need to set a specific platform, like Release|ARM, that your native library is compiled for. If the native library is installed as an extension (e.g. SQLite for Windows Runtime), you'll be able to compile your app for all 3 target platforms, each one referencing the appropriate native library, though they will need to be individual packages instead of a single universal one.
You'll still be able to submit your app to the store as a single app even if it has 3 separate packages, one for each platform.
I need to extend the functionality of the android.hardware.Camera class and so I have written my own class and companion JNI library to meet my needs. If I place my JNI code and Android.mk file in the Android source tree and build the OS, my library builds and I can use it and the Java class in an application without any problems (on an evaluation module at least).
The problem is that I would prefer to build my JNI library with the NDK but I need several libraries that are not in the NDK (e.g. libandroid_runtime and libcamera_client).
Is it possible to use the NDK to access hardware such as the camera? If so, what is the proper way to get access to OS libraries?
You can access non-standard shared libraries from NDK, but that is undocumented and is not guaranteed to work on different devices. Vendors like HTC, Samsung and other can simply implement them differently.
Only proper way how to use functionality not available in NDK is to wrap it with Java classe/functions, and then use them from native code.