読者です 読者をやめる 読者になる 読者になる

まるさや

技術っぽいことかきます

SystemCのSC_CTHREADはメソッド抜けちゃいけないらしい


どうも,まるさです.

SystemCのSC_CTHREAD使っててちょっと詰んだので覚書




開発環境

Windows版Vivado HLS 2016.3を使って,SystemCを記述していました.

OSはWindows10です.







ちょっとした実験がしたかった

SystemCを使って次のようなハードウェアを書いていました.

  • データの入力をトリガに動く
  • 実行は一度だけ
  • valid信号を使って外部から入力を待つ必要があった

具体的には,次のような記述をしました.


SC_MODULE(sample)
{
  sc_in_clk   CLK;
  sc_in<bool> RST;
  sc_in<int>  din;
  sc_in<bool> din_valid;

  SC_CTOR(sample):
      CLK("CLK"),
      RST("RST"),
      din("din"),
      din_valid("din_valid")
  {
    SC_CTHREAD(thread, CLK.pos());
    reset_signal_is(RST, false);
  }

  void thread(){
    // dinが入るまで待つ
    while (din_valid.read()){
      wait();
    }

    // データを受け取る
    int data = din.read();
    /* やりたい処理 */

    wait();
  }
};


このコードだと,次のようなエラーがでました.


Found exit operation(s) (<上記コードthreadの2行目>) in the main loop of SC_CTHREAD 'sample::thread'.


exitしてねえし,と思いましたが,どうもSC_CTHREADSC_THREADで指定したメソッドは 終了してはいけないということのようです.

whileで無限ループを作るのが必須なので,while文に対してエラーがついてしまうということかな?







解決策

というわけで,threadのメソッドが終了しないようにすれば動くようになりました.


void thread(){
  bool flag = false;

  while (true){ // 無限ループにする
    if (!flag){ // 一度だけ実行されるようにするためのフラグ
      // dinが入るまで待つ
      while (din_valid.read()){
        wait();
      }

      // データを受け取る
      int data = din.read();
      /* やりたい処理 */

      flag = true;
    }

    wait();
  }
}







まちがった解決策

次のようなコードは,解決策とはなりませんでした.

最初と同じエラーが出てしまいます.


void thread(){
  // dinが入るまで待つ
  while (din_valid.read()){
    wait();
  }

  // データを受け取る
  int data = din.read();
  /* やりたい処理 */

  while (true) wait(); // 終了しないように無限ループ
}


メソッド直下のwhileが終了してはいけないようです.

ループを含まないような場合ならこれでもよいかもしれませんが, 今回はdinのためのビジーウェイトが入っているのでこのコードでは解決できませんでした.







それでは,

こんかいはこのへんで ノ


まるさ

Zynqberryを観察する(2)


どうも,まるさ@maruuusa83です.

前の記事に引き続いてZynqberryを観察していきます.




Zynqberryには何が書き込まれるのか

Zynqberry用のVivadoプロジェクトを自動生成するスクリプトvivado_create_project_guimode.cmdがあるので, こいつを使ってみます.

ただし,block_design\zsys_bd.tclはVivado 2016.2で吐かれているので,scripts_vivado_versionの値を2016.3に 変更しておく必要があります.

すると,こんなBoard Designが書き込まれたプロジェクトができました.


f:id:maruuusa83:20161110134934p:plain Board Design


PS部に加えて,RasPi2のGPIOを実現するIPと, こいつをコンフィグするための信号をAXIからデコードするようなIPが追加されています.

クロック周りがどうなっているかチェックしました.


f:id:maruuusa83:20161110135355p:plain Clock Configuration


チュートリアルではPSは33.3333MHzで動いていると書いてありますが,やはりInput Frequencyが33MHzなだけであって, CPUは666MHzで動いているようです.

33MHzっておそすぎでしょ(#^ω^)


FCLKは50MHzのCLK0と100MHzのCLK1が生成されていますが,なぜかCLK1は使われていません.PLには50MHzが供給されていました.






とりあえずImplementしてみる

リファレンス・デザインそのままでImplementしてみました.


f:id:maruuusa83:20161110141842p:plain ハードウェア使用率(post-implementation)


GPIOに引っ張り出すためにI/Oの消費量が伸びていますが,ほかに特に不思議はありませんでした.


XC7Z020版がほしいなあ・・・






それでは

今回はこのへんで ノ


まるさ

Zynqberryを観察する


どうも,まるさ@maruuusa83です.




Zynqberryってなんだ

トレンツエレクトロニック社が作っているシングルボードコンピュータ的なやつです.

Raspberry Pi2互換で,SoCにZynq XC7Z010を積んだボードです.


www.trenz.jp


f:id:maruuusa83:20161109000841j:plain こんなかんじのやつ


今回は外観とか中身とかあれこれ観察してみます.







外観

かなりPi2とそっくりですね.


f:id:maruuusa83:20161109001127j:plain f:id:maruuusa83:20161109002107j:plain Raspberry Pi 2(奥)とZynqberry TE0726(手前)


実際基板サイズやねじ穴,各コネクタの位置もそっくり同じでした.

ですからRaspberry Pi 2が入るケースに収めることが・・・

できないこともあるかもしれません.


f:id:maruuusa83:20161109001617j:plain 若干浮いてしまっている


基板が本家よりも若干厚く,手元のケースだと手で押さえないと土台から若干浮いてしまいました.

まぁきちんとケースを閉じることはできるのでそれほど気になりませんが.


f:id:maruuusa83:20161109001948j:plain いちおう普通に閉まった


表面

f:id:maruuusa83:20161109002331j:plain Zynqberry表面

USBとEthernetのコントローラはRasPi2と同じLAN9514ですね.

Lattice社のCPLDであるLCMXO2とFTDI社のUSB-UART変換ICのFT2232HQが乗っています. MicroUSBでUSB-JTAGをするために乗せているようです. 実際RasPiと違ってUSBでPCとつながっていればアレコレできちゃうので良い感じです.

他にも,SPIFlashが乗っています.ZynqのBootModeがQSPIに固定されており,このFlashから読みだされます. Linuxが動くようにするには,ここにSDを読みだすu-bootを置く必要がありました.

ところでZynqが乗っている位置はRasPiのSoCと微妙にずれているので,ケースに収めたとき若干カッコ悪くなりますw

f:id:maruuusa83:20161109003101j:plain 若干右に寄っている


裏面

f:id:maruuusa83:20161110142651j:plain Zynqberry裏面

RasPi2と違ってRAMが表に移動しているので,裏はあっさりしていますね.

SDカードスロットですがが,SDを取り出すときに押し込んでもバネで飛び出してくれませんでした.


まんまRasPi2の代用になりそう






それでは

今回はこのへんで ノ


まるさ

Zynqberryで公式Debianを動かしてみる


どうも,まるさ@maruuusa83です.




なにかボードを振り回したい

なんかRasPiとかArduinoとか流行りのアイテムって,買うだけ買って放置しちゃう系なので, たまにはちゃんと使いたいなあなんておもいます.

というわけで,最近研究がら使えるようになったZynqberryをとりあえず動かせるようにします.







Zynqberryってなんだ

トレンツエレクトロニック社が作っているシングルボードコンピュータ的なやつです.

Raspberry Pi2互換で,SoCにZynq XC7Z010を積んだボードです.

なぜだかBoot ModeがQSPIモードに固定されているので,Linuxを起動するにはそれらしいブートローダを 内蔵のフラッシュに書き込む必要があります.

最初が大変.

f:id:maruuusa83:20161108191651j:plain Zynqberryってこんなの


でも日本語のチュートリアルもあるのでちょっぴり安心.

www.trenz.jp







とりあえずSDにイメージを焼く

ここからは,チュートリアルの内容に基いて進めていきます. 筆者なりに内容をまとめなおしていますが,基本的にはチュートリアルと変わらないことを書いています.

トレンツのサポートから必要な諸々を落としてきます.


http://www.trenz-electronic.de/download/d0/Trenz_Electronic/d1/TE0726/d2/Reference_Design.htmlwww.trenz-electronic.de


次のものを落としてください.

zynq-debian.imgをWin32DiskImagerとかで適当なmicro SDに焼きます.

2GBしか消費しないのであまり大きくないmicro SDで大丈夫です.


f:id:maruuusa83:20161108192648p:plain diskmgmt.mscで見た様子


Windowsではリムーバブルドライブの類は先頭のパーティションしか見えませんから,11MBくらいのドライブに見えます.


f:id:maruuusa83:20161108193459p:plain


ここに先ほど落としてきた残りのimage.ubsystem.dtbを置いてください.

これでSDの準備は完了しました.







内蔵Flashにu-bootを突っ込む

ZynqではいくつかBoot Modeがあります.が,なぜかZynqberryではQSPIモードに固定されているので,ブートさせたいソフト は必ず内蔵のSPIフラッシュメモリに置く必要があります.

このフラッシュは,USBで繋いだらFAT32のディスクに見えるとかそういう便利な機能はついてないので,がんばって書き込む 必要があります.

今回はLinuxを動かしたいので,フラッシュにブートローダを置いてあげる必要があります.


とりあえず先ほどのページからブートローダとリファレンスデザインを持ってきます.

  • Debian8.4 > Flash > BOOT.bin
  • 2016.2 > test_board > te0726-test_board-vivado_2016.2-build_xxxxx.zip

zipを展開するとtest_boardフォルダができます.

test_bard/prebuilt/boot_images/te0726-mの下にu-boot-debianフォルダを作って,その中にBOOT.binを置いてください.


test_board直下のdesign_basic_settings.cmdを編集します.

- @set VIVADO_VERSION=2016.2
+ @set VIVADO_VERSION=2016.3

- @set PARTNUMBER=LAST_ID
+ @set PARTNUMBER=3

- @set SWAPP=NA
+ @set SWAPP=u-boot-debian

お察しの通り,フラッシュの書き込みにVivadoを要求してきます.

もしVivadoが入ってないのであれば,インストールする必要があります.


設定が完了したので,同じくtest_board直下のprogram_flash_binfile.cmdを実行します.

ありれ,なにやらエラーが.


f:id:maruuusa83:20161108221444p:plain Booting from configuration memory device unsuccessful


なんか書き込みが止まってしまいます.

色々試してみましたが,どうも同じところで止まってしまいます.

仕方がないので,とりあえず無視してTeraTermでつないで,SDを挿して再起動してみました.

すると・・・


f:id:maruuusa83:20161108223249p:plain ブートするじゃないか







ログインして色々調べる

なんかよくわからないエラーがありましたが,無事Debianがブートしました(笑) Vivadoが2016.2じゃないことが原因でしょうか・・・

Baud rateを115200でシリアルで接続して,最初に作ったSDを挿してZynqberryを再起動すればアクセスできます.

root/rootでログインできました.ちょっと色々みていきます.

なんかこの時点で既にボードがほくほく温かいです.


ネットワークとか

LANのケーブルつないで,とりあえずifconfigしてみる.


f:id:maruuusa83:20161108232119p:plain ifconfigの結果


普通にDHCPでIPもらってきてますね.すばらしい.

というかシリアルで接続できるとディスプレイ用意しなくてもネットワーク設定できて最高ですね!!!!!


CPUとかメモリとか

nproccpuinfomeminfoを見てみました.


f:id:maruuusa83:20161108233929p:plain 上からnproc-cpuinfo-meminfo


あっクロック出ないのか・・・

トレンツのチュートリアルでは次のように言っているけど,こんなに遅いの?ほんと?

PS(CPU部分)のクロックは33.3333MHzですが、PLへはボード上ではクロックが接続されていないので、PLを動作させるにはPSが動作して、内部でFCLKをもらう必要があります。

参考になるかわかりませんが,ウチのi3-4130@3.40GHzのBogoMIPSは6799.62でした.

メモリはきちんと512MB全部みえるみたいですね.


/devのなかみ

どんなデバイスがいるのか覗いてみました.


f:id:maruuusa83:20161108235847p:plain ls /devの結果


おっ,xdevcfgがいますね.ということはPLのコンフィグ用のドライバが入っているってことかな?

あとで実験してみたいですね.







というわけで,ZynqberryをLinuxとして動くようにするまでやってみました.

これから少しずつ色々やってみようと思います.

ZedBoardとかより全然楽カモ



それでは

今回はこのへんで ノ


まるさ