Prevent app sockets from being deleted by attacker 28/76228/2 accepted/tizen/common/20160703.125824 accepted/tizen/ivi/20160629.015700 accepted/tizen/mobile/20160629.015619 accepted/tizen/tv/20160629.015737 accepted/tizen/wearable/20160629.015548 submit/tizen/20160627.042541
authorHwankyu Jhun <h.jhun@samsung.com>
Thu, 23 Jun 2016 07:12:29 +0000 (16:12 +0900)
committerHwankyu Jhun <h.jhun@samsung.com>
Thu, 23 Jun 2016 10:33:35 +0000 (19:33 +0900)
- Requires:
https://review.tizen.org/gerrit/#/c/76214/

Change-Id: I761a86f219f0c9c7513930430c38c699d3fd1625
Signed-off-by: Hwankyu Jhun <h.jhun@samsung.com>
include/common.h
src/common.c
src/signal_util.c

index c01d142..9210790 100644 (file)
@@ -69,6 +69,7 @@ void _set_env(appinfo_t *app_info, bundle *kb);
 char **_create_argc_argv(bundle *kb, int *margc, const char *app_path);
 int _proc_check_cmdline_bypid(int pid);
 void _prepare_listen_sock(void);
+int _delete_sock_path(int pid, uid_t uid);
 
 #endif /* __COMMON_H__ */
 
index 6b19d93..0f14356 100644 (file)
@@ -28,6 +28,7 @@
 #include <sys/un.h>
 #include <errno.h>
 #include <dirent.h>
+#include <unistd.h>
 #include <bundle.h>
 #include <bundle_internal.h>
 #ifdef _APPFW_FEATURE_SOCKET_ACTIVATION
@@ -77,6 +78,7 @@ static int __create_server_socket(bool is_app)
 {
        struct sockaddr_un saddr;
        int fd;
+       int ret;
 
        if (is_app)
                fd = socket(AF_UNIX, SOCK_STREAM, 0);
@@ -103,6 +105,25 @@ static int __create_server_socket(bool is_app)
                snprintf(saddr.sun_path, sizeof(saddr.sun_path),
                                "%s/apps/%d/%d",
                                SOCKET_PATH, getuid(), getpid());
+               ret = mkdir(saddr.sun_path, 0700);
+               if (ret != 0) {
+                       if (errno == EEXIST) {
+                               if (access(saddr.sun_path, R_OK) != 0) {
+                                       _E("Failed to access %s directory - %d",
+                                                       saddr.sun_path, errno);
+                                       close(fd);
+                                       return -1;
+                               }
+                       } else {
+                               _E("Failed to create %s directory - %d",
+                                               saddr.sun_path, errno);
+                               close(fd);
+                               return -1;
+                       }
+               }
+               snprintf(saddr.sun_path, sizeof(saddr.sun_path),
+                               "%s/apps/%d/%d/.app-sock",
+                               SOCKET_PATH, getuid(), getpid());
        } else {
                snprintf(saddr.sun_path, sizeof(saddr.sun_path),
                                "%s/daemons/%d/.debug-launchpad-sock",
@@ -799,3 +820,53 @@ void _prepare_listen_sock(void)
        setenv("AUL_LISTEN_SOCK", buf, 1);
 }
 
+static int __delete_dir(const char *path)
+{
+       DIR *dp;
+       struct dirent dentry;
+       struct dirent *result = NULL;
+       char buf[PATH_MAX];
+       struct stat statbuf;
+       int ret;
+
+       if (path == NULL)
+               return -1;
+
+       dp = opendir(path);
+       if (dp == NULL)
+               return -1;
+
+       while (readdir_r(dp, &dentry, &result) == 0 && result) {
+               if (!strcmp(dentry.d_name, ".") || !strcmp(dentry.d_name, ".."))
+                       continue;
+
+               snprintf(buf, sizeof(buf), "%s/%s", path, dentry.d_name);
+               ret = stat(buf, &statbuf);
+               if (ret == 0) {
+                       if (S_ISDIR(statbuf.st_mode))
+                               __delete_dir(buf);
+                       else
+                               unlink(buf);
+               }
+       }
+
+       rmdir(path);
+       closedir(dp);
+
+       return 0;
+}
+
+int _delete_sock_path(int pid, uid_t uid)
+{
+       char path[PATH_MAX];
+
+       snprintf(path, sizeof(path), "/run/aul/apps/%d/%d", uid, pid);
+       if (access(path, F_OK) == 0)
+               __delete_dir(path);
+
+       if (access(path, F_OK) == 0)
+               return -1;
+
+       return 0;
+}
+
index 8b1d62f..f0e8dee 100644 (file)
@@ -15,6 +15,7 @@
  */
 
 #include <stdio.h>
+#include <stdlib.h>
 #include <signal.h>
 #include <sys/smack.h>
 #include <sys/types.h>
@@ -55,9 +56,7 @@ static void __socket_garbage_collector(void)
 
                snprintf(path, sizeof(path), "/proc/%s", dentry->d_name);
                if (access(path, F_OK) != 0) { /* Flawfinder: ignore */
-                       snprintf(path, sizeof(path), "%s/apps/%d/%s",
-                                       SOCKET_PATH, getuid(), dentry->d_name);
-                       unlink(path);
+                       _delete_sock_path(atoi(dentry->d_name), getuid());
                        continue;
                }
        }
@@ -146,9 +145,7 @@ static int __sigchild_action(pid_t dead_pid)
 
        _send_app_dead_signal(dead_pid);
 
-       snprintf(buf, MAX_LOCAL_BUFSZ, "%s/apps/%d/%d",
-                               SOCKET_PATH, getuid(), dead_pid);
-       unlink(buf);
+       _delete_sock_path(dead_pid, getuid());
 
        __socket_garbage_collector();