e0fe999def62a8681b6628c2e75e4a817ec5910a
[platform/core/appfw/app-installers.git] / src / common / step / mount / step_mount_unpacked.cc
1 // Copyright (c) 2016 Samsung Electronics Co., Ltd All Rights Reserved
2 // Use of this source code is governed by an apache-2.0 license that can be
3 // found in the LICENSE file.
4
5 #include "common/step/mount/step_mount_unpacked.h"
6
7 #include <boost/filesystem/operations.hpp>
8 #include <boost/filesystem/path.hpp>
9 #include <unistd.h>
10
11 #include <string>
12
13 #include "common/utils/paths.h"
14 #include "common/utils/file_util.h"
15 #include "common/tzip_interface.h"
16 #include "common/zip_interface.h"
17
18 namespace bf = boost::filesystem;
19 namespace bs = boost::system;
20
21 namespace {
22
23 const char kPackageUnpackDirPath[] = UNPACKDIR;
24
25 }  // namespace
26
27 namespace common_installer {
28 namespace mount {
29
30 Step::Status StepMountUnpacked::process() {
31   bf::path tmp_dir = GenerateTmpDir(kPackageUnpackDirPath);
32   context_->unpacked_dir_path.set(tmp_dir);
33   // write unpacked directory for recovery file
34   // to remove unpacked dir properly when recovery mode
35   if (context_->recovery_info.get().recovery_file) {
36     context_->recovery_info.get().recovery_file->set_unpacked_dir(tmp_dir);
37     context_->recovery_info.get().recovery_file->WriteAndCommitFileContent();
38   }
39
40   auto zip = CreateZipInterface(context_->unpacked_dir_path.get());
41   if (!zip->MountZip(context_->file_path.get())) {
42     LOG(ERROR) << "Failed to mount zip file: " << context_->file_path.get();
43     return Status::IMAGE_ERROR;
44   }
45   LOG(DEBUG) << "Zip mounted in unpacked_dir: "
46              << context_->unpacked_dir_path.get();
47   return Status::OK;
48 }
49
50 Step::Status StepMountUnpacked::undo() {
51   auto zip = CreateZipInterface(context_->unpacked_dir_path.get());
52   if (!zip->UnmountZip()) {
53     LOG(ERROR) << "Failed to unmount zip file: " << context_->file_path.get();
54     return Status::IMAGE_ERROR;
55   }
56
57   RemoveAll(context_->unpacked_dir_path.get());
58
59   if (context_->request_type.get() == RequestType::MountUpdate) {
60     bf::path mount_point = GetMountLocation(context_->GetPkgPath());
61     auto zip_final = CreateZipInterface(mount_point);
62     if (!zip_final->UnmountZip()) {
63       LOG(ERROR) << "Failed to unmount zip package after revoke";
64       return Status::APP_DIR_ERROR;
65     }
66   }
67   return Status::OK;
68 }
69
70 Step::Status StepMountUnpacked::precheck() {
71   if (context_->file_path.get().empty()) {
72     LOG(ERROR) << "file_path attribute is empty";
73     return Step::Status::INVALID_VALUE;
74   }
75   if (!bf::exists(context_->file_path.get())) {
76     LOG(ERROR) << "file_path ("
77                << context_->file_path.get()
78                << ") path does not exist";
79     return Step::Status::INVALID_VALUE;
80   }
81   if (context_->root_application_path.get().empty()) {
82     LOG(ERROR) << "root_application_path attribute is empty";
83     return Step::Status::INVALID_VALUE;
84   }
85   if (!bf::exists(context_->root_application_path.get())) {
86     LOG(ERROR) << "root_application_path ("
87                << context_->root_application_path.get()
88                << ") path does not exist";
89     return Step::Status::INVALID_VALUE;
90   }
91   return Status::OK;
92 }
93
94 std::unique_ptr<IZipInterface> StepMountUnpacked::CreateZipInterface(
95     const boost::filesystem::path& mount_path) {
96   std::unique_ptr<IZipInterface> zip_interface(
97       new TzipInterface(mount_path));
98   return zip_interface;
99 }
100
101 }  // namespace mount
102 }  // namespace common_installer