10

私は自分のプロジェクトでこのコードを使用しています:

var
  P: TPoint;

MyControl.Perform(WM_LBUTTONDOWN, 0, Longint(PointToSmallPoint(P)));

コンパイラは私に警告を出します:

[Warning]: Unsafe typecast of 'TSmallPoint' to 'Integer'

ただし、同じコードがControls.pas 警告なしで使用されています。たとえば、TControl.BeginDragメソッドでは次のようになります。

....
Perform(WM_LBUTTONUP, 0, Longint(PointToSmallPoint(P)));

ユニットに何も表示{$warnings off}されませんControls.pas

コンパイラが警告を表示するのに、警告をスキップするのはなぜControls.pasですか?
このコードは安全ではありませんか?


編集:私のプロジェクトオプション->コンパイラメッセージ->安全でない型キャストがチェックされています(デフォルトではチェックされていません)。
たぶんこれが@Davidと@Kenが警告を再現できなかった理由です。

4

2 に答える 2

11

これはunsafe typecast、[プロジェクト]->[オプション]->[コンパイラメッセージ]で警告がチェックされているために発生します。これはチェックを外しても安全です(その上にunsafe typeありunsafe codeます。(以下を参照してください)。

安全でない型キャストがチェックされていないため、警告を再現できませんでした。もはや適用されません。(Delphi for .NETを開発しているときに、Delphi 6または7で.net互換性のために追加され、.NETとWin32の両方で機能するコードを簡単に記述できるようになりました。Delphifor.NET製品が廃止されたため、その警告(およびその上の2つ)はもう適用されません)。これらの3つの警告の「安全でない」は、「管理されていない」を意味する「安全でない」の.NETの意味を使用します。

Delphi 7ヘルプファイルから(「コンパイラの変更」を検索)(私の強調):

Delphi dcc32コンパイラは、Unsafe_Type、Unsafe_Code、およびUnsafe_Castの3つの追加のコンパイラ警告をサポートするようになりました。 これらの警告はデフォルトで無効になっていますが、コンパイラディレクティブ{$ WARN UNSAFE_CODE ON}、コンパイラコマンドラインスイッチ(dcc32 -W + UNSAFE_CODE)、およびIDEの[プロジェクト]|[オプション]|[コンパイラメッセージ]ページで有効にできます。

この機能は、コードをMicrosoftの.NETプラットフォームの管理された実行環境に移植するのに役立つことを目的としています。管理された実行環境では、「安全でない」とは、Just In Time(JIT)コンパイラーによって実行される静的分析中に操作を検証できないことを意味します。JITコンパイラが実行時の動作を検証するための十分な情報がないため、このようなコードはセキュリティリスクをもたらす可能性があります。安全でないコードの例には、ポインタ操作やメモリの上書きが含まれます。

于 2012-12-28T23:28:23.513 に答える
5

安全でない型キャスト警告を有効にして、コントロールユニットを自分でコンパイルすると、警告が表示されます。ただし、ビルド済みの.dcuファイルをリンクすると、警告は表示されません。コンパイラは、コンパイルするユニットに対してのみ警告を発します。

原則として、RTLユニットとVCLユニットは、多数のヒントと警告を生成します。それらを再コンパイルする必要がある場合は、常にそれらのユニットのヒントと警告をオフにする必要があります。


警告に関する現代のドキュメントには、次のように書かれています。

静的コード分析でメモリが上書きされないことを証明できないデータ型または操作を使用しました。たとえば、あるレコードを別のレコードに、またはあるインスタンスを別のインスタンスにケース化(原文のまま)したとします。

そして、その警告はあなたのコードに適用されます。あなたのコードは安全ではありません。コンパイラは、2つの16ビット整数を32ビット整数にオーバーレイすることが正しいことを確認できません。したがって、コンパイラは警告します。コードが正しいかどうかを判断するのはあなた次第です。

現在、警告は主に.netコンパイラを対象としているようです。それでも、Win32コンパイラにとっては意味があります。あるレコードを別のレコードにオーバーレイすることは、疑わしい動作です。

于 2012-12-28T23:21:47.450 に答える