Android NDK about Library (static library , share library and 3rd party library)
A:Static library
文件Android.mk:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := hello-jni
LOCAL_SRC_FILES := hello-jni.c
include $(BUILD_STATIC_LIBRARY)
文件Application.mk:
APP_MODULES :=hello-jni
B: Share library
文件Android.mk:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := hello-jni
LOCAL_SRC_FILES := hello-jni.c
include $(BUILD_SHARED_LIBRARY)
C: Static library+Share library
文件Android.mk:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := mylib_static
LOCAL_SRC_FILES := src.c
include $(BUILD_STATIC_LIBRARY)
include $(CLEAR_VARS)
LOCAL_MODULE := mylib_shared
LOCAL_SRC_FILES := src2.c
LOCAL_STATIC_LIBRARIES := mylib_static
include $(BUILD_SHARED_LIBRARY)
D:Using 3rd party library
文件Android.mk:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := thirdlib1 # name it whatever
LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/libthird1.a # or $(so_path)/libthird1.so
#LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/include
include $(PREBUILT_STATIC_LIBRARY) #or PREBUILT_SHARED_LIBRARY
include $(CLEAR_VARS)
LOCAL_MODULE := mylib_use_thirdlib
LOCAL_SRC_FILES := src.c
LOCAL_STATIC_LIBRARIES := thirdlib1 #or LOCAL_SHARED_LIBRARY
include $(BUILD_SHARED_LIBRARY) #if static lib,need Application.mk(needn't,I have cheked!)
When I use the static library ,I always got the undefined reference to**error no matter what I do.After a whole tough day,I found thatit's not the problem of the mk file,it's the library!Holy Shit!!
My static library was built in cygwin of windows.Of course it can't be used in Linux!!!!Then I built it with android ndk tool and it runs perfectly!!!
a. check your library's mode (whether it isARM)
$ file libtest.so
libtest.so: ELF 32-bit LSB shared object, ARM, version 1 (SYSV), dynamically linked, not stripped
make sure you library is ARM mode.
b. use nm to view the method of the so file
$ nm libtutorial.so |grep T
00001344 a _GLOBAL_OFFSET_TABLE_
000002a8 T getinformation
000002b4 T getinformation2
To use android ndk tool:http://stackoverflow.com/questions/7403036/compile-library-for-android-ndk
What you will need to do this is the android Native Development Kit (NDK)http://developer.android.com/sdk/ndk/index.html and a GCC compiler.
You can then create a Makefile with the parameters as shown below (thanks ViTo Brothers Apoyan) and create your shared library.
GCC := C:\Tools\ndk-toolchain\ndk-standalone\bin\arm-linux-androideabi-gcc.exe GPP := C:\Tools\ndk-toolchain\ndk-standalone\bin\arm-linux-androideabi-g++.exe AR := C:\Tools\ndk-toolchain\ndk-standalone\bin\arm-linux-androideabi-ar.exe OPTIONS :=\ -fpic \ -ffunction-sections \ -funwind-tables \ -fstack-protector \ -D__ARM_ARCH_5__ \ -D__ARM_ARCH_5T__ \ -D__ARM_ARCH_5E__ \ -D__ARM_ARCH_5TE__ \ -Wno-psabi \ -march=armv5te \ -mtune=xscale \ -msoft-float \ -mthumb \ -Os \ -fomit-frame-pointer \ -fno-strict-aliasing \ -finline-limit=64 \ -DANDROID \ -Wa, \ -O2 \ -DNDEBUG \ -g \ default: all all: obj $(AR) r mysharedlibrary.so *.o obj: $(GCC) $(OPTIONS) -c *.c
#Scripting manually
#!/bin/bash # # FFmpeg-Android, a bash script to build FFmpeg for Android.## Copyright (c) 2012 Cedric Fung <wolfplanet@gmail.com> # # FFmpeg-Android will build FFmpeg for Android automatically, # with patches from VPlayer's Android version <https://vplayer.net/>. # # FFmpeg-Android is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 3 of the License, or (at your option) any later version. # FFmpeg-Android is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # You should have received a copy of the GNU Lesser General Public # License along with FFmpeg-Android; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA # # # Instruction: # # 0. Install git and Android ndk # 1. $ export ANDROID_NDK=/path/to/your/android-ndk # 2. $ ./FFmpeg-Android.sh # 3. libffmpeg.so will be built to build/ffmpeg/{neon,armv7,vfp,armv6}/ # 4. one option for installing ccache, one software packet speeding up recompiling. #
FFMPEG_DIR=AndroidFFmpeg
DEST=`pwd`/$FFMPEG_DIR/libs && rm -rf $DEST
SOURCE=`pwd`/$FFMPEG_DIR
if [ -d $FFMPEG_DIR ]; then echo "11111111111" cd $FFMPEG_DIR else git clone git://source.ffmpeg.org/ffmpeg.git $FFMPEG_DIR cd $FFMPEG_DIR fi
git log | head -n 1 | awk '{print $2}' > ffmpeg-version
TOOLCHAIN=/opt/uwplayer SYSROOT=$TOOLCHAIN/sysroot/ $ANDROID_NDK_ROOT/build/tools/make-standalone-toolchain.sh --arch=arm --platform=android-14 --toolchain=arm-linux-androideabi-4.4.3 --install-dir=$TOOLCHAIN
export PATH=$TOOLCHAIN/bin:$PATH #note: if ccache not installed, following line will be export CC="arm-linux-androideabi-gcc"
export CC="ccache arm-linux-androideabi-gcc" export LD=arm-linux-androideabi-ld export AR=arm-linux-androideabi-ar
# note: tab rather than space is in front of -finline-limit etc \
# \ is the last character, ie., no space is behind it.
CFLAGS="-O3 -Wall -mthumb -pipe -fpic -fasm \ -finline-limit=300 -ffast-math \ -fstrict-aliasing -Werror=strict-aliasing \ -fmodulo-sched -fmodulo-sched-allow-regmoves \ -Wno-psabi -Wa,--noexecstack \ -D__ARM_ARCH_5__ -D__ARM_ARCH_5E__ -D__ARM_ARCH_5T__ \ -D__ARM_ARCH_5TE__ \ -DANDROID -DNDEBUG"
FFMPEG_FLAGS="--prefix=/usr/local/android/ffmpeg --target-os=linux --arch=arm\ --cross-prefix=arm-linux-androideabi- \ --enable-cross-compile \ --enable-cross-compile \ --enable-shared \ --disable-symver \ --disable-doc \ --disable-ffplay \ --disable-ffmpeg \ --disable-ffprobe \ --disable-ffserver \ --disable-avdevice \ --disable-avfilter \ --disable-muxers \ --disable-bsfs \ --disable-filters \ --disable-devices \ --disable-everything \ --enable-protocols \ --enable-parsers \ --enable-demuxers \ --disable-demuxer=sbg \ --enable-decoders \ --enable-encoders \ --enable-encoder=rawvideo \ --enable-network \ --enable-swscale \ --enable-asm \ --enable-version3"
#for version in neon armv7 vfp armv6; do for version in armv7; do cd $SOURCE
case $version in neon) EXTRA_CFLAGS="-march=armv7-a -mfpu=neon -mfloat-abi=softfp -mvectorize-with-neon-quad" EXTRA_LDFLAGS="-Wl,--fix-cortex-a8" ;; armv7) EXTRA_CFLAGS="-march=armv7-a -mfpu=vfpv3-d16 -mfloat-abi=softfp" EXTRA_LDFLAGS="-Wl,--fix-cortex-a8" ;; vfp) EXTRA_CFLAGS="-march=armv6 -mfpu=vfp -mfloat-abi=softfp" EXTRA_LDFLAGS="" ;; armv6) EXTRA_CFLAGS="-march=armv6" EXTRA_LDFLAGS="" ;; *) EXTRA_CFLAGS="" EXTRA_LDFLAGS="" ;; esac
PREFIX="$DEST/$version" && mkdir -p $PREFIX FFMPEG_FLAGS="$FFMPEG_FLAGS --prefix=$PREFIX"
./configure $FFMPEG_FLAGS --extra-cflags="$CFLAGS $EXTRA_CFLAGS" --extra-ldflags="$EXTRA_LDFLAGS" | tee $PREFIX/configuration.txt cp config.* $PREFIX [ $PIPESTATUS == 0 ] || exit 1
make clean make -j4 || exit 1 make install || exit 1
[ ! -f libavcodec/inverse.o ] || rm libavcodec/inverse.o [ ! -f libavcodec/log2_tab.o ] || rm libavcodec/log2_tab.o [ ! -f libavformat/log2_tab.o ] || rm libavformat/log2_tab.o [ ! -f libswresample/log2_tab.o ] || rm libswresample/log2_tab.o
$AR cr $PREFIX/libffmpeg.a libavutil/*.o libavutil/arm/*.o libavcodec/*.o libavcodec/arm/*.o libavformat/*.o libswresample/*.o libswresample/arm/*.o libswscale/*.o
cp $PREFIX/libffmpeg.a $PREFIX/libffmpeg-debug.a arm-linux-androideabi-strip --strip-unneeded $PREFIX/libffmpeg.a
$CC -lm -lz -shared --sysroot=$SYSROOT -Wl,--no-undefined -Wl,-z,noexecstack $EXTRA_LDFLAGS libavutil/*.o libavutil/arm/*.o libavcodec/*.o libavcodec/arm/*.o libavformat/*.o libswresample/*.o libswresample/arm/*.o libswscale/*.o -o $PREFIX/libffmpeg.so
cp $PREFIX/libffmpeg.so $PREFIX/libffmpeg-debug.so arm-linux-androideabi-strip --strip-unneeded $PREFIX/libffmpeg.so
done
e. generate executable image
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES:= \ surfaceflinger.cpp \ demo.c
LOCAL_MODULE:= demo
LOCAL_SHARED_LIBRARIES := libui libutils
include $(BUILD_EXECUTABLE)