Permalink
Browse files

Merge pull request #2 from anders94/master

node-spi: added getters / setters and some examples
  • Loading branch information...
2 parents ca6f59e + 6f745be commit 2c643ab09dbf499d46a62b6b5eb177af734f5e4a @RussTheAerialist committed Feb 1, 2013
Showing with 367 additions and 113 deletions.
  1. +107 −42 README.md
  2. +144 −38 spi.js
  3. +105 −27 src/spi_binding.cc
  4. +11 −6 src/spi_binding.h
View
149 README.md
@@ -1,37 +1,37 @@
node-spi
========
-A NodeJS interface to the SPI bus on embedded linux machines.
+A NodeJS interface to the SPI bus typically found on embedded linux machines
+such as the Raspberry Pi.
There is a native interface and a wrapped JS interface with a slightly
better API.
-**THIS CODE IS NOT FINISHED YET, NOTHING IS FUNCTIONING YET!**
-
-*Note: The first version will be blocking. I know this is antithetics to
-the nodejs philosophy, but I think it's important, when dealing with blocking
-interfaces, to get the code working in a blocking manner, and then introduce
-the async calls using eio.*
+*Note: The first version will be blocking. I know this is antithetical to
+the node.js philosophy, but I think its important to get the code working in a
+blocking manner first, and then introduce the async calls using eio.*
Basic Usage
===========
```javascript
-var spi = require("spi");
-
-var MyDevice = new spi.Spi("/dev/spidev1.1", {
- "mode": 0, // Always do mode first if you need something other than Mode 0
- "chip_select": spi.NO_CS
- "max_speed": 1000000, // In Hz
- "size": 8, // How many bits per word
-});
-
-var out_buffer = new Buffer([ 0x23, 0x48, 0xAF, 0x19, 0x19, 0x19 ]);
-
-MyDevice.transfer(out_buffer, outbuffer.Length(),
- function(device, recv_buffer) {
- // Do Something with the data in the recv buffer, if anything exists
-});
+var SPI = require('spi');
+
+var spi = new SPI.Spi('/dev/spidev0.0', {
+ 'mode': SPI.MODE['MODE_0'], // always set mode as the first option
+ 'chipSelect': SPI.CS['none'] // 'none', 'high' - defaults to low
+ }, function(s){s.open();});
+
+var txbuf = new Buffer([ 0x23, 0x48, 0xAF, 0x19, 0x19, 0x19 ]);
+var rxbuf = new Buffer([ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ]);
+
+spi.transfer(txbuf, rxbuf, function(device, buf) {
+ // rxbuf and buf should be the same here
+ var s = "";
+ for (var i=0; i < buf.length; i++)
+ s = s + buf[i] + " ";
+ console.log(s + "- " + new Date().getTime());
+ });
```
How you should **really** use the library
@@ -42,31 +42,66 @@ Ideally, for each SPI device that is being controlled should have it's own
object that implements the protocol necessary to talk to your device so that
the device protocol is defined in one place.
-An example project is
-[node-adafruit-pixel](https://github.com/RussTheAerialist/node-adafruit-pixel)
-which is a node module to control the
-[AdaFruit RGB Pixels](http://www.adafruit.com/products/738). The interface is
-defined in terms of color and pixels, and not in messages being sent via the
-SPI bus, but it uses node-spi to do it's work.
+An example project is [node-adafruit-pixel](https://github.com/RussTheAerialist/node-adafruit-pixel)
+which is a node module to control the [AdaFruit RGB Pixels](http://www.adafruit.com/products/738).
+The interface is defined in terms of color and pixels, and not in messages
+being sent via the SPI bus, but it uses node-spi to do it's work.
Native Api Reference
====================
-This section documents the native api which is defined in module \_spi.node.
+This section documents the native api which is defined in module _spi.node.
This is the interface that the normal Spi interface uses, but having a good
understanding of this part is important, as some people may want to use the
native interface directly.
Creating, Opening, and Closing the device
-----------------------------------------
-**\_spi.Spi constructor** - The constructor takes a single argument, the path
-to the spi dev file in /dev. We do not check that the file exists until you
-call open.
+**\_spi.Spi constructor** - The constructor only requires the path to the spi
+dev file in /dev. Options and a callback are not required but can be specified.
+
+Example:
+```javascript
+var spi = new SPI.Spi('/dev/spidev0.1');
+```
+
+Options can include:
+* mode
+* chipSelect
+* bitsPerWord
+* bitOrder
+* maxSpeed
+* halfDuplex
+* loopback
+
+Example:
+```javascript
+var spi = new SPI.Spi('/dev/spidev0.0', {'mode': SPI.MODE['MODE_0']});
+```
+
+The callback returns a handle to the newly created SPI object. It might be
+handy to .open() it if you set all of your options in one shot.
-**open()** - This function takes no arguments and will open the device, setting
+Example:
+```javascript
+var spi = new SPI.Spi('/dev/spidev0.0', {}, function(s){s.open();});
+```
+
+**open()** - This function takes no arguments and will open the device using
all of the options that were previously set. Once the device is open, we do not
-allow you to change the settings to the device.
+allow you to change the settings on the device.
+
+Example:
+```javascript
+var spi = new SPI.Spi('/dev/spidev0.0', {'mode': SPI.MODE['MODE_0']});
+
+// get/set aditional options
+spi.maxSpeed(20000); // in Hz
+console.log('max speed: ' + spi.maxSpeed());
+
+spi.open(); // once opened, you can't change the options
+```
**close()** - This function should always be called before ending. Right now
the destructor for the underlying C++ class does not call close(), but that
@@ -115,21 +150,51 @@ if you'd like.
Getting and Sending Data
------------------------
+**transfer(txbuf, rxbuf, callback)** - This takes two buffers, a write and a
+read buffer, and optionally a callback. SPI only reads when a byte is written
+so communicaton is usually full duplex.
+
+Exmple:
+```javascript
+var txbuf = new Buffer([ 0x23, 0x48, 0xAF, 0x19, 0x19, 0x19 ]);
+var rxbuf = new Buffer([ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ]);
+
+spi.transfer(txbuf, rxbuf, function(device, buf) {
+ var s = "";
+ for (var i=0; i < buf.length; i++)
+ s = s + buf[i] + " ";
+ console.log(s);
+ });
+```
+
+As a convenience feature, read and write functions pad zeros in the opposite
+direction to make simple read and writes work.
-**transfer()** - This takes two buffers, a write buffer and a read buffer.
-If you only want to do one way transfer, then pass null to that argument. For
-example, writes would look like this:
+**read(buffer, callback)** - Reads as much data as the given buffer is big.
+The results of the read are available in the callback.
+Example:
```javascript
-var buff = new Buffer([0x12, 0x12, 0x12]);
-spi.transfer(buff, null);
+var buf1 = new Buffer(8);
+spi.read(buf1, function(device, buf2) {
+ var s = "";
+ for (var i=0; i < buf.length; i++)
+ s = s + buf[i] + " ";
+ console.log(s);
+ });
```
-Reads would look like this:
+**write(buffer, callback)** - Writes out the given buffer.
+Example:
```javascript
-var buff = new Buffer(8);
-spi.transfer(null, buff);
+var buf = new Buffer([0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0]);
+spi.write(buf, function(device, buf2) {
+ var s = "";
+ for (var i=0; i < buf.length; i++)
+ s = s + buf[i] + " ";
+ console.log(s);
+ });
```
Remember that these native apis are currently blocking. I will update, once I
Oops, something went wrong.

1 comment on commit 2c643ab

Contributor

vicary commented on 2c643ab Apr 8, 2013

wow it's been so much updates since my last fork, thanks for the work.

How do I pull the current version from my fork?

Please sign in to comment.