2017-01-21 12:21:16 -08:00
|
|
|
"use strict";
|
2017-01-18 20:31:53 -08:00
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
const fs = require('fs'),
|
|
|
|
EventEmitter = require('events'),
|
|
|
|
Epoll = require('epoll').Epoll
|
2017-01-18 20:31:53 -08:00
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
const GPIO_ROOT_PATH = '/sys/class/gpio/'
|
2017-01-18 20:31:53 -08:00
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
class Interrupt extends EventEmitter {
|
2017-01-18 20:31:53 -08:00
|
|
|
// bus is i2c-bus bus object
|
2017-01-21 12:21:16 -08:00
|
|
|
constructor(pin_number, opts = {}) {
|
|
|
|
super()
|
|
|
|
this.num = pin_number;
|
|
|
|
this.hook = opts.hook // will be passed back with the emit
|
|
|
|
this.path = GPIO_ROOT_PATH + 'gpio' + this.num + '/'
|
|
|
|
this.edge = opts.edge ? opts.edge : 'falling'
|
|
|
|
this.debounce = opts.debounce ? opts.debounce : 200
|
|
|
|
this.poller = new Epoll(function (err, fd, events) {
|
|
|
|
if (err) { this.emit('error', err) }
|
|
|
|
this.clear()
|
|
|
|
this.emit('fired', this.hook)
|
|
|
|
}.bind(this))
|
2017-01-18 20:31:53 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
init() {
|
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
try {
|
|
|
|
if (fs.existsSync(this.path)) { this.exit() }
|
|
|
|
|
|
|
|
fs.writeFileSync(GPIO_ROOT_PATH + 'export', this.gpio);
|
|
|
|
fs.writeFileSync(this.path + 'direction', 'in');
|
|
|
|
fs.writeFileSync(this.path + 'edge', this.edge);
|
|
|
|
this.valueFd = fs.openSync(this.path + 'value', 'r+'); // Cache fd for performance.
|
|
|
|
|
|
|
|
this.clear();
|
|
|
|
this.start()
|
|
|
|
|
|
|
|
process.on('SIGINT', function () {
|
|
|
|
console.log('\ncleaning up interrupt before exiting')
|
|
|
|
this.exit();
|
|
|
|
})
|
|
|
|
} catch (err) { return Promise.reject(err) }
|
|
|
|
|
|
|
|
return Promise.resolve('interrupt ready')
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
fire(name = 'fired') {
|
|
|
|
this.emit(name, this.hook)
|
2017-01-18 20:31:53 -08:00
|
|
|
}
|
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
clear() {
|
|
|
|
fs.readSync(this.valuefd, null, 0, 1, 0);
|
|
|
|
}
|
|
|
|
|
|
|
|
exit() {
|
|
|
|
if (this.valuefd) {
|
|
|
|
this.stop()
|
|
|
|
fs.closeSync(this.valueFd)
|
|
|
|
}
|
|
|
|
try {
|
|
|
|
fs.writeFileSync(GPIO_ROOT_PATH + 'unexport', this.gpio);
|
|
|
|
} catch (ignore) {}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
start() {
|
|
|
|
this.poller.add(this.valuefd, Epoll.EPOLLPRI);
|
|
|
|
}
|
|
|
|
|
|
|
|
stop() {
|
|
|
|
this.poller.remove(this.valuefd).close();
|
2017-01-18 20:31:53 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2017-01-21 12:21:16 -08:00
|
|
|
module.exports = {
|
|
|
|
Interrupt
|
|
|
|
}
|