android - 为 Android 上的 MediaStreamer2 控制台应用程序提供 JVM

标签 android c++ c android-ndk video-streaming

我正在为使用 rtp 传输编码视频信号的嵌入式设备开发 Android 固件。底层库是 MediaStreamer2,因为它支持 Android、各种编解码器和 libortp。因此,我将 libmediastreamer 及其依赖项集成到我的固件构建过程中。

作为第二步,我编写了一个简单的 Android 命令行应用程序作为 PoC,它通过网络传输音频或视频。不幸的是,由于以下原因,第一次调用 ms_init() 失败:

bctbx-fatal-Calling ms_get_jni_env() while no jvm has been set using ms_set_jvm()

更深入地研究这个问题,Android 版本的 libmediastreamer 似乎是从 NDK 的角度设计的:它可以作为 Android 应用程序的一部分被调用,因此自动获取对 JVM(DVM?)的引用.不幸的是,这不是我的用例。

我尝试删除依赖项(查询 Sdk 版本、硬件回声消除支持等)但没有成功。所以我的下一个方法是手动启动 VM 并将其传递给库。我试过像这样的 Oracles API:

JNIEnv env;
JavaVM vm;
JavaVMInitArgs vm_args;
JavaVMOption options[4];
options[0].optionString = "-Djava.compiler=NONE";
options[1].optionString = "-verbose:jni"; 
vm_args.version = JNI_VERSION_1_2;
vm_args.options = options;
vm_args.nOptions = 4;
vm_args.ignoreUnrecognized = TRUE;
jint res = JNI_CreateJavaVM(&vm, (void **)&env, &vm_args);

但是应用程序以简单的“中止”退出。不过,我不确定这是否可行,因为它是 Android 和 Dalvik 世界。

有什么建议吗?

最佳答案

可以在 root 和非 root 设备上为 Android 上的 shell 构建可执行文件,请参阅引用资料 How to build an executable for Android shell .

尝试以下代码并使用 NDK 构建它以获得可执行文件:

#include <jni.h>
#include <iostream>
#include <string>
using namespace std;

int main(int argc, char **argv) {

   JavaVMOption jvmopt[1];
   jvmopt[0].optionString = "-Djava.class.path=" + ".";

   JavaVMInitArgs vmArgs;
   vmArgs.version = JNI_VERSION_1_2;
   vmArgs.nOptions = 1;
   vmArgs.options = jvmopt;
   vmArgs.ignoreUnrecognized = JNI_TRUE;

   // Create the JVM
   JavaVM *javaVM;
   JNIEnv *jniEnv;
   long flag = JNI_CreateJavaVM(&javaVM, (void**)
      &jniEnv, &vmArgs);
   if (flag == JNI_ERR) {
      cout << "Error creating VM. Exiting...\n";
      return 1;
   }

   /** ----------------------------------------------
    * Put your own JNI related code from here if any. 
    * -----------------------------------------------
    **/

   javaVM->DestroyJavaVM();
   return 0;
}

检查 <jni.h>关于您可以使用的接口(interface),例如

/*
 * VM initialization functions.
 *
 * Note these are the only symbols exported for JNI by the VM.
 */
jint JNI_GetDefaultJavaVMInitArgs(void*);
jint JNI_CreateJavaVM(JavaVM**, JNIEnv**, void*);
jint JNI_GetCreatedJavaVMs(JavaVM**, jsize, jsize*);

您可以引用以下内容,看看它们是否有帮助:

  1. how-to-create-a-jvm-instance-in-jni
  2. https://calebfenton.github.io/2017/04/05/creating_java_vm_from_android_native_code/

关于android - 为 Android 上的 MediaStreamer2 控制台应用程序提供 JVM,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54804008/

相关文章:

应用程序启动时的 Android 事件处理程序

android - Roboelectic Maven Build 中的 "ant maven-setup"是什么意思?

C++11 类属性作为另一个对象?

c++ - 有指针的计算机实验室

c - %*[^\n] (scanf) 在 c 中如何工作?

android - 将两个 recyclerView 滚动为一个

python - 无法在 macOS 上安装 pybind

c - strtok() 返回奇怪的值和段错误

c - 当函数中的值发生变化时,指针不反射(reflect)变化

android - 在 Okhttp 中处理身份验证