diff options
author | wolfbeast <mcwerewolf@gmail.com> | 2018-05-14 10:50:01 +0200 |
---|---|---|
committer | wolfbeast <mcwerewolf@gmail.com> | 2018-05-14 10:50:01 +0200 |
commit | e9dd029f5d00590e1a53e63b0ab805110a10b54c (patch) | |
tree | 1126ca5dda925a62be3dc12c99c90e953d08afcf /toolkit/mozapps/update/updater | |
parent | 9d6a7ae25d7f5da855a8f8df884de483b4e2a538 (diff) | |
parent | 36b8fd734f590eb726ca2e50f8d1ff9cc968b8e1 (diff) | |
download | UXP-e9dd029f5d00590e1a53e63b0ab805110a10b54c.tar UXP-e9dd029f5d00590e1a53e63b0ab805110a10b54c.tar.gz UXP-e9dd029f5d00590e1a53e63b0ab805110a10b54c.tar.lz UXP-e9dd029f5d00590e1a53e63b0ab805110a10b54c.tar.xz UXP-e9dd029f5d00590e1a53e63b0ab805110a10b54c.zip |
Merge branch 'master' into Basilisk-release
Diffstat (limited to 'toolkit/mozapps/update/updater')
-rw-r--r-- | toolkit/mozapps/update/updater/automounter_gonk.cpp | 251 | ||||
-rw-r--r-- | toolkit/mozapps/update/updater/automounter_gonk.h | 48 | ||||
-rw-r--r-- | toolkit/mozapps/update/updater/progressui_gonk.cpp | 53 | ||||
-rw-r--r-- | toolkit/mozapps/update/updater/updater-common.build | 11 | ||||
-rw-r--r-- | toolkit/mozapps/update/updater/updater.cpp | 137 |
5 files changed, 3 insertions, 497 deletions
diff --git a/toolkit/mozapps/update/updater/automounter_gonk.cpp b/toolkit/mozapps/update/updater/automounter_gonk.cpp deleted file mode 100644 index 3dff2a133..000000000 --- a/toolkit/mozapps/update/updater/automounter_gonk.cpp +++ /dev/null @@ -1,251 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* vim:set ts=2 sw=2 sts=2 et cindent: */ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ - -#include <android/log.h> -#include <cutils/android_reboot.h> -#include <errno.h> -#include <stdlib.h> -#include <sys/mount.h> -#include <sys/reboot.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <fcntl.h> -#include <unistd.h> - -#include "automounter_gonk.h" -#include "updatedefines.h" -#include "updatelogging.h" - -#define LOG_TAG "GonkAutoMounter" - -#define GONK_LOG(level, format, ...) \ - LOG((LOG_TAG ": " format "\n", ##__VA_ARGS__)); \ - __android_log_print(level, LOG_TAG, format, ##__VA_ARGS__) - -#define LOGI(format, ...) GONK_LOG(ANDROID_LOG_INFO, format, ##__VA_ARGS__) -#define LOGE(format, ...) GONK_LOG(ANDROID_LOG_ERROR, format, ##__VA_ARGS__) - -const char *kGonkMountsPath = "/proc/mounts"; -const char *kGonkSystemPath = "/system"; - -GonkAutoMounter::GonkAutoMounter() : mDevice(nullptr), mAccess(Unknown) -{ - if (!RemountSystem(ReadWrite)) { - LOGE("Could not remount %s as read-write.", kGonkSystemPath); - } -} - -GonkAutoMounter::~GonkAutoMounter() -{ - bool result = RemountSystem(ReadOnly); - free(mDevice); - - if (!result) { - // Don't take any chances when remounting as read-only fails, just reboot. - Reboot(); - } -} - -void -GonkAutoMounter::Reboot() -{ - // The android_reboot wrapper provides more safety, doing fancier read-only - // remounting and attempting to sync() the filesystem first. If this fails - // our only hope is to force a reboot directly without these protections. - // For more, see system/core/libcutils/android_reboot.c - LOGE("Could not remount %s as read-only, forcing a system reboot.", - kGonkSystemPath); - LogFlush(); - - if (android_reboot(ANDROID_RB_RESTART, 0, nullptr) != 0) { - LOGE("Safe system reboot failed, attempting to force"); - LogFlush(); - - if (reboot(RB_AUTOBOOT) != 0) { - LOGE("CRITICAL: Failed to force restart"); - } - } -} - -static const char * -MountAccessToString(MountAccess access) -{ - switch (access) { - case ReadOnly: return "read-only"; - case ReadWrite: return "read-write"; - default: return "unknown"; - } -} - -bool -GonkAutoMounter::RemountSystem(MountAccess access) -{ - if (!UpdateMountStatus()) { - return false; - } - - if (mAccess == access) { - return true; - } - - unsigned long flags = MS_REMOUNT; - if (access == ReadOnly) { - flags |= MS_RDONLY; - // Give the system a chance to flush file buffers - sync(); - } - - if (!MountSystem(flags)) { - return false; - } - - // Check status again to verify /system has been properly remounted - if (!UpdateMountStatus()) { - return false; - } - - if (mAccess != access) { - LOGE("Updated mount status %s should be %s", - MountAccessToString(mAccess), - MountAccessToString(access)); - return false; - } - - return true; -} - -bool -GonkAutoMounter::UpdateMountStatus() -{ - FILE *mountsFile = NS_tfopen(kGonkMountsPath, "r"); - - if (mountsFile == nullptr) { - LOGE("Error opening %s: %s", kGonkMountsPath, strerror(errno)); - return false; - } - - // /proc/mounts returns a 0 size from fstat, so we use the same - // pre-allocated buffer size that ADB does here - const int mountsMaxSize = 4096; - char mountData[mountsMaxSize]; - size_t read = fread(mountData, 1, mountsMaxSize - 1, mountsFile); - mountData[read + 1] = '\0'; - - if (ferror(mountsFile)) { - LOGE("Error reading %s, %s", kGonkMountsPath, strerror(errno)); - fclose(mountsFile); - return false; - } - - char *token, *tokenContext; - bool foundSystem = false; - - for (token = strtok_r(mountData, "\n", &tokenContext); - token; - token = strtok_r(nullptr, "\n", &tokenContext)) - { - if (ProcessMount(token)) { - foundSystem = true; - break; - } - } - - fclose(mountsFile); - - if (!foundSystem) { - LOGE("Couldn't find %s mount in %s", kGonkSystemPath, kGonkMountsPath); - } - return foundSystem; -} - -bool -GonkAutoMounter::ProcessMount(const char *mount) -{ - const int strSize = 256; - char mountDev[strSize]; - char mountDir[strSize]; - char mountAccess[strSize]; - - int rv = sscanf(mount, "%255s %255s %*s %255s %*d %*d\n", - mountDev, mountDir, mountAccess); - mountDev[strSize - 1] = '\0'; - mountDir[strSize - 1] = '\0'; - mountAccess[strSize - 1] = '\0'; - - if (rv != 3) { - return false; - } - - if (strcmp(kGonkSystemPath, mountDir) != 0) { - return false; - } - - free(mDevice); - mDevice = strdup(mountDev); - mAccess = Unknown; - - char *option, *optionContext; - for (option = strtok_r(mountAccess, ",", &optionContext); - option; - option = strtok_r(nullptr, ",", &optionContext)) - { - if (strcmp("ro", option) == 0) { - mAccess = ReadOnly; - break; - } else if (strcmp("rw", option) == 0) { - mAccess = ReadWrite; - break; - } - } - - return true; -} - -/* - * Mark the given block device as read-write or read-only, using the BLKROSET - * ioctl. - */ -static void SetBlockReadWriteStatus(const char *blockdev, bool setReadOnly) { - int fd; - int roMode = setReadOnly ? 1 : 0; - - fd = open(blockdev, O_RDONLY); - if (fd < 0) { - return; - } - - if (ioctl(fd, BLKROSET, &roMode) == -1) { - LOGE("Error setting read-only mode on %s to %s: %s", blockdev, - setReadOnly ? "true": "false", strerror(errno)); - } - close(fd); -} - - -bool -GonkAutoMounter::MountSystem(unsigned long flags) -{ - if (!mDevice) { - LOGE("No device was found for %s", kGonkSystemPath); - return false; - } - - // Without setting the block device ro mode to false, we get a permission - // denied error while trying to remount it in read-write. - SetBlockReadWriteStatus(mDevice, (flags & MS_RDONLY)); - - const char *readOnly = flags & MS_RDONLY ? "read-only" : "read-write"; - int result = mount(mDevice, kGonkSystemPath, "none", flags, nullptr); - - if (result != 0) { - LOGE("Error mounting %s as %s: %s", kGonkSystemPath, readOnly, - strerror(errno)); - return false; - } - - LOGI("Mounted %s partition as %s", kGonkSystemPath, readOnly); - return true; -} diff --git a/toolkit/mozapps/update/updater/automounter_gonk.h b/toolkit/mozapps/update/updater/automounter_gonk.h deleted file mode 100644 index e40cacbc2..000000000 --- a/toolkit/mozapps/update/updater/automounter_gonk.h +++ /dev/null @@ -1,48 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* vim:set ts=2 sw=2 sts=2 et cindent: */ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ - -#ifndef AUTOMOUNTER_GONK_H__ -#define AUTOMOUNTER_GONK_H__ - -typedef enum { - ReadOnly, - ReadWrite, - Unknown -} MountAccess; - -/** - * This class will remount the /system partition as read-write in Gonk to allow - * the updater write access. Upon destruction, /system will be remounted back to - * read-only. If something causes /system to remain read-write, this class will - * reboot the device and allow the system to mount as read-only. - * - * Code inspired from AOSP system/core/adb/remount_service.c - */ -class GonkAutoMounter -{ -public: - GonkAutoMounter(); - ~GonkAutoMounter(); - - MountAccess GetAccess() const - { - return mAccess; - } - -private: - bool RemountSystem(MountAccess access); - bool ForceRemountReadOnly(); - bool UpdateMountStatus(); - bool ProcessMount(const char *mount); - bool MountSystem(unsigned long flags); - void Reboot(); - -private: - char *mDevice; - MountAccess mAccess; -}; - -#endif // AUTOMOUNTER_GONK_H__ diff --git a/toolkit/mozapps/update/updater/progressui_gonk.cpp b/toolkit/mozapps/update/updater/progressui_gonk.cpp deleted file mode 100644 index f77d0af63..000000000 --- a/toolkit/mozapps/update/updater/progressui_gonk.cpp +++ /dev/null @@ -1,53 +0,0 @@ -/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- - * vim: sw=2 ts=8 et : - */ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this file, - * You can obtain one at http://mozilla.org/MPL/2.0/. */ - -#include <assert.h> -#include <stdio.h> - -#include <string> - -#include "android/log.h" - -#include "progressui.h" - -#define LOG(args...) __android_log_print(ANDROID_LOG_INFO, "GeckoUpdater" , ## args) - -using namespace std; - -int InitProgressUI(int *argc, char ***argv) -{ - return 0; -} - -int ShowProgressUI() -{ - LOG("Starting to apply update ...\n"); - return 0; -} - -void QuitProgressUI() -{ - LOG("Finished applying update\n"); -} - -void UpdateProgressUI(float progress) -{ - assert(0.0f <= progress && progress <= 100.0f); - - static const size_t kProgressBarLength = 50; - static size_t sLastNumBars; - size_t numBars = size_t(float(kProgressBarLength) * progress / 100.0f); - if (numBars == sLastNumBars) { - return; - } - sLastNumBars = numBars; - - size_t numSpaces = kProgressBarLength - numBars; - string bars(numBars, '='); - string spaces(numSpaces, ' '); - LOG("Progress [ %s%s ]\n", bars.c_str(), spaces.c_str()); -} diff --git a/toolkit/mozapps/update/updater/updater-common.build b/toolkit/mozapps/update/updater/updater-common.build index 02b7338bc..6444df8d9 100644 --- a/toolkit/mozapps/update/updater/updater-common.build +++ b/toolkit/mozapps/update/updater/updater-common.build @@ -90,17 +90,6 @@ if CONFIG['MOZ_WIDGET_TOOLKIT'] == 'cocoa': LOCAL_INCLUDES += [ '/toolkit/xre', ] -elif CONFIG['MOZ_WIDGET_TOOLKIT'] == 'gonk': - have_progressui = 1 - srcs += [ - 'automounter_gonk.cpp', - 'progressui_gonk.cpp', - ] - DISABLE_STL_WRAPPING = True - OS_LIBS += [ - 'cutils', - 'sysutils', - ] if have_progressui == 0: srcs += [ diff --git a/toolkit/mozapps/update/updater/updater.cpp b/toolkit/mozapps/update/updater/updater.cpp index 63a92c084..dbf50329c 100644 --- a/toolkit/mozapps/update/updater/updater.cpp +++ b/toolkit/mozapps/update/updater/updater.cpp @@ -110,33 +110,10 @@ struct UpdateServerThreadArgs #define USE_EXECV #endif -#if defined(MOZ_WIDGET_GONK) -# include "automounter_gonk.h" -# include <unistd.h> -# include <android/log.h> -# include <linux/ioprio.h> -# include <sys/resource.h> - -#if ANDROID_VERSION < 21 -// The only header file in bionic which has a function prototype for ioprio_set -// is libc/include/sys/linux-unistd.h. However, linux-unistd.h conflicts -// badly with unistd.h, so we declare the prototype for ioprio_set directly. -extern "C" MOZ_EXPORT int ioprio_set(int which, int who, int ioprio); -#else -# include <sys/syscall.h> -static int ioprio_set(int which, int who, int ioprio) { - return syscall(__NR_ioprio_set, which, who, ioprio); -} -#endif - -# define MAYBE_USE_HARD_LINKS 1 -static bool sUseHardLinks = true; -#else # define MAYBE_USE_HARD_LINKS 0 -#endif #if defined(MOZ_VERIFY_MAR_SIGNATURE) && !defined(XP_WIN) && \ - !defined(XP_MACOSX) && !defined(MOZ_WIDGET_GONK) + !defined(XP_MACOSX) #include "nss.h" #include "prerror.h" #endif @@ -2495,44 +2472,9 @@ ReadMARChannelIDs(const NS_tchar *path, MARChannelStringTable *results) static int GetUpdateFileName(NS_tchar *fileName, int maxChars) { -#if defined(MOZ_WIDGET_GONK) - // If an update.link file exists, then it will contain the name - // of the update file (terminated by a newline). - - NS_tchar linkFileName[MAXPATHLEN]; - NS_tsnprintf(linkFileName, sizeof(linkFileName)/sizeof(linkFileName[0]), - NS_T("%s/update.link"), gPatchDirPath); - AutoFile linkFile(NS_tfopen(linkFileName, NS_T("rb"))); - if (linkFile == nullptr) { - NS_tsnprintf(fileName, maxChars, - NS_T("%s/update.mar"), gPatchDirPath); - return OK; - } - - char dataFileName[MAXPATHLEN]; - size_t bytesRead; - - if ((bytesRead = fread(dataFileName, 1, sizeof(dataFileName)-1, linkFile)) <= 0) { - *fileName = NS_T('\0'); - return READ_ERROR; - } - if (dataFileName[bytesRead-1] == '\n') { - // Strip trailing newline (for \n and \r\n) - bytesRead--; - } - if (dataFileName[bytesRead-1] == '\r') { - // Strip trailing CR (for \r, \r\n) - bytesRead--; - } - dataFileName[bytesRead] = '\0'; - - strncpy(fileName, dataFileName, maxChars-1); - fileName[maxChars-1] = '\0'; -#else - // We currently only support update.link files under GONK + // We currently don't support update.link files NS_tsnprintf(fileName, maxChars, NS_T("%s/update.mar"), gPatchDirPath); -#endif return OK; } @@ -2776,26 +2718,8 @@ int NS_main(int argc, NS_tchar **argv) } #endif -#if defined(MOZ_WIDGET_GONK) - if (EnvHasValue("LD_PRELOAD")) { - // If the updater is launched with LD_PRELOAD set, then we wind up - // preloading libmozglue.so. Under some circumstances, this can cause - // the remount of /system to fail when going from rw to ro, so if we - // detect LD_PRELOAD we unsetenv it and relaunch ourselves without it. - // This will cause the offending preloaded library to be closed. - // - // For a variety of reasons, this is really hard to do in a safe manner - // in the parent process, so we do it here. - unsetenv("LD_PRELOAD"); - execv(argv[0], argv); - __android_log_print(ANDROID_LOG_INFO, "updater", - "execve failed: errno: %d. Exiting...", errno); - _exit(1); - } -#endif - #if defined(MOZ_VERIFY_MAR_SIGNATURE) && !defined(XP_WIN) && \ - !defined(XP_MACOSX) && !defined(MOZ_WIDGET_GONK) + !defined(XP_MACOSX) // On Windows and Mac we rely on native APIs to do verifications so we don't // need to initialize NSS at all there. // Otherwise, minimize the amount of NSS we depend on by avoiding all the NSS @@ -3085,36 +3009,6 @@ int NS_main(int argc, NS_tchar **argv) } #endif -#ifdef MOZ_WIDGET_GONK - const char *prioEnv = getenv("MOZ_UPDATER_PRIO"); - if (prioEnv) { - int32_t prioVal; - int32_t oomScoreAdj; - int32_t ioprioClass; - int32_t ioprioLevel; - if (sscanf(prioEnv, "%d/%d/%d/%d", - &prioVal, &oomScoreAdj, &ioprioClass, &ioprioLevel) == 4) { - LOG(("MOZ_UPDATER_PRIO=%s", prioEnv)); - if (setpriority(PRIO_PROCESS, 0, prioVal)) { - LOG(("setpriority(%d) failed, errno = %d", prioVal, errno)); - } - if (ioprio_set(IOPRIO_WHO_PROCESS, 0, - IOPRIO_PRIO_VALUE(ioprioClass, ioprioLevel))) { - LOG(("ioprio_set(%d,%d) failed: errno = %d", - ioprioClass, ioprioLevel, errno)); - } - FILE *fs = fopen("/proc/self/oom_score_adj", "w"); - if (fs) { - fprintf(fs, "%d", oomScoreAdj); - fclose(fs); - } else { - LOG(("Unable to open /proc/self/oom_score_adj for writing, errno = %d", - errno)); - } - } - } -#endif - #ifdef XP_WIN if (pid > 0) { HANDLE parent = OpenProcess(SYNCHRONIZE, false, (DWORD) pid); @@ -3439,27 +3333,6 @@ int NS_main(int argc, NS_tchar **argv) } #endif -#if defined(MOZ_WIDGET_GONK) - // In gonk, the master b2g process sets its umask to 0027 because - // there's no reason for it to ever create world-readable files. - // The updater binary, however, needs to do this, and it inherits - // the master process's cautious umask. So we drop down a bit here. - umask(0022); - - // Remount the /system partition as read-write for gonk. The destructor will - // remount /system as read-only. We add an extra level of scope here to avoid - // calling LogFinish() before the GonkAutoMounter destructor has a chance - // to be called - { -#if !defined(TEST_UPDATER) - GonkAutoMounter mounter; - if (mounter.GetAccess() != MountAccess::ReadWrite) { - WriteStatusFile(FILESYSTEM_MOUNT_READWRITE_ERROR); - return 1; - } -#endif -#endif - if (sStagedUpdate) { // When staging updates, blow away the old installation directory and create // it from scratch. @@ -3759,10 +3632,6 @@ int NS_main(int argc, NS_tchar **argv) } #endif /* XP_WIN */ -#if defined(MOZ_WIDGET_GONK) - } // end the extra level of scope for the GonkAutoMounter -#endif - #ifdef XP_MACOSX // When the update is successful remove the precomplete file in the root of // the application bundle and move the distribution directory from |