//
// eval_debug.cpp
// fornax3
//
// Created by Anders on 24/03/2020.
//
#include <stdlib.h>
#include <stdio.h>
#include "eval_debug_print.hpp"
#include "eval.hpp"
#include "../libs/strings.h"
typedef struct {
const char* topic;
eval w_mg;
eval b_mg;
eval diff_mg;
eval w_eg;
eval b_eg;
eval diff_eg;
} Eval_debug_line;
static bool isWhiteMove;
static Eval_debug_line* lines;
static int length = 0;
static Eval_debug_line* eval_debug_add(const char* topic) {
Eval_debug_line line = {topic, 0, 0, EVAL_NONE, 0, 0, EVAL_NONE};
lines[length] = line;
return &lines[length++];
}
static eval eval_debug_add_comp(const char* topic, void (*function)(Eval_debug_line*, eval val), eval val) {
Eval_debug_line* line = NULL;
for (int i = 0; i < length; i++) {
if (string_equals(topic, lines[i].topic)) {
line = &lines[i];
}
}
if (line == NULL) {
line = eval_debug_add(topic);
}
(*function)(line, val);
return val;
}
static void add_w(Eval_debug_line* line, eval val) {
line->w_mg += val;
line->w_eg += val;
}
static void add_w_mg(Eval_debug_line* line, eval val) {
line->w_mg += val;
}
static void add_w_eg(Eval_debug_line* line, eval val) {
line->w_eg += val;
}
static void add_b(Eval_debug_line* line, eval val) {
line->b_mg += val;
line->b_eg += val;
}
static void add_b_mg(Eval_debug_line* line, eval val) {
line->b_mg += val;
}
static void add_b_eg(Eval_debug_line* line, eval val) {
line->b_eg += val;
}
static void add_diff_mg(Eval_debug_line* line, eval val) {
line->diff_mg = line->diff_mg == EVAL_NONE ? val : line->diff_mg + val;
}
static void add_diff_eg(Eval_debug_line* line, eval val) {
line->diff_eg = line->diff_eg == EVAL_NONE ? val : line->diff_eg + val;
}
static void add_diff(Eval_debug_line* line, eval val) {
add_diff_mg(line, val);
add_diff_eg(line, val);
}
eval eval_debug_add_white_mg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_w_mg, val);
}
eval eval_debug_add_white_eg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_w_eg, val);
}
eval eval_debug_add_white(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_w, val);
}
eval eval_debug_add_black_mg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_b_mg, val);
}
eval eval_debug_add_black_eg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_b_eg, val);
}
eval eval_debug_add_black(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_b, val);
}
eval eval_debug_add_diff_mg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_diff_mg, val);
}
eval eval_debug_add_diff_eg(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_diff_eg, val);
}
eval eval_debug_add_diff(const char* topic, eval val) {
return eval_debug_add_comp(topic, &add_diff, val);
}
static void eval_debug_print_hr() {
printf("|----------------+-------------------+-------------------+--------------------|\n");
}
static void eval_debug_print_headers() {
printf("|topic |white mg / eg |black mg / eg |diff mg / eg |\n");
eval_debug_print_hr();
}
static void eval_debug_print(Eval_debug_line* line) {
eval diff_mg = line->diff_mg == EVAL_NONE ? line->w_mg - line->b_mg : line->diff_mg;
eval diff_eg = line->diff_eg == EVAL_NONE ? line->w_eg - line->b_eg : line->diff_eg;
printf("|%-16s|%8d / %8d|%8d / %8d|%8d / %8d |\n",
line->topic,
line->w_mg,
line->w_eg,
line->b_mg,
line->b_eg,
diff_mg,
diff_eg);
}
void eval_debug_start(bool isWhite) {
lines = (Eval_debug_line*) malloc(sizeof(*lines) * 64);
isWhiteMove = isWhite;
for (int i = 0; i < 64; ++i) {
eval_debug_add(NULL);
}
length = 0;
}
void eval_debug_end(const Board* board, eval total) {
Eval_debug_line* tline = eval_debug_add("total");
tline->diff_mg = 0;
tline->diff_eg = 0;
int i = 0;
eval_debug_print_headers();
while (!string_equals("total", lines[i].topic)) {
Eval_debug_line line = lines[i];
line.diff_mg = line.diff_mg == EVAL_NONE ? line.w_mg - line.b_mg : line.diff_mg;
line.diff_eg= line.diff_eg == EVAL_NONE ? line.w_eg - line.b_eg : line.diff_eg;
eval_debug_print(&line);
tline->w_mg += line.w_mg;
tline->w_eg += line.w_eg;
tline->b_mg += line.b_mg;
tline->b_eg += line.b_eg;
tline->diff_mg += line.diff_mg;
tline->diff_eg += line.diff_eg;
i++;
}
eval_debug_print_hr();
eval_debug_print(tline);
free(lines);
length = 0;
printf("\ngame phase = %d/%d", board_get_phase(board), PHASE_START);
printf("\nstatic cp eval white = %d\n", total);
}