- + minor refactoring
---
 src/dbus/abrt-dbus.c    |   71 +++++++++++++++++++++++++++++++++-------------
 src/include/abrt-dbus.h |    4 ++
 src/lib/Makefile.am     |    3 +-
 src/lib/abrt_glib.c     |   54 +++++++++++++++++++++++++++++++++++
 4 files changed, 111 insertions(+), 21 deletions(-)
 create mode 100644 src/lib/abrt_glib.c

diff --git a/src/dbus/abrt-dbus.c b/src/dbus/abrt-dbus.c
index cf04a0d..abeadaf 100644
--- a/src/dbus/abrt-dbus.c
+++ b/src/dbus/abrt-dbus.c
@@ -6,6 +6,7 @@
 #include "libabrt.h"
 #include "abrt-polkit.h"
 #include "abrt-dbus.h"
+#include "dump_dir.h"
 
 GMainLoop *loop;
 guint g_timeout;
@@ -34,6 +35,9 @@ static const gchar introspection_xml[] =
   "    <method name='ChownProblemDir'>"
   "      <arg type='s' name='problem_dir' direction='in'/>"
   "    </method>"
+  "    <method name='DeleteProblem'>"
+  "      <arg type='as' name='problem_dir' direction='in'/>"
+  "    </method>"
   "    <method name='Quit' />"
   "  </interface>"
   "</node>";
@@ -131,6 +135,25 @@ static bool uid_in_group(uid_t uid, gid_t gid)
     return FALSE;
 }
 
+/*
+ 0 - user doesn't have access
+ 1 - user has access
+*/
+static int dir_accessible_by_uid(const char* dir_path, uid_t uid)
+{
+    struct stat statbuf;
+    if (stat(dir_path, &statbuf) == 0 && S_ISDIR(statbuf.st_mode))
+    {
+        if (uid == 0 || uid_in_group(uid, statbuf.st_gid))
+        {
+            VERB1 log("caller has access to the requested directory %s", 
dir_path);
+            return 1;
+        }
+    }
+
+    return 0;
+}
+
 static GList* scan_directory(const char *path, uid_t caller_uid)
 {
     GList *list = NULL;
@@ -185,19 +208,7 @@ static GVariant *get_problem_dirs_for_uid(uid_t uid, const 
char *dump_location)
 {
     GList *dirs = scan_directory(dump_location, uid);
 
-    GVariantBuilder *builder;
-    builder = g_variant_builder_new(G_VARIANT_TYPE("as"));
-    while (dirs)
-    {
-        g_variant_builder_add(builder, "s", (char*)dirs->data);
-        free(dirs->data);
-        dirs = g_list_delete_link(dirs, dirs);
-    }
-
-    GVariant *response = g_variant_new("(as)", builder);
-    g_variant_builder_unref(builder);
-
-    return response;
+    return variant_from_string_list(dirs);
 }
 
 static void handle_method_call(GDBusConnection *connection,
@@ -331,8 +342,9 @@ static void handle_method_call(GDBusConnection *connection,
                 g_dbus_method_invocation_return_dbus_error(invocation,
                                                   
"org.freedesktop.problems.ChownError",
                                                   strerror(errno));
+            else
+                g_dbus_method_invocation_return_value(invocation, NULL);
 
-            g_dbus_method_invocation_return_value(invocation, NULL);
             dd_close(dd);
             return;
         }
@@ -390,10 +402,7 @@ static void handle_method_call(GDBusConnection *connection,
                                                        | DD_FAIL_QUIETLY_ENOENT
                                                        | 
DD_FAIL_QUIETLY_EACCES);
         if (not_reportable_reason)
-            g_variant_builder_add (builder, "{ss}", 
xstrdup(FILENAME_NOT_REPORTABLE), dd_load_text_ext(dd, FILENAME_NOT_REPORTABLE, 0
-                                                                               
                | DD_LOAD_TEXT_RETURN_NULL_ON_FAILURE
-                                                                               
                | DD_FAIL_QUIETLY_ENOENT
-                                                                               
                | DD_FAIL_QUIETLY_EACCES));
+            g_variant_builder_add (builder, "{ss}", 
xstrdup(FILENAME_NOT_REPORTABLE), not_reportable_reason);
         /* the source of the problem:
         * - first we try to load component, as we use it on Fedora
         */
@@ -406,7 +415,6 @@ static void handle_method_call(GDBusConnection *connection,
         if (!source)
         {
             source = dd_load_text_ext(dd, FILENAME_EXECUTABLE, 0
-                    | DD_LOAD_TEXT_RETURN_NULL_ON_FAILURE
                     | DD_FAIL_QUIETLY_ENOENT
                     | DD_FAIL_QUIETLY_EACCES
             );
@@ -434,6 +442,30 @@ static void handle_method_call(GDBusConnection *connection,
         return;
     }
 
+    else if (g_strcmp0(method_name, "DeleteProblem") == 0)
+    {
+        VERB1 log("DeleteProblem");
+
+        GList *problem_dirs = string_list_from_variant(parameters);
+
+        while (problem_dirs)
+        {
+            if (!dir_accessible_by_uid((const char*)problem_dirs->data, 
caller_uid))
+            {
+                if (polkit_check_authorization_dname(caller, 
"org.freedesktop.problems.getall") != PolkitYes)
+                { // if user didn't provide correct credentials, just move to 
the next dir
+                    problem_dirs = g_list_next((const 
char*)problem_dirs->data);
+                    continue;
+                }
+            }
+            delete_dump_dir((const char*)problem_dirs->data);
+            problem_dirs = g_list_next(problem_dirs);
+        }
+
+        g_dbus_method_invocation_return_value(invocation, NULL);
+        return;
+    }
+
     else if (g_strcmp0(method_name, "Quit") == 0)
     {
         VERB1 log("Quit");
@@ -441,7 +473,6 @@ static void handle_method_call(GDBusConnection *connection,
         g_dbus_method_invocation_return_value(invocation, NULL);
 
         g_main_loop_quit(loop);
-
     }
 }
 
diff --git a/src/include/abrt-dbus.h b/src/include/abrt-dbus.h
index 898dd94..dfc5b80 100644
--- a/src/include/abrt-dbus.h
+++ b/src/include/abrt-dbus.h
@@ -5,4 +5,8 @@
 #define ABRT_DBUS_OBJECT     "/org/freedesktop/problems"
 #define ABRT_DBUS_IFACE    "org.freedesktop.problems"
 
+GList *string_list_from_variant(GVariant *variant);
+
+GVariant *variant_from_string_list(GList *strings);
+
 #endif /* ABRTDBUS_H_ */
diff --git a/src/lib/Makefile.am b/src/lib/Makefile.am
index bbeb687..4ea19ef 100644
--- a/src/lib/Makefile.am
+++ b/src/lib/Makefile.am
@@ -8,7 +8,8 @@ libabrt_la_SOURCES = \
     abrt_conf.c \
     hooklib.c \
     daemon_is_ok.c \
-    kernel.c
+    kernel.c \
+    abrt_glib.c
 
 libabrt_la_CPPFLAGS = \
     -Wall -Wwrite-strings -Werror \
diff --git a/src/lib/abrt_glib.c b/src/lib/abrt_glib.c
new file mode 100644
index 0000000..c54a33a
--- /dev/null
+++ b/src/lib/abrt_glib.c
@@ -0,0 +1,54 @@
+/*
+    Copyright (C) 2011  ABRT team
+    Copyright (C) 2011  RedHat Inc
+
+    This program is free software; you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation; either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License along
+    with this program; if not, write to the Free Software Foundation, Inc.,
+    51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+*/
+#include <glib-2.0/glib.h>
+#include "libabrt.h"
+
+GList *string_list_from_variant(GVariant *variant)
+{
+    GList *list = NULL;
+    GVariantIter *iter;
+    gchar *str;
+    g_variant_get(variant, "(as)", &iter);
+    while (g_variant_iter_loop(iter, "s", &str))
+    {
+        VERB1 log("adding: %s", str);
+        list = g_list_prepend(list, xstrdup(str));
+    }
+    g_variant_unref(variant);
+
+    return list;
+}
+
+GVariant *variant_from_string_list(GList *strings)
+{
+    GVariantBuilder *builder;
+    builder = g_variant_builder_new(G_VARIANT_TYPE("as"));
+
+    while (strings)
+    {
+        g_variant_builder_add(builder, "s", (char*)strings->data);
+        free(strings->data);
+        strings = g_list_delete_link(strings, strings);
+    }
+
+    GVariant *variant = g_variant_new("(as)", builder);
+    g_variant_builder_unref(builder);
+
+    return variant;
+}
\ No newline at end of file
-- 
1.7.7.6

Reply via email to