]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw: acl grants num limit 16291/head
authorEnming Zhang <enming.zhang@umcloud.com>
Wed, 12 Jul 2017 14:21:54 +0000 (22:21 +0800)
committerEnming Zhang <enming.zhang@umcloud.com>
Sun, 16 Jul 2017 12:58:43 +0000 (20:58 +0800)
According to AWS S3 in this document[1], an ACL can have up to 100
grants.

If the nums of grants is larger than 100, S3 will return like following:
400
<?xml version="1.0" encoding="UTF-8"?>
<Error><Code>MalformedACLError</Code><Message>The XML you provided was not well-formed or did not validate against our published schema</Message><RequestId>10EC67824572C378</RequestId><HostId>AWL3NnQChs/HCfOTu5MtyEc9uzRuxpYMhmvXQry2CovCcuxO2/tMqY1zGoWOur86ipQt3v/WEiA=</HostId></Error>

Now if the nums of request acl grants is larger than the maximum allowed, rgw will return
like following:
400
<?xml version="1.0" encoding="UTF-8"?><Error><Code>MalformedACLError</Code><Message>The request is rejected, because the acl grants number you requested is larger than the maximum 101 grants allowed in an acl.</Message><BucketName>222</BucketName><RequestId>tx000000000000000000017-00596b5fad-101a-default</RequestId><HostId>101a-default-default</HostId></Error>

The maximum number of acl grants can be configured in config file with the configuration item:

rgw_acl_grants_max_num

[1] http://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html

Signed-off-by: Enming Zhang <enming.zhang@umcloud.com>
src/common/config_opts.h
src/rgw/rgw_common.cc
src/rgw/rgw_common.h
src/rgw/rgw_op.cc

index 15dc65600e0437615f8b533f04e89b68bfd8c4c2..b36022d1115113e8a89c6eaec39eb06fc937f0a8 100644 (file)
@@ -1796,3 +1796,5 @@ OPTION(rgw_reshard_bucket_lock_duration, OPT_INT, 120) // duration of lock on bu
 OPTION(rgw_dynamic_resharding, OPT_BOOL, true)
 OPTION(rgw_max_objs_per_shard, OPT_INT, 100000)
 OPTION(rgw_reshard_thread_interval, OPT_U32, 60 * 10) // maximum time between rounds of reshard thread processing
+
+OPTION(rgw_acl_grants_max_num, OPT_INT, 100) // According to AWS S3(http://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html), An ACL can have up to 100 grants.
index d7fb6cfdcf2ff1611372d1ec626da0d0070bfc79..05b92d2ee5a4761341d9bb0f1da01ccd430a8ade 100644 (file)
@@ -74,6 +74,7 @@ rgw_http_errors rgw_http_s3_errors({
     { ERR_MALFORMED_XML, {400, "MalformedXML" }},
     { ERR_AMZ_CONTENT_SHA256_MISMATCH, {400, "XAmzContentSHA256Mismatch" }},
     { ERR_INVALID_TAG, {400, "InvalidTag"}},
+    { ERR_MALFORMED_ACL_ERROR, {400, "MalformedACLError" }},
     { ERR_LENGTH_REQUIRED, {411, "MissingContentLength" }},
     { EACCES, {403, "AccessDenied" }},
     { EPERM, {403, "AccessDenied" }},
index 1ca88ebb99a788722b96b999c6c89c951341c2e4..b8dfb49d74a3b3790f1e7c0d82505f1d064a98b1 100644 (file)
@@ -213,6 +213,7 @@ using ceph::crypto::MD5;
 #define ERR_TAG_CONFLICT         2209
 #define ERR_INVALID_TAG          2210
 #define ERR_ZERO_IN_URL          2211
+#define ERR_MALFORMED_ACL_ERROR  2212
 
 #define ERR_BUSY_RESHARDING      2300
 
index c02b3d8396ddf4a3af5987feccfdb7d9f853a9e9..c99d8a8f12f1f4f33ca4f1c6631f716b065244fe 100644 (file)
@@ -4610,6 +4610,27 @@ void RGWPutACLs::execute()
     return;
   }
 
+  const RGWAccessControlList& req_acl = policy->get_acl();
+  const multimap<string, ACLGrant>& req_grant_map = req_acl.get_grant_map();
+#define ACL_GRANTS_MAX_NUM      100
+  int max_num = s->cct->_conf->rgw_acl_grants_max_num;
+  if (max_num < 0) {
+    max_num = ACL_GRANTS_MAX_NUM;
+  }
+
+  int grants_num = req_grant_map.size();
+  if (grants_num > max_num) {
+    ldout(s->cct, 4) << "An acl can have up to "
+                     << max_num
+                     << " grants, request acl grants num: "
+                     << grants_num << dendl;
+    op_ret = -ERR_MALFORMED_ACL_ERROR;
+    s->err.message = "The request is rejected, because the acl grants number you requested is larger than the maximum "
+                     + std::to_string(max_num)
+                     + " grants allowed in an acl.";
+    return;
+  }
+
   // forward bucket acl requests to meta master zone
   if (s->object.empty() && !store->is_meta_master()) {
     bufferlist in_data;