diff --git a/pkg/token/token.go b/pkg/token/token.go index b6d1fbcdc..70b6132e7 100644 --- a/pkg/token/token.go +++ b/pkg/token/token.go @@ -473,6 +473,10 @@ func (v tokenVerifier) Verify(token string) (*Identity, error) { return nil, FormatError{"malformed query parameter"} } + if err = validateDuplicateParameters(queryParams); err != nil { + return nil, err + } + for key, values := range queryParams { if !parameterWhitelist[strings.ToLower(key)] { return nil, FormatError{fmt.Sprintf("non-whitelisted query parameter %q", key)} @@ -576,6 +580,17 @@ func (v tokenVerifier) Verify(token string) (*Identity, error) { return id, nil } +func validateDuplicateParameters(queryParams url.Values) error { + duplicateCheck := make(map[string]bool) + for key, _ := range queryParams { + if _, found := duplicateCheck[strings.ToLower(key)]; found { + return FormatError{fmt.Sprintf("duplicate query parameter found: %q", key)} + } + duplicateCheck[strings.ToLower(key)] = true + } + return nil +} + func hasSignedClusterIDHeader(paramsLower *url.Values) bool { signedHeaders := strings.Split(paramsLower.Get("x-amz-signedheaders"), ";") for _, hdr := range signedHeaders { diff --git a/pkg/token/token_test.go b/pkg/token/token_test.go index c8e4e6528..b67e9bf2d 100644 --- a/pkg/token/token_test.go +++ b/pkg/token/token_test.go @@ -190,6 +190,7 @@ func TestVerifyTokenPreSTSValidations(t *testing.T) { validationSuccessTest(t, "aws", toToken(fmt.Sprintf("https://sts.ca-central-1.amazonaws.com/?action=GetCallerIdentity&x-amz-signedheaders=x-k8s-aws-id&x-amz-date=%s&x-amz-expires=60", timeStr))) validationSuccessTest(t, "aws", toToken(fmt.Sprintf("https://sts.eu-west-1.amazonaws.com/?action=GetCallerIdentity&x-amz-signedheaders=x-k8s-aws-id&x-amz-date=%s&x-amz-expires=60", timeStr))) validationSuccessTest(t, "aws", toToken(fmt.Sprintf("https://sts.sa-east-1.amazonaws.com/?action=GetCallerIdentity&x-amz-signedheaders=x-k8s-aws-id&x-amz-date=%s&x-amz-expires=60", timeStr))) + validationErrorTest(t, "aws", toToken(fmt.Sprintf("https://sts.us-west-2.amazonaws.com/?Action=GetCallerIdentity&Version=2011-06-15&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=ASIAAAAAAAAAAAAAAAAA%%2F20220601%%2Fus-west-2%%2Fsts%%2Faws4_request&X-Amz-Date=%s&X-Amz-Expires=900&X-Amz-Security-Token=XXXXXXXXXXXXX&X-Amz-SignedHeaders=host%%3Bx-k8s-aws-id&x-amz-credential=eve&X-Amz-Signature=999999999999999999", timeStr)), "input token was not properly formatted: duplicate query parameter found:") } func TestVerifyHTTPError(t *testing.T) {