Benchmark is actually broken right now, for mysterious double-free related reasons. I will dig into this tomorrow.
This commit is contained in:
parent
771de6f98b
commit
c24044230b
2 changed files with 40 additions and 0 deletions
|
|
@ -20,23 +20,39 @@
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#define false 0
|
||||||
|
#define true 1
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
HBenchmarkResults *h_benchmark(const HParser* parser, HParserTestcase* testcases) {
|
HBenchmarkResults *h_benchmark(const HParser* parser, HParserTestcase* testcases) {
|
||||||
// For now, just output the results to stderr
|
// For now, just output the results to stderr
|
||||||
HParserTestcase* tc = testcases;
|
HParserTestcase* tc = testcases;
|
||||||
HParserBackend backend = PB_MIN;
|
HParserBackend backend = PB_MIN;
|
||||||
|
HBenchmarkResults *ret = (HBenchmarkResults*)malloc(sizeof(HBenchmarkResults*));
|
||||||
|
ret->len = PB_MAX-PB_MIN;
|
||||||
|
ret->results = (HBackendResults*)malloc(ret->len * sizeof(HBackendResults*));
|
||||||
|
|
||||||
for (backend = PB_MIN; backend < PB_MAX; backend++) {
|
for (backend = PB_MIN; backend < PB_MAX; backend++) {
|
||||||
fprintf(stderr, "Compiling for backend %d ... ", backend);
|
fprintf(stderr, "Compiling for backend %d ... ", backend);
|
||||||
|
ret->results[backend].backend = backend;
|
||||||
// Step 1: Compile grammar for given parser...
|
// Step 1: Compile grammar for given parser...
|
||||||
if (h_compile(parser, PB_MIN, NULL) == -1) {
|
if (h_compile(parser, PB_MIN, NULL) == -1) {
|
||||||
// backend inappropriate for grammar...
|
// backend inappropriate for grammar...
|
||||||
fprintf(stderr, "failed\n");
|
fprintf(stderr, "failed\n");
|
||||||
|
ret->results[backend].compile_success = false;
|
||||||
|
ret->results[backend].n_testcases = 0;
|
||||||
|
ret->results[backend].failed_testcases = 0;
|
||||||
|
ret->results[backend].cases = NULL;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
ret->results[backend].compile_success = true;
|
||||||
int tc_failed = 0;
|
int tc_failed = 0;
|
||||||
// Step 1: verify all test cases.
|
// Step 1: verify all test cases.
|
||||||
|
ret->results[backend].n_testcases = 0;
|
||||||
|
ret->results[backend].failed_testcases = 0;
|
||||||
for (tc = testcases; tc->input != NULL; tc++) {
|
for (tc = testcases; tc->input != NULL; tc++) {
|
||||||
|
ret->results[backend].n_testcases++;
|
||||||
HParseResult *res = h_parse(parser, tc->input, tc->length);
|
HParseResult *res = h_parse(parser, tc->input, tc->length);
|
||||||
char* res_unamb;
|
char* res_unamb;
|
||||||
if (res != NULL) {
|
if (res != NULL) {
|
||||||
|
|
@ -51,6 +67,7 @@ HBenchmarkResults *h_benchmark(const HParser* parser, HParserTestcase* testcases
|
||||||
// report. (eg, if users are trying to fix a grammar for a
|
// report. (eg, if users are trying to fix a grammar for a
|
||||||
// faster backend)
|
// faster backend)
|
||||||
tc_failed++;
|
tc_failed++;
|
||||||
|
ret->results[backend].failed_testcases++;
|
||||||
}
|
}
|
||||||
h_parse_result_free(res);
|
h_parse_result_free(res);
|
||||||
}
|
}
|
||||||
|
|
@ -61,6 +78,9 @@ HBenchmarkResults *h_benchmark(const HParser* parser, HParserTestcase* testcases
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ret->results[backend].cases = (HCaseResult*)malloc(ret->results[backend].n_testcases * sizeof(HCaseResult*));
|
||||||
|
size_t cur_case = 0;
|
||||||
|
|
||||||
for (tc = testcases; tc->input != NULL; tc++) {
|
for (tc = testcases; tc->input != NULL; tc++) {
|
||||||
// The goal is to run each testcase for at least 50ms each
|
// The goal is to run each testcase for at least 50ms each
|
||||||
// TODO: replace this with a posix timer-based benchmark. (cf. timerfd_create, timer_create, setitimer)
|
// TODO: replace this with a posix timer-based benchmark. (cf. timerfd_create, timer_create, setitimer)
|
||||||
|
|
@ -78,7 +98,9 @@ HBenchmarkResults *h_benchmark(const HParser* parser, HParserTestcase* testcases
|
||||||
// time_diff is in ns
|
// time_diff is in ns
|
||||||
time_diff = (ts_end.tv_sec - ts_start.tv_sec) * 1000000000 + (ts_end.tv_nsec - ts_start.tv_nsec);
|
time_diff = (ts_end.tv_sec - ts_start.tv_sec) * 1000000000 + (ts_end.tv_nsec - ts_start.tv_nsec);
|
||||||
} while (time_diff < 100000000);
|
} while (time_diff < 100000000);
|
||||||
|
ret->results[backend].cases[cur_case].parse_time = (time_diff / count);
|
||||||
fprintf(stderr, "Case %d: %lld ns/parse\n", (int)(tc - testcases), time_diff / count);
|
fprintf(stderr, "Case %d: %lld ns/parse\n", (int)(tc - testcases), time_diff / count);
|
||||||
|
cur_case++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
|
||||||
18
src/hammer.h
18
src/hammer.h
|
|
@ -125,7 +125,25 @@ typedef struct HParserTestcase_ {
|
||||||
char* output_unambiguous;
|
char* output_unambiguous;
|
||||||
} HParserTestcase;
|
} HParserTestcase;
|
||||||
|
|
||||||
|
typedef struct HCaseResult_ {
|
||||||
|
bool success;
|
||||||
|
union {
|
||||||
|
const char* actual_results; // on failure, filled in with the results of h_write_result_unamb
|
||||||
|
size_t parse_time; // on success, filled in with time for a single parse, in nsec
|
||||||
|
};
|
||||||
|
} HCaseResult;
|
||||||
|
|
||||||
|
typedef struct HBackendResults_ {
|
||||||
|
HParserBackend backend;
|
||||||
|
bool compile_success;
|
||||||
|
size_t n_testcases;
|
||||||
|
size_t failed_testcases; // actually a count...
|
||||||
|
HCaseResult *cases;
|
||||||
|
} HBackendResults;
|
||||||
|
|
||||||
typedef struct HBenchmarkResults_ {
|
typedef struct HBenchmarkResults_ {
|
||||||
|
size_t len;
|
||||||
|
HBackendResults *results;
|
||||||
} HBenchmarkResults;
|
} HBenchmarkResults;
|
||||||
// }}}
|
// }}}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue