この記事では,mruby/cのα版をPSoC5 Prototyping Kit(CY8CKIT-059)で動かす手順を示します.
PSoC4 Prototyping Kit(CY8CKIT-049)も同様の手順で可能です.
mruby/cは,実行時に必要な資源が少なくなるようにした mrubyの実装です.64KB以下での動作を想定しています.現在,α版を配布しております.
mruby/c α版の入手については,しまねソフト開発センター(ITOC)のmruby/c の取り組みをご覧ください.
必要なもの
- CY8CKIT-059
- PSoC Creator
- mruby/c α版
- mruby OSS版(mrubyフォーラムからダウンロードできます)
全体の流れ
- 簡単なCのプログラムのプロジェクトを作成する
- 1のプロジェクトにmruby/cを追加する
- mrubyプログラムをコンパイルして,2に組込む
プロジェクト作成
空のプロジェクトを作成します.
もし「Target hardware」に「CY8CKIT-059」が出てこない場合は,「Target device」で「CY8C5888LTI-LP097」を選択します.
PSoC4の場合は「CY8CKIT-049」または「CY8C4247AZI-M485」になります.
次の画面では「Empty Schematic」を選択します.次に,プロジェクト名などを入力します.ここではプロジェクト名を「mrubyc_sample」としています.
LEDを点滅させる
回路図にDigital Output Pinを追加します.
このPinをダブルクリックして,設定します.
- 「Name」を「LED」にする
- 「HW connection」のチェックを外す
ピンを設定する
<プロジェクト名>.cydwr ファイルを開き,LEDのポートを「P2[1]」に設定します.
PSoC4の場合は,LEDのポートは「P1[6]」になります.
ビルドする
ここでプロジェクトをビルドします.
ビルドすることで,先ほど設定したLEDの出力に関するコードが自動生成されます.
Cプログラムの作成
main.cのmain関数を次のように作成します.
int main()
{
CyGlobalIntEnable; /* Enable global interrupts. */
/* Place your initialization/startup code here (e.g. MyInst_Start()) */
for(;;)
{
/* Place your application code here. */
LED_Write(1);
CyDelay(200);
LED_Write(0);
CyDelay(200);
}
}
実行
ビルドを行い,[Debug]-[Program]でボードに書き込まれます.ボード上のLEDが点滅すればOKです.
mruby/c のファイルをコピーする
mruby/c α版を解凍して得られる srcフォルダ内の以下のすべてのファイル(xxx.cとxxx.h)を,PSoC Creatorのプロジェクトフォルダ(main.cがあるフォルダにコピーします).
プロジェクトにファイルを追加する
[Project]-[Existing Item...]で,mruby/c α版のファイル(xxx.c)を追加します.複数のファイルを選択して,一度に追加できます.
メソッドの追加
Cのプログラムで使用したLED_Write関数とCyDelay関数を,mrubyから利用できるようにします.Objectクラスにそれぞれのメソッドを追加します.
class.cファイルを開き,以下を追加,修正します.
#include "LED.h"
#include "CyLib.h"
mrb_value c_led(struct VM *vm, mrb_value v)
{
LED_Write( v.value.i );
return v;
}
mrb_value c_delay(struct VM *vm, mrb_value v)
{
CyDelay(v.value.i);
return v;
}
static void mrb_init_class_object(void)
{
// Class
static_class_object = mrb_class_alloc("Object", -1);
// Methods
mrb_define_method(static_class_object, "led", c_led);
mrb_define_method(static_class_object, "delay", c_delay);
}
mrb_init_class_object関数内のmrb_define_method関数により,Cの関数とmrubyのメソッドを対応付けます.
mrubyプログラムの作成
次のmrubyのプログラムを sample.rb として作成します.Cで作ったプログラムと違うタイミングでLEDが点滅します.
led 1
delay 100
led 0
delay 900
mrbcによるコンパイル
sample.rb を mruby(OSS版)でコンパイルして sample.c を作成します.sample.cをPSoCのプロジェクト内のmain.cと同じフォルダにコピーしておきます.
mrbc -E -Bary sample.rb
main.c を書き換え,Cからmrubyプログラムを呼び出す
main.cに以下を追加します.
#include "vm.h"
#include "load.h"
#include "errorcode.h"
#include "static.h"
#include "sample.c"
mrubyc関数を追加します.
int mrubyc(void)
{
struct VM *vm;
init_static();
vm = vm_open();
if( vm == 0 ){
printf("VM open Error\n");
return -1;
}
int ret = loca_mrb_array(vm, ary);
if( ret != NO_ERROR ){
printf("MRB Load Error (%04x_%04x)\n", ret>>16, ret&0xffff);
return -1;
}
vm_boot( vm );
int keep_execute = 1;
while( keep_execute ){
if( vm_run_step(vm) < 0 ){
keep_execute = 0;
}
}
vm_close( vm );
return 0;
}
int main()
{
CyGlobalIntEnable; /* Enable global interrupts. */
/* Place your initialization/startup code here (e.g. MyInst_Start()) */
for(;;)
{
/* Place your application code here. */
mrubyc();
}
}
ビルドと実行
ビルドを行い,[Debug]-[Program]でボードに書き込まれます.ボード上のLEDが点滅すればOKです.
少々長い説明となりましたが,以上で mruby/c α版を PSoC5で動かすことができます.