2 * Copyright (c) 2021 Samsung Electronics Co., Ltd.
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
8 * http://www.apache.org/licenses/LICENSE-2.0
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.
17 #include "manager/pkginfo_manager.h"
19 #include <sys/types.h>
30 #include "pkgmgr_parser.h"
31 #include "pkgmgrinfo_private.h"
33 #include "client/pkginfo_client.hh"
34 #include "common/database/abstract_db_handler.hh"
35 #include "common/database/pkg_set_db_handler.hh"
36 #include "common/parcel/appinfo_parcelable.hh"
37 #include "common/parcel/certinfo_parcelable.hh"
38 #include "common/parcel/command_parcelable.hh"
39 #include "common/parcel/depinfo_parcelable.hh"
40 #include "common/parcel/filter_parcelable.hh"
41 #include "common/parcel/pkginfo_parcelable.hh"
42 #include "common/parcel/query_parcelable.hh"
43 #include "common/parcel/result_parcelable.hh"
50 #define LOG_TAG "PKGMGR_INFO"
55 #define EXPORT_API __attribute__((visibility("default")))
57 namespace pcp = pkgmgr_common::parcel;
58 namespace pcd = pkgmgr_common::database;
60 extern "C" EXPORT_API int _pkginfo_get_packages(uid_t uid,
61 pkgmgrinfo_filter_x* filter, int flag, GHashTable* packages) {
62 std::shared_ptr<pcp::AbstractParcelable> parcelable(
63 new pcp::FilterParcelable(uid,
64 static_cast<pkgmgrinfo_filter_x*>(filter), flag, false));
66 pkgmgr_client::PkgInfoClient client(parcelable, uid,
67 pkgmgr_common::ReqType::GET_PKG_INFO);
68 if (!client.SendRequest())
69 return PMINFO_R_ERROR;
71 auto ptr = client.GetResultParcel();
73 LOG(ERROR) << "Fail to get return parcelable";
74 return PMINFO_R_ERROR;
77 if (ptr->GetRequestResult() != PMINFO_R_OK) {
78 if (ptr->GetRequestResult() == PMINFO_R_ERROR)
79 LOG(ERROR) << "Request fail";
80 return ptr->GetRequestResult();
83 if (ptr->GetType() != pcp::ParcelableType::PkgInfo) {
84 LOG(ERROR) << "Invalid parcelable type";
85 return PMINFO_R_ERROR;
88 std::shared_ptr<pcp::PkgInfoParcelable> return_parcel(
89 std::static_pointer_cast<pcp::PkgInfoParcelable>(
92 auto result_list = return_parcel->ExtractPkgInfo();
93 if (result_list.size() == 0) {
94 LOG(DEBUG) << "No packages meets given condition for user " << uid;
95 return PMINFO_R_ENOENT;
97 for (auto &pkginfo : result_list)
98 g_hash_table_insert(packages, (gpointer)pkginfo->package,
104 extern "C" EXPORT_API int _pkginfo_get_depends_on(uid_t uid,
105 const char* pkgid, GList** dependencies) {
106 std::shared_ptr<pcp::AbstractParcelable> parcelable(
107 new pcp::DepInfoParcelable(std::string(pkgid)));
109 pkgmgr_client::PkgInfoClient client(parcelable, uid,
110 pkgmgr_common::ReqType::GET_PKG_DEP_INFO);
111 if (!client.SendRequest())
112 return PMINFO_R_ERROR;
114 auto ptr = client.GetResultParcel();
115 if (ptr == nullptr) {
116 LOG(ERROR) << "Fail to get return parcelable";
117 return PMINFO_R_ERROR;
120 if (ptr->GetRequestResult() != PMINFO_R_OK) {
121 LOG(ERROR) << "Request fail";
122 return ptr->GetRequestResult();
125 if (ptr->GetType() != pcp::ParcelableType::DepInfo) {
126 LOG(ERROR) << "Invalid parcelable type";
127 return PMINFO_R_ERROR;
130 std::shared_ptr<pcp::DepInfoParcelable> return_parcel(
131 std::static_pointer_cast<pcp::DepInfoParcelable>(ptr));
133 auto dependency_list = return_parcel->ExtractDependencyInfo();
134 for (auto &dependency : dependency_list)
135 *dependencies = g_list_prepend(*dependencies, dependency);
139 // TODO: Need to add target db uid to identify which database to be searched
140 extern "C" EXPORT_API int _appinfo_get_applications(uid_t db_uid, uid_t uid,
141 pkgmgrinfo_filter_x* filter, int flag, GHashTable* packages) {
142 std::shared_ptr<pcp::AbstractParcelable> parcelable(
143 new pcp::FilterParcelable(uid,
144 static_cast<pkgmgrinfo_filter_x*>(filter), flag, false));
146 pkgmgr_client::PkgInfoClient client(
147 parcelable, uid, pkgmgr_common::ReqType::GET_APP_INFO);
148 if (!client.SendRequest())
149 return PMINFO_R_ERROR;
151 auto ptr = client.GetResultParcel();
152 if (ptr == nullptr) {
153 LOG(ERROR) << "Fail to get return parcelable";
154 return PMINFO_R_ERROR;
157 int ret = ptr->GetRequestResult();
158 if (ret != PMINFO_R_OK) {
159 if (ret == PMINFO_R_ENOENT)
160 LOG(DEBUG) << "No such application";
162 LOG(ERROR) << "Request fail";
166 if (ptr->GetType() != pcp::ParcelableType::AppInfo) {
167 LOG(ERROR) << "Invalid parcelable type";
168 return PMINFO_R_ERROR;
171 std::shared_ptr<pcp::AppInfoParcelable> return_parcel(
172 std::static_pointer_cast<pcp::AppInfoParcelable>(ptr));
174 std::vector<application_x*> result_list = return_parcel->ExtractAppInfo();
175 for (application_x* app : result_list)
176 g_hash_table_insert(packages, (gpointer)app->appid,
182 extern "C" EXPORT_API char* _appinfo_get_localed_label(
183 const char* appid, const char* locale, uid_t uid) {
184 char* query = nullptr;
185 query = sqlite3_mprintf(
186 "SELECT COALESCE((SELECT app_label FROM package_app_localized_info "
187 "WHERE app_id=%Q AND app_locale=%Q),"
188 "(SELECT app_label FROM package_app_localized_info WHERE "
189 "app_id=%Q AND app_locale='No Locale'))",
190 appid, locale, appid);
191 if (query == nullptr) {
192 LOG(ERROR) << "Out of memory";
196 std::shared_ptr<pcp::AbstractParcelable> parcelable(
197 new pcp::QueryParcelable(uid, std::string(query),
198 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
199 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
202 pkgmgr_client::PkgInfoClient client(parcelable, uid,
203 pkgmgr_common::ReqType::QUERY);
204 if (!client.SendRequest())
206 auto ptr = client.GetResultParcel();
207 if (ptr == nullptr) {
208 LOG(ERROR) << "Fail to get return parcelable";
212 if (ptr->GetRequestResult() != PMINFO_R_OK) {
213 LOG(ERROR) << "Request fail";
217 if (ptr->GetType() != pcp::ParcelableType::Result) {
218 LOG(ERROR) << "Invalid parcelable type";
222 std::shared_ptr<pcp::ResultParcelable> return_parcel(
223 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
225 // result_list is vector of string vector
226 char* label = nullptr;
227 auto result_list = return_parcel->GetResult();
228 for (auto result : result_list) {
229 // result is string vector
230 // it only has one string or not.
231 if (result.front().empty() || result.front().length() == 0)
233 label = strdup(result.front().c_str());
234 if (label == nullptr) {
235 LOG(ERROR) << "Out of memory";
244 extern "C" EXPORT_API int _appinfo_get_datacontrol_info(
245 const char* providerid, const char* type, uid_t uid,
246 char** appid, char** access) {
247 char* query = nullptr;
248 query = sqlite3_mprintf("SELECT app_id, access FROM "
249 "package_app_data_control WHERE "
250 "providerid=%Q AND type=%Q",
252 if (query == nullptr) {
253 LOG(ERROR) << "Out of memory";
254 return PMINFO_R_ERROR;
257 std::shared_ptr<pcp::AbstractParcelable> parcelable(
258 new pcp::QueryParcelable(uid, std::string(query),
259 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
260 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
263 pkgmgr_client::PkgInfoClient client(parcelable, uid,
264 pkgmgr_common::ReqType::QUERY);
265 if (!client.SendRequest())
266 return PMINFO_R_ERROR;
268 auto ptr = client.GetResultParcel();
269 if (ptr == nullptr) {
270 LOG(ERROR) << "Fail to get return parcelable";
271 return PMINFO_R_ERROR;
274 if (ptr->GetRequestResult() != PMINFO_R_OK) {
275 LOG(ERROR) << "Request fail";
276 return ptr->GetRequestResult();
279 if (ptr->GetType() != pcp::ParcelableType::Result) {
280 LOG(ERROR) << "Invalid parcelable type";
281 return PMINFO_R_ERROR;
284 std::shared_ptr<pcp::ResultParcelable> return_parcel(
285 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
287 auto result_list = return_parcel->GetResult();
288 if (result_list.size() == 0)
289 return PMINFO_R_ENOENT;
290 for (auto result : result_list) {
291 if (result.size() != 2)
292 return PMINFO_R_ERROR;
293 if (result.front().empty() || result.front().size() == 0 ||
294 result.back().empty() || result.back().size() == 0)
295 return PMINFO_R_ERROR;
296 *appid = strdup(result.front().c_str());
297 *access = strdup(result.back().c_str());
298 if (*appid == nullptr || *access == nullptr) {
299 LOG(ERROR) << "Out of memory";
300 return PMINFO_R_ERROR;
307 extern "C" EXPORT_API int _appinfo_get_datacontrol_appid(
308 const char* providerid, uid_t uid, char** appid) {
309 char* query = nullptr;
311 query = sqlite3_mprintf("SELECT app_id FROM package_app_data_control "
312 "WHERE providerid=%Q",
314 if (query == nullptr) {
315 LOGE("Out of memory");
316 return PMINFO_R_ERROR;
318 std::shared_ptr<pcp::AbstractParcelable> parcelable(
319 new pcp::QueryParcelable(uid, std::string(query),
320 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
321 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
324 pkgmgr_client::PkgInfoClient client(parcelable, uid,
325 pkgmgr_common::ReqType::QUERY);
326 if (!client.SendRequest())
327 return PMINFO_R_ERROR;
329 auto ptr = client.GetResultParcel();
330 if (ptr == nullptr) {
331 LOG(ERROR) << "Fail to get return parcelable";
332 return PMINFO_R_ERROR;
335 if (ptr->GetRequestResult() != PMINFO_R_OK) {
336 LOG(ERROR) << "Request fail";
337 return ptr->GetRequestResult();
340 if (ptr->GetType() != pcp::ParcelableType::Result) {
341 LOG(ERROR) << "Invalid parcelable type";
342 return PMINFO_R_ERROR;
345 std::shared_ptr<pcp::ResultParcelable> return_parcel(
346 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
348 // result_list is vector of string vector
349 auto result_list = return_parcel->GetResult();
350 if (result_list.size() == 0)
351 return PMINFO_R_ENOENT;
352 for (auto result : result_list) {
353 if (result.size() != 1)
354 return PMINFO_R_ERROR;
355 if (result.front().empty() || result.front().size() == 0)
356 return PMINFO_R_ERROR;
357 *appid = strdup(result.front().c_str());
358 if (*appid == nullptr) {
359 LOG(ERROR) << "Out of memory";
360 return PMINFO_R_ERROR;
367 extern "C" EXPORT_API int _appinfo_get_datacontrol_trusted_info(
368 const char* providerid, const char* type, uid_t uid,
369 char** appid, char** trusted) {
370 char* query = nullptr;
371 query = sqlite3_mprintf(
372 "SELECT app_id, trusted FROM package_app_data_control "
373 "WHERE providerid=%Q AND type=%Q",
375 if (query == nullptr) {
376 LOGE("Out of memory");
377 return PMINFO_R_ERROR;
380 std::shared_ptr<pcp::AbstractParcelable> parcelable(
381 new pcp::QueryParcelable(uid, std::string(query),
382 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
383 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
386 pkgmgr_client::PkgInfoClient client(parcelable, uid,
387 pkgmgr_common::ReqType::QUERY);
388 if (!client.SendRequest())
389 return PMINFO_R_ERROR;
391 auto ptr = client.GetResultParcel();
392 if (ptr == nullptr) {
393 LOG(ERROR) << "Fail to get return parcelable";
394 return PMINFO_R_ERROR;
397 if (ptr->GetRequestResult() != PMINFO_R_OK) {
398 LOG(ERROR) << "Request fail";
399 return ptr->GetRequestResult();
402 if (ptr->GetType() != pcp::ParcelableType::Result) {
403 LOG(ERROR) << "Invalid parcelable type";
404 return PMINFO_R_ERROR;
407 std::shared_ptr<pcp::ResultParcelable> return_parcel(
408 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
410 // result_list is vector of string vector
411 auto result_list = return_parcel->GetResult();
412 if (result_list.size() == 0)
413 return PMINFO_R_ENOENT;
414 for (auto result : result_list) {
415 if (result.size() != 2)
416 return PMINFO_R_ERROR;
417 if (result.front().empty() || result.front().size() == 0 ||
418 result.back().empty() || result.back().size() == 0)
419 return PMINFO_R_ERROR;
420 *appid = strdup(result.front().c_str());
421 *trusted = strdup(result.back().c_str());
422 if (*appid == nullptr || *trusted == nullptr) {
423 LOG(ERROR) << "Out of memory";
424 return PMINFO_R_ERROR;
431 extern "C" EXPORT_API int _appinfo_get_datacontrol_privileges(
432 const char* providerid, const char* type, uid_t uid, GList** privileges) {
433 char* query = nullptr;
434 query = sqlite3_mprintf(
435 "SELECT privilege FROM package_app_data_control_privilege "
436 "WHERE providerid=%Q AND type=%Q",
438 if (query == nullptr) {
439 LOGE("Out of memory");
440 return PMINFO_R_ERROR;
443 std::shared_ptr<pcp::AbstractParcelable> parcelable(
444 new pcp::QueryParcelable(uid, std::string(query),
445 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
446 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
449 pkgmgr_client::PkgInfoClient client(parcelable, uid,
450 pkgmgr_common::ReqType::QUERY);
451 if (!client.SendRequest())
452 return PMINFO_R_ERROR;
454 auto ptr = client.GetResultParcel();
455 if (ptr == nullptr) {
456 LOG(ERROR) << "Fail to get return parcelable";
457 return PMINFO_R_ERROR;
460 if (ptr->GetRequestResult() != PMINFO_R_OK) {
461 LOG(ERROR) << "Request fail";
462 return ptr->GetRequestResult();
465 if (ptr->GetType() != pcp::ParcelableType::Result) {
466 LOG(ERROR) << "Invalid parcelable type";
467 return PMINFO_R_ERROR;
470 std::shared_ptr<pcp::ResultParcelable> return_parcel(
471 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
473 // result_list is vector of string vector
474 auto result_list = return_parcel->GetResult();
475 if (result_list.size() == 0)
476 return PMINFO_R_ENOENT;
478 for (auto result : result_list) {
479 if (result.size() != 1)
480 return PMINFO_R_ERROR;
481 if (result.front().empty() || result.front().size() == 0)
482 return PMINFO_R_ERROR;
483 char* privilege = strdup(result.front().c_str());
484 if (privilege == nullptr) {
485 LOG(ERROR) << "Out of memory";
486 return PMINFO_R_ERROR;
488 *privileges = g_list_append(*privileges, privilege);
494 extern "C" EXPORT_API int _appinfo_get_appcontrol_privileges(
495 const char* appid, const char* operation, uid_t uid, GList** privileges) {
496 char* query = nullptr;
497 query = sqlite3_mprintf(
498 "SELECT app_control, privilege FROM package_app_app_control_privilege "
499 "WHERE app_id=%Q", appid);
500 if (query == nullptr) {
501 LOG(ERROR) << "Out of memory";
502 return PMINFO_R_ERROR;
505 std::shared_ptr<pcp::AbstractParcelable> parcelable(
506 new pcp::QueryParcelable(uid, std::string(query),
507 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
508 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
511 pkgmgr_client::PkgInfoClient client(parcelable, uid,
512 pkgmgr_common::ReqType::QUERY);
513 if (!client.SendRequest())
514 return PMINFO_R_ERROR;
516 auto ptr = client.GetResultParcel();
517 if (ptr == nullptr) {
518 LOG(ERROR) << "Fail to get return parcelable";
519 return PMINFO_R_ERROR;
522 if (ptr->GetRequestResult() != PMINFO_R_OK) {
523 LOG(ERROR) << "Request fail";
524 return ptr->GetRequestResult();
527 if (ptr->GetType() != pcp::ParcelableType::Result) {
528 LOG(ERROR) << "Invalid parcelable type";
529 return PMINFO_R_ERROR;
532 std::shared_ptr<pcp::ResultParcelable> return_parcel(
533 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
535 // result_list is vector of string vector
536 auto result_list = return_parcel->GetResult();
537 if (result_list.size() == 0)
538 return PMINFO_R_ENOENT;
540 for (auto result : result_list) {
541 if (result.size() != 2)
542 return PMINFO_R_ERROR;
543 if (result.front().empty() || result.front().size() == 0 ||
544 result.back().empty() || result.back().size() == 0)
545 return PMINFO_R_ERROR;
546 std::string app_control = result.front();
547 std::stringstream ss(app_control);
549 while (std::getline(ss, token, '|')) {
550 if (token.compare(std::string(operation))) {
551 char* privilege = strdup(result.back().c_str());
552 if (privilege == nullptr) {
553 LOG(ERROR) << "Out of memory";
554 return PMINFO_R_ERROR;
556 *privileges = g_list_append(*privileges, privilege);
563 extern "C" EXPORT_API int _plugininfo_get_appids(
564 const char* pkgid, const char* plugin_type,
565 const char* plugin_name, GList** list) {
566 if (!pkgid || !plugin_type || !plugin_name || !list) {
567 LOG(ERROR) << "Invalid parameter";
568 return PMINFO_R_EINVAL;
571 char* query = nullptr;
572 query = sqlite3_mprintf(
574 "package_plugin_info WHERE pkgid=%Q AND "
575 "plugin_type=%Q AND plugin_name=%Q",
576 pkgid, plugin_type, plugin_name);
577 if (query == nullptr) {
578 LOG(ERROR) << "Out of memory";
579 return PMINFO_R_ERROR;
582 std::shared_ptr<pcp::AbstractParcelable> parcelable(
583 new pcp::QueryParcelable(_getuid(), std::string(query),
584 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
585 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
588 pkgmgr_client::PkgInfoClient client(parcelable, _getuid(),
589 pkgmgr_common::ReqType::QUERY);
590 if (!client.SendRequest())
591 return PMINFO_R_ERROR;
593 auto ptr = client.GetResultParcel();
594 if (ptr == nullptr) {
595 LOG(ERROR) << "Fail to get return parcelable";
596 return PMINFO_R_ERROR;
599 if (ptr->GetRequestResult() != PMINFO_R_OK) {
600 LOG(ERROR) << "Request fail";
601 return ptr->GetRequestResult();
604 if (ptr->GetType() != pcp::ParcelableType::Result) {
605 LOG(ERROR) << "Invalid parcelable type";
606 return PMINFO_R_ERROR;
609 std::shared_ptr<pcp::ResultParcelable> return_parcel(
610 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
612 if (return_parcel->GetCol() != 1) {
613 LOG(ERROR) << "Invalid result";
614 return PMINFO_R_ERROR;
616 // result_list is vector of string vector
617 auto &result_list = return_parcel->GetResult();
618 if (result_list.size() == 0)
619 return PMINFO_R_ENOENT;
621 for (auto result : result_list) {
622 if (result.size() != 1) {
623 LOG(ERROR) << "Invalid result";
624 g_list_free_full(*list, free);
625 return PMINFO_R_ERROR;
627 *list = g_list_append(*list, strdup(result[0].c_str()));
633 static int __convert_update_type(const char* type,
634 pkgmgrinfo_updateinfo_update_type* convert_type) {
635 if (strncasecmp(type, PMINFO_UPDATEINFO_TYPE_NONE,
636 strlen(PMINFO_UPDATEINFO_TYPE_NONE)) == 0)
637 *convert_type = PMINFO_UPDATEINFO_NONE;
638 else if (strncasecmp(type, PMINFO_UPDATEINFO_TYPE_FORCE,
639 strlen(PMINFO_UPDATEINFO_TYPE_FORCE)) == 0)
640 *convert_type = PMINFO_UPDATEINFO_FORCE;
641 else if (strncasecmp(type, PMINFO_UPDATEINFO_TYPE_OPTIONAL,
642 strlen(PMINFO_UPDATEINFO_TYPE_OPTIONAL)) == 0)
643 *convert_type = PMINFO_UPDATEINFO_OPTIONAL;
649 static void __free_update_info(gpointer data) {
650 updateinfo_x* update_info = reinterpret_cast<updateinfo_x*>(data);
651 if (update_info == nullptr)
654 if (update_info->pkgid)
655 free(reinterpret_cast<void*>(update_info->pkgid));
656 if (update_info->version)
657 free(reinterpret_cast<void*>(update_info->version));
658 free(reinterpret_cast<void*>(update_info));
661 extern "C" EXPORT_API int _get_pkg_updateinfo(const char* pkgid,
662 GSList** update_info_list, uid_t uid) {
663 char* query = nullptr;
666 if (pkgid == nullptr)
667 query = sqlite3_mprintf(
668 "SELECT package, update_version, update_type "
669 "FROM package_update_info");
671 query = sqlite3_mprintf(
672 "SELECT package, update_version, update_type "
673 "FROM package_update_info WHERE package=%Q",
675 if (query == nullptr) {
676 LOG(ERROR) << "Out of memory";
677 return PMINFO_R_ERROR;
680 std::shared_ptr<pcp::AbstractParcelable> parcelable(
681 new pcp::QueryParcelable(uid, std::string(query),
682 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
683 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
686 pkgmgr_client::PkgInfoClient client(parcelable, uid,
687 pkgmgr_common::ReqType::QUERY);
688 if (!client.SendRequest())
689 return PMINFO_R_ERROR;
691 auto ptr = client.GetResultParcel();
692 if (ptr == nullptr) {
693 LOG(ERROR) << "Fail to get return parcelable";
694 return PMINFO_R_ERROR;
697 if (ptr->GetRequestResult() != PMINFO_R_OK) {
698 LOG(ERROR) << "Request fail";
699 return ptr->GetRequestResult();
702 if (ptr->GetType() != pcp::ParcelableType::Result) {
703 LOG(ERROR) << "Invalid parcelable type";
704 return PMINFO_R_ERROR;
707 std::shared_ptr<pcp::ResultParcelable> return_parcel(
708 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
710 if (return_parcel->GetCol() != 3) {
711 LOG(ERROR) << "Invalid result";
712 return PMINFO_R_ERROR;
715 auto result_list = return_parcel->GetResult();
716 if (result_list.size() == 0)
717 return PMINFO_R_ENOENT;
719 for (auto result : result_list) {
720 if (result.size() != 3) {
721 LOG(ERROR) << "Invalid result";
722 g_slist_free_full(*update_info_list, __free_update_info);
723 return PMINFO_R_ERROR;
725 updateinfo_x* update_info = reinterpret_cast<updateinfo_x*>(
726 calloc(1, sizeof(updateinfo_x)));
727 if (update_info == nullptr) {
728 LOG(ERROR) << "Out of memory";
729 return PMINFO_R_ERROR;
731 update_info->pkgid = strdup(result[0].c_str());
732 update_info->version = strdup(result[1].c_str());
733 pkgmgrinfo_updateinfo_update_type convert_type;
734 ret = __convert_update_type(result[2].c_str(), &convert_type);
736 __free_update_info(update_info);
737 g_slist_free_full(*update_info_list, __free_update_info);
738 return PMINFO_R_ERROR;
740 update_info->type = static_cast<int>(convert_type);
741 *update_info_list = g_slist_prepend(*update_info_list,
748 extern "C" EXPORT_API int _pkginfo_set_usr_installed_storage(const char* pkgid,
749 INSTALL_LOCATION location, const char* external_pkg_path, uid_t uid) {
750 char* query = nullptr;
751 const char* location_str;
752 std::vector<std::string> queries;
754 if (location == INSTALL_INTERNAL)
755 location_str = "installed_internal";
756 else if (location == INSTALL_EXTERNAL)
757 location_str = "installed_external";
759 location_str = "installed_extended";
760 /* pkgcakge_info table */
761 query = sqlite3_mprintf(
762 "UPDATE package_info SET installed_storage=%Q, external_path=%Q "
764 location_str, external_pkg_path, pkgid);
765 queries.emplace_back(query);
768 /* package_app_info table */
769 query = sqlite3_mprintf(
770 "UPDATE package_app_info SET app_installed_storage=%Q, "
771 "app_external_path=%Q WHERE package=%Q",
772 location_str, external_pkg_path, pkgid);
773 queries.emplace_back(query);
776 std::shared_ptr<pcp::AbstractParcelable> parcelable(
777 new pcp::QueryParcelable(uid, queries,
778 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
779 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_WRITE));
781 pkgmgr_client::PkgInfoClient client(parcelable, uid,
782 pkgmgr_common::ReqType::QUERY);
783 if (!client.SendRequest())
784 return PMINFO_R_ERROR;
786 auto ptr = client.GetResultParcel();
787 if (ptr == nullptr) {
788 LOG(ERROR) << "Fail to get return parcelable";
789 return PMINFO_R_ERROR;
792 if (ptr->GetRequestResult() != PMINFO_R_OK) {
793 LOG(ERROR) << "Request fail";
794 return ptr->GetRequestResult();
797 if (ptr->GetType() != pcp::ParcelableType::Result) {
798 LOG(ERROR) << "Invalid parcelable type";
799 return PMINFO_R_ERROR;
805 extern "C" EXPORT_API int _certinfo_compare_pkg_certinfo(const char* l_pkgid,
806 const char* r_pkgid, pkgmgrinfo_cert_compare_result_type_e* result) {
807 char* query = sqlite3_mprintf("SELECT package, "
808 "COALESCE(author_signer_cert, -1) FROM package_cert_info WHERE "
809 "package IN (%Q, %Q)",
811 if (query == nullptr) {
812 LOG(ERROR) << "Out of memory";
813 return PMINFO_R_ERROR;
815 std::vector<std::string> queries;
816 queries.emplace_back(query);
819 std::shared_ptr<pcp::AbstractParcelable> parcelable(
820 new pcp::QueryParcelable(0, queries,
821 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_CERTDB,
822 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
823 pkgmgr_client::PkgInfoClient client(parcelable, 0,
824 pkgmgr_common::ReqType::QUERY);
825 if (!client.SendRequest())
826 return PMINFO_R_ERROR;
828 auto ptr = client.GetResultParcel();
829 if (ptr == nullptr) {
830 LOG(ERROR) << "Fail to get return parcelable";
831 return PMINFO_R_ERROR;
834 if (ptr->GetRequestResult() != PMINFO_R_OK) {
835 LOG(ERROR) << "Request fail";
836 return ptr->GetRequestResult();
839 if (ptr->GetType() != pcp::ParcelableType::Result) {
840 LOG(ERROR) << "Invalid parcelable type";
841 return PMINFO_R_ERROR;
844 std::shared_ptr<pcp::ResultParcelable> return_parcel(
845 std::static_pointer_cast<pcp::ResultParcelable>(
848 auto certinfo_list = return_parcel->GetResult();
849 if (certinfo_list.size() != 2)
850 return PMINFO_R_ERROR;
852 std::map<std::string, std::string> result_map;
853 for (auto &certinfo : certinfo_list)
854 result_map.insert(make_pair(certinfo.front(), certinfo.back()));
856 if (result_map.find(std::string(l_pkgid))->second == "-1" &&
857 result_map.find(std::string(r_pkgid))->second == "-1")
858 *result = PMINFO_CERT_COMPARE_BOTH_NO_CERT;
859 else if (result_map.find(std::string(l_pkgid))->second == "-1")
860 *result = PMINFO_CERT_COMPARE_LHS_NO_CERT;
861 else if (result_map.find(std::string(r_pkgid))->second == "-1")
862 *result = PMINFO_CERT_COMPARE_RHS_NO_CERT;
863 else if (result_map.find(std::string(l_pkgid))->second ==
864 result_map.find(std::string(r_pkgid))->second)
865 *result = PMINFO_CERT_COMPARE_MATCH;
867 *result = PMINFO_CERT_COMPARE_MISMATCH;
872 extern "C" EXPORT_API int _certinfo_compare_app_certinfo(uid_t uid,
873 const char* l_appid, const char* r_appid,
874 pkgmgrinfo_cert_compare_result_type_e* result) {
875 char* query = sqlite3_mprintf("SELECT app_id, package FROM "
876 "package_app_info WHERE app_id IN (%Q, %Q)",
878 if (query == nullptr) {
879 LOG(ERROR) << "Out of memory";
880 return PMINFO_R_ERROR;
882 std::vector<std::string> queries;
883 queries.emplace_back(query);
886 std::shared_ptr<pcp::AbstractParcelable> parcelable(
887 new pcp::QueryParcelable(uid, queries,
888 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
889 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_READ));
890 pkgmgr_client::PkgInfoClient client(parcelable, uid,
891 pkgmgr_common::ReqType::QUERY);
892 if (!client.SendRequest())
893 return PMINFO_R_ERROR;
895 auto ptr = client.GetResultParcel();
896 if (ptr == nullptr) {
897 LOG(ERROR) << "Fail to get return parcelable";
898 return PMINFO_R_ERROR;
901 if (ptr->GetRequestResult() != PMINFO_R_OK) {
902 LOG(ERROR) << "Request fail";
903 return ptr->GetRequestResult();
906 if (ptr->GetType() != pcp::ParcelableType::Result) {
907 LOG(ERROR) << "Invalid parcelable type";
908 return PMINFO_R_ERROR;
911 std::shared_ptr<pcp::ResultParcelable> return_parcel(
912 std::static_pointer_cast<pcp::ResultParcelable>(ptr));
914 auto pkgid_list = return_parcel->GetResult();
915 std::map<std::string, std::string> result_map;
916 for (auto &pkgid : pkgid_list)
917 result_map.insert(make_pair(pkgid.front(), pkgid.back()));
919 if (result_map.find(std::string(l_appid)) == result_map.end()) {
920 LOG(ERROR) << "Cannot find pkgid of app " << l_appid
921 << " for uid " << uid;
922 return PMINFO_R_ENOENT;
923 } else if (result_map.find(std::string(r_appid)) == result_map.end()) {
924 LOG(ERROR) << "Cannot find pkgid of app " << r_appid
925 << " for uid " << uid;
926 return PMINFO_R_ENOENT;
929 const char* l_pkgid = result_map.find(std::string(l_appid))->second.c_str();
930 const char* r_pkgid = result_map.find(std::string(r_appid))->second.c_str();
932 return _certinfo_compare_pkg_certinfo(l_pkgid, r_pkgid, result);
935 extern "C" EXPORT_API int _parser_execute_write_query(
936 const char* query, uid_t uid) {
937 std::shared_ptr<pcp::AbstractParcelable> parcelable(
938 new pcp::QueryParcelable(uid, query,
939 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
940 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_WRITE));
942 pkgmgr_client::PkgInfoClient client(parcelable, uid,
943 pkgmgr_common::ReqType::QUERY);
944 if (!client.SendRequest())
947 auto ptr = client.GetResultParcel();
948 if (ptr == nullptr) {
949 LOG(ERROR) << "Fail to get return parcelable";
953 if (ptr->GetRequestResult() != PMINFO_R_OK) {
954 LOG(ERROR) << "Request fail";
958 if (ptr->GetType() != pcp::ParcelableType::Result) {
959 LOG(ERROR) << "Invalid parcelable type";
966 extern "C" EXPORT_API int _parser_execute_write_queries(
967 const char** queries, int len, uid_t uid) {
968 std::vector<std::string> query_vt;
969 for (int i = 0; i < len; ++i)
970 query_vt.emplace_back(queries[i]);
972 std::shared_ptr<pcp::AbstractParcelable> parcelable(
973 new pcp::QueryParcelable(uid, query_vt,
974 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_PKGDB,
975 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_WRITE));
977 pkgmgr_client::PkgInfoClient client(parcelable, uid,
978 pkgmgr_common::ReqType::QUERY);
979 if (!client.SendRequest())
982 auto ptr = client.GetResultParcel();
983 if (ptr == nullptr) {
984 LOG(ERROR) << "Fail to get return parcelable";
988 if (ptr->GetRequestResult() != PMINFO_R_OK) {
989 LOG(ERROR) << "Request fail";
993 if (ptr->GetType() != pcp::ParcelableType::Result) {
994 LOG(ERROR) << "Invalid parcelable type";
1001 extern "C" EXPORT_API int _parser_insert_manifest_info(
1002 manifest_x* mfx, uid_t uid) {
1004 std::make_shared<pcp::PkgInfoParcelable>(uid,
1005 std::vector<package_x*>{mfx}, WriteType::Insert, false);
1007 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1008 pkgmgr_common::ReqType::SET_PKG_INFO);
1009 if (!client.SendRequest())
1012 auto ptr = client.GetResultParcel();
1013 if (ptr == nullptr) {
1014 LOG(ERROR) << "Fail to get return parcelable";
1018 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1019 LOG(ERROR) << "Request fail";
1023 if (ptr->GetType() != pcp::ParcelableType::Result) {
1024 LOG(ERROR) << "Invalid parcelable type";
1031 extern "C" EXPORT_API int _parser_update_manifest_info(
1032 manifest_x* mfx, uid_t uid) {
1034 std::make_shared<pcp::PkgInfoParcelable>(uid,
1035 std::vector<package_x*>{mfx}, WriteType::Update, false);
1037 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1038 pkgmgr_common::ReqType::SET_PKG_INFO);
1039 if (!client.SendRequest())
1042 auto ptr = client.GetResultParcel();
1043 if (ptr == nullptr) {
1044 LOG(ERROR) << "Fail to get return parcelable";
1048 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1049 LOG(ERROR) << "Request fail";
1053 if (ptr->GetType() != pcp::ParcelableType::Result) {
1054 LOG(ERROR) << "Invalid parcelable type";
1061 extern "C" EXPORT_API int _parser_delete_manifest_info(
1062 manifest_x* mfx, uid_t uid) {
1064 std::make_shared<pcp::PkgInfoParcelable>(uid,
1065 std::vector<package_x*>{mfx}, WriteType::Delete, false);
1067 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1068 pkgmgr_common::ReqType::SET_PKG_INFO);
1069 if (!client.SendRequest())
1072 auto ptr = client.GetResultParcel();
1073 if (ptr == nullptr) {
1074 LOG(ERROR) << "Fail to get return parcelable";
1078 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1079 LOG(ERROR) << "Request fail";
1083 if (ptr->GetType() != pcp::ParcelableType::Result) {
1084 LOG(ERROR) << "Invalid parcelable type";
1091 extern "C" EXPORT_API int _pkginfo_insert_certinfo(const char* pkgid,
1092 pkgmgr_certinfo_x* cert, uid_t uid) {
1093 std::shared_ptr<pcp::AbstractParcelable> parcelable(
1094 new pcp::CertInfoParcelable(uid, cert, false));
1095 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1096 pkgmgr_common::ReqType::SET_CERT_INFO);
1098 if (!client.SendRequest())
1099 return PMINFO_R_ERROR;
1101 auto ptr = client.GetResultParcel();
1102 if (ptr == nullptr) {
1103 LOG(ERROR) << "Fail to get return parcelable";
1104 return PMINFO_R_ERROR;
1107 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1108 LOG(ERROR) << "Request fail";
1109 return ptr->GetRequestResult();
1112 if (ptr->GetType() != pcp::ParcelableType::Result) {
1113 LOG(ERROR) << "Invalid parcelable type";
1114 return PMINFO_R_ERROR;
1120 extern "C" EXPORT_API int _pkginfo_get_certinfo(const char* pkgid,
1121 pkgmgr_certinfo_x* cert, uid_t uid) {
1122 std::shared_ptr<pcp::AbstractParcelable> parcelable(
1123 new pcp::CertInfoParcelable(uid,
1124 std::string(pkgid)));
1126 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1127 pkgmgr_common::ReqType::GET_CERT_INFO);
1128 if (!client.SendRequest())
1129 return PMINFO_R_ERROR;
1131 auto ptr = client.GetResultParcel();
1132 if (ptr == nullptr) {
1133 LOG(ERROR) << "Fail to get return parcelable";
1134 return PMINFO_R_ERROR;
1137 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1138 LOG(ERROR) << "Request fail";
1139 return ptr->GetRequestResult();
1142 if (ptr->GetType() != pcp::ParcelableType::CertInfo) {
1143 LOG(ERROR) << "Invalid parcelable type";
1144 return PMINFO_R_ERROR;
1147 std::shared_ptr<pcp::CertInfoParcelable> return_parcel(
1148 std::static_pointer_cast<pcp::CertInfoParcelable>(ptr));
1150 pkgmgr_certinfo_x* certinfo = return_parcel->ExtractCertInfo();
1151 if (certinfo == nullptr)
1152 return PMINFO_R_ERROR;
1154 cert->for_all_users = certinfo->for_all_users;
1155 cert->pkgid = certinfo->pkgid;
1156 certinfo->pkgid = nullptr;
1157 cert->cert_value = certinfo->cert_value;
1158 certinfo->cert_value = nullptr;
1159 for (int i = 0; i < MAX_CERT_TYPE; i++) {
1160 cert->cert_info[i] = certinfo->cert_info[i];
1161 certinfo->cert_info[i] = nullptr;
1163 for (int i = 0; i < MAX_CERT_TYPE; i++)
1164 cert->cert_id[i] = certinfo->cert_id[i];
1171 extern "C" EXPORT_API int _pkginfo_delete_certinfo(const char* pkgid) {
1172 char* query = sqlite3_mprintf("UPDATE package_cert_info SET "
1173 "package_count = package_count - 1 WHERE package=%Q", pkgid);
1174 if (query == nullptr) {
1175 LOG(ERROR) << "Out of memory";
1176 return PMINFO_R_ERROR;
1179 std::vector<std::string> queries;
1180 queries.emplace_back(query);
1181 sqlite3_free(query);
1183 std::shared_ptr<pcp::AbstractParcelable> parcelable(
1184 new pcp::QueryParcelable(0, queries,
1185 pcd::AbstractDBHandler::DBType::DB_TYPE_FILE_CERTDB,
1186 pcd::AbstractDBHandler::OperationType::OPERATION_TYPE_WRITE));
1188 pkgmgr_client::PkgInfoClient client(parcelable, 0,
1189 pkgmgr_common::ReqType::QUERY);
1190 if (!client.SendRequest())
1191 return PMINFO_R_ERROR;
1193 auto ptr = client.GetResultParcel();
1194 if (ptr == nullptr) {
1195 LOG(ERROR) << "Fail to get return parcelable";
1196 return PMINFO_R_ERROR;
1199 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1200 LOG(ERROR) << "Request fail";
1201 return PMINFO_R_ERROR;
1204 if (ptr->GetType() != pcp::ParcelableType::Result) {
1205 LOG(ERROR) << "Invalid parcelable type";
1206 return PMINFO_R_ERROR;
1212 extern "C" EXPORT_API int _parser_clear_cache_memory_db(uid_t uid) {
1213 std::shared_ptr<pcp::AbstractParcelable> parcelable(
1214 new pcp::CommandParcelable(uid, CommandType::RemoveCache));
1216 pkgmgr_client::PkgInfoClient client(parcelable, uid,
1217 pkgmgr_common::ReqType::COMMAND);
1219 if (!client.SendRequest())
1220 return PMINFO_R_ERROR;
1222 auto ptr = client.GetResultParcel();
1223 if (ptr == nullptr) {
1224 LOG(ERROR) << "Fail to get return parcelable";
1225 return PMINFO_R_ERROR;
1228 if (ptr->GetRequestResult() != PMINFO_R_OK) {
1229 LOG(ERROR) << "Request fail";
1230 return PMINFO_R_ERROR;
1233 if (ptr->GetType() != pcp::ParcelableType::Result) {
1234 LOG(ERROR) << "Invalid parcelable type";
1235 return PMINFO_R_ERROR;