Math-Pach とは、MSX−BASIC の数値演算ルーチンの中核をなすもので、これらを機械語から呼び出すことにより、簡単に浮動小数点演算や三角関数ルーチンを利用することができます。
Math-Pack での実数演算はすべて BCD (Binary Coded Decimal = 2 進化 10 進法) 表現によって行われます。また、実数表現には "単精度" と "倍精度" の 2 種類があり、単精度 (6 桁) は 4 バイト、倍精度 (14 桁) は 8 バイトで表現されます (図 A.1、図 A.2)。
1 つの実数は、符号部、指数部、仮数部から成り立っています。符号部とはこの仮数の符号を表し、0 ならば正、1 ならば負となります。指数部はバイナリ表現であり、+63 乗〜 -63 乗まで表すことができます (図 A.3)。倍精度実数の有効範囲を図 A.4 に示します。
Math-Pack では、演算の対象となるメモリがあらかじめ決められています。このメモリエリアを "DAC (Decmal ACcumlator) (F7F6H)" 、それと演算対象となる数値を格納するエリアを "ARG (F847H)" といいます。たとえば乗算ルーチンの場合、DAC に入っている数と ARG に入っている数の積が計算され、その結果が DAC に入ることになります。
DAC には、単精度実数、倍精度実数、2 バイト整数を格納することができますが、これらのうちのどれが入っているのかを示すために "VALTYP (F663H)" が使われ、それぞれの場合について 4, 8, 2 の値が入ります。
単精度実数と倍精度実数は、いずれも DAC の先頭から数値を格納しなければなりません。ただし、2 バイト整数の場合だけは、下位、上位を DAC+2, +3 に格納して下さい。
Math-Pack は BASIC の内部ルーチンであるため、エラーが起きた場合 (0 除算やオーバーフローなど) はそれに応じたエラールーチンへ自動的に分岐し、その後 BASIC コマンドレベルに戻ります。それを避けたいときは、H.ERRO (FFB1H) を書き換えてください。
●Math-Pack のワークエリア
ラベル | アドレス | サイズ | 意味 |
VALTYP | F663H | 1 | DAC に入っている数値の形式を表す |
DAC | F7F6H | 16 | BCD 形式の浮動小数点アキュムレータ |
ARG | F847H | 16 | DAC の演算対象 |
●Math-Pack エントリ
基本演算
ラベル | アドレス | 機能 |
DECSUB | 268CH | DAC ← DAC-ARG |
DECADD | 269AH | DAC ← DAC+ARG |
DECNRM | 26FAH | DAC を正規化する (*1) |
DECROU | 273CH | DAC を四捨五入する |
DECMUL | 27E6H | DAC ← DAC*ARG |
DECDIV | 289FH | DAC ← DAC/ARG |
レジスタはいずれも保存されない
*1 仮数部の不要な 0 を取り去ること (0.00123 → 0.123E-2)
関数 1
ラベル | アドレス | 機能 | 変化するレジスタ |
COS | 2993H | DAC ← COS(DAC) | すべて |
SIN | 29ACH | DAC ← SIN(DAC) | すべて |
TAN | 29FBH | DAC ← TAN(DAC) | すべて |
ATN | 2A14H | DAC ← ATN(DAC) | すべて |
LOG | 2A72H | DAC ← LOG(DAC) | すべて |
SQR | 2AFFH | DAC ← SQR(DAC) | すべて |
EXP | 2B4AH | DAC ← EXP(DAC) | すべて |
RND | 2BDFH | DAC ← RND(DAC) | すべて |
変化するレジスタすべてとは、A,B,C,D,E,H,L の各レジスタを指す
関数 2
ラベル | アドレス | 機能 | 変化するレジスタ |
SIGN | 2E71H | A ← DAC の符号 | A |
ABSFN | 2E82H | DAC ← ABS(DAC) | すべて |
NEG | 2E8DH | DAC ← NEG(DAC) | A,H,L |
SGN | 2E97H | DAC ← SGN(DAC) | A,H,L |
変化するレジストリすべてとは、A,B,C,D,E,H,L の各レジスタを指す
SGN は、結果が 2 バイト整数で表されるので注意
移動
ラベル | アドレス | 機能 | 対象 | 変化するレジスタ |
MAF | 2C4DH | ARG ← DAC | 倍精度 | A,B,D,E,H,L |
MAM | 2C50H | ARG ← [HL] | 倍精度 | A,B,D,E,H,L |
MOV8DH | 2C53H | [DE] ← [HL] | 倍精度 | A,B,D,E,H,L |
MFA | 2C59H | DAC ← ARG | 倍精度 | A,B,D,E,H,L |
MFM | 2C5CH | [HL] ← DAC | 倍精度 | A,B,D,E,H,L |
MMF | 2C67H | [HL] ← DAC | 倍精度 | A,B,D,E,H,L |
MOV8HD | 2C6AH | [HL] ← [DE] | 倍精度 | A,B,D,E,H,L |
XTF | 2C6FH | [SP] ←→ DAC | 倍精度 | A,B,D,E,H,L |
PHA | 2CC7H | ARG → [SP] | 倍精度 | A,B,D,E,H,L |
PHF | 2CCCH | DAC → [SP] | 倍精度 | A,B,D,E,H,L |
PPA | 2CDCH | [SP] → ARG | 倍精度 | A,B,D,E,H,L |
PPF | 2CE1H | [SP] → DAC | 倍精度 | A,B,D,E,H,L |
PUSHF | 2EB1H | DAC → [SP] | 単精度 | D,E |
MOVFM | 2EBEH | DAC ← [HL] | 単精度 | B,C,D,E,H,L |
MOVFR | 2EC1H | DAC ← (CBED) | 単精度 | D,E |
MOVRF | 2ECCH | (CBED) ← DAC | 単精度 | B,C,D,E,H,L |
MOVRMI | 2ED6H | (CBDE) ← [HL] | 単精度 | B,C,D,E,H,L |
MOVRM | 2EDFH | (BCDE) ← [HL] | 単精度 | B,C,D,E,H,L |
MOVMF | 2EE8H | [HL] ← DAC | 単精度 | B,C,D,E,H,L |
MOVE | 2EEBH | [HL] ← [DE] | 単精度 | B,C,D,E,H,L |
VMOVAM | 2EEFH | ARG ← [HL] | VALTYP | B,C,D,E,H,L |
MOVVFM | 2EF2H | [DE] ← [HL] | VALTYP | B,C,D,E,H,L |
VMOVE | 2EF3H | [HL] ← [DE] | VALTYP | B,C,D,E,H,L |
VMOVFA | 2F05H | DAC ← ARG | VALTYP | B,C,D,E,H,L |
VMOVFM | 2F08H | DAC ← [HL] | VALTYP | B,C,D,E,H,L |
VMOVAF | 2F0DH | ARG ← DAC | VALTYP | B,C,D,E,H,L |
VMOVMF | 2F10H | [HL] ← DAC | VALTYP | B,C,D,E,H,L |
( ) 内の 4 レジスタ名は、左から (符号 + 指数部)、(仮数部 1,2 桁)、(仮数部 3.4 桁) 、(仮数部 5,6 桁) を示す単精度実数である
移動の対象が VALTYP となっているものは、VALTYP (F663H 番地) に示されている型に応じた移動 (2,4,8 バイト) を行う
比較
ラベル | アドレス | 対象 | 左辺 | 右辺 | 変化するレジスタ |
FCOMP | 2F21H | 単精度実数 | CBED | DAC | HL |
ICOMP | 2F4DH | 2 バイト整数 | DE | HL | HL |
XDCOMP | 2F5CH | 倍精度実数 | ARG | DAC | すべて |
A=1 → 左辺 < 右辺
A=0 → 左辺 = 右辺
A=-1 → 左辺 > 右辺
単精度の比較で、左辺の CBED とは各レジスタに、それぞれ(符号 + 指数部)、(仮数部 1,2 桁)、(仮数部 3.4 桁) 、(仮数部 5,6 桁) が入ることを意味する
浮動小数点入出力
ラベル | アドレス | 機能 |
FIN | 3299H | 浮動小数点を表す文字列を、実数表現に変換して DAC に格納する |
エントリー条件 HL ← 文字列の先頭アドレス A ← 文字列の先頭文字 リターン条件 DAC ← 実数 C ← FFH : 小数点なし、0 : 小数点あり B ← 小数点以降のケタ数 D ← 総ケタ数 |
ラベル | アドレス | 機能 |
FOUT | 3425H | DAC に入っている実数表現の数を文字列に変換する (フォーマット指定なし) |
PUFOUT | 3426H | DAC に入っている実数表現の数を文字列に変換する (フォーマット指定あり) |
エントリー条件 A ← 変換のフォーマット bit7 0 : フォーマット指定なし、 1 : フォーマット指定あり bit6 0 : コンマによる区切りなし、 1 : 3 ごとにコンマで区切る bit5 0 : 意味無し、 1 : 先頭のスペースを "*" でうめる bit4 0 : 意味無し、 1 : 数値の前に "$" を付ける bit3 0 : 意味無し、 1 : 正の数の場合も符号 "+" を付ける bit2 0 : 意味無し、 1 : 数値の後ろに符号を付ける bit1 0 : 未使用 bit0 0 : 固定小数点、 1 : 浮動小数点 B ← 小数点を含まない、小数点以前のケタ数 C ← 小数点を含む、小数点以降のケタ数 リターン条件 HL ← 文字列の先頭アドレス |
ラベル | アドレス | 機能 |
FOUTB | 371AH | DAC+2,3 に入っている 2 バイト整数を 2 進数表現の文字列に変換する |
FOUTO | 371EH | DAC+2,3 に入っている 2 バイト整数を 8 進数表現の文字列に変換する |
FOUTH | 3722H | DAC+2,3 に入っている 2 バイト整数を 16 進数表現の文字列に変換する |
エントリー条件 DAC+2 ← 2 バイト整数 VALTYP ← 2 リターン条件 HL ← 文字列の先頭アドレス |
出力ルーチンにおける文字列先頭アドレスは、通常 FBUFFR (F7C5H 番地から) 内となるが、場合により先頭アドレスは前後する
FOUTB,FOUTO,FOUTH に限らず DAC+2 に入れた整数を扱うときには、VALTYP (F663H) に必ず 2 を入れること
型変換
ラベル | アドレス | 機能 |
FRCINT | 2F8AH | DAC を 2 バイト整数にする (DAC+2,3) |
FRCSNG | 2FB2H | DAC を単精度実数にする |
FRCDBL | 303AH | DAC を倍精度実数にする |
FIXER | 30BEH | DAC ← SGN(DAC)*INT(ABS(DAC)) |
レジスタは、いずれも保存されない
整数演算
ラベル | アドレス | 機能 | 変化するレジスタ |
UMULT | 314AH | DE ← BC*DE | A,B,C,D,E |
ISUB | 3167H | HL ← DE-HL | すべて |
IADD | 3172H | HL ← DE+HL | すべて |
IMULT | 3193H | HL ← DE*HL | すべて |
IDIV | 31E6H | HL ← DE/HL | すべて |
IMOD | 323AH | HL ← DE mod HL (DE ← DE/HL) | すべて |
べき乗
ラベル | アドレス | 機能 | 基数 | 指数 | 結果 |
SNGEXP | 37C8H | 単精度実数のべき乗を求める | DAC | ARG | DAC |
DBLEXP | 37D7H | 倍精度実数のべき乗を求める | DAC | ARG | DAC |
INTEXP | 383FH | 2 バイト整数のべき乗を求める | DE | HL | DAC |