[ccan] [PATCH 1/5] cppmagic: New module
David Gibson
david at gibson.dropbear.id.au
Wed Jan 27 22:39:57 AEDT 2016
A module for some of the awesome / horrifying techniques described at:
http://jhnet.co.uk/articles/cpp_magic
https://github.com/pfultz2/Cloak/wiki/C-Preprocessor-tricks,-tips,-and-idioms
Start off with just some simple things.
Signed-off-by: David Gibson <david at gibson.dropbear.id.au>
---
ccan/cppmagic/LICENSE | 1 +
ccan/cppmagic/_info | 30 ++++++++++++++++++++++++++++++
ccan/cppmagic/cppmagic.h | 42 ++++++++++++++++++++++++++++++++++++++++++
ccan/cppmagic/test/run.c | 34 ++++++++++++++++++++++++++++++++++
4 files changed, 107 insertions(+)
create mode 120000 ccan/cppmagic/LICENSE
create mode 100644 ccan/cppmagic/_info
create mode 100644 ccan/cppmagic/cppmagic.h
create mode 100644 ccan/cppmagic/test/run.c
diff --git a/ccan/cppmagic/LICENSE b/ccan/cppmagic/LICENSE
new file mode 120000
index 0000000..2354d12
--- /dev/null
+++ b/ccan/cppmagic/LICENSE
@@ -0,0 +1 @@
+../../licenses/BSD-MIT
\ No newline at end of file
diff --git a/ccan/cppmagic/_info b/ccan/cppmagic/_info
new file mode 100644
index 0000000..aad394b
--- /dev/null
+++ b/ccan/cppmagic/_info
@@ -0,0 +1,30 @@
+#include "config.h"
+#include <stdio.h>
+#include <string.h>
+
+/**
+ * cppmagic - Abuse of the C preprocessor
+ *
+ * This contains a bunch of fancy macro techniques such as
+ * preprocessor-time evaluated conditionals and (quasi) recursion and
+ * iteration.
+ *
+ * It's based on these articles:
+ * - http://jhnet.co.uk/articles/cpp_magic
+ * - https://github.com/pfultz2/Cloak/wiki/C-Preprocessor-tricks,-tips,-and-idioms
+ * and code from the Boost C++ library.
+ *
+ * License: BSD-MIT
+ */
+int main(int argc, char *argv[])
+{
+ /* Expect exactly one argument */
+ if (argc != 2)
+ return 1;
+
+ if (strcmp(argv[1], "depends") == 0) {
+ return 0;
+ }
+
+ return 1;
+}
diff --git a/ccan/cppmagic/cppmagic.h b/ccan/cppmagic/cppmagic.h
new file mode 100644
index 0000000..f29e0ec
--- /dev/null
+++ b/ccan/cppmagic/cppmagic.h
@@ -0,0 +1,42 @@
+/* MIT (BSD) license - see LICENSE file for details */
+#ifndef CCAN_CPPMAGIC_H
+#define CCAN_CPPMAGIC_H
+
+/**
+ * CPPMAGIC_NOTHING - expands to nothing
+ */
+#define CPPMAGIC_NOTHING()
+
+/**
+ * CPPMAGIC_STRINGIFY - convert arguments to a string literal
+ */
+#define _CPPMAGIC_STRINGIFY(...) #__VA_ARGS__
+#define CPPMAGIC_STRINGIFY(...) _CPPMAGIC_STRINGIFY(__VA_ARGS__)
+
+/**
+ * CPPMAGIC_GLUE2 - glue arguments together
+ *
+ * CPPMAGIC_GLUE2(@a_, @b_)
+ * expands to the expansion of @a_ followed immediately
+ * (combining tokens) by the expansion of @b_
+ */
+#define _CPPMAGIC_GLUE2(a_, b_) a_##b_
+#define CPPMAGIC_GLUE2(a_, b_) _CPPMAGIC_GLUE2(a_, b_)
+
+/**
+ * CPPMAGIC_1ST - return 1st argument
+ *
+ * CPPMAGIC_1ST(@a_, ...)
+ * expands to the expansion of @a_
+ */
+#define CPPMAGIC_1ST(a_, ...) a_
+
+/**
+ * CPPMAGIC_2ND - return 2nd argument
+ *
+ * CPPMAGIC_2ST(@a_, @b_, ...)
+ * expands to the expansion of @b_
+ */
+#define CPPMAGIC_2ND(a_, b_, ...) b_
+
+#endif /* CCAN_CPPMAGIC_H */
diff --git a/ccan/cppmagic/test/run.c b/ccan/cppmagic/test/run.c
new file mode 100644
index 0000000..0ed830d
--- /dev/null
+++ b/ccan/cppmagic/test/run.c
@@ -0,0 +1,34 @@
+#include "config.h"
+
+#include <string.h>
+
+#include <ccan/cppmagic/cppmagic.h>
+#include <ccan/tap/tap.h>
+
+static inline void check1(const char *orig, const char *expand,
+ const char *match)
+{
+ ok(strcmp(expand, match) == 0,
+ "%s => %s : %s", orig, expand, match);
+}
+
+#define CHECK1(orig, match) \
+ check1(#orig, CPPMAGIC_STRINGIFY(orig), match)
+
+int main(void)
+{
+ plan_tests(7);
+
+ CHECK1(CPPMAGIC_NOTHING(), "");
+ CHECK1(CPPMAGIC_GLUE2(a, b), "ab");
+
+ CHECK1(CPPMAGIC_1ST(a), "a");
+ CHECK1(CPPMAGIC_1ST(a, b), "a");
+ CHECK1(CPPMAGIC_1ST(a, b, c), "a");
+
+ CHECK1(CPPMAGIC_2ND(a, b), "b");
+ CHECK1(CPPMAGIC_2ND(a, b, c), "b");
+
+ /* This exits depending on whether all tests passed */
+ return exit_status();
+}
--
2.5.0
More information about the ccan
mailing list