From: Aki Tuomi Date: Mon, 8 May 2023 05:38:20 +0000 (+0300) Subject: lib-oauth2: Validate scope when configured X-Git-Tag: 2.4.0~2767 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=9bb7dd0ceb504637a0892a44f1ed522df79e6cbb;p=thirdparty%2Fdovecot%2Fcore.git lib-oauth2: Validate scope when configured --- diff --git a/src/lib-oauth2/oauth2-jwt.c b/src/lib-oauth2/oauth2-jwt.c index bb7c8e763a..ce9c76ec26 100644 --- a/src/lib-oauth2/oauth2-jwt.c +++ b/src/lib-oauth2/oauth2-jwt.c @@ -352,6 +352,17 @@ oauth2_jwt_header_process(struct json_tree *tree, const char **alg_r, return 0; } +static bool check_scope(const char *req, const char *got) +{ + const char *const *scope_req = t_strsplit_spaces(req, " ,"); + const char *const *scope_got = t_strsplit_spaces(got, " ,"); + + for (; *scope_req != NULL; scope_req++) + if (!str_array_icase_find(scope_got, *scope_req)) + return FALSE; + return TRUE; +} + static int oauth2_jwt_body_process(const struct oauth2_settings *set, const char *alg, const char *kid, ARRAY_TYPE(oauth2_field) *fields, @@ -437,6 +448,22 @@ oauth2_jwt_body_process(const struct oauth2_settings *set, const char *alg, } } + const char *got_scope = get_field(tree, "scope", NULL); + const char *req_scope = set->scope; + + if (req_scope != NULL && *req_scope != '\0') { + if (got_scope == NULL) { + *error_r = "scope set but not found in token"; + return -1; + } + + if (!check_scope(req_scope, got_scope)) { + *error_r = t_strdup_printf("configured scope '%s' missing from token scope '%s'", + req_scope, got_scope); + return -1; + } + } + /* see if there is azp */ const char *azp = get_field(tree, "azp", NULL); if (azp == NULL) diff --git a/src/lib-oauth2/test-oauth2-jwt.c b/src/lib-oauth2/test-oauth2-jwt.c index b0c5324344..68a64ed114 100644 --- a/src/lib-oauth2/test-oauth2-jwt.c +++ b/src/lib-oauth2/test-oauth2-jwt.c @@ -83,7 +83,6 @@ static int parse_jwt_token(struct oauth2_request *req, const char *token, struct oauth2_settings set; i_zero(&set); - set.scope = "mail"; set.key_dict = keys_dict; set.key_cache = key_cache; i_zero(req);