2021年2月第1週レポート
インプット
📝 VuetifyのIconで自作のSVGを使いたい
VuetifyのIconsコンポーネントはとても便利で、スロットに文字列を指定するだけでMaterial Design Iconsにあるアイコンを表示することができます。
使っていく上で自作のSVGアイコンを使えるようにしたくなるのは自然だと思うのですが 、方法を探してみるとドンピシャの記事を見つけました。
具体的な方法は基本記事にある通りなのですが、自分はNuxt.jsを利用しているので出力されたcssは/assts/css/style.cssに追記し、フォントデータの置き場所だけ少し調整しました。
📝 JavaScriptでゼロパディング
ゼロパティングとは目的の桁数に数値が満たないときにゼロで埋めるというものです。例えば数値を5桁で表示する必要があるとしたときには125
は00125
に変換する、といったものです。
JavaScriptではpadStart
メソッドでゼロパティングを実現できます。
const str = '125';
console.log(str.padStart(5, '0'));
// output: "00125"
第一引数には変換後の文字列の長さを、第二引数にはパディングに使う文字列を指定します。
参考 String.prototype.padStart() - JavaScript | MDN (mozilla.org)
アウトプット
🛠️ RustでNESエミュレータを作っている
今週は少し進捗がありまして、nestestのROMを起動できるようになりました!
nestestとは、NESで使われているCPUである6502(のカスタム)に備わっている命令セットの動作をテストできるROMです。命令実行時のフラグやレジスタ状態を確認してくれるスグレモノです。
くぅ〜、おしい #NES pic.twitter.com/50XSNIKW8R
— d_yama (@dy_karous) February 5, 2021
うわっ…私のCPU、バグすぎ…?#NES pic.twitter.com/K8ihywpSwf
— d_yama (@dy_karous) February 7, 2021
といってもテストがパスしたわけではなく、画面表示と操作ができるようになっただけなのですが…。しかも選択カーソルであるアスタリスクの場所がおかしいので画面表示も完全にうまくいったとは言えないですね。CPU側に原因があるのかPPU側に原因があるのかちょっと検討がつかないので、まずはnestestのテストが全てパスするようCPUの修正に着手しています。
修正においてはリファレンスモデルとして使っているFCEUXのデバッガを眺めながら各種レジスタやCPUステータスを比較しています。この比較作業を少しでも容易にするためデバッグ出力周りの機能を強化しました。プログラムカウンタから読み取った命令とそのアドレッシングモード、また命令実行前の各種レジスタの値を標準出力に出力できるようにしています。
ステップ実行printfデバッグマン #NES pic.twitter.com/l0Tk1Lf0W2
— d_yama (@dy_karous) February 4, 2021
CPUのステータスレジスタは構造体で、アドレッシングモードや命令はenumを使って表現しています。これらに対してDebugトレイトを実装して、インスタンスをそのままprintln!
で出力できるようにしています。
参考までにアドレッシングモードは次のようなコードになっています。
pub enum Addressing {
Accumulator,
Immediate(u16),
Absolute(u16),
Zeropage(u16),
AbsoluteX(u16),
AbsoluteY(u16),
ZeropageX(u16),
ZeropageY(u16),
Indirect(u16),
IndirectIndexed(u16),
IndexedIndirect(u16),
}
impl fmt::Debug for Addressing {
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
match *self {
Addressing::Accumulator =>
write!(f, "Accumulator"),
Addressing::Immediate(addr) =>
write!(f, "Immediate {:#06X}", addr),
Addressing::Absolute(addr) =>
write!(f, "Absolute {:#06X}", addr),
Addressing::Zeropage(addr) =>
write!(f, "Zeropage {:#06X}", addr),
Addressing::AbsoluteX(addr) =>
write!(f, "AbsoluteX {:#06X}", addr),
Addressing::AbsoluteY(addr) =>
write!(f, "AbsoluteY {:#06X}", addr),
Addressing::ZeropageX(addr) =>
write!(f, "ZeropageX {:#06X}", addr),
Addressing::ZeropageY(addr) =>
write!(f, "ZeropageY {:#06X}", addr),
Addressing::Indirect(addr) =>
write!(f, "Indirect {:#06X}", addr),
Addressing::IndirectIndexed(addr) =>
write!(f, "IndirectIndexed {:#06X}", addr),
Addressing::IndexedIndirect(addr) =>
write!(f, "IndexedIndirect {:#06X}", addr)
}
}
}
自動導出でもデバッグできないこともないのですが、アドレス値は16進数で表示したほうがやはり比較しやすいのでこのように実装しました。値をもつenumに対するパターンマッチングは個人的に書き味が好きで気に入りました。