packages feed

sundown 0.4.1.2 → 0.4.2

raw patch · 9 files changed

+325/−161 lines, 9 files

Files

cbits/autolink.c view
@@ -15,12 +15,17 @@  */  #include "buffer.h"+#include "autolink.h"  #include <string.h> #include <stdlib.h> #include <stdio.h> #include <ctype.h> +#if defined(_WIN32)+#define strncasecmp	_strnicmp+#endif+ int sd_autolink_issafe(const uint8_t *link, size_t link_len) {@@ -128,7 +133,7 @@ }  static size_t-check_domain(uint8_t *data, size_t size)+check_domain(uint8_t *data, size_t size, int allow_short) { 	size_t i, np = 0; @@ -140,13 +145,27 @@ 		else if (!isalnum(data[i]) && data[i] != '-') break; 	} -	/* a valid domain needs to have at least a dot.-	 * that's as far as we get */-	return np ? i : 0;+	if (allow_short) {+		/* We don't need a valid domain in the strict sense (with+		 * least one dot; so just make sure it's composed of valid+		 * domain characters and return the length of the the valid+		 * sequence. */+		return i;+	} else {+		/* a valid domain needs to have at least a dot.+		 * that's as far as we get */+		return np ? i : 0;+	} }  size_t-sd_autolink__www(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size)+sd_autolink__www(+	size_t *rewind_p,+	struct buf *link,+	uint8_t *data,+	size_t offset,+	size_t size,+	unsigned int flags) { 	size_t link_end; @@ -156,7 +175,7 @@ 	if (size < 4 || memcmp(data, "www.", strlen("www.")) != 0) 		return 0; -	link_end = check_domain(data, size);+	link_end = check_domain(data, size, 0);  	if (link_end == 0) 		return 0;@@ -176,7 +195,13 @@ }  size_t-sd_autolink__email(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size)+sd_autolink__email(+	size_t *rewind_p,+	struct buf *link,+	uint8_t *data,+	size_t offset,+	size_t size,+	unsigned int flags) { 	size_t link_end, rewind; 	int nb = 0, np = 0;@@ -225,7 +250,13 @@ }  size_t-sd_autolink__url(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size)+sd_autolink__url(+	size_t *rewind_p,+	struct buf *link,+	uint8_t *data,+	size_t offset,+	size_t size,+	unsigned int flags) { 	size_t link_end, rewind = 0, domain_len; @@ -237,9 +268,14 @@  	if (!sd_autolink_issafe(data - rewind, size + rewind)) 		return 0;+ 	link_end = strlen("://"); -	domain_len = check_domain(data + link_end, size - link_end);+	domain_len = check_domain(+		data + link_end,+		size - link_end,+		flags & SD_AUTOLINK_SHORT_DOMAINS);+ 	if (domain_len == 0) 		return 0; 
cbits/autolink.h view
@@ -19,17 +19,32 @@  #include "buffer.h" -extern int+#ifdef __cplusplus+extern "C" {+#endif++enum {+	SD_AUTOLINK_SHORT_DOMAINS = (1 << 0),+};++int sd_autolink_issafe(const uint8_t *link, size_t link_len); -extern size_t-sd_autolink__www(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size);+size_t+sd_autolink__www(size_t *rewind_p, struct buf *link,+	uint8_t *data, size_t offset, size_t size, unsigned int flags); -extern size_t-sd_autolink__email(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size);+size_t+sd_autolink__email(size_t *rewind_p, struct buf *link,+	uint8_t *data, size_t offset, size_t size, unsigned int flags); -extern size_t-sd_autolink__url(size_t *rewind_p, struct buf *link, uint8_t *data, size_t offset, size_t size);+size_t+sd_autolink__url(size_t *rewind_p, struct buf *link,+	uint8_t *data, size_t offset, size_t size, unsigned int flags);++#ifdef __cplusplus+}+#endif  #endif 
cbits/buffer.c view
@@ -127,7 +127,9 @@  	if (n < 0) { #ifdef _MSC_VER+		va_start(ap, fmt); 		n = _vscprintf(fmt, ap);+		va_end(ap); #else 		return; #endif
cbits/buffer.h view
@@ -22,6 +22,10 @@ #include <stdarg.h> #include <stdint.h> +#ifdef __cplusplus+extern "C" {+#endif+ #if defined(_MSC_VER) #define __attribute__(x) #define inline@@ -84,5 +88,9 @@  /* bufprintf: formatted printing to a buffer */ void bufprintf(struct buf *, const char *, ...) __attribute__ ((format (printf, 2, 3)));++#ifdef __cplusplus+}+#endif  #endif
cbits/markdown.c view
@@ -25,6 +25,10 @@ #include <ctype.h> #include <stdio.h> +#if defined(_WIN32)+#define strncasecmp	_strnicmp+#endif+ #define REF_TABLE_SIZE 8  #define BUFFER_BLOCK 0@@ -767,7 +771,7 @@  	link = rndr_newbuf(rndr, BUFFER_SPAN); -	if ((link_len = sd_autolink__www(&rewind, link, data, offset, size)) > 0) {+	if ((link_len = sd_autolink__www(&rewind, link, data, offset, size, 0)) > 0) { 		link_url = rndr_newbuf(rndr, BUFFER_SPAN); 		BUFPUTSL(link_url, "http://"); 		bufput(link_url, link->data, link->size);@@ -799,7 +803,7 @@  	link = rndr_newbuf(rndr, BUFFER_SPAN); -	if ((link_len = sd_autolink__email(&rewind, link, data, offset, size)) > 0) {+	if ((link_len = sd_autolink__email(&rewind, link, data, offset, size, 0)) > 0) { 		ob->size -= rewind; 		rndr->cb.autolink(ob, link, MKDA_EMAIL, rndr->opaque); 	}@@ -819,7 +823,7 @@  	link = rndr_newbuf(rndr, BUFFER_SPAN); -	if ((link_len = sd_autolink__url(&rewind, link, data, offset, size)) > 0) {+	if ((link_len = sd_autolink__url(&rewind, link, data, offset, size, 0)) > 0) { 		ob->size -= rewind; 		rndr->cb.autolink(ob, link, MKDA_NORMAL, rndr->opaque); 	}@@ -1150,9 +1154,10 @@ 	return n >= 3; } -/* check if a line is a code fence; return its size if it is */+/* check if a line begins with a code fence; return the+ * width of the code fence */ static size_t-is_codefence(uint8_t *data, size_t size, struct buf *syntax)+prefix_codefence(uint8_t *data, size_t size) { 	size_t i = 0, n = 0; 	uint8_t c;@@ -1177,43 +1182,56 @@ 	if (n < 3) 		return 0; -	if (syntax != NULL) {-		size_t syn = 0;+	return i;+} -		while (i < size && data[i] == ' ')-			i++;+/* check if a line is a code fence; return its size if it is */+static size_t+is_codefence(uint8_t *data, size_t size, struct buf *syntax)+{+	size_t i = 0, syn_len = 0;+	uint8_t *syn_start; -		syntax->data = data + i;+	i = prefix_codefence(data, size);+	if (i == 0)+		return 0; -		if (i < size && data[i] == '{') {-			i++; syntax->data++;+	while (i < size && data[i] == ' ')+		i++; -			while (i < size && data[i] != '}' && data[i] != '\n') {-				syn++; i++;-			}+	syn_start = data + i; -			if (i == size || data[i] != '}')-				return 0;+	if (i < size && data[i] == '{') {+		i++; syn_start++; -			/* strip all whitespace at the beginning and the end-			 * of the {} block */-			while (syn > 0 && _isspace(syntax->data[0])) {-				syntax->data++; syn--;-			}+		while (i < size && data[i] != '}' && data[i] != '\n') {+			syn_len++; i++;+		} -			while (syn > 0 && _isspace(syntax->data[syn - 1]))-				syn--;+		if (i == size || data[i] != '}')+			return 0; -			i++;-		} else {-			while (i < size && !_isspace(data[i])) {-				syn++; i++;-			}+		/* strip all whitespace at the beginning and the end+		 * of the {} block */+		while (syn_len > 0 && _isspace(syn_start[0])) {+			syn_start++; syn_len--; 		} -		syntax->size = syn;+		while (syn_len > 0 && _isspace(syn_start[syn_len - 1]))+			syn_len--;++		i++;+	} else {+		while (i < size && !_isspace(data[i])) {+			syn_len++; i++;+		} 	} +	if (syntax) {+		syntax->data = syn_start;+		syntax->size = syn_len;+	}+ 	while (i < size && data[i] != '\n') { 		if (!_isspace(data[i])) 			return 0;@@ -1416,19 +1434,48 @@ 	while (i < size) { 		for (end = i + 1; end < size && data[end - 1] != '\n'; end++) /* empty */; -		if (is_empty(data + i, size - i) || (level = is_headerline(data + i, size - i)) != 0)+		if (is_empty(data + i, size - i)) 			break; -		if (rndr->ext_flags & MKDEXT_LAX_HTML_BLOCKS) {-			if (data[i] == '<' && rndr->cb.blockhtml && parse_htmlblock(ob, rndr, data + i, size - i, 0)) {+		if ((level = is_headerline(data + i, size - i)) != 0)+			break;++		if (is_atxheader(rndr, data + i, size - i) ||+			is_hrule(data + i, size - i) ||+			prefix_quote(data + i, size - i)) {+			end = i;+			break;+		}++		/*+		 * Early termination of a paragraph with the same logic+		 * as Markdown 1.0.0. If this logic is applied, the+		 * Markdown 1.0.3 test suite won't pass cleanly+		 *+		 * :: If the first character in a new line is not a letter,+		 * let's check to see if there's some kind of block starting+		 * here+		 */+		if ((rndr->ext_flags & MKDEXT_LAX_SPACING) && !isalnum(data[i])) {+			if (prefix_oli(data + i, size - i) ||+				prefix_uli(data + i, size - i)) { 				end = i; 				break; 			}-		} -		if (is_atxheader(rndr, data + i, size - i) || is_hrule(data + i, size - i)) {-			end = i;-			break;+			/* see if an html block starts here */+			if (data[i] == '<' && rndr->cb.blockhtml &&+				parse_htmlblock(ob, rndr, data + i, size - i, 0)) {+				end = i;+				break;+			}++			/* see if a code fence starts here */+			if ((rndr->ext_flags & MKDEXT_FENCED_CODE) != 0 &&+				is_codefence(data + i, size - i, NULL) != 0) {+				end = i;+				break;+			} 		}  		i = end;@@ -1500,9 +1547,10 @@  	while (beg < size) { 		size_t fence_end;+		struct buf fence_trail = { 0, 0, 0, 0 }; -		fence_end = is_codefence(data + beg, size - beg, NULL);-		if (fence_end != 0) {+		fence_end = is_codefence(data + beg, size - beg, &fence_trail);+		if (fence_end != 0 && fence_trail.size == 0) { 			beg += fence_end; 			break; 		}@@ -1577,8 +1625,7 @@ { 	struct buf *work = 0, *inter = 0; 	size_t beg = 0, end, pre, sublist = 0, orgpre = 0, i;-	int in_empty = 0, has_inside_empty = 0;-	size_t has_next_uli, has_next_oli;+	int in_empty = 0, has_inside_empty = 0, in_fence = 0;  	/* keeping track of the first indentation prefix */ 	while (orgpre < 3 && orgpre < size && data[orgpre] == ' ')@@ -1606,6 +1653,8 @@  	/* process the following lines */ 	while (beg < size) {+		size_t has_next_uli = 0, has_next_oli = 0;+ 		end++;  		while (end < size && data[end - 1] != '\n')@@ -1625,9 +1674,18 @@  		pre = i; -		has_next_uli = prefix_uli(data + beg + i, end - beg - i);-		has_next_oli = prefix_oli(data + beg + i, end - beg - i);+		if (rndr->ext_flags & MKDEXT_FENCED_CODE) {+			if (is_codefence(data + beg + i, end - beg - i, NULL) != 0)+				in_fence = !in_fence;+		} +		/* Only check for new list items if we are **not** inside+		 * a fenced code block */+		if (!in_fence) {+			has_next_uli = prefix_uli(data + beg + i, end - beg - i);+			has_next_oli = prefix_oli(data + beg + i, end - beg - i);+		}+ 		/* checking for ul/ol switch */ 		if (in_empty && ( 			((*flags & MKD_LIST_ORDERED) && has_next_uli) ||@@ -1647,10 +1705,12 @@ 			if (!sublist) 				sublist = work->size; 		}-		/* joining only indented stuff after empty lines */-		else if (in_empty && i < 4) {-				*flags |= MKD_LI_END;-				break;+		/* joining only indented stuff after empty lines;+		 * note that now we only require 1 space of indentation+		 * to continue a list */+		else if (in_empty && pre == 0) {+			*flags |= MKD_LI_END;+			break; 		} 		else if (in_empty) { 			bufputc(work, '\n');@@ -1758,7 +1818,12 @@ /* htmlblock_end • checking end of HTML block : </tag>[ \t]*\n[ \t*]\n */ /*	returns the length on match, 0 otherwise */ static size_t-htmlblock_end(const char *tag, size_t tag_len, struct sd_markdown *rndr, uint8_t *data, size_t size)+htmlblock_end_tag(+	const char *tag,+	size_t tag_len,+	struct sd_markdown *rndr,+	uint8_t *data,+	size_t size) { 	size_t i, w; @@ -1776,25 +1841,60 @@ 	i += w; 	w = 0; -	if (rndr->ext_flags & MKDEXT_LAX_HTML_BLOCKS) {-		if (i < size)-			w = is_empty(data + i, size - i);-	} else  {-		if (i < size && (w = is_empty(data + i, size - i)) == 0)-			return 0; /* non-blank line after tag line */-	}+	if (i < size)+		w = is_empty(data + i, size - i);  	return i + w; } +static size_t+htmlblock_end(const char *curtag,+	struct sd_markdown *rndr,+	uint8_t *data,+	size_t size,+	int start_of_line)+{+	size_t tag_size = strlen(curtag);+	size_t i = 1, end_tag;+	int block_lines = 0; +	while (i < size) {+		i++;+		while (i < size && !(data[i - 1] == '<' && data[i] == '/')) {+			if (data[i] == '\n')+				block_lines++;++			i++;+		}++		/* If we are only looking for unindented tags, skip the tag+		 * if it doesn't follow a newline.+		 *+		 * The only exception to this is if the tag is still on the+		 * initial line; in that case it still counts as a closing+		 * tag+		 */+		if (start_of_line && block_lines > 0 && data[i - 2] != '\n')+			continue;++		if (i + 2 + tag_size >= size)+			break;++		end_tag = htmlblock_end_tag(curtag, tag_size, rndr, data + i - 1, size - i + 1);+		if (end_tag)+			return i + end_tag - 1;+	}++	return 0;+}++ /* parse_htmlblock • parsing of inline HTML block */ static size_t parse_htmlblock(struct buf *ob, struct sd_markdown *rndr, uint8_t *data, size_t size, int do_render) {-	size_t i, j = 0;+	size_t i, j = 0, tag_end; 	const char *curtag = NULL;-	int found; 	struct buf work = { data, 0, 0, 0 };  	/* identification of the opening tag */@@ -1855,40 +1955,23 @@  	/* looking for an unindented matching closing tag */ 	/*	followed by a blank line */-	i = 1;-	found = 0;+	tag_end = htmlblock_end(curtag, rndr, data, size, 1);  	/* if not found, trying a second pass looking for indented match */ 	/* but not if tag is "ins" or "del" (following original Markdown.pl) */-	if (strcmp(curtag, "ins") != 0 && strcmp(curtag, "del") != 0) {-		size_t tag_size = strlen(curtag);-		i = 1;-		while (i < size) {-			i++;-			while (i < size && !(data[i - 1] == '<' && data[i] == '/'))-				i++;--			if (i + 2 + tag_size >= size)-				break;--			j = htmlblock_end(curtag, tag_size, rndr, data + i - 1, size - i + 1);--			if (j) {-				i += j - 1;-				found = 1;-				break;-			}-		}+	if (!tag_end && strcmp(curtag, "ins") != 0 && strcmp(curtag, "del") != 0) {+		tag_end = htmlblock_end(curtag, rndr, data, size, 0); 	} -	if (!found) return 0;+	if (!tag_end)+		return 0;  	/* the end of the block has been found */-	work.size = i;+	work.size = tag_end; 	if (do_render && rndr->cb.blockhtml) 		rndr->cb.blockhtml(ob, &work, rndr->opaque); -	return i;+	return tag_end; }  static void@@ -1970,10 +2053,13 @@  	header_end = i; +	while (header_end > 0 && _isspace(data[header_end - 1]))+		header_end--;+ 	if (data[0] == '|') 		pipes--; -	if (i > 2 && data[i - 1] == '|')+	if (header_end && data[header_end - 1] == '|') 		pipes--;  	*columns = pipes + 1;@@ -2247,8 +2333,8 @@ 			line_end = title_end; 			title_end = i; } } -	if (!line_end)-		return 0; /* garbage after the link */+	if (!line_end || link_end == link_offset)+		return 0; /* garbage after the link empty link */  	/* a valid ref has been found, filling-in return structures */ 	if (last)@@ -2258,6 +2344,8 @@ 		struct link_ref *ref;  		ref = add_link_ref(refs, data + id_offset, id_end - id_offset);+		if (!ref)+			return 0;  		ref->link = bufnew(link_end - link_offset); 		bufput(ref->link, data + link_offset, link_end - link_offset);@@ -2455,9 +2543,9 @@ void sd_version(int *ver_major, int *ver_minor, int *ver_revision) {-	*ver_major = UPSKIRT_VER_MAJOR;-	*ver_minor = UPSKIRT_VER_MINOR;-	*ver_revision = UPSKIRT_VER_REVISION;+	*ver_major = SUNDOWN_VER_MAJOR;+	*ver_minor = SUNDOWN_VER_MINOR;+	*ver_revision = SUNDOWN_VER_REVISION; }  /* vim: set filetype=c: */
cbits/markdown.h view
@@ -22,11 +22,15 @@ #include "buffer.h" #include "autolink.h" -#define UPSKIRT_VERSION "1.15.2"-#define UPSKIRT_VER_MAJOR 1-#define UPSKIRT_VER_MINOR 15-#define UPSKIRT_VER_REVISION 2+#ifdef __cplusplus+extern "C" {+#endif +#define SUNDOWN_VERSION "1.16.0"+#define SUNDOWN_VER_MAJOR 1+#define SUNDOWN_VER_MINOR 16+#define SUNDOWN_VER_REVISION 0+ /********************  * TYPE DEFINITIONS *  ********************/@@ -52,9 +56,9 @@ 	MKDEXT_FENCED_CODE = (1 << 2), 	MKDEXT_AUTOLINK = (1 << 3), 	MKDEXT_STRIKETHROUGH = (1 << 4),-	MKDEXT_LAX_HTML_BLOCKS = (1 << 5), 	MKDEXT_SPACE_HEADERS = (1 << 6), 	MKDEXT_SUPERSCRIPT = (1 << 7),+	MKDEXT_LAX_SPACING = (1 << 8), };  /* sd_callbacks - functions for rendering parsed data */@@ -124,6 +128,10 @@  extern void sd_version(int *major, int *minor, int *revision);++#ifdef __cplusplus+}+#endif  #endif 
cbits/stack.h view
@@ -3,6 +3,10 @@  #include <stdlib.h> +#ifdef __cplusplus+extern "C" {+#endif+ struct stack { 	void **item; 	size_t size;@@ -17,5 +21,9 @@  void *stack_pop(struct stack *); void *stack_top(struct stack *);++#ifdef __cplusplus+}+#endif  #endif
src/Text/Sundown/Markdown/Foreign.hsc view
@@ -17,22 +17,23 @@ #include "markdown.h"  -- | A set of switches to enable or disable markdown features.-data Extensions = Extensions { extNoIntraEmphasis :: Bool -- ^ Turn off underscores insode a word-                                                         --   does designating emphasis.-                             , extTables :: Bool-                             , extFencedCode :: Bool -- ^ Turns on a non-indentation form of-                                                    -- code-blocks, by blocking off a regionwith ~-                                                    -- or \`.-                             , extAutolink :: Bool -- ^ Turn things that look like URLs and email-                                                  -- addresses into links-                             , extStrikethrough :: Bool -- ^ Surround text with `~` to designate it-                                                       -- as struck through-                             , extLaxHtmlBlocks :: Bool -- ^ Allow HTML markup inside of paragraphs,-                                                       -- instead requireing tags to be on separate-                                                       -- lines-                             , extSpaceHeaders :: Bool-                             , extSuperscript :: Bool-                             }+data Extensions = Extensions+  { extNoIntraEmphasis :: Bool+    -- ^ Turn off underscores insode a word does designating emphasis.+  , extTables :: Bool+  , extFencedCode :: Bool+    -- ^ Turns on a non-indentation form of code-blocks, by blocking off a+    --   regionwith ~ or \`.+  , extAutolink :: Bool+    -- ^ Turn things that look like URLs and email addresses into links+  , extStrikethrough :: Bool+    -- ^ Surround text with `~` to designate it as struck through+  , extSpaceHeaders :: Bool+  , extSuperscript :: Bool+  , extLaxSpacing :: Bool+    -- ^ Allow blocks inside of paragraphs, instead requireing tags to be on+    --   separate lines+  }  instance Flag Extensions where   flagIndexes exts = [ (#{const MKDEXT_NO_INTRA_EMPHASIS}, extNoIntraEmphasis exts)@@ -40,9 +41,9 @@                      , (#{const MKDEXT_FENCED_CODE}, extFencedCode exts)                      , (#{const MKDEXT_AUTOLINK}, extAutolink exts)                      , (#{const MKDEXT_STRIKETHROUGH}, extStrikethrough exts)-                     , (#{const MKDEXT_LAX_HTML_BLOCKS}, extLaxHtmlBlocks exts)                      , (#{const MKDEXT_SPACE_HEADERS}, extSpaceHeaders exts)                      , (#{const MKDEXT_SUPERSCRIPT}, extSuperscript exts)+                     , (#{const MKDEXT_LAX_SPACING}, extLaxSpacing exts)                      ]  
sundown.cabal view
@@ -1,49 +1,47 @@-Cabal-version:          >= 1.6-Name:                   sundown-Version:                0.4.1.2-Author:                 Francesco Mazzoli (f@mazzo.li)-Maintainer:             Francesco Mazzoli (f@mazzo.li)-Build-Type:             Simple-License:                PublicDomain-Build-Type:             Simple-Category:               Foreign binding, Text-Synopsis:               Bindings to the sundown markdown library-Tested-With:            GHC==7.2.2-Homepage:               https://github.com/bitonic/sundown-Bug-Reports:            https://github.com/bitonic/sundown/issues+Cabal-version:      >= 1.6+Name:               sundown+Version:            0.4.2+Author:             Francesco Mazzoli (f@mazzo.li)+Maintainer:         Francesco Mazzoli (f@mazzo.li)+Build-Type:         Simple+License:            PublicDomain+Build-Type:         Simple+Category:           Foreign binding, Text+Synopsis:           Bindings to the sundown markdown library+Tested-With:        GHC==7.4.2, GHC==7.2.2, GHC==7.0.4, GHC==6.12.3+Homepage:           https://github.com/bitonic/sundown+Bug-Reports:        https://github.com/bitonic/sundown/issues Description:-  Bindings to the github fork of sundown, a nice C markdown library:-  <https://github.com/tanoku/sundown>+  Bindings to GitHub's C markdown library: <https://github.com/tanoku/sundown>  source-repository head   type:     git   location: git://github.com/bitonic/sundown.git  Library-  Hs-Source-Dirs:       src--  Build-Depends:        base >= 3 && < 5-                      , bytestring--  GHC-Options:          -Wall -O2 -fno-cse--  Extensions:           ForeignFunctionInterface, EmptyDataDecls+  Hs-Source-Dirs:   src+  Build-Depends:    base >= 3 && < 5, bytestring+  GHC-Options:      -Wall -O2 -fno-cse+  Extensions:       ForeignFunctionInterface, EmptyDataDecls -  Exposed-Modules:      Text.Sundown-                      , Text.Sundown.Markdown-                      , Text.Sundown.Renderers.Html+  Exposed-Modules:  Text.Sundown,+                    Text.Sundown.Markdown,+                    Text.Sundown.Renderers.Html -  Other-Modules:        Text.Sundown.Buffer.Foreign-                      , Text.Sundown.Renderers.Html.Foreign-                      , Text.Sundown.Flag-                      , Text.Sundown.Markdown.Foreign+  Other-Modules:    Text.Sundown.Buffer.Foreign,+                    Text.Sundown.Renderers.Html.Foreign,+                    Text.Sundown.Flag,+                    Text.Sundown.Markdown.Foreign -  C-Sources:            cbits/autolink.c, cbits/buffer.c, cbits/houdini_href_e.c,-                        cbits/houdini_html_e.c, cbits/html.c, cbits/html_smartypants.c,-                        cbits/markdown.c, cbits/stack.c+  C-Sources:        cbits/autolink.c, cbits/buffer.c,+                    cbits/houdini_href_e.c, cbits/houdini_html_e.c,+                    cbits/html.c, cbits/html_smartypants.c,+                    cbits/markdown.c, cbits/stack.c -  Include-Dirs:         cbits+  Include-Dirs:     cbits -  Includes:             autolink.h, buffer.h, html.h, html_blocks.h, markdown.h, stack.h+  Includes:         autolink.h, buffer.h, html.h, html_blocks.h, markdown.h,+                    stack.h -  Install-includes:     autolink.h, buffer.h, houdini.h, html.h, html_blocks.h, markdown.h, stack.h+  Install-includes: autolink.h, buffer.h, houdini.h, html.h, html_blocks.h,+                    markdown.h, stack.h