From 0ca6b8ebbb28a28c212ac0a72ae11d4d2ddc3594 Mon Sep 17 00:00:00 2001 From: wangzhiqiang <wangzhiqiang95@huawei.com> Date: Wed, 22 Mar 2023 10:56:20 +0800 Subject: [PATCH] fix potential null pointer dereference. Signed-off-by: wangzhiqiang <wangzhiqiang95@huawei.com> (cherry picked from commit 128a1b9499f62969a190e5d0dc4a13915dff131a) --- ...x-potential-null-pointer-dereference.patch | 348 ++++++++++++++++++ 0007-Update-file-cryptsetup-ssh.c.patch | 24 ++ cryptsetup.spec | 7 +- 3 files changed, 378 insertions(+), 1 deletion(-) create mode 100644 0006-fix-potential-null-pointer-dereference.patch create mode 100644 0007-Update-file-cryptsetup-ssh.c.patch diff --git a/0006-fix-potential-null-pointer-dereference.patch b/0006-fix-potential-null-pointer-dereference.patch new file mode 100644 index 0000000..fea8385 --- /dev/null +++ b/0006-fix-potential-null-pointer-dereference.patch @@ -0,0 +1,348 @@ +From 5dd515878f23610e541ab761f9c45c6dab1c9700 Mon Sep 17 00:00:00 2001 +From: wangzhiqiang <wangzhiqiang95@huawei.com> +Date: Fri, 10 Feb 2023 15:02:23 +0800 +Subject: [PATCH 1/2] fix potential null pointer dereference. + +Signed-off-by: wangzhiqiang <wangzhiqiang95@huawei.com> +--- + lib/luks2/luks2_digest_pbkdf2.c | 3 +++ + lib/luks2/luks2_json_format.c | 38 +++++++++++++++++++++++++++++---- + lib/luks2/luks2_json_metadata.c | 8 +++++++ + lib/luks2/luks2_keyslot.c | 8 +++++++ + lib/luks2/luks2_keyslot_luks2.c | 18 ++++++++++++++++ + lib/luks2/luks2_luks1_convert.c | 24 +++++++++++++++++++++ + src/cryptsetup.c | 3 +++ + src/integritysetup.c | 3 +++ + src/veritysetup.c | 3 +++ + tokens/ssh/cryptsetup-ssh.c | 8 ++++++- + 10 files changed, 111 insertions(+), 5 deletions(-) + +diff --git a/lib/luks2/luks2_digest_pbkdf2.c b/lib/luks2/luks2_digest_pbkdf2.c +index 03c6f49..003d86d 100644 +--- a/lib/luks2/luks2_digest_pbkdf2.c ++++ b/lib/luks2/luks2_digest_pbkdf2.c +@@ -148,6 +148,9 @@ static int PBKDF2_digest_store(struct crypt_device *cd, + json_object_object_get_ex(hdr->jobj, "digests", &jobj_digests); + } + ++ if (!jobj_digest) ++ return -ENOMEM; ++ + json_object_object_add(jobj_digest, "type", json_object_new_string("pbkdf2")); + json_object_object_add(jobj_digest, "keyslots", json_object_new_array()); + json_object_object_add(jobj_digest, "segments", json_object_new_array()); +diff --git a/lib/luks2/luks2_json_format.c b/lib/luks2/luks2_json_format.c +index 350ebf4..45541c3 100644 +--- a/lib/luks2/luks2_json_format.c ++++ b/lib/luks2/luks2_json_format.c +@@ -300,29 +300,59 @@ int LUKS2_generate_hdr( + return -EINVAL; + + hdr->jobj = json_object_new_object(); ++ if (!hdr->jobj) { ++ r = -ENOMEM; ++ goto err; ++ } + + jobj_keyslots = json_object_new_object(); ++ if (!jobj_keyslots) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(hdr->jobj, "keyslots", jobj_keyslots); + json_object_object_add(hdr->jobj, "tokens", json_object_new_object()); + jobj_segments = json_object_new_object(); ++ if (!jobj_segments) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(hdr->jobj, "segments", jobj_segments); + json_object_object_add(hdr->jobj, "digests", json_object_new_object()); + jobj_config = json_object_new_object(); ++ if (!jobj_config) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(hdr->jobj, "config", jobj_config); + + digest = LUKS2_digest_create(cd, "pbkdf2", hdr, vk); +- if (digest < 0) ++ if (digest < 0) { ++ r = -EINVAL; + goto err; ++ } + +- if (LUKS2_digest_segment_assign(cd, hdr, 0, digest, 1, 0) < 0) ++ if (LUKS2_digest_segment_assign(cd, hdr, 0, digest, 1, 0) < 0) { ++ r = -EINVAL; + goto err; ++ } + + jobj_segment = json_segment_create_crypt(data_offset, 0, NULL, cipher, sector_size, 0); +- if (!jobj_segment) ++ if (!jobj_segment) { ++ r = -EINVAL; + goto err; ++ } + + if (integrity) { + jobj_integrity = json_object_new_object(); ++ if (!jobj_integrity) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_integrity, "type", json_object_new_string(integrity)); + json_object_object_add(jobj_integrity, "journal_encryption", json_object_new_string("none")); + json_object_object_add(jobj_integrity, "journal_integrity", json_object_new_string("none")); +@@ -339,7 +369,7 @@ int LUKS2_generate_hdr( + err: + json_object_put(hdr->jobj); + hdr->jobj = NULL; +- return -EINVAL; ++ return r; + } + + int LUKS2_wipe_header_areas(struct crypt_device *cd, +diff --git a/lib/luks2/luks2_json_metadata.c b/lib/luks2/luks2_json_metadata.c +index 0c449ee..e12b3c7 100644 +--- a/lib/luks2/luks2_json_metadata.c ++++ b/lib/luks2/luks2_json_metadata.c +@@ -90,6 +90,9 @@ struct json_object *LUKS2_array_remove(struct json_object *array, const char *nu + + /* Create new array without jobj_removing. */ + array_new = json_object_new_array(); ++ if (!array_new) ++ return NULL; ++ + for (i = 0; i < (int) json_object_array_length(array); i++) { + jobj1 = json_object_array_get_idx(array, i); + if (jobj1 != jobj_removing) +@@ -456,6 +459,9 @@ static int hdr_validate_json_size(struct crypt_device *cd, json_object *hdr_jobj + + json = json_object_to_json_string_ext(hdr_jobj, + JSON_C_TO_STRING_PLAIN | JSON_C_TO_STRING_NOSLASHESCAPE); ++ if (!json) ++ return 1; ++ + json_area_size = crypt_jobj_get_uint64(jobj1); + json_size = (uint64_t)strlen(json); + +@@ -1362,6 +1368,8 @@ int LUKS2_config_set_flags(struct crypt_device *cd, struct luks2_hdr *hdr, uint3 + return 0; + + jobj_flags = json_object_new_array(); ++ if (!jobj_flags) ++ return -ENOMEM; + + for (i = 0; persistent_flags[i].description; i++) { + if (flags & persistent_flags[i].flag) { +diff --git a/lib/luks2/luks2_keyslot.c b/lib/luks2/luks2_keyslot.c +index 3d70186..c2a4088 100644 +--- a/lib/luks2/luks2_keyslot.c ++++ b/lib/luks2/luks2_keyslot.c +@@ -838,6 +838,9 @@ int placeholder_keyslot_alloc(struct crypt_device *cd, + return -EINVAL; + + jobj_keyslot = json_object_new_object(); ++ if (!jobj_keyslot) ++ return -ENOMEM; ++ + json_object_object_add(jobj_keyslot, "type", json_object_new_string("placeholder")); + /* + * key_size = -1 makes placeholder keyslot impossible to pass validation. +@@ -848,6 +851,11 @@ int placeholder_keyslot_alloc(struct crypt_device *cd, + + /* Area object */ + jobj_area = json_object_new_object(); ++ if (!jobj_area) { ++ json_object_put(jobj_keyslot); ++ return -ENOMEM; ++ } ++ + json_object_object_add(jobj_area, "offset", crypt_jobj_new_uint64(area_offset)); + json_object_object_add(jobj_area, "size", crypt_jobj_new_uint64(area_length)); + json_object_object_add(jobj_keyslot, "area", jobj_area); +diff --git a/lib/luks2/luks2_keyslot_luks2.c b/lib/luks2/luks2_keyslot_luks2.c +index 49b3a75..1513d25 100644 +--- a/lib/luks2/luks2_keyslot_luks2.c ++++ b/lib/luks2/luks2_keyslot_luks2.c +@@ -489,17 +489,32 @@ static int luks2_keyslot_alloc(struct crypt_device *cd, + } + + jobj_keyslot = json_object_new_object(); ++ if (!jobj_keyslot) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_keyslot, "type", json_object_new_string("luks2")); + json_object_object_add(jobj_keyslot, "key_size", json_object_new_int(volume_key_len)); + + /* AF object */ + jobj_af = json_object_new_object(); ++ if (!jobj_af) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_af, "type", json_object_new_string("luks1")); + json_object_object_add(jobj_af, "stripes", json_object_new_int(params->af.luks1.stripes)); + json_object_object_add(jobj_keyslot, "af", jobj_af); + + /* Area object */ + jobj_area = json_object_new_object(); ++ if (!jobj_area) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_area, "type", json_object_new_string("raw")); + json_object_object_add(jobj_area, "offset", crypt_jobj_new_uint64(area_offset)); + json_object_object_add(jobj_area, "size", crypt_jobj_new_uint64(area_length)); +@@ -518,6 +533,9 @@ static int luks2_keyslot_alloc(struct crypt_device *cd, + json_object_object_del_by_uint(jobj_keyslots, keyslot); + + return r; ++err: ++ json_object_put(jobj_keyslot); ++ return r; + } + + static int luks2_keyslot_open(struct crypt_device *cd, +diff --git a/lib/luks2/luks2_luks1_convert.c b/lib/luks2/luks2_luks1_convert.c +index 84fd44f..8350dba 100644 +--- a/lib/luks2/luks2_luks1_convert.c ++++ b/lib/luks2/luks2_luks1_convert.c +@@ -38,13 +38,24 @@ static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struc + size_t base64_len; + struct json_object *keyslot_obj, *field, *jobj_kdf, *jobj_af, *jobj_area; + uint64_t offset, area_size, offs_a, offs_b, length; ++ int r; + + keyslot_obj = json_object_new_object(); ++ if (!keyslot_obj) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(keyslot_obj, "type", json_object_new_string("luks2")); + json_object_object_add(keyslot_obj, "key_size", json_object_new_int64(hdr_v1->keyBytes)); + + /* KDF */ + jobj_kdf = json_object_new_object(); ++ if (!jobj_kdf) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_kdf, "type", json_object_new_string(CRYPT_KDF_PBKDF2)); + json_object_object_add(jobj_kdf, "hash", json_object_new_string(hdr_v1->hashSpec)); + json_object_object_add(jobj_kdf, "iterations", json_object_new_int64(hdr_v1->keyblock[keyslot].passwordIterations)); +@@ -64,6 +75,11 @@ static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struc + + /* AF */ + jobj_af = json_object_new_object(); ++ if (!jobj_af) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_af, "type", json_object_new_string("luks1")); + json_object_object_add(jobj_af, "hash", json_object_new_string(hdr_v1->hashSpec)); + /* stripes field ignored, fixed to LUKS_STRIPES (4000) */ +@@ -72,6 +88,11 @@ static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struc + + /* Area */ + jobj_area = json_object_new_object(); ++ if (!jobj_area) { ++ r = -ENOMEM; ++ goto err; ++ } ++ + json_object_object_add(jobj_area, "type", json_object_new_string("raw")); + + /* encryption algorithm field */ +@@ -97,6 +118,9 @@ static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struc + + *keyslot_object = keyslot_obj; + return 0; ++err: ++ json_object_put(keyslot_obj); ++ return r; + } + + static int json_luks1_keyslots(const struct luks_phdr *hdr_v1, struct json_object **keyslots_object) +diff --git a/src/cryptsetup.c b/src/cryptsetup.c +index e785dc3..78421a6 100644 +--- a/src/cryptsetup.c ++++ b/src/cryptsetup.c +@@ -3767,6 +3767,9 @@ int main(int argc, const char **argv) + textdomain(PACKAGE); + + popt_context = poptGetContext(PACKAGE, argc, argv, popt_options, 0); ++ if (!popt_context) ++ exit(EXIT_FAILURE); ++ + poptSetOtherOptionHelp(popt_context, + _("[OPTION...] <action> <action-specific>")); + +diff --git a/src/integritysetup.c b/src/integritysetup.c +index 4604302..468a8cf 100644 +--- a/src/integritysetup.c ++++ b/src/integritysetup.c +@@ -569,6 +569,9 @@ int main(int argc, const char **argv) + textdomain(PACKAGE); + + popt_context = poptGetContext("integrity", argc, argv, popt_options, 0); ++ if (!popt_context) ++ exit(EXIT_FAILURE); ++ + poptSetOtherOptionHelp(popt_context, + _("[OPTION...] <action> <action-specific>")); + +diff --git a/src/veritysetup.c b/src/veritysetup.c +index 04fd996..2a701af 100644 +--- a/src/veritysetup.c ++++ b/src/veritysetup.c +@@ -588,6 +588,9 @@ int main(int argc, const char **argv) + textdomain(PACKAGE); + + popt_context = poptGetContext("verity", argc, argv, popt_options, 0); ++ if (!popt_context) ++ exit(EXIT_FAILURE); ++ + poptSetOtherOptionHelp(popt_context, + _("[OPTION...] <action> <action-specific>")); + +diff --git a/tokens/ssh/cryptsetup-ssh.c b/tokens/ssh/cryptsetup-ssh.c +index c1d0a60..87c55d5 100644 +--- a/tokens/ssh/cryptsetup-ssh.c ++++ b/tokens/ssh/cryptsetup-ssh.c +@@ -78,13 +78,19 @@ static int token_add( + + r = -EINVAL; + jobj = json_object_new_object(); +- if (!jobj) ++ if (!jobj) { ++ r = -ENOMEM; + goto out; ++ } + + /* type is mandatory field in all tokens and must match handler name member */ + json_object_object_add(jobj, "type", json_object_new_string(TOKEN_NAME)); + + jobj_keyslots = json_object_new_array(); ++ if (!jobj_keyslots) { ++ r = -ENOMEM; ++ goto out; ++ } + + /* mandatory array field (may be empty and assigned later */ + json_object_object_add(jobj, "keyslots", jobj_keyslots); +-- +2.33.0 + diff --git a/0007-Update-file-cryptsetup-ssh.c.patch b/0007-Update-file-cryptsetup-ssh.c.patch new file mode 100644 index 0000000..52bc974 --- /dev/null +++ b/0007-Update-file-cryptsetup-ssh.c.patch @@ -0,0 +1,24 @@ +From 7883cf7f2b8f2a37aea78aced53b7a445ec72c3b Mon Sep 17 00:00:00 2001 +From: wangzhiqiang <zhiqiangwang12_4@163.com> +Date: Fri, 10 Feb 2023 16:48:19 +0000 +Subject: [PATCH 2/2] Update file cryptsetup-ssh.c + +--- + tokens/ssh/cryptsetup-ssh.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/tokens/ssh/cryptsetup-ssh.c b/tokens/ssh/cryptsetup-ssh.c +index 87c55d5..0d06000 100644 +--- a/tokens/ssh/cryptsetup-ssh.c ++++ b/tokens/ssh/cryptsetup-ssh.c +@@ -76,7 +76,6 @@ static int token_add( + if (r) + goto out; + +- r = -EINVAL; + jobj = json_object_new_object(); + if (!jobj) { + r = -ENOMEM; +-- +2.33.0 + diff --git a/cryptsetup.spec b/cryptsetup.spec index 0df419b..06f5ec4 100644 --- a/cryptsetup.spec +++ b/cryptsetup.spec @@ -1,6 +1,6 @@ Name: cryptsetup Version: 2.4.1 -Release: 4 +Release: 5 Summary: Utility used to conveniently set up disk encryption License: GPLv2+ and CC0-1.0 and LGPLv2+ URL: https://gitlab.com/cryptsetup/cryptsetup @@ -11,6 +11,8 @@ Patch2: 0002-fix-compat-test.patch Patch3: 0003-add-test-case-for-sm4.patch Patch4: 0004-Fix-CVE-2021-4122-LUKS2-reencryption-crash-recovery-.patch Patch5: 0005-Fix-OpenSSL-2-crypto-backend-PBKDF2-possible-iterati.patch +Patch6: 0006-fix-potential-null-pointer-dereference.patch +Patch7: 0007-Update-file-cryptsetup-ssh.c.patch BuildRequires: openssl-devel, popt-devel, device-mapper-devel, gcc, libssh-devel, gettext-devel libtool BuildRequires: libuuid-devel, json-c-devel, libargon2-devel, libpwquality-devel, libblkid-devel @@ -117,6 +119,9 @@ make check %{_mandir}/man8/* %changelog +* Wed Mar 22 2023 wangzhiqiang <wangzhiqiang95@huawei.com> - 2.4.1-5 +- fix potential null pointer dereference + * Sat Feb 25 2023 volcanodragon <linfeilong@huawei.com> - 2.4.1-4 - fix pbkdf-force-iterations in openssl -- Gitee