shill: Manager: Track loaded profiles internally
Before this change, the list of logged-in profiles was passed to
shill by the shill.conf init script. This change allows shill to
track the list of profiles (and the hashes assigned to them)
internally, ignoring the "--push" flag. A follow-on change will
remove the --push flag entirely.
BUG=chromium:231858
TEST=Unit tests + manual: Restart shill while logged in and make
sure "list-profiles" shows the user profile is loaded. Reboot
while logged in and make sure "list-profiles" only shows the default
profile. Log in and make sure /var/run/shill/loaded_profile_list
contains the user profile name.
Change-Id: Ib3d8cd6d78eeeec532cf876a38da6986587403aa
Reviewed-on: https://gerrit.chromium.org/gerrit/48582
Tested-by: Paul Stewart <pstew@chromium.org>
Reviewed-by: Christopher Wiley <wiley@chromium.org>
Reviewed-by: mukesh agrawal <quiche@chromium.org>
Commit-Queue: Paul Stewart <pstew@chromium.org>
diff --git a/profile.cc b/profile.cc
index 7d84243..f719243 100644
--- a/profile.cc
+++ b/profile.cc
@@ -11,6 +11,7 @@
#include <base/file_path.h>
#include <base/file_util.h>
#include <base/stl_util.h>
+#include <base/string_split.h>
#include <base/string_util.h>
#include <base/stringprintf.h>
#include <chromeos/dbus/service_constants.h>
@@ -31,6 +32,10 @@
namespace shill {
+// static
+const char Profile::kUserProfileListPathname[] =
+ RUNDIR "/loaded_profile_list";
+
Profile::Profile(ControlInterface *control_interface,
Metrics *metrics,
Manager *manager,
@@ -267,6 +272,62 @@
"~%s/%s", name.user.c_str(), name.identifier.c_str());
}
+// static
+vector<Profile::Identifier> Profile::LoadUserProfileList(const FilePath &path) {
+ vector<Identifier> profile_identifiers;
+ string profile_data;
+ if (!file_util::ReadFileToString(path, &profile_data)) {
+ return profile_identifiers;
+ }
+
+ vector<string> profile_lines;
+ base::SplitStringDontTrim(profile_data, '\n', &profile_lines);
+ vector<string>::const_iterator it;
+ for (it = profile_lines.begin(); it != profile_lines.end(); ++it) {
+ const string &line = *it;
+ if (line.empty()) {
+ // This will be the case on the last line, so let's not complain about it.
+ continue;
+ }
+ size_t space = line.find(' ');
+ if (space == string::npos || space == 0) {
+ LOG(ERROR) << "Invalid line found in " << path.value()
+ << ": " << line;
+ continue;
+ }
+ string name(line.begin(), line.begin() + space);
+ Identifier identifier;
+ if (!ParseIdentifier(name, &identifier) || identifier.user.empty()) {
+ LOG(ERROR) << "Invalid profile name found in " << path.value()
+ << ": " << name;
+ continue;
+ }
+ identifier.user_hash = string(line.begin() + space + 1, line.end());
+ profile_identifiers.push_back(identifier);
+ }
+
+ return profile_identifiers;
+}
+
+// static
+bool Profile::SaveUserProfileList(const FilePath &path,
+ const vector<ProfileRefPtr> &profiles) {
+ vector<string> lines;
+ vector<ProfileRefPtr>::const_iterator it;
+ for (it = profiles.begin(); it != profiles.end(); ++it) {
+ Identifier &id = (*it)->name_;
+ if (id.user.empty()) {
+ continue;
+ }
+ lines.push_back(base::StringPrintf("%s %s\n",
+ IdentifierToString(id).c_str(),
+ id.user_hash.c_str()));
+ }
+ string content = JoinString(lines, "");
+ size_t ret = file_util::WriteFile(path, content.c_str(), content.length());
+ return ret == content.length();
+}
+
bool Profile::MatchesIdentifier(const Identifier &name) const {
return name.user == name_.user && name.identifier == name_.identifier;
}