summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEthan Yonker <dees_troy@teamw.in>2016-01-28 21:03:33 +0100
committerDees Troy <dees_troy@teamw.in>2016-01-29 21:58:33 +0100
commitb5fab76bea98dff8d0825d16c3dd359397449e9a (patch)
treea92cf2c085a22c8f246543f558619edd5fd3367e
parentadds TW_ADDITIONAL_RES to TW_RES (diff)
downloadandroid_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar.gz
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar.bz2
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar.lz
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar.xz
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.tar.zst
android_bootable_recovery-b5fab76bea98dff8d0825d16c3dd359397449e9a.zip
-rw-r--r--Android.mk3
-rw-r--r--fixContexts.cpp163
-rw-r--r--fixContexts.hpp35
-rw-r--r--fixPermissions.cpp548
-rw-r--r--fixPermissions.hpp52
-rw-r--r--gui/action.cpp14
-rw-r--r--gui/objects.hpp1
-rwxr-xr-xgui/theme/common/landscape.xml29
-rwxr-xr-xgui/theme/common/languages/en.xml20
-rwxr-xr-xgui/theme/common/portrait.xml29
-rwxr-xr-xgui/theme/common/watch.xml29
-rw-r--r--openrecoveryscript.cpp4
-rw-r--r--partition.cpp1
-rw-r--r--partitionmanager.cpp33
-rw-r--r--partitions.hpp2
-rw-r--r--prebuilt/Android.mk9
16 files changed, 274 insertions, 698 deletions
diff --git a/Android.mk b/Android.mk
index 47c30c425..52c2907de 100644
--- a/Android.mk
+++ b/Android.mk
@@ -42,7 +42,7 @@ TARGET_RECOVERY_GUI := true
LOCAL_SRC_FILES := \
twrp.cpp \
- fixPermissions.cpp \
+ fixContexts.cpp \
twrpTar.cpp \
twrpDU.cpp \
twrpDigest.cpp \
@@ -342,7 +342,6 @@ LOCAL_ADDITIONAL_DEPENDENCIES := \
dump_image \
erase_image \
flash_image \
- fix_permissions.sh \
mke2fs.conf \
pigz \
teamwin \
diff --git a/fixContexts.cpp b/fixContexts.cpp
new file mode 100644
index 000000000..64429446e
--- /dev/null
+++ b/fixContexts.cpp
@@ -0,0 +1,163 @@
+/*
+ Copyright 2012-2016 bigbiff/Dees_Troy TeamWin
+ This file is part of TWRP/TeamWin Recovery Project.
+
+ TWRP is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ TWRP is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with TWRP. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <string>
+#include <unistd.h>
+#include <sys/stat.h>
+#include <dirent.h>
+#include <errno.h>
+#include <cctype>
+#include "fixContexts.hpp"
+#include "twrp-functions.hpp"
+#include "twcommon.h"
+#ifdef HAVE_SELINUX
+#include "selinux/selinux.h"
+#include "selinux/label.h"
+#include "selinux/android.h"
+#include "selinux/label.h"
+#endif
+
+using namespace std;
+
+#ifdef HAVE_SELINUX
+struct selabel_handle *sehandle;
+struct selinux_opt selinux_options[] = {
+ { SELABEL_OPT_PATH, "/file_contexts" }
+};
+
+int fixContexts::restorecon(string entry, struct stat *sb) {
+ char *oldcontext, *newcontext;
+
+ if (lgetfilecon(entry.c_str(), &oldcontext) < 0) {
+ LOGINFO("Couldn't get selinux context for %s\n", entry.c_str());
+ return -1;
+ }
+ if (selabel_lookup(sehandle, &newcontext, entry.c_str(), sb->st_mode) < 0) {
+ LOGINFO("Couldn't lookup selinux context for %s\n", entry.c_str());
+ return -1;
+ }
+ if (strcmp(oldcontext, newcontext) != 0) {
+ LOGINFO("Relabeling %s from %s to %s\n", entry.c_str(), oldcontext, newcontext);
+ if (lsetfilecon(entry.c_str(), newcontext) < 0) {
+ LOGINFO("Couldn't label %s with %s: %s\n", entry.c_str(), newcontext, strerror(errno));
+ }
+ }
+ freecon(oldcontext);
+ freecon(newcontext);
+ return 0;
+}
+
+int fixContexts::fixContextsRecursively(string name, int level) {
+ DIR *d;
+ struct dirent *de;
+ struct stat sb;
+ string path;
+
+ if (!(d = opendir(name.c_str())))
+ return -1;
+ if (!(de = readdir(d)))
+ return -1;
+
+ do {
+ if (de->d_type == DT_DIR) {
+ if (strcmp(de->d_name, ".") == 0 || strcmp(de->d_name, "..") == 0)
+ continue;
+ path = name + "/" + de->d_name;
+ restorecon(path, &sb);
+ fixContextsRecursively(path, level + 1);
+ }
+ else {
+ path = name + "/" + de->d_name;
+ restorecon(path, &sb);
+ }
+ } while ((de = readdir(d)));
+ closedir(d);
+ return 0;
+}
+
+int fixContexts::fixDataMediaContexts(string Mount_Point) {
+ DIR *d;
+ struct dirent *de;
+ struct stat sb;
+
+ LOGINFO("Fixing media contexts on '%s'\n", Mount_Point.c_str());
+
+ sehandle = selabel_open(SELABEL_CTX_FILE, selinux_options, 1);
+ if (!sehandle) {
+ LOGINFO("Unable to open /file_contexts\n");
+ return 0;
+ }
+
+ if (TWFunc::Path_Exists(Mount_Point + "/media/0")) {
+ string dir = Mount_Point + "/media";
+ if (!(d = opendir(dir.c_str()))) {
+ LOGINFO("opendir failed (%s)\n", strerror(errno));
+ return -1;
+ }
+ if (!(de = readdir(d))) {
+ LOGINFO("readdir failed (%s)\n", strerror(errno));
+ closedir(d);
+ return -1;
+ }
+
+ do {
+ if (strcmp(de->d_name, ".") == 0 || strcmp(de->d_name, "..") == 0 || de->d_type != DT_DIR)
+ continue;
+ size_t len = strlen(de->d_name);
+ bool is_numeric = true;
+ char* folder_name = de->d_name;
+ for (size_t i = 0; i < len; i++) {
+ if (!isdigit(*folder_name)) {
+ is_numeric = false;
+ break;
+ }
+ folder_name++;
+ }
+ if (is_numeric) {
+ dir = Mount_Point + "/media/";
+ dir += de->d_name;
+ restorecon(dir, &sb);
+ fixContextsRecursively(dir, 0);
+ }
+ } while ((de = readdir(d)));
+ closedir(d);
+ } else if (TWFunc::Path_Exists(Mount_Point + "/media")) {
+ restorecon(Mount_Point + "/media", &sb);
+ fixContextsRecursively(Mount_Point + "/media", 0);
+ } else {
+ LOGINFO("fixDataMediaContexts: %s/media does not exist!\n", Mount_Point.c_str());
+ return 0;
+ }
+ selabel_close(sehandle);
+ return 0;
+}
+
+#else
+
+int fixContexts::restorecon(string entry __unused, struct stat *sb __unused) {
+ return -1;
+}
+
+int fixContexts::fixContextsRecursively(string name __unused, int level __unused) {
+ return -1;
+}
+
+int fixContexts::fixDataMediaContexts(string Mount_Point __unused) {
+ return -1;
+}
+#endif
diff --git a/fixContexts.hpp b/fixContexts.hpp
new file mode 100644
index 000000000..e5e05dedf
--- /dev/null
+++ b/fixContexts.hpp
@@ -0,0 +1,35 @@
+/*
+ Copyright 2012-2016 bigbiff/Dees_Troy TeamWin
+ This file is part of TWRP/TeamWin Recovery Project.
+
+ TWRP is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ TWRP is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with TWRP. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef __FIXCONTEXTS_HPP
+#define __FIXCONTEXTS_HPP
+
+#include <string>
+
+using namespace std;
+
+class fixContexts {
+ public:
+ static int fixDataMediaContexts(string Mount_Point);
+
+ private:
+ static int restorecon(string entry, struct stat *sb);
+ static int fixContextsRecursively(string path, int level);
+};
+
+#endif
diff --git a/fixPermissions.cpp b/fixPermissions.cpp
deleted file mode 100644
index 0648eb69a..000000000
--- a/fixPermissions.cpp
+++ /dev/null
@@ -1,548 +0,0 @@
-/*
- Copyright 2012 bigbiff/Dees_Troy TeamWin
- This file is part of TWRP/TeamWin Recovery Project.
-
- TWRP is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- TWRP is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with TWRP. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include <iostream>
-#include <fstream>
-#include <sstream>
-#include <string>
-#include <vector>
-#include <string.h>
-#include <libgen.h>
-#include <unistd.h>
-#include <sys/stat.h>
-#include <dirent.h>
-#include <errno.h>
-#include "gui/rapidxml.hpp"
-#include "fixPermissions.hpp"
-#include "twrp-functions.hpp"
-#include "twcommon.h"
-#ifdef HAVE_SELINUX
-#include "selinux/selinux.h"
-#include "selinux/label.h"
-#include "selinux/android.h"
-#include "selinux/label.h"
-#endif
-
-using namespace std;
-using namespace rapidxml;
-
-static const mode_t kMode_0600 = 0600; // S_IRUSR | S_IWUSR
-static const mode_t kMode_0640 = 0640; // S_IRUSR | S_IWUSR | S_IRGRP
-static const mode_t kMode_0644 = 0644; // S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH
-static const mode_t kMode_0660 = 0660; // S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP
-static const mode_t kMode_0755 = 0755; // S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH
-static const mode_t kMode_0771 = 0771; // S_IRWXU | S_IRWXG | S_IXOTH
-
-fixPermissions::fixPermissions() : head(NULL) {
-}
-
-fixPermissions::~fixPermissions() {
- deletePackages();
-}
-
-#ifdef HAVE_SELINUX
-struct selabel_handle *sehandle;
-struct selinux_opt selinux_options[] = {
- { SELABEL_OPT_PATH, "/file_contexts" }
-};
-
-int fixPermissions::restorecon(string entry, struct stat *sb) {
- char *oldcontext, *newcontext;
-
- if (lgetfilecon(entry.c_str(), &oldcontext) < 0) {
- LOGINFO("Couldn't get selinux context for %s\n", entry.c_str());
- return -1;
- }
- if (selabel_lookup(sehandle, &newcontext, entry.c_str(), sb->st_mode) < 0) {
- LOGINFO("Couldn't lookup selinux context for %s\n", entry.c_str());
- return -1;
- }
- if (strcmp(oldcontext, newcontext) != 0) {
- LOGINFO("Relabeling %s from %s to %s\n", entry.c_str(), oldcontext, newcontext);
- if (lsetfilecon(entry.c_str(), newcontext) < 0) {
- LOGINFO("Couldn't label %s with %s: %s\n", entry.c_str(), newcontext, strerror(errno));
- }
- }
- freecon(oldcontext);
- freecon(newcontext);
- return 0;
-}
-
-int fixPermissions::fixDataDataContexts(void) {
- string dir = "/data/data/";
- sehandle = selabel_open(SELABEL_CTX_FILE, selinux_options, 1);
- if (!sehandle) {
- LOGINFO("Unable to open /file_contexts\n");
- return 0;
- }
- if (TWFunc::Path_Exists(dir)) {
- fixContextsRecursively(dir, 0);
- }
- selabel_close(sehandle);
- return 0;
-}
-
-int fixPermissions::fixContextsRecursively(string name, int level) {
- DIR *d;
- struct dirent *de;
- struct stat sb;
- string path;
-
- if (!(d = opendir(name.c_str())))
- return -1;
- if (!(de = readdir(d)))
- return -1;
-
- do {
- if (de->d_type == DT_DIR) {
- if (strcmp(de->d_name, ".") == 0 || strcmp(de->d_name, "..") == 0)
- continue;
- path = name + "/" + de->d_name;
- restorecon(path, &sb);
- fixContextsRecursively(path, level + 1);
- }
- else {
- path = name + "/" + de->d_name;
- restorecon(path, &sb);
- }
- } while ((de = readdir(d)));
- closedir(d);
- return 0;
-}
-
-int fixPermissions::fixDataInternalContexts(void) {
- DIR *d;
- struct dirent *de;
- struct stat sb;
- string dir, androiddir;
- sehandle = selabel_open(SELABEL_CTX_FILE, selinux_options, 1);
- if (!sehandle) {
- LOGINFO("Unable to open /file_contexts\n");
- return 0;
- }
- // TODO: what about /data/media/1 etc.?
- if (TWFunc::Path_Exists("/data/media/0"))
- dir = "/data/media/0";
- else
- dir = "/data/media";
- if (!TWFunc::Path_Exists(dir)) {
- LOGINFO("fixDataInternalContexts: '%s' does not exist!\n", dir.c_str());
- return 0;
- }
- LOGINFO("Fixing %s contexts\n", dir.c_str());
- restorecon(dir, &sb);
- d = opendir(dir.c_str());
-
- while (( de = readdir(d)) != NULL) {
- stat(de->d_name, &sb);
- string f;
- f = dir + "/" + de->d_name;
- restorecon(f, &sb);
- }
- closedir(d);
-
- androiddir = dir + "/Android/";
- if (TWFunc::Path_Exists(androiddir)) {
- fixContextsRecursively(androiddir, 0);
- }
- selabel_close(sehandle);
- return 0;
-}
-#endif
-
-int fixPermissions::fixPerms(bool enable_debug, bool remove_data_for_missing_apps) {
- string packageFile = "/data/system/packages.xml";
- debug = enable_debug;
- remove_data = remove_data_for_missing_apps;
- bool multi_user = TWFunc::Path_Exists("/data/user");
-
- if (!(TWFunc::Path_Exists(packageFile))) {
- gui_print("Can't check permissions\n");
- gui_print("after Factory Reset.\n");
- gui_print("Please boot rom and try\n");
- gui_print("again after you reboot into\n");
- gui_print("recovery.\n");
- return -1;
- }
-
- gui_print("Fixing permissions...\nLoading packages...\n");
- if ((getPackages(packageFile)) != 0) {
- return -1;
- }
-
- gui_print("Fixing app permissions...\n");
- if (fixApps() != 0) {
- return -1;
- }
-
- if (multi_user) {
- DIR *d = opendir("/data/user");
- string new_path, user_id;
-
- if (d == NULL) {
- LOGERR("Error opening '/data/user'\n");
- return -1;
- }
-
- if (d) {
- struct dirent *p;
- while ((p = readdir(d))) {
- if (!strcmp(p->d_name, ".") || !strcmp(p->d_name, ".."))
- continue;
-
- new_path = "/data/user/";
- new_path.append(p->d_name);
- user_id = "u";
- user_id += p->d_name;
- user_id += "_";
- if (p->d_type == DT_LNK) {
- char link[512], realPath[512];
- strcpy(link, new_path.c_str());
- memset(realPath, 0, sizeof(realPath));
- while (readlink(link, realPath, sizeof(realPath)) > 0) {
- strcpy(link, realPath);
- memset(realPath, 0, sizeof(realPath));
- }
- new_path = link;
- } else if (p->d_type != DT_DIR) {
- continue;
- } else {
- new_path.append("/");
- // We're probably going to need to fix permissions on multi user but
- // it will have to wait for another time. Need to figure out where
- // the uid and gid is stored for other users.
- continue;
- }
- gui_print("Fixing %s permissions...\n", new_path.c_str());
- if ((fixDataData(new_path)) != 0) {
- closedir(d);
- return -1;
- }
- }
- closedir(d);
- }
- } else {
- gui_print("Fixing /data/data permissions...\n");
- if ((fixDataData("/data/data/")) != 0) {
- return -1;
- }
- }
- gui_print("Done fixing permissions.\n");
- return 0;
-}
-
-int fixPermissions::fixContexts()
-{
-#ifdef HAVE_SELINUX
- gui_print("Fixing /data/data/ contexts.\n");
- fixDataDataContexts();
- fixDataInternalContexts();
- gui_print("Done fixing contexts.\n");
- return 0;
-#endif
- gui_print("Not fixing SELinux contexts; support not compiled in.\n");
- return -1;
-}
-
-int fixPermissions::pchown(string fn, int puid, int pgid) {
- LOGINFO("Fixing %s, uid: %d, gid: %d\n", fn.c_str(), puid, pgid);
- if (chown(fn.c_str(), puid, pgid) != 0) {
- LOGERR("Unable to chown '%s' %i %i\n", fn.c_str(), puid, pgid);
- return -1;
- }
- return 0;
-}
-
-int fixPermissions::pchmod(string fn, mode_t mode) {
- LOGINFO("Fixing %s, mode: %o\n", fn.c_str(), mode);
-
- if (chmod(fn.c_str(), mode) != 0) {
- LOGERR("Unable to chmod '%s' %o\n", fn.c_str(), mode);
- return -1;
- }
-
- return 0;
-}
-
-int fixPermissions::fixApps() {
- package* temp = head;
- while (temp != NULL) {
- struct stat st;
- if (stat(temp->codePath.c_str(), &st) == 0) {
- int new_uid = 0;
- int new_gid = 0;
- mode_t perms = 0;
- bool fix = false;
- if (temp->appDir.compare("/system/app") == 0 || temp->appDir.compare("/system/priv-app") == 0) {
- fix = true;
- new_uid = 0;
- new_gid = 0;
- perms = kMode_0644;
- } else if (temp->appDir.compare("/data/app") == 0 || temp->appDir.compare("/sd-ext/app") == 0) {
- fix = true;
- new_uid = 1000;
- new_gid = 1000;
- perms = kMode_0644;
- } else if (temp->appDir.compare("/data/app-private") == 0 || temp->appDir.compare("/sd-ext/app-private") == 0) {
- fix = true;
- new_uid = 1000;
- new_gid = temp->gid;
- perms = kMode_0640;
- } else
- fix = false;
- if (fix) {
- if (debug) {
- LOGINFO("Looking at '%s'\n", temp->codePath.c_str());
- LOGINFO("Fixing permissions on '%s'\n", temp->pkgName.c_str());
- LOGINFO("Directory: '%s'\n", temp->appDir.c_str());
- LOGINFO("Original package owner: %d, group: %d\n", temp->uid, temp->gid);
- }
- if (S_ISDIR(st.st_mode)) {
- // Android 5.0 introduced codePath pointing to a directory instead of the apk itself
- // TODO: check what this should do
- if (fixDir(temp->codePath, new_uid, new_gid, kMode_0755, new_uid, new_gid, perms) != 0)
- return -1;
- } else {
- if (pchown(temp->codePath, new_uid, new_gid) != 0)
- return -1;
- if (pchmod(temp->codePath, perms) != 0)
- return -1;
- }
- }
- } else if (remove_data) {
- //Remove data directory since app isn't installed
- string datapath = "/data/data/" + temp->dDir;
- if (TWFunc::Path_Exists(datapath) && temp->appDir.size() >= 9 && temp->appDir.substr(0, 9) != "/mnt/asec") {
- if (debug)
- LOGINFO("Looking at '%s', removing data dir: '%s', appDir: '%s'", temp->codePath.c_str(), datapath.c_str(), temp->appDir.c_str());
- if (TWFunc::removeDir(datapath, false) != 0) {
- LOGINFO("Unable to removeDir '%s'\n", datapath.c_str());
- return -1;
- }
- }
- }
- temp = temp->next;
- }
- return 0;
-}
-
-int fixPermissions::fixAllFiles(string directory, int uid, int gid, mode_t file_perms) {
- vector <string> files;
- string file;
-
- files = listAllFiles(directory);
- for (unsigned i = 0; i < files.size(); ++i) {
- file = directory + "/";
- file.append(files.at(i));
- if (debug)
- LOGINFO("Looking at file '%s'\n", file.c_str());
- if (pchmod(file, file_perms) != 0)
- return -1;
- if (pchown(file, uid, gid) != 0)
- return -1;
- }
- return 0;
-}
-
-int fixPermissions::fixDir(const string& dir, int diruid, int dirgid, mode_t dirmode, int fileuid, int filegid, mode_t filemode)
-{
- if (pchmod(dir.c_str(), dirmode) != 0)
- return -1;
- if (pchown(dir.c_str(), diruid, dirgid) != 0)
- return -1;
- if (fixAllFiles(dir, fileuid, filegid, filemode) != 0)
- return -1;
- return 0;
-}
-
-int fixPermissions::fixDataData(string dataDir) {
- package* temp = head;
- while (temp != NULL) {
- string dir = dataDir + temp->dDir;
- if (TWFunc::Path_Exists(dir)) {
- vector <string> dataDataDirs = listAllDirectories(dir);
- for (unsigned n = 0; n < dataDataDirs.size(); ++n) {
- string directory = dir + "/";
- directory.append(dataDataDirs.at(n));
- if (debug)
- LOGINFO("Looking at data directory: '%s'\n", directory.c_str());
- if (dataDataDirs.at(n) == ".") {
- if (fixDir(directory, temp->uid, temp->gid, kMode_0755, temp->uid, temp->gid, kMode_0755) != 0)
- return -1;
- }
- else if (dataDataDirs.at(n) == "..") {
- if (debug)
- LOGINFO("Skipping ..\n");
- continue;
- }
- // TODO: when any of these fails, do we really want to stop everything?
- else if (dataDataDirs.at(n) == "lib") {
- if (fixDir(directory, 1000, 1000, kMode_0755, 1000, 1000, kMode_0755) != 0)
- return -1;
- }
- else if (dataDataDirs.at(n) == "shared_prefs") {
- if (fixDir(directory, temp->uid, temp->gid,kMode_0771, temp->uid, temp->gid, kMode_0660) != 0)
- return -1;
- }
- else if (dataDataDirs.at(n) == "databases") {
- if (fixDir(directory, temp->uid, temp->gid,kMode_0771, temp->uid, temp->gid, kMode_0660) != 0)
- return -1;
- }
- else if (dataDataDirs.at(n) == "cache") {
- if (fixDir(directory, temp->uid, temp->gid,kMode_0771, temp->uid, temp->gid, kMode_0600) != 0)
- return -1;
- }
- else {
- if (fixDir(directory, temp->uid, temp->gid,kMode_0771, temp->uid, temp->gid, kMode_0755) != 0)
- return -1;
- }
- }
- }
- temp = temp->next;
- }
- return 0;
-}
-
-// TODO: merge to listAllDirEntries(path, type)
-vector <string> fixPermissions::listAllDirectories(string path) {
- DIR *dir = opendir(path.c_str());
- vector <string> dirs;
-
- if (dir == NULL) {
- LOGERR("Error opening '%s'\n", path.c_str());
- return dirs;
- }
- struct dirent *entry = readdir(dir);
- while (entry != NULL) {
- if (entry->d_type == DT_DIR)
- dirs.push_back(entry->d_name);
- entry = readdir(dir);
- }
- closedir(dir);
- return dirs;
-}
-
-vector <string> fixPermissions::listAllFiles(string path) {
- DIR *dir = opendir(path.c_str());
- vector <string> files;
-
- if (dir == NULL) {
- LOGERR("Error opening '%s'\n", path.c_str());
- return files;
- }
- struct dirent *entry = readdir(dir);
- while (entry != NULL) {
- if (entry->d_type == DT_REG)
- files.push_back(entry->d_name);
- entry = readdir(dir);
- }
- closedir(dir);
- return files;
-}
-
-void fixPermissions::deletePackages() {
- while (head) {
- package* temp = head;
- head = temp->next;
- delete temp;
- }
-}
-
-int fixPermissions::getPackages(const string& packageFile) {
- deletePackages();
- head = NULL;
-
- // TODO: simply skip all packages in /system/framework? or why are these excluded?
- vector <string> skip;
- skip.push_back("/system/framework/framework-res.apk");
- skip.push_back("/system/framework/com.htc.resources.apk");
-
- ifstream xmlFile(packageFile.c_str());
- xmlFile.seekg(0, ios::end);
- int len = (int) xmlFile.tellg();
- xmlFile.seekg(0, ios::beg);
- vector<char> xmlBuf(len + 1);
- xmlFile.read(&xmlBuf[0], len);
- xmlBuf[len] = '\0';
- xml_document<> pkgDoc;
- LOGINFO("Parsing packages.xml, size=%i...\n", len);
- pkgDoc.parse<parse_full>(&xmlBuf[0]);
-
- xml_node<> * pkgNode = pkgDoc.first_node("packages");
- if (pkgNode == NULL) {
- LOGERR("No packages found to fix.\n");
- return -1;
- }
-
- // Get packages
- for (xml_node<>* node = pkgNode->first_node(); node; node = node->next_sibling()) {
- if (node->type() != node_element)
- continue;
- string elementName = node->name();
- // we want <package> and <updated-package>
- if (!(elementName == "package" || elementName == "updated-package"))
- continue;
-
- xml_attribute<>* attName = node->first_attribute("name");
- if (!attName)
- continue;
- string name = attName->value();
-
- xml_attribute<>* attCodePath = node->first_attribute("codePath");
- if (!attCodePath)
- {
- LOGINFO("No codePath on %s, skipping.\n", name.c_str());
- continue;
- }
- string codePath = attCodePath->value();
-
- bool doskip = std::find(skip.begin(), skip.end(), codePath) != skip.end();
- if (doskip) {
- if (debug)
- LOGINFO("Skipping package %s\n", codePath.c_str());
- continue;
- }
-
- if (debug)
- LOGINFO("Loading pkg: %s\n", name.c_str());
-
- package* temp = new package;
- temp->pkgName = name;
- temp->codePath = codePath;
- temp->appDir = codePath;
- temp->dDir = name;
- xml_attribute<>* attUserId = node->first_attribute("userId");
- if (!attUserId)
- attUserId = node->first_attribute("sharedUserId");
- if (!attUserId) {
- LOGINFO("Problem with userID on %s\n", name.c_str());
- } else {
- temp->uid = atoi(attUserId->value());
- temp->gid = atoi(attUserId->value());
- }
- temp->next = head;
- head = temp;
- }
-
- if (head == NULL) {
- LOGERR("No package found to fix.\n");
- return -1;
- }
-
- return 0;
-}
diff --git a/fixPermissions.hpp b/fixPermissions.hpp
deleted file mode 100644
index f61a9a172..000000000
--- a/fixPermissions.hpp
+++ /dev/null
@@ -1,52 +0,0 @@
-#include <iostream>
-#include <fstream>
-#include <sstream>
-#include <string>
-#include <vector>
-#include <string.h>
-#include <libgen.h>
-#include <unistd.h>
-#include <sys/stat.h>
-#include <dirent.h>
-#include <errno.h>
-#include "gui/rapidxml.hpp"
-#include "twrp-functions.hpp"
-
-using namespace std;
-
-class fixPermissions {
- public:
- fixPermissions();
- ~fixPermissions();
- int fixPerms(bool enable_debug, bool remove_data_for_missing_apps);
- int fixContexts();
- int fixDataInternalContexts(void);
-
- private:
- int pchown(string fn, int puid, int pgid);
- int pchmod(string fn, mode_t mode);
- vector <string> listAllDirectories(string path);
- vector <string> listAllFiles(string path);
- void deletePackages();
- int getPackages(const string& packageFile);
- int fixApps();
- int fixAllFiles(string directory, int uid, int gid, mode_t file_perms);
- int fixDir(const string& dir, int diruid, int dirgid, mode_t dirmode, int fileuid, int filegid, mode_t filemode);
- int fixDataData(string dataDir);
- int restorecon(string entry, struct stat *sb);
- int fixDataDataContexts(void);
- int fixContextsRecursively(string path, int level);
-
- struct package {
- string pkgName;
- string codePath;
- string appDir;
- string dDir;
- int gid;
- int uid;
- package *next;
- };
- bool debug;
- bool remove_data;
- package* head;
-};
diff --git a/gui/action.cpp b/gui/action.cpp
index 240db8f24..e08111850 100644
--- a/gui/action.cpp
+++ b/gui/action.cpp
@@ -209,6 +209,7 @@ GUIAction::GUIAction(xml_node<>* node)
ADD_ACTION(wipe);
ADD_ACTION(refreshsizes);
ADD_ACTION(nandroid);
+ ADD_ACTION(fixcontexts);
ADD_ACTION(fixpermissions);
ADD_ACTION(dd);
ADD_ACTION(partitionsd);
@@ -1219,16 +1220,16 @@ int GUIAction::cancelbackup(std::string arg __unused) {
return 0;
}
-int GUIAction::fixpermissions(std::string arg __unused)
+int GUIAction::fixcontexts(std::string arg __unused)
{
int op_status = 0;
- operation_start("Fix Permissions");
- LOGINFO("fix permissions started!\n");
+ operation_start("Fix Contexts");
+ LOGINFO("fix contexts started!\n");
if (simulate) {
simulate_progress_bar();
} else {
- op_status = PartitionManager.Fix_Permissions();
+ op_status = PartitionManager.Fix_Contexts();
if (op_status != 0)
op_status = 1; // failure
}
@@ -1236,6 +1237,11 @@ int GUIAction::fixpermissions(std::string arg __unused)
return 0;
}
+int GUIAction::fixpermissions(std::string arg)
+{
+ return fixcontexts(arg);
+}
+
int GUIAction::dd(std::string arg)
{
operation_start("imaging");
diff --git a/gui/objects.hpp b/gui/objects.hpp
index e7ade18a5..d64a5fcfd 100644
--- a/gui/objects.hpp
+++ b/gui/objects.hpp
@@ -337,6 +337,7 @@ protected:
int wipe(std::string arg);
int refreshsizes(std::string arg);
int nandroid(std::string arg);
+ int fixcontexts(std::string arg);
int fixpermissions(std::string arg);
int dd(std::string arg);
int partitionsd(std::string arg);
diff --git a/gui/theme/common/landscape.xml b/gui/theme/common/landscape.xml
index 3bbb8bebd..7ce8d6534 100755
--- a/gui/theme/common/landscape.xml
+++ b/gui/theme/common/landscape.xml
@@ -3094,9 +3094,10 @@
</button>
<button style="main_button">
+ <condition var1="tw_has_data_media" var2="1"/>
<placement x="%center_x%" y="%row2_y%"/>
- <text>{@fix_perm_btn=Fix Permissions}</text>
- <action function="page">fixperms</action>
+ <text>{@fix_context_btn=Fix Contexts}</text>
+ <action function="page">fixcontexts</action>
</button>
<button style="main_button">
@@ -4467,7 +4468,7 @@
</action>
</page>
- <page name="fixperms">
+ <page name="fixcontexts">
<template name="page"/>
<text style="text_l">
@@ -4477,37 +4478,31 @@
<text style="text_m">
<placement x="%col1_x_header%" y="%row4_header_y%"/>
- <text>{@fix_perms_hdr=Fix Permissions}</text>
+ <text>{@fix_contexts_hdr=Fix Contexts}</text>
</text>
<text style="text_m_accent">
<placement x="%center_x%" y="%row2_y%" placement="5"/>
- <text>{@fix_perms_note=Note: Fixing permissions is rarely needed.}</text>
+ <text>{@fix_contexts_note1=Note: Fixing contexts is rarely needed.}</text>
</text>
- <checkbox>
- <placement x="%col2_x_left%" y="%row4_y%"/>
- <text>{@fix_perms_selinux_chk=Also fix SELinux Contexts}</text>
- <data variable="tw_fixperms_restorecon"/>
- </checkbox>
-
<text style="text_m_fail">
<placement x="%center_x%" y="%row6_y%" placement="5"/>
- <text>{@fix_perms_sel_note1=Fixing SELinux Contexts may cause}</text>
+ <text>{@fix_contexts_note2=Fixing SELinux Contexts may cause}</text>
</text>
<text style="text_m_fail">
<placement x="%center_x%" y="%row7_y%" placement="5"/>
- <text>{@fix_perms_sel_note2=your device to not boot properly.}</text>
+ <text>{@fix_contexts_note3=your device to not boot properly.}</text>
</text>
<slider style="slider_centered">
- <text>{@swipe_to_fix_perms=Swipe to Fix Permissions}</text>
+ <text>{@swipe_to_fix_contexts=Swipe to Fix Contexts}</text>
<actions>
<action function="set">tw_back=advanced</action>
- <action function="set">tw_action=fixpermissions</action>
- <action function="set">tw_action_text1={@fixing_perms=Fixing Permissions...}</action>
- <action function="set">tw_complete_text1={@fix_perms_complete=Fix Permissions Complete}</action>
+ <action function="set">tw_action=fixcontexts</action>
+ <action function="set">tw_action_text1={@fixing_contexts=Fixing Contexts...}</action>
+ <action function="set">tw_complete_text1={@fix_contexts_complete=Fix Contexts Complete}</action>
<action function="set">tw_slider_text={@swipe_to_confirm=Swipe to Confirm}</action>
<action function="set">tw_show_reboot=1</action>
<action function="page">action_page</action>
diff --git a/gui/theme/common/languages/en.xml b/gui/theme/common/languages/en.xml
index 8c04af3fc..1bb9b6842 100755
--- a/gui/theme/common/languages/en.xml
+++ b/gui/theme/common/languages/en.xml
@@ -365,8 +365,7 @@
<string name="copy_log_confirm">Copy Log to SD Card?</string>
<string name="copying_log">Copying Log to SD Card...</string>
<string name="copy_log_complete">Log Copy Complete</string>
- <string name="fix_perm_btn">Fix Permissions</string>
- <string name="fix_perm_s_btn">Fix Perms</string>
+ <string name="fix_context_btn">Fix Contexts</string>
<string name="part_sd_btn">Partition SD Card</string>
<string name="part_sd_s_btn">SD Card</string>
<string name="file_manager_btn">File Manager</string>
@@ -453,15 +452,14 @@
<string name="sideload_confirm">ADB Sideload</string>
<string name="sideload_usage">Usage: adb sideload filename.zip</string>
<string name="sideload_complete">ADB Sideload Complete</string>
- <string name="fix_perms_hdr">Fix Permissions</string>
- <string name="fix_perms_note">Note: Fixing permissions is rarely needed.</string>
- <string name="fix_perms_selinux_chk">Also fix SELinux Contexts</string>
- <string name="fix_perms_sel_note1">Fixing SELinux Contexts may cause</string>
- <string name="fix_perms_sel_note2">your device to not boot properly.</string>
- <string name="swipe_to_fix_perms">Swipe to Fix Permissions</string>
- <string name="swipe_fix_perms"> Fix Perms</string>
- <string name="fixing_perms">Fixing Permissions...</string>
- <string name="fix_perms_complete">Fix Permissions Complete</string>
+ <string name="fix_contexts_hdr">Fix Contexts</string>
+ <string name="fix_contexts_note1">Note: Fixing contexts is rarely needed.</string>
+ <string name="fix_contexts_note2">Fixing SELinux Contexts may cause</string>
+ <string name="fix_contexts_note3">your device to not boot properly.</string>
+ <string name="swipe_to_fix_contexts">Swipe to Fix Contexts</string>
+ <string name="swipe_fix_contexts"> Fix Contexts</string>
+ <string name="fixing_contexts">Fixing Contexts...</string>
+ <string name="fix_contexts_complete">Fix Contexts Complete</string>
<string name="reboot_hdr">Reboot</string>
<string name="su_hdr">SuperSU Check</string>
<string name="su_note1">Your device does not appear to be rooted.</string>
diff --git a/gui/theme/common/portrait.xml b/gui/theme/common/portrait.xml
index f253b2207..8e1a0d27a 100755
--- a/gui/theme/common/portrait.xml
+++ b/gui/theme/common/portrait.xml
@@ -3168,9 +3168,10 @@
</button>
<button style="main_button">
+ <condition var1="tw_has_data_media" var2="1"/>
<placement x="%center_x%" y="%row2a_y%"/>
- <text>{@fix_perm_btn=Fix Permissions}</text>
- <action function="page">fixperms</action>
+ <text>{@fix_context_btn=Fix Contexts}</text>
+ <action function="page">fixcontexts</action>
</button>
<button style="main_button">
@@ -4363,7 +4364,7 @@
</action>
</page>
- <page name="fixperms">
+ <page name="fixcontexts">
<template name="page"/>
<text style="text_l">
@@ -4373,37 +4374,31 @@
<text style="text_m">
<placement x="%col1_x_header%" y="%row4_header_y%"/>
- <text>{@fix_perms_hdr=Fix Permissions}</text>
+ <text>{@fix_contexts_hdr=Fix Contexts}</text>
</text>
<text style="text_m_accent">
<placement x="%center_x%" y="%row2_y%" placement="5"/>
- <text>{@fix_perms_note=Note: Fixing permissions is rarely needed.}</text>
+ <text>{@fix_contexts_note1=Note: Fixing contexts is rarely needed.}</text>
</text>
- <checkbox>
- <placement x="%indent%" y="%row4_y%"/>
- <text>{@fix_perms_selinux_chk=Also fix SELinux Contexts}</text>
- <data variable="tw_fixperms_restorecon"/>
- </checkbox>
-
<text style="text_m_fail">
<placement x="%center_x%" y="%row6_y%" placement="5"/>
- <text>{@fix_perms_sel_note1=Fixing SELinux Contexts may cause}</text>
+ <text>{@fix_contexts_note2=Fixing SELinux Contexts may cause}</text>
</text>
<text style="text_m_fail">
<placement x="%center_x%" y="%row7_y%" placement="5"/>
- <text>{@fix_perms_sel_note2=your device to not boot properly.}</text>
+ <text>{@fix_contexts_note3=your device to not boot properly.}</text>
</text>
<slider>
- <text>{@swipe_to_fix_perms=Swipe to Fix Permissions}</text>
+ <text>{@swipe_to_fix_contexts=Swipe to Fix Contexts}</text>
<actions>
<action function="set">tw_back=advanced</action>
- <action function="set">tw_action=fixpermissions</action>
- <action function="set">tw_action_text1={@fixing_perms=Fixing Permissions...}</action>
- <action function="set">tw_complete_text1={@fix_perms_complete=Fix Permissions Complete}</action>
+ <action function="set">tw_action=fixcontexts</action>
+ <action function="set">tw_action_text1={@fixing_contexts=Fixing Contexts...}</action>
+ <action function="set">tw_complete_text1={@fix_contexts_complete=Fix Contexts Complete}</action>
<action function="set">tw_slider_text={@swipe_to_confirm=Swipe to Confirm}</action>
<action function="set">tw_show_reboot=1</action>
<action function="page">action_page</action>
diff --git a/gui/theme/common/watch.xml b/gui/theme/common/watch.xml
index 22cc02bc6..e840687c5 100755
--- a/gui/theme/common/watch.xml
+++ b/gui/theme/common/watch.xml
@@ -3887,9 +3887,10 @@
</button>
<button style="main_button">
+ <condition var1="tw_has_data_media" var2="1"/>
<placement x="%col1_x_right%" y="%row1_y%"/>
- <text>{@fix_perm_s_btn=Fix Perms}</text>
- <action function="page">fixperms</action>
+ <text>{@fix_context_btn=Fix Contexts}</text>
+ <action function="page">fixcontexts</action>
</button>
<button style="main_button">
@@ -5158,44 +5159,38 @@
</action>
</page>
- <page name="fixperms">
+ <page name="fixcontexts">
<template name="page"/>
<template name="statusbar"/>
<text style="text_m">
<placement x="%col1_x_left%" y="%row1_header_y%"/>
- <text>{@advanced_hdr=Advanced} &gt; {@fix_perms_hdr=Fix Permissions}</text>
+ <text>{@advanced_hdr=Advanced} &gt; {@fix_contexts_hdr=Fix Contexts}</text>
</text>
<text style="text_m_accent">
<placement x="%center_x%" y="%row2_y%" placement="5"/>
- <text>{@fix_perms_note=Note: Fixing permissions is rarely needed.}</text>
+ <text>{@fix_contexts_note1=Note: Fixing contexts is rarely needed.}</text>
</text>
- <checkbox>
- <placement x="%indent%" y="%row4_y%"/>
- <text>{@fix_perms_selinux_chk=Also fix SELinux Contexts}</text>
- <data variable="tw_fixperms_restorecon"/>
- </checkbox>
-
<text style="text_m_fail">
<placement x="%center_x%" y="%row6a_y%" placement="5"/>
- <text>{@fix_perms_sel_note1=Fixing SELinux Contexts may cause}</text>
+ <text>{@fix_contexts_note2=Fixing SELinux Contexts may cause}</text>
</text>
<text style="text_m_fail">
<placement x="%center_x%" y="%row7a_y%" placement="5"/>
- <text>{@fix_perms_sel_note2=your device to not boot properly.}</text>
+ <text>{@fix_contexts_note3=your device to not boot properly.}</text>
</text>
<slider>
- <text>{@swipe_fix_perms= Fix Perms}</text>
+ <text>{@swipe_fix_contexts= Fix Contexts}</text>
<actions>
<action function="set">tw_back=advanced</action>
- <action function="set">tw_action=fixpermissions</action>
- <action function="set">tw_action_text1={@fixing_perms=Fixing Permissions...}</action>
- <action function="set">tw_complete_text1={@fix_perms_complete=Fix Permissions Complete}</action>
+ <action function="set">tw_action=fixcontexts</action>
+ <action function="set">tw_action_text1={@fixing_contexts=Fixing Contexts...}</action>
+ <action function="set">tw_complete_text1={@fix_contexts_complete=Fix Contexts Complete}</action>
<action function="set">tw_slider_text={@swipe_confirm= Confirm}</action>
<action function="set">tw_show_reboot=1</action>
<action function="page">action_page</action>
diff --git a/openrecoveryscript.cpp b/openrecoveryscript.cpp
index d66e16f7e..e974f9d20 100644
--- a/openrecoveryscript.cpp
+++ b/openrecoveryscript.cpp
@@ -381,8 +381,8 @@ int OpenRecoveryScript::run_script_file(void) {
}
property_set("ctl.start", "adbd");
gui_msg("done=Done.");
- } else if (strcmp(command, "fixperms") == 0 || strcmp(command, "fixpermissions") == 0) {
- ret_val = PartitionManager.Fix_Permissions();
+ } else if (strcmp(command, "fixperms") == 0 || strcmp(command, "fixpermissions") == 0 || strcmp(command, "fixcontexts") == 0) {
+ ret_val = PartitionManager.Fix_Contexts();
if (ret_val != 0)
ret_val = 1; // failure
} else if (strcmp(command, "decrypt") == 0) {
diff --git a/partition.cpp b/partition.cpp
index 8ddd4bed4..4626a5ff6 100644
--- a/partition.cpp
+++ b/partition.cpp
@@ -41,7 +41,6 @@
#include "twrpDigest.hpp"
#include "twrpTar.hpp"
#include "twrpDU.hpp"
-#include "fixPermissions.hpp"
#include "infomanager.hpp"
#include "set_metadata.h"
#include "gui/gui.hpp"
diff --git a/partitionmanager.cpp b/partitionmanager.cpp
index 81d448dc6..89580d069 100644
--- a/partitionmanager.cpp
+++ b/partitionmanager.cpp
@@ -37,7 +37,7 @@
#include "partitions.hpp"
#include "data.hpp"
#include "twrp-functions.hpp"
-#include "fixPermissions.hpp"
+#include "fixContexts.hpp"
#include "twrpDigest.hpp"
#include "twrpDU.hpp"
#include "set_metadata.h"
@@ -1490,25 +1490,24 @@ int TWPartitionManager::Decrypt_Device(string Password) {
return 1;
}
-int TWPartitionManager::Fix_Permissions(void) {
- int result = 0;
- if (!Mount_By_Path("/data", true))
- return false;
-
- if (!Mount_By_Path("/system", true))
- return false;
-
- Mount_By_Path("/sd-ext", false);
-
- fixPermissions perms;
- result = perms.fixPerms(true, false);
+int TWPartitionManager::Fix_Contexts(void) {
#ifdef HAVE_SELINUX
- if (result == 0 && DataManager::GetIntValue("tw_fixperms_restorecon") == 1)
- result = perms.fixContexts();
-#endif
+ std::vector<TWPartition*>::iterator iter;
+ for (iter = Partitions.begin(); iter != Partitions.end(); iter++) {
+ if ((*iter)->Has_Data_Media) {
+ if ((*iter)->Mount(true)) {
+ if (fixContexts::fixDataMediaContexts((*iter)->Mount_Point) != 0)
+ return -1;
+ }
+ }
+ }
UnMount_Main_Partitions();
gui_msg("done=Done.");
- return result;
+ return 0;
+#else
+ LOGERR("Cannot fix contexts, no selinux support present.\n");
+ return -1;
+#endif
}
TWPartition* TWPartitionManager::Find_Next_Storage(string Path, bool Exclude_Data_Media) {
diff --git a/partitions.hpp b/partitions.hpp
index bc44384ee..a020ee229 100644
--- a/partitions.hpp
+++ b/partitions.hpp
@@ -228,7 +228,7 @@ public:
TWPartition *Get_Default_Storage_Partition(); // Returns a pointer to a default storage partition
int Cancel_Backup(); // Signals partition backup to cancel
void Clean_Backup_Folder(string Backup_Folder); // Clean Backup Folder on Error
- int Fix_Permissions();
+ int Fix_Contexts();
void Get_Partition_List(string ListType, std::vector<PartitionList> *Partition_List);
int Fstab_Processed(); // Indicates if the fstab has been processed or not
void Output_Storage_Fstab(); // Creates a /cache/recovery/storage.fstab file with a list of all potential storage locations for app use
diff --git a/prebuilt/Android.mk b/prebuilt/Android.mk
index e22883c8c..f1cdc90db 100644
--- a/prebuilt/Android.mk
+++ b/prebuilt/Android.mk
@@ -234,15 +234,6 @@ LOCAL_MODULE_PATH := $(TARGET_RECOVERY_ROOT_OUT)/sbin
LOCAL_SRC_FILES := $(LOCAL_MODULE)
include $(BUILD_PREBUILT)
-#fix_permissions
-include $(CLEAR_VARS)
-LOCAL_MODULE := fix_permissions.sh
-LOCAL_MODULE_TAGS := eng
-LOCAL_MODULE_CLASS := RECOVERY_EXECUTABLES
-LOCAL_MODULE_PATH := $(TARGET_RECOVERY_ROOT_OUT)/sbin
-LOCAL_SRC_FILES := $(LOCAL_MODULE)
-include $(BUILD_PREBUILT)
-
#mke2fs.conf
include $(CLEAR_VARS)
LOCAL_MODULE := mke2fs.conf