嗨,我是android-ndk的新手,到目前为止我使用android-ndk中的所有示例应用程序,现在我正在尝试在android中移植fftw3库,你能不能为我推荐任何教程。
感谢。
答案 0 :(得分:17)
FFTW3构建系统使用Autotools,因此您无法直接将其与Android NDK一起使用。 处理此问题的好文章是here。
我们的想法是离线生成一个合适的config.h
文件并创建Android Makefile,它取代了通常由Autotools生成的缺失文件。
要为您可能使用的不同本机模块实现模块化布局,我建议如下:
在您的热门jni/
目录中输入以下两个文件:
Application.mk
:
APP_OPTIM := release
APP_ABI := armeabi armeabi-v7a
APP_MODULES := fftw3
Android.mk
:
TOP_DIR := $(call my-dir)
include $(TOP_DIR)/fftw3/project/jni/Android.mk
通过这种方式,您可以通过创建jni/new_module_name
目录然后将new_module_name
添加到APP_MODULES
列表来轻松添加新模块。
然后创建一个新的jni/fftw3
目录并在其中放置另一个Application.mk
:
Application.mk
:
APP_PROJECT_PATH := $(call my-dir)/project
APP_MODULES += fftw3
APP_OPTIM := release
APP_ABI := armeabi armeabi-v7a
然后将原始FFTW3包放在jni/fftw3/project/jni
下。
此时您需要生成config.h
。您可以使用像this这样的小型shell脚本来完成此操作。
最后一步是创建所需的Android Makefile。在jni/fftw3/project/jni
中放置了一个顶部Android.mk
:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
include $(LOCAL_PATH)/api/sources.mk
include $(LOCAL_PATH)/dft/sources.mk
include $(LOCAL_PATH)/dft/scalar/sources.mk
include $(LOCAL_PATH)/dft/scalar/codelets/sources.mk
include $(LOCAL_PATH)/kernel/sources.mk
include $(LOCAL_PATH)/rdft/sources.mk
include $(LOCAL_PATH)/rdft/scalar/sources.mk
include $(LOCAL_PATH)/rdft/scalar/r2cb/sources.mk
include $(LOCAL_PATH)/rdft/scalar/r2cf/sources.mk
include $(LOCAL_PATH)/rdft/scalar/r2r/sources.mk
include $(LOCAL_PATH)/reodft/sources.mk
LOCAL_MODULE := fftw3
LOCAL_C_INCLUDES := $(LOCAL_PATH) \
$(LOCAL_PATH)/api \
$(LOCAL_PATH)/dft \
$(LOCAL_PATH)/dft/scalar \
$(LOCAL_PATH)/dft/scalar/codelets \
$(LOCAL_PATH)/kernel \
$(LOCAL_PATH)/rdft \
$(LOCAL_PATH)/rdft/scalar \
$(LOCAL_PATH)/rdft/scalar/r2cb \
$(LOCAL_PATH)/rdft/scalar/r2cf \
$(LOCAL_PATH)/rdft/scalar/r2r \
$(LOCAL_PATH)/reodft
# Use APP_OPTIM in Application.mk
LOCAL_CFLAGS := -g
include $(BUILD_SHARED_LIBRARY)
现在,您必须创建所有这些sources.mk
文件。
例如。一个典型的sources.mk
看起来像这样:
rdft/sources.mk
:
sources = buffered2.c \
buffered.c \
<....>
vrank-geq1.c \
vrank-geq1-rdft2.c
LOCAL_SRC_FILES += $(sources:%=rdft/%)
调用应用程序顶级目录中的ndk-build
脚本,最终应该有两个即用型FFTW3库:
libs/armeabi-v7a/libfftw3.so
libs/armeabi/libfftw3.so
答案 1 :(得分:1)
我目前正在解决类似的问题,但没有显着的结果。
我可以推荐使用经过良好测试的其他库,比如JTransforms(java非常快)或者找到Badlogic KissFFT实现(JNI,大约快2倍,数值不稳定)。
答案 2 :(得分:1)
注意到,在最近的fftw版本中有大量的新目录,包含.c而未在原始的Android.mk中列出,我懒得编写source.mk生成脚本,并用google搜索:< / p>
include $(LOCAL_PATH)/api/sources.mk
感谢Sudhakar Fomra(github上的sfomra),让我的构建在几分钟内完成。
答案 3 :(得分:0)
为Android armeabi-v7a编译fftw3的最佳方法是:
export SYSROOT="$NDK_ROOT/platforms/$TARGET/arch-arm"
export CFLAGS="-I$NDK_ROOT/platforms/$TARGET/arch-arm/usr/include --sysroot=$SYSROOT"
export CPPFLAGS="-I$NDK_ROOT/platforms/$TARGET/arch-arm/usr/include --sysroot=$SYSROOT"
export CC=$($NDK_ROOT/ndk-which gcc)
export LD=$($NDK_ROOT/ndk-which ld)
export CPP=$($NDK_ROOT/ndk-which cpp)
export CXX=$($NDK_ROOT/ndk-which g++)
export AS=$($NDK_ROOT/ndk-which as)
export AR=$($NDK_ROOT/ndk-which ar)
export RANLIB=$($NDK_ROOT/ndk-which ranlib)
./configure --host=arm-linux-androideabi --target=arm-linux-androideabi
make OS=android NDKROOT=$NDK_ROOT TARGET=android-9 ARCH=arm NDKLEVEL=9
答案 4 :(得分:0)
毫不费力地,可以使用http://fftw.org/fftw-3.3.8.tar.gz中的官方CMake脚本为Android构建FFTW:
externalNativeBuild {
cmake {
arguments "-DANDROID_ARM_NEON=TRUE"
arguments "-DCMAKE_BUILD_TYPE=Release"
arguments "-DBUILD_SHARED_LIBS=OFF"
arguments "-DBUILD_TESTS=OFF"
arguments "-DDISABLE_FORTRAN=ON"
arguments "-DENABLE_FLOAT=ON"
targets "fftw3f"
}
}