diff --git a/lib/kc3/0.1/facts.kc3 b/lib/kc3/0.1/facts.kc3
index 838c1b4..2af460d 100644
--- a/lib/kc3/0.1/facts.kc3
+++ b/lib/kc3/0.1/facts.kc3
@@ -45,6 +45,9 @@ defmodule Facts do
# with(facts, [[?, ?, ?]], fn (fact) {result}) -> result
def with = cfn Tag "kc3_facts_with" (Facts, List, Fn, Result)
+ # with_macro(facts, [[?, ?, ?]], do result end) -> result
+ def with_macro = cfn_macro Tag "kc3_facts_with_macro" (Facts, List, Block, Result)
+
# with_tags(facts, subject, predicate, object,
# fn (fact) {result}) -> result
def with_tags = cfn Tag "kc3_facts_with_tags" (Facts, Tag, Tag, Tag,
diff --git a/libkc3/env.c b/libkc3/env.c
index ff4ef47..713c0f3 100644
--- a/libkc3/env.c
+++ b/libkc3/env.c
@@ -2312,6 +2312,41 @@ s_tag * env_facts_with (s_env *env, s_facts *facts, s_list **spec,
return NULL;
}
+s_tag * env_facts_with_macro (s_env *env, s_facts *facts, s_list **spec,
+ s_block *block, s_tag *dest)
+{
+ s_facts_with_cursor cursor = {0};
+ const s_fact *fact = NULL;
+ s_tag spec_tag = {0};
+ s_tag tmp = {0};
+ if (! env_eval_list(env, *spec, &spec_tag))
+ return NULL;
+ if (spec_tag.type != TAG_LIST) {
+ err_puts("env_facts_with_macro: spec is not a List");
+ assert(! "env_facts_with_macro: spec is not a List");
+ return NULL;
+ }
+ if (! facts_with_list(facts, &cursor, spec_tag.data.list))
+ return NULL;
+ while (1) {
+ if (! facts_with_cursor_next(&cursor, &fact))
+ goto clean;
+ if (! fact)
+ break;
+ tag_clean(&tmp);
+ if (! env_eval_block(env, block, &tmp)) {
+ goto clean;
+ }
+ }
+ *dest = tmp;
+ return dest;
+ clean:
+ err_puts("env_facts_with: error");
+ assert(! "env_facts_with: error");
+ tag_clean(&tmp);
+ return NULL;
+}
+
s_tag * env_facts_with_tags (s_env *env, s_facts *facts, s_tag *subject,
s_tag *predicate, s_tag *object,
s_fn *callback, s_tag *dest)
diff --git a/libkc3/env.h b/libkc3/env.h
index 1373b4b..33d6e51 100644
--- a/libkc3/env.h
+++ b/libkc3/env.h
@@ -78,6 +78,9 @@ s_tag * env_facts_first_with_tags (s_env *env, s_facts *facts,
s_tag * env_facts_with (s_env *env, s_facts *facts,
s_list **spec, s_fn *callback,
s_tag *dest);
+s_tag * env_facts_with_macro (s_env *env, s_facts *facts,
+ s_list **spec, s_block *block,
+ s_tag *dest);
s_tag * env_facts_with_tags (s_env *env, s_facts *facts,
s_tag *subject, s_tag *predicate,
s_tag *object, s_fn *callback,
diff --git a/libkc3/kc3.c b/libkc3/kc3.c
index c9e96a4..9dad5b2 100644
--- a/libkc3/kc3.c
+++ b/libkc3/kc3.c
@@ -311,6 +311,12 @@ s_tag * kc3_facts_with (s_facts *facts, s_list **spec,
return env_facts_with(&g_kc3_env, facts, spec, callback, dest);
}
+s_tag * kc3_facts_with_macro (s_facts *facts, s_list **spec,
+ s_block *block, s_tag *dest)
+{
+ return env_facts_with_macro(&g_kc3_env, facts, spec, block, dest);
+}
+
s_tag * kc3_facts_with_tags (s_facts *facts, s_tag *subject,
s_tag *predicate, s_tag *object,
s_fn *callback, s_tag *dest)
diff --git a/libkc3/kc3_main.h b/libkc3/kc3_main.h
index c3c2972..60647be 100644
--- a/libkc3/kc3_main.h
+++ b/libkc3/kc3_main.h
@@ -100,6 +100,8 @@ bool * kc3_facts_replace_tags (s_facts *facts,
bool *dest);
s_tag * kc3_facts_with (s_facts *facts, s_list **spec,
s_fn *callback, s_tag *dest);
+s_tag * kc3_facts_with_macro (s_facts *facts, s_list **spec,
+ s_block *block, s_tag *dest);
s_tag * kc3_facts_with_tags (s_facts *facts, s_tag *subject,
s_tag *predicate, s_tag *object,
s_fn *callback, s_tag *dest);