フォト
無料ブログはココログ

MyList

« 2024年11月 | トップページ | 2025年2月 »

2025年1月

2025年1月26日 (日)

CH559picoでTOYOSHIKI-BASIC

今年の目標の一つ
積んCPUを使ってみることにした。

2020年に買ったCH559pico を使ってみることにした。
CH559picoボード↓
Ch559pico

CH559はざっくり8051core+USB I/F+Flash 60KB+RAM 6KBだ。

単体でBASIC 52が動きそうだ。
USB I/FがあるのでCDCクラスを実装すると、USBコネクタに刺すだけでお手軽BASIC マイコンになりそうだ。
昔、EZ-USBで遊んでいたときに、思いついたのだが、EZ-USBはメモリが少なくて実現出来なかった。

CH55xシリーズはarduinoIDEで開発できることがわかった。
しかも、CDCクラスのシリアルデバイスとして認識する。
何とお手軽

ここを参考にCH55xduinoをインストールし、blinkを書き込むとあっけなく動いた。
先達に感謝

arduinoでシリアルの入出力は、aerial.begin()で初期化してaerial.Read、Serial.write()でデータを送受信する。
USBSerialでは関数に先頭にUSBをつけてUSBSerial_Read()
Serial.Begin()での初期化は必要ない。

こんなスケッチを書いUSBシリアルのループバックテストをやってみた。

void setup() {
  while (!USBSerial());
}


// the loop function runs over and over again forever
void loop() {
  uint8_t c;

  if (USBSerial_available()) {
    c=USBSerial_read();
    USBSerial_write('[');
    USBSerial_write(c);
    USBSerial_write(']');
  }
}

1字づつ送受信出来ることが分かった。
大量のデータを転送するなら、パケットサイズを大きくして一度の転送で多くのデータを送受信した方が効率が良い。
今回は、BASICのコンソールに使うので、速度よりリアルタイム性が重要だ。BASIC52を実装する前に、
鈴木哲也氏の著書「タイニーBASICをCで書く」で、豊四季BASICがarduinoに実装されているのを思い出したので、これを動かしてみることにした。

arduino用の豊四季BASICはこのページ(https://vintagechips.wordpress.com/2015/12/06/豊四季タイニー BCbasic確定版 /)のリンクからダウンロードできる。

豊四季BASICは、c_getch, c_putch, c_kbhit, rand, を環境に合わせて実装すれば動くようになっている。
書籍では、Serial.read(), Serial.write(), Serial.available()を使う方法が説明されている。

今回は、USBシリアルを使用するので、

#define c_getch(c) USBSerial_read(c)
#define c_putch() USBSerial_write()
#define c_kbhit()  USBSerial_available()

rand() はCH55xduinoのコンパイラsdccにもあるのでそのまま使える。
rand()に使用するシードの初期化は、randomseed()になるべくランダムな値を使用しする。
組み込み用のCPUではアナログポートから読み取った値を使う方法が紹介されている。
今回は、USBシリアルの初期化が終了した時刻を取得してシードとした。

randomseed(moicros());

arduinoIDEのシリアルの設定をCOMx(CH559picoが認識されているポート)にすると、シリアルモニタが使える。
arduino用豊四季BASICは、ttbasic.ino 内のloop() から、ttbasic.ccpのbasic() 関数を呼び出している。 
arduinoIDEで検証(Check)すると、キャストのwarningが出るが、コンパイルできて、USB経由で書き込むことができる。
書き込むと自動的にリセットされて、バナーが表示されるはずだが、いくら待っても表示されない。

ENTERを連打すると、バナーが表示され、> OK がたくさん表示される。
コマンドを入力してもエコーバックされず、一定数キー入力するとまとめて入力されているようだ。

テストプログラムを書いて調べたら、
loop()の外でUSBSerial_read()を呼ぶと1文字づつ取得できないことが判った。

豊四季BASICはbasic()関数内の無限ループで、c_gets()で1行取得し、処理するようになっている。
c_gets()関数も、関数内のwhileループでENTERまで文字をバッファに格納するようになっている。

loop()関数の中なら1文字づつ取得できるので、basic()を初期化部、1行取得部、処理部に分けて、初期化部をsetup()に書いて、loop()内で1行取得して、BASICの処理部を呼ぶようにしたら、動くようになった。

ところが、INPUT A を実行しようとすると、1文字づつ取得できない。
調べてみると、INPUTコマンドで入力する数字を数値に変化する関数 getnum()のwhileループ内で文字入力していることが分かった。

c_gets(),getnum()で使用する文字入力でloop()を呼ぶようにすればよさそうだが、loop()関数内でarduinoの内部関数を呼んでいると良くないことが起こりそうだ、と考えソースを見てみたら、

main()関数の中の無限ループがloop()を呼ぶシンプル構成だった。
CH55xduinoの main()の部分

void main(void) {
  init();

  //!!!initVariant();

  setup();

  for (;;) {
    loop();
    if (1) {
#ifndef USER_USB_RAM
      USBSerial_flush();
#endif
      // serialEvent();
    }
  }

  //    return 0;
}
 

よく見ると、無限ループの中でUSBSerial_refresh()
を実行していることを発見した。
どうやらこれが解決方法のようだ。

ということで、
c_gets(), getnum()の中のループから、USBSerial_flush()を実行するように書き換えたら動いた。

BASICが動くようになったらお約束の8queen問題を解くプログラムを書てみたら挙動がおかしい。
同じプログラムを豊四季BASIC linux版で動かしたら正常だった。
A=5, B=2, @(2)=3 のとき、A-@(B)の結果が 0 になっている。

つづく...



最近の投稿】【最近のCPUボード】【最近のプログラミング】【2019の投稿】【2018の投稿】【2017の投稿】【2016の投稿】【2015の投稿

« 2024年11月 | トップページ | 2025年2月 »