首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >使用Android q ffmpeg拒绝权限“:error=13,权限被拒绝

使用Android q ffmpeg拒绝权限“:error=13,权限被拒绝
EN

Stack Overflow用户
提问于 2020-02-24 14:12:33
回答 7查看 17.1K关注 0票数 25

我想得到的帧从RTSP视频使用ffmpeg。但对于android 10以上版本,我得到的错误如下所示。

代码语言:javascript
复制
 E/FFmpeg: Exception while trying to run: [Ljava.lang.String;@55e447f
java.io.IOException: Cannot run program "/data/user/0/com.example.downloadimagefromurl/files/ffmpeg": error=13, Permission denied
    at java.lang.ProcessBuilder.start(ProcessBuilder.java:1050)
    at java.lang.Runtime.exec(Runtime.java:698)
    at java.lang.Runtime.exec(Runtime.java:563)
    at com.github.hiteshsondhi88.libffmpeg.ShellCommand.run(ShellCommand.java:10)
    at com.github.hiteshsondhi88.libffmpeg.FFmpegExecuteAsyncTask.doInBackground(FFmpegExecuteAsyncTask.java:38)
    at com.github.hiteshsondhi88.libffmpeg.FFmpegExecuteAsyncTask.doInBackground(FFmpegExecuteAsyncTask.java:10)
    at android.os.AsyncTask$3.call(AsyncTask.java:378)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:289)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
    at java.lang.Thread.run(Thread.java:919)
 Caused by: java.io.IOException: error=13, Permission denied
    at java.lang.UNIXProcess.forkAndExec(Native Method)
    at java.lang.UNIXProcess.<init>(UNIXProcess.java:133)

根据@Saurabh Thorat提供的答案,Google不允许应用程序运行/data/user目录中的二进制文件。

据我所知,一个糟糕的解决方案是将compileSdkVersion和targetSdkVersion更改为28或更低,然后重新发布我的应用程序,这是不推荐的。

因此,我也在为未来的版本寻找更可行的解决方案。

任何提示,链接或建议将受到高度赞赏。提前谢谢。

EN

回答 7

Stack Overflow用户

发布于 2020-02-24 14:28:58

从Android Q开始,你不能在你的应用的私有数据目录中执行二进制文件。

来自issuetracker:https://issuetracker.google.com/issues/128554619

在targetAPI >= Q的应用程序数据文件上对数据块exec()所做的更改按预期工作。有关此更改的背景信息,请参阅https://android-review.googlesource.com/c/platform/system/sepolicy/+/804149。对可写应用程序文件调用exec()违反了W^X (https://en.wikipedia.org/wiki/W%5EX),并代表了一种不安全的应用程序实践。可执行代码应始终从应用程序APK加载。

虽然exec()不再对应用程序主目录中的文件起作用,但它仍然支持只读/data/app目录中的文件。特别是,应该可以将二进制文件打包到应用程序的本机libs目录中并启用android:extractNativeLibs=true,然后对/data/app工件调用exec()。https://developer.android.com/ndk/guides/wrap-script#packaging_wrapsh中记录的wrap.sh功能也采用了类似的方法。

此外,请注意,通过exec()执行的可执行文件不会根据Android进程生命周期进行管理,一般来说,不建议在Android应用程序中使用exec()。虽然不是Android文档,但Using "exec()" with NDK详细介绍了这一点。在未来的安卓版本中依赖exec()可能会有问题。

票数 12
EN

Stack Overflow用户

发布于 2020-03-25 13:54:32

仅更改Build.gradle文件上的 targetSdkVersion 29至28并在您的设备上重新安装您的应用程序-临时解决了您的权限问题,因为发布的build on play商店需要targetSdkVersion 29平台,所以我建议您使用此库,它支持目标Sdk 30

票数 8
EN

Stack Overflow用户

发布于 2020-03-12 20:05:25

earlier answer正确地解释了您遇到的问题。这也是去年9月提出的一个open issue,在您正在使用的库的论坛上进行了讨论(从堆栈跟踪中我可以看到)。

为SDK 29编译的解决方案是停止将二进制文件放在/data/目录中,并确保它们在本机libs目录中。这是在非根设备上安装并解压缩APK后无法实现的,因此在准备Android项目时应该正确完成(例如通过gradle设置),并确保在安装时正确解压内容:android:extractNativeLibs=true

在您的示例中,此代码将打包为“assets”的二进制文件移动到用户数据目录中:

https://github.com/WritingMinds/ffmpeg-android-java/blob/master/FFmpegAndroid/src/main/java/com/github/hiteshsondhi88/libffmpeg/FileUtils.java

这是一个安全问题,在可读/可写的位置运行任何可执行文件。我链接到上面的源代码需要删除,取而代之的是打包在/libs中的本机二进制文件。更改更安全,因为应用程序安装目录中的/libs位置是可执行的,但不可写。

总而言之,第三方库需要解决它,或者你可以这样做,并贡献一个拉取请求。或者自己创建fork,然后自己重新编译。

如果你的应用程序在安装后真的下载了内容,并且希望执行任何下载,这仍然是一个问题。据我所知,这在Android10中是不可能实现的。

面向未来的解决方案是停止使用外部二进制文件,并将依赖项编译为NDK项目。他们将需要jni包装器来包装本机代码(需要一些工作)。我知道有个a related project你可以查一下。

票数 6
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/60370424

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档