diff --git a/README.md b/README.md
index a7bd184..25c43e2 100644
--- a/README.md
+++ b/README.md
@@ -293,7 +293,7 @@ Script interpreter. Works the same as ic3 but is not interactive.
- height function `(TAG_VOID: 0, TAG_TUPLE: max(height(tuple->tags)))`
- has_ident
- collect_idents
- - macros
+ - DONE macros
- modules
- defmodule
- def
@@ -321,7 +321,9 @@ Script interpreter. Works the same as ic3 but is not interactive.
- ffi ?
- libdwarf
- control structures
- - if / when / unless
+ - if
+ - when
+ - unless
- switch/case/cond
- while
- quote
diff --git a/lib/c3/0.1/c3.facts b/lib/c3/0.1/c3.facts
index 7de6335..2604539 100644
--- a/lib/c3/0.1/c3.facts
+++ b/lib/c3/0.1/c3.facts
@@ -199,3 +199,6 @@ add {C3, :symbol, C3.fib}
replace {C3.fib, :fn, fn { (0) { 1 }
(1) { 1 }
(x) { fib(x - 1) + fib(x - 2) } }}
+add {C3, :symbol, C3.if}
+replace {C3.if, :is_a, :macro}
+replace {C3.if, :cfn, cfn Tag "c3_if" (Tag, Tag, Tag, Result)
\ No newline at end of file
diff --git a/libc3/c3.c b/libc3/c3.c
index c3b5930..1ed8a1b 100644
--- a/libc3/c3.c
+++ b/libc3/c3.c
@@ -15,11 +15,13 @@
#include <err.h>
#include <stdio.h>
#include <stdlib.h>
+#include "bool.h"
#include "buf.h"
#include "c3_main.h"
#include "env.h"
#include "str.h"
#include "sym.h"
+#include "tag.h"
const s_str g_c3_base_binary = {{NULL}, 2, {"01"}};
const s_str g_c3_base_octal = {{NULL}, 8, {"01234567"}};
@@ -76,6 +78,29 @@ s_str * c3_getenv (const s_str *name, s_str *dest)
return str_init_1(dest, NULL, p);
}
+/* Special operator. */
+s_tag * c3_if (const s_tag *cond, const s_tag *then, const s_tag *else_,
+ s_tag *dest)
+{
+ bool b;
+ s_tag tmp;
+ if (! env_eval_tag(&g_c3_env, cond, &tmp))
+ return NULL;
+ if (! bool_init_cast(&b, &tmp)) {
+ tag_clean(&tmp);
+ return NULL;
+ }
+ tag_clean(&tmp);
+ if (b) {
+ if (! env_eval_tag(&g_c3_env, then, dest))
+ return NULL;
+ return dest;
+ }
+ if (! env_eval_tag(&g_c3_env, else_, dest))
+ return NULL;
+ return dest;
+}
+
s_env * c3_init (s_env *env, int argc, char **argv)
{
if (! env)
diff --git a/libc3/c3_main.h b/libc3/c3_main.h
index 596599c..0fde3b7 100644
--- a/libc3/c3_main.h
+++ b/libc3/c3_main.h
@@ -32,6 +32,10 @@ void c3_clean (s_env *env);
/* Observers. */
s_str * c3_getenv (const s_str *name, s_str *dest);
+/* Special operators. */
+s_tag * c3_if (const s_tag *cond, const s_tag *then,
+ const s_tag *else_, s_tag *dest);
+
/* debug */
void c3_break (void);