program Project1; uses System.SysUtils; type TIntegerHelper = record helper for Integer function ToString: String; end; function TIntegerHelper.ToString: String; begin Result := IntToStr(Self); end; var i: Integer; begin i := $ff Writeln(i.ToString); // ここ end.
上記のコード "ここ" とコメントしている部分は
lea eax, [iのアドレス] call TIntegerHelpder.ToString
こんな風になってるかなと思ったのですが、さて。
mov [$00423ed8], $000000ff lea edx, [ebp - $14] mov eax, $00423ed8 // ここ call TIntegerHelper.ToString mov edx, [ebp - $14] mov eax, [$0041e618] call @Write0UString call @WriteLn call @_IOTest
こうなっていました。
lea ではなく、普通に eax にアドレスを代入していました。
これは、 i がグローバル変数だからだと思います。多分。(実効アドレスを計算する必要がない)
↓こんな風に procedure を呼ぶようにしてやると
procedure Test;
var
i: Integer;
begin
i := $ff;
Writeln(i.ToString);
end;
begin
Test;
end.
こうなってました。
lea eax, [ebp - $04] // ここ call TIntegerHelper.ToString
大体予想通りです。
ただ、これらの結果は全部 debug ビルドなので、release にすると少し変わってるかもしれません。
ということで、record helper は Self (= eax) に、変数の値を入れて、関数を呼んでいる、という実装でした。
0 件のコメント:
コメントを投稿