This repository has been archived on 2021-04-21. You can view files and clone it, but cannot push or open issues or pull requests.
Files
node-pcsclite/lib/pcsclite.js
Santiago Gimeno 0c5e07e0e5 src: migrate pthreads to uv_threads
- So it can be compatible in every platform supported by libuv.
- Use attached threads instead of detached.
- Remove all CardReader 'status' listeners before emitting the
  'end' event.
2015-05-27 16:09:29 +02:00

138 lines
3.6 KiB
JavaScript

var events = require('events');
var bt = require('buffertools');
/* Make sure we choose the correct build directory */
var bindings = require('bindings')('pcsclite');
var PCSCLite = bindings.PCSCLite;
var CardReader = bindings.CardReader;
inherits(PCSCLite, events.EventEmitter);
inherits(CardReader, events.EventEmitter);
var parse_readers_string = function(readers_str) {
var pos;
var readers = [];
var ini = 0;
while ((pos = bt.indexOf(readers_str.slice(ini), '\0')) > 0) {
readers.push(readers_str.slice(ini, ini + pos).toString());
ini += pos + 1;
}
return readers;
};
module.exports = function() {
var readers = [];
var p = new PCSCLite();
process.nextTick(function() {
p.start(function(err, data) {
if (err) {
return p.emit('error', err);
}
var names = parse_readers_string(data);
var new_names = readers.length === 0 ? names : names.filter(function(name) {
return readers.every(function(reader) {
return reader.name !== name;
});
});
readers = readers.filter(function(reader) {
return names.indexOf(reader.name) !== -1;
});
new_names.forEach(function(name) {
var r = new CardReader(name);
readers.push(r);
r.get_status(function(err, state, atr) {
if (err) {
return r.emit('error', err);
}
var status = { state : state };
if (atr) {
status.atr = atr;
}
r.emit('status', status);
r.state = state;
});
r.on('_end', function() {
r.removeAllListeners('status');
r.emit('end');
});
p.emit('reader', r);
});
});
});
return p;
};
CardReader.prototype.connect = function(options, cb) {
if (typeof options === 'function') {
cb = options;
options = undefined;
}
options = options || {};
options.share_mode = options.share_mode || this.SCARD_SHARE_EXCLUSIVE;
options.protocol = options.protocol || this.SCARD_PROTOCOL_T0 | this.SCARD_PROTOCOL_T1;
if (!this.connected) {
this._connect(options.share_mode, options.protocol, cb);
} else {
cb();
}
};
CardReader.prototype.disconnect = function(disposition, cb) {
if (typeof disposition === 'function') {
cb = disposition;
disposition = undefined;
}
if (typeof disposition !== 'number') {
disposition = this.SCARD_UNPOWER_CARD;
}
if (this.connected) {
this._disconnect(disposition, cb);
} else {
cb();
}
};
CardReader.prototype.transmit = function(data, res_len, protocol, cb) {
if (!this.connected) {
return cb(new Error("Card Reader not connected"));
}
this._transmit(data, res_len, protocol, cb);
};
CardReader.prototype.control = function(data, control_code, res_len, cb) {
if (!this.connected) {
return cb(new Error("Card Reader not connected"));
}
var output = new Buffer(res_len);
this._control(data, control_code, output, function(err, len) {
if (err) {
return cb(err);
}
cb(err, output.slice(0, len));
});
};
// extend prototype
function inherits(target, source) {
for (var k in source.prototype) {
target.prototype[k] = source.prototype[k];
}
}