init
This commit is contained in:
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
core
|
||||||
|
a.out
|
43
README.md
Normal file
43
README.md
Normal file
@@ -0,0 +1,43 @@
|
|||||||
|
# test matrix vizualizer
|
||||||
|
|
||||||
|
Visualize test matrix, while tests are running, and then output summary.
|
||||||
|
|
||||||
|
Easy to integrate
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## Input format
|
||||||
|
```bash
|
||||||
|
arithmetic x86 1
|
||||||
|
arithmetic amd64 1
|
||||||
|
arithmetic rv64 1
|
||||||
|
# you can put comments anywhere
|
||||||
|
arithmetic emit-qbe 1
|
||||||
|
# empty lines are ignored
|
||||||
|
|
||||||
|
|
||||||
|
# omitting entries will mark them as skipped.
|
||||||
|
# note that you have to keep the order of th elines once you use them in that order
|
||||||
|
qbe-verify emit-qbe 1
|
||||||
|
loops x86 1
|
||||||
|
loops amd64 1
|
||||||
|
loops rv64 1
|
||||||
|
loops emit-qbe 0
|
||||||
|
floats x86 0
|
||||||
|
floats amd64 1
|
||||||
|
floats rv64 0
|
||||||
|
floats emit-qbe -
|
||||||
|
|
||||||
|
vectorize-loops-1 amd64 1
|
||||||
|
vectorize-loops-1 rv64 0
|
||||||
|
|
||||||
|
vectorize-loops-2 amd64 1
|
||||||
|
vectorize-loops-2 rv64 0
|
||||||
|
vectorize-loops-3 amd64 0
|
||||||
|
vectorize-loops-3 rv64 1
|
||||||
|
|
||||||
|
extern-func x86 1
|
||||||
|
extern-func amd64 1
|
||||||
|
extern-func rv64 1
|
||||||
|
extern-func emit-qbe 1
|
||||||
|
```
|
32
example_input.txt
Normal file
32
example_input.txt
Normal file
@@ -0,0 +1,32 @@
|
|||||||
|
arithmetic x86 1
|
||||||
|
arithmetic amd64 1
|
||||||
|
arithmetic rv64 1
|
||||||
|
# you can put comments anywhere
|
||||||
|
arithmetic emit-qbe 1
|
||||||
|
# empty lines are ignored
|
||||||
|
|
||||||
|
|
||||||
|
# omitting entries will mark them as skipped.
|
||||||
|
# note that you have to keep the order of th elines once you use them in that order
|
||||||
|
qbe-verify emit-qbe 1
|
||||||
|
loops x86 1
|
||||||
|
loops amd64 1
|
||||||
|
loops rv64 1
|
||||||
|
loops emit-qbe 0
|
||||||
|
floats x86 0
|
||||||
|
floats amd64 1
|
||||||
|
floats rv64 0
|
||||||
|
floats emit-qbe -
|
||||||
|
|
||||||
|
vectorize-loops-1 amd64 1
|
||||||
|
vectorize-loops-1 rv64 0
|
||||||
|
|
||||||
|
vectorize-loops-2 amd64 1
|
||||||
|
vectorize-loops-2 rv64 0
|
||||||
|
vectorize-loops-3 amd64 0
|
||||||
|
vectorize-loops-3 rv64 1
|
||||||
|
|
||||||
|
extern-func x86 1
|
||||||
|
extern-func amd64 1
|
||||||
|
extern-func rv64 1
|
||||||
|
extern-func emit-qbe 1
|
29
example_input.txt.sh
Normal file
29
example_input.txt.sh
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
echo arithmetic x86 1
|
||||||
|
echo arithmetic amd64 1
|
||||||
|
sleep 1
|
||||||
|
echo arithmetic rv64 1
|
||||||
|
echo arithmetic emit-qbe 1
|
||||||
|
echo qbe-verify emit-qbe 1
|
||||||
|
echo loops x86 1
|
||||||
|
echo loops amd64 1
|
||||||
|
echo loops rv64 1
|
||||||
|
sleep 1
|
||||||
|
echo loops emit-qbe 0
|
||||||
|
echo floats x86 0
|
||||||
|
echo floats amd64 1
|
||||||
|
echo floats rv64 0
|
||||||
|
sleep 1
|
||||||
|
echo floats emit-qbe -
|
||||||
|
echo vectorize-loops-1 amd64 1
|
||||||
|
echo vectorize-loops-1 rv64 0
|
||||||
|
echo vectorize-loops-2 amd64 1
|
||||||
|
echo vectorize-loops-2 rv64 0
|
||||||
|
sleep 1
|
||||||
|
echo vectorize-loops-3 amd64 0
|
||||||
|
sleep 1
|
||||||
|
echo vectorize-loops-3 rv64 1
|
||||||
|
echo extern-func x86 1
|
||||||
|
echo extern-func amd64 1
|
||||||
|
sleep 1
|
||||||
|
echo extern-func rv64 1
|
||||||
|
echo extern-func emit-qbe 1
|
199
main.c
Normal file
199
main.c
Normal file
@@ -0,0 +1,199 @@
|
|||||||
|
#include <ctype.h>
|
||||||
|
#include <stddef.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#define lenof(x) (sizeof((x)) / sizeof(*(x)))
|
||||||
|
|
||||||
|
#define MAX_LINE_LEN 256
|
||||||
|
#define MAX_RCOL 32
|
||||||
|
#define RCOL_LEN 64
|
||||||
|
|
||||||
|
#define RED "\033[0;31m"
|
||||||
|
#define GREEN "\033[0;32m"
|
||||||
|
#define YELLOW "\033[0;33m"
|
||||||
|
|
||||||
|
#define HRED "\033[0;91m"
|
||||||
|
#define HGREEN "\033[0;92m"
|
||||||
|
#define HYELLOW "\033[0;93m"
|
||||||
|
|
||||||
|
#define RESET "\033[0m"
|
||||||
|
|
||||||
|
unsigned hash(char const *buf) {
|
||||||
|
unsigned res = 5381;
|
||||||
|
for (; *buf; buf++) {
|
||||||
|
res = (res << 5) + res + *buf;
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
void err_misfmt_input(char const *reason) {
|
||||||
|
fprintf(stderr, "error: misformatted input: %s\n", reason);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
char buf[MAX_LINE_LEN];
|
||||||
|
|
||||||
|
struct counters {
|
||||||
|
unsigned char pfs[3];
|
||||||
|
};
|
||||||
|
|
||||||
|
unsigned num_rcol = 0;
|
||||||
|
unsigned rcol_hashes[MAX_RCOL] = {0};
|
||||||
|
char rcol_values[MAX_RCOL][RCOL_LEN];
|
||||||
|
struct counters rcol_ctr[MAX_RCOL] = {0};
|
||||||
|
|
||||||
|
unsigned rcol_lut(unsigned hash) {
|
||||||
|
for (unsigned *p = rcol_hashes; *p; p++)
|
||||||
|
if (*p == hash)
|
||||||
|
return p - rcol_hashes + 1;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void rstrip(char *buf) {
|
||||||
|
char *sub;
|
||||||
|
for (; *buf; buf++) {
|
||||||
|
if (isspace(*buf)) {
|
||||||
|
for (sub = buf + 1; *sub && isspace(*sub); sub++)
|
||||||
|
;
|
||||||
|
if (!*sub) {
|
||||||
|
*buf = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void put(int pfs_mode) {
|
||||||
|
if (pfs_mode == 0)
|
||||||
|
printf(HGREEN "* " RESET);
|
||||||
|
else if (pfs_mode == 1)
|
||||||
|
printf(HRED "X " RESET);
|
||||||
|
else
|
||||||
|
printf(HYELLOW "- " RESET);
|
||||||
|
}
|
||||||
|
|
||||||
|
void finish(int last_lc, unsigned last_rcol_idx) {
|
||||||
|
if (last_lc == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (; last_rcol_idx < num_rcol; last_rcol_idx++) {
|
||||||
|
put(2);
|
||||||
|
rcol_ctr[last_rcol_idx - 1].pfs[2] += 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int argc, char **argv) {
|
||||||
|
int lcol_width;
|
||||||
|
int last_lc = 0;
|
||||||
|
char *p, *lcol, *rcol;
|
||||||
|
unsigned lcol_hash, rcol_hash, rcol_idx, last_rcol_idx = 0,
|
||||||
|
actual_last_rcol_idx, i, j, pfs_mode;
|
||||||
|
struct counters sum = {0};
|
||||||
|
|
||||||
|
if (argc != 2 || !((lcol_width = atoi(argv[1])))) {
|
||||||
|
fprintf(stderr, "usage: %s <left column width>\n", *argv);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (buf == fgets(buf, lenof(buf), stdin)) {
|
||||||
|
p = buf;
|
||||||
|
for (; isspace(*p); p++)
|
||||||
|
;
|
||||||
|
if (*p == '#' || !*p)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
lcol = strtok(p, " \t");
|
||||||
|
rcol = strtok(0, " \t");
|
||||||
|
p = strtok(0, " \t");
|
||||||
|
rstrip(p);
|
||||||
|
|
||||||
|
if (!p || p[1])
|
||||||
|
err_misfmt_input("3rd column invalid");
|
||||||
|
|
||||||
|
if (*p == '0')
|
||||||
|
pfs_mode = 1;
|
||||||
|
else if (*p == '1')
|
||||||
|
pfs_mode = 0;
|
||||||
|
else if (*p == '-')
|
||||||
|
pfs_mode = 2;
|
||||||
|
else
|
||||||
|
err_misfmt_input("3rd column invalid");
|
||||||
|
|
||||||
|
lcol_hash = hash(lcol);
|
||||||
|
rcol_hash = hash(rcol);
|
||||||
|
|
||||||
|
actual_last_rcol_idx = last_rcol_idx;
|
||||||
|
if (lcol_hash != last_lc) {
|
||||||
|
last_rcol_idx = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
rcol_idx = rcol_lut(rcol_hash);
|
||||||
|
if (rcol_idx == 0) {
|
||||||
|
rcol_idx = ++num_rcol;
|
||||||
|
// TODO: validate length
|
||||||
|
rcol_hashes[rcol_idx - 1] = rcol_hash;
|
||||||
|
// TODO: validate length
|
||||||
|
strcpy(rcol_values[rcol_idx - 1], rcol);
|
||||||
|
} else if (rcol_idx <= last_rcol_idx && last_rcol_idx != 0) {
|
||||||
|
err_misfmt_input("ordering different from last time");
|
||||||
|
}
|
||||||
|
|
||||||
|
rcol_ctr[rcol_idx - 1].pfs[pfs_mode] += 1;
|
||||||
|
|
||||||
|
if (lcol[0] == '-' && lcol[1] == 0)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (lcol_hash != last_lc) {
|
||||||
|
finish(last_lc, actual_last_rcol_idx);
|
||||||
|
if (last_lc != 0)
|
||||||
|
putchar('\n');
|
||||||
|
last_lc = lcol_hash;
|
||||||
|
last_rcol_idx = 0;
|
||||||
|
printf("%*s ", lcol_width, lcol);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = last_rcol_idx + 1; i < rcol_idx; i++) {
|
||||||
|
put(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
put(pfs_mode);
|
||||||
|
last_rcol_idx = rcol_idx;
|
||||||
|
|
||||||
|
fflush(stdout);
|
||||||
|
}
|
||||||
|
|
||||||
|
finish(last_lc, last_rcol_idx);
|
||||||
|
if (last_lc != 0)
|
||||||
|
putchar('\n');
|
||||||
|
|
||||||
|
for (i = 0; i <= num_rcol; i++) {
|
||||||
|
for (j = 0; j < lcol_width + (num_rcol - i) * 2; j++)
|
||||||
|
putchar(' ');
|
||||||
|
if (i != num_rcol) {
|
||||||
|
putchar('^');
|
||||||
|
sum.pfs[0] += rcol_ctr[i].pfs[0];
|
||||||
|
sum.pfs[1] += rcol_ctr[i].pfs[1];
|
||||||
|
sum.pfs[2] += rcol_ctr[i].pfs[2];
|
||||||
|
} else
|
||||||
|
putchar(' ');
|
||||||
|
if (i != 0) {
|
||||||
|
printf(" %s \t(%u/%u passed", rcol_values[num_rcol - i],
|
||||||
|
rcol_ctr[num_rcol - i].pfs[0],
|
||||||
|
rcol_ctr[num_rcol - i].pfs[0] + rcol_ctr[num_rcol - i].pfs[1]);
|
||||||
|
if (rcol_ctr[num_rcol - i].pfs[2])
|
||||||
|
printf(", %u skipped", rcol_ctr[num_rcol - i].pfs[2]);
|
||||||
|
printf(")");
|
||||||
|
}
|
||||||
|
putchar('\n');
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("\nSummary:\n");
|
||||||
|
if (sum.pfs[0])
|
||||||
|
printf(HGREEN " %u passed" RESET "\n", sum.pfs[0]);
|
||||||
|
if (sum.pfs[1])
|
||||||
|
printf(HRED " %u failed" RESET "\n", sum.pfs[1]);
|
||||||
|
if (sum.pfs[2])
|
||||||
|
printf(HYELLOW " %u skipped" RESET "\n", sum.pfs[2]);
|
||||||
|
}
|
Reference in New Issue
Block a user