>>739 所詮はその程度の知識よのぅ。まんまと釣り針にかかるとは。
もう何年もアセンブラは書いてないが、当時他のコンパイラに比べて最適化された
コードを吐くと言われたx86のMSCあたりでさえ、MSCの出したアセンブラソースを
雛形に手で直していくと、自己書き換えとかトリッキーな手段を使わなくとも、
生成されるバイナリ比較で1/2〜1/3以下になった。
アセンブラならCフラグの状態でエラーの有無を返せるが、Cでは実装により決ま
ったレジスタで返さなければならない。 汎用レジスタは関数内で破壊される可能
性があるので、上位関数では関数の前後で変数の保持に使えない。
例えば、x86系の多くのコンパイラは、16bit値ならAXレジスタ、32bit値ならDX:AX
レジスタで値を返すが、戻り値がvoid型の関数として定義しても、コンパイラは
これらのレジスタは破壊される前提でコードを吐く。
したがって、register宣言を付けてレジスタ渡にしても、実際は関数の呼び出し
前に、スタック上のローカル変数ないしグローバル変数から汎用レジスタへの
コピーが行われるため速くはならない。おまけに、レジスタ渡しにしたところで、
その関数内から別の関数を呼ぶと、変数渡しに割り当てられたレジスタが破壊
される想定が必要なので、結局、コンパイラは関数内でスタック領域へ変数の
コピーを置く領域を割り当て、ストアしなければならない。
さらに、レジスタ渡しの関数をあちこちで呼び出すと、上記の関数呼び出し
の際のレジスタ代入コードがばら撒かれ、コード量も増える。
アセンブラでは関数ごとに、呼び出し前後のレジスタ保持ルールや、同じint型
の値でも返すレジスタを任意に選択するなど、一歩間違うとバグるリスクと引き
換えに、最大限の最適化ができるが、Cコンパイラはそこまで賢くはなれない。