Remove GUID and refactoring update mode
[framework/web/wrt-installer.git] / src / wrt-installer / wrt_installer.cpp
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 /* @file    wrt_installer.cpp
17  * @version 1.0
18  * @brief   Implementation file for installer
19  */
20
21 #include "wrt_installer.h"
22 #include "plugin_utils.h"
23
24 #include <cstdlib>
25 #include <string>
26 #include <fstream>
27 #include <unistd.h>
28 #include <memory>
29 #include <sys/resource.h>
30 #include <dpl/optional.h>
31 #include <dpl/scoped_free.h>
32 #include <dpl/optional_typedefs.h>
33 #include <dpl/exception.h>
34 #include <dpl/sstream.h>
35 #include <vconf.h>
36 #include <dpl/wrt-dao-ro/global_config.h>
37 #include <dpl/wrt-dao-ro/config_parser_data.h>
38 #include <dpl/localization/localization_utils.h>
39 #include <dpl/optional_typedefs.h>
40 #include <dpl/string.h>
41 #include <dpl/abstract_waitable_input_adapter.h>
42 #include <dpl/abstract_waitable_output_adapter.h>
43 #include <dpl/zip_input.h>
44 #include <dpl/binary_queue.h>
45 #include <dpl/copy.h>
46 #include <dpl/errno_string.h>
47 #include <dpl/utils/wrt_global_settings.h>
48 #include "option_parser.h"
49 #include <parser_runner.h>
50 #include <widget_parser.h>
51 #include <root_parser.h>
52
53 #define NOFILE_CNT_FOR_INSTALLER 9999
54
55 using namespace WrtDB;
56
57 namespace { // anonymous
58 const char AUL_ARG_KEY[] = "widget_arg";
59 const char * const PKGMGR_INSTALL_MSG = "Install widget";
60 const char * const PKGMGR_UNINSTALL_MSG = "Uninstall widget";
61
62 const double BASE_LAYOUT_W = 720.0f;
63 const double BASE_LAYOUT_H = 1280.0f;
64
65 const char * const CONFIG_XML = "config.xml";
66 const char * const HYBRID_CONFIG_XML = "res/wgt/config.xml";
67
68 struct free_deleter
69 {
70     void operator()(void* x)
71     {
72         free(x);
73     }
74 };
75
76 struct PluginInstallerData
77 {
78     void* wrtInstaller;
79     std::string pluginPath;
80 };
81 } // namespace anonymous
82
83 WrtInstaller::WrtInstaller(int argc, char **argv) :
84     Application(argc, argv, "backend", false),
85     DPL::TaskDecl<WrtInstaller>(this),
86     m_installPolicy(WRT_WIM_NOT_INSTALLED),
87     m_packagePath(),
88     m_handle(-1),
89     m_initialized(false),
90     m_numPluginsToInstall(0),
91     m_totalPlugins(0),
92     m_returnStatus(-1),
93     m_installByPkgmgr(false),
94     m_quiet(true),
95     m_popup(NULL),
96     m_startupPluginInstallation(false),
97     m_preloadWidget(false)
98 {
99     Touch();
100     LogDebug("App Created");
101 }
102
103 WrtInstaller::~WrtInstaller()
104 {
105     LogDebug("App Finished");
106 }
107
108 void WrtInstaller::OnStop()
109 {
110     LogInfo("Stopping Dummy Client");
111 }
112
113 void WrtInstaller::OnCreate()
114 {
115     LogInfo("Creating DummyClient");
116     fprintf(stderr,
117             "===========================================================\n");
118     fprintf(stderr, "# wrt-installer #\n");
119     fprintf(stderr, "# argc [%d]\n", m_argc);
120     fprintf(stderr, "# argv[0] = [%s]\n", m_argv[0]);
121     fprintf(stderr, "# argv[1] = [%s]\n", m_argv[1]);
122     fprintf(stderr, "# argv[2] = [%s]\n", m_argv[2]);
123     fprintf(stderr,
124             "===========================================================\n");
125
126     AddStep(&WrtInstaller::initStep);
127
128     std::string arg = m_argv[0];
129
130     pkgmgrSignalInterface =
131         std::static_pointer_cast<PackageManager::IPkgmgrSignal>(
132             std::shared_ptr<PackageManager::PkgmgrSignalDummy>(
133                 new PackageManager::PkgmgrSignalDummy()
134                 )
135             );
136
137     if (arg.empty()) {
138         return showHelpAndQuit();
139     }
140
141     installNewPlugins();
142
143     if (arg.find("wrt-installer") != std::string::npos) {
144         if (m_argc <= 1) {
145             return showHelpAndQuit();
146         }
147
148         arg = m_argv[1];
149         if (arg == "-h" || arg == "--help") {
150             if (m_argc != 2) {
151                 return showHelpAndQuit();
152             }
153
154             // Just show help
155             return showHelpAndQuit();
156         } else if (arg == "-p" || arg == "--install-plugins") {
157             if (m_argc != 2) {
158                 return showHelpAndQuit();
159             }
160             if (!m_startupPluginInstallation) {
161                 AddStep(&WrtInstaller::installPluginsStep);
162             } else {
163                 LogInfo("Plugin installation alredy started");
164             }
165         } else if (arg == "-i" || arg == "--install") {
166             if (m_argc != 3) {
167                 return showHelpAndQuit();
168             }
169
170             struct stat info;
171             if (-1 != stat(m_argv[2], &info) && S_ISDIR(info.st_mode)) {
172                 LogInfo("Installing package directly from directory");
173                 m_installPolicy = WRT_WIM_POLICY_DIRECTORY_FORCE_INSTALL;
174             } else {
175                 LogInfo("Installing from regular location");
176                 m_installPolicy = WRT_WIM_POLICY_WAC;
177             }
178             m_packagePath = m_argv[2];
179             AddStep(&WrtInstaller::installStep);
180         } else if (arg == "-if" || arg == "--install-force") {
181             if (m_argc != 3) {
182                 return showHelpAndQuit();
183             }
184
185             m_packagePath = m_argv[2];
186             m_installPolicy = WRT_WIM_POLICY_FORCE_INSTALL;
187             AddStep(&WrtInstaller::installStep);
188         } else if (arg == "-il" || arg == "--install-preload") {
189             if (m_argc != 3) {
190                 return showHelpAndQuit();
191             }
192
193             m_packagePath = m_argv[2];
194             m_preloadWidget = true;
195             m_installPolicy = WRT_WIM_POLICY_WAC;
196             AddStep(&WrtInstaller::installStep);
197         } else if (arg == "-un" || arg == "--uninstall-name") {
198             if (m_argc != 3) {
199                 return showHelpAndQuit();
200             }
201             m_name = m_argv[2];
202             AddStep(&WrtInstaller::uninstallPkgNameStep);
203         } else if (arg == "-up" || arg == "--uninstall-packagepath") {
204             if (m_argc != 3) {
205                 return showHelpAndQuit();
206             }
207             m_packagePath = m_argv[2];
208             AddStep(&WrtInstaller::unistallWgtFileStep);
209         } else {
210             return showHelpAndQuit();
211         }
212     } else if (arg.find("backend") != std::string::npos) {
213         using namespace PackageManager;
214         m_installByPkgmgr = true;
215
216         auto pkgmgrSignal = std::shared_ptr<PackageManager::PkgmgrSignal>(
217                 new PackageManager::PkgmgrSignal()
218                 );
219
220         pkgmgrSignal->initialize(m_argc, m_argv);
221         m_quiet = pkgmgrSignal->isNoPopupRequired();
222         LogDebug("backend m_quiet" << m_quiet);
223
224         int reqType = pkgmgrSignal->getRequestedType();
225
226         pkgmgrSignalInterface =
227             std::static_pointer_cast<PackageManager::IPkgmgrSignal>(
228                 pkgmgrSignal);
229         switch (reqType) {
230         case PKGMGR_REQ_INSTALL:
231             m_packagePath = m_argv[4];
232             struct stat info;
233             if (-1 != stat(m_argv[4], &info) && S_ISDIR(info.st_mode)) {
234                 LogInfo("Installing package directly from directory");
235                 m_installPolicy = WRT_WIM_POLICY_DIRECTORY_FORCE_INSTALL;
236             } else {
237                 LogInfo("Installing from regular location");
238                 m_installPolicy = WRT_WIM_POLICY_WAC;
239             }
240             AddStep(&WrtInstaller::installStep);
241             break;
242         case PKGMGR_REQ_UNINSTALL:
243             m_name = m_argv[4];
244             AddStep(&WrtInstaller::uninstallPkgNameStep);
245             break;
246         default:
247             LogDebug("Not available type");
248             break;
249         }
250     }
251
252     AddStep(&WrtInstaller::shutdownStep);
253     DPL::Event::ControllerEventHandler<WRTInstallerNS::NextStepEvent>::
254         PostEvent(
255         WRTInstallerNS::NextStepEvent());
256 }
257
258 void WrtInstaller::OnReset(bundle *b)
259 {
260     const char * bundledVal = bundle_get_val(b, AUL_ARG_KEY);
261     if (bundledVal != NULL) {
262         m_bundleValue = bundledVal;
263         LogInfo("Bundled value for (" << AUL_ARG_KEY << ") key received: " <<
264                 m_bundleValue);
265     }
266 }
267
268 int WrtInstaller::getReturnStatus() const
269 {
270     if (!m_returnStatus) {
271         return RE_SUCCESS;
272     } else {
273         return RE_FAIL;
274     }
275 }
276
277 void WrtInstaller::OnTerminate()
278 {
279     LogDebug("Wrt Shutdown now");
280     PluginUtils::unlockPluginInstallation();
281     if (m_initialized) {
282         wrt_installer_shutdown();
283     }
284     delete m_popup;
285 }
286
287 void WrtInstaller::showHelpAndQuit()
288 {
289     printf("Usage: wrt-installer [OPTION]... [WIDGET: ID/NAME/PATH]...\n"
290            "Operate with WebRuntime daemon: install, uninstall"
291            " and launch widgets.\n"
292            "Query list of installed widgets and setup up debugging support.\n"
293            "\n"
294            "Exactly one option must be selected.\n"
295            "Mandatory arguments to long options are mandatory for short "
296            "options too.\n"
297            "  -h,    --help                                 show this help\n"
298            "  -p,    --install-plugins                      install plugins\n"
299            "  -i,    --install                              "
300            "install or update widget package for given path\n"
301            "  -if,   --install-force                        "
302            "install forcibly widget package for given path\n"
303            "  -un,   --uninstall-name                       "
304            "uninstall widget for given package name\n"
305            "  -up,   --uninstall-packagepath                "
306            "uninstall widget for given package file path\n"
307            "\n");
308
309     Quit();
310 }
311
312 void WrtInstaller::OnEventReceived(const WRTInstallerNS::QuitEvent& /*event*/)
313 {
314     LogDebug("Quiting");
315
316     if (m_initialized) {
317         LogDebug("Wrt Shutdown now");
318         SwitchToStep(&WrtInstaller::shutdownStep);
319         DPL::Event::ControllerEventHandler<WRTInstallerNS::NextStepEvent>::
320             PostEvent(
321             WRTInstallerNS::NextStepEvent());
322     } else {
323         LogDebug("Quiting application");
324         return Quit();
325     }
326 }
327
328 void WrtInstaller::OnEventReceived(
329     const WRTInstallerNS::NextStepEvent& /*event*/)
330 {
331     LogDebug("Executing next step");
332     NextStep();
333 }
334
335 void WrtInstaller::OnEventReceived(
336     const WRTInstallerNS::InstallPluginEvent& /*event*/)
337 {
338     PluginInstallerData* privateData = new PluginInstallerData;
339     privateData->wrtInstaller = this;
340
341     if (!(*m_pluginsPaths).empty()) {
342         privateData->pluginPath = (*m_pluginsPaths).front();
343         (*m_pluginsPaths).pop_front();
344
345         wrt_install_plugin(privateData->pluginPath.c_str(),
346                            static_cast<void*>(privateData),
347                            &staticWrtPluginInstallationCallback,
348                            &staticWrtPluginInstallProgressCb);
349     } else {
350         delete privateData;
351     }
352 }
353
354 void WrtInstaller::initStep()
355 {
356     wrt_installer_init(this, staticWrtInitCallback);
357 }
358
359 void WrtInstaller::installStep()
360 {
361     LogDebug("Installing widget ...");
362     std::unique_ptr<char, free_deleter> packagePath(canonicalize_file_name(
363                                                         m_packagePath.c_str()));
364
365     wrt_install_widget(packagePath ? packagePath.get() : m_packagePath.c_str(),
366                        this, &staticWrtStatusCallback,
367                        (!m_quiet || m_installByPkgmgr)
368                        ? &staticWrtInstallProgressCallback : NULL,
369                        m_installPolicy,
370                        m_quiet,
371                        m_preloadWidget,
372                        pkgmgrSignalInterface);
373 }
374
375 void WrtInstaller::installPluginsStep()
376 {
377     LogDebug("Installing plugins ...");
378     fprintf(stderr, "Installing plugins ...\n");
379
380     if (m_startupPluginInstallation) {
381         LogInfo("Plugin installation started because new plugin package found");
382     } else if (!PluginUtils::lockPluginInstallation()) {
383         LogError("Failed to open plugin installation lock file"
384                  " Plugins are currently installed by other process");
385         staticWrtPluginInstallationCallback(WRT_INSTALLER_ERROR_PLUGIN_INSTALLATION_FAILED,
386                                             this);
387         return;
388     }
389
390     std::string PLUGIN_PATH = std::string(GlobalConfig::GetDevicePluginPath());
391
392     DIR *dir;
393     dir = opendir(PLUGIN_PATH.c_str());
394
395     if (!dir) {
396         return;
397     }
398
399     LogInfo("Plugin DIRECTORY IS" << PLUGIN_PATH);
400
401     std::list<std::string> pluginsPaths;
402     struct dirent libdir;
403     struct dirent *result;
404     int return_code;
405     errno = 0;
406     for (return_code = readdir_r(dir, &libdir, &result);
407             result != NULL && return_code == 0;
408             return_code = readdir_r(dir, &libdir, &result))
409     {
410         if (strcmp(libdir.d_name, ".") == 0 ||
411             strcmp(libdir.d_name, "..") == 0)
412         {
413             continue;
414         }
415
416         std::string path = PLUGIN_PATH;
417         path += "/";
418         path += libdir.d_name;
419
420         struct stat tmp;
421
422         if (stat(path.c_str(), &tmp) == -1) {
423             LogError("Failed to open file" << path);
424             continue;
425         }
426
427         if (!S_ISDIR(tmp.st_mode)) {
428             LogError("Not a directory" << path);
429             continue;
430         }
431
432         pluginsPaths.push_back(path);
433     }
434
435     if (return_code != 0 || errno != 0) {
436         LogError("readdir_r() failed with " << DPL::GetErrnoString());
437     }
438
439     //set nb of plugins to install
440     //this value indicate how many callbacks are expected
441     m_numPluginsToInstall = pluginsPaths.size();
442     LogInfo("Plugins to install: " << m_numPluginsToInstall);
443     m_pluginsPaths = pluginsPaths;
444
445     m_totalPlugins = m_numPluginsToInstall;
446     DPL::Event::ControllerEventHandler<WRTInstallerNS::InstallPluginEvent>
447         ::PostEvent(WRTInstallerNS::InstallPluginEvent());
448
449     if (-1 == TEMP_FAILURE_RETRY(closedir(dir))) {
450         LogError("Failed to close dir: " << PLUGIN_PATH << " with error: "
451                                          << DPL::GetErrnoString());
452     }
453 }
454
455 void WrtInstaller::uninstallPkgNameStep()
456 {
457     LogDebug("Uninstalling widget ...");
458     LogDebug("Package name : " << m_name);
459     wrt_uninstall_widget(m_name.c_str(), this, &staticWrtStatusCallback,
460                          (!m_quiet || m_installByPkgmgr)
461                          ? &staticWrtUninstallProgressCallback : NULL,
462                          pkgmgrSignalInterface);
463 }
464
465 void WrtInstaller::unistallWgtFileStep()
466 {
467     LogDebug("Uninstalling widget ...");
468
469     Try {
470         // Parse config
471         ParserRunner parser;
472         ConfigParserData configInfo;
473
474         // Open zip file
475         std::unique_ptr<DPL::ZipInput> zipFile(
476             new DPL::ZipInput(m_packagePath));
477         std::unique_ptr<DPL::ZipInput::File> configFile;
478
479         Try {
480             // Open config.xml file
481             configFile.reset(zipFile->OpenFile(CONFIG_XML));
482         }
483         Catch(DPL::ZipInput::Exception::OpenFileFailed)
484         {
485             // Open config.xml file for hybrid
486             configFile.reset(zipFile->OpenFile(HYBRID_CONFIG_XML));
487         }
488
489         // Extract config
490         DPL::BinaryQueue buffer;
491         DPL::AbstractWaitableInputAdapter inputAdapter(configFile.get());
492         DPL::AbstractWaitableOutputAdapter outputAdapter(&buffer);
493         DPL::Copy(&inputAdapter, &outputAdapter);
494         parser.Parse(&buffer,
495                      ElementParserPtr(
496                          new RootParser<WidgetParser>(configInfo,
497                                                       DPL::FromUTF32String(
498                                                           L"widget"))));
499
500         DPL::OptionalString pkgId = configInfo.tizenPkgId;
501         if (!pkgId.IsNull()) {
502             LogDebug("Pkgid from packagePath : " << pkgId);
503             wrt_uninstall_widget(
504                 DPL::ToUTF8String(*pkgId).c_str(), this, &staticWrtStatusCallback,
505                 !m_quiet ? &staticWrtUninstallProgressCallback
506                 : NULL,
507                 pkgmgrSignalInterface);
508         } else {
509             LogError("Fail to uninstalling widget... ");
510             m_returnStatus = -1;
511             DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
512                 PostEvent(
513                 WRTInstallerNS::QuitEvent());
514         }
515     }
516     Catch(DPL::ZipInput::Exception::OpenFailed)
517     {
518         LogError("Failed to open widget package");
519         printf("failed: widget package does not exist\n");
520         m_returnStatus = -1;
521         DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
522             PostEvent(
523             WRTInstallerNS::QuitEvent());
524     }
525     Catch(DPL::ZipInput::Exception::OpenFileFailed)
526     {
527         printf("failed: widget config file does not exist\n");
528         LogError("Failed to open config.xml file");
529         m_returnStatus = -1;
530         DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
531             PostEvent(
532             WRTInstallerNS::QuitEvent());
533     }
534     Catch(ElementParser::Exception::ParseError)
535     {
536         printf("failed: can not parse config file\n");
537         LogError("Failed to parse config.xml file");
538         m_returnStatus = -1;
539         DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
540             PostEvent(
541             WRTInstallerNS::QuitEvent());
542     }
543 }
544
545 void WrtInstaller::shutdownStep()
546 {
547     LogDebug("Closing Wrt connection ...");
548     if (m_initialized) {
549         wrt_installer_shutdown();
550         m_initialized = false;
551         DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
552             PostEvent(
553             WRTInstallerNS::QuitEvent());
554     }
555 }
556
557 void WrtInstaller::staticWrtInitCallback(WrtErrStatus status,
558                                          void* userdata)
559 {
560     WrtInstaller *This = static_cast<WrtInstaller*>(userdata);
561     Assert(This);
562
563     if (status == WRT_SUCCESS) {
564         LogDebug("Init succesfull");
565         This->m_initialized = true;
566         This->m_returnStatus = 0;
567
568         if (This->popupsEnabled()) {
569             This->m_popup = new InstallerPopup;
570             This->m_popup->init();
571         }
572
573         This->DPL::Event::ControllerEventHandler<WRTInstallerNS::NextStepEvent>
574             ::PostEvent(WRTInstallerNS::NextStepEvent());
575     } else {
576         LogError("Init unsuccesfull");
577         This->m_returnStatus = -1;
578         This->DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>::
579             PostEvent(
580             WRTInstallerNS::QuitEvent());
581     }
582 }
583
584 void WrtInstaller::staticWrtStatusCallback(std::string tizenId,
585                                            WrtErrStatus status,
586                                            void* userdata)
587 {
588     WrtInstaller *This = static_cast<WrtInstaller*>(userdata);
589     Assert(This);
590
591     Step current = This->GetCurrentStep();
592     DPL::String resultMsg;
593     std::string printMsg;
594
595     if (current == &WrtInstaller::installStep) {
596         resultMsg = DPL::FromUTF8String(PKGMGR_INSTALL_MSG);
597         printMsg = "installation";
598     } else if (current == &WrtInstaller::uninstallPkgNameStep ||
599                current == &WrtInstaller::unistallWgtFileStep)
600     {
601         resultMsg = DPL::FromUTF8String(PKGMGR_UNINSTALL_MSG);
602         printMsg = "uninstallation";
603     }
604
605     if (WRT_SUCCESS != status) {
606         // Failure
607         LogError("Step failed");
608         This->m_returnStatus = -1;
609
610         if (This->popupsEnabled()) {
611             resultMsg += L" : " + DPL::FromUTF8String(PKGMGR_END_FAILURE);
612             This->m_popup->showPopup(This, resultMsg, failResultCallback);
613         } else {
614             This->DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>
615                 ::PostEvent(WRTInstallerNS::QuitEvent());
616         }
617
618         switch (status) {
619             case WRT_INSTALLER_ERROR_PACKAGE_NOT_FOUND:
620                 This->m_returnStatus = 1; //this status is specific
621                 fprintf(stderr, "## wrt-installer : %s %s has failed - widget package does not exist\n",
622                         tizenId.c_str(), printMsg.c_str());
623                 break;
624
625             case WRT_INSTALLER_ERROR_PACKAGE_INVALID:
626                 This->m_returnStatus = 1; //this status is specific
627                 fprintf(stderr, "## wrt-installer : %s %s has failed - invalid widget package\n",
628                         tizenId.c_str(), printMsg.c_str());
629                 break;
630
631             case WRT_INSTALLER_ERROR_PACKAGE_LOWER_VERSION:
632                 This->m_returnStatus = 1; //this status is specific
633                 fprintf(stderr, "## wrt-installer : %s %s has failed - given"
634                         " version is lower than existing version\n",
635                         tizenId.c_str(), printMsg.c_str());
636                 break;
637
638             case WRT_INSTALLER_ERROR_MANIFEST_NOT_FOUND:
639                 This->m_returnStatus = 1; //this status is specific
640                 fprintf(stderr, "## wrt-installer : %s %s has failed - manifest"
641                         " file doesn't find in package.\n",
642                         tizenId.c_str(), printMsg.c_str());
643                 break;
644
645             case WRT_INSTALLER_ERROR_MANIFEST_INVALID:
646                 This->m_returnStatus = 1; //this status is specific
647                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
648                         "invalid manifestx.xml\n",
649                         tizenId.c_str(), printMsg.c_str());
650                 break;
651
652             case WRT_INSTALLER_CONFIG_NOT_FOUND:
653                 This->m_returnStatus = 1; //this status is specific
654                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
655                         "config.xml does not exist\n",
656                         tizenId.c_str(), printMsg.c_str());
657                 break;
658
659             case WRT_INSTALLER_ERROR_CONFIG_INVALID:
660                 This->m_returnStatus = 1; //this status is specific
661                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
662                         "invalid config.xml\n",
663                         tizenId.c_str(), printMsg.c_str());
664                 break;
665
666             case WRT_INSTALLER_ERROR_SIGNATURE_NOT_FOUND:
667                 This->m_returnStatus = 1; //this status is specific
668                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
669                         "signature doesn't exist in package.\n",
670                         tizenId.c_str(), printMsg.c_str());
671                 break;
672
673             case WRT_INSTALLER_ERROR_SIGNATURE_INVALID:
674                 This->m_returnStatus = 1; //this status is specific
675                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
676                         "invalid signature.\n",
677                         tizenId.c_str(), printMsg.c_str());
678                 break;
679
680             case WRT_INSTALLER_ERROR_SIGNATURE_VERIFICATION_FAILED:
681                 This->m_returnStatus = 1; //this status is specific
682                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
683                         "signature verification failed.\n",
684                         tizenId.c_str(), printMsg.c_str());
685                 break;
686
687             case WRT_INSTALLER_ERROR_ROOT_CERTIFICATE_NOT_FOUND:
688                 This->m_returnStatus = 1; //this status is specific
689                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
690                         "root certificate could not find.\n",
691                         tizenId.c_str(), printMsg.c_str());
692                 break;
693
694             case WRT_INSTALLER_ERROR_CERTIFICATION_INVAID:
695                 This->m_returnStatus = 1; //this status is specific
696                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
697                         "invalid certification.\n",
698                         tizenId.c_str(), printMsg.c_str());
699                 break;
700
701             case WRT_INSTALLER_ERROR_CERTIFICATE_CHAIN_VERIFICATION_FAILED:
702                 This->m_returnStatus = 1; //this status is specific
703                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
704                         "certificate chain verification failed.\n",
705                         tizenId.c_str(), printMsg.c_str());
706                 break;
707
708             case WRT_INSTALLER_ERROR_CERTIFICATE_EXPIRED:
709                 This->m_returnStatus = 1; //this status is specific
710                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
711                         "certificate expired.\n",
712                         tizenId.c_str(), printMsg.c_str());
713                 break;
714
715             case WRT_INSTALLER_ERROR_INVALID_PRIVILEGE:
716                 This->m_returnStatus = 1; //this status is specific
717                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
718                         "invalid privilege\n",
719                         tizenId.c_str(), printMsg.c_str());
720                 break;
721
722             case WRT_INSTALLER_ERROR_MENU_ICON_NOT_FOUND:
723                 This->m_returnStatus = 1; //this status is specific
724                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
725                         "menu icon could not find\n",
726                         tizenId.c_str(), printMsg.c_str());
727                 break;
728
729             case WRT_INSTALLER_ERROR_FATAL_ERROR:
730                 This->m_returnStatus = 1; //this status is specific
731                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
732                         "fatal error\n",
733                         tizenId.c_str(), printMsg.c_str());
734                 break;
735
736             case WRT_INSTALLER_ERROR_OUT_OF_STORAGE:
737                 This->m_returnStatus = 1; //this status is specific
738                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
739                         "out of storage\n",
740                         tizenId.c_str(), printMsg.c_str());
741                 break;
742
743             case WRT_INSTALLER_ERROR_OUT_OF_MEMORY:
744                 This->m_returnStatus = 1; //this status is specific
745                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
746                         "out of memory\n",
747                         tizenId.c_str(), printMsg.c_str());
748                 break;
749
750             case WRT_INSTALLER_ERROR_PACKAGE_ALREADY_INSTALLED:
751                 This->m_returnStatus = 1; //this status is specific
752                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
753                         "package already installed\n",
754                         tizenId.c_str(), printMsg.c_str());
755                 break;
756
757             case WRT_INSTALLER_ERROR_ACE_CHECK_FAILED:
758                 This->m_returnStatus = 1; //this status is specific
759                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
760                         "ace check failure\n",
761                         tizenId.c_str(), printMsg.c_str());
762                 break;
763
764             case WRT_INSTALLER_ERROR_MANIFEST_CREATE_FAILED:
765                 This->m_returnStatus = 1; //this status is specific
766                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
767                         "to create manifest failed\n",
768                         tizenId.c_str(), printMsg.c_str());
769                 break;
770
771             case WRT_INSTALLER_ERROR_ENCRYPTION_FAILED:
772                 This->m_returnStatus = 1; //this status is specific
773                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
774                         "encryption of resource failed\n",
775                         tizenId.c_str(), printMsg.c_str());
776                 break;
777
778             case WRT_INSTALLER_ERROR_INSTALL_OSP_SERVCIE:
779                 This->m_returnStatus = 1; //this status is specific
780                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
781                         "installation of osp service failed\n",
782                         tizenId.c_str(), printMsg.c_str());
783                 break;
784
785             case WRT_INSTALLER_ERROR_UNINSTALLATION_FAILED:
786                 This->m_returnStatus = 1; //this status is specific
787                 fprintf(stderr, "## wrt-installer : %s %s has failed - "
788                         "widget uninstallation failed\n",
789                         tizenId.c_str(), printMsg.c_str());
790                 break;
791
792
793             case WRT_INSTALLER_ERROR_UNKNOWN:
794                 fprintf(stderr,"## wrt-installer : %s %s has failed - unknown error\n",
795                         tizenId.c_str(), printMsg.c_str());
796                 break;
797
798             default:
799                 break;
800         }
801     } else {
802         fprintf(stderr,
803                 "## wrt-installer : %s %s was successful.\n",
804                 tizenId.c_str(),
805                 printMsg.c_str());
806         LogDebug("Status succesfull");
807         This->m_returnStatus = 0;
808         resultMsg += L" : " + DPL::FromUTF8String(PKGMGR_END_SUCCESS);
809
810         if (This->popupsEnabled()) {
811             This->m_popup->showPopup(This, resultMsg, showResultCallback);
812         } else {
813             This->DPL::Event::ControllerEventHandler<WRTInstallerNS::
814                                                          NextStepEvent>
815                 ::PostEvent(WRTInstallerNS::NextStepEvent());
816         }
817     }
818 }
819
820 void WrtInstaller::staticWrtPluginInstallationCallback(WrtErrStatus status,
821                                                        void* userdata)
822 {
823     Assert(userdata);
824
825     PluginInstallerData* data = static_cast<PluginInstallerData*>(userdata);
826
827     WrtInstaller *This = static_cast<WrtInstaller*>(data->wrtInstaller);
828
829     std::string path = std::string(data->pluginPath);
830     delete data;
831
832     This->m_numPluginsToInstall--;
833     LogDebug("Plugins to install: " << This->m_numPluginsToInstall);
834
835     if (This->m_numPluginsToInstall < 1) {
836         LogDebug("All plugins installation completed");
837         fprintf(stderr, "All plugins installation completed.\n");
838
839         //remove installation request
840         if (!PluginUtils::removeInstallationRequiredFlag()) {
841             LogInfo("Failed to remove file initializing plugin installation");
842         }
843
844         //remove lock file
845         if (!PluginUtils::unlockPluginInstallation()) {
846             LogInfo("Failed to remove installation lock");
847         }
848
849         if (This->popupsEnabled()) {
850             This->m_popup->init();
851             elm_progressbar_value_set(This->m_popup->m_progressbar, 100.0);
852             evas_object_show(This->m_popup->m_popup);
853         }
854
855         This->DPL::Event::ControllerEventHandler<WRTInstallerNS::NextStepEvent>
856             ::PostEvent(WRTInstallerNS::NextStepEvent());
857     } else {
858         if (This->popupsEnabled()) {
859             This->m_popup->init();
860             float percent =
861                 (This->m_totalPlugins -
862                  This->m_numPluginsToInstall) / (float)This->m_totalPlugins;
863             elm_progressbar_value_set(This->m_popup->m_progressbar, percent);
864             evas_object_show(This->m_popup->m_popup);
865         }
866
867         This->DPL::Event::ControllerEventHandler<WRTInstallerNS::
868                                                      InstallPluginEvent>::
869             PostEvent(
870             WRTInstallerNS::InstallPluginEvent());
871     }
872
873     if (WRT_SUCCESS == status) {
874         This->m_returnStatus = 0;
875         fprintf(stderr,
876                 "## wrt-installer : plugin installation successfull [%s]\n",
877                 path.c_str());
878         LogDebug("One plugin Installation succesfull: " << path);
879         return;
880     }
881
882     // Failure
883     LogWarning("One of the plugins installation failed!: " << path);
884
885     switch (status) {
886     case WRT_INSTALLER_ERROR_PLUGIN_INSTALLATION_FAILED:
887         LogError("failed: plugin installation failed\n");
888         break;
889
890     case WRT_INSTALLER_ERROR_UNKNOWN:
891         LogError("failed: unknown error\n");
892         break;
893
894     default:
895         break;
896     }
897 }
898
899 void WrtInstaller::staticWrtPluginInstallProgressCb(float percent,
900                                                     const char* description,
901                                                     void* userdata)
902 {
903     PluginInstallerData* data = static_cast<PluginInstallerData*>(userdata);
904
905     std::string path = std::string(data->pluginPath);
906
907     LogInfo("Plugin Installation: " << path <<
908             " progress: " << percent <<
909             "description " << description);
910 }
911
912 void WrtInstaller::staticWrtInstallProgressCallback(float percent,
913                                                     const char* description,
914                                                     void* userdata)
915 {
916     WrtInstaller *This = static_cast<WrtInstaller*>(userdata);
917     LogInfo(" progress: " << percent <<
918             " description: " << description);
919
920     if (This->popupsEnabled()) {
921         This->m_popup->init();
922         elm_progressbar_value_set(This->m_popup->m_progressbar, percent / 100.0);
923         evas_object_show(This->m_popup->m_popup);
924     }
925 }
926 void WrtInstaller::staticWrtUninstallProgressCallback(float percent,
927                                                       const char* description,
928                                                       void* userdata)
929 {
930     WrtInstaller *This = static_cast<WrtInstaller*>(userdata);
931     LogInfo(" progress: " << percent <<
932             " description: " << description);
933
934     if (This->popupsEnabled()) {
935         This->m_popup->init();
936         elm_progressbar_value_set(This->m_popup->m_progressbar, percent / 100.0);
937         evas_object_show(This->m_popup->m_popup);
938     }
939 }
940
941 WrtInstaller::InstallerPopup::InstallerPopup() :
942     m_win(NULL),
943     m_popup(NULL),
944     m_progressbar(NULL)
945 {}
946
947 WrtInstaller::InstallerPopup::~InstallerPopup()
948 {
949     LogDebug("App Finished");
950 }
951
952 void WrtInstaller::InstallerPopup::init()
953 {
954     LogDebug("Window Init");
955
956     if (m_win == NULL) {
957         // create window
958         m_win = createWin("wrt-installer");
959
960         // create popup
961         m_popup = elm_popup_add(m_win);
962
963         // create progressbar
964         m_progressbar = elm_progressbar_add(m_popup);
965         elm_object_style_set(m_progressbar, "list_progress");
966         elm_progressbar_horizontal_set(m_progressbar, EINA_TRUE);
967         evas_object_size_hint_align_set(m_progressbar, EVAS_HINT_FILL,
968                                         EVAS_HINT_FILL);
969         evas_object_size_hint_weight_set(m_progressbar, EVAS_HINT_EXPAND,
970                                          EVAS_HINT_EXPAND);
971         elm_object_content_set(m_popup, m_progressbar);
972         elm_progressbar_value_set(m_progressbar, 0.0);
973         evas_object_show(m_progressbar);
974
975         evas_object_show(m_popup);
976         evas_object_show(m_win);
977     }
978 }
979
980 Evas_Object* WrtInstaller::InstallerPopup::createWin(const char *name)
981 {
982     Evas_Object *win;
983     win = elm_win_add(NULL, name, ELM_WIN_DIALOG_BASIC);
984
985     int w, h;
986     if (!win) {
987         return NULL;
988     }
989
990     elm_win_alpha_set(win, EINA_TRUE);
991     elm_win_title_set(win, name);
992     elm_win_borderless_set(win, EINA_TRUE);
993     elm_win_raise(win);
994
995     ecore_x_window_size_get(ecore_x_window_root_first_get(), &w, &h);
996     evas_object_resize(win, w, h);
997     return win;
998 }
999
1000 void WrtInstaller::InstallerPopup::showPopup(void* userdata,
1001                                              const DPL::String& pkgMsg,
1002                                              ShowResultCallback callback)
1003 {
1004     Evas_Object *btn;
1005
1006     LogDebug("Result Popup Created");
1007     evas_object_del(m_popup);
1008     m_popup = NULL;
1009
1010     m_popup = elm_popup_add(m_win);
1011     if (!m_popup) {
1012         return;
1013     }
1014
1015     btn = elm_button_add(m_popup);
1016     if (!btn) {
1017         evas_object_del(m_popup);
1018         return;
1019     }
1020     elm_object_text_set(btn, "OK");
1021     evas_object_smart_callback_add(btn, "clicked", callback, userdata);
1022     elm_object_part_content_set(m_popup, "button1", btn);
1023     elm_object_part_text_set(m_popup, "title,text", "RESULT");
1024     elm_object_text_set(m_popup, DPL::ToUTF8String(pkgMsg).c_str());
1025
1026     evas_object_show(m_popup);
1027     evas_object_show(m_win);
1028 }
1029
1030 void WrtInstaller::showResultCallback(void *data, Evas_Object* /*obj*/,
1031                                       void* /*event_info*/)
1032 {
1033     WrtInstaller *This = static_cast<WrtInstaller*>(data);
1034     Assert(This);
1035
1036     This->DPL::Event::ControllerEventHandler<WRTInstallerNS::NextStepEvent>
1037         ::PostEvent(WRTInstallerNS::NextStepEvent());
1038 }
1039
1040 void WrtInstaller::failResultCallback(void *data, Evas_Object* /*obj*/,
1041                                       void* /*event_info*/)
1042 {
1043     WrtInstaller *This = static_cast<WrtInstaller*>(data);
1044     Assert(This);
1045
1046     This->DPL::Event::ControllerEventHandler<WRTInstallerNS::QuitEvent>
1047         ::PostEvent(WRTInstallerNS::QuitEvent());
1048 }
1049
1050 void WrtInstaller::installNewPlugins()
1051 {
1052     LogDebug("Install new plugins");
1053
1054     if (!PluginUtils::lockPluginInstallation()) {
1055         LogInfo("Lock NOT created");
1056         return;
1057     }
1058
1059     if (!PluginUtils::checkPluginInstallationRequired()) {
1060         LogDebug("Plugin installation not required");
1061         PluginUtils::unlockPluginInstallation();
1062         return;
1063     }
1064
1065     m_startupPluginInstallation = true;
1066     AddStep(&WrtInstaller::installPluginsStep);
1067 }
1068
1069 bool WrtInstaller::popupsEnabled() const
1070 {
1071     return !m_quiet && !GlobalSettings::PopupsTestModeEnabled();
1072 }
1073
1074 int main(int argc, char *argv[])
1075 {
1076     UNHANDLED_EXCEPTION_HANDLER_BEGIN
1077     {
1078         // Output on stdout will be flushed after every newline character,
1079         // even if it is redirected to a pipe. This is useful for running
1080         // from a script and parsing output.
1081         // (Standard behavior of stdlib is to use full buffering when
1082         // redirected to a pipe, which means even after an end of line
1083         // the output may not be flushed).
1084         setlinebuf(stdout);
1085
1086         // Check and re-set the file open limitation
1087         struct rlimit rlim;
1088         if (getrlimit(RLIMIT_NOFILE, &rlim) != -1) {
1089             LogDebug("RLIMIT_NOFILE sft(" << rlim.rlim_cur << ")");
1090             LogDebug("RLIMIT_NOFILE hrd(" << rlim.rlim_max << ")");
1091
1092             if (rlim.rlim_cur < NOFILE_CNT_FOR_INSTALLER) {
1093                 rlim.rlim_cur = NOFILE_CNT_FOR_INSTALLER;
1094                 rlim.rlim_max = NOFILE_CNT_FOR_INSTALLER;
1095                 if (setrlimit(RLIMIT_NOFILE, &rlim) == -1) {
1096                     LogError("setrlimit is fail!!");
1097                 }
1098             }
1099         } else {
1100             LogError("getrlimit is fail!!");
1101         }
1102
1103         // set evas backend type for emulator
1104         // popup isn't showed in the emulator,
1105         // if backend isn't set to SW backend
1106         if (GlobalSettings::IsEmulator()) {
1107             if (setenv("ELM_ENGINE", "x11", 1)) {
1108                 LogDebug("Enable backend");
1109             }
1110         }
1111
1112         WrtInstaller app(argc, argv);
1113         int ret = app.Exec();
1114         LogDebug("App returned: " << ret);
1115         ret = app.getReturnStatus();
1116         LogDebug("WrtInstaller returned: " << ret);
1117         return ret;
1118     }
1119     UNHANDLED_EXCEPTION_HANDLER_END
1120 }