Dec13th

CC65(CA65)

Top / CC65(CA65)

CC65(CA65) is

  • 各種ファミコンエミュレータで動作する.nesファイルを生成するassembler
  • パッケージがCC65なのでこのタイトルですが、中身はCA65(アセンブラ)なのであしからず

環境整備

  • Virtual NES
    • 作成した.nesファイルのエミュレート用

ビルド

  • NES研究室さんのサンプル内のmakefileを利用してmake
    • makeコマンドはcygwinを入れるかmake on Windowsを入れる
    • メモリマップを記述したmain.cfgも必要
  • 以下のファイルを同じディレクトリに入れて,cmd.exeからmakeを実行
    • CC65一式
    • 各種割り込みを記述した,mainとなる.asmファイル
    • makefile
    • main.cfg

文法

  • コントロールコマンド
    ドットから始まる命令
    C言語でのプリプロセッサに当たる処理を行う
  • ラベル
    文字列とコロンからなる
    ジャンプ命令の行き先やメモリに配置したデータへのアクセスに使用
  • 16進数値
    $を付ける
    例: $00、$81
  • 即値

    #を付ける
    例: #$00、 #$29

  • マクロ定数
    コードの任意の位置で定数名=数値で定義できる


コントロールコマンド

  • .segment
    セグメントを切り替える。
    データやニーモニックを配置するには、.cfgファイルでセグメントにメモリ割り当てをしておく必要がある。
  • .byte
    バイトサイズのデータ(8bit)を配置する。
    .cfgファイルでセグメントにメモリを割り当てる必要がある。
  • .word
    ワードサイズのデータ(16bit)を配置する。
    ラベルを指定した場合,そのラベルのアドレスが配置される。
  • .proc、.endproc
    サブルーチンを定義する。
  • .res
    メモリ領域を予約する
    変数領域として使用
  • .include
    他ファイルのソースコードを埋め込む


サウンド再生

  • 440Hz(ラ)の矩形波音を一瞬だけ再生
    • レジスタにセットする値x = 1790000 / (f * 32) - 1 = 126 = $007e
    • $4002にセットする値の下位8bit,$4003に上位8bitをセット

cfgファイル

  • メモリマップとセグメントを記述
    • ld65呼び出し時に--configオプションで指定
  • メモリマップ
    • 基本
      • MEMORYと中括弧で記述
      • 各項目はメモリマップ名とコロンで記述
  • start
    メモリの開始位置を指定
  • セグメント
    • 基本

用語

  • ネームテーブル
    画面上のどのブロックにどのキャラクタを配置するのかを指定するテーブル。

メモ

  • a: というラベルは使えない。おそらくaレジスタと競合していると思われる
  • BGM等の巨大なデータはラベルで細かく分けてアクセスする
  • :+ ,:-
    Unnamed Label、無名ラベル
    +・-の数だけ前・後ろの無名ラベル:に飛ぶ
  • @ラベル
    普通のラベル内だけで有効なラベル
    ループ等に用いられる
    Cheap Labelと呼ばれる
  • jmpで飛んだ先からrtsで帰ってこれる
    .proc~.endprocとの違いは不明
    jmpは一方通行もできるから、.procは戻ってくることを明確にしてるのかもしれない
  • .ifdef、.else、.endifを使えばプリプロセスで分岐制御できる
  • ?jsrでラベル以外の番地に飛ぶ方法
    8bitレジスタで16bitアドレスを計算する方法が分からんちん
  • プログラムのエントリーポイントはリセット割り込みの指定先アドレスになる。
  • $0000番地から4+12byte分の領域は、NES用ヘッダのデータが指定される。
    先頭4byteには固有の値が、残りの12byteにはバンクの数やミラーリング方式が指定される。
  • $FFFA番地からword3つ分の領域は、各種割り込みの分岐先が指定される。
    上から順に、VBlank割り込み、リセット割り込み、ハードウェア割り込み。
  • メモリサイズは8bit以上16bit以下なので、16bitの値で指定する。
    レジスタにメモリアドレスを格納する場合2つ使用する必要がある。
  • ROMとRAMの違いを押さえておく
  • VirtualNESだと.incbinにオフセット値を与える命令が使えない
    これが含まれると「未定義の命令が実行されました」のダイアログが出て止まる

リンク