Skip to content

Commit 8b00500

Browse files
authored
Custom generator groups (#215)
- Group subflows into a subflow group - This can then be used by Target to create easy task dependencies
1 parent d952b6f commit 8b00500

File tree

7 files changed

+459
-132
lines changed

7 files changed

+459
-132
lines changed

buildcc/lib/target/include/target/custom_generator.h

+55-17
Original file line numberDiff line numberDiff line change
@@ -41,23 +41,27 @@ namespace buildcc {
4141
class CustomGeneratorContext {
4242
public:
4343
CustomGeneratorContext(const env::Command &c, const fs_unordered_set &i,
44-
const fs_unordered_set &o)
45-
: command(c), inputs(i), outputs(o) {}
44+
const fs_unordered_set &o,
45+
const std::vector<uint8_t> &ub)
46+
: command(c), inputs(i), outputs(o), userblob(ub) {}
4647

47-
public:
4848
const env::Command &command;
4949
const fs_unordered_set &inputs;
5050
const fs_unordered_set &outputs;
51+
const std::vector<uint8_t> &userblob;
5152
};
5253

5354
// clang-format off
54-
typedef std::function<bool(CustomGeneratorContext &)> GenerateCb;
55+
using GenerateCb = std::function<bool (CustomGeneratorContext &)>;
5556

56-
typedef std::function<void(std::unordered_map<std::string, tf::Task> &)> DependencyCb;
57+
using DependencyCb = std::function<void (std::unordered_map<std::string, tf::Task> &&)>;
5758
// clang-format on
5859

5960
class CustomBlobHandler {
6061
public:
62+
CustomBlobHandler() = default;
63+
virtual ~CustomBlobHandler() = default;
64+
6165
bool CheckChanged(const std::vector<uint8_t> &previous,
6266
const std::vector<uint8_t> &current) const {
6367
env::assert_fatal(
@@ -69,7 +73,7 @@ class CustomBlobHandler {
6973
return !IsEqual(previous, current);
7074
};
7175

72-
std::vector<uint8_t> GetSerializedData() {
76+
std::vector<uint8_t> GetSerializedData() const {
7377
auto serialized_data = Serialize();
7478
env::assert_fatal(
7579
Verify(serialized_data),
@@ -94,12 +98,11 @@ struct UserCustomGeneratorSchema : public internal::CustomGeneratorSchema {
9498
std::unordered_map<std::string, UserGenInfo> gen_info_map;
9599

96100
void ConvertToInternal() {
97-
for (auto &r_miter : gen_info_map) {
98-
r_miter.second.internal_inputs = path_schema_convert(
99-
r_miter.second.inputs, internal::Path::CreateExistingPath);
100-
auto p = internal_gen_info_map.emplace(r_miter.first, r_miter.second);
101-
env::assert_fatal(p.second,
102-
fmt::format("Could not save {}", r_miter.first));
101+
for (auto &[id, gen_info] : gen_info_map) {
102+
gen_info.internal_inputs = path_schema_convert(
103+
gen_info.inputs, internal::Path::CreateExistingPath);
104+
auto [_, success] = internal_gen_info_map.try_emplace(id, gen_info);
105+
env::assert_fatal(success, fmt::format("Could not save {}", id));
103106
}
104107
}
105108
};
@@ -136,6 +139,10 @@ class CustomGenerator : public internal::BuilderInterface {
136139
const GenerateCb &generate_cb,
137140
std::shared_ptr<CustomBlobHandler> blob_handler = nullptr);
138141

142+
void AddGroup(const std::string &group_id,
143+
std::initializer_list<std::string> ids,
144+
const DependencyCb &dependency_cb = DependencyCb());
145+
139146
// Callbacks
140147
/**
141148
* @brief Setup dependencies between Tasks using their `id`
@@ -168,20 +175,48 @@ class CustomGenerator : public internal::BuilderInterface {
168175
private:
169176
void Initialize();
170177

171-
template <bool run> void TaskRunner(const std::string &id);
178+
void TaskRunner(bool run, const std::string &id);
179+
tf::Task CreateTaskRunner(tf::Subflow &subflow, bool build,
180+
const std::string &id);
172181

173182
void GenerateTask();
174-
void BuildGenerate(
175-
std::unordered_map<std::string, UserGenInfo> &gen_selected_map,
176-
std::unordered_map<std::string, UserGenInfo> &dummy_gen_selected_map);
183+
void BuildGenerate(std::unordered_set<std::string> &gen_selected_ids,
184+
std::unordered_set<std::string> &dummy_gen_selected_ids);
185+
186+
void InvokeDependencyCb(std::unordered_map<std::string, tf::Task>
187+
&&registered_tasks) const noexcept;
177188

178189
// Recheck states
179190
void IdRemoved();
180191
void IdAdded();
181192
void IdUpdated();
182193

183194
protected:
184-
env::Command command_;
195+
const env::Command &ConstCommand() const { return command_; }
196+
env::Command &RefCommand() { return command_; }
197+
198+
private:
199+
struct GroupMetadata {
200+
std::vector<std::string> ids;
201+
DependencyCb dependency_cb;
202+
203+
void InvokeDependencyCb(const std::string &group_id,
204+
std::unordered_map<std::string, tf::Task>
205+
&&registered_tasks) const noexcept {
206+
if (!dependency_cb) {
207+
return;
208+
}
209+
try {
210+
dependency_cb(std::move(registered_tasks));
211+
} catch (...) {
212+
env::log_critical(
213+
__FUNCTION__,
214+
fmt::format("Dependency callback failed for group id {}",
215+
group_id));
216+
env::set_task_state(env::TaskState::FAILURE);
217+
}
218+
}
219+
};
185220

186221
private:
187222
std::string name_;
@@ -190,11 +225,14 @@ class CustomGenerator : public internal::BuilderInterface {
190225

191226
// Serialization
192227
UserCustomGeneratorSchema user_;
228+
std::unordered_map<std::string, GroupMetadata> grouped_ids_;
229+
std::unordered_set<std::string> ungrouped_ids_;
193230

194231
std::mutex success_schema_mutex_;
195232
std::unordered_map<std::string, UserGenInfo> success_schema_;
196233

197234
// Internal
235+
env::Command command_;
198236
tf::Taskflow tf_;
199237

200238
// Callbacks

buildcc/lib/target/include/target/file_generator.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -23,9 +23,8 @@ namespace buildcc {
2323

2424
class FileGenerator : public CustomGenerator {
2525
public:
26-
FileGenerator(const std::string &name, const TargetEnv &env)
27-
: CustomGenerator(name, env) {}
28-
virtual ~FileGenerator() = default;
26+
using CustomGenerator::CustomGenerator;
27+
~FileGenerator() override = default;
2928
FileGenerator(const FileGenerator &) = delete;
3029

3130
/**
@@ -73,6 +72,7 @@ class FileGenerator : public CustomGenerator {
7372
private:
7473
using CustomGenerator::AddDependencyCb;
7574
using CustomGenerator::AddGenInfo;
75+
using CustomGenerator::AddGroup;
7676
using CustomGenerator::Build;
7777

7878
private:

buildcc/lib/target/include/target/template_generator.h

+5-3
Original file line numberDiff line numberDiff line change
@@ -23,12 +23,13 @@ namespace buildcc {
2323

2424
class TemplateGenerator : public CustomGenerator {
2525
public:
26-
TemplateGenerator(const std::string &name, const TargetEnv &env)
27-
: CustomGenerator(name, env) {}
26+
using CustomGenerator::CustomGenerator;
27+
~TemplateGenerator() override = default;
28+
TemplateGenerator(const TemplateGenerator &) = delete;
2829

2930
void AddTemplate(const fs::path &input_filename,
3031
const fs::path &output_filename);
31-
std::string Parse(const std::string &pattern);
32+
std::string Parse(const std::string &pattern) const;
3233

3334
/**
3435
* @brief Build FileGenerator Tasks
@@ -41,6 +42,7 @@ class TemplateGenerator : public CustomGenerator {
4142
private:
4243
using CustomGenerator::AddDependencyCb;
4344
using CustomGenerator::AddGenInfo;
45+
using CustomGenerator::AddGroup;
4446
using CustomGenerator::Build;
4547

4648
private:

0 commit comments

Comments
 (0)