add normalization guideline in security best practice (#9961)

* add normalization guideline in security best practice

* Apply suggestions from code review

Co-authored-by: Justin Pettit <jdpettit@google.com>

* add link

* Apply suggestions from code review

Co-authored-by: Frank Budinsky <frankb@ca.ibm.com>

Co-authored-by: Justin Pettit <jdpettit@google.com>
Co-authored-by: Frank Budinsky <frankb@ca.ibm.com>
This commit is contained in:
Yangmin Zhu 2021-07-08 14:13:38 -07:00 committed by GitHub
parent aa636228be
commit ef5b9ca506
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 75 additions and 2 deletions

View File

@ -90,6 +90,79 @@ spec:
notPaths: ["/public"]
{{< /text >}}
### Understand path normalization in authorization policy
The enforcement point for authorization policies is the Envoy proxy instead of the usual resource access point in the backend application. A policy mismatch happens when the Envoy proxy and the backend application interpret the request
differently.
A mismatch can lead to either unexpected rejection or a policy bypass. The latter is usually a security incident that needs to be
fixed immediately, and it's also why we need path normalization in the authorization policy.
For example, consider an authorization policy to reject requests with path `/data/secret`. A request with path `/data//secret` will
not be rejected because it does not match the path defined in the authorization policy due to the extra forward slash `/` in the path.
The request goes through and later the backend application returns the same response that it returns for the path `/data/secret`
because the backend application normalizes the path `/data//secret` to `/data/secret` as it considers the double forward slashes
`//` equivalent to a single forward slash `/`.
In this example, the policy enforcement point (Envoy proxy) had a different understanding of the path than the resource access
point (backend application). The different understanding caused the mismatch and subsequently the bypass of the authorization policy.
This becomes a complicated problem because of the following factors:
* Lack of a clear standard for the normalization.
* Backends and frameworks in different layers have their own special normalization.
* Applications can even have arbitrary normalizations for their own use cases.
Istio authorization policy implements built-in support of various basic normalization options to help you to better address
the problem:
* Refer to [Guideline on configuring the path normalization option](/docs/ops/best-practices/security/#guideline-on-configuring-the-path-normalization-option)
to understand which normalization options you may want to use.
* Refer to [Customize your system on path normalization](/docs/ops/best-practices/security/#customize-your-system-on-path-normalization) to
understand the detail of each normalization option.
* Refer to [Mitigation for unsupported normalization](/docs/ops/best-practices/security/#mitigation-for-unsupported-normalization) for
alternative solutions in case you need any unsupported normalization options.
### Guideline on configuring the path normalization option
#### Case 1: You do not need normalization at all
Before diving into the details of configuring normalization, you should first make sure that normalizations are needed.
You do not need normalization if you don't use authorization policies or if your authorization policies don't
use any `path` fields.
You may not need normalization if all your authorization policies follow the [safer authorization pattern](/docs/ops/best-practices/security/#safer-authorization-policy-patterns)
which, in the worst case, results in unexpected rejection instead of policy bypass.
#### Case 2: You need normalization but not sure which normalization option to use
You need normalization but you have no idea of which option to use. The safest choice is the strictest normalization option
that provides the maximum level of normalization in the authorization policy.
This is often the case due to the fact that complicated multi-layered systems make it practically impossible to figure
out what normalization is actually happening to a request beyond the enforcement point.
You could use a less strict normalization option if it already satisfies your requirements and you are sure of its implications.
For either option, make sure you write both positive and negative tests specifically for your requirements to verify the
normalization is working as expected. The tests are useful in catching potential bypass issues caused by a misunderstanding
or incomplete knowledge of the normalization happening to your request.
Refer to [Customize your system on path normalization](/docs/ops/best-practices/security/#customize-your-system-on-path-normalization)
for more details on configuring the normalization option.
#### Case 3: You need an unsupported normalization option
If you need a specific normalization option that is not supported by Istio yet, please follow
[Mitigation for unsupported normalization](/docs/ops/best-practices/security/#mitigation-for-unsupported-normalization)
for customized normalization support or create a feature request for the Istio community.
### Customize your system on path normalization
Istio authorization policies can be based on the URL paths in the HTTP request.
@ -125,7 +198,7 @@ applications may interpret a URL in any way it chooses to. When using denial pol
For a complete list of supported normalizations, please refer to [authorization policy normalization](/docs/reference/config/security/normalization/).
### Examples of configuration
#### Examples of configuration
Ensuring Envoy normalizes request paths to match your backend services' expectation is critical to the security of your system.
The following examples can be used as reference for you to configure your system.
@ -142,7 +215,7 @@ The normalized URL paths, or the original URL paths if _NONE_ is selected, will
| Normalizes request paths based on [RFC 3986](https://tools.ietf.org/html/rfc3986), decodes [percent-encoded](https://tools.ietf.org/html/rfc3986#section-2.1) slashes and merges slashes | `DECODE_AND_MERGE_SLASHES` |
| Processes request paths in a way that is incompatible with [RFC 3986](https://tools.ietf.org/html/rfc3986) | `NONE` |
### How to configure
#### How to configure
You can use `istioctl` to update the [mesh config](/docs/reference/config/istio.mesh.v1alpha1/):