Policy Support

Wsutil processes policy specified in input metadata, and generates helper routines for service model support.

How to use policy support in wsutil

Developers should follow the following steps to use the policy support in wsutil compiler:

  • Collect all the input metadata files necessary for the targeted web service.
  • Compile all the collected WSDL/XSD/policy files using wsutil.exe. Wsutil generates one set of stub file and header file for each input WSDL and XSD files.
  • Inspect generated header file, all the policy helper routine names are listed in the comment section at the beginning of the header file.
  • Use bindingName_CreateServiceProxy helper routine to create service proxy.
  • Use bindingName_CreateServiceEndpoint helper routine to create service endpoint.
  • Fill in WS_bindingTemplateType_BINDING_TEMPLATE structure specified in the method signature. Developers can provide additional channel properties and/or security properties as needed.
  • Call the helper routines, on successful return service proxy or service endpoint is created.

Following sections describes related topics in detail.

Handle policy input

The following are compiler options related to policy processing.

By default, wsutil will always generate policy templates unless called with the "/nopolicy" option. Policy can be embedded as part of a WSDL file or can be created separately as a policy metadata file which wsutil takes as input. The compiler option "/wsp:" is used to indicate that specified input metadata is a policy file. Wsutil generates potential policy related helpers with the following compilation:

wsutil /wsdl:trusted.wsdl /wsdl:trusted1.wsdl

wstuil /wsdl:input.wsdl /wsp:policy.wsp

No policy helpers are generated when the "/nopolicy" option is used as in the following example.

wsutil /nopolicy /wsdl:trusted.wsdl /wsdl:trusted1.wsdl

Metadata Mapping page details the mapping between metadata constructs with different binding types.

Three categories of policy settings can be specified in policy settings:

Binding template type

There are limited numbers of bindings that are supported in wsutil. All those supported combinations of these bindings are listed in WS_BINDING_TEMPLATE_TYPE definition. For example, for the following binding in wsdl

<soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http" />

Wsutil generates WS_HTTP_BINDING_TEMPLATE_TYPE binding template type for this binding.

Policy descriptions

With the input policy setting, wsutil generates a set of policy descriptions describing the input policy, including the template type, as well as the values specified in the policy. For example, for input

<wsdl:binding...>
  <soap11:binding.../> =< WS_ENVELOPE_VERSION_SOAP_1_1
</wsdl:binding>

wsutil generates channel property description like:

WS_ENVELOPE_VERSION_SOAP_1_1,
{
  WS_CHANNEL_PROPERTY_ENVELOPE_VERSION,
  (void*)&locaDefinitions.policies.bindHostedClientSoap.envelopeVersion, //points to the WS_ENVELOPE_VERSION_SOAP_1_1 value above
  sizeof(&localDefinitions.policies.bindHostedClientSoap.envelopeVersion),
},

All the policy settings (channel properties, security properties and security binding properties) in one binding is aggregated into one WS_bindingTemplateType_POLICY_DESCRIPTION structure. WS_BINDING_TEMPLATE_TYPE specifies the different binding policy combinations wsutil supports.

Template structure to be filled in by application

Policy description contains all the policy information specified in input metadata for a given binding, but there are information that cannot be represented in the policy yet requires user input when using those policies setting to create service proxy and/or service endpoint. For example, application must provide credentials for HTTP header authentication.

Application needs to fill in template structure, named WS_bindingTemplateType_BINDING_TEMPLATE for each different binding template type, defined in webservices.h:

struct WS_bindingTemplateType_BINDING_TEMPLATE
{
  WS_CHANNEL_PROPERTIES channelProperties;
  WS_SECURITY_PROPERTIES securityProperties;
  possible_list_of_SECURITY_BINDING_TEMPLATEs;
  ...
};

The list of security binding templates is optional depends on the matched security binding. For example, WS_SSL_TRANSPORT_SECURITY_BINDING_TEMPLATE field is presented in WS_HTTP_SSL_BINDING_TEMPLATE for application to provide SSL related security binding information, including the credential information.

Application needs to fill in all the fields in this structure before calling into webservices template APIs. Additional security properties, as well as security binding properties that are not representable in policy needs to be filled in, and webservices APIs merges the two set of properties in runtime. Fields can be zeroed out if not applicable. For example, securityProperties can be zeroed out if no additional security properties are needed.

Helper routines and policy description declaration in header files

wsutil creates helper routine to facilitate better support in service model layer, such that application can create service proxy and service endpoint easier. The policy description is also exposed such that application can use them directly. A CreateSerivceProxy help routine looks like:

HRESULT bindingName_CreateServiceProxy(
  __in_ecount_opt(propertyCount) const WS_PROXY_PROPERTY* properties,
  __in const ULONG propertyCount,
  __in WS_constraintName_BINDING_TEMPLATE* templateValue,
  __deref_out WS_SERVICE_PROXY** serviceProxy,
  __in_opt WS_ERROR* error);

Developers are encouraged to use those helper routines, though they can also directly use the underneath runtime routine provided by webservices.dll. Developers are not encouraged to use the policy descriptions directly when programming using service model layer.

Policy description references are also generated in the header for advanced user. If developers do not use service model functionalities, they can use the policy descriptions directly.

struct {
  ...
  struct {
    ...
    } contracts;
  struct {
    WS_bindingTemplateType_POLICY_DESCRIPTION bindingName;
    ...
    } policies;
  }

Definition prototypes in stub files

A single policy description structure field per binding and its internally referenced helper descriptions are created in the local prototype structure. The policy descriptions are generated in the file where the WS_CONTRACT_DESCRIPTION is generated. Generally developers do not need to inspect the stub file during development, though stub file contains all the details about the policy specifications.

struct {
  ...
  struct {
  ... } contracts;
  ...
 struct {
      struct {
        hierarchy of policy template descriptions;
        } bindingName;
      ...
      list of bindings in the input wsdl file.
  } policies;
} fileNameLocalDefinitions;

Helper routines implementation in the stub files

Wsutil generates helper routines to simplify application calls to WsCreateServiceProxy and creating WS_SERVICE_ENDPOINT base on information provided in policy settings.

Depends on the binding constraints specified for the given port, the first argument is different according to the template structure. Following example assumes HTTP transport, signature for service proxy creation is similar with one additional channel type parameter.

HRESULT bindingName_CreateServiceProxy(
    __in WS_bindingTemplateType_BINDING_TEMPLATE* templateValue,
    __in_ecount_opt(propertyCount) const WS_PROXY_PROPERTY* properties,
    __in const ULONG propertyCount,
    __deref_out WS_SERVICE_PROXY** serviceProxy,
    __in_opt WS_ERROR* error)
{
    return WsCreateServiceProxyFromTemplate(
      WS_CHANNEL_TYPE_REQUEST,    // this is fixed for http, requires input for TCP
      properties,     
      propertyCount, 
      WS_bindingTemplateType_BINDING_TEMPLATE_TYPE,
      templateValue,
      sizeof(WS_bindingTemplateType_BINDING_TEMPLATE),  
      &fileName.policies.bindingName,   // template description as generated in the stub file
      sizeof(WS_constraintName_POLICY_DESCRIPTION),
      serviceProxy,     
      error);     
}
HRESULT bindingName_CreateServiceEndpoint(
__in WS_bindingTemplateType_BINDING_TEMPLATE* templateValue,
__in_opt const WS_STRING* addressUrl,
__in bindingNameFunctionTable* functionTable,
__in WS_SERVICE_SECURITY_CALLBACK authorizationCallback,
__in const WS_SERVICE_ENDPOINT_PROPERTY* properties,
__in ULONG propertyCount,
__in WS_HEAP* heap,
  __deref_out WS_SERVICE_ENDPOINT** serviceEndpoint,
  __in_opt WS_ERROR* error)
{
  WS_SERVICE_CONTRACT serviceContract;
  serviceContract.contractDescription = &fileName.contracts.bindingName;
  serviceContract.defaultMessageHandlerCallback = NULL;
  serviceContract.methodTable = (const void *)functionTable;

  return WsCreateServiceEndpointFromTemplate(
      properties,
      propertyCount,
      addressUrl,    // service endpoint address
      WS_CHANNEL_TYPE_RESPONSE,    // this is fixed for http, requires input for TCP
      &serviceContract,
      authorizationCallback,
      heap,
      WS_bindingTemplateType_BINDING_TEMPLATE_TYPE,
      templateValue,
      sizeof(WS_bindingTemplateType_BINDING_TEMPLATE),
      &fileName.policies.bindingName,   // template description as generated in the stub file
      sizeof(WS_bindingTemplateType_POLICY_DESCRIPTION),
      serviceEndpoint,
      error);
}

Supported policy settings

Following table list all the supported binding template types, the matching security bindings required in the type, the template structure to be filled in by application for the type, and the matching description type. Application needs to fill in the template structure, while application developer should understand what are the security bindings required in the given policy.

WS_BINDING_TEMPLATE_TYPE Security binding combinations template structure to be filled in by application policy description
WS_HTTP_BINDING_TEMPLATE_TYPE WS_HTTP_BINDING_TEMPLATE WS_HTTP_POLICY_DESCRIPTION
WS_HTTP_SSL_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING WS_HTTP_SSL_BINDING_TEMPLATE WS_HTTP_SSL_POLICY_DESCRIPTION
WS_HTTP_HEADER_AUTH_BINDING_TEMPLATE_TYPE WS_HTTP_HEADER_AUTH_SECURITY_BINDING WS_HTTP_HEADER_AUTH_BINDING_TEMPLATE WS_HTTP_HEADER_AUTH_POLICY_DESCRIPTION
WS_HTTP_SSL_HEADER_AUTH_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING and WS_HTTP_HEADER_AUTH_SECURITY_BINDING WS_HTTP_SSL_HEADER_AUTH_BINDING_TEMPLATE WS_HTTP_SSL_HEADER_AUTH_POLICY_DESCRIPTION
WS_HTTP_SSL_USERNAME_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING and WS_USERNAME_MESSAGE_SECURITY_BINDING WS_HTTP_SSL_USERNAME_BINDING_TEMPLATE WS_HTTP_SSL_USERNAME_POLICY_DESCRIPTION
WS_HTTP_SSL_KERBEROS_APREQ_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING and WS_KERBEROS_APREQ_MESSAGE_SECURITY_BINDING WS_HTTP_SSL_KERBEROS_APREQ_BINDING_TEMPLATE WS_HTTP_SSL_KERBEROS_APREQ_POLICY_DESCRIPTION
WS_TCP_BINDING_TEMPLATE_TYPE WS_TCP_BINDING_TEMPLATE WS_TCP_POLICY_DESCRIPTION
WS_TCP_SSPI_BINDING_TEMPLATE_TYPE WS_TCP_SSPI_TRANSPORT_SECURITY_BINDING WS_TCP_SSPI_BINDING_TEMPLATE WS_TCP_SSPI_POLICY_DESCRIPTION
WS_TCP_SSPI_USERNAME_BINDING_TEMPLATE_TYPE WS_TCP_SSPI_TRANSPORT_SECURITY_BINDING and WS_USERNAME_MESSAGE_SECURITY_BINDING WS_TCP_SSPI_USERNAME_BINDING_TEMPLATE WS_TCP_SSPI_USERNAME_POLICY_DESCRIPTION
WS_TCP_SSPI_KERBEROS_APREQ_BINDING_TEMPLATE_TYPE WS_TCP_SSPI_TRANSPORT_SECURITY_BINDING and WS_KERBEROS_APREQ_MESSAGE_SECURITY_BINDING WS_TCP_SSPI_KERBEROS_APREQ_BINDING_TEMPLATE WS_TCP_SSPI_KERBEROS_APREQ_POLICY_DESCRIPTION
WS_HTTP_SSL_USERNAME_SECURITY_CONTEXT_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING and WS_SECURITY_CONTEXT_MESSAGE_SECURITY_BINDING with WS_USERNAME_MESSAGE_SECURITY_BINDING in bootstrap channel WS_HTTP_SSL_USERNAME_SECURITY_CONTEXT_BINDING_TEMPLATE WS_HTTP_SSL_USERNAME_SECURITY_CONTEXT_POLICY_DESCRIPTION
WS_HTTP_SSL_KERBEROS_APREQ_SECURITY_CONTEXT_BINDING_TEMPLATE_TYPE WS_SSL_TRANSPORT_SECURITY_BINDING and WS_SECURITY_CONTEXT_MESSAGE_SECURITY_BINDING with WS_KERBEROS_APREQ_MESSAGE_SECURITY_BINDING in bootstrap channel WS_HTTP_SSL_KERBEROS_APREQ_SECURITY_CONTEXT_BINDING_TEMPLATE WS_HTTP_SSL_KERBEROS_APREQ_SECURITY_CONTEXT_POLICY_DESCRIPTION
WS_TCP_SSPI_USERNAME_SECURITY_CONTEXT_BINDING_TEMPLATE_TYPE WS_TCP_SSPI_TRANSPORT_SECURITY_BINDING and WS_SECURITY_CONTEXT_MESSAGE_SECURITY_BINDING with WS_USERNAME_MESSAGE_SECURITY_BINDING in bootstrap channel WS_TCP_SSPI_USERNAME_SECURITY_CONTEXT_BINDING_TEMPLATE WS_TCP_SSPI_USERNAME_SECURITY_CONTEXT_POLICY_DESCRIPTION
WS_TCP_SSPI_KERBEROS_APREQ_SECURITY_CONTEXT_BINDING_TEMPLATE_TYPE WS_TCP_SSPI_TRANSPORT_SECURITY_BINDING and WS_SECURITY_CONTEXT_MESSAGE_SECURITY_BINDING with WS_KERBEROS_APREQ_MESSAGE_SECURITY_BINDING in bootstrap channel WS_TCP_SSPI_KERBEROS_APREQ_SECURITY_CONTEXT_BINDING_TEMPLATE WS_TCP_SSPI_KERBEROS_APREQ_SECURITY_CONTEXT_POLICY_DESCRIPTION

 

For example, WS_HTTP_SSL_BINDING_TEMPLATE_TYPE indicates the input policy for the binding specifies HTTP transport, and WS_SSL_TRANSPORT_SECURITY_BINDING. Application needs to fill in WS_HTTP_SSL_BINDING_TEMPLATE structure before calling the helper routines, and the matching policy description is WS_HTTP_SSL_POLICY_DESCRIPTION. More specifically, the binding section in WSDL contains following segments:

<wsp:Policy...>
  <sp:TransportBinding...>
    <wsp:Policy...>
      <sp:TransportToken...>
        <wsp:Policy...>
          <sp:HttpsToken.../>
        </wsp:Policy...>
      </sp:TransportToken...>
    </wsp:Policy>
  </sp:TransportBinding...>
</wsp:Policy>
<wsdl:binding...>
<soap11:binding.../> => WS_ENVELOPE_VERSION_SOAP_1_1
</wsdl:binding>

Security Context support

In Security Context, the bootstrap channel is created to establish the secure conversation in service channel. Wsutil only supports the scenario where bootstrap channel is the same as service channel, with the same channel properties and security properties. Transport security is required for security context message binding; wsutil supports bootstrap channels with other message security bindings, but only support security context as the only message security binding in the service channel, without combination with other message security bindings. Developers can support those combinations outside of the policy template support.

The following enumeration is part of policy support:

The following functions are part of policy support:

The following structures are part of policy support: