On 2025/9/3 16:29, ChengyuZhu6 wrote:
From: Chengyu Zhu <hudson...@tencent.com>

Refactor OCI code to improve code organization and maintainability:

Key changes:
- Add `ocierofs_get_api_registry()` and unify API endpoint selection.
- Implement Bearer token discovery with Basic fallback; cache auth header.
- Parse layer metadata (digest, mediaType, size) and add a proper free helper.
- Split blob download from tar processing; process tar via a temp fd.
- Rework init/teardown into `ocierofs_init()` and `ocierofs_ctx_cleanup()`.
- Update mkfs to use `struct ocierofs_config` and new `--oci` parsing.

Signed-off-by: Chengyu Zhu <hudson...@tencent.com>
---
  lib/liberofs_oci.h |  84 ++---
  lib/remotes/oci.c  | 885 ++++++++++++++++++++++++++-------------------
  mkfs/main.c        | 192 ++--------
  3 files changed, 566 insertions(+), 595 deletions(-)

diff --git a/lib/liberofs_oci.h b/lib/liberofs_oci.h
index 3a8108b..d119a2b 100644
--- a/lib/liberofs_oci.h
+++ b/lib/liberofs_oci.h
@@ -8,85 +8,65 @@
#include <stdbool.h> -#define DOCKER_REGISTRY "docker.io"
-#define DOCKER_API_REGISTRY "registry-1.docker.io"
-
  #ifdef __cplusplus
  extern "C" {
  #endif
-struct erofs_inode;
-struct CURL;
  struct erofs_importer;
-/**
- * struct erofs_oci_params - OCI configuration parameters
- * @registry: registry hostname (e.g., "registry-1.docker.io")
- * @repository: image repository (e.g., "library/ubuntu")
- * @tag: image tag or digest (e.g., "latest" or sha256:...)
+/*
+ * struct ocierofs_config - OCI configuration structure
+ * @image_ref: OCI image reference (e.g., "ubuntu:latest", 
"myregistry.com/app:v1.0")
   * @platform: target platform in "os/arch" format (e.g., "linux/amd64")
   * @username: username for authentication (optional)
   * @password: password for authentication (optional)
   * @layer_index: specific layer to extract (-1 for all layers)
   *
- * Configuration structure for OCI image parameters including registry
- * location, image identification, platform specification, and authentication
- * credentials.
   */
-struct erofs_oci_params {
-       char *registry;
-       char *repository;
-       char *tag;
+struct ocierofs_config {
+       char *image_ref;
        char *platform;
        char *username;
        char *password;
        int layer_index;
  };
-/**
- * struct erofs_oci - Combined OCI client structure
- * @curl: CURL handle for HTTP requests
- * @params: OCI configuration parameters
- *
- * Main OCI client structure combining CURL HTTP client with
- * OCI-specific configuration parameters.
- */
-struct erofs_oci {
-       struct CURL *curl;
-       struct erofs_oci_params params;
+struct ocierofs_layer_info {
+       char *digest;
+       char *media_type;
+       u64 size;
  };
-/*
- * ocierofs_init - Initialize OCI client with default parameters
- * @oci: OCI client structure to initialize
- *
- * Return: 0 on success, negative errno on failure
- */
-int ocierofs_init(struct erofs_oci *oci);
+struct ocierofs_ctx {
+       struct {
+               struct CURL *curl;
+               char *auth_header;
+               bool using_basic;
+       } net;

Is it necessary to use two anonymous structures here?

Could we just unfold those fields?

...

diff --git a/mkfs/main.c b/mkfs/main.c
index bc895f1..5e8da7a 100644
--- a/mkfs/main.c
+++ b/mkfs/main.c
@@ -150,18 +150,18 @@ static void usage(int argc, char **argv)
                                 * "0-9,100-109" instead of a continuous 
"0-109", and to
                                 * state what those two subranges respectively 
mean.  */
                                printf("%s  [,level=<0-9,100-109>]\t0-9=normal, 
100-109=extreme (default=%i)\n",
-                                      spaces, s->c->default_level);
+                              spaces, s->c->default_level);
                        else
                                printf("%s  [,level=<0-%i>]\t\t(default=%i)\n",
-                                      spaces, s->c->best_level, 
s->c->default_level);
+                              spaces, s->c->best_level, s->c->default_level);
                }
                if (s->c->setdictsize) {
                        if (s->c->default_dictsize)
                                printf("%s  [,dictsize=<dictsize>]\t(default=%u, 
max=%u)\n",
-                                      spaces, s->c->default_dictsize, 
s->c->max_dictsize);
+                              spaces, s->c->default_dictsize, 
s->c->max_dictsize);
                        else
                                printf("%s  [,dictsize=<dictsize>]\t(default=<auto>, 
max=%u)\n",
-                                      spaces, s->c->max_dictsize);
+                              spaces, s->c->max_dictsize);

Are those changes unnecessary?

                }
        }
        printf(
@@ -272,7 +272,7 @@ static struct erofs_s3 s3cfg;
  #endif
#ifdef OCIEROFS_ENABLED
-static struct erofs_oci ocicfg;
+static struct ocierofs_config ocicfg;
  static char *mkfs_oci_options;
  #endif
@@ -689,21 +689,14 @@ static int mkfs_parse_s3_cfg(char *cfg_str)
  #endif
#ifdef OCIEROFS_ENABLED
-
-
-/**
- * mkfs_parse_oci_options - Parse comma-separated OCI options string
+/*
+ * mkfs_parse_oci_options - Parse OCI options for mkfs tool
+ * @cfg: OCI configuration structure to update
   * @options_str: comma-separated options string
- *
- * Parse OCI options string containing comma-separated key=value pairs.
- * Supported options include platform, layer, username, and password.
- *
- * Return: 0 on success, negative errno on failure
   */
-static int mkfs_parse_oci_options(char *options_str)
+static int mkfs_parse_oci_options(struct ocierofs_config *oci_cfg, char 
*options_str)
  {
        char *opt, *q, *p;
-       int ret;
if (!options_str)
                return 0;
@@ -717,41 +710,38 @@ static int mkfs_parse_oci_options(char *options_str)
                p = strstr(opt, "platform=");
                if (p) {
                        p += strlen("platform=");
-                       ret = 
erofs_oci_params_set_string(&ocicfg.params.platform, p);
-                       if (ret) {
-                               erofs_err("failed to set platform");
-                               return ret;
-                       }
+                       free(oci_cfg->platform);
+                       oci_cfg->platform = strdup(p);
+                       if (!oci_cfg->platform)
+                               return -ENOMEM;
                } else {
                        p = strstr(opt, "layer=");
                        if (p) {
                                p += strlen("layer=");
-                               ocicfg.params.layer_index = atoi(p);
-                               if (ocicfg.params.layer_index < 0) {
+                               oci_cfg->layer_index = atoi(p);
+                               if (oci_cfg->layer_index < 0) {

Could you just use `strtoul` since it can check invalid
arguments better?

                                        erofs_err("invalid layer index %d",
-                                                 ocicfg.params.layer_index);
+                                         oci_cfg->layer_index);
                                        return -EINVAL;
                                }
                        } else {
                                p = strstr(opt, "username=");
                                if (p) {
                                        p += strlen("username=");
-                                       ret = 
erofs_oci_params_set_string(&ocicfg.params.username, p);
-                                       if (ret) {
-                                               erofs_err("failed to set 
username");
-                                               return ret;
-                                       }
+                                       free(oci_cfg->username);
+                                       oci_cfg->username = strdup(p);
+                                       if (!oci_cfg->username)
+                                               return -ENOMEM;
                                } else {
                                        p = strstr(opt, "password=");
                                        if (p) {
                                                p += strlen("password=");
-                                               ret = 
erofs_oci_params_set_string(&ocicfg.params.password, p);
-                                               if (ret) {
-                                                       erofs_err("failed to set 
password");
-                                                       return ret;
-                                               }
+                                                                                  
     free(oci_cfg->password);
+                                       oci_cfg->password = strdup(p);
+                                       if (!oci_cfg->password)
+                                               return -ENOMEM;
                                        } else {
-                                               erofs_err("invalid --oci value 
%s", opt);
+                                               erofs_err("mkfs: invalid --oci value 
%s", opt);

`mkfs:` prefix is unneeded.

Thanks,
Gao Xiang

Reply via email to