]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
discover-image: nicely support .sysext.raw + .confext.raw suffix for DDIs
authorLennart Poettering <lennart@poettering.net>
Thu, 28 Sep 2023 16:22:24 +0000 (18:22 +0200)
committerLennart Poettering <lennart@poettering.net>
Thu, 5 Oct 2023 17:09:12 +0000 (19:09 +0200)
Back at Plumbers 2022 we discussed that we should push people towards
using the .sysext.raw and .confext.raw for their DDIs if they are
extension images. Let's actually support that, by chopping off these
suffixes when turning file names into "pretty image names".

src/shared/discover-image.c
src/shared/import-util.c

index f94fac1b4102f5942e3d1184c8f062b83f08fb61..50662037dee256d3e1ef2389584cb0652863f117 100644 (file)
@@ -85,6 +85,13 @@ static const char* const image_search_path_initrd[_IMAGE_CLASS_MAX] = {
                             "/.extra/sysext\0"             /* put sysext picked up by systemd-stub last, since not trusted */
 };
 
+static const char* image_class_suffix_table[_IMAGE_CLASS_MAX] = {
+        [IMAGE_SYSEXT]  = ".sysext",
+        [IMAGE_CONFEXT] = ".confext",
+};
+
+DEFINE_PRIVATE_STRING_TABLE_LOOKUP_TO_STRING(image_class_suffix, ImageClass);
+
 static Image *image_free(Image *i) {
         assert(i);
 
@@ -201,29 +208,36 @@ static int image_new(
         return 0;
 }
 
-static int extract_pretty(const char *path, const char *suffix, char **ret) {
+static int extract_pretty(
+                const char *path,
+                const char *class_suffix,
+                const char *format_suffix,
+                char **ret) {
+
         _cleanup_free_ char *name = NULL;
-        const char *p;
+        int r;
 
         assert(path);
         assert(ret);
 
-        p = last_path_component(path);
-
-        name = strdupcspn(p, "/");
-        if (!name)
-                return -ENOMEM;
-
-        if (suffix) {
-                char *e;
+        r = path_extract_filename(path, &name);
+        if (r < 0)
+                return r;
 
-                e = endswith(name, suffix);
-                if (!e)
+        if (format_suffix) {
+                char *e = endswith(name, format_suffix);
+                if (!e) /* Format suffix is required */
                         return -EINVAL;
 
                 *e = 0;
         }
 
+        if (class_suffix) {
+                char *e = endswith(name, class_suffix);
+                if (e) /* Class suffix is optional */
+                        *e = 0;
+        }
+
         if (!image_name_is_valid(name))
                 return -EINVAL;
 
@@ -282,7 +296,7 @@ static int image_make(
                         return 0;
 
                 if (!pretty) {
-                        r = extract_pretty(filename, NULL, &pretty_buffer);
+                        r = extract_pretty(filename, image_class_suffix_to_string(c), NULL, &pretty_buffer);
                         if (r < 0)
                                 return r;
 
@@ -369,7 +383,7 @@ static int image_make(
                 (void) fd_getcrtime_at(dfd, filename, AT_SYMLINK_FOLLOW, &crtime);
 
                 if (!pretty) {
-                        r = extract_pretty(filename, ".raw", &pretty_buffer);
+                        r = extract_pretty(filename, image_class_suffix_to_string(c), ".raw", &pretty_buffer);
                         if (r < 0)
                                 return r;
 
@@ -403,7 +417,7 @@ static int image_make(
                         return 0;
 
                 if (!pretty) {
-                        r = extract_pretty(filename, NULL, &pretty_buffer);
+                        r = extract_pretty(filename, NULL, NULL, &pretty_buffer);
                         if (r < 0)
                                 return r;
 
@@ -592,8 +606,7 @@ int image_discover(
 
                 FOREACH_DIRENT_ALL(de, d, return -errno) {
                         _cleanup_(image_unrefp) Image *image = NULL;
-                        _cleanup_free_ char *truncated = NULL;
-                        const char *pretty;
+                        _cleanup_free_ char *pretty = NULL;
                         struct stat st;
                         int flags;
 
@@ -610,22 +623,16 @@ int image_discover(
                                 return -errno;
                         }
 
-                        if (S_ISREG(st.st_mode)) {
-                                const char *e;
-
-                                e = endswith(de->d_name, ".raw");
-                                if (!e)
-                                        continue;
-
-                                truncated = strndup(de->d_name, e - de->d_name);
-                                if (!truncated)
-                                        return -ENOMEM;
-
-                                pretty = truncated;
-                        } else if (S_ISDIR(st.st_mode) || S_ISBLK(st.st_mode))
-                                pretty = de->d_name;
+                        if (S_ISREG(st.st_mode))
+                                r = extract_pretty(de->d_name, image_class_suffix_to_string(class), ".raw", &pretty);
+                        else if (S_ISDIR(st.st_mode))
+                                r = extract_pretty(de->d_name, image_class_suffix_to_string(class), NULL, &pretty);
+                        else if (S_ISBLK(st.st_mode))
+                                r = extract_pretty(de->d_name, NULL, NULL, &pretty);
                         else
                                 continue;
+                        if (r < 0)
+                                return r;
 
                         if (!image_name_is_valid(pretty))
                                 continue;
index ec8906450611491777ff81ca6175c35152746bdd..9057b78d286164d6aedafbd407f9e0000caf1e9d 100644 (file)
@@ -167,6 +167,8 @@ int raw_strip_suffixes(const char *p, char **ret) {
                 ".xz\0"
                 ".gz\0"
                 ".bz2\0"
+                ".sysext.raw\0"
+                ".confext.raw\0"
                 ".raw\0"
                 ".qcow2\0"
                 ".img\0"