Skip to content
This repository has been archived by the owner on Jan 6, 2025. It is now read-only.

Commit

Permalink
support api level 16 on android by implementing missing functions in …
Browse files Browse the repository at this point in the history
…android_lts_support library
  • Loading branch information
tanersener committed Apr 26, 2019
1 parent c103dc0 commit a91f51b
Show file tree
Hide file tree
Showing 18 changed files with 208 additions and 50 deletions.
17 changes: 15 additions & 2 deletions android.sh
Original file line number Diff line number Diff line change
Expand Up @@ -181,8 181,8 @@ optimize_for_speed() {
enable_lts_build() {
export MOBILE_FFMPEG_LTS_BUILD="1"

# USING API LEVEL 21 / Android 5.0 (LOLLIPOP)
export API=21
# USING API LEVEL 16 / Android 4.1 (JELLY BEAN)
export API=16
}

reconf_library() {
Expand Down Expand Up @@ -633,9 633,20 @@ do
fi
done

# SAVE API VALUE
export ORIGINAL_API=${API};

for run_arch in {0..4}
do
if [[ ${ENABLED_ARCHITECTURES[$run_arch]} -eq 1 ]]; then
if [[ ( ${run_arch} -eq ${ARCH_ARM64_V8A} || ${run_arch} -eq ${ARCH_X86_64} ) && ${API} < 21 ]] ; then

# 64 bit ABIs supported after API 21
export API=21
else
export API=${ORIGINAL_API}
fi

export ARCH=$(get_arch_name $run_arch)
export TOOLCHAIN=$(get_toolchain)
export TOOLCHAIN_ARCH=$(get_toolchain_arch)
Expand All @@ -652,6 663,8 @@ do
fi
done

export API=${ORIGINAL_API}

rm -f ${BASEDIR}/android/build/.neon 1>>${BASEDIR}/build.log 2>&1
ANDROID_ARCHITECTURES=""
if [[ ${ENABLED_ARCHITECTURES[1]} -eq 1 ]]; then
Expand Down
2 changes: 2 additions & 0 deletions android/app/src/main/cpp/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 1,2 @@
/android_lts_support.o
/libandroidltssupport.a
69 changes: 69 additions & 0 deletions android/app/src/main/cpp/android_lts_support.c
Original file line number Diff line number Diff line change
@@ -0,0 1,69 @@
/*
* Copyright (C) 2008 The Android Open Source Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
* COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/

#include <math.h>
#include <errno.h>
#include <malloc.h>
#include <stdlib.h>

#ifdef __cplusplus
extern "C" {
#endif

#if __ANDROID_API__ < 17

int posix_memalign(void** memptr, size_t alignment, size_t size) {
if ((alignment & (alignment - 1)) != 0 || alignment == 0) {
return EINVAL;
}

if (alignment % sizeof(void*) != 0) {
return EINVAL;
}

*memptr = memalign(alignment, size);
if (*memptr == NULL) {
return errno;
}

return 0;
}

#endif /* __ANDROID_API__ < 17 */

double log2(double x) {
return (log(x) / M_LN2);
}

float log2f(float x) {
return (float) log2((double) x);
}

#ifdef __cplusplus
}; /* end of extern "C" */
#endif
19 changes: 5 additions & 14 deletions android/app/src/main/cpp/mobileffmpeg.c
Original file line number Diff line number Diff line change
Expand Up @@ -47,8 47,8 @@
#include "config.h"
#include "libavcodec/jni.h"
#include "libavutil/bprint.h"
#include "mobileffmpeg.h"
#include "fftools_ffmpeg.h"
#include "mobileffmpeg.h"

/** Callback data structure */
struct CallbackData {
Expand Down Expand Up @@ -104,7 104,9 @@ JNINativeMethod configMethods[] = {
{"getNativeVersion", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_Config_getNativeVersion},
{"nativeExecute", "([Ljava/lang/String;)I", (void*) Java_com_arthenica_mobileffmpeg_Config_nativeExecute},
{"nativeCancel", "()V", (void*) Java_com_arthenica_mobileffmpeg_Config_nativeCancel},
{"getNativeBuildConf", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_Config_getNativeBuildConf}
{"registerNewNativeFFmpegPipe", "(Ljava/lang/String;)I", (void*) Java_com_arthenica_mobileffmpeg_Config_registerNewNativeFFmpegPipe},
{"getNativeBuildDate", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_Config_getNativeBuildDate},
{"setNativeEnvironmentVariable", "(Ljava/lang/String;Ljava/lang/String;)I", (void*) Java_com_arthenica_mobileffmpeg_Config_setNativeEnvironmentVariable}
};

/** Forward declaration for function defined in fftools_ffmpeg.c */
Expand Down Expand Up @@ -494,7 496,7 @@ jint JNI_OnLoad(JavaVM *vm, void *reserved) {
return JNI_FALSE;
}

if ((*env)->RegisterNatives(env, localConfigClass, configMethods, 9) < 0) {
if ((*env)->RegisterNatives(env, localConfigClass, configMethods, 11) < 0) {
LOGE("OnLoad failed to RegisterNatives for class %s.\n", configClassName);
return JNI_FALSE;
}
Expand Down Expand Up @@ -689,17 691,6 @@ JNIEXPORT void JNICALL Java_com_arthenica_mobileffmpeg_Config_nativeCancel(JNIEn
cancel_operation();
}

/**
* Returns build configuration for FFmpeg.
*
* @param env pointer to native method interface
* @param object reference to the class on which this method is invoked
* @return build configuration string
*/
JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_Config_getNativeBuildConf(JNIEnv *env, jclass object) {
return (*env)->NewStringUTF(env, FFMPEG_CONFIGURATION);
}

/**
* Creates natively a new named pipe to use in FFmpeg operations.
*
Expand Down
11 changes: 2 additions & 9 deletions android/app/src/main/cpp/mobileffmpeg.h
Original file line number Diff line number Diff line change
Expand Up @@ -103,17 103,10 @@ JNIEXPORT jint JNICALL Java_com_arthenica_mobileffmpeg_Config_nativeExecute(JNIE
*/
JNIEXPORT void JNICALL Java_com_arthenica_mobileffmpeg_Config_nativeCancel(JNIEnv *, jclass);

/*
* Class: com_arthenica_mobileffmpeg_Config
* Method: getNativeBuildConf
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_Config_getNativeBuildConf(JNIEnv *, jclass);

/*
* Class: com_arthenica_mobileffmpeg_Config
* Method: registerNewNativeFFmpegPipe
* Signature: (Ljava/lang/String)I;
* Signature: (Ljava/lang/String;)I
*/
JNIEXPORT int JNICALL Java_com_arthenica_mobileffmpeg_Config_registerNewNativeFFmpegPipe(JNIEnv *env, jclass object, jstring ffmpegPipePath);

Expand All @@ -127,7 120,7 @@ JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_Config_getNativeBuildD
/**
* Class: com_arthenica_mobileffmpeg_Config
* Method: setNativeEnvironmentVariable
* Signature: (Ljava/lang/String;Ljava/lang/String)I;
* Signature: (Ljava/lang/String;Ljava/lang/String;)I
*/
JNIEXPORT int JNICALL Java_com_arthenica_mobileffmpeg_Config_setNativeEnvironmentVariable(JNIEnv *env, jclass object, jstring variableName, jstring variableValue);

Expand Down
18 changes: 16 additions & 2 deletions android/app/src/main/cpp/mobileffmpeg_abidetect.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 18,7 @@
*/

#include "cpu-features.h"
#include "fftools_ffmpeg.h"
#include "mobileffmpeg_abidetect.h"

/** Full name of the Java class that owns native functions in this file. */
Expand All @@ -26,7 27,9 @@ const char *abiDetectClassName = "com/arthenica/mobileffmpeg/AbiDetect";
/** Prototypes of native functions defined by this file. */
JNINativeMethod abiDetectMethods[] = {
{"getNativeAbi", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeAbi},
{"getNativeCpuAbi", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeCpuAbi}
{"getNativeCpuAbi", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeCpuAbi},
{"isNativeLTSBuild", "()Z", (void*) Java_com_arthenica_mobileffmpeg_AbiDetect_isNativeLTSBuild},
{"getNativeBuildConf", "()Ljava/lang/String;", (void*) Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeBuildConf}
};

/**
Expand All @@ -49,7 52,7 @@ jint JNI_OnLoad(JavaVM *vm, void *reserved) {
return JNI_FALSE;
}

if ((*env)->RegisterNatives(env, abiDetectClass, abiDetectMethods, 2) < 0) {
if ((*env)->RegisterNatives(env, abiDetectClass, abiDetectMethods, 4) < 0) {
LOGE("OnLoad failed to RegisterNatives for class %s.\n", abiDetectClassName);
return JNI_FALSE;
}
Expand Down Expand Up @@ -128,3 131,14 @@ JNIEXPORT jboolean JNICALL Java_com_arthenica_mobileffmpeg_AbiDetect_isNativeLTS
return JNI_FALSE;
#endif
}

/**
* Returns build configuration for FFmpeg.
*
* @param env pointer to native method interface
* @param object reference to the class on which this method is invoked
* @return build configuration string
*/
JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeBuildConf(JNIEnv *env, jclass object) {
return (*env)->NewStringUTF(env, FFMPEG_CONFIGURATION);
}
7 changes: 7 additions & 0 deletions android/app/src/main/cpp/mobileffmpeg_abidetect.h
Original file line number Diff line number Diff line change
Expand Up @@ -65,4 65,11 @@ JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeCpu
*/
JNIEXPORT jboolean JNICALL Java_com_arthenica_mobileffmpeg_AbiDetect_isNativeLTSBuild(JNIEnv *, jclass);

/*
* Class: com_arthenica_mobileffmpeg_AbiDetect
* Method: getNativeBuildConf
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_com_arthenica_mobileffmpeg_AbiDetect_getNativeBuildConf(JNIEnv *, jclass);

#endif /* MOBILE_FFMPEG_ABIDETECT_H */
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 19,8 @@

package com.arthenica.mobileffmpeg;

import android.os.Build;

/**
* <p>This class is used to detect running ABI name using Android's <code>cpufeatures</code>
* library.
Expand All @@ -30,6 32,11 @@ public class AbiDetect {

static {
armV7aNeonLoaded = false;

/* LOAD NOT-LOADED LIBRARIES ON API < 21 */
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
System.loadLibrary("cpufeatures");
}
System.loadLibrary("mobileffmpeg-abidetect");

/* ALL LIBRARIES LOADED AT STARTUP */
Expand Down Expand Up @@ -87,4 94,11 @@ public static String getAbi() {
*/
native static boolean isNativeLTSBuild();

/**
* <p>Returns build configuration for <code>FFmpeg</code>.
*
* @return build configuration string
*/
native static String getNativeBuildConf();

}
34 changes: 22 additions & 12 deletions android/app/src/main/java/com/arthenica/mobileffmpeg/Config.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 20,14 @@
package com.arthenica.mobileffmpeg;

import android.content.Context;
import android.os.Build;
import android.util.Log;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.atomic.AtomicReference;

import static com.arthenica.mobileffmpeg.FFmpeg.getBuildDate;
Expand Down Expand Up @@ -84,15 84,32 @@ public class Config {

Log.i(Config.TAG, "Loading mobile-ffmpeg.");

/* ALL LIBRARIES LOADED AT STARTUP */
Abi cpuAbi = Abi.from(AbiDetect.getNativeCpuAbi());
/* LOAD NOT-LOADED LIBRARIES ON API < 21 */
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
final List<String> externalLibrariesEnabled = getExternalLibraries();
if (externalLibrariesEnabled.contains("tesseract") || externalLibrariesEnabled.contains("x265")) {
// libc _shared.so included only when tesseract or x265 is enabled
System.loadLibrary("c _shared");
}
System.loadLibrary("cpufeatures");
System.loadLibrary("avutil");
System.loadLibrary("swscale");
System.loadLibrary("swresample");
System.loadLibrary("avcodec");
System.loadLibrary("avformat");
System.loadLibrary("avfilter");
System.loadLibrary("avdevice");
}

/* ALL MOBILE-FFMPEG LIBRARIES LOADED AT STARTUP */
Abi.class.getName();
FFmpeg.class.getName();

/*
* NEON supported arm-v7a library has a different name
*/
boolean nativeLibraryLoaded = false;
if (Objects.equals(AbiDetect.getNativeAbi(), AbiDetect.ARM_V7A)) {
if (AbiDetect.ARM_V7A.equals(AbiDetect.getNativeAbi())) {
if (AbiDetect.isNativeLTSBuild()) {

/*
Expand Down Expand Up @@ -570,13 587,6 @@ static String getSystemCommandOutput() {
*/
native static void nativeCancel();

/**
* <p>Returns build configuration for <code>FFmpeg</code>.
*
* @return build configuration string
*/
native static String getNativeBuildConf();

/**
* <p>Creates natively a new named pipe to use in <code>FFmpeg</code> operations.
*
Expand All @@ -597,7 607,7 @@ static String getSystemCommandOutput() {
/**
* <p>Sets an environment variable natively.
*
* @param variableName environment variable name
* @param variableName environment variable name
* @param variableValue environment variable value
* @return zero on success, non-zero on error
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,10 53,12 @@ class Packages {
supportedExternalLibraries.add("libxml2");
supportedExternalLibraries.add("opencore-amr");
supportedExternalLibraries.add("opus");
supportedExternalLibraries.add("sdl2");
supportedExternalLibraries.add("shine");
supportedExternalLibraries.add("snappy");
supportedExternalLibraries.add("soxr");
supportedExternalLibraries.add("speex");
supportedExternalLibraries.add("tesseract");
supportedExternalLibraries.add("twolame");
supportedExternalLibraries.add("wavpack");
supportedExternalLibraries.add("x264");
Expand All @@ -70,7 72,7 @@ class Packages {
* @return enabled external libraries
*/
static List<String> getExternalLibraries() {
final String buildConfiguration = Config.getNativeBuildConf();
final String buildConfiguration = AbiDetect.getNativeBuildConf();

final List<String> enabledLibraryList = new ArrayList<>();
for (String supportedExternalLibrary : supportedExternalLibraries) {
Expand Down Expand Up @@ -261,7 263,11 @@ static String getPackageName() {
}
}

return "min";
if (externalLibraryList.size() == 0) {
return "min";
} else {
return "custom";
}
}

}
3 changes: 0 additions & 3 deletions android/jni/Android.mk
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 14,6 @@ ifeq ($(TARGET_ARCH_ABI), arm64-v8a)
MY_ARCH_FLAGS := ARM64_V8A
MY_ARM_NEON := true
endif
ifeq ($(TARGET_ARCH_ABI), arm64-v8a)
MY_ARCH_FLAGS := ARM64_V8A
endif
ifeq ($(TARGET_ARCH_ABI), x86)
MY_ARCH_FLAGS := X86
endif
Expand Down
Loading

0 comments on commit a91f51b

Please sign in to comment.