首页 > 解决方案 > GPIO 状态转换的回调(中断)子例程中允许和不允许的内容(perl、RPi::WiringPi、Raspberry pi、Raspbian)

问题描述

我正在尝试使用 Pi 上的 GPIO 引脚来连接一些按钮,然后我的软件将响应这些按钮。这是在现有的 Perl 应用程序中添加一些控件,所以我的新工作也在 Perl 中。

真正简单的原型硬件和软件工作;我将引脚配置为输入和上拉模式(并将其接线,以便按下按钮将引脚接地),并建立一个中断程序,事实上,当我按下按钮时,中断程序被调用。所以我实际上可能至少正确安装了各种包和模块。(观察到联系人弹跳;我最终会在软件中处理它。)

然而,当我试图把它提升到一个水平时,我遇到了奇怪的麻烦。我尝试了很多事情,但都以不同的方式失败了。我在这里寻找的是一些关于允许我在中断函数中做哪些事情的附加信息(由 $pin->set_interrupt('main::function_name') 设置)。这称为“中断函数”,也称为“回调”。我怀疑它是否真的在硬件中断级别运行(不认为 Linux 甚至不支持用户中断处理程序!),但通常在这种回调中,有一些硬性规则,或者至少非常强烈的建议,关于你能做什么和不能做什么在那里做,你应该稍后推迟。

但是我找不到的任何文档(当然不是加载的模块上的基本 CPAN 文档或 perldoc)真正告诉我很多关于约束的信息。

例如,我发现对 Log4Perl 记录器的调用在中断函数的早期工作,但不会延迟:-)。我怀疑它们在中断函数中是一个坏主意,而我尝试过的一件事碰巧很幸运,但我可能是错的,并且没有关于允许什么和不允许什么的文档。

有人建议中断函数可能在另一个线程中运行(但这来自底层 WiringPi 库而不是 Perl 包装器,我发现它与未由 Perl 包装器包装的函数有关,所以可能不是)。我的应用程序没有加载线程库(我一直在避免它;正式地“不鼓励”perl 线程),但也许我在更复杂的应用程序中使用的是(我打算将其与使用 MCE,它使用线程或多个分叉进程;但我遇到问题的原型更简单并且没有)。

我也在使用 Class::Tiny; 我似乎可以在中断函数中调用类方法,但一段时间后它变得很奇怪。我目前正在尽可能避免它。

通常你想要做的是,在中断函数中,注意中断发生,然后将事件排队在你的主事件循环中处理,并做一些事情可能会解除该循环的阻塞(比如说一个 condvar 循环等等)。但不知道是否可以在中断函数中安全地访问 MCE::Shared::Condvar。

是否有更多关于某处的中断函数中允许和不允许的信息?那里有更复杂的代码示例(不仅仅是在中断函数中打印一些东西)吗?

标签: perlraspberry-pi

解决方案


推荐阅读