次の方法で共有


WPF 部分信頼セキュリティ

一般に、悪質な被害を防止するため、インターネット アプリケーションによる重要なシステム リソースへの直接アクセスは制限する必要があります。 既定では、HTML およびクライアント側のスクリプト言語は、重要なシステム リソースにはアクセスできません。 Windows Presentation Foundation (WPF) ブラウザー ホスト アプリケーションは、ブラウザーから起動できるため、同様に、一連の制限に従う必要があります。 この制限を適用するために、WPF は Code Access Security (CAS) と ClickOnce の両方に依存します (「WPF のセキュリティ方針 - プラットフォーム セキュリティ」を参照)。 既定では、ブラウザー ホスト アプリケーションは、インターネット、ローカル イントラネット、ローカル コンピューターのどこから起動されたかに関係なく、インターネット ゾーン CAS のアクセス許可セットを要求します。 無制限ではないアクセス許可の元で実行するアプリケーションは、部分信頼で実行しているものと見なされます。

WPF は、さまざまなサポートを提供し、最大限の機能を部分信頼で安全に使用できることを実現します。また、CAS と共に、部分信頼のプログラミングへの追加サポートを提供します。

このトピックは、次のセクションで構成されています。

  • WPF 機能の部分信頼サポート

  • 部分信頼のプログラミング

  • アクセス許可の管理

WPF 機能の部分信頼サポート

次の表は、インターネット ゾーン アクセス許可セットの制限内で、安全に使用できる Windows Presentation Foundation (WPF) の高レベル機能の一覧です。

表 1 : 部分信頼で安全な WPF 機能

機能エリア

機能

全般

ブラウザー ウィンドウ

起点サイト アクセス

IsolatedStorage (512 KB 制限)

UIAutomation プロバイダー

コマンド実行

入力方式エディター (IME)

タブレット スタイラスとインク

マウス キャプチャと移動イベントを使用してシミュレートされたドラッグ/ドロップ

OpenFileDialog

XAML 逆シリアル化 (XamlReader.Load 経由)

Web 統合

ブラウザー ダウンロード ダイアログ

トップレベル ユーザーが実行するナビゲーション

mailto: リンク

Uniform Resource Identifier パラメーター

HTTPWebRequest

IFRAME でホストされた WPF コンテンツ

フレームを使用した同一サイトの HTML ページのホスト

WebBrowser を使用した同一サイトの HTML ページのホスト

Web サービス (ASMX)

Web サービス (Windows Communication Foundation を使用)

スクリプト

ドキュメント オブジェクト モデル

ビジュアル

2D と 3D

アニメーション

メディア (起点サイトおよびドメイン間)

イメージング/オーディオ/ビデオ

読み取り

FlowDocument

XPS ドキュメント

埋め込みフォントとシステム フォント

CFF フォントと TrueType フォント

編集

スペル チェック

RichTextBox

プレーンテキストおよびインク クリップボード サポート

ユーザーが実行する貼り付け

選択した内容のコピー

コントロール

コントロール全般

この表は、高レベルの WPF 機能を示しています。 詳細情報に関して Windows Software Development Kit (SDK) では、WPF の各メンバーが必要とするアクセス許可について文書化しています。 また、以下の機能については、特別な考慮事項など、部分信頼での実行に関するさらに詳細な情報があります。

次の表は、インターネット ゾーン アクセス許可セットの制限内では、安全に実行できない WPF 機能の一覧です。

表 2 : 部分信頼で安全でない WPF 機能

機能エリア

機能

全般

ウィンドウ (アプリケーションで定義したウィンドウおよびダイアログ ボックス)

SaveFileDialog

ファイル システム

レジストリへのアクセス

ドラッグ アンド ドロップ

XAML シリアル化 (XamlWriter.Save 経由)

UIAutomation クライアント

ソース ウィンドウ アクセス (HwndHost)

完全な音声サポート

Windows フォームの相互運用性

ビジュアル

ビットマップ効果

イメージ エンコード

編集

リッチ テキスト形式のクリップボード

完全な XAML サポート

部分信頼のプログラミング

XBAP アプリケーションでは、コードが既定のアクセス許可セットを越える場合、セキュリティ ゾーンによって動作が異なります。 ユーザーがアプリケーションをインストールしようとすると警告が表示されることもあります。 ユーザーは、インストールを続行するか取り消すかを選択できます。 次の表は、各セキュリティ ゾーンのアプリケーション動作と、完全信頼を受け取るアプリケーションで行う必要のある操作を示しています。

セキュリティ ゾーン

動作

完全信頼を受け取るための操作

ローカル コンピューター

完全信頼を自動的に受け取る

アクションは必要ありません。

イントラネットおよび信頼されたサイト

完全信頼のプロンプトを表示

ユーザーへのプロンプトにソースが表示されるように、証明書を使用して XBAP を署名します。

インターネット

"信頼されていません" というメッセージが表示され、失敗する

証明書を使用して XBAP に署名します。

メモメモ

前の表で説明した動作は、ClickOnce 信頼済み配置モデルに従っていない完全信頼の XBAP の動作です。

一般に、設定されているアクセス許可を超える可能性のあるコードは、スタンドアロン アプリケーションとブラウザー ホスト アプリケーションの間で共有される通常のコードと考えられます。 CAS と WPF には、このシナリオを処理するためのいくつかの手法が用意されています。

CAS を使用したアクセス許可の検出

状況によっては、ライブラリ アセンブリで共有されるコードを、スタンドアロン アプリケーションと XBAPs の両方で使用することができます。 この場合、コードは、アプリケーションに付与されているアクセス許可セットの制限よりも高い許可を要求する機能を実行する可能性があります。 アプリケーションは、Microsoft .NET Framework セキュリティを使用して、特定のアクセス許可を得ているかどうかを検出できます。 特に、必要なアクセス許可のインスタンスで Demand メソッドを呼び出して、特定のアクセス許可を持っているかどうかをテストすることができます。 これを次の例に示します。このコードでは、ローカル ディスクにファイルを保存できるかどうかを照会します。


Imports System.IO ' File, FileStream, StreamWriter
Imports System.IO.IsolatedStorage ' IsolatedStorageFile
Imports System.Security ' CodeAccesPermission, IsolatedStorageFileStream
Imports System.Security.Permissions ' FileIOPermission, FileIOPermissionAccess
Imports System.Windows ' MessageBox

Namespace SDKSample
    Public Class FileHandling
        Public Sub Save()
            If IsPermissionGranted(New FileIOPermission(FileIOPermissionAccess.Write, "c:\newfile.txt")) Then
                ' Write to local disk
                Using stream As FileStream = File.Create("c:\newfile.txt")
                Using writer As New StreamWriter(stream)
                    writer.WriteLine("I can write to local disk.")
                End Using
                End Using
            Else
                MessageBox.Show("I can't write to local disk.")
            End If
        End Sub

        ' Detect whether or not this application has the requested permission
        Private Function IsPermissionGranted(ByVal requestedPermission As CodeAccessPermission) As Boolean
            Try
                ' Try and get this permission
                requestedPermission.Demand()
                Return True
            Catch
                Return False
            End Try
        End Function



...


    End Class
End Namespace
using System.IO; // File, FileStream, StreamWriter
using System.IO.IsolatedStorage; // IsolatedStorageFile
using System.Security; // CodeAccesPermission, IsolatedStorageFileStream
using System.Security.Permissions; // FileIOPermission, FileIOPermissionAccess
using System.Windows; // MessageBox

namespace SDKSample
{
    public class FileHandling
    {
        public void Save()
        {
            if (IsPermissionGranted(new FileIOPermission(FileIOPermissionAccess.Write, @"c:\newfile.txt")))
            {
                // Write to local disk
                using (FileStream stream = File.Create(@"c:\newfile.txt"))
                using (StreamWriter writer = new StreamWriter(stream))
                {
                    writer.WriteLine("I can write to local disk.");
                }
            }
            else
            {
                MessageBox.Show("I can't write to local disk.");
            }
        }

        // Detect whether or not this application has the requested permission
        bool IsPermissionGranted(CodeAccessPermission requestedPermission)
        {
            try
            {
                // Try and get this permission
                requestedPermission.Demand();
                return true;
            }
            catch
            {
                return false;
            }
        }



...


    }
}

アプリケーションに必要なアクセス許可がない場合、Demand の呼び出しによって、セキュリティ例外がスローされます。 それ以外の場合は、アクセス許可が付与されます。 IsPermissionGranted は、この動作をカプセル化し、必要に応じて true または false を返します。

機能の正常な低下

コードに必要なアクセス許可があるかどうかを検出できることは、別のゾーンから実行できるコードにとって重要です。 ゾーンが 1 つであることを検出している間に、可能であれば、ユーザーに代替手段を提供する方がより望ましいでしょう。 たとえば、完全信頼アプリケーションを使用すると、通常、ユーザーは任意の場所にファイルを作成できますが、部分信頼アプリケーションでは、ファイルを作成できるのは分離ストレージだけです。 ファイルを作成するコードが、完全信頼 (スタンドアロン) アプリケーションと部分信頼 (ブラウザー ホスト) アプリケーションとで共有されるアセンブリ内にある場合、ユーザーが両方のアプリケーションでファイルを作成できるようにするには、適切な場所にファイルを作成する前に、この共有されるコードが、部分信頼で実行されているのか完全信頼で実行されているのかを検出する必要があります。 次のコードで両方の例を示します。


Imports System.IO ' File, FileStream, StreamWriter
Imports System.IO.IsolatedStorage ' IsolatedStorageFile
Imports System.Security ' CodeAccesPermission
Imports System.Security.Permissions ' FileIOPermission, FileIOPermissionAccess
Imports System.Windows ' MessageBox

Namespace SDKSample
    Public Class FileHandlingGraceful
        Public Sub Save()
            If IsPermissionGranted(New FileIOPermission(FileIOPermissionAccess.Write, "c:\newfile.txt")) Then
                ' Write to local disk
                Using stream As FileStream = File.Create("c:\newfile.txt")
                Using writer As New StreamWriter(stream)
                    writer.WriteLine("I can write to local disk.")
                End Using
                End Using
            Else
                ' Persist application-scope property to 
                ' isolated storage
                Dim storage As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication()
                Using stream As New IsolatedStorageFileStream("newfile.txt", FileMode.Create, storage)
                Using writer As New StreamWriter(stream)
                    writer.WriteLine("I can write to Isolated Storage")
                End Using
                End Using
            End If
        End Sub

        ' Detect whether or not this application has the requested permission
        Private Function IsPermissionGranted(ByVal requestedPermission As CodeAccessPermission) As Boolean
            Try
                ' Try and get this permission
                requestedPermission.Demand()
                Return True
            Catch
                Return False
            End Try
        End Function



...


    End Class
End Namespace
using System.IO; // File, FileStream, StreamWriter
using System.IO.IsolatedStorage; // IsolatedStorageFile
using System.Security; // CodeAccesPermission
using System.Security.Permissions; // FileIOPermission, FileIOPermissionAccess
using System.Windows; // MessageBox

namespace SDKSample
{
    public class FileHandlingGraceful
    {
        public void Save()
        {
            if (IsPermissionGranted(new FileIOPermission(FileIOPermissionAccess.Write, @"c:\newfile.txt")))
            {
                // Write to local disk
                using (FileStream stream = File.Create(@"c:\newfile.txt"))
                using (StreamWriter writer = new StreamWriter(stream))
                {
                    writer.WriteLine("I can write to local disk.");
                }
            }
            else
            {
                // Persist application-scope property to 
                // isolated storage
                IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForApplication();
                using (IsolatedStorageFileStream stream = 
                    new IsolatedStorageFileStream("newfile.txt", FileMode.Create, storage))
                using (StreamWriter writer = new StreamWriter(stream))
                {
                    writer.WriteLine("I can write to Isolated Storage");
                }
            }
        }

        // Detect whether or not this application has the requested permission
        bool IsPermissionGranted(CodeAccessPermission requestedPermission)
        {
            try
            {
                // Try and get this permission
                requestedPermission.Demand();
                return true;
            }
            catch
            {
                return false;
            }
        }



...


    }
}

多くの場合、部分信頼の代替を見つける必要があります。

イントラネットなどの制御された環境では、カスタム マネージ フレームワークを、クライアント ベース全体にわたって、global assembly cache (GAC) にインストールすることができます。 このライブラリは、完全信頼を必要とするコードを実行することができ、AllowPartiallyTrustedCallersAttribute を使用することで、部分信頼だけを付与されているアプリケーションからも参照できます (詳細については、「セキュリティ (WPF)」および「WPF のセキュリティ方針 - プラットフォーム セキュリティ」を参照してください)。

ブラウザー ホストの検出

CAS を使用したアクセス許可の確認は、アクセス許可ごとの確認が必要な場合に適した手法です。 ただし、この手法は、通常の処理の一部として例外をキャッチすることに依存し、一般には推奨されません。また、パフォーマンスの問題を抱える可能性があります。 代わりに、XAML browser application (XBAP) がインターネット ゾーンのサンドボックス内でのみ実行される場合、BrowserInteropHelper.IsBrowserHosted プロパティを使用することができ、これは XAML browser applications (XBAPs) に true を返します。

メモメモ

IsBrowserHosted は、アプリケーションがブラウザーで実行されているかどうかを区別するだけで、実行中のアプリケーションに付与されているアクセス許可セットについての区別はしません。

アクセス許可の管理

既定では、XBAPs は、部分信頼 (既定のインターネット ゾーン アクセス許可セット) で実行されます。 ただし、アプリケーションの要求に応じて、アクセス許可セットを既定から変更することができます。 たとえば、XBAPs がローカル イントラネットから起動される場合、より高いアクセス許可セットを利用できます。これを次の表に示します。

表 3 : ローカル イントラネットのアクセス許可とインターネットのアクセス許可

アクセス許可

属性

ローカル イントラネット

インターネット

DNS

アクセス DNS サーバー

環境変数

読み取り

ファイル ダイアログ

開く

ファイル ダイアログ

制限なし

分離ストレージ

ユーザーによるアセンブリの分離

分離ストレージ

不明な分離

分離ストレージ

無制限のユーザー クォータ

メディア

安全なオーディオ、ビデオ、イメージ

印刷

既定の印刷

印刷

安全な印刷

リフレクション

出力

セキュリティ

マネージ コードの実行

セキュリティ

付与されたアクセス許可の Assert

ユーザー インターフェイス

制限なし

ユーザー インターフェイス

安全なトップレベル ウィンドウ

ユーザー インターフェイス

独自のクリップボード

Web ブラウザー

HTML への安全なフレーム ナビゲーション

メモメモ

切り取りと貼り付けは、ユーザーが開始する部分信頼でのみ許可されます。

アクセス許可を増やす必要がある場合は、プロジェクト設定と ClickOnce アプリケーション マニフェストを変更する必要があります。 詳細については、「WPF XAML ブラウザー アプリケーションの概要」を参照してください。 次のドキュメントが役に立つこともあります。

XBAP が完全信頼を必要とする場合、同じツールを使用して要求されたアクセス許可を強化できます。 ただし、XBAP は、イントラネットのローカル コンピューター上にインストールされ、ローカル コンピューターから起動されるか、ブラウザーの信頼されたサイトまたは許可されたサイトのリストに含まれる URL から起動する場合にのみ、完全信頼を受け取ります。 アプリケーションがイントラネットまたは信頼されたサイトからインストールされる場合、アクセス許可が昇格されたことを通知する標準の ClickOnce プロンプトがユーザーに表示されます。 ユーザーは、インストールを続行するか取り消すかを選択できます。

または、任意のセキュリティ ゾーンで完全信頼配置用の ClickOnce 信頼済み配置モデルを使用することもできます。 詳細については、「信頼されたアプリケーションの配置の概要」および「セキュリティ (WPF)」を参照してください。

参照

概念

セキュリティ (WPF)

WPF のセキュリティ方針 - プラットフォーム セキュリティ

WPF のセキュリティ方針 - セキュリティ エンジニアリング