|
|
@ -39,14 +39,12 @@ Builder::Builder(GUI &g, GameEngine &engine) |
|
|
|
FILE *start_command(string &build_cmd) { |
|
|
|
FILE *start_command(string &build_cmd) { |
|
|
|
FILE *build_out = popen(build_cmd.c_str(), "r"); |
|
|
|
FILE *build_out = popen(build_cmd.c_str(), "r"); |
|
|
|
dbc::check(build_out != nullptr, "Failed to run command."); |
|
|
|
dbc::check(build_out != nullptr, "Failed to run command."); |
|
|
|
|
|
|
|
|
|
|
|
return build_out; |
|
|
|
return build_out; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
string read_line(FILE *build_out, bool &done_out) { |
|
|
|
string read_line(FILE *build_out, bool &done_out) { |
|
|
|
char buffer[BUF_MAX]; |
|
|
|
char buffer[BUF_MAX]; |
|
|
|
char *res = fgets(buffer, BUF_MAX, build_out); |
|
|
|
char *res = fgets(buffer, BUF_MAX, build_out); |
|
|
|
//!!! exception if res == nullptr
|
|
|
|
|
|
|
|
done_out = res == nullptr; |
|
|
|
done_out = res == nullptr; |
|
|
|
|
|
|
|
|
|
|
|
if(!done_out) { |
|
|
|
if(!done_out) { |
|
|
@ -56,33 +54,28 @@ string read_line(FILE *build_out, bool &done_out) { |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void end_build(FILE *build_out, GUI &gui, string &build_cmd) { |
|
|
|
bool end_build(FILE *build_out, GUI &gui, string &build_cmd) { |
|
|
|
int rc = pclose(build_out); |
|
|
|
int rc = pclose(build_out); |
|
|
|
|
|
|
|
return rc == 0; |
|
|
|
if(rc == 0) { |
|
|
|
|
|
|
|
gui.build_works(); |
|
|
|
|
|
|
|
} else { |
|
|
|
|
|
|
|
// BUG: make it not play two sounds
|
|
|
|
|
|
|
|
gui.build_failed(true, build_cmd); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void Builder::run_build(const string &line) { |
|
|
|
MatchResult Builder::parse_line(const string &line) { |
|
|
|
std::regex err_re("(.*?):([0-9]+):([0-9]+):\\s*(.*?):\\s*(.*)\n*"); |
|
|
|
std::regex err_re("(.*?):([0-9]+):([0-9]+):\\s*(.*?):\\s*(.*)\n*"); |
|
|
|
|
|
|
|
|
|
|
|
std::smatch err; |
|
|
|
std::smatch err; |
|
|
|
bool match = std::regex_match(line, err, err_re); |
|
|
|
bool match = std::regex_match(line, err, err_re); |
|
|
|
|
|
|
|
|
|
|
|
if(match) { |
|
|
|
if(match) { |
|
|
|
string file_name = err[1].str(); |
|
|
|
return { |
|
|
|
string lnumber = err[2].str(); |
|
|
|
.match = true, |
|
|
|
string col = err[3].str(); |
|
|
|
.file_name = err[1].str(), |
|
|
|
string type = err[4].str(); |
|
|
|
.lnumber = err[2].str(), |
|
|
|
string message = err[5].str(); |
|
|
|
.col = err[3].str(), |
|
|
|
|
|
|
|
.type = err[4].str(), |
|
|
|
gui.output(format("HIT WITH {} @ {}:{}:{} {}", type, file_name, lnumber, col, message)); |
|
|
|
.message = err[5].str(), |
|
|
|
|
|
|
|
}; |
|
|
|
game.hit(type); |
|
|
|
} else { |
|
|
|
|
|
|
|
return { .match = false }; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
@ -130,20 +123,33 @@ void Builder::run() { |
|
|
|
case BUILDING: { |
|
|
|
case BUILDING: { |
|
|
|
// check if there's output
|
|
|
|
// check if there's output
|
|
|
|
string line = read_line(build_out, build_done); |
|
|
|
string line = read_line(build_out, build_done); |
|
|
|
|
|
|
|
|
|
|
|
if(build_done) { |
|
|
|
if(build_done) { |
|
|
|
end_build(build_out, gui, build_cmd); |
|
|
|
bool good = end_build(build_out, gui, build_cmd); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if(good) { |
|
|
|
|
|
|
|
gui.build_works(); |
|
|
|
|
|
|
|
} else { |
|
|
|
|
|
|
|
// BUG: make it not play two sounds
|
|
|
|
|
|
|
|
gui.build_failed(true, build_cmd); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
build_out = NULL; |
|
|
|
build_out = NULL; |
|
|
|
state = DONE; |
|
|
|
state = DONE; |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
// get the command line
|
|
|
|
auto m = parse_line(line); |
|
|
|
// run the build if it's available
|
|
|
|
|
|
|
|
run_build(line); |
|
|
|
if(m.match) { |
|
|
|
|
|
|
|
gui.output(format("HIT WITH {} @ {}:{}:{} {}", m.type, m.file_name, m.lnumber, m.col, m.message)); |
|
|
|
|
|
|
|
game.hit(m.type); |
|
|
|
|
|
|
|
} |
|
|
|
state = BUILDING; |
|
|
|
state = BUILDING; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
break; |
|
|
|
break; |
|
|
|
|
|
|
|
|
|
|
|
case DONE: { |
|
|
|
case DONE: { |
|
|
|
|
|
|
|
|
|
|
|
game.end_round(); |
|
|
|
game.end_round(); |
|
|
|
|
|
|
|
|
|
|
|
if(game.is_dead()) { |
|
|
|
if(game.is_dead()) { |
|
|
|