pkgcmd killapp run on server submit/tizen_2.1/20130515.031847
authorjunsuk77.oh <junsuk77.oh@samsung.com>
Tue, 14 May 2013 11:42:32 +0000 (20:42 +0900)
committerjunsuk77.oh <junsuk77.oh@samsung.com>
Tue, 14 May 2013 11:43:34 +0000 (20:43 +0900)
Change-Id: Icd0c142cd3654bfd81436eaacabbe35b2f134c9e
Signed-off-by: junsuk77.oh <junsuk77.oh@samsung.com>
client/include/package-manager.h
client/src/pkgmgr.c
comm/comm_config.h
packaging/pkgmgr.spec
server/src/pkgmgr-server.c
tool/pkg_cmd.c

index 72f4939..c96976b 100755 (executable)
@@ -257,6 +257,7 @@ typedef enum {
        PM_REQUEST_CSC = 0,
        PM_REQUEST_MOVE = 1,
        PM_REQUEST_GET_SIZE = 2,
+       PM_REQUEST_KILL_APP = 3,
        PM_REQUEST_MAX
 }pkgmgr_request_service_type;
 
index ca1b21b..898b828 100755 (executable)
@@ -764,6 +764,40 @@ catch:
        return ret;
 }
 
+static int __kill_app_process(pkgmgr_client * pc, const char *pkgid)
+{
+       const char *pkgtype;
+       char *req_key;
+       char *cookie = NULL;
+       int ret;
+       pkgmgrinfo_pkginfo_h handle;
+
+       /* Check for NULL value of pc */
+       pkgmgr_client_t *mpc = (pkgmgr_client_t *) pc;
+       retvm_if(mpc->ctype != PC_REQUEST, PKGMGR_R_EINVAL, "mpc->ctype is not PC_REQUEST\n");
+
+       ret = pkgmgrinfo_pkginfo_get_pkginfo(pkgid, &handle);
+       retvm_if(ret < 0, PKGMGR_R_ERROR, "pkgmgr_pkginfo_get_pkginfo failed");
+
+       ret = pkgmgrinfo_pkginfo_get_type(handle, &pkgtype);
+       tryvm_if(ret < 0, ret = PKGMGR_R_ERROR, "pkgmgr_pkginfo_get_type failed");
+
+       /* 2. generate req_key */
+       req_key = __get_req_key(pkgid);
+
+       /* 3. request activate */
+       ret = comm_client_request(mpc->info.request.cc, req_key, COMM_REQ_KILL_APP, pkgtype, pkgid, NULL, NULL, 1);
+       if (ret < 0)
+               _LOGE("request failed, ret=%d\n", ret);
+
+catch:
+       free(req_key);
+       pkgmgrinfo_pkginfo_destroy_pkginfo(handle);
+
+       return ret;
+
+}
+
 API pkgmgr_client *pkgmgr_client_new(client_type ctype)
 {
        pkgmgr_client_t *pc = NULL;
@@ -1907,6 +1941,18 @@ API int pkgmgr_client_request_service(pkgmgr_request_service_type service_type,
 
                break;
 
+       case PM_REQUEST_KILL_APP:
+               tryvm_if(pkgid == NULL, ret = PKGMGR_R_EINVAL, "pkgid is NULL\n");
+               tryvm_if(pc == NULL, ret = PKGMGR_R_EINVAL, "pc is NULL\n");
+
+               ret = __kill_app_process(pc, pkgid);
+               if (ret < 0)
+                       _LOGE("__kill_app_process fail \n");
+               else
+                       ret = PKGMGR_R_OK;
+
+               break;
+
        default:
                _LOGE("Wrong Request\n");
                ret = -1;
index adb09f5..c394285 100755 (executable)
@@ -114,6 +114,9 @@ enum {
        /*get package size */
        COMM_REQ_GET_SIZE,
 
+       /*kill app */
+       COMM_REQ_KILL_APP,
+
        COMM_REQ_MAX_SENTINEL
 };
 
index 9229439..dce29a0 100755 (executable)
@@ -1,7 +1,7 @@
 #sbs-git:slp/pkgs/s/slp-pkgmgr pkgmgr 0.1.103 29b53909a5d6e8728429f0a188177eac691cb6ce
 Name:       pkgmgr
 Summary:    Packager Manager client library package
-Version:    0.2.87
+Version:    0.2.88
 Release:    1
 Group:      System/Libraries
 License:    Apache License, Version 2.0
index 82dc55b..02fdeca 100755 (executable)
@@ -127,6 +127,12 @@ typedef enum {
        OPERATION_MAX
 } OPERATION_TYPE;
 
+typedef enum {
+       PMSVC_ALL_APP = 0,
+       PMSVC_UI_APP,
+       PMSVC_SVC_APP
+}pkgmgr_svc_app_component;
+
 struct appdata {
        Evas_Object *win;
        Evas_Object *notify;
@@ -1044,6 +1050,20 @@ void req_cb(void *cb_data, const char *req_id, const int req_type,
                        g_idle_add(queue_job, NULL);
                *ret = COMM_RET_OK;
                break;
+       case COMM_REQ_KILL_APP:
+               /* In case of activate, there is no popup */
+               err = _pm_queue_push(item);
+               p = __get_position_from_pkg_type(item->pkg_type);
+               __set_backend_mode(p);
+               /* Free resource */
+               free(item);
+
+/*             g_idle_add(queue_job, NULL); */
+               if (err == 0)
+                       queue_job(NULL);
+               *ret = COMM_RET_OK;
+               break;
+
        default:
                DBG("Check your request..\n");
                *ret = COMM_RET_ERROR;
@@ -1185,6 +1205,111 @@ int __app_func(const pkgmgrinfo_appinfo_h handle, void *user_data)
        return 0;
 }
 
+static int __pkgcmd_read_proc(const char *path, char *buf, int size)
+{
+       int fd;
+       int ret;
+       if (buf == NULL || path == NULL)
+               return -1;
+       fd = open(path, O_RDONLY);
+       if (fd < 0)
+               return -1;
+       ret = read(fd, buf, size - 1);
+       if (ret <= 0) {
+               close(fd);
+               return -1;
+       } else
+               buf[ret] = 0;
+       close(fd);
+       return ret;
+}
+
+static int __pkgcmd_find_pid_by_cmdline(const char *dname,
+                       const char *cmdline, const char *apppath)
+{
+       int pid = 0;
+
+       if (strcmp(cmdline, apppath) == 0) {
+               pid = atoi(dname);
+               if (pid != getpgid(pid))
+                       pid = 0;
+       }
+       return pid;
+}
+
+static int __pkgcmd_proc_iter_kill_cmdline(const char *apppath, int option)
+{
+       DIR *dp;
+       struct dirent *dentry;
+       int pid;
+       int ret;
+       char buf[1024] = {'\0'};
+       int pgid;
+
+       dp = opendir("/proc");
+       if (dp == NULL) {
+               return -1;
+       }
+
+       while ((dentry = readdir(dp)) != NULL) {
+               if (!isdigit(dentry->d_name[0]))
+                       continue;
+
+               snprintf(buf, sizeof(buf), "/proc/%s/cmdline", dentry->d_name);
+               ret = __pkgcmd_read_proc(buf, buf, sizeof(buf));
+               if (ret <= 0)
+                       continue;
+
+               pid = __pkgcmd_find_pid_by_cmdline(dentry->d_name, buf, apppath);
+               if (pid > 0) {
+                       if (option == 0) {
+                               closedir(dp);
+                               return pid;
+                       }
+                       pgid = getpgid(pid);
+                       if (pgid <= 1) {
+                               closedir(dp);
+                               return -1;
+                       }
+                       if (killpg(pgid, SIGKILL) < 0) {
+                               closedir(dp);
+                               return -1;
+                       }
+                       closedir(dp);
+                       return pid;
+               }
+       }
+       closedir(dp);
+       return 0;
+}
+
+static int __app_list_cb(const pkgmgrinfo_appinfo_h handle, void *user_data)
+{
+       char *exec = NULL;
+       char *appid = NULL;
+       int ret = 0;
+       int pid = -1;
+       if (handle == NULL) {
+               perror("appinfo handle is NULL\n");
+               exit(1);
+       }
+       ret = pkgmgrinfo_appinfo_get_exec(handle, &exec);
+       if (ret) {
+               perror("Failed to get app exec path\n");
+               exit(1);
+       }
+       ret = pkgmgrinfo_appinfo_get_appid(handle, &appid);
+       if (ret) {
+               perror("Failed to get appid\n");
+               exit(1);
+       }
+
+       pid = __pkgcmd_proc_iter_kill_cmdline(exec, 1);
+       if (pid > 0)
+               DBG("Appid: %s is Terminated\n", appid);
+
+       return 0;
+}
 
 gboolean queue_job(void *data)
 {
@@ -1620,6 +1745,60 @@ pop:
                }
                break;
 
+       case COMM_REQ_KILL_APP:
+               DBG("COMM_REQ_KILL_APP start");
+               _save_queue_status(item, "processing");
+               DBG("saved queue status. Now try fork()");
+               /*save pkg type and pkg name for future*/
+               x = (pos + num_of_backends - 1) % num_of_backends;
+               strncpy((ptr + x)->pkgtype, item->pkg_type, MAX_PKG_TYPE_LEN-1);
+               strncpy((ptr + x)->pkgid, item->pkgid, MAX_PKG_NAME_LEN-1);
+               strncpy((ptr + x)->args, item->args, MAX_PKG_ARGS_LEN-1);
+               (ptr + x)->pid = fork();
+               DBG("child forked [%d]\n", (ptr + x)->pid);
+
+               switch ((ptr + x)->pid) {
+               case 0: /* child */
+                       DBG("child run parse argv()");
+
+                       pkgmgrinfo_pkginfo_h handle;
+                       ret = pkgmgrinfo_pkginfo_get_pkginfo(item->pkgid, &handle);
+                       if (ret < 0) {
+                               DBG("Failed to get handle\n");
+                               exit(1);
+                       }
+                       ret = pkgmgrinfo_appinfo_get_list(handle, PMSVC_UI_APP, __app_list_cb, NULL);
+                       if (ret < 0) {
+                               DBG("pkgmgrinfo_appinfo_get_list() failed\n");
+                               pkgmgrinfo_pkginfo_destroy_pkginfo(handle);
+                               exit(1);
+                       }
+                       ret = pkgmgrinfo_appinfo_get_list(handle, PMSVC_SVC_APP, __app_list_cb, NULL);
+                       if (ret < 0) {
+                               DBG("pkgmgrinfo_appinfo_get_list() failed\n");
+                               pkgmgrinfo_pkginfo_destroy_pkginfo(handle);
+                               exit(1);
+                       }
+
+                       pkgmgrinfo_pkginfo_destroy_pkginfo(handle);
+
+                       _save_queue_status(item, "done");
+                       exit(0);
+                       break;
+
+               case -1:        /* error */
+                       fprintf(stderr, "Fail to execute fork()\n");
+                       exit(1);
+                       break;
+
+               default:        /* parent */
+                       DBG("parent exit\n");
+                       _save_queue_status(item, "done");
+                       break;
+               }
+               break;
+
+
        default:
                break;
        }
index b8d2de4..56c7be0 100755 (executable)
@@ -915,6 +915,28 @@ static int __process_request()
                break;
 
        case KILLAPP_REQ:
+               if (data.pkgid[0] == '\0') {
+                       printf("Please provide the arguments.\n");
+                       printf("use -h option to see usage\n");
+                       data.result = PKGCMD_ERR_ARGUMENT_INVALID;
+                       break;
+               }
+
+               pc = pkgmgr_client_new(PC_REQUEST);
+               if (pc == NULL) {
+                       printf("PkgMgr Client Creation Failed\n");
+                       data.result = PKGCMD_ERR_FATAL_ERROR;
+                       break;
+               }
+
+               ret = pkgmgr_client_request_service(PM_REQUEST_KILL_APP, NULL, pc, NULL, data.pkgid, NULL, NULL, NULL);
+               if (ret < 0){
+                       data.result = PKGCMD_ERR_FATAL_ERROR;
+                       break;
+               }
+               ret = data.result;
+               break;
+
        case CHECKAPP_REQ:
                if (data.pkg_type[0] == '\0' || data.pkgid[0] == '\0') {
                        printf("Please provide the arguments.\n");