Change gcov installation path
[platform/core/api/package-manager.git] / src / package_manager_internal.c
1 /*
2  * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  * Licensed under the Apache License, Version 2.0 (the License);
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an AS IS BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include <stdio.h>
18 #include <stdlib.h>
19 #include <fcntl.h>
20 #include <sys/syscall.h>
21 #include <unistd.h>
22
23 #include <pkgmgr-info.h>
24 #include <tzplatform_config.h>
25 #include <cynara-client.h>
26 #include <cynara-session.h>
27
28 #include "package_info.h"
29 #include "package_manager.h"
30 #include "package_manager_internal.h"
31
32 #define MAX_SMACK_LABEL_LEN 255
33 #define gettid() syscall(SYS_gettid)
34
35 typedef struct _foreach_pkg_context_ {
36         package_manager_package_info_cb callback;
37         void *user_data;
38 } foreach_pkg_context_s;
39
40 int check_privilege(privilege_type type)
41 {
42         cynara *p_cynara;
43         int fd;
44         int ret;
45         char subject_label[MAX_SMACK_LABEL_LEN + 1] = { 0 };
46         char uid[10];
47         char *session;
48         const char *privilege;
49         unsigned long pid = getpid();
50         unsigned long tid = gettid();
51
52         if (pid == tid) {
53                 fd = open("/proc/self/attr/current", O_RDONLY);
54         } else {
55                 // Check current thread smack label.
56                 char path[256] = { 0 };
57                 pid = tid;
58                 snprintf(path, sizeof(path), "/proc/%lu/attr/current", tid);
59                 fd = open(path, O_RDONLY);
60         }
61         if (fd < 0) {
62                 LOGE("open failed: %d", errno);
63                 return PACKAGE_MANAGER_ERROR_IO_ERROR;
64         }
65
66         ret = read(fd, subject_label, MAX_SMACK_LABEL_LEN);
67         if (ret < 0) {
68                 LOGE("read failed: %d", errno);
69                 close(fd);
70                 return PACKAGE_MANAGER_ERROR_IO_ERROR;
71         }
72         close(fd);
73
74         ret = cynara_initialize(&p_cynara, NULL);
75         if (ret != CYNARA_API_SUCCESS) {
76                 LOGE("init cynara failed: %d", ret);
77                 return PACKAGE_MANAGER_ERROR_IO_ERROR;
78         }
79
80         snprintf(uid, 10, "%d", getuid());
81         session = cynara_session_from_pid(pid);
82
83         switch (type) {
84         case PRIVILEGE_PACKAGE_MANAGER_INFO:
85                 privilege = "http://tizen.org/privilege/packagemanager.info";
86                 break;
87         case PRIVILEGE_PACKAGE_MANAGER_ADMIN:
88                 privilege = "http://tizen.org/privilege/packagemanager.admin";
89                 break;
90         case PRIVILEGE_PACKAGE_MANAGER_CACHE:
91                 privilege =
92                         "http://tizen.org/privilege/packagemanager.clearcache";
93                 break;
94         default:
95                 privilege = NULL;
96                 break;
97         }
98
99         ret = cynara_check(p_cynara, subject_label, session, uid, privilege);
100
101         free(session);
102         cynara_finish(p_cynara);
103
104         if (ret != CYNARA_API_ACCESS_ALLOWED) {
105                 LOGE("cynara access check failed: %d", ret);
106                 return PACKAGE_MANAGER_ERROR_PERMISSION_DENIED;
107         }
108
109         return PACKAGE_MANAGER_ERROR_NONE;
110 }
111
112 static const char *package_manager_error_to_string(package_manager_error_e
113                                                    error)
114 {
115         switch (error) {
116         case PACKAGE_MANAGER_ERROR_NONE:
117                 return "NONE";
118         case PACKAGE_MANAGER_ERROR_INVALID_PARAMETER:
119                 return "INVALID_PARAMETER";
120         case PACKAGE_MANAGER_ERROR_OUT_OF_MEMORY:
121                 return "OUT_OF_MEMORY";
122         case PACKAGE_MANAGER_ERROR_IO_ERROR:
123                 return "IO_ERROR";
124         case PACKAGE_MANAGER_ERROR_NO_SUCH_PACKAGE:
125                 return "NO_SUCH_PACKAGE";
126         case PACKAGE_MANAGER_ERROR_PERMISSION_DENIED:
127                 return "PERMISSION_DENIED";
128         case PACKAGE_MANAGER_ERROR_SYSTEM_ERROR:
129                 return "SEVERE_SYSTEM_ERROR";
130         default:
131                 return "UNKNOWN";
132         }
133 }
134
135 int package_manager_error(package_manager_error_e error,
136                                  const char *function, const char *description)
137 {
138         if (description) {
139                 _LOGE("[%s] %s(0x%08x) : %s", function,
140                      package_manager_error_to_string(error), error,
141                      description);
142         } else {
143                 _LOGE("[%s] %s(0x%08x)", function,
144                      package_manager_error_to_string(error), error);
145         }
146
147         return error;
148 }
149
150 int package_info_get_package_info(const char *package, package_info_h *package_info)
151 {
152         return package_info_create(package, package_info);
153 }
154
155 static int package_info_foreach_package_info_cb(const pkgmgrinfo_pkginfo_h handle, void *user_data)
156 {
157         foreach_pkg_context_s *foreach_pkg_context = user_data;
158         package_info_h package_info = NULL;
159         bool r = false;
160         int ret;
161
162         if (handle == NULL || foreach_pkg_context == NULL) {
163                 package_manager_error(PACKAGE_MANAGER_ERROR_INVALID_PARAMETER, __FUNCTION__, NULL);
164                 return PMINFO_R_EINVAL;
165         }
166
167         ret = package_info_create_with_pkginfo(handle, &package_info);
168         if (ret != PACKAGE_MANAGER_ERROR_NONE)
169                 return package_manager_error(ret, __FUNCTION__, NULL);
170
171         r = foreach_pkg_context->callback(package_info, foreach_pkg_context->user_data);
172
173         package_info_destroy_handle(package_info);
174
175         return (r == true) ? PMINFO_R_OK : PMINFO_R_ERROR;
176 }
177
178 int package_info_foreach_package_info(package_manager_package_info_cb callback, void *user_data)
179 {
180         foreach_pkg_context_s foreach_pkg_context = {
181                 .callback = callback,
182                 .user_data = user_data,
183         };
184         int ret = 0;
185
186         if (callback == NULL)
187                 return package_manager_error(PACKAGE_MANAGER_ERROR_INVALID_PARAMETER, __FUNCTION__, NULL);
188
189         ret = pkgmgrinfo_pkginfo_get_list(package_info_foreach_package_info_cb, &foreach_pkg_context);
190
191         if (ret < 0)
192                 return PACKAGE_MANAGER_ERROR_NO_SUCH_PACKAGE;
193
194         return PACKAGE_MANAGER_ERROR_NONE;
195 }
196
197 int package_info_filter_foreach_package_info(pkgmgrinfo_pkginfo_filter_h handle, package_manager_package_info_cb callback, void *user_data)
198 {
199         foreach_pkg_context_s foreach_pkg_context = {
200                 .callback = callback,
201                 .user_data = user_data,
202         };
203         int ret;
204
205         if ((handle == NULL) || (callback == NULL))
206                 return package_manager_error(PACKAGE_MANAGER_ERROR_INVALID_PARAMETER, __FUNCTION__, NULL);
207
208         ret = pkgmgrinfo_pkginfo_filter_foreach_pkginfo(handle, package_info_foreach_package_info_cb, &foreach_pkg_context);
209
210         if (ret < 0)
211                 return PACKAGE_MANAGER_ERROR_IO_ERROR;
212
213         return PACKAGE_MANAGER_ERROR_NONE;
214 }
215