问题
Just a bit of background, I'm working with a raw data stream in Linux Mint (32 bit). It's from my library ruby-buzz, which reads 24-bit lumps out of the data stream file.
I've just re-installed my laptop with Linux Mint, 32-bit, and suddenly I'm seeing the error Errno::EINVAL: Invalid argument @ io_fread
.
ajfaraday@squishy ~ $ sudo chmod 777 /dev/input/by-id/*
ajfaraday@squishy ~ $ irb
2.2.1 :001 > path = '/dev/input/by-id/usb-Logitech_Logitech_Buzz_tm__Controller_V1-event-if00'
=> "/dev/input/by-id/usb-Logitech_Logitech_Buzz_tm__Controller_V1-event-if00"
2.2.1 :002 > f = File.open(path)
=> #<File:/dev/input/by-id/usb-Logitech_Logitech_Buzz_tm__Controller_V1-event-if00>
2.2.1 :003 > f.read(24)
Errno::EINVAL: Invalid argument @ io_fread - /dev/input/by-id/usb-Logitech_Logitech_Buzz_tm__Controller_V1-event-if00
from (irb):3:in `read'
from (irb):3
from /home/ajfaraday/.rvm/rubies/ruby-2.2.1/bin/irb:11:in `<main>'
2.2.1 :004 > f.read(32)
=> "\xAB>xW\x0E\xDC\x00\x00\x01\x00\xC0\x02\x01\x00\x00\x00\xAB>xW\x0E\xDC\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
On the same system, with the same input device, I saw the issue in /dev/input file created, but contains no data stream
I don't know why I've previously been fine to use tail -f
to watch a raw data stream from the terminal, and why I've previously been able to use file.read(24)
to grab that 24 bit chunk from ruby. Including on an install of Mint. But now I'm unable to do either.
回答1:
I don't fully understand the solution I found, but it will probably help anyone faced with the same problem, so here goes.
It appears to be a consequence of the 32-bit architecture of Linux Mint that it will not allow the file.read
method to work with an argument that's not a power of 2 (e.g. 8, 16, 32). I do not know why this is.
However, re-installing using the 64-bit version of Mint, this works as I was previously seeing on my KDE install (which, in retrospect, was probably a 64-bit architecture).
来源:https://stackoverflow.com/questions/38165055/reading-usb-input-stream-from-ruby