Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
Help us understand the problem. What is going on with this article?

豊四季タイニーBASIC Arduino版のフリーエリアを増やす実験(1)

More than 3 years have passed since last update.

はじめに

ソシム刊 鈴木哲哉『タイニーBASICをCで書く』で解説されている『豊四季タイニーBASIC』はコンパクトで遊ぶには面白い処理系なのですが、そのバリエーションのひとつである Arduino版は BASIC のプログラムを格納するバッファが 256バイトと極端に小さく設定されており、いくらか大きなプログラムでも実行することができません。
豊四季タイニーBASIC での 256バイトというのがどのような大きさなのかというと、

hello.bas(19バイト)
10 PRINT "hello, world"
zundoko.bas(96バイト)
10 R=RND(2)-1; IF R PRINT "ZUN ",; GOTO 30
20 PRINT "DOKO ",
30 N=16*R+N/2; IF N#15 GOTO 10
40 PRINT "KI.YO.SHI!"
fizzbuzz.bas(112バイト)
10 FOR I=1 TO 100
20 F=I/3*3=I; B=I/5*5=I
30 IF F PRINT "fizz",
40 IF B PRINT "buzz",
50 IF F+B=0 PRINT I,
60 PRINT
70 NEXT I
sieve.bas(165バイト)
100 INPUT N
110 I=2
120 IF I>N STOP
130 M=1
140 IF (M+1)*(M+1)<=I LET M=M+1; GOTO 140
150 J=2
160 IF J>M GOTO 190
170 IF I/J*J=I GOTO 200
180 J=J+1; GOTO 160
190 PRINT I
200 I=I+1; GOTO 120
n-queens.bas(324バイト)
100 INPUT N
110 P=1
120 I=0
130 I=I+1; @(I)=1
140 J=1
150 IF J>=I GOTO 180
160 IF (@(I-J)=@(I))+(@(I-J)+J=@(I))+(@(I-J)-J=@(I))GOTO 260
170 J=J+1; GOTO 150
180 IF I<N GOTO 130
190 PRINT P; P=P+1
200 FOR J=1 TO N; FOR K=1 TO N
220 IF @(J)=K PRINT "Q",
230 IF @(J)#K PRINT ".",
240 NEXT K; PRINT ; NEXT J; PRINT ; PRINT
260 @(I)=@(I)+1; IF @(I)<=N GOTO 140
270 I=I-1; IF I>0 GOTO 260
fibonacci.bas(353バイト)
100 INPUT N
110 P=0; D=0
120 FOR I=0 TO N
130 IF I<=1 LET @(P)=I; GOTO 210
140 C=0
150 FOR J=0 TO D
160 @(2*J+P)=@(2*J+P)+@(2*J+(P=0))+C
170 C=@(2*J+P)>=10;
180 @(2*J+P)=@(2*J+P)-10*C
190 NEXT J
200 IF C#0 D=D+1; @(2*D+P)=C; @(2*D+(P=0))=0
210 PRINT I,": ",
220 FOR J=D TO 0 STEP -1
230 PRINT #1,@(2*J+P),
240 NEXT J
250 PRINT
260 P=(P=0)
270 NEXT I
calendar.bas(371バイト)
100 INPUT Y
110 H=100; F=400
120 W=Y+(Y-1)/4-(Y-1)/H+(Y-1)/F
130 INPUT M
140 FOR I=1 TO M
150 D=31-(I=4)-(I=6)-(I=9)-(I=11)
160 IF I#2 GOTO 180
170 D=D-3+(Y/4*4=Y)-(Y/H*H=Y)+(Y/F*F=Y)
180 W=W+D
190 NEXT I
200 W=W-D; W=W-W/7*7
210 FOR I=1-W TO D
220 IF (I<1)PRINT "  ",; GOTO 240
230 PRINT #2,I,
240 IF ((I+W)/7*7=(I+W))+(I=D)PRINT ; GOTO 260
250 PRINT " ",
260 NEXT I

以上の例を見ていただければ、256バイトでは凡そ大きなプログラムは組めないであろうことはご理解いただけるものと思います。

豊四季タイニーBASIC はソース中の

#define SIZE_LIST 256 //List buffer size

というマクロで BASIC プログラムを格納するバッファのサイズを決めており、これを大きな値にすれば BASIC プログラムを格納するバッファの拡大することは可能なのですが、Arduino IDE 1.6.8 でマイコンボードに "Arduino/Genuino Uno" を選択してビルドした場合の IDE の出力するメッセージの内容が

最大32,256バイトのフラッシュメモリのうち、スケッチが8,790バイト(27%)を使っています。
最大2,048バイトのRAMのうち、グローバル変数が1,449バイト(70%)を使っていて、ローカル変数で599バイト使うことができます。

となっており、あまり RAM に余裕がありません。「ローカル変数で599バイト使うことができます。」にある 599バイトというのはプログラムの実行に必要なスタック領域も含んでいるため 599バイト全てを使用することはできません。仮にスタック領域に 256バイトを確保したとすると BASIC プログラムを格納するバッファの拡張に使用できる容量は 343バイトという計算となりますが、BASIC プログラムを格納するバッファ以外にも、配列変数の数やサブルーチンとFORループの段数など拡張したいと思われる要素は他にもあり、余裕のあるものではありません。
今回は実験として、Arduino IDE のビルド時に出力するメッセージ「ローカル変数で599バイト使うことができます。」がどこまで大きくできるかを検証します。一応の目標として、現状より 1000バイト多い 1599バイトを目指すものとします。

『豊四季タイニーBASIC Arduino版のフリーエリアを増やす実験(2)』につづく

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away