Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
What's new
7
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Open sidebar
steam
systemd
Commits
054e994d
Commit
054e994d
authored
Nov 15, 2015
by
Michael Biebl
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Fix namespace breakage due to incorrect path sorting
Closes: #787758
parent
9db05f9a
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
214 additions
and
0 deletions
+214
-0
debian/changelog
debian/changelog
+6
-0
debian/patches/core-namespace-fix-path-sorting.patch
debian/patches/core-namespace-fix-path-sorting.patch
+58
-0
debian/patches/series
debian/patches/series
+2
-0
debian/patches/shared-add-path_compare-an-ordering-path-comparison.patch
...shared-add-path_compare-an-ordering-path-comparison.patch
+148
-0
No files found.
debian/changelog
View file @
054e994d
systemd
(
215
-
17
+
deb8u3
)
UNRELEASED
;
urgency
=
medium
*
Fix
namespace
breakage
due
to
incorrect
path
sorting
.
(
Closes
:
#
787758
)
--
Michael
Biebl
<
biebl
@
debian
.
org
>
Mon
,
16
Nov
2015
17
:
49
:
20
+
0100
systemd
(
215
-
17
+
deb8u2
)
stable
;
urgency
=
medium
*
Disable
default
DNS
servers
in
systemd
-
resolved
.
In
v215
they
are
always
...
...
debian/patches/core-namespace-fix-path-sorting.patch
0 → 100644
View file @
054e994d
From: Michal Schmidt <mschmidt@redhat.com>
Date: Mon, 16 Mar 2015 22:04:21 +0100
Subject: core/namespace: fix path sorting
The comparison function we use for qsorting paths is overly indifferent.
Consider these 3 paths for sorting:
/foo
/bar
/foo/foo
qsort() may compare:
"/foo" with "/bar" => 0, indifference
"/bar" with "/foo/foo" => 0, indifference
and assume transitively that "/foo" and "/foo/foo" are also indifferent.
But this is wrong, we want "/foo" sorted before "/foo/foo".
The comparison function must be transitive.
Use path_compare(), which behaves properly.
Fixes: https://bugzilla.redhat.com/show_bug.cgi?id=1184016
(cherry-picked from commit a0827e2b123010c46cfe4f03eebba57d92f9efc4)
---
src/core/namespace.c | 12 ++++--------
1 file changed, 4 insertions(+), 8 deletions(-)
diff --git a/src/core/namespace.c b/src/core/namespace.c
index 5466b7b..23a85df 100644
--- a/src/core/namespace.c
+++ b/src/core/namespace.c
@@ -89,9 +89,11 @@
static int append_mounts(BindMount **p, char **strv, MountMode mode) {
static int mount_path_compare(const void *a, const void *b) {
const BindMount *p = a, *q = b;
+ int d;
- if (path_equal(p->path, q->path)) {
+ d = path_compare(p->path, q->path);
+ if (!d) {
/* If the paths are equal, check the mode */
if (p->mode < q->mode)
return -1;
@@ -103,13 +105,7 @@
static int mount_path_compare(const void *a, const void *b) {
}
/* If the paths are not equal, then order prefixes first */
- if (path_startswith(p->path, q->path))
- return 1;
-
- if (path_startswith(q->path, p->path))
- return -1;
-
- return 0;
+ return d;
}
static void drop_duplicates(BindMount *m, unsigned *n) {
debian/patches/series
View file @
054e994d
...
...
@@ -150,6 +150,8 @@ logind-handle-runtime-dir-without-CAP_SYS_ADMIN.patch
sd-bus-create-clean-error-when-a-property-Set-call-w.patch
manager-do-not-print-anything-while-passwords-are-be.patch
manager-pass-correct-errno-to-strerror.patch
shared-add-path_compare-an-ordering-path-comparison.patch
core-namespace-fix-path-sorting.patch
## Debian specific patches:
Add-back-support-for-Debian-specific-config-files.patch
...
...
debian/patches/shared-add-path_compare-an-ordering-path-comparison.patch
0 → 100644
View file @
054e994d
From: Michal Schmidt <mschmidt@redhat.com>
Date: Mon, 16 Mar 2015 21:58:35 +0100
Subject: shared: add path_compare(), an ordering path comparison
... and make path_equal() a simple wrapper around it.
(cherry-picked from commit 2230852bd9755e1b7bfd1260082471f559b0a005)
---
src/shared/path-util.c | 37 +++++++++++++++++++++++++++----------
src/shared/path-util.h | 1 +
src/test/test-path-util.c | 36 +++++++++++++++++++++++++-----------
3 files changed, 53 insertions(+), 21 deletions(-)
diff --git a/src/shared/path-util.c b/src/shared/path-util.c
index e68d367..60b14b7 100644
--- a/src/shared/path-util.c
+++ b/src/shared/path-util.c
@@ -402,12 +402,18 @@
char* path_startswith(const char *path, const char *prefix) {
}
}
-bool path_equal(const char *a, const char *b) {
+int path_compare(const char *a, const char *b) {
+ int d;
+
assert(a);
assert(b);
- if ((a[0] == '/') != (b[0] == '/'))
- return false;
+ /* A relative path and an abolute path must not compare as equal.
+ * Which one is sorted before the other does not really matter.
+ * Here a relative path is ordered before an absolute path. */
+ d = (a[0] == '/') - (b[0] == '/');
+ if (d)
+ return d;
for (;;) {
size_t j, k;
@@ -416,25 +422,36 @@
bool path_equal(const char *a, const char *b) {
b += strspn(b, "/");
if (*a == 0 && *b == 0)
- return true;
+ return 0;
- if (*a == 0 || *b == 0)
- return false;
+ /* Order prefixes first: "/foo" before "/foo/bar" */
+ if (*a == 0)
+ return -1;
+ if (*b == 0)
+ return 1;
j = strcspn(a, "/");
k = strcspn(b, "/");
- if (j != k)
- return false;
+ /* Alphabetical sort: "/foo/aaa" before "/foo/b" */
+ d = memcmp(a, b, MIN(j, k));
+ if (d)
+ return (d > 0) - (d < 0); /* sign of d */
- if (memcmp(a, b, j) != 0)
- return false;
+ /* Sort "/foo/a" before "/foo/aaa" */
+ d = (j > k) - (j < k); /* sign of (j - k) */
+ if (d)
+ return d;
a += j;
b += k;
}
}
+bool path_equal(const char *a, const char *b) {
+ return path_compare(a, b) == 0;
+}
+
int path_is_mount_point(const char *t, bool allow_symlink) {
union file_handle_union h = {
diff --git a/src/shared/path-util.h b/src/shared/path-util.h
index 976d2b2..54f00a8 100644
--- a/src/shared/path-util.h
+++ b/src/shared/path-util.h
@@ -44,6 +44,7 @@
char* path_make_absolute_cwd(const char *p);
int path_make_relative(const char *from_dir, const char *to_path, char **_r);
char* path_kill_slashes(char *path);
char* path_startswith(const char *path, const char *prefix) _pure_;
+int path_compare(const char *a, const char *b) _pure_;
bool path_equal(const char *a, const char *b) _pure_;
char** path_strv_make_absolute_cwd(char **l);
diff --git a/src/test/test-path-util.c b/src/test/test-path-util.c
index 19462c3..1055e9f 100644
--- a/src/test/test-path-util.c
+++ b/src/test/test-path-util.c
@@ -27,23 +27,37 @@
#include "macro.h"
#include "strv.h"
+#define test_path_compare(a, b, result) { \
+ assert_se(path_compare(a, b) == result); \
+ assert_se(path_compare(b, a) == -result); \
+ assert_se(path_equal(a, b) == !result); \
+ assert_se(path_equal(b, a) == !result); \
+ }
static void test_path(void) {
- assert_se(path_equal("/goo", "/goo"));
- assert_se(path_equal("//goo", "/goo"));
- assert_se(path_equal("//goo/////", "/goo"));
- assert_se(path_equal("goo/////", "goo"));
+ test_path_compare("/goo", "/goo", 0);
+ test_path_compare("/goo", "/goo", 0);
+ test_path_compare("//goo", "/goo", 0);
+ test_path_compare("//goo/////", "/goo", 0);
+ test_path_compare("goo/////", "goo", 0);
+
+ test_path_compare("/goo/boo", "/goo//boo", 0);
+ test_path_compare("//goo/boo", "/goo/boo//", 0);
- assert_se(path_equal("/goo/boo", "/goo//boo"));
- assert_se(path_equal("//goo/boo", "/goo/boo//"));
+ test_path_compare("/", "///", 0);
- assert_se(path_equal("/", "///"));
+ test_path_compare("/x", "x/", 1);
+ test_path_compare("x/", "/", -1);
- assert_se(!path_equal("/x", "x/"));
- assert_se(!path_equal("x/", "/"));
+ test_path_compare("/x/./y", "x/y", 1);
+ test_path_compare("x/.y", "x/y", -1);
- assert_se(!path_equal("/x/./y", "x/y"));
- assert_se(!path_equal("x/.y", "x/y"));
+ test_path_compare("foo", "/foo", -1);
+ test_path_compare("/foo", "/foo/bar", -1);
+ test_path_compare("/foo/aaa", "/foo/b", -1);
+ test_path_compare("/foo/aaa", "/foo/b/a", -1);
+ test_path_compare("/foo/a", "/foo/aaa", -1);
+ test_path_compare("/foo/a/b", "/foo/aaa", -1);
assert_se(path_is_absolute("/"));
assert_se(!path_is_absolute("./"));
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment