我有一个设备连接到树莓派。 Pi正在运行ARCH Linux。 该设备通过USB与Pi通信。 该设备必须通过一个脉冲打开和closures,我有一个继电器控制,从皮,导致这个脉冲。 不过,我永远无法确定设备是开始还是closures。
在我的代码中,我切换继电器,然后推测性地调用设备上的open()(标志为O_RDWR | O_NOCTTY)。 问题是,如果我这样做,当设备closuresopen()调用挂起。 我已经尝试了等待1秒后切换,以解决事情,但没有帮助。 我曾尝试在open()调用之前调用stat(),但是这总是返回零(因此,就stat()而言,设备在那里)。 我已经尝试在open()调用中指定O_NON_BLOCK,但是这会导致它始终失败。
任何人都可以build议(一)我做错了什么或(二)一个可靠的方法呢?
如果USB枚举,则可以确定设备已通电。 您可以使用libudev查找USB枚举设备的列表,并检查您的设备是否在列表中。
命令行“lsusb”这样做。 所以,如果你需要一个如何使用libudev的例子,那么你可以阅读lsusb源代码( https://github.com/gregkh/lsusb )。
如果你能确定设备最终会打开,阻塞open()
(“挂起”)实际上可能是你想要的! 当你的设备启动时, open()
的调用将会返回,希望成功。
stat()
调用只是检查设备特殊文件是否在那里。 它不能告诉你是否有任何东西在倾听。
一种可能的方法是使用O_NONBLOCK
在指数回退循环中open()
。
根据你的意思是“通过USB通信”,你可能想要使用libusb 。 如果它只是一个USB串行端口,那么包装open()
可能是最简单的。
目前还不清楚你已经做了什么来获得一个设备文件,保持断开连接。
通常的方法是使用hotplug
+ udev
来创建(和删除)设备符号链接,然后只有在插入设备时才有专用文件。
以下所有帮助人员的感谢,快速回答是在我的.rules文件中包含一个“删除”操作,以便与现有的“添加”操作一起使用。 所以在我拥有的文件中:
ACTION=="add", ATTRS{interface}=="Pololu Orangutan X2 Serial Adapter", MODE="7777", SYMLINK+="OrangutanUSB"
…给我一个/ dev / OrangutanUSB设备,我已经包含了一个新的行:
ACTION=="remove", ATTRS{interface}=="Pololu Orangutan X2 Serial Adapter", MODE="7777", SYMLINK-="OrangutanUSB"
…使操作系统在断电时删除/ dev / OrangutanUSB设备。 这样,open()调用在设备不在时正确地失败,而不是挂起。
最终,我应该做的是检查设备是枚举,而不是期待open()失败,但是可以等到我有时间了。 现在我的代码按照最初的设计工作。