for list in $_wgt_list
do
echo "Install $list"
- return_string=`wrt-installer -il $list 2>&1 | grep -v plugin`
+ return_string=`wrt-installer -i $list 2>&1 | grep -v plugin`
if [ "$return_string" != "${return_string/successful/}" ]; then
echo "$list widget installation success"
rm -rf $list
rm -rf %{buildroot}
%post
+/sbin/ldconfig
chmod +s /usr/bin/wrt-installer
#symlink for package manager
# for downloadable Application icons path
mkdir -p /opt/share/icons/default/small
+%postun -p /sbin/ldconfig
+
%files
%manifest wrt-installer.manifest
%attr(755,root,root) %{_bindir}/wrt-installer
LogDebug("Loading plugin: " << filename);
- void *dlHandle = dlopen(filename.c_str(), RTLD_NOW);
+ void *dlHandle = dlopen(filename.c_str(), RTLD_LAZY);
if (dlHandle == NULL) {
LogError(
"Failed to load plugin: " << filename <<
result = validator.check(data, widgetPath);
if (m_contextData.widgetConfig.packagingType
- == WrtDB::PKG_TYPE_DIRECTORY_WEB_APP)
+ == WrtDB::PKG_TYPE_DIRECTORY_WEB_APP ||
+ m_contextData.job->getInstallerStruct().m_installMode
+ == InstallMode::INSTALL_MODE_PRELOAD)
{
// In directory installation mode, the validation is skipped.
#include <dpl/foreach.h>
#include <dpl/log/log.h>
#include <dpl/assert.h>
+#include <dpl/errno_string.h>
#include <dpl/utils/folder_size.h>
+#include <dpl/wrt-dao-ro/global_config.h>
#include <string>
#include <fstream>
#include <widget_install_to_external.h>
closedir(dir);
return true;
}
+
+void changeOwnerForDirectory(std::string storagePath) {
+ if (euidaccess(storagePath.c_str(), F_OK) != 0) {
+ if (!WrtUtilMakeDir(storagePath, PRIVATE_STORAGE_MODE)) {
+ LogError("Failed to create directory for private storage");
+ ThrowMsg(Jobs::WidgetInstall::Exceptions::FileOperationFailed,
+ "Failed to create directory for private storage");
+ }
+ // '5000' is default uid, gid for applications.
+ // So installed applications should be launched as process of uid
+ // '5000'.
+ // the process can access private directory 'data' of itself.
+ if (chown(storagePath.c_str(),
+ WEBAPP_DEFAULT_UID,
+ WEBAPP_DEFAULT_GID) != 0)
+ {
+ ThrowMsg(Jobs::WidgetInstall::Exceptions::FileOperationFailed,
+ "Chown to invaild user");
+ }
+ } else if (euidaccess(storagePath.c_str(), W_OK | R_OK | X_OK) == 0) {
+ LogInfo("Private storage already exists.");
+ // Even if private directory already is created, private dircetory
+ // should change owner.
+ if (chown(storagePath.c_str(),
+ WEBAPP_DEFAULT_UID,
+ WEBAPP_DEFAULT_GID) != 0)
+ {
+ ThrowMsg(Jobs::WidgetInstall::Exceptions::FileOperationFailed,
+ "Chown to invaild user");
+ }
+ if (chmod(storagePath.c_str(), PRIVATE_STORAGE_MODE) != 0) {
+ ThrowMsg(Jobs::WidgetInstall::Exceptions::FileOperationFailed,
+ "chmod to 0700");
+ }
+ } else {
+ ThrowMsg(Jobs::WidgetInstall::Exceptions::FileOperationFailed,
+ "No access to private storage.");
+ }
+}
}
namespace Jobs {
AddStep(&TaskFileManipulation::StepRenamePath);
AddAbortStep(&TaskFileManipulation::StepAbortRenamePath);
}
+ AddStep(&TaskFileManipulation::StepLinkForPreload);
+
} else {
AddStep(&TaskFileManipulation::StepPrepareExternalDir);
AddStep(&TaskFileManipulation::StepInstallToExternal);
void TaskFileManipulation::StepCreatePrivateStorageDir()
{
std::string storagePath = m_context.locations->getPrivateStorageDir();
-
- if (euidaccess(storagePath.c_str(), F_OK) != 0) {
- if (!WrtUtilMakeDir(storagePath, PRIVATE_STORAGE_MODE)) {
- LogError("Failed to create directory for private storage");
- ThrowMsg(Exceptions::FileOperationFailed,
- "Failed to create directory for private storage");
- }
- // '5000' is default uid, gid for applications.
- // So installed applications should be launched as process of uid
- // '5000'.
- // the process can access private directory 'data' of itself.
- if (chown(storagePath.c_str(),
- WEBAPP_DEFAULT_UID,
- WEBAPP_DEFAULT_GID) != 0)
- {
- ThrowMsg(Exceptions::FileOperationFailed,
- "Chown to invaild user");
- }
- } else if (euidaccess(storagePath.c_str(), W_OK | R_OK | X_OK) == 0) {
- LogInfo("Private storage already exists.");
- // Even if private directory already is created, private dircetory
- // should change owner.
- if (chown(storagePath.c_str(),
- WEBAPP_DEFAULT_UID,
- WEBAPP_DEFAULT_GID) != 0)
- {
- ThrowMsg(Exceptions::FileOperationFailed,
- "Chown to invaild user");
- }
- if (chmod(storagePath.c_str(), PRIVATE_STORAGE_MODE) != 0) {
- ThrowMsg(Exceptions::FileOperationFailed,
- "chmod to 0700");
- }
- } else {
- ThrowMsg(Exceptions::FileOperationFailed,
- "No access to private storage.");
- }
+ LogDebug("Create private storage directory : " <<
+ m_context.locations->getPrivateStorageDir());
+ changeOwnerForDirectory(storagePath);
}
void TaskFileManipulation::StepRenamePath()
"Widget Rename path Finished");
}
+void TaskFileManipulation::StepLinkForPreload()
+{
+ if (m_context.job->getInstallerStruct().m_installMode
+ == InstallMode::INSTALL_MODE_PRELOAD)
+ {
+ std::string srcDir = m_context.locations->getUserDataRootDir() +
+ WrtDB::GlobalConfig::GetWidgetSrcPath();
+
+ if (0 != access(srcDir.c_str(), F_OK)) {
+ LogDebug("Make symbolic name for preaload app" << " to " << srcDir <<
+ "from " << m_context.locations->getSourceDir());
+ std::string resDir = m_context.locations->getUserDataRootDir() +
+ "/res";
+
+ WrtUtilMakeDir(resDir);
+ if (symlink(m_context.locations->getSourceDir().c_str(), srcDir.c_str()) != 0)
+ {
+ int error = errno;
+ if (error)
+ LogPedantic("Failed to make a symbolic name for a file "
+ << "[" << DPL::GetErrnoString(error) << "]");
+ ThrowMsg(Exceptions::FileOperationFailed,
+ "Symbolic link creating is not done.");
+ }
+ }
+
+ /* link for data directory */
+ std::string storagePath = m_context.locations->getPrivateStorageDir();
+ std::string dataDir = m_context.locations->getPackageInstallationDir() +
+ "/" + WrtDB::GlobalConfig::GetWidgetPrivateStoragePath();
+
+ if (symlink(storagePath.c_str(), dataDir.c_str()) != 0)
+ {
+ int error = errno;
+ if (error)
+ LogPedantic("Failed to make a symbolic name for a file "
+ << "[" << DPL::GetErrnoString(error) << "]");
+ ThrowMsg(Exceptions::FileOperationFailed,
+ "Symbolic link creating is not done.");
+ }
+ changeOwnerForDirectory(dataDir);
+ }
+}
+
void TaskFileManipulation::StepAbortRenamePath()
{
LogDebug("[Rename Widget Path] Aborting.... (Rename path)");
void StepCreatePrivateStorageDir();
void StepAbortRenamePath();
+ void StepLinkForPreload();
// install external location
void StepPrepareExternalDir();
LogDebug("Commiting manifest file : " << manifest_file);
std::ostringstream destFile;
- destFile << "/opt/share/packages" << "/"; //TODO constant with path
+ if (m_context.job->getInstallerStruct().m_installMode
+ == InstallMode::INSTALL_MODE_PRELOAD)
+ {
+ destFile << "/usr/share/packages" << "/"; //TODO constant with path
+ } else {
+ destFile << "/opt/share/packages" << "/"; //TODO constant with path
+ }
destFile << DPL::ToUTF8String(manifest_name);
LogInfo("cp " << manifest_file << " " << destFile.str());
namespace { //anonymous
const char* REG_TIZEN_PKGID_PATTERN = "^[a-zA-Z0-9]{10}$";
const int PKGID_LENTH = 10;
+const std::string PRELOAD_INSTALLED_PATH = "/usr/apps";
bool checkDirectoryExist(const std::string& pkgId)
{
}
return false;
}
+}
+
+namespace Jobs {
+namespace WidgetUninstall {
class UninstallerTaskFail :
public DPL::TaskDecl<UninstallerTaskFail>
{
private:
- bool m_uninstalled;
+ WidgetStatus m_status;
void StepFail()
{
- if (m_uninstalled) {
+ if (WidgetStatus::NOT_INSTALLED == m_status) {
ThrowMsg(Jobs::WidgetUninstall::Exceptions::WidgetNotExist,
"Widget does not exist");
+ } else if (WidgetStatus::PREALOAD == m_status) {
+ ThrowMsg(Jobs::WidgetUninstall::Exceptions::Unremovable,
+ "Widget cann't uninstall");
} else {
Throw(Jobs::WidgetUninstall::Exceptions::Base);
}
}
public:
- UninstallerTaskFail(bool uninstalled) :
+ UninstallerTaskFail(WidgetStatus status) :
DPL::TaskDecl<UninstallerTaskFail>(this),
- m_uninstalled(uninstalled)
+ m_status(status)
+
{
AddStep(&UninstallerTaskFail::StepFail);
}
};
-}
-namespace Jobs {
-namespace WidgetUninstall {
JobWidgetUninstall::JobWidgetUninstall(
const std::string & tizenAppId,
const WidgetUninstallationStruct &
PKGMGR_START_KEY,
PKGMGR_START_UNINSTALL);
}
- } else if (WidgetStatus::NOT_INSTALLED == status) {
- AddTask(new UninstallerTaskFail(true));
+ } else if (WidgetStatus::NOT_INSTALLED == status ||
+ WidgetStatus::PREALOAD == status) {
+ AddTask(new UninstallerTaskFail(status));
} else if (WidgetStatus::ABNORMAL == status) {
m_context.locations = WidgetLocation(m_context.tzPkgid);
m_context.removeAbnormal = true;
AddTask(new TaskRemoveFiles(m_context));
} else {
- AddTask(new UninstallerTaskFail(false));
+ AddTask(new UninstallerTaskFail(WidgetStatus::UNRECOGNIZED));
}
} Catch(WidgetDAOReadOnly::Exception::Base) {
- AddTask(new UninstallerTaskFail(false));
+ AddTask(new UninstallerTaskFail(WidgetStatus::UNRECOGNIZED));
}
}
-JobWidgetUninstall::WidgetStatus JobWidgetUninstall::getWidgetStatus(const std::string &id)
+WidgetStatus JobWidgetUninstall::getWidgetStatus(const std::string &id)
{
regex_t regx;
if(regcomp(®x, REG_TIZEN_PKGID_PATTERN, REG_NOSUB | REG_EXTENDED)!=0){
LogDebug("Regcomp failed");
}
std::string pkgId;
+ std::string installPath;
Try {
if ((regexec(®x, id.c_str(),
DPL::FromUTF8String(id));
LogDebug("Get appid from pkgid : " << appid);
m_context.tzAppid = DPL::ToUTF8String(appid);
+ WrtDB::WidgetDAOReadOnly dao(appid);
+ installPath = DPL::ToUTF8String(*dao.getWidgetInstalledPath());
} else {
pkgId = id.substr(0, PKGID_LENTH);
WrtDB::WidgetDAOReadOnly dao(DPL::FromUTF8String(id));
m_context.tzAppid = id;
+ installPath = DPL::ToUTF8String(*dao.getWidgetInstalledPath());
+ }
+
+ if (0 == installPath.compare(0, PRELOAD_INSTALLED_PATH.length(),
+ PRELOAD_INSTALLED_PATH)) {
+ LogError("This widget is prealoaded. So it cann't be removed");
+ return WidgetStatus::PREALOAD;
}
} Catch(WidgetDAOReadOnly::Exception::WidgetNotExist) {
LogDebug("package id : " << pkgId);
namespace Jobs {
namespace WidgetUninstall {
+
+enum class WidgetStatus
+{
+ Ok, NOT_INSTALLED, PREALOAD, ABNORMAL, UNRECOGNIZED
+};
+
class JobWidgetUninstall :
public Job,
public JobProgressBase<UninstallerContext::UninstallStep,
bool getRemoveStartedFlag() const;
bool getRemoveFinishedFlag() const;
- enum class WidgetStatus
- {
- Ok, NOT_INSTALLED, ABNORMAL
- };
-
WidgetStatus getWidgetStatus(const std::string &appId);
void SendProgress();
#include <widget_uninstall/task_remove_files.h>
#include <widget_uninstall/job_widget_uninstall.h>
#include <widget_uninstall/uninstaller_context.h>
+#include <widget_uninstall/widget_uninstall_errors.h>
#include <dpl/wrt-dao-rw/widget_dao.h>
#include <dpl/wrt-dao-ro/widget_config.h>
#include <dpl/wrt-dao-ro/vconf_config.h>
#include <dpl/assert.h>
+#include <dpl/exception.h>
#include <dpl/utils/wrt_utility.h>
#include <ail.h>
#include <pkgmgr/pkgmgr_parser.h>
void TaskRemoveFiles::StepRemoveInstallationDirectory()
{
LogInfo("StepRemoveInstallationDirectory started");
- if (APP2EXT_SD_CARD !=
- app2ext_get_app_location(m_context.tzPkgid.c_str()))
- {
- LogDebug("Removing directory");
- m_context.removeStarted = true;
- std::string widgetDir =
- m_context.locations->getPackageInstallationDir();
- if (!WrtUtilRemove(widgetDir)) {
- LogWarning("Removing widget installation directory failed");
- }
- std::string dataDir = m_context.locations->getUserDataRootDir();
- if (!WrtUtilRemove(dataDir)) {
- LogWarning(dataDir + " is already removed");
- }
- } else {
- LogDebug("Removing sdcard directory");
- Try {
- WidgetInstallToExtSingleton::Instance().initialize(m_context.tzPkgid);
- WidgetInstallToExtSingleton::Instance().uninstallation();
- WidgetInstallToExtSingleton::Instance().deinitialize();
- }
- Catch(WidgetInstallToExt::Exception::ErrorInstallToExt)
+ Try {
+ if (APP2EXT_SD_CARD !=
+ app2ext_get_app_location(m_context.tzPkgid.c_str()))
{
- Throw(Jobs::WidgetUninstall::TaskRemoveFiles::Exception::
- RemoveFilesFailed);
+ LogDebug("Removing directory");
+ m_context.removeStarted = true;
+ std::string widgetDir =
+ m_context.locations->getPackageInstallationDir();
+ if (!WrtUtilRemove(widgetDir)) {
+ LogError("Removing widget installation directory failed");
+ }
+ std::string dataDir = m_context.locations->getUserDataRootDir();
+ if (!WrtUtilRemove(dataDir)) {
+ LogWarning(dataDir + " is already removed");
+ }
+ } else {
+ LogDebug("Removing sdcard directory");
+ Try {
+ WidgetInstallToExtSingleton::Instance().initialize(m_context.tzPkgid);
+ WidgetInstallToExtSingleton::Instance().uninstallation();
+ WidgetInstallToExtSingleton::Instance().deinitialize();
+ }
+ Catch(WidgetInstallToExt::Exception::ErrorInstallToExt)
+ {
+ Throw(Jobs::WidgetUninstall::TaskRemoveFiles::Exception::
+ RemoveFilesFailed);
+ }
}
+ } Catch(Exception::RemoveFilesFailed) {
+ ThrowMsg(Exceptions::RemoveFileFailure, "Cann't remove directory");
+
}
m_context.job->UpdateProgress(
UninstallerContext::UNINSTALL_REMOVE_WIDGETDIR,
DECLARE_JOB_EXCEPTION(Base, UninstallOspSvcFailed,
ErrorWidgetUninstallationFailed)
DECLARE_JOB_EXCEPTION(Base, PlatformAPIFailure, ErrorWidgetUninstallationFailed)
+DECLARE_JOB_EXCEPTION(Base, RemoveFileFailure, ErrorWidgetUninstallationFailed)
+DECLARE_JOB_EXCEPTION(Base, Unremovable, ErrorWidgetUninstallationFailed)
} //namespace
} //namespace
} //namespace
static int s_plugin_install_lock_fd = -1;
-bool lockPluginInstallation()
+bool lockPluginInstallation(bool isPreload)
{
+ if (isPreload) {
+ fprintf(stderr, "Skip create lock file.. \n");
+ return true;
+ }
+
int ret = 0;
LogInfo("Try to lock for plugins installation.");
return true;
}
-bool unlockPluginInstallation()
+bool unlockPluginInstallation(bool isPreload)
{
LogInfo("Unlock for plugins installation.");
+ if (isPreload) {
+ fprintf(stderr, "Skip plugin unlock.. \n");
+ return true;
+ }
if (s_plugin_install_lock_fd != -1) {
int ret = 0;
};
};
-bool lockPluginInstallation();
-bool unlockPluginInstallation();
+bool lockPluginInstallation(bool isPreload);
+bool unlockPluginInstallation(bool isPreload);
bool checkPluginInstallationRequired();
bool removeInstallationRequiredFlag();
FileState::Type checkFile(const std::string& filename);
#include <dpl/copy.h>
#include <dpl/errno_string.h>
#include <dpl/utils/wrt_global_settings.h>
+#include <dpl/utils/wrt_utility.h>
#include <parser_runner.h>
#include <widget_parser.h>
#include <root_parser.h>
if (m_argc != 2) {
return showHelpAndQuit();
}
+
if (!m_startupPluginInstallation) {
AddStep(&WrtInstaller::installPluginsStep);
} else {
m_installMode = WRT_INSTALL_MODE_INSTALL_WGT;
}
m_packagePath = m_argv[2];
+
AddStep(&WrtInstaller::installStep);
- } else if (arg == "-il" || arg == "--install-preload") {
+ } else if (arg == "-ip" || arg == "--install-preload") {
+ LogDebug("Install preload web app");
if (m_argc != 3) {
return showHelpAndQuit();
}
void WrtInstaller::OnTerminate()
{
LogDebug("Wrt Shutdown now");
- PluginUtils::unlockPluginInstallation();
+ PluginUtils::unlockPluginInstallation(m_installMode ==
+ WRT_INSTALL_MODE_INSTALL_PRELOAD);
if (m_initialized) {
wrt_installer_shutdown();
}
if (m_startupPluginInstallation) {
LogInfo("Plugin installation started because new plugin package found");
- } else if (!PluginUtils::lockPluginInstallation()) {
+ } else if (!PluginUtils::lockPluginInstallation(m_installMode ==
+ WRT_INSTALL_MODE_INSTALL_PRELOAD)) {
LogError("Failed to open plugin installation lock file"
" Plugins are currently installed by other process");
staticWrtPluginInstallationCallback(WRT_INSTALLER_ERROR_PLUGIN_INSTALLATION_FAILED,
This->m_returnStatus = 0;
resultMsg += L" : " + DPL::FromUTF8String(PKGMGR_END_SUCCESS);
+ if (This->m_installMode == WRT_INSTALL_MODE_INSTALL_PRELOAD &&
+ !This->m_packagePath.empty()) {
+ LogDebug("This widget is preloaded so it will be removed : "
+ << This->m_packagePath);
+ if (!WrtUtilRemove(This->m_packagePath)) {
+ LogError("Failed to remove " << This->m_packagePath);
+ }
+ }
+
This->DPL::Event::ControllerEventHandler<WRTInstallerNS::
NextStepEvent>
::PostEvent(WRTInstallerNS::NextStepEvent());
}
//remove lock file
- if (!PluginUtils::unlockPluginInstallation()) {
+ if (!PluginUtils::unlockPluginInstallation(This->m_installMode ==
+ WRT_INSTALL_MODE_INSTALL_PRELOAD)) {
LogInfo("Failed to remove installation lock");
}
{
LogDebug("Install new plugins");
- if (!PluginUtils::lockPluginInstallation()) {
+ if (!PluginUtils::lockPluginInstallation(m_installMode ==
+ WRT_INSTALL_MODE_INSTALL_PRELOAD)) {
LogInfo("Lock NOT created");
return;
}
if (!PluginUtils::checkPluginInstallationRequired()) {
LogDebug("Plugin installation not required");
- PluginUtils::unlockPluginInstallation();
+ PluginUtils::unlockPluginInstallation(m_installMode ==
+ WRT_INSTALL_MODE_INSTALL_PRELOAD);
return;
}
{
UNHANDLED_EXCEPTION_HANDLER_BEGIN
{
+ if ( WRT_INSTALL_MODE_INSTALL_PRELOAD == installMode) {
+ DPL::Log::OldStyleLogProvider *oldStyleProvider =
+ new DPL::Log::OldStyleLogProvider(false, false, false, true,
+ false, true);
+ DPL::Log::LogSystemSingleton::Instance().AddProvider(oldStyleProvider);
+ }
+
LogInfo("[WRT-API] INSTALL WIDGET: " << path);
// Post installation event
CONTROLLER_POST_EVENT(