@@ -6962,6 +6962,7 @@ rgw::auth::s3::STSEngine::authenticate(
69626962 const req_state* const s,
69636963 optional_yield y) const
69646964{
6965+ bool is_system_request{false };
69656966 if (! s->info .args .exists (" x-amz-security-token" ) &&
69666967 ! s->info .env ->exists (" HTTP_X_AMZ_SECURITY_TOKEN" ) &&
69676968 s->auth .s3_postobj_creds .x_amz_security_token .empty ()) {
@@ -6973,10 +6974,36 @@ rgw::auth::s3::STSEngine::authenticate(
69736974 return result_t::reject (ret);
69746975 }
69756976 // Authentication
6977+ std::string secret_access_key;
69766978 // Check if access key is not the same passed in by client
69776979 if (token.access_key_id != _access_key_id) {
6978- ldpp_dout (dpp, 0 ) << " Invalid access key" << dendl;
6979- return result_t::reject (-EPERM);
6980+ /* In case the request is forwarded from secondary in case of multi-site,
6981+ we by-pass authentication using the session token credentials,
6982+ instead we use the system user's credentials that was used to sign
6983+ this request */
6984+ std::unique_ptr<rgw::sal::User> user;
6985+ const std::string access_key_id (_access_key_id);
6986+ if (driver->get_user_by_access_key (dpp, access_key_id, y, &user) < 0 ) {
6987+ ldpp_dout (dpp, 5 ) << " error reading user info, uid=" << access_key_id
6988+ << " can't authenticate" << dendl;
6989+ return result_t::reject (-ERR_INVALID_ACCESS_KEY);
6990+ }
6991+ // only allow system users as this could be a forwarded request from secondary
6992+ if (user->get_info ().system && driver->is_meta_master ()) {
6993+ const auto iter = user->get_info ().access_keys .find (access_key_id);
6994+ if (iter == std::end (user->get_info ().access_keys )) {
6995+ ldpp_dout (dpp, 0 ) << " ERROR: access key not encoded in user info" << dendl;
6996+ return result_t::reject (-EPERM);
6997+ }
6998+ const RGWAccessKey& k = iter->second ;
6999+ secret_access_key = k.key ;
7000+ is_system_request = true ;
7001+ } else {
7002+ ldpp_dout (dpp, 0 ) << " Invalid access key" << dendl;
7003+ return result_t::reject (-EPERM);
7004+ }
7005+ } else {
7006+ secret_access_key = token.secret_access_key ;
69807007 }
69817008 // Check if the token has expired
69827009 if (! token.expiration .empty ()) {
@@ -6997,7 +7024,7 @@ rgw::auth::s3::STSEngine::authenticate(
69977024 }
69987025 // Check for signature mismatch
69997026 const VersionAbstractor::server_signature_t server_signature = \
7000- signature_factory (cct, token. secret_access_key , string_to_sign);
7027+ signature_factory (cct, secret_access_key, string_to_sign);
70017028 auto compare = signature.compare (server_signature);
70027029
70037030 ldpp_dout (dpp, 15 ) << " string_to_sign="
@@ -7061,7 +7088,7 @@ rgw::auth::s3::STSEngine::authenticate(
70617088 t_attrs.token_issued_at = std::move (token.issued_at );
70627089 t_attrs.principal_tags = std::move (token.principal_tags );
70637090 auto apl = role_apl_factory->create_apl_role (cct, s, std::move (r),
7064- std::move (t_attrs));
7091+ std::move (t_attrs), is_system_request );
70657092 return result_t::grant (std::move (apl), completer_factory (token.secret_access_key ));
70667093 } else { // This is for all local users of type TYPE_RGW|ROOT|NONE
70677094 if (token.user .empty ()) {
0 commit comments