From 04795f0a7a999eb9004a9c492e62e9119a052a71 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stefan=20B=C3=BChler?= Date: Fri, 26 Jun 2009 23:58:27 +0200 Subject: [PATCH] Fix comparing with zero (added tolerance epsilon), added timestamp --- ovm/ovm.c | 28 +++++++++++++++++++++------- ovm/task.c | 1 + ovm/task.h | 3 ++- ovm/task1.c | 8 ++++---- 4 files changed, 28 insertions(+), 12 deletions(-) diff --git a/ovm/ovm.c b/ovm/ovm.c index 572b379..92a5548 100644 --- a/ovm/ovm.c +++ b/ovm/ovm.c @@ -49,10 +49,6 @@ ovm_t* ovm_load(const gchar *filename) { return ovm; } -static const gchar* cmp_op_strings[] = { - "<", "<=", "==", ">=", ">" -}; - void ovm_print_c(ovm_t *ovm, const gchar *filename) { guint i; instruction_t *oi = ovm->instructions; @@ -81,7 +77,23 @@ void ovm_print_c(ovm_t *ovm, const gchar *filename) { g_string_truncate(str, 0); break; case SOP_CMPZ: - g_string_printf(str, "\tovm_status = (v%u.d %s 0.0);\n", USED(instr_sop_r1(oi[i])), cmp_op_strings[instr_sop_cmp(oi[i])]); + switch (instr_sop_cmp(oi[i])) { + case CMP_LTZ: + g_string_printf(str, "\tovm_status = (v%u.d < -eps);\n", USED(instr_sop_r1(oi[i]))); + break; + case CMP_LEZ: + g_string_printf(str, "\tovm_status = (v%u.d <= eps);\n", USED(instr_sop_r1(oi[i]))); + break; + case CMP_EQZ: + g_string_printf(str, "\tovm_status = (fabs(v%u.d) <= eps);\n", USED(instr_sop_r1(oi[i]))); + break; + case CMP_GEZ: + g_string_printf(str, "\tovm_status = (v%u.d > eps);\n", USED(instr_sop_r1(oi[i]))); + break; + case CMP_GTZ: + g_string_printf(str, "\tovm_status = (v%u.d >= -eps);\n", USED(instr_sop_r1(oi[i]))); + break; + } break; case SOP_SQRT: g_string_printf(str, "\tv%u.d = sqrt(v%u.d);\n", USED(i), USED(instr_sop_r1(oi[i]))); @@ -108,7 +120,7 @@ void ovm_print_c(ovm_t *ovm, const gchar *filename) { g_string_printf(str, "\tv%u.d = v%u.d * v%u.d;\n", USED(i), USED(instr_dop_r1(oi[i])), USED(instr_dop_r2(oi[i]))); break; case OP_DIV: - g_string_printf(str, "\tv%u.d = (v%u.d == 0.0) ? 0.0 : v%u.d / v%u.d;\n", USED(i), USED(instr_dop_r2(oi[i])), USED(instr_dop_r1(oi[i])), instr_dop_r2(oi[i])); + g_string_printf(str, "\tv%u.d = (fabs(v%u.d) < eps) ? 0.0 : v%u.d / v%u.d;\n", USED(i), USED(instr_dop_r2(oi[i])), USED(instr_dop_r1(oi[i])), instr_dop_r2(oi[i])); break; case OP_OUT: g_string_printf(str, "\tout[%u] = v%u.d;\n", instr_dop_r1(oi[i]), USED(instr_dop_r2(oi[i]))); @@ -132,7 +144,8 @@ void ovm_print_c(ovm_t *ovm, const gchar *filename) { "\n" "typedef union { gdouble d; guint64 i; } double_int;\n" "\n" - "static gboolean ovm_status = FALSE;\n" + "static gboolean ovm_status;\n" + "static const gdouble eps = 1e-300;\n" "\n" "static double_int v0" )); @@ -150,6 +163,7 @@ void ovm_print_c(ovm_t *ovm, const gchar *filename) { )); for (i = 0; i < ovm->used; i++) { if (!usedv[i]) continue; + /* g_string_printf(str, "\tv%u.d = %f;\n", i, vi[i]); */ g_string_printf(str, "\tv%u.i = G_GUINT64_CONSTANT(%" G_GUINT64_FORMAT "); /* %f */ \n", i, uvi[i], vi[i]); write(f, GSTR_LEN(str)); } diff --git a/ovm/task.c b/ovm/task.c index 73bc4d8..d5c11a2 100644 --- a/ovm/task.c +++ b/ovm/task.c @@ -11,6 +11,7 @@ void task_free(task_t *task) { task_t* task_new(gdouble scenario, guint in_size, guint out_size) { task_t *task = g_slice_new(task_t); task->scenario = scenario; + task->timestamp = 0; task->in_size = in_size; task->out_size = out_size; task->in = g_slice_alloc0(task->in_size * sizeof(gdouble)); diff --git a/ovm/task.h b/ovm/task.h index 341b845..5fb37f0 100644 --- a/ovm/task.h +++ b/ovm/task.h @@ -5,6 +5,7 @@ typedef struct { gdouble scenario; + guint64 timestamp; guint in_size, out_size; gdouble *in, *out; } task_t; @@ -19,7 +20,7 @@ void ovm_step(gdouble scenario, gdouble *in, gdouble *out); static inline gdouble task_run(task_t *task, task_app_t app) { ovm_init(); - while (task->out[0] == 0.0) { + for ( ; task->out[0] == 0.0 && task->timestamp < 3000000; task->timestamp++) { app(task); ovm_step(task->scenario, task->in, task->out); } diff --git a/ovm/task1.c b/ovm/task1.c index 7a29b0a..8f9dec2 100644 --- a/ovm/task1.c +++ b/ovm/task1.c @@ -3,9 +3,9 @@ static void debug(task_t * task) { gdouble *o = task->out; - g_debug( - "Score: %5f Fuel: %5f x: %5f y: %5f r: %5f\n", - o[0], o[1], o[2], o[3], o[4]); + printf( + "Step: %9"G_GUINT64_FORMAT" Score: %5f Fuel: %5f x: %5f y: %5f r: %5f\n", + task->timestamp, o[0], o[1], o[2], o[3], o[4]); } static void run(task_t *task) { @@ -19,7 +19,7 @@ int main(int argc, char **argv) { UNUSED(argc); UNUSED(argv); - task = task_new(1001.0, 4, 5); + task = task_new(1002.0, 4, 5); score = task_run(task, run); printf("Final Score: %f\n", score); return 0;