18 void parse(
const std::vector<std::string> &loop_nest) {
19 std::unordered_map<std::string, std::vector<std::string>> stage_to_loop_nest;
20 for (
const auto &line : loop_nest) {
25 if (line.at(0) ==
'#') {
29 std::istringstream iss(line);
30 std::vector<std::string> tokens{
31 std::istream_iterator<std::string>(iss),
32 std::istream_iterator<std::string>()};
34 std::string stage = tokens.at(0);
35 bool is_inlined = tokens.at(0) ==
"inlined:";
37 if (tokens.at(0) ==
"realize:" || is_inlined) {
41 if (stage ==
"gpu_none") {
45 all_stages.insert(stage);
48 inlined.insert(stage);
52 if (tokens.back() ==
"gpu_none") {
53 partially_scheduled.insert(stage);
56 if (line.at(0) !=
' ' && compute_root_stages.count(stage) == 0) {
57 compute_root_stages[stage] = -1;
60 if (tokens.back() ==
"gpu_simd" && compute_root_stages.count(stage) == 1 && compute_root_stages[stage] == -1) {
61 const std::string &vector_dim = tokens[tokens.size() - 3];
62 compute_root_stages[stage] = std::stoi(vector_dim.substr(0, vector_dim.size() - 1));
65 if (partially_scheduled.count(stage) == 0) {
66 stage_to_loop_nest[stage].push_back(line);
70 for (
const auto &entry : stage_to_loop_nest) {
71 std::string loop_nest =
"";
72 for (
const auto &line : entry.second) {
73 loop_nest += line +
"\n";
76 per_stage_loop_nests[entry.first] = loop_nest;
80 std::vector<std::string> to_remove;
81 for (
const auto &entry : compute_root_stages) {
82 if (entry.second == -1) {
83 to_remove.push_back(entry.first);
87 for (
const auto &key : to_remove) {
88 compute_root_stages.erase(key);
89 partially_scheduled.erase(key);
90 all_stages.erase(key);
91 per_stage_loop_nests.erase(key);
95 std::vector<std::string> loop_nest;
96 std::unordered_map<std::string, std::string> per_stage_loop_nests;
97 std::unordered_set<std::string> inlined;
98 std::unordered_set<std::string> partially_scheduled;
99 std::unordered_map<std::string, int> compute_root_stages;
100 std::unordered_set<std::string> all_stages;
104 : loop_nest{loop_nest} {
109 aslog(1) <<
"All stages:\n";
110 for (
const auto &s : all_stages) {
111 aslog(1) << s <<
"\n";
114 aslog(1) <<
"\ncompute_root stages:\n";
115 for (
const auto &s : compute_root_stages) {
116 aslog(1) << s.first <<
" with vector_dim = " << s.second <<
"\n";
119 aslog(1) <<
"\nPartially scheduled stages:\n";
120 for (
const auto &s : partially_scheduled) {
121 aslog(1) << s <<
" with vector_dim = " << compute_root_stages.at(s) <<
"\n";
124 aslog(1) <<
"\nInlined stages:\n";
125 for (
const auto &s : inlined) {
126 aslog(1) << s <<
"\n";
129 aslog(1) <<
"\nFull loop nest:\n";
130 for (
const auto &s : loop_nest) {
131 aslog(1) << s <<
"\n";
137 return node && all_stages.count(node->
func.
name()) > 0;
148 for (
const auto &stage : other.all_stages) {
149 if (all_stages.count(stage) == 0) {
150 if (only_consider_shared_stages) {
156 if (other.partially_scheduled.count(stage) == 1) {
157 if (compute_root_stages.count(stage) == 0) {
161 return other.compute_root_stages.at(stage) == compute_root_stages.at(stage);
164 if (other.inlined.count(stage) > 0) {
165 if (inlined.count(stage) == 0) {
169 }
else if (inlined.count(stage) > 0) {
173 if (other.per_stage_loop_nests.at(stage) != per_stage_loop_nests.at(stage)) {
182 std::istringstream in(str);
184 std::vector<std::string> loop_nest;
186 while (std::getline(in, line)) {
187 loop_nest.push_back(line);
193 static std::unique_ptr<LoopNestParser>
from_file(
const std::string &filename) {
194 std::ifstream file(filename);
196 std::vector<std::string> loop_nest;
198 while (std::getline(file, line)) {
199 loop_nest.push_back(line);
202 return std::make_unique<LoopNestParser>(loop_nest);