我使用NDK将FFMpeg 2.1移植到Android,我编写了一个JNI函数来初始化视频。
以下是此C函数的代码:
JNIEXPORT int JNICALL Java_com_media_ffmpeg_FFMpeg_naInit(JNIEnv *pEnv, jobject pObj, jstring pfilename) {
gVideoFileName = (char *) (*pEnv)->GetStringUTFChars(pEnv, pfilename, NULL);
__android_log_print(ANDROID_LOG_INFO, TAG, "Init %s\n", gVideoFileName);
avcodec_register_all();
__android_log_print(ANDROID_LOG_INFO, TAG, "avcodec_register_all\n");
av_register_all();
__android_log_print(ANDROID_LOG_INFO, TAG, "av_register_all\n");
VideoState *vs;
__android_log_print(ANDROID_LOG_INFO, TAG, "VideoState var\n");
vs = malloc(sizeof (VideoState));
memset(vs, 0, sizeof(VideoState));
__android_log_print(ANDROID_LOG_INFO, TAG, "malloc\n");
gvs = vs;
__android_log_print(ANDROID_LOG_INFO, TAG, "VideoState\n");
//open the video file
avformat_open_input(&vs->pFormatCtx, gVideoFileName, NULL, NULL);
__android_log_print(ANDROID_LOG_INFO, TAG, "open_input\n");
//retrieve stream info
avformat_find_stream_info(vs->pFormatCtx, NULL);
__android_log_print(ANDROID_LOG_INFO, TAG, "find_stream_info\n");
//find the video stream
AVCodecContext *pcodecctx;
//find the first video stream
vs->videoStreamIdx = -1;
__android_log_print(ANDROID_LOG_INFO, TAG, "before loop\n");
AVCodec *pcodec;
vs->videoStreamIdx = av_find_best_stream(vs->pFormatCtx, AVMEDIA_TYPE_VIDEO, -1, -1, &pcodec, 0);
__android_log_print(ANDROID_LOG_INFO, TAG, "after loop. %d\n", vs->videoStreamIdx);
//get the decoder from the video stream
pcodecctx = vs->pFormatCtx->streams[vs->videoStreamIdx]->codec;
__android_log_print(ANDROID_LOG_INFO, TAG, "stream selected %d, %d\n", pcodecctx != NULL ? 1 : 0, pcodecctx->codec_id);
pcodec = avcodec_find_decoder(pcodecctx->codec_id);
__android_log_print(ANDROID_LOG_INFO, TAG, "find_decoder\n");
//open the codec
avcodec_open2(pcodecctx, pcodec, NULL);
__android_log_print(ANDROID_LOG_INFO, TAG, "open2\n");
return 0;
}
当我从我的Java代码执行此函数时,永远不会显示日志find_decoder
(在调用函数avcodec_find_decoder
之后)。
一切正确:指针的值正确,pcodecctx->codec_id
的值等于 28 。
但是当avcodec_find_decoder
没有更多时,就像崩溃一样,我没有更多的日志。
使用和初始化FFMpeg时,我做错了什么?
PS:在此之前,而不是拨打malloc
,然后memset
我打电话给av_mallocz
,但此时我也遇到了崩溃,并用{替换了此来电{1}}和malloc
修复了崩溃。
修改
我使用此脚本构建了memset
:
FFMpeg
编辑2
以下是库构建配置的输出
#!/bin/bash
NDK=/Users/me/android-ndk
SYSROOT=$NDK/platforms/android-8/arch-arm/
TOOLCHAIN=$NDK/toolchains/arm-linux-androideabi-4.6/prebuilt/darwin-x86_64
function build_one
{
./configure \
--prefix=$PREFIX \
--disable-shared \
--enable-static \
--disable-doc \
--disable-ffmpeg \
--disable-ffplay \
--disable-ffprobe \
--disable-ffserver \
--disable-avdevice \
--disable-doc \
--disable-symver \
--cross-prefix=$TOOLCHAIN/bin/arm-linux-androideabi- \
--target-os=linux \
--arch=arm \
--enable-cross-compile \
--sysroot=$SYSROOT \
--extra-cflags="-Os -fpic $ADDI_CFLAGS" \
--extra-ldflags="$ADDI_LDFLAGS" \
$ADDITIONAL_CONFIGURE_FLAG
make clean
make
make install
}
CPU=arm
PREFIX=$(pwd)/android/$CPU
ADDI_CFLAGS="-marm"
build_one