我目前正在开发一个使用 Android 的VpnService
. 在性能测试期间,我发现FileInputStream
我在FileDescriptor
返回的establish()
方法上创建的读取速度很慢。我的工作代码片段如下所示。
private val vpnIf0 = FileInputStream(fd)
suspend fun readVpnIf0(): IPDatagram = withContext(Dispatchers.IO) {
val bytes = ByteArray(BUFFER_SIZE)
val count = vpnIf0.read(bytes)
return@withContext IPMarshaller.marshal(bytes, count)
}
为了优化代码,我进行了如下封装FileInputStream
,BufferedInputStream
保持其他所有内容相同。
private val vpnIf0 = BufferedInputStream(FileInputStream(fd))
但是现在我的读取方法已经停止工作,这是我得到的错误。
Caught java.io.IOException: Invalid argument
at java.io.FileInputStream.available0(Native Method)
at java.io.FileInputStream.available(FileInputStream.java:389)
at java.io.BufferedInputStream.read(BufferedInputStream.java:355)
at java.io.FilterInputStream.read(FilterInputStream.java:107)
.txt
只是为了确保我没有做任何不正确的事情,我尝试了使用文件和 a完全相同的读取方法,BufferedInputStream
它就像一个魅力。在进一步检查FileInputStream
实现后,我在方法附近看到了一些注释available()
,如下所示。在我看来,Android 使用的版本似乎比标准 JDK 稍有修改。
// BEGIN Android-changed: available() implementation changed from bare native.
public int available() throws IOException {
// Android-added: close() check before I/O.
if (closed) {
throw new IOException("Stream Closed");
}
return available0();
}
private native int available0() throws IOException;
// END Android-changed: available() implementation changed from bare native.
注意:我拥有的用例在 Android 世界中是一个BufferedInputStream
过大的用例。这里,是一个虚拟网络接口。FileInputStream
FileDescriptor
FileDescriptor
/dev/tun0
问题:
- 我的理解是否存在差距,根本不可能将 a 包裹
BufferedInputStream
在 a上?FileDescriptor
我还没有在 JVM 上尝试过同样的方法。 - 或者这是 Android 特有的细微差别?在这种情况下,如何克服这个问题并确保缓冲读取。
任何帮助深表感谢!