Commit 8584975817cad2c463a39ae51e820bad40491039

Thomas de Grivel 2025-04-18T22:33:48

fix env_eval_equal_tag warnings

diff --git a/lib/kc3/0.1/httpd.kc3 b/lib/kc3/0.1/httpd.kc3
index 9f71580..dd6f1e1 100644
--- a/lib/kc3/0.1/httpd.kc3
+++ b/lib/kc3/0.1/httpd.kc3
@@ -317,7 +317,7 @@ defmodule HTTPd do
       error_404_page(request)
     }
     (request, [route | next_routes]) {
-      response = if ((controller = HTTPd.Route.match(route, request))) do
+      response = if (controller = HTTPd.Route.match(route, request)) do
         let(request.params, controller(request))
       end
       response || route_and_render_request(request, next_routes)
diff --git a/libkc3/env_eval.c b/libkc3/env_eval.c
index 4de2066..b1a3b56 100644
--- a/libkc3/env_eval.c
+++ b/libkc3/env_eval.c
@@ -666,6 +666,7 @@ bool env_eval_equal_tag (s_env *env, bool macro, s_tag *a,
   bool is_var_b = false;
   s_tag tmp_a;
   s_tag tmp_b;
+  const s_sym *type = NULL;
   s_tag *var_a;
   s_tag *var_b;
   assert(env);
@@ -807,6 +808,16 @@ bool env_eval_equal_tag (s_env *env, bool macro, s_tag *a,
     break;
   }
   if (a->type != b->type) {
+    if (! env->silence_errors) {
+      err_write_1("env_eval_equal_tag: type mismatch: ");
+      tag_type(a, &type);
+      err_inspect_sym(&type);
+      err_write_1(" != ");
+      tag_type(b, &type);
+      err_inspect_sym(&type);
+      err_write_1("\n");
+      err_stacktrace();
+    }
     return false;
   }
   switch (a->type) {
diff --git a/libkc3/kc3.c b/libkc3/kc3.c
index b8da300..f50d255 100644
--- a/libkc3/kc3.c
+++ b/libkc3/kc3.c
@@ -507,8 +507,12 @@ s_tag * kc3_if_then_else (s_tag *cond, s_tag *then,
 {
   bool  cond_bool = false;
   s_tag cond_eval = {0};
+  bool silence_errors;
   const s_sym *type;
+  silence_errors = env_global()->silence_errors;
+  env_global()->silence_errors = true;
   if (env_eval_tag(env_global(), cond, &cond_eval)) {
+    env_global()->silence_errors = silence_errors;
     if (cond_eval.type == TAG_BOOL)
       cond_bool = cond_eval.data.bool_;
     else {
@@ -525,6 +529,8 @@ s_tag * kc3_if_then_else (s_tag *cond, s_tag *then,
       return dest;
     }
   }
+  else
+    env_global()->silence_errors = silence_errors;
   if (! env_eval_tag(env_global(), else_, dest))
     return NULL;
   return dest;
diff --git a/libkc3/struct_type.c b/libkc3/struct_type.c
index a478fe3..f8dea91 100644
--- a/libkc3/struct_type.c
+++ b/libkc3/struct_type.c
@@ -17,6 +17,7 @@
 #include "env.h"
 #include "list.h"
 #include "map.h"
+#include "mutex.h"
 #include "struct.h"
 #include "struct_type.h"
 #include "sym.h"
@@ -71,13 +72,23 @@ void struct_type_delete (s_struct_type *st)
   if (env_global()->pass_by_copy)
     assert(st->ref_count == 1);
   else {
+#ifdef HAVE_PTHREAD
+    mutex_lock(&st->mutex);
+#endif
     if (st->ref_count <= 0) {
       err_puts("struct_type_delete: invalid reference count");
       assert(! "struct_type_delete: invalid reference count");
       abort();
     }
-    if (--st->ref_count)
+    if (--st->ref_count) {
+#ifdef HAVE_PTHREAD
+      mutex_unlock(&st->mutex);
+#endif
       return;
+    }
+#ifdef HAVE_PTHREAD
+    mutex_unlock(&st->mutex);
+#endif
   }
   struct_type_clean(st);
   free(st);
@@ -193,6 +204,9 @@ s_struct_type * struct_type_init (s_struct_type *st,
 #endif
   }
   tmp.ref_count = 1;
+#ifdef HAVE_PTHREAD
+  mutex_init(&tmp.mutex);
+#endif
   *st = tmp;
   return st;
 }
@@ -218,6 +232,9 @@ s_struct_type * struct_type_init_copy (s_struct_type *st,
   memcpy(tmp.offset, src->offset, tmp.map.count * sizeof(uw));
   tmp.size = src->size;
   tmp.ref_count = 1;
+#ifdef HAVE_PTHREAD
+  mutex_init(&tmp.mutex);
+#endif
   *st = tmp;
   return st;
 }
@@ -268,15 +285,25 @@ s_struct_type * struct_type_new_copy (const s_struct_type *src)
   return st;
 }
 
-s_struct_type * struct_type_new_ref (s_struct_type *src)
+s_struct_type * struct_type_new_ref (s_struct_type *st)
 {
-  if (src->ref_count <= 0) {
+  assert(st);
+#ifdef HAVE_PTHREAD
+  mutex_lock(&st->mutex);
+#endif
+  if (st->ref_count <= 0) {
     err_puts("struct_type_new_ref: invalid reference count");
     assert(! "struct_type_new_ref: invalid reference count");
+#ifdef HAVE_PTHREAD
+    mutex_unlock(&st->mutex);
+#endif
     return NULL;
   }
-  src->ref_count++;
-  return src;
+  st->ref_count++;
+#ifdef HAVE_PTHREAD
+  mutex_unlock(&st->mutex);
+#endif
+  return st;
 }
 
 uw struct_type_padding (uw offset, uw size)
diff --git a/libkc3/types.h b/libkc3/types.h
index 8a26c59..aaa6e29 100644
--- a/libkc3/types.h
+++ b/libkc3/types.h
@@ -297,12 +297,6 @@ struct buf_save {
   uw wpos;
 };
 
-struct cow {
-  const s_sym *type;
-  s_list *list;
-  sw ref_count;
-};
-
 struct fact {
   s_tag *subject;
   s_tag *predicate;
@@ -459,6 +453,13 @@ struct buf {
   uw                wpos;
 };
 
+struct cow {
+  const s_sym *type;
+  s_list *list;
+  s_mutex mutex;
+  sw ref_count;
+};
+
 struct facts_spec_cursor {
   p_facts_spec spec;
   s_tag *subject;
@@ -503,6 +504,7 @@ struct struct_type {
   bool must_clean;
   uw *offset;
   uw size;
+  s_mutex mutex;
   sw ref_count;
 };
 
@@ -598,9 +600,9 @@ union callable_data {
 
 struct callable {
   e_callable_type type;
-  sw ref_count;
   u_callable_data data;
   s_mutex mutex;
+  sw ref_count;
 };
 
 union tag_data {
@@ -696,6 +698,7 @@ struct fact_w {
 struct list {
   s_tag tag;
   s_tag next;
+  s_mutex mutex;
   sw ref_count;
 };
 
@@ -831,6 +834,7 @@ struct env {
   s_frame          *read_time_frame;
   s_list           *search_modules;
   s_list           *search_modules_default;
+  bool              silence_errors;
   bool              trace;
   uw                unquote_level;
   s_unwind_protect *unwind_protect;