Inappropriate ioctl for device from FileOutputStre

2019-05-20 18:55发布

I have some code that saves some preferences to file using FileOutputStream. It is standard code I've written a thousand times:

FileOutputStream out = new FileOutputStream(file);
try {
    BufferedOutputStream bos = new BufferedOutputStream(out);
    try {
        store(bos, comments);
    } finally {
        bos.close();
    }
} finally {
    out.close();
}

One of our users is reporting the following error on Linux during the close() call.

java.io.IOException: Inappropriate ioctl for device
   at java.io.FileOutputStream.close0(Native Method)
   at java.io.FileOutputStream.close(FileOutputStream.java:341)
   at java.io.FilterOutputStream.close(FilterOutputStream.java:160)

Does anybody know if this ONLY happens when incorrectly launching the JVM with the wrong -d32 or -d64 parameter (like in this question), or is there possibly something else going on?

2条回答
够拽才男人
2楼-- · 2019-05-20 19:19

Java's close() method is a thin wrapper around the OS native close(); it will translate the native error code into an exception.

The linked-to docs are relatively ambiguous about what could cause a close to fail, noting that errors during write may be reported by close, and that "This can especially be observed with NFS...".

So, to debug I'd first look at the name of the file, and where the file is being stored for this particular user. I wouldn't place too much emphasis on non-close()-related hits for "Inappropriate ioctl".

查看更多
老娘就宠你
3楼-- · 2019-05-20 19:37

I am pretty sure you are correct with the 32/64 bit mode idea. We had this issue a couple of years ago working on an embedded device, the error was stemming from a lib that we were using to talk to a pci switch and the library did not support 64 bit ioctls.

My suggestion if you really want to get to the bottom of it and I have used this technique to debug jni code. Set a break point in the java app, then use gdb to attach to the process. You can then set a break point in gdb to watch for the ioctl on the device. See which request is being sent to the device and verify that it is correctly support for that architecture.

If fileoutput stream is reading from a filesystem file and not another type of device file. Then this is probably a problem with selinux, or some kind of virtualization like a chroot environment as in the following link.

This link may point in the right direction. It was a problem with the chroot
http://us.generation-nt.com/answer/sndctl-tmr-timebase-tcgets-help-170073041.html

Also definitely check the jre they are running, is it openjdk or is it sun java? I have had some very odd quirks with the older gcc jdk java and this may explain some of the discrepancies.

查看更多
登录 后发表回答