BeagleBone Blackにnode.jsを入れてJavaScriptからLチカ (on Ubuntu)

Ubuntu 14.04を入れたBeagleBone Blackにnode.jsを入れて、JavaScriptでGPIOやI2Cを制御できる開発環境を整えました。

デフォルトのAngstromに入っている BoneScript というツールを導入することにしましたがかなり手こずりました。これから作業する方の参考になればと思います。

スポンサーリンク
レクタングル(大)広告

セットアップ手順

Node.jsのインストール

BoneScript はnode libraryなので、実行環境としてNode.jsが必要です。まずはNode.jsのインストールから。

Node.jsはapt-getでインストールが可能ですが、標準リポジトリから取得すると少し古いバージョンになるようです。今回は非公式リポジトリ(PPA)から最新版を取得することにしました。

リポジトリの追加には add-apt-repository コマンドを使いますが、このコマンドは標準ではインストールされていません。このコマンドが含まれる software-properties-common というパッケージを先にインストールします。

$ sudo apt-get update
$ sudo apt-get install -y software-properties-common
$ sudo add-apt-repository ppa:chris-lea/node.js
# リポジトリを追加したら再度update
$ sudo apt-get update

そしてNode.jsをインストール。

$ sudo apt-get install -y nodejs

バージョン確認。

$ node --version
v0.10.37

これでNode.jsのインストールは完了。

ちなみに、apt-getで nodejs パッケージをインストールすると、実行ファイルは /usr/bin/nodejs という名前で作成されます。インストール方法によっては、node というコマンド名で実行できるようにするために update-alternatives コマンドでシンボリックリンクを張る必要がある様ですが、今回の方法ではインストールと同時に /usr/bin/node から nodejs へリンクが張られていました。

BoneScript のインストール

続いて BoneScript のインストールです。

BoneScript は npm を使ってインストールします。npm は Node.js のモジュールを管理するためのツールです。Ruby で言うところの gem のようなものでしょうか。

npm は Node.js をインストールすると一緒に入ります。

$ npm -v
1.4.28

でバージョンが表示されれば問題ありません。

jadonk/bonescript を参考に、以下のように実行します。

# 前準備
$ sudo apt-get install -y python-setuptools python2.7-dev
$ wget -c https://raw.github.com/RobertCNelson/tools/master/pkgs/dtc.sh
$ chmod +x dtc.sh
$ ./dtc.sh

# npm で BoneScript をインストール
$ sudo TERM=none npm install -g bonescript

これで BoneScript がインストールされました。

beagleboard.orgから持ってきたデモコード使って動作確認してみます。任意のディレクトリに、test.js という名前で以下のコードを保存。

# オンボードのUSR3 LEDを0.5秒間隔で10秒間点滅
var b = require('bonescript');
var led = "USR3";
var state = 0;

b.pinMode(led, b.OUTPUT);
toggleLED = function() {
    state = state ? 0 : 1;
    b.digitalWrite(led, state);
};

timer = setInterval(toggleLED, 500);

stopTimer = function() {
    clearInterval(timer);
    console.log('finish');
};

setTimeout(stopTimer, 10000);

node からこのスクリプトを実行します。デバイスへのアクセスにroot権限が必要なはずなのでsudo付きで実行。

$ sudo node test.js

module.js:340
 throw err;
 ^
Error: Cannot find module 'bonescript'
 at Function.Module._resolveFilename (module.js:338:15)
 at Function.Module._load (module.js:280:25)
 at Module.require (module.js:364:17)
 at require (module.js:380:17)
 at Object.<anonymous> (/home/user/test.js:1:71)
 at Module._compile (module.js:456:26)
 at Object.Module._extensions..js (module.js:474:10)
 at Module.load (module.js:356:32)
 at Function.Module._load (module.js:312:12)
 at Function.Module.runMain (module.js:497:10)

requireしたbonescriptが見つからないと言われました。

ちょっといろいろ確認してみます。

# npmのglobalでのインストール先を確認
$ npm root -g
/usr/lib/node_modules

# ディレクトリの中身確認
$ ls /usr/lib/node_modules
bonescript  npm
# ↑ ちゃんといる

# 環境変数NODE_PATH確認
$ echo $NODE_PATH
/usr/lib/nodejs:/usr/lib/node_modules:/usr/share/javascript
#               ↑ ちゃんといる

# nodeのruntimeのNODE_PATHを確認
$ sudo node
> process.env.NODE_PATH
undefined  # NODE_PATHが空

どうやら環境変数NODE_PATHがnodeの実行時に空になっているため、/usr/lib/node_modules 以下のライブラリが見つからない様です。

更に調べたところ、sudo を介してコマンドを実行した場合、デフォルトでは実行したシェルの環境変数は引き継がれないとのこと。なんという初歩的ミス。(昔からそんな仕様だっただろうか?)

/etc/sudoers を編集して、NODE_PATH を引き継ぐよう修正。

$ sudo visudo
#
# This file MUST be edited with the 'visudo' command as root.
#
# Please consider adding local content in /etc/sudoers.d/ instead of
# directly modifying this file.
#
# See the man page for details on how to write a sudoers file.
#
Defaults env_reset
Defaults mail_badpass
Defaults secure_path="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/s
bin:/bin"
Defaults env_keep += "NODE_PATH"  # <= この行を追加
   :

再度実行してみる。

$ sudo node test.js

error: Unable to find LED: usr3
error: Unable to find gpio: /sys/class/leds/beaglebone::usr3/brightness
error: Unable to write to /sys/class/leds/beaglebone::usr3/brightness
error: Unable to write to /sys/class/leds/beaglebone::usr3/brightness
   :
finish

先に進みましたが、なにやらエラーが出まくっています。

調べまわった結果衝撃の事実が。何と BoneScript は 3.8系kernelでないと動作しないらしい。このボードに入れたUbuntu 14.04のkernelは3.14。これが原因っぽいです。

ただ、BoneScript をベースにより改良された OctalBoneScript というのが開発されている模様。これならUbuntu 14.04でも動作し BoneScript との互換性もあるとのことなので、これを入れてみることにします。

OctalBoneScript のインストール

先ほどインストールした BoneScript を削除しておきます。

$ sudo npm uninstall -g bonescript

続いて OctalBoneScript をインストール。

$ sudo TERM=none npm install -g octalbonescript

先ほど作成したtest.jsは一行だけ修正。requireを ‘bonescript’ から ‘octalbonescript’ に変更します。

var b = require('octalbonescript');
    :

実行してみるがダメ。

$ sudo DEBUG=bone node test.js
 bone is_ocp() = /sys/devices/ocp.3 +0ms
 bone is_cape_universal() = /sys/devices/ocp.3/cape-universal.61 +41ms
 bone Using Universal Cape interface +18ms
 bone Enabling analog inputs +113ms
 bone load_dt_sync(cape-bone-iio) +11ms
 bone onFindCapeMgr: path = null +3ms

/usr/lib/node_modules/octalbonescript/lib/bone.js:230
        throw new verror(err, 'Unable to read from CapeMgr slots');
              ^
VError: Unable to read from CapeMgr slots: ENOENT, no such file or directory 'null/slots'
    at onReadSlots (/usr/lib/node_modules/octalbonescript/lib/bone.js:230:23)
    at readSlots (/usr/lib/node_modules/octalbonescript/lib/bone.js:224:13)
    at onFindCapeMgr (/usr/lib/node_modules/octalbonescript/lib/bone.js:214:13)
    at Object.module.exports.load_dt_sync (/usr/lib/node_modules/octalbonescript/lib/bone.js:204:9)
    at Object.module.exports.enable (/usr/lib/node_modules/octalbonescript/lib/analog.js:12:14)
    at Object.<anonymous> (/usr/lib/node_modules/octalbonescript/index.js:44:15)
    at Module._compile (module.js:456:26)
    at Object.Module._extensions..js (module.js:474:10)
    at Module.load (module.js:356:32)
    at Function.Module._load (module.js:312:12)

CapeMgr がらみでエラーが出ている模様。

前述の参考サイトでは、”error: CapeMgr not found: undefined” というログが出るものの、LEDの動作自体はうまく行っているとのこと。

よくよく見てみると、あちらは

OctalBoneScriptのバージョンは0.4.12です。

こちらは、

$ npm list -g octalbonescript
/usr/lib
+-- octalbonescript@1.0.1

バージョンが違う!

0.4.12 を入れなおしてみます。

$ sudo npm uninstall -g octalbonescript
$ sudo npm install -g octalbonescript@0.4.12

今度こそ!

$ sudo node test.js
error: CapeMgr not found: undefined
finish

CapeMgrのエラーログは出ているものの正常に実行が完了しました。LEDも期待通り点滅していました。

これにて目的達成です。

スポンサーリンク
レクタングル(大)広告
レクタングル(大)広告

この記事をシェア!

このブログをフォロー!