aboutsummaryrefslogtreecommitdiff
path: root/src/print.c
blob: 3c852400077586e331760ceaea14ca7c1fd4a438 (plain)
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <string.h>
  4. #include "ast.h"
  5. #include "cmark.h"
  6. #include "node.h"
  7. #include "debug.h"
  8. static void print_str(const unsigned char *s, int len)
  9. {
  10. int i;
  11. if (len < 0)
  12. len = strlen((char *)s);
  13. putchar('"');
  14. for (i = 0; i < len; ++i) {
  15. unsigned char c = s[i];
  16. switch (c) {
  17. case '\n':
  18. printf("\\n");
  19. break;
  20. case '"':
  21. printf("\\\"");
  22. break;
  23. case '\\':
  24. printf("\\\\");
  25. break;
  26. default:
  27. putchar((int)c);
  28. }
  29. }
  30. putchar('"');
  31. }
  32. // Prettyprint an inline list, for debugging.
  33. static void print_inlines(cmark_node* ils, int indent)
  34. {
  35. int i;
  36. while(ils != NULL) {
  37. for (i=0; i < indent; i++) {
  38. putchar(' ');
  39. }
  40. switch(ils->type) {
  41. case NODE_STRING:
  42. printf("str ");
  43. print_str(ils->as.literal.data, ils->as.literal.len);
  44. putchar('\n');
  45. break;
  46. case NODE_LINEBREAK:
  47. printf("linebreak\n");
  48. break;
  49. case NODE_SOFTBREAK:
  50. printf("softbreak\n");
  51. break;
  52. case NODE_INLINE_CODE:
  53. printf("code ");
  54. print_str(ils->as.literal.data, ils->as.literal.len);
  55. putchar('\n');
  56. break;
  57. case NODE_INLINE_HTML:
  58. printf("html ");
  59. print_str(ils->as.literal.data, ils->as.literal.len);
  60. putchar('\n');
  61. break;
  62. case NODE_LINK:
  63. case NODE_IMAGE:
  64. printf("%s url=", ils->type == NODE_LINK ? "link" : "image");
  65. if (ils->as.link.url)
  66. print_str(ils->as.link.url, -1);
  67. if (ils->as.link.title) {
  68. printf(" title=");
  69. print_str(ils->as.link.title, -1);
  70. }
  71. putchar('\n');
  72. print_inlines(ils->as.link.label, indent + 2);
  73. break;
  74. case NODE_STRONG:
  75. printf("strong\n");
  76. print_inlines(ils->as.link.label, indent + 2);
  77. break;
  78. case NODE_EMPH:
  79. printf("emph\n");
  80. print_inlines(ils->as.link.label, indent + 2);
  81. break;
  82. default:
  83. break;
  84. }
  85. ils = ils->next;
  86. }
  87. }
  88. // Functions to pretty-print inline and cmark_node lists, for debugging.
  89. // Prettyprint an inline list, for debugging.
  90. static void print_blocks(cmark_node* b, int indent)
  91. {
  92. cmark_list *data;
  93. int i;
  94. while(b != NULL) {
  95. for (i=0; i < indent; i++) {
  96. putchar(' ');
  97. }
  98. switch(b->type) {
  99. case NODE_DOCUMENT:
  100. printf("document\n");
  101. print_blocks(b->first_child, indent + 2);
  102. break;
  103. case NODE_BQUOTE:
  104. printf("block_quote\n");
  105. print_blocks(b->first_child, indent + 2);
  106. break;
  107. case NODE_LIST_ITEM:
  108. printf("list_item\n");
  109. print_blocks(b->first_child, indent + 2);
  110. break;
  111. case NODE_LIST:
  112. data = &(b->as.list);
  113. if (data->list_type == CMARK_ORDERED_LIST) {
  114. printf("list (type=ordered tight=%s start=%d delim=%s)\n",
  115. (data->tight ? "true" : "false"),
  116. data->start,
  117. (data->delimiter == CMARK_PAREN_DELIM ? "parens" : "period"));
  118. } else {
  119. printf("list (type=bullet tight=%s bullet_char=%c)\n",
  120. (data->tight ? "true" : "false"),
  121. data->bullet_char);
  122. }
  123. print_blocks(b->first_child, indent + 2);
  124. break;
  125. case NODE_ATX_HEADER:
  126. printf("atx_header (level=%d)\n", b->as.header.level);
  127. print_inlines(b->first_child, indent + 2);
  128. break;
  129. case NODE_SETEXT_HEADER:
  130. printf("setext_header (level=%d)\n", b->as.header.level);
  131. print_inlines(b->first_child, indent + 2);
  132. break;
  133. case NODE_PARAGRAPH:
  134. printf("paragraph\n");
  135. print_inlines(b->first_child, indent + 2);
  136. break;
  137. case NODE_HRULE:
  138. printf("hrule\n");
  139. break;
  140. case NODE_INDENTED_CODE:
  141. printf("indented_code ");
  142. print_str(b->string_content.ptr, -1);
  143. putchar('\n');
  144. break;
  145. case NODE_FENCED_CODE:
  146. printf("fenced_code length=%d info=",
  147. b->as.code.fence_length);
  148. print_str(b->as.code.info.ptr, -1);
  149. putchar(' ');
  150. print_str(b->string_content.ptr, -1);
  151. putchar('\n');
  152. break;
  153. case NODE_HTML:
  154. printf("html_block ");
  155. print_str(b->string_content.ptr, -1);
  156. putchar('\n');
  157. break;
  158. case NODE_REFERENCE_DEF:
  159. printf("reference_def\n");
  160. break;
  161. default:
  162. printf("# NOT IMPLEMENTED (%d)\n", b->type);
  163. break;
  164. }
  165. b = b->next;
  166. }
  167. }
  168. void cmark_debug_print(cmark_node *root)
  169. {
  170. print_blocks(root, 0);
  171. }