3.1.4.1 Application Invocation of the .NET NegotiateStream Protocol

The .NET NegotiateStream Protocol is triggered by an invocation from the application while in the Uninitialized state. If an application invocation is received when the Stream State is not equal to Uninitialized, an error MUST be returned to the application. The application specifies an underlying TCP connection to the server, the desired name to be used for client authentication, a channel binding token, the target name of the server, a required protection level, and an allowed impersonation level. The Underlying TCP Connection, Required Protection Level, Allowed Impersonation Level, Channel Binding Token, and Target Name MUST be set based on these inputs. The application-specified desired_name MUST be passed to the GSS_Acquire_cred function ([RFC2743] section 2.1.1). If the Required Protection Level is None, the implementation MUST pass a desired_mechs parameter indicating the NTLM mechanism. Otherwise, the implementation MUST pass a desired_mechs parameter indicating the SPNEGO mechanism. The cred_usage parameter MUST be set to INITIATE-ONLY and the lifetime_req parameter MUST be set to 0.

If the function returns any major_status other than GSS_S_COMPLETE, the implementation MUST notify the application of the failure without sending anything over the Underlying TCP Connection. Otherwise, the implementation MUST store the returned credential handle as the Client Credentials, and MUST set the Stream State to CreatingSecurityToken. The implementation MUST pass the Client Credentials to the GSS_Init_sec_context function ([RFC2743] section 2.2.1). The input_context_handle parameter MUST be GSS_C_NO_CONTEXT. The targ_name parameter MUST be the Target Name. The mech_type parameter MUST be the same as that passed to GSS_Acquire_cred. The deleg_req_flag MUST be true if and only if Allowed Impersonation Level is Delegation. The conf_req_flag MUST be true if and only if the Required Protection Level is EncryptAndSign. The integ_req_flag MUST be true if and only if the Required Protection Level is Sign or EncryptAndSign. The mutual_req_flag, replay_det_req_flag, and sequence_req_flag MUST be true. The anon_req_flag MUST be false. The chan_bindings parameter MUST be the Channel Binding Token. The input_token MUST be NULL, and the lifetime_req MUST be 0.

If the conf_avail return value is true, the integ_avail return value will also be true, and the Negotiated Protection Level is EncryptAndSign. If the conf_avail return value is false and the integ_avail return value is true, the Negotiated Protection Level is Sign. Otherwise, the Negotiated Protection Level is None.