Skip to content

Commit 14c2472

Browse files
author
Tom Cherry
committed
init: degeneralize subcontext init into only vendor_init
This code is more generic than it needs to be and one of the side effects is that an extra init process is forked for odm_init, despite it having the same context as vendor_init. I don't think anything is going to change regarding that soon, so this change stops forking that extra process to save its memory and simplifies the code overall. Bug: 141164879 Test: init still uses vendor_init for vendor_scripts Test: init unit tests Test: init only has one subcontext process Change-Id: I0d224455604a681711e32f89fb20132378f69060
1 parent b0321c1 commit 14c2472

10 files changed

+51
-60
lines changed

init/action_parser.cpp

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -121,13 +121,8 @@ Result<void> ActionParser::ParseSection(std::vector<std::string>&& args,
121121
}
122122

123123
Subcontext* action_subcontext = nullptr;
124-
if (subcontexts_) {
125-
for (auto& subcontext : *subcontexts_) {
126-
if (StartsWith(filename, subcontext.path_prefix())) {
127-
action_subcontext = &subcontext;
128-
break;
129-
}
130-
}
124+
if (subcontext_ && subcontext_->PathMatchesSubcontext(filename)) {
125+
action_subcontext = subcontext_;
131126
}
132127

133128
std::string event_trigger;

init/action_parser.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -30,16 +30,16 @@ namespace init {
3030

3131
class ActionParser : public SectionParser {
3232
public:
33-
ActionParser(ActionManager* action_manager, std::vector<Subcontext>* subcontexts)
34-
: action_manager_(action_manager), subcontexts_(subcontexts), action_(nullptr) {}
33+
ActionParser(ActionManager* action_manager, Subcontext* subcontext)
34+
: action_manager_(action_manager), subcontext_(subcontext), action_(nullptr) {}
3535
Result<void> ParseSection(std::vector<std::string>&& args, const std::string& filename,
3636
int line) override;
3737
Result<void> ParseLineSection(std::vector<std::string>&& args, int line) override;
3838
Result<void> EndSection() override;
3939

4040
private:
4141
ActionManager* action_manager_;
42-
std::vector<Subcontext>* subcontexts_;
42+
Subcontext* subcontext_;
4343
std::unique_ptr<Action> action_;
4444
};
4545

init/init.cpp

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@ static std::string shutdown_command;
103103
static bool do_shutdown = false;
104104
static bool load_debug_prop = false;
105105

106-
static std::vector<Subcontext>* subcontexts;
106+
static std::unique_ptr<Subcontext> subcontext;
107107

108108
void DumpState() {
109109
ServiceList::GetInstance().DumpState();
@@ -113,9 +113,10 @@ void DumpState() {
113113
Parser CreateParser(ActionManager& action_manager, ServiceList& service_list) {
114114
Parser parser;
115115

116-
parser.AddSectionParser(
117-
"service", std::make_unique<ServiceParser>(&service_list, subcontexts, std::nullopt));
118-
parser.AddSectionParser("on", std::make_unique<ActionParser>(&action_manager, subcontexts));
116+
parser.AddSectionParser("service", std::make_unique<ServiceParser>(
117+
&service_list, subcontext.get(), std::nullopt));
118+
parser.AddSectionParser("on",
119+
std::make_unique<ActionParser>(&action_manager, subcontext.get()));
119120
parser.AddSectionParser("import", std::make_unique<ImportParser>(&parser));
120121

121122
return parser;
@@ -125,8 +126,8 @@ Parser CreateParser(ActionManager& action_manager, ServiceList& service_list) {
125126
Parser CreateServiceOnlyParser(ServiceList& service_list) {
126127
Parser parser;
127128

128-
parser.AddSectionParser(
129-
"service", std::make_unique<ServiceParser>(&service_list, subcontexts, std::nullopt));
129+
parser.AddSectionParser("service", std::make_unique<ServiceParser>(
130+
&service_list, subcontext.get(), std::nullopt));
130131
return parser;
131132
}
132133

@@ -749,7 +750,7 @@ int SecondStageMain(int argc, char** argv) {
749750
PLOG(FATAL) << "SetupMountNamespaces failed";
750751
}
751752

752-
subcontexts = InitializeSubcontexts();
753+
subcontext = InitializeSubcontext();
753754

754755
ActionManager& am = ActionManager::GetInstance();
755756
ServiceList& sm = ServiceList::GetInstance();

init/property_service.cpp

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -530,7 +530,7 @@ uint32_t InitPropertySet(const std::string& name, const std::string& value) {
530530
uint32_t result = 0;
531531
ucred cr = {.pid = 1, .uid = 0, .gid = 0};
532532
std::string error;
533-
result = HandlePropertySet(name, value, kInitContext.c_str(), cr, nullptr, &error);
533+
result = HandlePropertySet(name, value, kInitContext, cr, nullptr, &error);
534534
if (result != PROP_SUCCESS) {
535535
LOG(ERROR) << "Init cannot set '" << name << "' to '" << value << "': " << error;
536536
}
@@ -645,11 +645,16 @@ static void LoadProperties(char* data, const char* filter, const char* filename,
645645
char *key, *value, *eol, *sol, *tmp, *fn;
646646
size_t flen = 0;
647647

648-
const char* context = kInitContext.c_str();
648+
static constexpr const char* const kVendorPathPrefixes[2] = {
649+
"/vendor",
650+
"/odm",
651+
};
652+
653+
const char* context = kInitContext;
649654
if (SelinuxGetVendorAndroidVersion() >= __ANDROID_API_P__) {
650-
for (const auto& [path_prefix, secontext] : paths_and_secontexts) {
651-
if (StartsWith(filename, path_prefix)) {
652-
context = secontext;
655+
for (const auto& vendor_path_prefix : kVendorPathPrefixes) {
656+
if (StartsWith(filename, vendor_path_prefix)) {
657+
context = kVendorContext;
653658
}
654659
}
655660
}

init/service_parser.cpp

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -537,13 +537,8 @@ Result<void> ServiceParser::ParseSection(std::vector<std::string>&& args,
537537
filename_ = filename;
538538

539539
Subcontext* restart_action_subcontext = nullptr;
540-
if (subcontexts_) {
541-
for (auto& subcontext : *subcontexts_) {
542-
if (StartsWith(filename, subcontext.path_prefix())) {
543-
restart_action_subcontext = &subcontext;
544-
break;
545-
}
546-
}
540+
if (subcontext_ && subcontext_->PathMatchesSubcontext(filename)) {
541+
restart_action_subcontext = subcontext_;
547542
}
548543

549544
std::vector<std::string> str_args(args.begin() + 2, args.end());

init/service_parser.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,10 @@ namespace init {
3030
class ServiceParser : public SectionParser {
3131
public:
3232
ServiceParser(
33-
ServiceList* service_list, std::vector<Subcontext>* subcontexts,
33+
ServiceList* service_list, Subcontext* subcontext,
3434
const std::optional<InterfaceInheritanceHierarchyMap>& interface_inheritance_hierarchy)
3535
: service_list_(service_list),
36-
subcontexts_(subcontexts),
36+
subcontext_(subcontext),
3737
interface_inheritance_hierarchy_(interface_inheritance_hierarchy),
3838
service_(nullptr) {}
3939
Result<void> ParseSection(std::vector<std::string>&& args, const std::string& filename,
@@ -84,7 +84,7 @@ class ServiceParser : public SectionParser {
8484
bool IsValidName(const std::string& name) const;
8585

8686
ServiceList* service_list_;
87-
std::vector<Subcontext>* subcontexts_;
87+
Subcontext* subcontext_;
8888
std::optional<InterfaceInheritanceHierarchyMap> interface_inheritance_hierarchy_;
8989
std::unique_ptr<Service> service_;
9090
std::string filename_;

init/subcontext.cpp

Lines changed: 13 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -49,15 +49,6 @@ using android::base::unique_fd;
4949

5050
namespace android {
5151
namespace init {
52-
53-
const std::string kInitContext = "u:r:init:s0";
54-
const std::string kVendorContext = "u:r:vendor_init:s0";
55-
56-
const char* const paths_and_secontexts[2][2] = {
57-
{"/vendor", kVendorContext.c_str()},
58-
{"/odm", kVendorContext.c_str()},
59-
};
60-
6152
namespace {
6253

6354
class SubcontextProcess {
@@ -237,6 +228,15 @@ void Subcontext::Restart() {
237228
Fork();
238229
}
239230

231+
bool Subcontext::PathMatchesSubcontext(const std::string& path) {
232+
for (const auto& prefix : path_prefixes_) {
233+
if (StartsWith(path, prefix)) {
234+
return true;
235+
}
236+
}
237+
return false;
238+
}
239+
240240
Result<SubcontextReply> Subcontext::TransmitMessage(const SubcontextCommand& subcontext_command) {
241241
if (auto result = SendMessage(socket_, subcontext_command); !result) {
242242
Restart();
@@ -313,13 +313,12 @@ Result<std::vector<std::string>> Subcontext::ExpandArgs(const std::vector<std::s
313313
static std::vector<Subcontext> subcontexts;
314314
static bool shutting_down;
315315

316-
std::vector<Subcontext>* InitializeSubcontexts() {
316+
std::unique_ptr<Subcontext> InitializeSubcontext() {
317317
if (SelinuxGetVendorAndroidVersion() >= __ANDROID_API_P__) {
318-
for (const auto& [path_prefix, secontext] : paths_and_secontexts) {
319-
subcontexts.emplace_back(path_prefix, secontext);
320-
}
318+
return std::make_unique<Subcontext>(std::vector<std::string>{"/vendor", "/odm"},
319+
kVendorContext);
321320
}
322-
return &subcontexts;
321+
return nullptr;
323322
}
324323

325324
bool SubcontextChildReap(pid_t pid) {

init/subcontext.h

Lines changed: 8 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,7 @@
1414
* limitations under the License.
1515
*/
1616

17-
#ifndef _INIT_SUBCONTEXT_H
18-
#define _INIT_SUBCONTEXT_H
17+
#pragma once
1918

2019
#include <signal.h>
2120

@@ -31,41 +30,38 @@
3130
namespace android {
3231
namespace init {
3332

34-
extern const std::string kInitContext;
35-
extern const std::string kVendorContext;
36-
extern const char* const paths_and_secontexts[2][2];
33+
static constexpr const char kInitContext[] = "u:r:init:s0";
34+
static constexpr const char kVendorContext[] = "u:r:vendor_init:s0";
3735

3836
class Subcontext {
3937
public:
40-
Subcontext(std::string path_prefix, std::string context)
41-
: path_prefix_(std::move(path_prefix)), context_(std::move(context)), pid_(0) {
38+
Subcontext(std::vector<std::string> path_prefixes, std::string context)
39+
: path_prefixes_(std::move(path_prefixes)), context_(std::move(context)), pid_(0) {
4240
Fork();
4341
}
4442

4543
Result<void> Execute(const std::vector<std::string>& args);
4644
Result<std::vector<std::string>> ExpandArgs(const std::vector<std::string>& args);
4745
void Restart();
46+
bool PathMatchesSubcontext(const std::string& path);
4847

49-
const std::string& path_prefix() const { return path_prefix_; }
5048
const std::string& context() const { return context_; }
5149
pid_t pid() const { return pid_; }
5250

5351
private:
5452
void Fork();
5553
Result<SubcontextReply> TransmitMessage(const SubcontextCommand& subcontext_command);
5654

57-
std::string path_prefix_;
55+
std::vector<std::string> path_prefixes_;
5856
std::string context_;
5957
pid_t pid_;
6058
android::base::unique_fd socket_;
6159
};
6260

6361
int SubcontextMain(int argc, char** argv, const BuiltinFunctionMap* function_map);
64-
std::vector<Subcontext>* InitializeSubcontexts();
62+
std::unique_ptr<Subcontext> InitializeSubcontext();
6563
bool SubcontextChildReap(pid_t pid);
6664
void SubcontextTerminate();
6765

6866
} // namespace init
6967
} // namespace android
70-
71-
#endif

init/subcontext_benchmark.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ static void BenchmarkSuccess(benchmark::State& state) {
3333
return;
3434
}
3535

36-
auto subcontext = Subcontext("path", context);
36+
auto subcontext = Subcontext({"path"}, context);
3737
free(context);
3838

3939
while (state.KeepRunning()) {

init/subcontext_test.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ void RunTest(F&& test_function) {
5252
auto context_string = std::string(context);
5353
free(context);
5454

55-
auto subcontext = Subcontext("dummy_path", context_string);
55+
auto subcontext = Subcontext({"dummy_path"}, context_string);
5656
ASSERT_NE(0, subcontext.pid());
5757

5858
test_function(subcontext, context_string);

0 commit comments

Comments
 (0)