CPU実験室

誰も見向きもしない古いCPUをいじって動かしてみようというプロジェクトです

メモリモデル


SDCCでMCS51をターゲットにコンパイルするときはメモリモデルの選択ができます。
通常はsmallモデルで行えば、データ領域は8031内蔵RAM領域に取られコード効率も良いようです

例えば静的変数 char str[16] を含むソースを 

    sdcc -mmcs51 --model-small --code-loc 0x8000

コンパイルした時の中間アセンブリコードは:

     225 ;--------------------------------------------------------
     226 ; internal ram data
     227 ;--------------------------------------------------------
     228 .area DSEG (DATA)
000008 229 _str::
000008 230 .ds 16

 

たしかに内蔵RAM領域に配置されますが、ここは128バイトしかないのでうっかり 
char str[256] なんてやるとリンク時に


?ASlink-Error-Could not get 256 consecutive bytes in internal RAM for area DSEG.+ C:\PROGRA~1\SDCC\bin\sdld.exe -nf "****.lk" returned errorcode 1
と当然エラーが出ます。

 

大きいデータ領域が必要な場合はlargeモデルでコンパイルすることになります。
char str[256]を含むソースを 
    sdcc -mmcs51 --model-large --code-loc 0x8000 --xram-loc 0xf000 

コンパイルすると


    256 ;--------------------------------------------------------
    257 ; external ram data
    258 ;--------------------------------------------------------
    259 .area XSEG (XDATA)
00F000  260 _str::
00F000  261 .ds 256

という具合に外部データメモリ上に配置されます

ただし今回のボードではプログラム空間とデータ空間を1つの物理メモリ上にオーバーライドしてしまっているので、例えばコードは0x8000番地から、データは0xf000番地からというように被らないアドレスへ明示的にロケートしてあげなければなりません。

これって元々アーキテクチャ的に分離していた空間を、ハード的に同一視されるようにした後、またソフト的に分離し直してるわけでずいぶん無駄なことをしています。
本来であればプログラム空間とデータ空間にそれぞれ別にメモリを実装、ただしプログラム空間にユーザプログラムをDLLもしたいので、そのときだけプログラムメモリがデータメモリとすり替わる、というような作りにしたいところです。

 

f:id:O3I:20190828214646j:plain