[PATCH] erofs-utils: lib: simplify s3erofs_prepare_url logic

Yifan Zhao zhaoyifan28 at huawei.com
Tue Sep 30 18:40:56 AEST 2025


From: zhaoyifan <zhaoyifan28 at huawei.com>

`mkfs.erofs` failed to generate image from Huawei OBS with the following command:

	mkfs.erofs --s3=<endpoint>,urlstyle=vhost,sig=2 s3.erofs test-bucket

because it mistakenly generated a url with repeated '/':

	https://test-bucket.<endpoint>//<keyname>

In fact, the splitting of bucket name and path has already been performed prior
to the call to `s3erofs_prepare_url`, and this function does not need to handle
this logic. This patch simplifies this part accordingly and fixes the problem.

Fixes: 29728ba8f6f6 ("erofs-utils: mkfs: support EROFS meta-only image generation from S3")
Signed-off-by: Yifan Zhao <zhaoyifan28 at huawei.com>
---
 lib/remotes/s3.c | 35 ++++++++++-------------------------
 1 file changed, 10 insertions(+), 25 deletions(-)

diff --git a/lib/remotes/s3.c b/lib/remotes/s3.c
index 2e7763e..2bd5322 100644
--- a/lib/remotes/s3.c
+++ b/lib/remotes/s3.c
@@ -41,17 +41,16 @@ struct s3erofs_curl_request {
 
 static int s3erofs_prepare_url(struct s3erofs_curl_request *req,
 			       const char *endpoint,
-			       const char *path, const char *key,
+			       const char *bucket, const char *key,
 			       struct s3erofs_query_params *params,
 			       enum s3erofs_url_style url_style)
 {
 	static const char https[] = "https://";
 	const char *schema, *host;
-	bool slash = false;
 	char *url = req->url;
 	int pos, i;
 
-	if (!endpoint || !path)
+	if (!endpoint || !bucket)
 		return -EINVAL;
 
 	schema = strstr(endpoint, "://");
@@ -65,30 +64,16 @@ static int s3erofs_prepare_url(struct s3erofs_curl_request *req,
 			return -ENOMEM;
 	}
 
-	if (url_style == S3EROFS_URL_STYLE_PATH) {
-		pos = snprintf(url, S3EROFS_URL_LEN, "%s%s/%s", schema,
-			       host, path);
-	} else {
-		const char * split = strchr(path, '/');
+	if (url_style == S3EROFS_URL_STYLE_PATH)
+		pos = snprintf(url, S3EROFS_URL_LEN, "%s%s/%s/", schema, host, bucket);
+	else
+		pos = snprintf(url, S3EROFS_URL_LEN, "%s%s.%s/", schema, bucket, host);
 
-		if (!split) {
-			pos = snprintf(url, S3EROFS_URL_LEN, "%s%s.%s/",
-				       schema, path, host);
-			slash = true;
-		} else {
-			pos = snprintf(url, S3EROFS_URL_LEN, "%s%.*s.%s%s",
-				       schema, (int)(split - path), path,
-				       host, split);
-		}
-	}
-	if (key) {
-		slash |= url[pos - 1] != '/';
-		pos -= !slash;
-		pos += snprintf(url + pos, S3EROFS_URL_LEN - pos, "/%s", key);
-	}
+	if (key)
+		pos += snprintf(url + pos, S3EROFS_URL_LEN - pos, "%s", key);
 
 	i = snprintf(req->canonical_query, S3EROFS_CANONICAL_QUERY_LEN,
-		     "/%s%s%s", path, slash ? "/" : "", key ? key : "");
+		     "/%s/%s", bucket, key ? key : "");
 	req->canonical_query[i] = '\0';
 
 	for (i = 0; i < params->num; i++)
@@ -503,7 +488,7 @@ s3erofs_create_object_iterator(struct erofs_s3 *s3, const char *path,
 	if (prefix) {
 		if (++prefix - path > S3EROFS_PATH_MAX)
 			return ERR_PTR(-EINVAL);
-		iter->bucket = strndup(path, prefix - path);
+		iter->bucket = strndup(path, prefix - 1 - path);
 		iter->prefix = strdup(prefix);
 	} else {
 		iter->bucket = strdup(path);
-- 
2.46.0



More information about the Linux-erofs mailing list