From 25465336f77be1332c4536f90eb6ebd8edfd71de Mon Sep 17 00:00:00 2001
From: lifeng68 <lifeng68@huawei.com>
Date: Fri, 27 Nov 2020 11:29:58 +0800
Subject: [PATCH 09/17] iSulad: only qsort the configed mounts

Signed-off-by: lifeng68 <lifeng68@huawei.com>
---
 src/daemon/entry/cri/cri_security_context.cc |   1 -
 src/daemon/modules/spec/specs_mount.c        | 216 ++++++++++---------
 2 files changed, 114 insertions(+), 103 deletions(-)

diff --git a/src/daemon/entry/cri/cri_security_context.cc b/src/daemon/entry/cri/cri_security_context.cc
index 1d332261..cf5b300e 100644
--- a/src/daemon/entry/cri/cri_security_context.cc
+++ b/src/daemon/entry/cri/cri_security_context.cc
@@ -179,7 +179,6 @@ static void ModifyContainerNamespaceOptions(const runtime::v1alpha2::NamespaceOp
         hostConfig->pid_mode = util_strdup_s(sandboxNSMode.c_str());
     }
 
-    
     if (nsOpts.pid() == runtime::v1alpha2::NamespaceMode::TARGET) {
         std::string targetPidNsMode = "container:" + nsOpts.target_id();
         free(hostConfig->pid_mode);
diff --git a/src/daemon/modules/spec/specs_mount.c b/src/daemon/modules/spec/specs_mount.c
index db7e4fd8..6099a918 100644
--- a/src/daemon/modules/spec/specs_mount.c
+++ b/src/daemon/modules/spec/specs_mount.c
@@ -372,7 +372,8 @@ static defs_mount *mount_point_to_defs_mnt(container_config_v2_common_config_mou
         ERROR("Out of memory");
         return NULL;
     }
-    mnt->options = util_common_calloc_s(sizeof(char *) * (options_len + 3)); // +2 for readonly/propagation/selinux_relabel
+    mnt->options =
+        util_common_calloc_s(sizeof(char *) * (options_len + 3)); // +2 for readonly/propagation/selinux_relabel
     if (mnt->options == NULL) {
         ERROR("Out of memory");
         ret = -1;
@@ -647,10 +648,10 @@ out:
     return m;
 }
 
-static defs_mount * parse_anonymous_volume(char *volume)
+static defs_mount *parse_anonymous_volume(char *volume)
 {
     int ret = 0;
-    char path[PATH_MAX] = {0};
+    char path[PATH_MAX] = { 0 };
     defs_mount *mount_element = NULL;
 
     if (!util_clean_path(volume, path, sizeof(path))) {
@@ -1378,17 +1379,12 @@ out:
 }
 #endif
 
-static int merge_fs_mounts_to_oci_and_spec(oci_runtime_spec *oci_spec, defs_mount **mounts, size_t mounts_len,
-                                           container_config_v2_common_config *common_config)
+static int merge_fs_mounts_to_oci_spec(oci_runtime_spec *oci_spec, defs_mount **mounts, size_t mounts_len)
 {
     int ret = 0;
     size_t new_size = 0, old_size = 0;
-    size_t new_mp_key_size, new_mp_val_size, old_mp_key_size, old_mp_val_size;
     size_t i = 0;
-    char **mp_key = NULL;
-    container_config_v2_common_config_mount_points_element **mp_val = NULL;
     defs_mount **mounts_temp = NULL;
-    struct volume *vol = NULL;
 
     if (mounts_len == 0) {
         return 0;
@@ -1414,42 +1410,66 @@ static int merge_fs_mounts_to_oci_and_spec(oci_runtime_spec *oci_spec, defs_moun
     }
     oci_spec->mounts = mounts_temp;
 
-    if (common_config != NULL) {
-        if (common_config->mount_points == NULL) {
-            common_config->mount_points = util_common_calloc_s(sizeof(container_config_v2_common_config_mount_points));
-            if (common_config->mount_points == NULL) {
+    for (i = 0; i < mounts_len; i++) {
+        defs_mount *mnt = mounts[i];
+        oci_spec->mounts[oci_spec->mounts_len] = mnt;
+        oci_spec->mounts_len++;
+        mounts[i] = NULL;
+    }
+
+out:
+    return ret;
+}
+
+static int merge_fs_mounts_to_v2_spec(defs_mount **mounts, size_t mounts_len,
+                                      container_config_v2_common_config *v2_spec)
+{
+    int ret = 0;
+    size_t new_mp_key_size, new_mp_val_size, old_mp_key_size, old_mp_val_size;
+    size_t i = 0;
+    char **mp_key = NULL;
+    container_config_v2_common_config_mount_points_element **mp_val = NULL;
+    struct volume *vol = NULL;
+
+    if (mounts_len == 0) {
+        return 0;
+    }
+
+    if (v2_spec != NULL) {
+        if (v2_spec->mount_points == NULL) {
+            v2_spec->mount_points = util_common_calloc_s(sizeof(container_config_v2_common_config_mount_points));
+            if (v2_spec->mount_points == NULL) {
                 ERROR("Out of memory");
                 ret = -1;
                 goto out;
             }
         }
-        new_mp_key_size = (common_config->mount_points->len + mounts_len) * sizeof(char *);
-        old_mp_key_size = common_config->mount_points->len * sizeof(char *);
-        new_mp_val_size = (common_config->mount_points->len + mounts_len) *
+        new_mp_key_size = (v2_spec->mount_points->len + mounts_len) * sizeof(char *);
+        old_mp_key_size = v2_spec->mount_points->len * sizeof(char *);
+        new_mp_val_size = (v2_spec->mount_points->len + mounts_len) *
                           sizeof(container_config_v2_common_config_mount_points_element *);
-        old_mp_val_size =
-            common_config->mount_points->len * sizeof(container_config_v2_common_config_mount_points_element *);
+        old_mp_val_size = v2_spec->mount_points->len * sizeof(container_config_v2_common_config_mount_points_element *);
 
-        ret = util_mem_realloc((void **)&mp_key, new_mp_key_size, common_config->mount_points->keys, old_mp_key_size);
+        ret = util_mem_realloc((void **)&mp_key, new_mp_key_size, v2_spec->mount_points->keys, old_mp_key_size);
         if (ret != 0) {
             ERROR("Failed to realloc memory mount point");
             ret = -1;
             goto out;
         }
-        common_config->mount_points->keys = mp_key;
-        ret = util_mem_realloc((void **)&mp_val, new_mp_val_size, common_config->mount_points->values, old_mp_val_size);
+        v2_spec->mount_points->keys = mp_key;
+        ret = util_mem_realloc((void **)&mp_val, new_mp_val_size, v2_spec->mount_points->values, old_mp_val_size);
         if (ret != 0) {
             ERROR("Failed to realloc memory mount point");
             ret = -1;
             goto out;
         }
-        common_config->mount_points->values = mp_val;
+        v2_spec->mount_points->values = mp_val;
     }
 
     for (i = 0; i < mounts_len; i++) {
         defs_mount *mnt = mounts[i];
         if (strcmp(mnt->type, "volume") == 0) {
-            struct volume_options opts = {.ref = common_config->id};
+            struct volume_options opts = { .ref = v2_spec->id };
             // support local volume only currently.
             vol = volume_create(VOLUME_DEFAULT_DRIVER_NAME, mnt->source, &opts);
             if (vol == NULL) {
@@ -1461,8 +1481,8 @@ static int merge_fs_mounts_to_oci_and_spec(oci_runtime_spec *oci_spec, defs_moun
             mnt->source = util_strdup_s(vol->path);
 
 #ifdef ENABLE_SELINUX
-            if (oci_spec->linux != NULL) {
-                ret = relabel_volume(vol, mnt, oci_spec->linux->mount_label);
+            if (v2_spec->mount_label != NULL) {
+                ret = relabel_volume(vol, mnt, v2_spec->mount_label);
                 if (ret != 0) {
                     ERROR("Failed to relabel volume");
                     ret = -1;
@@ -1472,41 +1492,37 @@ static int merge_fs_mounts_to_oci_and_spec(oci_runtime_spec *oci_spec, defs_moun
 #endif
         }
 
-        if (common_config != NULL) {
-            common_config->mount_points->values[common_config->mount_points->len] = defs_mnt_to_mount_point(mnt);
-            if (common_config->mount_points->values[common_config->mount_points->len] == NULL) {
+        if (v2_spec != NULL) {
+            v2_spec->mount_points->values[v2_spec->mount_points->len] = defs_mnt_to_mount_point(mnt);
+            if (v2_spec->mount_points->values[v2_spec->mount_points->len] == NULL) {
                 ERROR("Failed to transform to mount point");
                 ret = -1;
                 goto out;
             }
             if (vol != NULL) {
-                common_config->mount_points->values[common_config->mount_points->len]->name = util_strdup_s(vol->name);
-                common_config->mount_points->values[common_config->mount_points->len]->driver = util_strdup_s(vol->driver);
+                v2_spec->mount_points->values[v2_spec->mount_points->len]->name = util_strdup_s(vol->name);
+                v2_spec->mount_points->values[v2_spec->mount_points->len]->driver = util_strdup_s(vol->driver);
             }
-            common_config->mount_points->values[common_config->mount_points->len]->named = mnt->named;
-            common_config->mount_points->keys[common_config->mount_points->len] = util_strdup_s(mnt->destination);
-            common_config->mount_points->len++;
+            v2_spec->mount_points->values[v2_spec->mount_points->len]->named = mnt->named;
+            v2_spec->mount_points->keys[v2_spec->mount_points->len] = util_strdup_s(mnt->destination);
+            v2_spec->mount_points->len++;
         }
 
         if (vol != NULL && !have_nocopy(mnt)) {
             /* if mount point have data and it's mounted from volume,
              * we need to copy data from destination mount point to volume */
-            ret = copy_data_to_volume(common_config->base_fs, mnt);
+            ret = copy_data_to_volume(v2_spec->base_fs, mnt);
             if (ret != 0) {
                 ERROR("Failed to copy data to volume");
                 goto out;
             }
         }
 
-        // mount -t have no type volume, use bind in oci spec
+        // mount -t have no type volume, trans volume to bind
         if (strcmp(mnt->type, "volume") == 0) {
             free(mnt->type);
             mnt->type = util_strdup_s("bind");
         }
-        oci_spec->mounts[oci_spec->mounts_len] = mnt;
-        oci_spec->mounts_len++;
-        mounts[i] = NULL;
-
         free_volume(vol);
         vol = NULL;
     }
@@ -2137,39 +2153,36 @@ out:
     return ret;
 }
 
-static bool mounts_expand(oci_runtime_spec *container, size_t add_len)
+static bool mounts_expand(defs_mount ***all_mounts, size_t *all_mounts_len, size_t add_len)
 {
     defs_mount **tmp_mount = NULL;
     int ret = 0;
-    size_t old_len = container->mounts_len;
+    defs_mount **old_mount = *all_mounts;
+    size_t old_len = *all_mounts_len;
+
     if (add_len > SIZE_MAX / sizeof(defs_mount *) - old_len) {
         ERROR("Too many mount elements!");
         return false;
     }
-    ret = util_mem_realloc((void **)&tmp_mount, (old_len + add_len) * sizeof(defs_mount *), container->mounts,
+    ret = util_mem_realloc((void **)&tmp_mount, (old_len + add_len) * sizeof(defs_mount *), old_mount,
                            old_len * sizeof(defs_mount *));
     if (ret < 0) {
         ERROR("memory realloc failed for mount array expand");
         return false;
     }
-    container->mounts = tmp_mount;
-    container->mounts_len = old_len + add_len;
+    *all_mounts = tmp_mount;
+    *all_mounts_len = old_len + add_len;
 
     return true;
 }
 
-static bool mount_file(oci_runtime_spec *container, const char *src_path, const char *dst_path)
+static bool mount_file(defs_mount ***all_mounts, size_t *all_mounts_len, const char *src_path, const char *dst_path)
 {
     char **options = NULL;
     size_t options_len = 2;
     bool ret = false;
     defs_mount *tmp_mounts = NULL;
 
-    /* mount options */
-    if (options_len > SIZE_MAX / sizeof(char *)) {
-        ERROR("Options len is too long!");
-        goto out_free;
-    }
     options = util_common_calloc_s(options_len * sizeof(char *));
     if (options == NULL) {
         ERROR("Out of memory");
@@ -2192,11 +2205,12 @@ static bool mount_file(oci_runtime_spec *container, const char *src_path, const
     options = NULL;
 
     /* expand mount array */
-    if (!mounts_expand(container, 1)) {
+    if (!mounts_expand(all_mounts, all_mounts_len, 1)) {
         goto out_free;
     }
+
     /* add a new mount node */
-    container->mounts[container->mounts_len - 1] = tmp_mounts;
+    (*all_mounts)[(*all_mounts_len) - 1] = tmp_mounts;
 
     ret = true;
 out_free:
@@ -2208,17 +2222,14 @@ out_free:
     return ret;
 }
 
-static bool add_host_channel_mount(oci_runtime_spec *container, const host_config_host_channel *host_channel)
+static bool add_host_channel_mount(defs_mount ***all_mounts, size_t *all_mounts_len,
+                                   const host_config_host_channel *host_channel)
 {
     char **options = NULL;
     size_t options_len = 3;
     bool ret = false;
     defs_mount *tmp_mounts = NULL;
 
-    if (options_len > SIZE_MAX / sizeof(char *)) {
-        ERROR("Invalid option size");
-        return ret;
-    }
     options = util_common_calloc_s(options_len * sizeof(char *));
     if (options == NULL) {
         ERROR("Out of memory");
@@ -2242,15 +2253,14 @@ static bool add_host_channel_mount(oci_runtime_spec *container, const host_confi
     options = NULL;
 
     /* expand mount array */
-    if (!mounts_expand(container, 1)) {
+    if (!mounts_expand(all_mounts, all_mounts_len, 1)) {
         goto out_free;
     }
-    /* add a new mount node */
-    container->mounts[container->mounts_len - 1] = tmp_mounts;
+
+    (*all_mounts)[(*all_mounts_len) - 1] = tmp_mounts;
 
     ret = true;
 out_free:
-
     if (!ret) {
         util_free_array_by_len(options, options_len);
         free_defs_mount(tmp_mounts);
@@ -2319,7 +2329,7 @@ static inline bool is_mount_destination_hostname(const char *destination)
  * if not exists: append mounts to ocispec by v2_spec
  * if exists: replace the source in v2_spec
  */
-static int append_network_files_mounts(oci_runtime_spec *oci_spec, host_config *host_spec,
+static int append_network_files_mounts(defs_mount ***all_mounts, size_t *all_mounts_len, host_config *host_spec,
                                        container_config_v2_common_config *v2_spec)
 {
     int ret = 0;
@@ -2327,25 +2337,27 @@ static int append_network_files_mounts(oci_runtime_spec *oci_spec, host_config *
     bool has_hosts_mount = false;
     bool has_resolv_mount = false;
     bool has_hostname_mount = false;
+    defs_mount **old_mounts = *all_mounts;
+    size_t old_mounts_len = *all_mounts_len;
 #ifdef ENABLE_SELINUX
     bool share = namespace_is_container(host_spec->network_mode);
 #endif
 
-    for (i = 0; i < oci_spec->mounts_len; i++) {
-        if (is_mount_destination_hosts(oci_spec->mounts[i]->destination)) {
+    for (i = 0; i < old_mounts_len; i++) {
+        if (is_mount_destination_hosts(old_mounts[i]->destination)) {
             has_hosts_mount = true;
             free(v2_spec->hosts_path);
-            v2_spec->hosts_path = util_strdup_s(oci_spec->mounts[i]->source);
+            v2_spec->hosts_path = util_strdup_s(old_mounts[i]->source);
         }
-        if (is_mount_destination_resolv(oci_spec->mounts[i]->destination)) {
+        if (is_mount_destination_resolv(old_mounts[i]->destination)) {
             has_resolv_mount = true;
             free(v2_spec->resolv_conf_path);
-            v2_spec->resolv_conf_path = util_strdup_s(oci_spec->mounts[i]->source);
+            v2_spec->resolv_conf_path = util_strdup_s(old_mounts[i]->source);
         }
-        if (is_mount_destination_hostname(oci_spec->mounts[i]->destination)) {
+        if (is_mount_destination_hostname(old_mounts[i]->destination)) {
             has_hostname_mount = true;
             free(v2_spec->hostname_path);
-            v2_spec->hostname_path = util_strdup_s(oci_spec->mounts[i]->source);
+            v2_spec->hostname_path = util_strdup_s(old_mounts[i]->source);
         }
     }
 
@@ -2361,7 +2373,7 @@ static int append_network_files_mounts(oci_runtime_spec *oci_spec, host_config *
                 goto out;
             }
 #endif
-            if (!mount_file(oci_spec, v2_spec->hosts_path, ETC_HOSTS)) {
+            if (!mount_file(all_mounts, all_mounts_len, v2_spec->hosts_path, ETC_HOSTS)) {
                 ERROR("Merge hosts mount failed");
                 ret = -1;
                 goto out;
@@ -2379,7 +2391,7 @@ static int append_network_files_mounts(oci_runtime_spec *oci_spec, host_config *
                 goto out;
             }
 #endif
-            if (!mount_file(oci_spec, v2_spec->resolv_conf_path, RESOLV_CONF_PATH)) {
+            if (!mount_file(all_mounts, all_mounts_len, v2_spec->resolv_conf_path, RESOLV_CONF_PATH)) {
                 ERROR("Merge resolv.conf mount failed");
                 ret = -1;
                 goto out;
@@ -2397,7 +2409,7 @@ static int append_network_files_mounts(oci_runtime_spec *oci_spec, host_config *
                 return -1;
             }
 #endif
-            if (!mount_file(oci_spec, v2_spec->hostname_path, ETC_HOSTNAME)) {
+            if (!mount_file(all_mounts, all_mounts_len, v2_spec->hostname_path, ETC_HOSTNAME)) {
                 ERROR("Merge hostname mount failed");
                 ret = -1;
                 goto out;
@@ -2497,8 +2509,7 @@ out:
     return ret;
 }
 
-static int prepare_share_shm(oci_runtime_spec *oci_spec, host_config *host_spec,
-                             container_config_v2_common_config *v2_spec)
+static int prepare_share_shm(host_config *host_spec, container_config_v2_common_config *v2_spec)
 {
 #define MAX_PROPERTY_LEN 64
     char shmproperty[MAX_PROPERTY_LEN] = { 0 };
@@ -2551,17 +2562,13 @@ out:
     return ret;
 }
 
-static bool add_shm_mount(oci_runtime_spec *container, const char *shm_path)
+static bool add_shm_mount(defs_mount ***all_mounts, size_t *all_mounts_len, const char *shm_path)
 {
     char **options = NULL;
     size_t options_len = 3;
     bool ret = false;
     defs_mount *tmp_mounts = NULL;
 
-    if (options_len > SIZE_MAX / sizeof(char *)) {
-        ERROR("Invalid option size");
-        return ret;
-    }
     options = util_common_calloc_s(options_len * sizeof(char *));
     if (options == NULL) {
         ERROR("Out of memory");
@@ -2586,11 +2593,11 @@ static bool add_shm_mount(oci_runtime_spec *container, const char *shm_path)
     options = NULL;
 
     /* expand mount array */
-    if (!mounts_expand(container, 1)) {
+    if (!mounts_expand(all_mounts, all_mounts_len, 1)) {
         goto out_free;
     }
-    /* add a new mount node */
-    container->mounts[container->mounts_len - 1] = tmp_mounts;
+
+    (*all_mounts)[(*all_mounts_len) - 1] = tmp_mounts;
 
     ret = true;
 out_free:
@@ -2603,8 +2610,7 @@ out_free:
 }
 
 #define SHM_MOUNT_POINT "/dev/shm"
-static int setup_ipc_dirs(oci_runtime_spec *oci_spec, host_config *host_spec,
-                          container_config_v2_common_config *v2_spec)
+static int setup_ipc_dirs(host_config *host_spec, container_config_v2_common_config *v2_spec)
 {
     int ret = 0;
     container_t *cont = NULL;
@@ -2617,7 +2623,7 @@ static int setup_ipc_dirs(oci_runtime_spec *oci_spec, host_config *host_spec,
     }
     // setup shareable dirs
     if (host_spec->ipc_mode == NULL || namespace_is_shareable(host_spec->ipc_mode)) {
-        return prepare_share_shm(oci_spec, host_spec, v2_spec);
+        return prepare_share_shm(host_spec, v2_spec);
     }
 
     if (namespace_is_container(host_spec->ipc_mode)) {
@@ -2654,7 +2660,7 @@ int destination_compare(const void *p1, const void *p2)
     return strcmp(mount_1->destination, mount_2->destination);
 }
 
-static defs_mount * get_conflict_mount_point(defs_mount **mounts, size_t mounts_len, defs_mount *mnt)
+static defs_mount *get_conflict_mount_point(defs_mount **mounts, size_t mounts_len, defs_mount *mnt)
 {
     size_t i = 0;
 
@@ -2832,7 +2838,7 @@ static int add_image_config_volumes(container_config *container_spec, defs_mount
     defs_mount *mnt = NULL;
     defs_mount *conflict = NULL;
 
-    for (i = 0; container_spec->volumes != 0 &&  i < container_spec->volumes->len; i++) {
+    for (i = 0; container_spec->volumes != 0 && i < container_spec->volumes->len; i++) {
         mnt = parse_anonymous_volume(container_spec->volumes->keys[i]);
         if (mnt == NULL) {
             ERROR("parse binds %s failed", container_spec->volumes->keys[i]);
@@ -2863,8 +2869,8 @@ out:
 // 2. if --volumes-from conflict with -v/--mount, drop the mount of --volumes-from
 // 3. if anonymous volumes in image config conflict with -v/--mount/--volumes-from,
 //    drop the anonymous volumes in image config
-static int merge_all_fs_mounts(host_config *host_spec, container_config *container_spec,
-                               defs_mount ***all_mounts, size_t *all_mounts_len)
+static int merge_all_fs_mounts(host_config *host_spec, container_config *container_spec, defs_mount ***all_mounts,
+                               size_t *all_mounts_len)
 {
     int ret = 0;
     defs_mount **merged_mounts = NULL;
@@ -2943,9 +2949,9 @@ int merge_conf_mounts(oci_runtime_spec *oci_spec, host_config *host_spec, contai
     }
 
     /* mounts to mount filesystem */
-    ret = merge_fs_mounts_to_oci_and_spec(oci_spec, all_fs_mounts, all_fs_mounts_len, v2_spec);
+    ret = merge_fs_mounts_to_v2_spec(all_fs_mounts, all_fs_mounts_len, v2_spec);
     if (ret) {
-        ERROR("Failed to merge mounts");
+        ERROR("Failed to merge mounts in to v2 spec");
         goto out;
     }
 
@@ -2954,7 +2960,7 @@ int merge_conf_mounts(oci_runtime_spec *oci_spec, host_config *host_spec, contai
 
     /* host channel to mount */
     if (host_spec->host_channel != NULL) {
-        if (!add_host_channel_mount(oci_spec, host_spec->host_channel)) {
+        if (!add_host_channel_mount(&all_fs_mounts, &all_fs_mounts_len, host_spec->host_channel)) {
             ERROR("Failed to merge host channel mount");
             goto out;
         }
@@ -2965,7 +2971,7 @@ int merge_conf_mounts(oci_runtime_spec *oci_spec, host_config *host_spec, contai
     }
 
     /* setup ipc dir */
-    if (setup_ipc_dirs(oci_spec, host_spec, v2_spec) != 0) {
+    if (setup_ipc_dirs(host_spec, v2_spec) != 0) {
         ret = -1;
         goto out;
     }
@@ -2973,27 +2979,33 @@ int merge_conf_mounts(oci_runtime_spec *oci_spec, host_config *host_spec, contai
     /* add ipc mount */
     if (v2_spec->shm_path != NULL) {
         // check whether duplication
-        add_shm_mount(oci_spec, v2_spec->shm_path);
+        add_shm_mount(&all_fs_mounts, &all_fs_mounts_len, v2_spec->shm_path);
     }
 
-    if (!has_mount_shm(host_spec, v2_spec) && host_spec->shm_size > 0) {
-        ret = change_dev_shm_size(oci_spec, host_spec);
+    if (!host_spec->system_container) {
+        ret = append_network_files_mounts(&all_fs_mounts, &all_fs_mounts_len, host_spec, v2_spec);
         if (ret) {
-            ERROR("Failed to set dev shm size");
+            ERROR("Failed to append network mounts");
             goto out;
         }
     }
 
-    if (!host_spec->system_container) {
-        ret = append_network_files_mounts(oci_spec, host_spec, v2_spec);
+    qsort(all_fs_mounts, all_fs_mounts_len, sizeof(all_fs_mounts[0]), destination_compare);
+
+    ret = merge_fs_mounts_to_oci_spec(oci_spec, all_fs_mounts, all_fs_mounts_len);
+    if (ret) {
+        ERROR("Failed to merge all mounts in to oci spec");
+        goto out;
+    }
+
+    if (!has_mount_shm(host_spec, v2_spec) && host_spec->shm_size > 0) {
+        ret = change_dev_shm_size(oci_spec, host_spec);
         if (ret) {
-            ERROR("Failed to append network mounts");
+            ERROR("Failed to set dev shm size");
             goto out;
         }
     }
 
-    qsort(oci_spec->mounts, oci_spec->mounts_len, sizeof(oci_spec->mounts[0]), destination_compare);
-
 out:
     if (mounted) {
         (void)im_umount_container_rootfs(v2_spec->image_type, v2_spec->image, v2_spec->id);
-- 
2.25.1

