メモ
とりあえず easy に BNUMNE をナニする事にしてメモを以下に控え。
Reading Gauche /vm/insn/BNUMNEI を参考に以下。
gosh> (disasm (lambda (x y) (if (= x y) #t #f))) main_code (name=#f, code=0x80f8ec0, size=7, const=0, stack=1): args: #f 0 LREF1-PUSH ; x 1 LREF0 ; y 2 BNUMNE 6 ; (= x y) 4 CONST-RET #t 6 CONSTF-RET #<undef> gosh>
ええと、= なら 4 でそうでなければ 6 ですか。BNUMNE のソースが以下な部分。
CASE(SCM_VM_BNUMNE) { ScmObj x, y = VAL0; POP_ARG(x); if (!Scm_NumEq(x, y)) { VAL0 = SCM_FALSE; FETCH_LOCATION(PC); } else { VAL0 = SCM_TRUE; INCR_PC; } NEXT1; }
これって以下だとどうなるんだろうか。
gosh> (disasm (lambda (x y) (if (not (= x y)) #t #f))) main_code (name=#f, code=0x80f8c80, size=7, const=0, stack=1): args: #f 0 LREF1-PUSH ; x 1 LREF0 ; y 2 BNUMNE 5 ; (= x y) 4 CONSTF-RET 5 CONST-RET #t #<undef> gosh>
なんだか not equal なので頭がこんがらがります。上のは = なら #t が戻りますが、下のは not = なら #t が戻る。説明は以下なカンジ?
BNUMNE では VAL0 レジスタにおかれた数値とスタック先頭の数値が不一致のときにはオペランド then を取り出しそれを PC レジスタに格納する。
一致したときはオペランド then を無視して PC レジスタをインクリメントし次の命令に進む。BNUMNE は Branch if NUMber Not Equal の略と思われる。
完全に BNUMNEI のパクリです。でも何故に Branch if Not なんだろう。