java - 将大字节数组通过管道传输到 Android 应用程序中的 Process

标签 java android embedded-linux

我正在开发一个项目,当前的结构可以发挥最大作用 意义是将 1.2MB 文件发送到托管 ARM 进程的标准输入。 在Java中,这个进程是用ProcessBuilder创建的, 并尝试写入进程的输出流 os.write(buf) 结果 以下堆栈跟踪表明写入 导致进程/管道终止。 此写入一直适用于较小的缓冲区 100 个字节。

enter image description here

我尝试过使用 Apache 的 IOUtils、BufferedOutputStream、 和 OutputStreamWriter,但它们都会导致进程终止。

我尝试将写入分块以发送 1k 字节 时间如以下代码 fragment 所示。

int chunkSize = 1000, sentBytes = 0, i = 0;
while (sentBytes < b.length) {
    Log.d(TAG, "Writing chunk " + i);
    int sz = sentBytes+chunkSize > b.length ? b.length % chunkSize : chunkSize;
    os.write(b, i*chunkSize, sz);
    os.flush();
    sentBytes += chunkSize; i++;
}

但是,这在崩溃之前只能发送 68k 字节。 我已经运行了多次并且代码始终崩溃 在写入 block 68 时。

enter image description here

我尝试制作一个最小的工作示例 here尝试 来隔离这个问题。然而,这段代码完全 尝试写入 1MB 数据时挂起。 当写入 100 个字节时,此代码可以正确运行。

我不确定我是否正在寻找正确的术语,但是 以下是我找到的一些相关帖子,没有涉及 这个问题。

那么,如何正确地将大(1.2MB)文件写入OutputStream Android Java 中管理的进程? 我还可以尝试哪些其他方法?

我的备份计划是修改子进程以不读取这么多数据 来自stdin,但这种修改并不理想。

最佳答案

先说第二个问题。默认情况下,ProcessBuilder 将安排您的子进程的 stdinstdout 连接到您的程序。您的测试程序生成 cat 并将 1 MB 数据写入其 stdin。但是 cat 的工作是将其 stdin 复制到其 stdout,而您永远不会从其 stdout 中读取数据!一旦内核的管道缓冲区填满,cat 将在尝试写入时阻塞。由于它被阻止,它不再从其 stdin 读取数据,因此您的程序会依次阻塞。

您的原始程序有一个不同的问题:EPIPE 上的写入失败,而不是挂起。正如您所指出的,这意味着您的子进程已终止(或至少已关闭其 stdin)。您的帮助程序进程不知道也不关心您正在使用哪个 Java API:它只是从管道中读取数据,并且 POSIX 管道机制中没有任何内容可以导致管道读取器退出。 (另一方面,如果最后一个读取器消失,则可以通过 SIGPIPE 杀死写入者。)您是否排除了数据内容中的某些内容您'重新发送会导致您的帮助进程退出吗?

关于java - 将大字节数组通过管道传输到 Android 应用程序中的 Process,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26083731/

相关文章:

java - ARCore:如何检测光照不足?

java - 从 ZipInputStream 获取特定文件

java - 如何使用 FileReader 而不是使用 BufferReader

android - 在库中使用外部 google-services.json 文件

android - 滚动到列表末尾

linux-kernel - 在Linux内核空间执行程序

linux-kernel - 哪个驱动程序正在处理我的 IOCTL

operating-system - 如何查找调试信息是否仅包含相对路径或绝对路径?

java - Hibernate 中的表级锁

java - Hibernate 条件查询抛出异常