Windows 認証エラーのデバッグDebugging Windows Authentication Errors

セキュリティ機構として Windows 認証を使用する場合、セキュリティ サポート プロバイダー インターフェイス (SSPI: Security Support Provider Interface) がセキュリティ プロセスを処理します。When using Windows authentication as a security mechanism, the Security Support Provider Interface (SSPI) handles security processes. SSPI 層でセキュリティエラーが発生すると、Windows Communication Foundation (WCF) によって表示されます。When security errors occur at the SSPI layer, they are surfaced by Windows Communication Foundation (WCF). このトピックでは、エラーの診断に役立つフレームワークと一連の質問を示します。This topic provides a framework and set of questions to help diagnose the errors.

Kerberos プロトコルの概要については、 kerberos の説明を参照してください。SSPI の概要については、「 sspi」を参照してください。For an overview of the Kerberos protocol, see Kerberos Explained; for an overview of SSPI, see SSPI.

Windows 認証の場合、WCF は通常、クライアントとサービスの間で Kerberos 相互認証を実行するネゴシエートセキュリティサポートプロバイダー (SSP) を使用します。For Windows authentication, WCF typically uses the Negotiate Security Support Provider (SSP), which performs Kerberos mutual authentication between the client and service. Kerberos プロトコルが使用できない場合、既定では、WCF は NT LAN Manager (NTLM) にフォールバックします。If the Kerberos protocol is not available, by default WCF falls back to NT LAN Manager (NTLM). ただし、Kerberos プロトコルのみを使用するように WCF を構成することができます (および Kerberos が使用できない場合は例外をスローします)。However, you can configure WCF to use only the Kerberos protocol (and to throw an exception if Kerberos is not available). Kerberos プロトコルの制限付き形式を使用するように WCF を構成することもできます。You can also configure WCF to use restricted forms of the Kerberos protocol.

デバッグ方法Debugging Methodology

基本的な方法は次のとおりです。The basic method is as follows:

  1. Windows 認証を使用しているかどうかを確認します。Determine whether you are using Windows authentication. 他の方式を使用している場合には、このトピックは該当しません。If you are using any other scheme, this topic does not apply.

  2. Windows 認証を使用していることがわかっている場合は、WCF 構成で Kerberos 直接またはネゴシエートのどちらを使用するかを決定します。If you are sure you are using Windows authentication, determine whether your WCF configuration uses Kerberos direct or Negotiate.

  3. 構成で Kerberos プロトコルと NTLM のどちらを使用しているかを確認した後は、現在のコンテキストでのエラー メッセージを理解できます。Once you have determined whether your configuration is using the Kerberos protocol or NTLM, you can understand error messages in the correct context.

Kerberos プロトコルと NTLM の可用性Availability of the Kerberos Protocol and NTLM

Kerberos SSP は、Kerberos キー配布センター (KDC: Key Distribution Center) として機能するドメイン コントローラーを必要とします。The Kerberos SSP requires a domain controller to act as the Kerberos Key Distribution Center (KDC). Kerberos プロトコルを使用できるのは、クライアントとサービスの両方がドメイン ID を使用している場合だけです。The Kerberos protocol is available only when both the client and service are using domain identities. 次の表に示すように、アカウントの他の組み合わせでは NTLM が使用されます。In other account combinations, NTLM is used, as summarized in the following table.

この表の列見出しは、サーバーが使用すると考えられるアカウントの種類を示します。The table headers show possible account types used by the server. 左の列は、クライアントが使用すると考えられるアカウントの種類を示します。The left column shows possible account types used by the client.

Local UserLocal User ローカル システムLocal System Domain UserDomain User Domain MachineDomain Machine
Local UserLocal User NTLMNTLM NTLMNTLM NTLMNTLM NTLMNTLM
ローカル システムLocal System 匿名 NTLMAnonymous NTLM 匿名 NTLMAnonymous NTLM 匿名 NTLMAnonymous NTLM 匿名 NTLMAnonymous NTLM
Domain UserDomain User NTLMNTLM NTLMNTLM KerberosKerberos KerberosKerberos
Domain MachineDomain Machine NTLMNTLM NTLMNTLM KerberosKerberos KerberosKerberos

具体的には、次の 4 種類のアカウントがあります。Specifically, the four account types include:

  • ローカルユーザー:コンピューターのみのユーザープロファイル。Local User: Machine-only user profile. 例 : MachineName\Administrator または MachineName\ProfileNameFor example: MachineName\Administrator or MachineName\ProfileName.

  • ローカルシステム:ドメインに参加していないコンピューター上のビルトインアカウントシステム。Local System: The built-in account SYSTEM on a machine that is not joined to a domain.

  • ドメインユーザー:Windows ドメインのユーザーアカウント。Domain User: A user account on a Windows domain. たとえば、DomainName\ProfileName のように指定します。For example: DomainName\ProfileName.

  • ドメインマシン:Windows ドメインに参加しているコンピューター上で実行されているコンピューター id を持つプロセス。Domain Machine: A process with machine identity running on a machine joined to a Windows domain. たとえば、MachineName\Network Service のように指定します。For example: MachineName\Network Service.

注意

サービス資格情報は、Open クラスの ServiceHost メソッドが呼び出されたときにキャプチャされます。The service credential is captured when the Open method of the ServiceHost class is called. クライアント資格情報は、クライアントがメッセージを送信するたびに読み取られます。The client credential is read whenever the client sends a message.

Windows 認証の一般的な問題Common Windows Authentication Problems

ここでは、Windows 認証に関するいくつかの一般的な問題と、考えられる解決策について説明します。This section discusses some common Windows authentication problems and possible remedies.

Kerberos プロトコルKerberos Protocol

Kerberos プロトコルでの SPN と UPN の問題SPN/UPN Problems with the Kerberos Protocol

Windows 認証を使用し、SSPI が Kerberos プロトコルを使用またはネゴシエートする場合、クライアント エンドポイントが使用する URL には、サービス URL 内のサービスのホストの完全修飾ドメイン名が含まれている必要があります。When using Windows authentication, and the Kerberos protocol is used or negotiated by SSPI, the URL the client endpoint uses must include the fully qualified domain name of the service's host inside the service URL. これは、サービスを実行しているアカウントが、コンピューターを Active Directory ドメインに追加したときに作成されるコンピューター (既定) のサービスプリンシパル名 (SPN) キーにアクセスできることを前提としています。これは、通常、ネットワークサービスアカウント。This assumes that the account under which the service is running has access to the machine (default) service principal name (SPN) key that is created when the computer is added to the Active Directory domain, which is most commonly done by running the service under the Network Service account. サービスがコンピューターの SPN キーにアクセスできない場合は、クライアントのエンドポイント ID でサービスを実行しているアカウントの正しい SPN またはユーザー プリンシパル名 (UPN: User Principal Name) を指定する必要があります。If the service does not have access to the machine SPN key, you must supply the correct SPN or user principal name (UPN) of the account under which the service is running in the client's endpoint identity. WCF での SPN と UPN の使用方法の詳細については、「サービス id と認証」を参照してください。For more information about how WCF works with SPN and UPN, see Service Identity and Authentication.

Web ファームや Web ガーデンなどの負荷分散シナリオでは、各アプリケーションに一意のアカウントを定義し、そのアカウントに SPN を割り当て、アプリケーションのサービスすべてがそのアカウントで実行されるようにするのが一般的です。In load-balancing scenarios, such as Web farms or Web gardens, a common practice is to define a unique account for each application, assign an SPN to that account, and ensure that all of the application's services run in that account.

サービスのアカウント用の SPN を取得するには、Active Directory ドメイン管理者である必要があります。To obtain an SPN for your service's account, you need to be an Active Directory domain administrator. 詳細については、「 Windows 用の Kerberos テクニカル補完」を参照してください。For more information, see Kerberos Technical Supplement for Windows.

Kerberos プロトコル ダイレクトでは Domain Machine アカウントでサービスを実行する必要があるKerberos Protocol Direct Requires the Service to Run Under a Domain Machine Account

この状況は、次のコードに示すように、ClientCredentialType プロパティが Windows に設定され、NegotiateServiceCredential プロパティが false に設定されている場合に発生します。This occurs when the ClientCredentialType property is set to Windows and the NegotiateServiceCredential property is set to false, as shown in the following code.

WSHttpBinding b = new WSHttpBinding();
// By default, the WSHttpBinding uses Windows authentication 
// and Message mode.
b.Security.Message.NegotiateServiceCredential = false;
Dim b As New WSHttpBinding()
' By default, the WSHttpBinding uses Windows authentication 
' and Message mode.
b.Security.Message.NegotiateServiceCredential = False

これを解決するには、ドメインに参加しているコンピューターで、Domain Machine アカウント (Network Service など) を使用してサービスを実行します。To remedy, run the service using a Domain Machine account, such as Network Service, on a domain joined machine.

委任には資格情報ネゴシエーションが必要Delegation Requires Credential Negotiation

委任で Kerberos 認証プロトコルを使用するには、資格情報ネゴシエーションを使用する Kerberos プロトコル ("マルチレッグ" Kerberos または "マルチステップ" Kerberos とも呼ばれます) を実装する必要があります。To use the Kerberos authentication protocol with delegation, you must implement the Kerberos protocol with credential negotiation (sometimes called "multi-leg" or "multi-step" Kerberos). 資格情報ネゴシエーションを使用しない Kerberos 認証 ("ワンショット" Kerberos または "シングルレッグ" Kerberos とも呼ばれます) を実装した場合は、例外がスローされます。If you implement Kerberos authentication without credential negotiation (sometimes called "one-shot" or "single-leg" Kerberos), an exception will be thrown.

資格情報ネゴシエーションを使用する Kerberos を実装するには、次の手順を実行します。To implement Kerberos with credential negotiation, do the following steps:

  1. AllowedImpersonationLevelDelegation に設定して委任を実装します。Implement delegation by setting AllowedImpersonationLevel to Delegation.

  2. 次のような SSPI ネゴシエーションが必要です。Require SSPI negotiation:

    1. 標準バインディングを使用する場合は、NegotiateServiceCredential プロパティを true に設定します。If you are using standard bindings, set the NegotiateServiceCredential property to true.

    2. カスタム バインドを使用する場合は、AuthenticationMode 要素の Security 属性を SspiNegotiated に設定します。If you are using custom bindings, set the AuthenticationMode attribute of the Security element to SspiNegotiated.

  3. 次のように、NTLM を使用できないようにすることで、SSPI ネゴシエーションで Kerberos を使用する必要があります。Require the SSPI negotiation to use Kerberos by disallowing the use of NTLM:

    1. NTLM を使用できないようにするには、コードで ChannelFactory.Credentials.Windows.AllowNtlm = false ステートメントを使用します。Do this in code, with the following statement: ChannelFactory.Credentials.Windows.AllowNtlm = false

    2. 構成ファイルで allowNtlm 属性を false に設定することもできます。Or you can do this in the configuration file by setting the allowNtlm attribute to false. この属性は、 <windows >に含まれています。This attribute is contained in the <windows>.

NTLM プロトコルNTLM Protocol

ネゴシエート SSP は NTLM にフォールバックするが、NTLM が無効になっているNegotiate SSP Falls Back to NTLM, but NTLM Is Disabled

プロパティAllowNtlmがにfalse設定されている場合、NTLM が使用されている場合、Windows Communication Foundation (WCF) がベストエフォートで例外をスローします。The AllowNtlm property is set to false, which causes Windows Communication Foundation (WCF) to make a best-effort to throw an exception if NTLM is used. ただし、このプロパティを false に設定しても、ネットワーク経由で NTLM 資格情報が送信されなくなるとは限りません。Note that setting this property to false may not prevent NTLM credentials from being sent over the wire.

NTLM へのフォールバックを無効にする方法を次に示します。The following shows how to disable fallback to NTLM.

CalculatorClient cc = new 
    CalculatorClient("WSHttpBinding_ICalculator");
cc.ClientCredentials.Windows.AllowNtlm = false;
Dim cc As New CalculatorClient("WSHttpBinding_ICalculator")
cc.ClientCredentials.Windows.AllowNtlm = False

NTLM ログオンが失敗するNTLM Logon Fails

サービスで、クライアント資格情報が無効です。The client credentials are not valid on the service. ユーザー名とパスワードが正しく設定されており、サービスを実行しているコンピューターに認識されているアカウントに対応していることを確認します。Check that the user name and password are correctly set and correspond to an account that is known to the computer where the service is running. NTLM では、指定された資格情報を使用してサービスのコンピューターにログオンします。NTLM uses the specified credentials to log on to the service's computer. 資格情報がクライアントを実行しているコンピューターで有効であっても、サービスのコンピューターでは無効な場合、このログオンは失敗します。While the credentials may be valid on the computer where the client is running, this logon will fail if the credentials are not valid on the service's computer.

匿名 NTLM ログオンが発生するが、既定では匿名ログオンが無効になっているAnonymous NTLM Logon Occurs, but Anonymous Logons Are Disabled by Default

次の例に示すように、クライアントの作成時に、AllowedImpersonationLevel プロパティを Anonymous に設定します。ただし、既定では、サーバーは匿名ログオンを許可しません。When creating a client, the AllowedImpersonationLevel property is set to Anonymous, as shown in the following example, but by default the server disallows anonymous logons. これは、AllowAnonymousLogons クラスの WindowsServiceCredential プロパティの既定値が false であるためです。This occurs because the default value of the AllowAnonymousLogons property of the WindowsServiceCredential class is false.

匿名ログオンを有効にすることを試みるクライアント コードを次に示します (既定のプロパティは Identification です)。The following client code attempts to enable anonymous logons (note that the default property is Identification).

CalculatorClient cc =
    new CalculatorClient("WSHttpBinding_ICalculator");
cc.ClientCredentials.Windows.AllowedImpersonationLevel =
System.Security.Principal.TokenImpersonationLevel.Anonymous;
Dim cc As New CalculatorClient("WSHttpBinding_ICalculator")
cc.ClientCredentials.Windows.AllowedImpersonationLevel = _
System.Security.Principal.TokenImpersonationLevel.Anonymous

サーバーによって匿名ログオンを有効にするように既定値を変更するサービス コードを次に示します。The following service code changes the default to enable anonymous logons by the server.

Uri httpUri = new Uri("http://localhost:8000/");
ServiceHost sh = new ServiceHost(typeof(Calculator), httpUri);
sh.Credentials.WindowsAuthentication.AllowAnonymousLogons = true;
Dim httpUri As New Uri("http://localhost:8000/")
Dim sh As New ServiceHost(GetType(Calculator), httpUri)
sh.Credentials.WindowsAuthentication.AllowAnonymousLogons = True

権限借用の詳細については、「委任と偽装」を参照してください。For more information about impersonation, see Delegation and Impersonation.

もう 1 つの方法として、SYSTEM ビルトイン アカウントを使用する Windows サービスとしてクライアントを実行します。Alternatively, the client is running as a Windows service, using the built-in account SYSTEM.

その他の問題Other Problems

クライアント資格情報が正しく設定されていないClient Credentials Are Not Set Correctly

Windows 認証では、WindowsClientCredential ではなく、ClientCredentials クラスの ClientBase<TChannel> プロパティによって返された UserNamePasswordClientCredential インスタンスを使用します。Windows authentication uses the WindowsClientCredential instance returned by the ClientCredentials property of the ClientBase<TChannel> class, not the UserNamePasswordClientCredential. 誤りのあるコード例を次に示します。The following shows an incorrect example.

CalculatorClient cc = new
    CalculatorClient("WSHttpBinding_ICalculator");            
cc.ClientCredentials.UserName.UserName = GetUserName(); // wrong!
cc.ClientCredentials.UserName.Password = GetPassword(); // wrong!
Dim cc As New CalculatorClient("WSHttpBinding_ICalculator")
cc.ClientCredentials.UserName.UserName = GetUserName() ' wrong!
cc.ClientCredentials.UserName.Password = GetPassword() ' wrong!

正しいコード例を次に示します。The following shows the correct example.

CalculatorClient cc = new 
    CalculatorClient("WSHttpBinding_ICalculator");
// This code returns the WindowsClientCredential type.            
cc.ClientCredentials.Windows.ClientCredential.UserName = GetUserName();
cc.ClientCredentials.Windows.ClientCredential.Password = GetPassword();
Dim cc As New CalculatorClient("WSHttpBinding_ICalculator")
' This code returns the WindowsClientCredential type.            
cc.ClientCredentials.Windows.ClientCredential.UserName = GetUserName()
cc.ClientCredentials.Windows.ClientCredential.Password = GetPassword()

SSPI を使用できないSSPI Is Not Available

サーバーとして使用する場合、次のオペレーティングシステムは Windows 認証をサポートしていません。Windows XPWindows XPHome edition、 Windows XPWindows XP Media Center Edition、およびWindows VistaWindows Vistahome edition。The following operating systems do not support Windows authentication when used as a server: Windows XPWindows XP Home Edition, Windows XPWindows XP Media Center Edition, and Windows VistaWindows VistaHome editions.

異なる ID を使用した開発と展開Developing and Deploying with Different Identities

アプリケーションを 1 台のコンピューターで開発し、別のコンピューターに展開し、異なるアカウントの種類を使用して各コンピューターで認証を行う場合、動作の違いが発生する場合があります。If you develop your application on one machine, and deploy on another, and use different account types to authenticate on each machine, you may experience different behavior. たとえば、SSPI Negotiated 認証モードを使用して Windows XP Professional コンピューターでアプリケーションを開発するとします。For example, suppose you develop your application on a Windows XP Pro machine using the SSPI Negotiated authentication mode. ローカル ユーザー アカウントを使用して認証する場合は、NTLM プロトコルが使用されます。If you use a local user account to authenticate with, then NTLM protocol will be used. アプリケーションを開発した後は、ドメイン アカウントで実行されるサービスを Windows Server 2003 コンピューターに展開します。Once the application is developed, you deploy the service to a Windows Server 2003 machine where it runs under a domain account. この時点で、クライアントは Kerberos とドメイン コントローラーを使用するため、このサービスを認証できなくなります。At this point the client will not be able to authenticate the service because it will be using Kerberos and a domain controller.

関連項目See also