lucy-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From nwelln...@apache.org
Subject [08/12] lucy-clownfish git commit: Update CommonMark source code
Date Sun, 18 Jan 2015 18:44:44 GMT
http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/cmark_ctype.c
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/cmark_ctype.c b/compiler/modules/CommonMark/src/cmark_ctype.c
new file mode 100644
index 0000000..5de8199
--- /dev/null
+++ b/compiler/modules/CommonMark/src/cmark_ctype.c
@@ -0,0 +1,53 @@
+#include <stdint.h>
+
+#include "cmark_ctype.h"
+
+/** 1 = space, 2 = punct, 3 = digit, 4 = alpha, 0 = other
+ */
+static const int8_t cmark_ctype_class[256] = {
+	/*      0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f */
+	/* 0 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0,
+	/* 1 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* 2 */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
+	/* 3 */ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 2,
+	/* 4 */ 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+	/* 5 */ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, 2, 2,
+	/* 6 */ 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+	/* 7 */ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, 2, 0,
+	/* 8 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* 9 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* a */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* b */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* c */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* d */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* e */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+	/* f */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
+};
+
+/**
+ * Returns 1 if c is a "whitespace" character as defined by the spec.
+ */
+int cmark_isspace(char c)
+{
+	return cmark_ctype_class[(int8_t)c] == 1;
+}
+
+/**
+ * Returns 1 if c is an ascii punctuation character.
+ */
+int cmark_ispunct(char c)
+{
+	return cmark_ctype_class[(int8_t)c] == 2;
+}
+
+int cmark_isalnum(char c)
+{
+	int8_t result;
+	result = cmark_ctype_class[(int8_t)c];
+	return (result == 3 || result == 4);
+}
+
+int cmark_isdigit(char c)
+{
+	return cmark_ctype_class[(int8_t)c] == 3;
+}

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/cmark_ctype.h
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/cmark_ctype.h b/compiler/modules/CommonMark/src/cmark_ctype.h
new file mode 100644
index 0000000..f803946
--- /dev/null
+++ b/compiler/modules/CommonMark/src/cmark_ctype.h
@@ -0,0 +1,24 @@
+#ifndef CMARK_CMARK_CTYPE_H
+#define CMARK_CMARK_CTYPE_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** Locale-independent versions of functions from ctype.h.
+ * We want cmark to behave the same no matter what the system locale.
+ */
+
+int cmark_isspace(char c);
+
+int cmark_ispunct(char c);
+
+int cmark_isalnum(char c);
+
+int cmark_isdigit(char c);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/cmark_export.h
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/cmark_export.h b/compiler/modules/CommonMark/src/cmark_export.h
index fa14b4d..1102c36 100644
--- a/compiler/modules/CommonMark/src/cmark_export.h
+++ b/compiler/modules/CommonMark/src/cmark_export.h
@@ -1,7 +1,35 @@
+
 #ifndef CMARK_EXPORT_H
 #define CMARK_EXPORT_H
 
-#define CMARK_EXPORT
-#define CMARK_NO_EXPORT
+#ifdef CMARK_STATIC_DEFINE
+#  define CMARK_EXPORT
+#  define CMARK_NO_EXPORT
+#else
+#  ifndef CMARK_EXPORT
+#    ifdef libcmark_EXPORTS
+        /* We are building this library */
+#      define CMARK_EXPORT __attribute__((visibility("default")))
+#    else
+        /* We are using this library */
+#      define CMARK_EXPORT __attribute__((visibility("default")))
+#    endif
+#  endif
+
+#  ifndef CMARK_NO_EXPORT
+#    define CMARK_NO_EXPORT __attribute__((visibility("hidden")))
+#  endif
+#endif
+
+#ifndef CMARK_DEPRECATED
+#  define CMARK_DEPRECATED __attribute__ ((__deprecated__))
+#  define CMARK_DEPRECATED_EXPORT CMARK_EXPORT __attribute__ ((__deprecated__))
+#  define CMARK_DEPRECATED_NO_EXPORT CMARK_NO_EXPORT __attribute__ ((__deprecated__))
+#endif
+
+#define DEFINE_NO_DEPRECATED 0
+#if DEFINE_NO_DEPRECATED
+# define CMARK_NO_DEPRECATED
+#endif
 
 #endif

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/config.h
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/config.h b/compiler/modules/CommonMark/src/config.h
index ce3064e..ecfa334 100644
--- a/compiler/modules/CommonMark/src/config.h
+++ b/compiler/modules/CommonMark/src/config.h
@@ -9,3 +9,7 @@ typedef char bool;
 #endif
 
 #define CMARK_ATTRIBUTE(list)
+
+#ifndef CHY_HAS_VA_COPY
+  #define va_copy(dest, src) ((dest) = (src))
+#endif

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/config.h.in
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/config.h.in b/compiler/modules/CommonMark/src/config.h.in
index 5294bc9..c1e9597 100644
--- a/compiler/modules/CommonMark/src/config.h.in
+++ b/compiler/modules/CommonMark/src/config.h.in
@@ -15,3 +15,9 @@
 #else
   #define CMARK_ATTRIBUTE(list)
 #endif
+
+#cmakedefine HAVE_VA_COPY
+
+#ifndef HAVE_VA_COPY
+  #define va_copy(dest, src) ((dest) = (src))
+#endif

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/houdini.h
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/houdini.h b/compiler/modules/CommonMark/src/houdini.h
index 9e1200e..9f00f6d 100644
--- a/compiler/modules/CommonMark/src/houdini.h
+++ b/compiler/modules/CommonMark/src/houdini.h
@@ -31,19 +31,19 @@ extern "C" {
 #define HOUDINI_ESCAPED_SIZE(x) (((x) * 12) / 10)
 #define HOUDINI_UNESCAPED_SIZE(x) (x)
 
-extern size_t houdini_unescape_ent(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_html(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_html0(strbuf *ob, const uint8_t *src, size_t size, int secure);
-extern int houdini_unescape_html(strbuf *ob, const uint8_t *src, size_t size);
-extern void houdini_unescape_html_f(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_xml(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_uri(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_url(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_href(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_unescape_uri(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_unescape_url(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_escape_js(strbuf *ob, const uint8_t *src, size_t size);
-extern int houdini_unescape_js(strbuf *ob, const uint8_t *src, size_t size);
+extern size_t houdini_unescape_ent(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_html(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_html0(cmark_strbuf *ob, const uint8_t *src, size_t size, int secure);
+extern int houdini_unescape_html(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern void houdini_unescape_html_f(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_xml(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_uri(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_url(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_href(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_unescape_uri(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_unescape_url(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_escape_js(cmark_strbuf *ob, const uint8_t *src, size_t size);
+extern int houdini_unescape_js(cmark_strbuf *ob, const uint8_t *src, size_t size);
 
 #ifdef __cplusplus
 }

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/houdini_href_e.c
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/houdini_href_e.c b/compiler/modules/CommonMark/src/houdini_href_e.c
index 1c99432..7527780 100644
--- a/compiler/modules/CommonMark/src/houdini_href_e.c
+++ b/compiler/modules/CommonMark/src/houdini_href_e.c
@@ -49,7 +49,7 @@ static const char HREF_SAFE[] = {
 };
 
 int
-houdini_escape_href(strbuf *ob, const uint8_t *src, size_t size)
+houdini_escape_href(cmark_strbuf *ob, const uint8_t *src, size_t size)
 {
 	static const uint8_t hex_chars[] = "0123456789ABCDEF";
 	size_t  i = 0, org;
@@ -63,7 +63,7 @@ houdini_escape_href(strbuf *ob, const uint8_t *src, size_t size)
 			i++;
 
 		if (likely(i > org))
-			strbuf_put(ob, src + org, i - org);
+			cmark_strbuf_put(ob, src + org, i - org);
 
 		/* escaping */
 		if (i >= size)
@@ -73,23 +73,23 @@ houdini_escape_href(strbuf *ob, const uint8_t *src, size_t size)
 		/* amp appears all the time in URLs, but needs
 		 * HTML-entity escaping to be inside an href */
 		case '&':
-			strbuf_puts(ob, "&amp;");
+			cmark_strbuf_puts(ob, "&amp;");
 			break;
 
 		/* the single quote is a valid URL character
 		 * according to the standard; it needs HTML
 		 * entity escaping too */
 		case '\'':
-			strbuf_puts(ob, "&#x27;");
+			cmark_strbuf_puts(ob, "&#x27;");
 			break;
 
-		/* the space can be escaped to %20 or a plus
-		 * sign. we're going with the generic escape
-		 * for now. the plus thing is more commonly seen
-		 * when building GET strings */
+			/* the space can be escaped to %20 or a plus
+			 * sign. we're going with the generic escape
+			 * for now. the plus thing is more commonly seen
+			 * when building GET strings */
 #if 0
 		case ' ':
-			strbuf_putc(ob, '+');
+			cmark_strbuf_putc(ob, '+');
 			break;
 #endif
 
@@ -97,7 +97,7 @@ houdini_escape_href(strbuf *ob, const uint8_t *src, size_t size)
 		default:
 			hex_str[1] = hex_chars[(src[i] >> 4) & 0xF];
 			hex_str[2] = hex_chars[src[i] & 0xF];
-			strbuf_put(ob, hex_str, 3);
+			cmark_strbuf_put(ob, hex_str, 3);
 		}
 
 		i++;

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/houdini_html_e.c
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/houdini_html_e.c b/compiler/modules/CommonMark/src/houdini_html_e.c
index db5034b..1a4c3e1 100644
--- a/compiler/modules/CommonMark/src/houdini_html_e.c
+++ b/compiler/modules/CommonMark/src/houdini_html_e.c
@@ -35,17 +35,17 @@ static const char HTML_ESCAPE_TABLE[] = {
 };
 
 static const char *HTML_ESCAPES[] = {
-        "",
-        "&quot;",
-        "&amp;",
-        "&#39;",
-        "&#47;",
-        "&lt;",
-        "&gt;"
+	"",
+	"&quot;",
+	"&amp;",
+	"&#39;",
+	"&#47;",
+	"&lt;",
+	"&gt;"
 };
 
 int
-houdini_escape_html0(strbuf *ob, const uint8_t *src, size_t size, int secure)
+houdini_escape_html0(cmark_strbuf *ob, const uint8_t *src, size_t size, int secure)
 {
 	size_t  i = 0, org, esc = 0;
 
@@ -55,7 +55,7 @@ houdini_escape_html0(strbuf *ob, const uint8_t *src, size_t size, int secure)
 			i++;
 
 		if (i > org)
-			strbuf_put(ob, src + org, i - org);
+			cmark_strbuf_put(ob, src + org, i - org);
 
 		/* escaping */
 		if (unlikely(i >= size))
@@ -63,9 +63,9 @@ houdini_escape_html0(strbuf *ob, const uint8_t *src, size_t size, int secure)
 
 		/* The forward slash is only escaped in secure mode */
 		if ((src[i] == '/' || src[i] == '\'') && !secure) {
-			strbuf_putc(ob, src[i]);
+			cmark_strbuf_putc(ob, src[i]);
 		} else {
-			strbuf_puts(ob, HTML_ESCAPES[esc]);
+			cmark_strbuf_puts(ob, HTML_ESCAPES[esc]);
 		}
 
 		i++;
@@ -75,7 +75,7 @@ houdini_escape_html0(strbuf *ob, const uint8_t *src, size_t size, int secure)
 }
 
 int
-houdini_escape_html(strbuf *ob, const uint8_t *src, size_t size)
+houdini_escape_html(cmark_strbuf *ob, const uint8_t *src, size_t size)
 {
 	return houdini_escape_html0(ob, src, size, 1);
 }

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/houdini_html_u.c
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/houdini_html_u.c b/compiler/modules/CommonMark/src/houdini_html_u.c
index b88b9d1..ecd7faa 100644
--- a/compiler/modules/CommonMark/src/houdini_html_u.c
+++ b/compiler/modules/CommonMark/src/houdini_html_u.c
@@ -8,7 +8,7 @@
 #include "html_unescape.h"
 
 size_t
-houdini_unescape_ent(strbuf *ob, const uint8_t *src, size_t size)
+houdini_unescape_ent(cmark_strbuf *ob, const uint8_t *src, size_t size)
 {
 	size_t i = 0;
 
@@ -55,7 +55,8 @@ houdini_unescape_ent(strbuf *ob, const uint8_t *src, size_t size)
 				const struct html_ent *entity = find_entity((char *)src, i);
 
 				if (entity != NULL) {
-					strbuf_put(ob, entity->utf8, entity->utf8_len);
+					size_t len = strnlen((const char *)entity->utf8, 4);
+					cmark_strbuf_put(ob, entity->utf8, len);
 					return i + 1;
 				}
 
@@ -68,7 +69,7 @@ houdini_unescape_ent(strbuf *ob, const uint8_t *src, size_t size)
 }
 
 int
-houdini_unescape_html(strbuf *ob, const uint8_t *src, size_t size)
+houdini_unescape_html(cmark_strbuf *ob, const uint8_t *src, size_t size)
 {
 	size_t  i = 0, org, ent;
 
@@ -82,10 +83,10 @@ houdini_unescape_html(strbuf *ob, const uint8_t *src, size_t size)
 				if (i >= size)
 					return 0;
 
-				strbuf_grow(ob, HOUDINI_UNESCAPED_SIZE(size));
+				cmark_strbuf_grow(ob, HOUDINI_UNESCAPED_SIZE(size));
 			}
 
-			strbuf_put(ob, src + org, i - org);
+			cmark_strbuf_put(ob, src + org, i - org);
 		}
 
 		/* escaping */
@@ -99,14 +100,14 @@ houdini_unescape_html(strbuf *ob, const uint8_t *src, size_t size)
 
 		/* not really an entity */
 		if (ent == 0)
-			strbuf_putc(ob, '&');
+			cmark_strbuf_putc(ob, '&');
 	}
 
 	return 1;
 }
 
-void houdini_unescape_html_f(strbuf *ob, const uint8_t *src, size_t size)
+void houdini_unescape_html_f(cmark_strbuf *ob, const uint8_t *src, size_t size)
 {
 	if (!houdini_unescape_html(ob, src, size))
-		strbuf_put(ob, src, size);
+		cmark_strbuf_put(ob, src, size);
 }

http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/5672da15/compiler/modules/CommonMark/src/html.c
----------------------------------------------------------------------
diff --git a/compiler/modules/CommonMark/src/html.c b/compiler/modules/CommonMark/src/html.c
index 60229cc..abc3e83 100644
--- a/compiler/modules/CommonMark/src/html.c
+++ b/compiler/modules/CommonMark/src/html.c
@@ -11,10 +11,7 @@
 
 // Functions to convert cmark_nodes to HTML strings.
 
-static bool
-finish_node(strbuf *html, cmark_node *node, bool tight);
-
-static void escape_html(strbuf *dest, const unsigned char *source, int length)
+static void escape_html(cmark_strbuf *dest, const unsigned char *source, int length)
 {
 	if (length < 0)
 		length = strlen((char *)source);
@@ -22,7 +19,7 @@ static void escape_html(strbuf *dest, const unsigned char *source, int length)
 	houdini_escape_html0(dest, source, (size_t)length, 0);
 }
 
-static void escape_href(strbuf *dest, const unsigned char *source, int length)
+static void escape_href(cmark_strbuf *dest, const unsigned char *source, int length)
 {
 	if (length < 0)
 		length = strlen((char *)source);
@@ -30,328 +27,298 @@ static void escape_href(strbuf *dest, const unsigned char *source, int
length)
 	houdini_escape_href(dest, source, (size_t)length);
 }
 
-static inline void cr(strbuf *html)
+static inline void cr(cmark_strbuf *html)
 {
 	if (html->size && html->ptr[html->size - 1] != '\n')
-		strbuf_putc(html, '\n');
+		cmark_strbuf_putc(html, '\n');
 }
 
-// Convert the inline children of a node to a plain string.
-static void inlines_to_plain_html(strbuf *html, cmark_node* node)
-{
-	cmark_node* cur = node->first_child;
-
-	if (cur == NULL) {
-		return;
-	}
-
-	while (true) {
-		switch(cur->type) {
-		case NODE_TEXT:
-		case NODE_INLINE_CODE:
-		case NODE_INLINE_HTML:
-			escape_html(html, cur->as.literal.data, cur->as.literal.len);
-			break;
-
-		case NODE_LINEBREAK:
-		case NODE_SOFTBREAK:
-			strbuf_putc(html, ' ');
-			break;
+struct render_state {
+	cmark_strbuf* html;
+	cmark_node *plain;
+};
 
-		default:
-			break;
-		}
-
-		if (cur->first_child) {
-			cur = cur->first_child;
-			continue;
-		}
-
-	next_sibling:
-		if (cur->next) {
-			cur = cur->next;
-			continue;
-		}
-		cur = cur->parent;
-		if (cur == node) {
-			break;
-		}
-		goto next_sibling;
+static void
+S_render_sourcepos(cmark_node *node, cmark_strbuf *html, long options)
+{
+	if (CMARK_OPT_SOURCEPOS & options) {
+		cmark_strbuf_printf(html, " data-sourcepos=\"%d:%d-%d:%d\"",
+		                    cmark_node_get_start_line(node),
+		                    cmark_node_get_start_column(node),
+		                    cmark_node_get_end_line(node),
+		                    cmark_node_get_end_column(node));
 	}
 }
 
-
-// Convert a cmark_node to HTML.
-static void node_to_html(strbuf *html, cmark_node *node)
+static int
+S_render_node(cmark_node *node, cmark_event_type ev_type,
+              struct render_state *state, long options)
 {
-	cmark_node *cur;
-	char start_header[] = "<h0>";
-	bool tight = false;
-	bool visit_children;
-	strbuf *info;
-
-	if (node == NULL) {
-		return;
-	}
+	cmark_node *parent;
+	cmark_node *grandparent;
+	cmark_strbuf *html = state->html;
+	char start_header[] = "<h0";
+	char end_header[] = "</h0";
+	bool tight;
 
-	cur = node;
-	while (true) {
-		// Only NODE_IMAGE wants to skip its children.
-		visit_children = true;
+	bool entering = (ev_type == CMARK_EVENT_ENTER);
 
-		switch(cur->type) {
-		case NODE_DOCUMENT:
-			break;
+	if (state->plain == node) { // back at original node
+		state->plain = NULL;
+	}
 
-		case NODE_PARAGRAPH:
-			if (!tight) {
-				cr(html);
-				strbuf_puts(html, "<p>");
-			}
+	if (state->plain != NULL) {
+		switch(node->type) {
+		case CMARK_NODE_TEXT:
+		case CMARK_NODE_CODE:
+		case CMARK_NODE_INLINE_HTML:
+			escape_html(html, node->as.literal.data,
+			            node->as.literal.len);
 			break;
 
-		case NODE_BLOCK_QUOTE:
-			cr(html);
-			strbuf_puts(html, "<blockquote>\n");
-			// BLOCK_QUOTE doesn't use any of the 'as' structs,
-			// so the 'list' member can be used to store the
-			// current value of 'tight'.
-			cur->as.list.tight = tight;
-			tight = false;
+		case CMARK_NODE_LINEBREAK:
+		case CMARK_NODE_SOFTBREAK:
+			cmark_strbuf_putc(html, ' ');
 			break;
 
-		case NODE_LIST_ITEM:
-			cr(html);
-			strbuf_puts(html, "<li>");
+		default:
 			break;
+		}
+		return 1;
+	}
 
-		case NODE_LIST: {
-			cmark_list *list = &cur->as.list;
-			bool tmp;
+	switch (node->type) {
+	case CMARK_NODE_DOCUMENT:
+		break;
 
-			// make sure a list starts at the beginning of the line:
+	case CMARK_NODE_BLOCK_QUOTE:
+		if (entering) {
 			cr(html);
-
-			if (list->list_type == CMARK_BULLET_LIST) {
-				strbuf_puts(html, "<ul>\n");
-			}
-			else if (list->start == 1) {
-				strbuf_puts(html, "<ol>\n");
-			}
-			else {
-				strbuf_printf(html, "<ol start=\"%d\">\n",
-					      list->start);
-			}
-
-			// Store the current value of 'tight' by swapping.
-			tmp = list->tight;
-			list->tight = tight;
-			tight = tmp;
-			break;
+			cmark_strbuf_puts(html, "<blockquote");
+			S_render_sourcepos(node, html, options);
+			cmark_strbuf_puts(html, ">\n");
+		} else {
+			cr(html);
+			cmark_strbuf_puts(html, "</blockquote>\n");
 		}
+		break;
 
-		case NODE_HEADER:
-			cr(html);
-			start_header[2] = '0' + cur->as.header.level;
-			strbuf_puts(html, start_header);
-			break;
+	case CMARK_NODE_LIST: {
+		cmark_list_type list_type = node->as.list.list_type;
+		int start = node->as.list.start;
 
-		case NODE_CODE_BLOCK:
-			info = &cur->as.code.info;
+		if (entering) {
 			cr(html);
-
-			if (&cur->as.code.fence_length == 0
-			    || strbuf_len(info) == 0) {
-				strbuf_puts(html, "<pre><code>");
+			if (list_type == CMARK_BULLET_LIST) {
+				cmark_strbuf_puts(html, "<ul");
+				S_render_sourcepos(node, html, options);
+				cmark_strbuf_puts(html, ">\n");
+			} else if (start == 1) {
+				cmark_strbuf_puts(html, "<ol");
+				S_render_sourcepos(node, html, options);
+				cmark_strbuf_puts(html, ">\n");
+			} else {
+				cmark_strbuf_printf(html,
+				                    "<ol start=\"%d\"",
+				                    start);
+				S_render_sourcepos(node, html, options);
+				cmark_strbuf_puts(html, ">\n");
 			}
-			else {
-				int first_tag = strbuf_strchr(info, ' ', 0);
-				if (first_tag < 0)
-					first_tag = strbuf_len(info);
-
-				strbuf_puts(html,
-					    "<pre><code class=\"language-");
-				escape_html(html, info->ptr, first_tag);
-				strbuf_puts(html, "\">");
-			}
-
-			escape_html(html, cur->string_content.ptr, cur->string_content.size);
-			break;
+		} else {
+			cmark_strbuf_puts(html,
+			                  list_type == CMARK_BULLET_LIST ?
+			                  "</ul>\n" : "</ol>\n");
+		}
+		break;
+	}
 
-		case NODE_HTML:
+	case CMARK_NODE_ITEM:
+		if (entering) {
 			cr(html);
-			strbuf_put(html, cur->string_content.ptr, cur->string_content.size);
-			break;
+			cmark_strbuf_puts(html, "<li");
+			S_render_sourcepos(node, html, options);
+			cmark_strbuf_putc(html, '>');
+		} else {
+			cmark_strbuf_puts(html, "</li>\n");
+		}
+		break;
 
-		case NODE_HRULE:
+	case CMARK_NODE_HEADER:
+		if (entering) {
 			cr(html);
-			strbuf_puts(html, "<hr />\n");
-			break;
-
-		case NODE_REFERENCE_DEF:
-			break;
-
-		case NODE_TEXT:
-			escape_html(html, cur->as.literal.data, cur->as.literal.len);
-			break;
-
-		case NODE_LINEBREAK:
-			strbuf_puts(html, "<br />\n");
-			break;
-
-		case NODE_SOFTBREAK:
-			strbuf_putc(html, '\n');
-			break;
-
-		case NODE_INLINE_CODE:
-			strbuf_puts(html, "<code>");
-			escape_html(html, cur->as.literal.data, cur->as.literal.len);
-			break;
-
-		case NODE_INLINE_HTML:
-			strbuf_put(html,
-				   cur->as.literal.data,
-				   cur->as.literal.len);
-			break;
-
-		case NODE_LINK:
-			strbuf_puts(html, "<a href=\"");
-			if (cur->as.link.url)
-				escape_href(html, cur->as.link.url, -1);
-
-			if (cur->as.link.title) {
-				strbuf_puts(html, "\" title=\"");
-				escape_html(html, cur->as.link.title, -1);
-			}
-
-			strbuf_puts(html, "\">");
-			break;
-
-		case NODE_IMAGE:
-			strbuf_puts(html, "<img src=\"");
-			if (cur->as.link.url)
-				escape_href(html, cur->as.link.url, -1);
-
-			strbuf_puts(html, "\" alt=\"");
-			inlines_to_plain_html(html, cur);
+			start_header[2] = '0' + node->as.header.level;
+			cmark_strbuf_puts(html, start_header);
+			S_render_sourcepos(node, html, options);
+			cmark_strbuf_putc(html, '>');
+		} else {
+			end_header[3] = '0' + node->as.header.level;
+			cmark_strbuf_puts(html, end_header);
+			cmark_strbuf_puts(html, ">\n");
+		}
+		break;
 
-			if (cur->as.link.title) {
-				strbuf_puts(html, "\" title=\"");
-				escape_html(html, cur->as.link.title, -1);
+	case CMARK_NODE_CODE_BLOCK:
+		cr(html);
+
+		if (!node->as.code.fenced || node->as.code.info.len == 0) {
+			cmark_strbuf_puts(html, "<pre");
+			S_render_sourcepos(node, html, options);
+			cmark_strbuf_puts(html, "><code>");
+		} else {
+			int first_tag = 0;
+			while (first_tag < node->as.code.info.len &&
+			       node->as.code.info.data[first_tag] != ' ') {
+				first_tag += 1;
 			}
 
-			strbuf_puts(html, "\" />");
-			visit_children = false;
-			break;
-
-		case NODE_STRONG:
-			strbuf_puts(html, "<strong>");
-			break;
-
-		case NODE_EMPH:
-			strbuf_puts(html, "<em>");
-			break;
-
-		default:
-			assert(false);
+			cmark_strbuf_puts(html, "<pre");
+			S_render_sourcepos(node, html, options);
+			cmark_strbuf_puts(html, "><code class=\"language-");
+			escape_html(html, node->as.code.info.data, first_tag);
+			cmark_strbuf_puts(html, "\">");
 		}
 
-		if (visit_children && cur->first_child) {
-			cur = cur->first_child;
-			continue;
-		}
+		escape_html(html, node->as.code.literal.data,
+		            node->as.code.literal.len);
+		cmark_strbuf_puts(html, "</code></pre>\n");
+		break;
 
-	next_sibling:
-		tight = finish_node(html, cur, tight);
-		if (cur == node) {
-			break;
-		}
-		if (cur->next) {
-			cur = cur->next;
-			continue;
-		}
-		cur = cur->parent;
-		goto next_sibling;
-	}
-}
+	case CMARK_NODE_HTML:
+		cr(html);
+		cmark_strbuf_put(html, node->as.literal.data, node->as.literal.len);
+		break;
 
-// Returns the restored value of 'tight'.
-static bool
-finish_node(strbuf *html, cmark_node *node, bool tight)
-{
-	char end_header[] = "</h0>\n";
+	case CMARK_NODE_HRULE:
+		cr(html);
+		cmark_strbuf_puts(html, "<hr");
+		S_render_sourcepos(node, html, options);
+		cmark_strbuf_puts(html, " />\n");
+		break;
 
-	switch (node->type) {
-	case NODE_PARAGRAPH:
+	case CMARK_NODE_PARAGRAPH:
+		parent = cmark_node_parent(node);
+		grandparent = cmark_node_parent(parent);
+		if (grandparent != NULL &&
+		    grandparent->type == CMARK_NODE_LIST) {
+			tight = grandparent->as.list.tight;
+		} else {
+			tight = false;
+		}
 		if (!tight) {
-			strbuf_puts(html, "</p>\n");
+			if (entering) {
+				cr(html);
+				cmark_strbuf_puts(html, "<p");
+				S_render_sourcepos(node, html, options);
+				cmark_strbuf_putc(html, '>');
+			} else {
+				cmark_strbuf_puts(html, "</p>\n");
+			}
 		}
 		break;
 
-	case NODE_BLOCK_QUOTE: {
-		cmark_list *list = &node->as.list;
-		strbuf_puts(html, "</blockquote>\n");
-		// Restore old 'tight' value.
-		tight = list->tight;
-		list->tight = false;
+	case CMARK_NODE_TEXT:
+		escape_html(html, node->as.literal.data,
+		            node->as.literal.len);
 		break;
-	}
 
-	case NODE_LIST_ITEM:
-		strbuf_puts(html, "</li>\n");
+	case CMARK_NODE_LINEBREAK:
+		cmark_strbuf_puts(html, "<br />\n");
 		break;
 
-	case NODE_LIST: {
-		cmark_list *list = &node->as.list;
-		bool tmp;
-		strbuf_puts(html,
-			    list->list_type == CMARK_BULLET_LIST ?
-			    "</ul>\n" : "</ol>\n");
-		// Restore old 'tight' value.
-		tmp = tight;
-		tight = list->tight;
-		list->tight = tmp;
+	case CMARK_NODE_SOFTBREAK:
+		if (options & CMARK_OPT_HARDBREAKS) {
+			cmark_strbuf_puts(html, "<br />\n");
+		} else {
+			cmark_strbuf_putc(html, '\n');
+		}
 		break;
-	}
 
-	case NODE_HEADER:
-		end_header[3] = '0' + node->as.header.level;
-		strbuf_puts(html, end_header);
+	case CMARK_NODE_CODE:
+		cmark_strbuf_puts(html, "<code>");
+		escape_html(html, node->as.literal.data, node->as.literal.len);
+		cmark_strbuf_puts(html, "</code>");
 		break;
 
-	case NODE_CODE_BLOCK:
-		strbuf_puts(html, "</code></pre>\n");
+	case CMARK_NODE_INLINE_HTML:
+		cmark_strbuf_put(html, node->as.literal.data, node->as.literal.len);
 		break;
 
-	case NODE_INLINE_CODE:
-		strbuf_puts(html, "</code>");
+	case CMARK_NODE_STRONG:
+		if (entering) {
+			cmark_strbuf_puts(html, "<strong>");
+		} else {
+			cmark_strbuf_puts(html, "</strong>");
+		}
 		break;
 
-	case NODE_LINK:
-		strbuf_puts(html, "</a>");
+	case CMARK_NODE_EMPH:
+		if (entering) {
+			cmark_strbuf_puts(html, "<em>");
+		} else {
+			cmark_strbuf_puts(html, "</em>");
+		}
 		break;
 
-	case NODE_STRONG:
-		strbuf_puts(html, "</strong>");
+	case CMARK_NODE_LINK:
+		if (entering) {
+			cmark_strbuf_puts(html, "<a href=\"");
+			if (node->as.link.url)
+				escape_href(html, node->as.link.url, -1);
+
+			if (node->as.link.title) {
+				cmark_strbuf_puts(html, "\" title=\"");
+				escape_html(html, node->as.link.title, -1);
+			}
+
+			cmark_strbuf_puts(html, "\">");
+		} else {
+			cmark_strbuf_puts(html, "</a>");
+		}
 		break;
 
-	case NODE_EMPH:
-		strbuf_puts(html, "</em>");
+	case CMARK_NODE_IMAGE:
+		if (entering) {
+			cmark_strbuf_puts(html, "<img src=\"");
+			if (node->as.link.url)
+				escape_href(html, node->as.link.url, -1);
+
+			cmark_strbuf_puts(html, "\" alt=\"");
+			state->plain = node;
+		} else {
+			if (node->as.link.title) {
+				cmark_strbuf_puts(html, "\" title=\"");
+				escape_html(html, node->as.link.title, -1);
+			}
+
+			cmark_strbuf_puts(html, "\" />");
+		}
 		break;
 
 	default:
+		assert(false);
 		break;
 	}
 
-	return tight;
+	// cmark_strbuf_putc(html, 'x');
+	return 1;
 }
 
-char *cmark_render_html(cmark_node *root)
+char *cmark_render_html(cmark_node *root, long options)
 {
 	char *result;
-	strbuf html = GH_BUF_INIT;
-	node_to_html(&html, root);
-	result = (char *)strbuf_detach(&html);
-	strbuf_free(&html);
+	cmark_strbuf html = GH_BUF_INIT;
+	cmark_event_type ev_type;
+	cmark_node *cur;
+	struct render_state state = { &html, NULL };
+	cmark_iter *iter = cmark_iter_new(root);
+
+	while ((ev_type = cmark_iter_next(iter)) != CMARK_EVENT_DONE) {
+		cur = cmark_iter_get_node(iter);
+		S_render_node(cur, ev_type, &state, options);
+	}
+	result = (char *)cmark_strbuf_detach(&html);
+
+	cmark_iter_free(iter);
+	cmark_strbuf_free(&html);
 	return result;
 }


Mime
View raw message