backport four bugfix patches
fix issue:https://gitee.com/src-openeuler/mdadm/issues/I62L1B?from=project-issue Signed-off-by: liuzhiqiang <lzhq28@mail.ustc.edu.cn> (cherry picked from commit 304fa34fea4c4543d0c07bd9ab14abffcf45a8bb)
This commit is contained in:
parent
6aaef226aa
commit
5ee6fbf059
@ -0,0 +1,76 @@
|
||||
From ac934fb9123ac13e1de5883df1e5d136ebbb544e Mon Sep 17 00:00:00 2001
|
||||
From: Mateusz Grzonka <mateusz.grzonka@intel.com>
|
||||
Date: Mon, 13 Jun 2022 11:59:34 +0200
|
||||
Subject: [PATCH 2/5] Fix possible NULL ptr dereferences and memory leaks
|
||||
|
||||
In Assemble there was a NULL check for sra variable,
|
||||
which effectively didn't stop the execution in every case.
|
||||
That might have resulted in a NULL pointer dereference.
|
||||
|
||||
Also in super-ddf, mu variable was set to NULL for some condition,
|
||||
and then immidiately dereferenced.
|
||||
Additionally some memory wasn't freed as well.
|
||||
|
||||
Conflict:NA
|
||||
Reference:https://git.kernel.org/pub/scm/utils/mdadm/mdadm.git//commit?id=626bc45396c4959f2c4685c2faa7c4f553f4efdf
|
||||
|
||||
Signed-off-by: Mateusz Grzonka <mateusz.grzonka@intel.com>
|
||||
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
|
||||
---
|
||||
Assemble.c | 7 ++++++-
|
||||
super-ddf.c | 9 +++++++--
|
||||
2 files changed, 13 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/Assemble.c b/Assemble.c
|
||||
index 914c193..3ef4b29 100644
|
||||
--- a/Assemble.c
|
||||
+++ b/Assemble.c
|
||||
@@ -1909,7 +1909,12 @@ int assemble_container_content(struct supertype *st, int mdfd,
|
||||
}
|
||||
|
||||
sra = sysfs_read(mdfd, NULL, GET_VERSION|GET_DEVS);
|
||||
- if (sra == NULL || strcmp(sra->text_version, content->text_version) != 0) {
|
||||
+ if (sra == NULL) {
|
||||
+ pr_err("Failed to read sysfs parameters\n");
|
||||
+ return 1;
|
||||
+ }
|
||||
+
|
||||
+ if (strcmp(sra->text_version, content->text_version) != 0) {
|
||||
if (content->array.major_version == -1 &&
|
||||
content->array.minor_version == -2 &&
|
||||
c->readonly &&
|
||||
diff --git a/super-ddf.c b/super-ddf.c
|
||||
index c095e8a..b61aa2f 100644
|
||||
--- a/super-ddf.c
|
||||
+++ b/super-ddf.c
|
||||
@@ -5121,13 +5121,16 @@ static struct mdinfo *ddf_activate_spare(struct active_array *a,
|
||||
*/
|
||||
vc = find_vdcr(ddf, a->info.container_member, rv->disk.raid_disk,
|
||||
&n_bvd, &vcl);
|
||||
- if (vc == NULL)
|
||||
+ if (vc == NULL) {
|
||||
+ free(rv);
|
||||
return NULL;
|
||||
+ }
|
||||
|
||||
mu = xmalloc(sizeof(*mu));
|
||||
if (posix_memalign(&mu->space, 512, sizeof(struct vcl)) != 0) {
|
||||
free(mu);
|
||||
- mu = NULL;
|
||||
+ free(rv);
|
||||
+ return NULL;
|
||||
}
|
||||
|
||||
mu->len = ddf->conf_rec_len * 512 * vcl->conf.sec_elmnt_count;
|
||||
@@ -5157,6 +5160,8 @@ static struct mdinfo *ddf_activate_spare(struct active_array *a,
|
||||
pr_err("BUG: can't find disk %d (%d/%d)\n",
|
||||
di->disk.raid_disk,
|
||||
di->disk.major, di->disk.minor);
|
||||
+ free(mu);
|
||||
+ free(rv);
|
||||
return NULL;
|
||||
}
|
||||
vc->phys_refnum[i_prim] = ddf->phys->entries[dl->pdnum].refnum;
|
||||
--
|
||||
1.8.3.1
|
||||
|
||||
@ -0,0 +1,43 @@
|
||||
From e3130805d3b9768325837b43587a74723f9222c5 Mon Sep 17 00:00:00 2001
|
||||
From: Kinga Tanska <kinga.tanska@intel.com>
|
||||
Date: Thu, 14 Jul 2022 09:02:10 +0200
|
||||
Subject: [PATCH 3/5] Monitor: use devname as char array instead of pointer
|
||||
|
||||
Device name wasn't filled properly due to incorrect use of strcpy.
|
||||
Strcpy was used twice. Firstly to fill devname with "/dev/md/"
|
||||
and then to add chosen name. First strcpy result was overwritten by
|
||||
second one (as a result <device_name> instead of "/dev/md/<device_name>"
|
||||
was assigned). This commit changes this implementation to use snprintf
|
||||
and devname with fixed size.
|
||||
|
||||
Conflict:context adaptation
|
||||
Reference:https://git.kernel.org/pub/scm/utils/mdadm/mdadm.git//commit?id=c8d1c398505b62d9129a4e711f17e4469f4327ff
|
||||
|
||||
Signed-off-by: Kinga Tanska <kinga.tanska@intel.com>
|
||||
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
|
||||
---
|
||||
Monitor.c | 8 +++++---
|
||||
1 file changed, 5 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/Monitor.c b/Monitor.c
|
||||
index 036103f..1980764 100644
|
||||
--- a/Monitor.c
|
||||
+++ b/Monitor.c
|
||||
@@ -175,9 +175,11 @@ int Monitor(struct mddev_dev *devlist,
|
||||
if (mdlist->devname[0] == '/')
|
||||
st->devname = xstrdup(mdlist->devname);
|
||||
else {
|
||||
- st->devname = xmalloc(8+strlen(mdlist->devname)+1);
|
||||
- strcpy(strcpy(st->devname, "/dev/md/"),
|
||||
- mdlist->devname);
|
||||
+ /* length of "/dev/md/" + device name + terminating byte */
|
||||
+ size_t _len = sizeof("/dev/md/") + strnlen(mdlist->devname, PATH_MAX);
|
||||
+
|
||||
+ st->devname = xcalloc(_len, sizeof(char));
|
||||
+ snprintf(st->devname, _len, "/dev/md/%s", mdlist->devname);
|
||||
}
|
||||
st->next = statelist;
|
||||
st->devnm[0] = 0;
|
||||
--
|
||||
1.8.3.1
|
||||
|
||||
75
6018-mdadm-block-creation-with-long-names.patch
Normal file
75
6018-mdadm-block-creation-with-long-names.patch
Normal file
@ -0,0 +1,75 @@
|
||||
From b088a60fb9c5b11e61e4dff46048b904cd03a218 Mon Sep 17 00:00:00 2001
|
||||
From: Blazej Kucman <blazej.kucman@intel.com>
|
||||
Date: Fri, 3 Dec 2021 15:31:15 +0100
|
||||
Subject: [PATCH 1/2] mdadm: block creation with long names
|
||||
|
||||
This fixes buffer overflows in create_mddev(). It prohibits
|
||||
creation with not supported names for DDF and native. For IMSM,
|
||||
mdadm will do silent cut to 16 later.
|
||||
|
||||
Conflict:NA
|
||||
Reference:https://git.kernel.org/pub/scm/utils/mdadm/mdadm.git//commit?id=ced5fa8b170ad448f4076e24a10c731b5cfb36ce
|
||||
|
||||
Signed-off-by: Mariusz Tkaczyk <mariusz.tkaczyk@linux.intel.com>
|
||||
Signed-off-by: Blazej Kucman <blazej.kucman@intel.com>
|
||||
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
|
||||
---
|
||||
mdadm.8.in | 5 +++++
|
||||
mdadm.c | 9 ++++++++-
|
||||
mdadm.h | 5 +++++
|
||||
3 files changed, 18 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/mdadm.8.in b/mdadm.8.in
|
||||
index 9aec9f4..58614fd 100644
|
||||
--- a/mdadm.8.in
|
||||
+++ b/mdadm.8.in
|
||||
@@ -2129,6 +2129,11 @@ is run, but will be created by
|
||||
.I udev
|
||||
once the array becomes active.
|
||||
|
||||
+The max length md-device name is limited to 32 characters.
|
||||
+Different metadata types have more strict limitation
|
||||
+(like IMSM where only 16 characters are allowed).
|
||||
+For that reason, long name could be truncated or rejected, it depends on metadata policy.
|
||||
+
|
||||
As devices are added, they are checked to see if they contain RAID
|
||||
superblocks or filesystems. They are also checked to see if the variance in
|
||||
device size exceeds 1%.
|
||||
diff --git a/mdadm.c b/mdadm.c
|
||||
index 25a1abd..cb45b59 100644
|
||||
--- a/mdadm.c
|
||||
+++ b/mdadm.c
|
||||
@@ -1354,9 +1354,16 @@ int main(int argc, char *argv[])
|
||||
mdfd = open_mddev(devlist->devname, 1);
|
||||
if (mdfd < 0)
|
||||
exit(1);
|
||||
- } else
|
||||
+ } else {
|
||||
+ char *bname = basename(devlist->devname);
|
||||
+
|
||||
+ if (strlen(bname) > MD_NAME_MAX) {
|
||||
+ pr_err("Name %s is too long.\n", devlist->devname);
|
||||
+ exit(1);
|
||||
+ }
|
||||
/* non-existent device is OK */
|
||||
mdfd = open_mddev(devlist->devname, 0);
|
||||
+ }
|
||||
if (mdfd == -2) {
|
||||
pr_err("device %s exists but is not an md array.\n", devlist->devname);
|
||||
exit(1);
|
||||
diff --git a/mdadm.h b/mdadm.h
|
||||
index 387e681..e25d8a2 100644
|
||||
--- a/mdadm.h
|
||||
+++ b/mdadm.h
|
||||
@@ -1793,3 +1793,8 @@ char *xstrdup(const char *str);
|
||||
#define INVALID_SECTORS 1
|
||||
/* And another special number needed for --data_offset=variable */
|
||||
#define VARIABLE_OFFSET 3
|
||||
+
|
||||
+/**
|
||||
+ * This is true for native and DDF, IMSM allows 16.
|
||||
+ */
|
||||
+#define MD_NAME_MAX 32
|
||||
--
|
||||
1.8.3.1
|
||||
|
||||
173
6019-mdadm-Don-t-open-md-device-for-CREATE-and-ASSEMBLE.patch
Normal file
173
6019-mdadm-Don-t-open-md-device-for-CREATE-and-ASSEMBLE.patch
Normal file
@ -0,0 +1,173 @@
|
||||
From 64b5618da8217bff1ad84c0631e0baf90398693b Mon Sep 17 00:00:00 2001
|
||||
From: Logan Gunthorpe <logang@deltatee.com>
|
||||
Date: Wed, 27 Jul 2022 15:52:46 -0600
|
||||
Subject: [PATCH] mdadm: Don't open md device for CREATE and ASSEMBLE
|
||||
|
||||
The mdadm command tries to open the md device for most modes, first
|
||||
thing, no matter what. When running to create or assemble an array,
|
||||
in most cases, the md device will not exist, the open call will fail
|
||||
and everything will proceed correctly.
|
||||
|
||||
However, when running tests, a create or assembly command may be run
|
||||
shortly after stopping an array and the old md device file may still
|
||||
be around. Then, if create_on_open is set in the kernel, a new md
|
||||
device will be created when mdadm does its initial open.
|
||||
|
||||
When mdadm gets around to creating the new device with the new_array
|
||||
parameter it issues this error:
|
||||
|
||||
mdadm: Fail to create md0 when using
|
||||
/sys/module/md_mod/parameters/new_array, fallback to creation via node
|
||||
|
||||
This is because an mddev was already created by the kernel with the
|
||||
earlier open() call and thus the new one being created will fail with
|
||||
EEXIST. The mdadm command will still successfully be created due to
|
||||
falling back to the node creation method. However, the error message
|
||||
itself will fail any test that's running it.
|
||||
|
||||
This issue is a race condition that is very rare, but a recent change
|
||||
in the kernel caused this to happen more frequently: about 1 in 50
|
||||
times.
|
||||
|
||||
To fix this, don't bother trying to open the md device for CREATE,
|
||||
ASSEMBLE and BUILD commands, as the file descriptor will never be used
|
||||
anyway even if it is successfully openned. The mdfd has not been used
|
||||
for these commands since:
|
||||
|
||||
7f91af49ad09 ("Delay creation of array devices for assemble/build/create")
|
||||
|
||||
The checks that were done on the open device can be changed to being
|
||||
done with stat.
|
||||
|
||||
Side note: it would be nice to disable create_on_open as well to help
|
||||
solve this, but it seems the work for this was never finished. By default,
|
||||
mdadm will create using the old node interface when a name is specified
|
||||
unless the user specifically puts names=yes in a config file, which
|
||||
doesn't seem to be common or desirable to require this..
|
||||
|
||||
Conflict:add stdbool.h
|
||||
Reference:https://git.kernel.org/pub/scm/utils/mdadm/mdadm.git//commit?id=27ad4900501c615b7c6b266bf23948e5606dba53
|
||||
|
||||
Signed-off-by: Logan Gunthorpe <logang@deltatee.com>
|
||||
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
|
||||
---
|
||||
lib.c | 12 ++++++++++++
|
||||
mdadm.c | 40 ++++++++++++++++++++--------------------
|
||||
mdadm.h | 2 ++
|
||||
3 files changed, 34 insertions(+), 20 deletions(-)
|
||||
|
||||
diff --git a/lib.c b/lib.c
|
||||
index 60890b9..57cc052 100644
|
||||
--- a/lib.c
|
||||
+++ b/lib.c
|
||||
@@ -152,6 +152,18 @@ char *stat2devnm(struct stat *st)
|
||||
return devid2devnm(st->st_rdev);
|
||||
}
|
||||
|
||||
+bool stat_is_md_dev(struct stat *st)
|
||||
+{
|
||||
+ if ((S_IFMT & st->st_mode) != S_IFBLK)
|
||||
+ return false;
|
||||
+ if (major(st->st_rdev) == MD_MAJOR)
|
||||
+ return true;
|
||||
+ if (major(st->st_rdev) == (unsigned)get_mdp_major())
|
||||
+ return true;
|
||||
+
|
||||
+ return false;
|
||||
+}
|
||||
+
|
||||
char *fd2devnm(int fd)
|
||||
{
|
||||
struct stat stb;
|
||||
diff --git a/mdadm.c b/mdadm.c
|
||||
index 7319d02..da66c76 100644
|
||||
--- a/mdadm.c
|
||||
+++ b/mdadm.c
|
||||
@@ -1343,6 +1343,9 @@ int main(int argc, char *argv[])
|
||||
|
||||
if (mode == MANAGE || mode == BUILD || mode == CREATE ||
|
||||
mode == GROW || (mode == ASSEMBLE && ! c.scan)) {
|
||||
+ struct stat stb;
|
||||
+ int ret;
|
||||
+
|
||||
if (devs_found < 1) {
|
||||
pr_err("an md device must be given in this mode\n");
|
||||
exit(2);
|
||||
@@ -1355,6 +1358,12 @@ int main(int argc, char *argv[])
|
||||
mdfd = open_mddev(devlist->devname, 1);
|
||||
if (mdfd < 0)
|
||||
exit(1);
|
||||
+
|
||||
+ ret = fstat(mdfd, &stb);
|
||||
+ if (ret) {
|
||||
+ pr_err("fstat failed on %s.\n", devlist->devname);
|
||||
+ exit(1);
|
||||
+ }
|
||||
} else {
|
||||
char *bname = basename(devlist->devname);
|
||||
|
||||
@@ -1362,30 +1371,21 @@ int main(int argc, char *argv[])
|
||||
pr_err("Name %s is too long.\n", devlist->devname);
|
||||
exit(1);
|
||||
}
|
||||
- /* non-existent device is OK */
|
||||
- mdfd = open_mddev(devlist->devname, 0);
|
||||
- }
|
||||
- if (mdfd == -2) {
|
||||
- pr_err("device %s exists but is not an md array.\n", devlist->devname);
|
||||
- exit(1);
|
||||
- }
|
||||
- if ((int)ident.super_minor == -2) {
|
||||
- struct stat stb;
|
||||
- if (mdfd < 0) {
|
||||
+
|
||||
+ ret = stat(devlist->devname, &stb);
|
||||
+ if (ident.super_minor == -2 && ret != 0) {
|
||||
pr_err("--super-minor=dev given, and listed device %s doesn't exist.\n",
|
||||
- devlist->devname);
|
||||
+ devlist->devname);
|
||||
+ exit(1);
|
||||
+ }
|
||||
+
|
||||
+ if (!ret && !stat_is_md_dev(&stb)) {
|
||||
+ pr_err("device %s exists but is not an md array.\n", devlist->devname);
|
||||
exit(1);
|
||||
}
|
||||
- fstat(mdfd, &stb);
|
||||
- ident.super_minor = minor(stb.st_rdev);
|
||||
- }
|
||||
- if (mdfd >= 0 && mode != MANAGE && mode != GROW) {
|
||||
- /* We don't really want this open yet, we just might
|
||||
- * have wanted to check some things
|
||||
- */
|
||||
- close(mdfd);
|
||||
- mdfd = -1;
|
||||
}
|
||||
+ if (ident.super_minor == -2)
|
||||
+ ident.super_minor = minor(stb.st_rdev);
|
||||
}
|
||||
|
||||
if (s.raiddisks) {
|
||||
diff --git a/mdadm.h b/mdadm.h
|
||||
index 58b14b9..8e7029c 100644
|
||||
--- a/mdadm.h
|
||||
+++ b/mdadm.h
|
||||
@@ -45,6 +45,7 @@ extern __off64_t lseek64 __P ((int __fd, __off64_t __offset, int __whence));
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include <syslog.h>
|
||||
+#include <stdbool.h>
|
||||
#ifdef __GLIBC__
|
||||
/* Newer glibc requires sys/sysmacros.h directly for makedev() */
|
||||
#include <sys/sysmacros.h>
|
||||
@@ -1581,6 +1582,7 @@ void *super1_make_v0(struct supertype *st, struct mdinfo *info, mdp_super_t *sb0
|
||||
extern char *stat2kname(struct stat *st);
|
||||
extern char *fd2kname(int fd);
|
||||
extern char *stat2devnm(struct stat *st);
|
||||
+bool stat_is_md_dev(struct stat *st);
|
||||
extern char *fd2devnm(int fd);
|
||||
extern void udev_block(char *devnm);
|
||||
extern void udev_unblock(void);
|
||||
--
|
||||
1.8.3.1
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
Name: mdadm
|
||||
Version: 4.1
|
||||
Release: rc2.0.11
|
||||
Release: rc2.0.12
|
||||
Summary: The software RAID arrays user manage tools
|
||||
License: GPLv2+
|
||||
URL: http://www.kernel.org/pub/linux/utils/raid/mdadm/
|
||||
@ -26,6 +26,10 @@ Patch6012: 6012-Create-Block-rounding-size-to-max.patch
|
||||
Patch6013: 6013-mdadm-fix-coredump-of-mdadm-monitor-r.patch
|
||||
Patch6014: 6014-mdadm-Fix-mdadm-r-remove-option-regresision.patch
|
||||
Patch6015: 6015-monitor-Avoid-segfault-when-calling-NULL-get_bad_blo.patch
|
||||
Patch6016: 6016-Fix-possible-NULL-ptr-dereferences-and-memory-leaks.patch
|
||||
Patch6017: 6017-Monitor-use-devname-as-char-array-instead-of-pointer.patch
|
||||
Patch6018: 6018-mdadm-block-creation-with-long-names.patch
|
||||
Patch6019: 6019-mdadm-Don-t-open-md-device-for-CREATE-and-ASSEMBLE.patch
|
||||
|
||||
BuildRequires: systemd gcc binutils
|
||||
Requires(post): systemd coreutils
|
||||
@ -88,6 +92,9 @@ install -d -m 710 %{buildroot}/var/run/mdadm/
|
||||
%{_mandir}/man*/*
|
||||
|
||||
%changelog
|
||||
* Thu Dec 8 2022 Zhiqiang Liu <liuzhiqiang26@huawei.com> - 4.1-rc2.0.12
|
||||
- backport four upstream bugfix patches
|
||||
|
||||
* Mon Nov 14 2022 Zhiqiang Liu <liuzhiqiang26@huawei.com> - 4.1-rc2.0.11
|
||||
- backport upstream bugfix patch to fix segfault problem in monitor.c
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user