lynxeyedの電音鍵盤

MBDとFPGAと車載で使うデバイスの備忘録

RODSZEPTA進捗状況(その1)

基板到着

エナジーハーベストイメージセンサボードRODSZEPTAの基板が到着しました。
f:id:Lynx-EyED:20140103102024j:plain


PCBはDesignSparkPCB v.5.1で作成、ViewMate Proで面付けしています。
おもて
f:id:Lynx-EyED:20140103102113j:plain

うら
f:id:Lynx-EyED:20140103102441j:plain
シルクもスルーホールもそこそこ奇麗。
部品もSRAM以外は届いているので試作してみようと思います。

省電力イメージセンサボードを作る

事の発端

今年の初めに友人と天王寺ミオで、
こんな↓ラジコンにラインスキャン乗せて映像撮ったら面白そうだねという会話

でも大容量Li-PO電池もたないといけないかも、ついでに重くなるから出力上げないと、という話をしてたときに、

「振動で発電すれば電池要らないんじゃね?」

ということになり、作ってみるかと。
その後、雑事に忙殺されてなかなか暇が取れませんでしたが思い出したように作ってみました。振動のみで発電するのは難しいことが分かったので、一次電池との組み合わせにしました

ボード外形

f:id:Lynx-EyED:20131221152047p:plain
・エナジーハーベストイメージセンサ制御ボード "RODSZEPTA (ラセタ)"
プロセッサ:NXP LPC800シリーズ
コプロ:Altera MAX V CPLD 5M570ZT

「勝手にAltera30周年記念祭り」と称してのAlteraデバイスの採用ですが、Avalon-MM MasterBridgeと外部マイコンの組み合わせは仕事でも重宝しています。今回もこれを前提にシステムを設計しています。
イメージセンサと振動発電用ピエゾフィルムは交換可能なように別基板でマウントする方式です。
イメージセンサ、コプロは必要なときだけ起動し、撮影が終わったら省電力モードに。
プロセッサはタイマで必要なときに起床します。

基板おもて面
f:id:Lynx-EyED:20131221152304p:plain

基板うら面(表面からの透過)
f:id:Lynx-EyED:20131221152323p:plain
試作は2層、デバッグ終わり次第4層の基板で製作する予定です。
週明けに発注すれば、年明けには来るかな?


職を選ぶということと難儀

過去の話をば

技術的なことから少しだけ離れた記事ですが、よく同じ研究室やサークルだった愛すべき(笑)後輩たちから聞かれるのでここで参考がてら私の話をしましょう。

まず
(1) 今何してるの
溶接、車載機器の開発をする会社の画像処理担当 兼 車載電装事業部長

アクセサリ(カーナビ、カーオーディオ)からASR(スリップ抑制)のための画像処理による運転支援。主に後者の開発が部署のメインです。またタイヤ成分の化学分析も行います。
悪環境な場面で活躍する車載電装が得意なことから、風雨にさらされやすい、街路樹などのLED電飾の依頼もあり今年は3箇所での設計をしています。LEDの点灯パターンを人の流量や挙動で変えたりと、どこかに画像処理が入ってたりします。


(2) そこに至るようになった経緯は

  1. 液晶ドライバが当時世界の80%以上のシェアをもっていた某ファブレス
  2. カーナビで有名な某社
  3. よくわからん迷走してたFPGAとかマイコンとかの謎設計屋
  4. 謎代理店

1,2は同時にやっていました。というか2の会社に1の部門がやってきたわけですが、半年スパンで行ったりきたりしてました。
その部門はリーマンショック、震災と続いたのが影響して部門としては解散してしまいましたが、いまでもお仕事を頂いたりします。(この記事を書いてる時点でも1件頂いてます。ありがとうございます)

3. の会社。ここには正直難儀しました。

(i) 当日になるまで何するか決まってない。社長の気まぐれで始まる
(ii) 言ったことを次の瞬間に撤回、やっぱり別のことをやれと言い出す
(iii) しばらくしたら「アレどうなった?」と撤回前の件の進捗を聞く(当然やってない)
(iv) わめきだす。

さて対策を練るわけです。たぶんぼくの仕事の仕方が悪かったのでしょう。次の日も前日のことを忘れて同じパターンで始まります

(i) 当日になるまで何するか決まってない。社長の気まぐれで始まる
(ii) 言ったことを次の瞬間に撤回、やっぱり別のことをやれと言い出す
(iii) 撤回前の件と撤回後の件、そのプロセスに必要な要素を見つけ、どこから最優先にすべきか聞く
(iv) 返事「全部」
(v) 「全部」の真意を聞く
(vi) わめ(ry


コントです。お笑いやりにここに来たつもりはありません。
だいたい、優先度を聞いて「全部」という返事はなんですか、組み込みRTOSだってそんなのディスパッチ処理しないでしょう。
で、わめいたり、嫌味をならべたてて騒ぐわけです。40歳目前のオトナが何をしてるんだ。



こっちも仕事中は録音機を四六時中作動させるようになりました。*1
理由はメモするな、といわれたので思い出せなくなると困るからですが、今録音聞き直したら、院時代の研究内容を聞いてそれをバカにしたりなどしてましたね。技術士の倫理規範を逸脱した行為です。


複数のタスクがある場合はスケジューリングをするのは当然です。


この社長、昼過ぎに出社して、3時過ぎに帰る。
まぁ別にそれは1,2の職場でもあった事のなので別にかまわないでしょう。外部の仕事もあるはずです。仕事と金とってくるのが仕事です。

が、家に帰って夜中に起きて、散々スタッフにメール出して、真夜中に反応なくてイラついたのか知りませんが「明日AM9:30までに仕上げてください」ってそれどうなんですか。


はー。スカイプID教えなくてよかった。夜中にかかってくるぞ(笑


計画性のなさは仕事中にもよく現れました。あるプログラムを共同で作る必要がありました。gitもsvnも使わないとか言い出すわけです。
まぁいいでしょう。開発は2,3人です。diffとって慎重にやればできなくはないでしょう。

とおもったら、目で見て判断してただけだったようです。私の作業全部ぶっつぶれてました。

そんなわけのわからんもの使えるか、とでもいいたかったようですがやってることが訳分からん。
それの繰り返し。いい加減苦言を呈したところ、「技術がないものがいわゆる便利ツールにたよるのは御法度」などとのたまう。

まぁいいでしょう。向こうも僕に言いたいことは山ほどあるでしょう。

さて、とあるとき、AndroidWindows Phone(iOSはJS関連の制約でやめたと記憶)でのサービスを提供するという話になったときがあり、端末側のアプリを担当することになっていました。
当時はAndroid StudioもありませんでしたのでEclipse for JavaやVS、Blenderxnaをインストールするわけです。


その後、別の案件が舞い込んできて2ヶ月ほど離れていましたが、その後そのPCの上記インストール物をみて「会社で遊ばないでください」


何いってんだホント。。。


Androidアプリが完成したときにもうこれ以上やりたくない。元気があるうちにここから去りたい、と心底思っていました。
そのころ、胃に穴があくことが度々あり、医者に20代の今はいい、40代以降になったときの癌の確率が大幅に上がる、いい加減身の振り方を考えろ。と助言をされていました。
また結婚を控えていて、これも少なからぬストレスにはなっていたと思います。

大幅なモチベーションの低下は仕事にも現れるわけで、当然できたことすら出来なくなっていくのを実感しました。
数社から(1,2含む)、「来いよ。待ってる」というオファがあったこともあり、会社都合によるドロップアウトをしました。

そして

で、就職活動を控えている後輩たちと、面接を控えてる皆さん。こんな脅しの文章書いて申し訳ない。
でも入ってみないと分からないのは事実です。面接官だって採用してしばらくたたないとその人が有用かどうか分からないはず。裏返せば、みんなも社内の風潮や面子を知りえることなどできない。
多くの約束をせよ。だがそれを果たすな。これが君主として振舞える条件である ― ナポレオン・ボナパルト (が言ったとされている)

ボーナス出る出るとか、待遇上がるよ、などとうそにならない程度にほのめかすと社員はがんばる、上手に半殺しにしておけ的な内容が「経営の上手な社長になるには」みたいな意識高い()啓蒙本に書いてありますね。なんなんですかねこれ。


ただ、言えることは「まじめ」の定義を曲じまげて皆さんに仕事を強要する組織にいる必要はありません。それこそ不真面目な組織なのです。

必ずその者たちは「常識」という言葉を使ってくるでしょう。なんですかそれは。
「説明できないけど、俺がお前たちにやらせたいことをお前の良心に訴えて無理やりやらせる口実」くらいに思っておいたほうがよいです。


お前は技術がない、お前は常識がない、お前は(ry

まぁ耳にタコができるくらいききましたわ。自分が知らないことを提示される焦りなのか知りませんが…これ、新人を蹴落とす洗礼のようですね。


看過できなくなる前に相談すべきと思う。研究室の教授、先輩、もし親がご健在なら親(もちろん、引退されてる方が多いでしょう。情勢は今と異なるので参考程度に)相談すべきです。
どこかで答えが返ってくるはず。後輩のみなさん、わたしも協力できるならその一助を担おうと思います。


今に至るにはもうワンステップあります、その話はまた別のときに。

*1:当然ですが、今も会議や商談では必ず録音します

PSoC4 Pioneer Kitでtelnet

何か作ろう

PSoC4 Pioneer KitキャンペーンPSoC 4 Pioneer Kitキャンペーン PSoC 4でデザインしよう!使ってみたいデザイン案を投稿して、無償でキットをゲット!の応募に当選しちゃいました。
f:id:Lynx-EyED:20131019230059j:plain
ありがとうございます!!(中野の方角向きながら

Cortex-M0ということで、すこし遊べるでしょう。

UARTの出力がUSBからでてこない

動かなくてうんうん唸ってましたが、マニュアル見ろってはなしでしたw
http://www.cypress.com/?docID=43713のp.61~
f:id:Lynx-EyED:20131019232510p:plain
ジャンパでPSoC5LPと配線してあげる必要があるみたいです。
ArduinoのD0(P0.4),D1(P0.5)以外にも接続可能な箇所があります。

Systickの割り込みってどうやれば

OSやらフレームワークやら移植するのにCortex-MシリーズはSystickから1msecタイマーを作ることが多いですが、PSoC4でどうやれば良いのか分からなかったので調べてみました。
PSoC4 SysTick interrupt-サイプレス
ここによるとVector#15がsystickの割り込みなので、1msecごとに割り込みを発生させてmsTicksをカウントアップするには以下の様にすれば良いはずです。メインルーチンからsetup_systickをコールしてやります。

int msTicks;
void SysTick_Handler(void) {
  msTicks++;                        /* increment counter necessary in Delay() */
}

void setup_systick (void) {

         CyIntSetSysVector(15,SysTick_Handler);

        // 1msecごとに割り込み
        if (SysTick_Config( (システムクロックの値) / 1000)) { 
                while (1);                                  /* Capture error */
        }
        CyGlobalIntEnable; 

}

W5100のEthernetシールドで遊ぶ

Element14のページにEthernet shieldのWebServerのサンプルがあります。
PSoC 4 Pioneer Kit Community Project#031 – Ethernet Shield - element14
さくっと動かそうとしたのですが、動きません。動かなくてうんうん唸ってましたが、写真にあったw
イーサーネットシールドは6ピンのICSP端子からしかSPIは接続されていない模様。
イーサーネットシールドの回路図
なので、6ピンを半田付けします。
f:id:Lynx-EyED:20131019235233p:plain
さて、Element14のサンプルそのままでも使えない事は無いのですが、やたらめったらArduinoライブラリがくっついてくるので収拾がつかなく、他のプロジェクトに転用できない感じです。
ちなみに純正ドライバ↓
Innovative Embedded Networking : Device Server, WiFi, Ethernet | WIZnet Co. Ltd.


Wiznetの純正ドライバを元に、低レイヤーをC、アプリケーションに近いレイヤーをC++で記述しました。
lynxeyed-atsu/W5100_PSoC4_telnet_test · GitHub

他のデバイスに移植したい場合、device_depend.cを該当デバイス用ドライバに書き換えれば動作するはずです。

main.cppのIPアドレスはご自分の環境に書き換えてください。自分の場合は169.254.22.31にしました。

// Network Settigs
uint8 mac[] = { 0x90, 0xA2, 0xDA, 0x0E, 0xA0, 0x8A };
uint8 ip[] = { 169, 254, 22, 31 };

// use port 23:Telnet
Server server = Server(23);

動作中の図。I2Cポートから何やらジャンパーが生えてますが、PSoC4のUARTです。この箇所にUARTを割り当ててます。
f:id:Lynx-EyED:20131020000823j:plain

■telnetループバック
TeraTermを立ち上げまして、
f:id:Lynx-EyED:20131020002951p:plain

telnetでループバックします。キーボードの入力をディスプレーに出力します
f:id:Lynx-EyED:20131020003222p:plain
はいバッチィです。
おしまい。

◆次回
PSoC4のCY8C4100シリーズはPSoCの特徴でもあったUDBが無く、今回のPioneer Kitに載っている4200も大幅に削減されてコストを抑える思い切ったデバイスになっています。UDBはVerilogでカスタムロジックの開発もできる尖ったデバイスですが、4200ではすぐにロジックが枯渇するでしょう。ここでCypressはシフト、加減算、バイトスワップなど単純なロジックはdatapath、それ以外の複雑なロジックはPLDベースのグルーロジックを使いわけることによってこの問題に対処することを提案しています。
次回はdatapath話題でも。

◆参考
PSoC CreatorでC++を使う方法
http://www.element14.com/community/servlet/JiveServlet/download/79763-114371/C%2B%2B%20In%20Creator.doc

ネットワークインターフェース部品の電子工作(W5100,ENC28J60,etc)
http://www.kako.com/neta/2009-003/2009-003.html

マイコン風雲録: Wiz820io(W5200)のドライバ (バグ?対応)

mbed LPC1768でJVM

RAMを豪快に使うだけのあそび

前回(RunnableインターフェースでマルチスレッドLチカ - Lynx-EyEDの電音鍵盤 新館)の続き。

JVMをmbedに移植しました。らくちん。mbedいいよmbed。
mbed LPC11U24/LPC1768には2MBのフラッシュがついています。classファイルをTest.claという名前にリネームしてmbedにコピー(←ファイル名が8.3形式にしか対応していない模様)すると、これを逐次解釈します。

↓こちらからフォークしてください。対応mbedはLPC11U24,LPC1768です*1
https://mbed.org/users/lynxeyed_atsu/code/FRDM_RaVem_JVM/


mallocとreallocがメモリーを取得できていないにもかかわらず、NULLを返さないコンパイラが一部にあったので、スタック領域に動的メモリを擬似的に確保するメモリプールマネージメントを実装しています。pool.hをご覧下さい。

今回作ったJVMはスレッドをnewするたびにメモリを動的に確保します。したがってメモリが少ないLPC812、LPC11U24、LPC1114だと1スレッド動作が現実的と言えます。

で、超ご無沙汰してるmbed LPC1768。LPC1768のCPUが使用できるRAMは比較的多いので4スレッドスーバーエコジャナイシステムを作りました。

上記のコードを2箇所修正します。
[device_depend.cpp]の5行目を

#define bc_str_length 2048 // from 32 to 1024

に変更(2048にする)。これはバイトコードをフラッシュからRAMにコピーするための領域です。(2048 = 2キロバイト)

[pool.h]の19行目。

#define pool_size           512 // 256 * (sizeof(int)) = 1kByte

に変更する。これはJVMが使うRAMのヒープ領域です*2。int型(=4バイト)アラインメントしてるので512 x 4 = 2キロバイトです。
コンパイルしてmbedに書き込みます。

Javaのコードの作成
(前回)のSoftBlinkLEDTest.javaを修正します。lpc800.javaも前回を参考に用意しておいてください。

public class SoftBlinkLEDTest implements Runnable{
    private int x,y;
    
    public SoftBlinkLEDTest(int bit_num, int sleep_time_ms){
        
        x = bit_num;
        y = sleep_time_ms;
       
    }
    
    public static void main(String[] args){
        
        SoftBlinkLEDTest LED1 = new SoftBlinkLEDTest(0, 90);     // LED1, half-cycle = 90msec
        SoftBlinkLEDTest LED2 = new SoftBlinkLEDTest(1, 100);    // LED2, half-cycle = 100msec
        SoftBlinkLEDTest LED3 = new SoftBlinkLEDTest(2, 500);    // LED3, half-cycle = 500msec
        SoftBlinkLEDTest LED4 = new SoftBlinkLEDTest(3, 1000);    // LED4, half-cycle = 1000msec
        
        
        Thread th1 = new Thread(LED1);
        Thread th2 = new Thread(LED2);
        Thread th3 = new Thread(LED3);
        Thread th4 = new Thread(LED4);
        
        th1.start();
        th2.start();
        th3.start();
        th4.start();
        
    }
    
    public void run(){
        
        int port_bit = x, time = y;
        
        while(true){
            try{
                Thread.sleep(time);
            }catch(Exception e){}
            
            lpc800.portWrite(port_bit, 1);
            //System.out.println("LED_on");
            
            try{
                Thread.sleep(time);
            }catch(Exception e){}
            
            lpc800.portWrite(port_bit, 0);
            //System.out.println("LED_off");
        }
    }
}

javacコンパイル。

$ javac SoftBlinkLEDTest.java

SoftBlinkLEDTest.classをリネーム

$ mv SoftBlinkLEDTest.class Test.cla

Test.claをmbed LPC1768にコピー。
mbedのマスストレージはこんな感じになってるはず。
f:id:Lynx-EyED:20130830001204p:plain
リセットボタンを押してスタート。ロードに2,3秒かかります。
↓こんな感じに動作するはず。

*1:最近mbedに追加された他のデバイス、たとえばLPC1114,KL25Zなどは今までLPC812で行っていた時と同様にバイトコードを配列変換すれば動作するはずです。余力のある方はraven.cpp/device_depend.cppを変更してください

*2:前述した通り、スタック領域に擬似的に形成してます

RunnableインターフェースでマルチスレッドLチカ

LPC800 JVMとRunnableクラスの実装

前回(LPC800にJVM載せてUARTループバック - Lynx-EyEDの電音鍵盤 新館)の続きです。

なお、JVMソースコード一式は以下を参照ください
lynxeyed-atsu/RaVem · GitHub

マルチスレッドで複数のLEDを別々の周期で点滅させようと思います。
そうなると、マイコンのIOポート番号や周期をThreadクラスに引数として持たせたい訳ですが、そうするにはJavaではRunnable実装クラスをインスタンス化したオブジェクト参照を、Threadクラスのコンストラクタ引数として渡す必要があります。

JVMレベルで考えると、オペランドスタックに引数をスタック → newされたオブジェクトのインスタンス初期化メソッドが呼び出された際にローカルレジスタにコピー → Public Field領域に引数を書き込みます。

このJVMの一連の動作をどのようにLPC812に実装するかが課題だったのですが、漸くできました。

とりあえず深い事は考えず、まず、以下のJavaのコードを SoftBlinkLEDTest.java という名前で保存します。

public class SoftBlinkLEDTest implements Runnable{
    private int x,y;
    
    public SoftBlinkLEDTest(int bit_num, int sleep_time_ms){
        
        x = bit_num;
        y = sleep_time_ms;
       
    }
    
    public static void main(String[] args){
        
        SoftBlinkLEDTest LED1 = new SoftBlinkLEDTest(7, 40);       // PIO0_7, half-cycle = 40msec
        SoftBlinkLEDTest LED2 = new SoftBlinkLEDTest(16, 1000);    // PIO0_16, half-cycle = 1000msec
        SoftBlinkLEDTest LED3 = new SoftBlinkLEDTest(17, 500);    // PIO0_17, half-cycle = 500msec
        
        
        Thread th1 = new Thread(LED1);
        Thread th2 = new Thread(LED2);
        Thread th3 = new Thread(LED3);
        
        th1.start();
        th2.start();
        th3.start();
    }
    
    public void run(){
        
        int port_bit = x, time = y;
        
        while(true){
            try{
                Thread.sleep(time);
            }catch(Exception e){}
            
            lpc800.portWrite(port_bit, 1);
            System.out.println("LED_on");
            
            try{
                Thread.sleep(time);
            }catch(Exception e){}
            
            lpc800.portWrite(port_bit, 0);
            System.out.println("LED_off");
        }
    }
}

ここで、GPIOにアクセスするためのportWrite(bit_num, value) というメソッドをlpc800クラスに用意しました。もちろんこれは独自のクラスです。そんなクラスもメソッドも無いとコンパイラに怒られてしまいますので、コンパイラを騙すフェイクを作ります。以下を lpc800.java という名前で保存します。

public class lpc800{
    
    public static void portWrite(int bit, int value){}
    
}

コレだけです。LPC812本体がこのクラスとメソッドを正しく認識すれば良く、Javacがこのクラスが何をするか知っていてもあまり意味はないので、何も実動作を記述する必要はありません。
二つのファイルを同一のフォルダに入れて、コンパイラバイトコードを生成してもらいます。

$ javac SoftBlinkLEDTest.java

2つのclassファイルができますが、必要なのは SoftBlinkLEDTest.class だけです。このクラスの実態バイトコードです。これをカンマ区切りデータで表現すると、以下の様になります。

0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x32, 0x00, 0x41, 0x0A, 0x00, 0x10, 
	0x00, 0x21, 0x09, 0x00, 0x04, 0x00, 0x22, 0x09, 0x00, 0x04, 0x00, 0x23, 0x07, 0x00, 0x24, 0x0A, 
	0x00, 0x04, 0x00, 0x25, 0x07, 0x00, 0x26, 0x0A, 0x00, 0x06, 0x00, 0x27, 0x0A, 0x00, 0x06, 0x00, 
	0x28, 0x0A, 0x00, 0x06, 0x00, 0x29, 0x07, 0x00, 0x2A, 0x0A, 0x00, 0x2B, 0x00, 0x2C, 0x09, 0x00, 
	0x2D, 0x00, 0x2E, 0x08, 0x00, 0x2F, 0x0A, 0x00, 0x30, 0x00, 0x31, 0x08, 0x00, 0x32, 0x07, 0x00, 
	0x33, 0x07, 0x00, 0x34, 0x01, 0x00, 0x01, 0x78, 0x01, 0x00, 0x01, 0x49, 0x01, 0x00, 0x01, 0x79, 
	0x01, 0x00, 0x06, 0x3C, 0x69, 0x6E, 0x69, 0x74, 0x3E, 0x01, 0x00, 0x05, 0x28, 0x49, 0x49, 0x29, 
	0x56, 0x01, 0x00, 0x04, 0x43, 0x6F, 0x64, 0x65, 0x01, 0x00, 0x0F, 0x4C, 0x69, 0x6E, 0x65, 0x4E, 
	0x75, 0x6D, 0x62, 0x65, 0x72, 0x54, 0x61, 0x62, 0x6C, 0x65, 0x01, 0x00, 0x04, 0x6D, 0x61, 0x69, 
	0x6E, 0x01, 0x00, 0x16, 0x28, 0x5B, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 
	0x2F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 0x3B, 0x29, 0x56, 0x01, 0x00, 0x03, 0x72, 0x75, 0x6E, 
	0x01, 0x00, 0x03, 0x28, 0x29, 0x56, 0x01, 0x00, 0x0D, 0x53, 0x74, 0x61, 0x63, 0x6B, 0x4D, 0x61, 
	0x70, 0x54, 0x61, 0x62, 0x6C, 0x65, 0x07, 0x00, 0x2A, 0x01, 0x00, 0x0A, 0x53, 0x6F, 0x75, 0x72, 
	0x63, 0x65, 0x46, 0x69, 0x6C, 0x65, 0x01, 0x00, 0x15, 0x53, 0x6F, 0x66, 0x74, 0x42, 0x6C, 0x69, 
	0x6E, 0x6B, 0x4C, 0x45, 0x44, 0x54, 0x65, 0x73, 0x74, 0x2E, 0x6A, 0x61, 0x76, 0x61, 0x0C, 0x00, 
	0x15, 0x00, 0x1C, 0x0C, 0x00, 0x12, 0x00, 0x13, 0x0C, 0x00, 0x14, 0x00, 0x13, 0x01, 0x00, 0x10, 
	0x53, 0x6F, 0x66, 0x74, 0x42, 0x6C, 0x69, 0x6E, 0x6B, 0x4C, 0x45, 0x44, 0x54, 0x65, 0x73, 0x74, 
	0x0C, 0x00, 0x15, 0x00, 0x16, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 
	0x67, 0x2F, 0x54, 0x68, 0x72, 0x65, 0x61, 0x64, 0x0C, 0x00, 0x15, 0x00, 0x35, 0x0C, 0x00, 0x36, 
	0x00, 0x1C, 0x0C, 0x00, 0x37, 0x00, 0x38, 0x01, 0x00, 0x13, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 
	0x61, 0x6E, 0x67, 0x2F, 0x45, 0x78, 0x63, 0x65, 0x70, 0x74, 0x69, 0x6F, 0x6E, 0x07, 0x00, 0x39, 
	0x0C, 0x00, 0x3A, 0x00, 0x16, 0x07, 0x00, 0x3B, 0x0C, 0x00, 0x3C, 0x00, 0x3D, 0x01, 0x00, 0x06, 
	0x4C, 0x45, 0x44, 0x5F, 0x6F, 0x6E, 0x07, 0x00, 0x3E, 0x0C, 0x00, 0x3F, 0x00, 0x40, 0x01, 0x00, 
	0x07, 0x4C, 0x45, 0x44, 0x5F, 0x6F, 0x66, 0x66, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 0x2F, 
	0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x4F, 0x62, 0x6A, 0x65, 0x63, 0x74, 0x01, 0x00, 0x12, 0x6A, 0x61, 
	0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x52, 0x75, 0x6E, 0x6E, 0x61, 0x62, 0x6C, 0x65, 
	0x01, 0x00, 0x17, 0x28, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x52, 
	0x75, 0x6E, 0x6E, 0x61, 0x62, 0x6C, 0x65, 0x3B, 0x29, 0x56, 0x01, 0x00, 0x05, 0x73, 0x74, 0x61, 
	0x72, 0x74, 0x01, 0x00, 0x05, 0x73, 0x6C, 0x65, 0x65, 0x70, 0x01, 0x00, 0x04, 0x28, 0x4A, 0x29, 
	0x56, 0x01, 0x00, 0x06, 0x6C, 0x70, 0x63, 0x38, 0x30, 0x30, 0x01, 0x00, 0x09, 0x70, 0x6F, 0x72, 
	0x74, 0x57, 0x72, 0x69, 0x74, 0x65, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 
	0x6E, 0x67, 0x2F, 0x53, 0x79, 0x73, 0x74, 0x65, 0x6D, 0x01, 0x00, 0x03, 0x6F, 0x75, 0x74, 0x01, 
	0x00, 0x15, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x50, 0x72, 0x69, 0x6E, 0x74, 
	0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 0x3B, 0x01, 0x00, 0x13, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 
	0x6F, 0x2F, 0x50, 0x72, 0x69, 0x6E, 0x74, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 0x01, 0x00, 0x07, 
	0x70, 0x72, 0x69, 0x6E, 0x74, 0x6C, 0x6E, 0x01, 0x00, 0x15, 0x28, 0x4C, 0x6A, 0x61, 0x76, 0x61, 
	0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 0x3B, 0x29, 0x56, 0x00, 
	0x21, 0x00, 0x04, 0x00, 0x10, 0x00, 0x01, 0x00, 0x11, 0x00, 0x02, 0x00, 0x02, 0x00, 0x12, 0x00, 
	0x13, 0x00, 0x00, 0x00, 0x02, 0x00, 0x14, 0x00, 0x13, 0x00, 0x00, 0x00, 0x03, 0x00, 0x01, 0x00, 
	0x15, 0x00, 0x16, 0x00, 0x01, 0x00, 0x17, 0x00, 0x00, 0x00, 0x33, 0x00, 0x02, 0x00, 0x03, 0x00, 
	0x00, 0x00, 0x0F, 0x2A, 0xB7, 0x00, 0x01, 0x2A, 0x1B, 0xB5, 0x00, 0x02, 0x2A, 0x1C, 0xB5, 0x00, 
	0x03, 0xB1, 0x00, 0x00, 0x00, 0x01, 0x00, 0x18, 0x00, 0x00, 0x00, 0x12, 0x00, 0x04, 0x00, 0x00, 
	0x00, 0x04, 0x00, 0x04, 0x00, 0x06, 0x00, 0x09, 0x00, 0x07, 0x00, 0x0E, 0x00, 0x09, 0x00, 0x09, 
	0x00, 0x19, 0x00, 0x1A, 0x00, 0x01, 0x00, 0x17, 0x00, 0x00, 0x00, 0x90, 0x00, 0x04, 0x00, 0x07, 
	0x00, 0x00, 0x00, 0x54, 0xBB, 0x00, 0x04, 0x59, 0x10, 0x07, 0x10, 0x28, 0xB7, 0x00, 0x05, 0x4C, 
	0xBB, 0x00, 0x04, 0x59, 0x10, 0x10, 0x11, 0x03, 0xE8, 0xB7, 0x00, 0x05, 0x4D, 0xBB, 0x00, 0x04, 
	0x59, 0x10, 0x11, 0x11, 0x01, 0xF4, 0xB7, 0x00, 0x05, 0x4E, 0xBB, 0x00, 0x06, 0x59, 0x2B, 0xB7, 
	0x00, 0x07, 0x3A, 0x04, 0xBB, 0x00, 0x06, 0x59, 0x2C, 0xB7, 0x00, 0x07, 0x3A, 0x05, 0xBB, 0x00, 
	0x06, 0x59, 0x2D, 0xB7, 0x00, 0x07, 0x3A, 0x06, 0x19, 0x04, 0xB6, 0x00, 0x08, 0x19, 0x05, 0xB6, 
	0x00, 0x08, 0x19, 0x06, 0xB6, 0x00, 0x08, 0xB1, 0x00, 0x00, 0x00, 0x01, 0x00, 0x18, 0x00, 0x00, 
	0x00, 0x2A, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x0D, 0x00, 0x0C, 0x00, 0x0E, 0x00, 0x19, 0x00, 0x0F, 
	0x00, 0x26, 0x00, 0x12, 0x00, 0x30, 0x00, 0x13, 0x00, 0x3A, 0x00, 0x14, 0x00, 0x44, 0x00, 0x16, 
	0x00, 0x49, 0x00, 0x17, 0x00, 0x4E, 0x00, 0x18, 0x00, 0x53, 0x00, 0x19, 0x00, 0x01, 0x00, 0x1B, 
	0x00, 0x1C, 0x00, 0x01, 0x00, 0x17, 0x00, 0x00, 0x00, 0x98, 0x00, 0x02, 0x00, 0x04, 0x00, 0x00, 
	0x00, 0x39, 0x2A, 0xB4, 0x00, 0x02, 0x3C, 0x2A, 0xB4, 0x00, 0x03, 0x3D, 0x1C, 0x85, 0xB8, 0x00, 
	0x09, 0xA7, 0x00, 0x04, 0x4E, 0x1B, 0x04, 0xB8, 0x00, 0x0B, 0xB2, 0x00, 0x0C, 0x12, 0x0D, 0xB6, 
	0x00, 0x0E, 0x1C, 0x85, 0xB8, 0x00, 0x09, 0xA7, 0x00, 0x04, 0x4E, 0x1B, 0x03, 0xB8, 0x00, 0x0B, 
	0xB2, 0x00, 0x0C, 0x12, 0x0F, 0xB6, 0x00, 0x0E, 0xA7, 0xFF, 0xD4, 0x00, 0x02, 0x00, 0x0A, 0x00, 
	0x0F, 0x00, 0x12, 0x00, 0x0A, 0x00, 0x20, 0x00, 0x25, 0x00, 0x28, 0x00, 0x0A, 0x00, 0x02, 0x00, 
	0x18, 0x00, 0x00, 0x00, 0x26, 0x00, 0x09, 0x00, 0x00, 0x00, 0x1D, 0x00, 0x0A, 0x00, 0x21, 0x00, 
	0x0F, 0x00, 0x22, 0x00, 0x13, 0x00, 0x24, 0x00, 0x18, 0x00, 0x25, 0x00, 0x20, 0x00, 0x28, 0x00, 
	0x25, 0x00, 0x29, 0x00, 0x29, 0x00, 0x2B, 0x00, 0x2E, 0x00, 0x2C, 0x00, 0x1D, 0x00, 0x00, 0x00, 
	0x11, 0x00, 0x05, 0xFD, 0x00, 0x0A, 0x01, 0x01, 0x47, 0x07, 0x00, 0x1E, 0x00, 0x54, 0x07, 0x00, 
	0x1E, 0x00, 0x00, 0x01, 0x00, 0x1F, 0x00, 0x00, 0x00, 0x02, 0x00, 0x20, 0x00, 0x00, 0x00

上記バイトコードを、MDK-ARMプロジェクトの中のravem.cにvm_array[]という配列名で記述し、コンパイルします。

LPCXpressoだとPIO0_7(赤色LED)が80msec周期、PIO0_16(青色LED)が2000msec周期、PIO0_17(緑色LED)が1000msec周期で点滅するのが確認できると思います。

f:id:Lynx-EyED:20130823203623j:plain

LPC800にJVM載せてUARTループバック

Java VMのせてみた

f:id:Lynx-EyED:20130802144748p:plain
とある必要にかられて、Flash ~32kB/RAM ~4kBクラスの小規模コントローラ向けにJVMを実装しました。
Javaを使いたい場合Linuxを搭載した組み込み機器にJavaを載せるのが通常ですがそれが困難な容量の少ないデバイス向けです。

ここではCortex-M0+のLPC812にJVMの移植を試みました。
lynxeyed-atsu/RaVem · GitHub
解釈できるニーモニックは限られてます。
上記のリンクからダウンロードできるのはMDK-ARMプロジェクト一式です。開発環境はMDK-ARMです。32kBまでなら無償のMDK-ARM Liteが使用できます。(要登録)
https://www.keil.com/demo/eval/arm.htm

なお、LPCXpresso LPC812ボード単体だと書き込み、デバッグが出来ません。LPC-Link2をCMSIS-DAPにして使う必要があります。
(参考) LPCマイコン情報:LPC-Link2ノート1-LPC-Link2を各デバッガにしてデバッグする その1 〜Redlink & LPCXPresso, CMSIS-DAPデバッガ & Keil, SEGGER J-Link & Keil〜


Java中間言語生成にはjavac-1.6.0_51を使用しています。(なにか特殊なコードを吐く様にコンパイラを細工したりはしていません)

SDカードなどからバイトコードをブートしても良いですが、始めてやる作業なので不確定要素が多いと困ります。まず力弱くバイトコードを配列にしてソースコードに貼付け、まるごとMDK-ARMでコンパイルます。const char配列にするのでcsv形式で出力ができるバイナリエディタで、コンパイルした*.classファイルをリードすると良いでしょう。

つまり、javacでコンパイル → バイナリをCの配列にする → JVM本体ごとMDK-ARMでコンパイル → LPC812に書き込み
という流れです。

とりあえず、こんなJavaコードを書きました。UARTから1文字受信して、それを表示します。

import java.io.*;
class hoge1{
    public static void main(String[] args){
        int  i;
        System.out.println( "enter any key" );
        while(true){
            try{
                i = System.in.read();
                System.out.print((char)i);
            }
            catch(IOException e){
                System.err.println( "error" );
            }
        }
    }
}

上記をhoge1.javaとして保存。
コンパイルします。

javac hoge1.java

生成されたhoge1.classは下に示すバイトコードが保存されています。

0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x32, 0x00, 0x34, 0x0A, 0x00, 0x0C, 
0x00, 0x17, 0x09, 0x00, 0x18, 0x00, 0x19, 0x08, 0x00, 0x1A, 0x0A, 0x00, 0x1B, 0x00, 0x1C, 0x09, 
0x00, 0x18, 0x00, 0x1D, 0x0A, 0x00, 0x1E, 0x00, 0x1F, 0x0A, 0x00, 0x1B, 0x00, 0x20, 0x07, 0x00, 
0x21, 0x09, 0x00, 0x18, 0x00, 0x22, 0x08, 0x00, 0x23, 0x07, 0x00, 0x24, 0x07, 0x00, 0x25, 0x01, 
0x00, 0x06, 0x3C, 0x69, 0x6E, 0x69, 0x74, 0x3E, 0x01, 0x00, 0x03, 0x28, 0x29, 0x56, 0x01, 0x00, 
0x04, 0x43, 0x6F, 0x64, 0x65, 0x01, 0x00, 0x0F, 0x4C, 0x69, 0x6E, 0x65, 0x4E, 0x75, 0x6D, 0x62, 
0x65, 0x72, 0x54, 0x61, 0x62, 0x6C, 0x65, 0x01, 0x00, 0x04, 0x6D, 0x61, 0x69, 0x6E, 0x01, 0x00, 
0x16, 0x28, 0x5B, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 
0x72, 0x69, 0x6E, 0x67, 0x3B, 0x29, 0x56, 0x01, 0x00, 0x0D, 0x53, 0x74, 0x61, 0x63, 0x6B, 0x4D, 
0x61, 0x70, 0x54, 0x61, 0x62, 0x6C, 0x65, 0x07, 0x00, 0x21, 0x01, 0x00, 0x0A, 0x53, 0x6F, 0x75, 
0x72, 0x63, 0x65, 0x46, 0x69, 0x6C, 0x65, 0x01, 0x00, 0x0A, 0x68, 0x6F, 0x67, 0x65, 0x31, 0x2E, 
0x6A, 0x61, 0x76, 0x61, 0x0C, 0x00, 0x0D, 0x00, 0x0E, 0x07, 0x00, 0x26, 0x0C, 0x00, 0x27, 0x00, 
0x28, 0x01, 0x00, 0x0D, 0x65, 0x6E, 0x74, 0x65, 0x72, 0x20, 0x61, 0x6E, 0x79, 0x20, 0x6B, 0x65, 
0x79, 0x07, 0x00, 0x29, 0x0C, 0x00, 0x2A, 0x00, 0x2B, 0x0C, 0x00, 0x2C, 0x00, 0x2D, 0x07, 0x00, 
0x2E, 0x0C, 0x00, 0x2F, 0x00, 0x30, 0x0C, 0x00, 0x31, 0x00, 0x32, 0x01, 0x00, 0x13, 0x6A, 0x61, 
0x76, 0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x49, 0x4F, 0x45, 0x78, 0x63, 0x65, 0x70, 0x74, 0x69, 0x6F, 
0x6E, 0x0C, 0x00, 0x33, 0x00, 0x28, 0x01, 0x00, 0x05, 0x65, 0x72, 0x72, 0x6F, 0x72, 0x01, 0x00, 
0x05, 0x68, 0x6F, 0x67, 0x65, 0x31, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 
0x6E, 0x67, 0x2F, 0x4F, 0x62, 0x6A, 0x65, 0x63, 0x74, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 
0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x79, 0x73, 0x74, 0x65, 0x6D, 0x01, 0x00, 0x03, 0x6F, 
0x75, 0x74, 0x01, 0x00, 0x15, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x50, 0x72, 
0x69, 0x6E, 0x74, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 0x3B, 0x01, 0x00, 0x13, 0x6A, 0x61, 0x76, 
0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x50, 0x72, 0x69, 0x6E, 0x74, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 
0x01, 0x00, 0x07, 0x70, 0x72, 0x69, 0x6E, 0x74, 0x6C, 0x6E, 0x01, 0x00, 0x15, 0x28, 0x4C, 0x6A, 
0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 0x3B, 
0x29, 0x56, 0x01, 0x00, 0x02, 0x69, 0x6E, 0x01, 0x00, 0x15, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 
0x69, 0x6F, 0x2F, 0x49, 0x6E, 0x70, 0x75, 0x74, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 0x3B, 0x01, 
0x00, 0x13, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x49, 0x6E, 0x70, 0x75, 0x74, 0x53, 
0x74, 0x72, 0x65, 0x61, 0x6D, 0x01, 0x00, 0x04, 0x72, 0x65, 0x61, 0x64, 0x01, 0x00, 0x03, 0x28, 
0x29, 0x49, 0x01, 0x00, 0x05, 0x70, 0x72, 0x69, 0x6E, 0x74, 0x01, 0x00, 0x04, 0x28, 0x43, 0x29, 
0x56, 0x01, 0x00, 0x03, 0x65, 0x72, 0x72, 0x00, 0x20, 0x00, 0x0B, 0x00, 0x0C, 0x00, 0x00, 0x00, 
0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0D, 0x00, 0x0E, 0x00, 0x01, 0x00, 0x0F, 0x00, 0x00, 0x00, 
0x1D, 0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x05, 0x2A, 0xB7, 0x00, 0x01, 0xB1, 0x00, 0x00, 
0x00, 0x01, 0x00, 0x10, 0x00, 0x00, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x03, 0x00, 0x09, 
0x00, 0x11, 0x00, 0x12, 0x00, 0x01, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x6B, 0x00, 0x02, 0x00, 0x03, 
0x00, 0x00, 0x00, 0x26, 0xB2, 0x00, 0x02, 0x12, 0x03, 0xB6, 0x00, 0x04, 0xB2, 0x00, 0x05, 0xB6, 
0x00, 0x06, 0x3C, 0xB2, 0x00, 0x02, 0x1B, 0x92, 0xB6, 0x00, 0x07, 0xA7, 0xFF, 0xF1, 0x4D, 0xB2, 
0x00, 0x09, 0x12, 0x0A, 0xB6, 0x00, 0x04, 0xA7, 0xFF, 0xE5, 0x00, 0x01, 0x00, 0x08, 0x00, 0x17, 
0x00, 0x1A, 0x00, 0x08, 0x00, 0x02, 0x00, 0x10, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x07, 0x00, 0x00, 
0x00, 0x06, 0x00, 0x08, 0x00, 0x09, 0x00, 0x0F, 0x00, 0x0A, 0x00, 0x17, 0x00, 0x0E, 0x00, 0x1A, 
0x00, 0x0C, 0x00, 0x1B, 0x00, 0x0D, 0x00, 0x23, 0x00, 0x0E, 0x00, 0x13, 0x00, 0x00, 0x00, 0x07, 
0x00, 0x02, 0x08, 0x51, 0x07, 0x00, 0x14, 0x00, 0x01, 0x00, 0x15, 0x00, 0x00, 0x00, 0x02, 0x00, 
0x16, 0x00, 0x00, 0x00

上記バイトコードを、MDK-ARMプロジェクトの中のravem.cにvm_array[]という配列名で記述し、コンパイル。
USB-UARTとLPC812を接続します。

PIO0_4 -> UART0_TXD
PIO0_0 -> UART0_RXD

無事動作すれば、下の様になります。
f:id:Lynx-EyED:20130802152912p:plain


開発風景(笑
f:id:Lynx-EyED:20130802154506j:plain

おまけ:マルチスレッドっぽい何かを実装してみた

ノンプリエンプティブ型でマルチスレッドを実装してみました。
このご時世にノンプリエンプティブとか何考えてるんですかwと言われかねませんが、、そもそも、すでにCortex-M0+にとってJVMが高負荷であり、メモリが限られていて、かつ10も20もスレッドを持つ意義が感じられない・持つことができない*1デバイスに複雑なTCBを持つプリエンプティブ型を採用するのは利点がないように思えたからです。このデバイスでマルチスレッドを持つとしてもメソッドの負荷によりますが2ないし3個が現実的でしょう。それならばノンプリエンプティブ型のほうが、トータルで見た開発時間が少なくてすみます。
Javacで以下のコードをコンパイルします

class hoge1 extends Thread{
    
        public void run() {
            while(true) {
                System.out.print("thread Number=");
                System.out.println(getName());
                try {
                    sleep(1000);
                } catch (InterruptedException e) {
                }
            }
        }
    
    
        public static void main(String[] args){
            System.out.println("Thread test");
            
            hoge1 thread1 = new hoge1();
            hoge1 thread2 = new hoge1();
            
            thread1.start();
            thread2.start();
        }
    
}

ここで、

System.out.println("thread Number=" + getName());

と記述した方が処理が高速になるよね?と考えた方、正解です。
すみません。StringBuilderを実装していないので、Stringの連結ができないんですよ。(ぉぃ
そのうちしますよそのうち
バイトコードは以下のようになります。

0xCA, 0xFE, 0xBA, 0xBE, 0x00, 0x00, 0x00, 0x32, 0x00, 0x35, 0x0A, 0x00, 0x0F, 
	0x00, 0x1B, 0x09, 0x00, 0x1C, 0x00, 0x1D, 0x08, 0x00, 0x1E, 0x0A, 0x00, 0x1F, 0x00, 0x20, 0x0A, 
	0x00, 0x0B, 0x00, 0x21, 0x0A, 0x00, 0x1F, 0x00, 0x22, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 
	0x03, 0xE8, 0x0A, 0x00, 0x0B, 0x00, 0x23, 0x07, 0x00, 0x24, 0x07, 0x00, 0x25, 0x0A, 0x00, 0x0B, 
	0x00, 0x1B, 0x0A, 0x00, 0x0B, 0x00, 0x26, 0x08, 0x00, 0x27, 0x07, 0x00, 0x28, 0x01, 0x00, 0x06, 
	0x3C, 0x69, 0x6E, 0x69, 0x74, 0x3E, 0x01, 0x00, 0x03, 0x28, 0x29, 0x56, 0x01, 0x00, 0x04, 0x43, 
	0x6F, 0x64, 0x65, 0x01, 0x00, 0x0F, 0x4C, 0x69, 0x6E, 0x65, 0x4E, 0x75, 0x6D, 0x62, 0x65, 0x72, 
	0x54, 0x61, 0x62, 0x6C, 0x65, 0x01, 0x00, 0x03, 0x72, 0x75, 0x6E, 0x01, 0x00, 0x0D, 0x53, 0x74, 
	0x61, 0x63, 0x6B, 0x4D, 0x61, 0x70, 0x54, 0x61, 0x62, 0x6C, 0x65, 0x07, 0x00, 0x24, 0x01, 0x00, 
	0x04, 0x6D, 0x61, 0x69, 0x6E, 0x01, 0x00, 0x16, 0x28, 0x5B, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 
	0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 0x3B, 0x29, 0x56, 0x01, 0x00, 
	0x0A, 0x53, 0x6F, 0x75, 0x72, 0x63, 0x65, 0x46, 0x69, 0x6C, 0x65, 0x01, 0x00, 0x0A, 0x68, 0x6F, 
	0x67, 0x65, 0x31, 0x2E, 0x6A, 0x61, 0x76, 0x61, 0x0C, 0x00, 0x10, 0x00, 0x11, 0x07, 0x00, 0x29, 
	0x0C, 0x00, 0x2A, 0x00, 0x2B, 0x01, 0x00, 0x0E, 0x74, 0x68, 0x72, 0x65, 0x61, 0x64, 0x20, 0x4E, 
	0x75, 0x6D, 0x62, 0x65, 0x72, 0x3D, 0x07, 0x00, 0x2C, 0x0C, 0x00, 0x2D, 0x00, 0x2E, 0x0C, 0x00, 
	0x2F, 0x00, 0x30, 0x0C, 0x00, 0x31, 0x00, 0x2E, 0x0C, 0x00, 0x32, 0x00, 0x33, 0x01, 0x00, 0x1E, 
	0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x49, 0x6E, 0x74, 0x65, 0x72, 0x72, 
	0x75, 0x70, 0x74, 0x65, 0x64, 0x45, 0x78, 0x63, 0x65, 0x70, 0x74, 0x69, 0x6F, 0x6E, 0x01, 0x00, 
	0x05, 0x68, 0x6F, 0x67, 0x65, 0x31, 0x0C, 0x00, 0x34, 0x00, 0x11, 0x01, 0x00, 0x0B, 0x54, 0x68, 
	0x72, 0x65, 0x61, 0x64, 0x20, 0x74, 0x65, 0x73, 0x74, 0x01, 0x00, 0x10, 0x6A, 0x61, 0x76, 0x61, 
	0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x54, 0x68, 0x72, 0x65, 0x61, 0x64, 0x01, 0x00, 0x10, 0x6A, 
	0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x79, 0x73, 0x74, 0x65, 0x6D, 0x01, 
	0x00, 0x03, 0x6F, 0x75, 0x74, 0x01, 0x00, 0x15, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 0x6F, 
	0x2F, 0x50, 0x72, 0x69, 0x6E, 0x74, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6D, 0x3B, 0x01, 0x00, 0x13, 
	0x6A, 0x61, 0x76, 0x61, 0x2F, 0x69, 0x6F, 0x2F, 0x50, 0x72, 0x69, 0x6E, 0x74, 0x53, 0x74, 0x72, 
	0x65, 0x61, 0x6D, 0x01, 0x00, 0x05, 0x70, 0x72, 0x69, 0x6E, 0x74, 0x01, 0x00, 0x15, 0x28, 0x4C, 
	0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 
	0x3B, 0x29, 0x56, 0x01, 0x00, 0x07, 0x67, 0x65, 0x74, 0x4E, 0x61, 0x6D, 0x65, 0x01, 0x00, 0x14, 
	0x28, 0x29, 0x4C, 0x6A, 0x61, 0x76, 0x61, 0x2F, 0x6C, 0x61, 0x6E, 0x67, 0x2F, 0x53, 0x74, 0x72, 
	0x69, 0x6E, 0x67, 0x3B, 0x01, 0x00, 0x07, 0x70, 0x72, 0x69, 0x6E, 0x74, 0x6C, 0x6E, 0x01, 0x00, 
	0x05, 0x73, 0x6C, 0x65, 0x65, 0x70, 0x01, 0x00, 0x04, 0x28, 0x4A, 0x29, 0x56, 0x01, 0x00, 0x05, 
	0x73, 0x74, 0x61, 0x72, 0x74, 0x00, 0x20, 0x00, 0x0B, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 
	0x03, 0x00, 0x00, 0x00, 0x10, 0x00, 0x11, 0x00, 0x01, 0x00, 0x12, 0x00, 0x00, 0x00, 0x1D, 0x00, 
	0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x05, 0x2A, 0xB7, 0x00, 0x01, 0xB1, 0x00, 0x00, 0x00, 0x01, 
	0x00, 0x13, 0x00, 0x00, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x14, 
	0x00, 0x11, 0x00, 0x01, 0x00, 0x12, 0x00, 0x00, 0x00, 0x60, 0x00, 0x02, 0x00, 0x02, 0x00, 0x00, 
	0x00, 0x1F, 0xB2, 0x00, 0x02, 0x12, 0x03, 0xB6, 0x00, 0x04, 0xB2, 0x00, 0x02, 0x2A, 0xB6, 0x00, 
	0x05, 0xB6, 0x00, 0x06, 0x14, 0x00, 0x07, 0xB8, 0x00, 0x09, 0xA7, 0xFF, 0xE8, 0x4C, 0xA7, 0xFF, 
	0xE4, 0x00, 0x01, 0x00, 0x12, 0x00, 0x18, 0x00, 0x1B, 0x00, 0x0A, 0x00, 0x02, 0x00, 0x13, 0x00, 
	0x00, 0x00, 0x1A, 0x00, 0x06, 0x00, 0x00, 0x00, 0x05, 0x00, 0x08, 0x00, 0x06, 0x00, 0x12, 0x00, 
	0x08, 0x00, 0x18, 0x00, 0x0A, 0x00, 0x1B, 0x00, 0x09, 0x00, 0x1C, 0x00, 0x0A, 0x00, 0x15, 0x00, 
	0x00, 0x00, 0x07, 0x00, 0x02, 0x00, 0x5A, 0x07, 0x00, 0x16, 0x00, 0x09, 0x00, 0x17, 0x00, 0x18, 
	0x00, 0x01, 0x00, 0x12, 0x00, 0x00, 0x00, 0x4D, 0x00, 0x02, 0x00, 0x03, 0x00, 0x00, 0x00, 0x21, 
	0xBB, 0x00, 0x0B, 0x59, 0xB7, 0x00, 0x0C, 0x4C, 0xBB, 0x00, 0x0B, 0x59, 0xB7, 0x00, 0x0C, 0x4D, 
	0x2B, 0xB6, 0x00, 0x0D, 0x2C, 0xB6, 0x00, 0x0D, 0xB2, 0x00, 0x02, 0x12, 0x0E, 0xB6, 0x00, 0x06, 
	0xB1, 0x00, 0x00, 0x00, 0x01, 0x00, 0x13, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x06, 0x00, 0x00, 0x00, 
	0x11, 0x00, 0x08, 0x00, 0x12, 0x00, 0x10, 0x00, 0x14, 0x00, 0x14, 0x00, 0x15, 0x00, 0x18, 0x00, 
	0x17, 0x00, 0x20, 0x00, 0x18, 0x00, 0x01, 0x00, 0x19, 0x00, 0x00, 0x00, 0x02, 0x00, 0x1A, 0x00, 
	0x00, 0x00

コンパイルして実行すると、UARTでマルチスレッドっぽくなっているところが確認できると思います。
f:id:Lynx-EyED:20130809213540p:plain


◆参考
Chapter 4. The class File Format
Javaのhello worldの読み方 | mwSoft




*1:LPC81xは省メモリで安価なデバイスですので機能ごとに複数のデバイスに分けて平行動作させたほうがデバッグ、機能安全の観点からもメリットがありますし、省電力デバイスなのでパワーマネージメントの設計に注力した方が良いと思われます