2011-01-31 10 views
7

一般に、ハードコードされた型ではなくConst(型なし)パラメータを利用してポインタを使用すると、多くの古典的なデザイントラップを回避しています。これにより、高度なグラフィカル関数を実行しながら、技術的な詳細をコンパイラに任せることができます。また、DelphiとFree Pascalで同じコードを最小限の変更で簡単に使用できるようにしました。しかし、最近私はEmbarcaderoのDelphiの進化に関する声明文と、これからの安全モデルのために疑問を持ち始めました。例えばconstパラメータとtypecastingは以前と同じようにDelphi 64bitで動作しますか?

、次の例concider:

Type TSomeDataProc = procedure (const aInput;var aOutput) of Object; 

(* Convert 8-bit pixel to 16-bit pixel *) 
Procedure TMyClass.ProcessSomeData08x565(Const aInput;var aOutput); 
var r,g,b: Byte; 
Begin 
    FPalette.ExportTriplets(Byte(aInput),r,g,b); 
    Word(aOutput):=(R SHR 3) SHL 11 or (G SHR 2) SHL 5 or (B SHR 3); 
End; 

(* Convert 16-bit pixel to 24-bit pixel *) 
Procedure TMyClass.ProcessSomeData565x888(Const aInput;var aOutput); 
Begin 
    With TRGBTriple(aOutput) do 
    Begin 
    rgbtRed:=(((word(aInput) and $F800) shr 11) shl 3); 
    rgbtGreen:= (((word(aInput) and $07E0) shr 5) shl 2); 
    rgbtBlue:= ((word(aInput) and $001f) shl 3); 
    end; 
End; 

現在同じ宣言を持つ2つの手順がありますが、彼らは非常に異なるピクセルデータを処理します。これにより、ルックアップテーブルを使用して正しい「コンバータ」メソッドを得ることの利点が得られます。これは、このように、コンストラクタまたはどこ画像ビットマップが割り当てられているいずれかで実行する必要があります。

Private 
FLookup: Array[pf8bit..pf32bit,pf8bit..pf32bit] of TSomeDataProc; 

Procedure TMyClass.Create; 
Begin 
    Inherited; 
    FLookup[pf8bit,pf16bit]:=ProcessSomeData08x565; 
    FLookup[pf16bit,pf24Bit]:=ProcessSomeData565x888; 
end; 

我々は単に正しい方法を検索し、それを使用するピクセルを変換する必要があるとき。構文はすべてのプロシージャで同じです。したがって、各プロシージャがどのように動作するかについて心配する必要はありません。私たちのクラスについては、すべて同じように見えます。

Procedure TMyClass.ConvertTo(aFormat:TpixelFormat); 
Begin 
// Get function for the correct pixel converter 
FConvertProc:=FLookup[CurrentFormat,aFormat]; 

//Use the pixel converter 
FConvertProc(GetSourcePixelAddr(x,y),GetTargetPixelAddr(x,y)); 
end; 

質問です:は型キャストこの種の(例えば:バイトまたは任意の定義されたレコードタイプへのconst)は、ウィル64の下で生き残りますか?私は個人的にはなぜそうではないのか分かりませんが、Embarcaderoは新しい "安全"モデルとポインタの使用に関してあまり漠然としているので、将来私のコードを守るのは少し難しいでしょう。

+1

私の人生のために私はあなたがそれを書いている理由を見ることはできません: 'ProcessSomeData(Const a Input :Byte; var aOutput:Word); ' –

+1

あなたはそのサンプルコードへのポインタを渡しませんか?好奇心の外に、ビルトインタイプのシステムに何が問題なのですか?ポインタのスピードは? –

+0

@Sertacスピードはここで同じです。このようなvar typelessパラメータとconst型なしパラメータと汎用ポインタの間には微妙な違いがあります。const型なしのパラメータは変更しないでください。ポインタは常に変更できます。このような型のないvarを使うと、コード中に^文字をいくつか入力することを避けることができます:PWord(aOutput)^:= 13例えば、生成されたアセンブラは単語(aOutput):= 13と同じになります。 –

答えて

3

このようなテクニックはRTLで使用されているので、多くのコードを壊すことなく、var型またはconst型のないパラメータを非難することはありません。

Embarcaderoは、できるだけ後方互換性を維持するために最善を尽くしています。

外部アセンブラの使用について最初に通知した後で、64ビットコンパイラにインラインasmをインクルードする必要があります。

このような変更は、64ビットモデルとは関係ありませんが、x86-64アセンブラは新しいコードの書き込みです。

公式のEmbarcaderoニュースグループのこの質問を投稿する必要がありますが、これについて心配する必要はありません。

+0

Allen Bauerは最近のポッドキャストhttp://www.delphi.orgで、インラインアセンブリーがDelphi 64ビットコンパイラーでサポートされていると報告しています(いくつかの制限があります)。 –

+0

@Remyはい、これは私が言ったことです。良いバックの動き。ニュースグループにDelphi 64ビットコンパイラのインラインアセンブラを削除するように言われたときに、いくつかのパニックがありました。新しい「スターター」エディションもまた良いものです。しかし、アレンがデルファイの未来とガベージコレクターについて話しているのを聞いたとき、私は再びパニックに陥ります。 ;) –

1

この場合ではなく、FPCが既にCONSTパラメータを変更していることに注意してください。

通常の場合、CONSTはすべての呼び出し規約でもはや参照によって保証されませんが、それぞれのABIが指定するものに従います。新しいパラメータ型、CONSTREFは参照によって保証されます。

互換性のすべての破損と同様に、TP/Delphiでは常にCONSTが参照されますが、TP/Delphiも常にx86です。

とりわけ、すべてのSTDCALL機能が変更されます。私は知らない。QueryInterface:

http://wiki.freepascal.org/User_Changes_Trunk#IInterface.QueryInterface.2C_._AddRef_and_._Release_definitions_have_been_changed

理由は、これらの例では、x86のABI情報は、クロスアーキテクチャ互換性がありません何かを汎用インタフェースを入力したことを、多かれ少なかれです。したがって、それが言語の一部であるのか、その言語のx86実装の一部であるのかを推測しなければなりません。

IUnknownは他のプラットフォームでも使用されています。 FirefoxのXPCOM

デルファイもこのような問題を抱えているかもしれませんが、私は主に明示的な呼び出し規約で関数/メソッドに影響を及ぼすと思いますが、内部の規約をニーズに合わせて変更することができるため、

関連する問題