Merge ~dbungert/update-notifier:lp-1706168 into update-notifier:master

Proposed by Dan Bungert
Status: Merged
Merged at revision: 0856b936e09153150c2b2402c62888ccf03282f0
Proposed branch: ~dbungert/update-notifier:lp-1706168
Merge into: update-notifier:master
Diff against target: 110 lines (+84/-0)
2 files modified
debian/changelog (+7/-0)
src/hooks.c (+77/-0)
Reviewer Review Type Date Requested Status
Brian Murray Approve
Review via email: mp+397367@code.launchpad.net
To post a comment you must log in.
Revision history for this message
Brian Murray (brian-murray) :
review: Approve
Revision history for this message
Sebastien Bacher (seb128) wrote :

I think the change here created bug #1926298 where update-notifier segfaults on valid hooks now, also it sounds like you could simplify the code by using https://developer.gnome.org/glib/stable/glib-Miscellaneous-Utility-Functions.html#g-find-program-in-path

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1diff --git a/debian/changelog b/debian/changelog
2index 926f3fc..d603649 100644
3--- a/debian/changelog
4+++ b/debian/changelog
5@@ -1,3 +1,10 @@
6+update-notifier (3.192.40) hirsute; urgency=medium
7+
8+ * Skip notify for an update if the command we need to run doesn't exist
9+ (LP: #1706168)
10+
11+ -- Dan Bungert <daniel.bungert@canonical.com> Tue, 02 Feb 2021 09:30:11 -0700
12+
13 update-notifier (3.192.39) hirsute; urgency=medium
14
15 * data/list-oem-metapackages:
16diff --git a/src/hooks.c b/src/hooks.c
17index f82a233..cb94081 100644
18--- a/src/hooks.c
19+++ b/src/hooks.c
20@@ -71,6 +71,74 @@ hook_file_time(const gchar *filename)
21 return mtime > ctime ? mtime : ctime;
22 }
23
24+/*
25+ Does the command we're offering to run actually exist?
26+ Command may be quoted, and anything after a space is presumed to be an
27+ argument for the command.
28+ Command may be present in PATH.
29+ */
30+static gboolean
31+hook_command_exists(const char *cmd)
32+{
33+ gboolean result = FALSE;
34+ gchar *unquoted = NULL;
35+ gchar **cargv = NULL;
36+ GError *error = NULL;
37+
38+ if(!cmd) goto out;
39+
40+ unquoted = g_shell_unquote(cmd, &error);
41+ if(!unquoted) {
42+ g_debug_hooks("g_shell_unquote: %s", error->message);
43+ goto out;
44+ }
45+
46+ gint cargc = 0;
47+ cargv = NULL;
48+ if(!g_shell_parse_argv(unquoted, &cargc, &cargv, &error)) {
49+ g_debug_hooks("g_shell_parse_argv: %s", error->message);
50+ goto out;
51+ }
52+
53+ if(cargc < 1) {
54+ g_debug_hooks("g_shell_parse_argv: unexpected output");
55+ goto out;
56+ }
57+
58+ if(cargv[0][0] == '/' &&
59+ g_file_test(cargv[0], G_FILE_TEST_EXISTS|G_FILE_TEST_IS_EXECUTABLE)) {
60+ result = TRUE;
61+ g_debug_hooks("command exists");
62+ goto out;
63+ }
64+
65+ g_debug_hooks("'%s' is not a valid absolute path", cargv[0]);
66+
67+ gchar **pathdirs = g_strsplit(getenv("PATH"), ":", 100);
68+ if(!pathdirs) goto out;
69+
70+ for(int i = 0; pathdirs[i] != NULL; i++) {
71+ gchar *pathdir = pathdirs[i];
72+ char *fname = g_strdup_printf("%s/%s", pathdir, cargv[0]);
73+ if(g_file_test(fname, G_FILE_TEST_EXISTS|G_FILE_TEST_IS_EXECUTABLE)) {
74+ g_debug_hooks("command exists at '%s'", fname);
75+ g_free(fname);
76+ result = TRUE;
77+ goto out;
78+ }
79+ g_free(fname);
80+ }
81+
82+ g_debug_hooks("failed to find command in PATH");
83+
84+out:
85+ if(error) g_error_free(error);
86+ if(cargv) g_strfreev(cargv);
87+ if(pathdirs) g_strfreev(pathdirs);
88+ if(unquoted) g_free(unquoted);
89+ return result;
90+}
91+
92 static gboolean
93 hook_file_md5(const gchar *filename, guint8 *md5)
94 {
95@@ -641,6 +709,15 @@ is_hook_relevant(const gchar *hook_file)
96 res = (exitc == 0);
97 }
98
99+ // check that the Command we are offering exists
100+ if(res) {
101+ b = rfc822_header_lookup(rfc822, "Command");
102+ if(b != NULL) {
103+ g_debug_hooks("found Command: '%s'", b);
104+ res = hook_command_exists(b);
105+ }
106+ }
107+
108 g_free(filename);
109 rfc822_header_free_all(rfc822);
110 return res;

Subscribers

People subscribed via source and target branches