rdiscount 1.3.1.1 → 1.3.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Rakefile +6 -3
- data/ext/Csio.c +49 -0
- data/ext/cstring.h +5 -0
- data/ext/extconf.rb +0 -6
- data/ext/generate.c +33 -23
- data/ext/markdown.c +18 -7
- data/ext/markdown.h +4 -0
- data/ext/mkdio.h +1 -0
- data/ext/rdiscount.c +24 -11
- data/ext/toc.c +38 -14
- data/lib/rdiscount.rb +1 -1
- data/rdiscount.gemspec +3 -4
- metadata +3 -4
- data/ext/rbstrio.c +0 -48
- data/ext/rbstrio.h +0 -4
data/Rakefile
CHANGED
@@ -99,14 +99,17 @@ end
|
|
99
99
|
desc 'Run conformance tests (MARKDOWN_TEST_VER=1.0)'
|
100
100
|
task 'test:conformance' => [:build] do |t|
|
101
101
|
script = "#{pwd}/bin/rdiscount"
|
102
|
-
test_version = ENV['MARKDOWN_TEST_VER'] || '1.0'
|
102
|
+
test_version = ENV['MARKDOWN_TEST_VER'] || '1.0.3'
|
103
103
|
chdir("test/MarkdownTest_#{test_version}") do
|
104
104
|
sh "./MarkdownTest.pl --script='#{script}' --tidy"
|
105
105
|
end
|
106
106
|
end
|
107
107
|
|
108
108
|
desc 'Run version 1.0 conformance suite'
|
109
|
-
task 'test:conformance:1.0' =>
|
109
|
+
task 'test:conformance:1.0' => [:build] do |t|
|
110
|
+
ENV['MARKDOWN_TEST_VER'] = '1.0'
|
111
|
+
Rake::Task['test:conformance'].invoke
|
112
|
+
end
|
110
113
|
|
111
114
|
desc 'Run 1.0.3 conformance suite'
|
112
115
|
task 'test:conformance:1.0.3' => [:build] do |t|
|
@@ -172,7 +175,7 @@ task :gather => 'discount' do |t|
|
|
172
175
|
files =
|
173
176
|
FileList[
|
174
177
|
'discount/{markdown,mkdio,amalloc,cstring}.h',
|
175
|
-
'discount/{markdown,docheader,dumptree,generate,mkdio,resource}.c'
|
178
|
+
'discount/{markdown,docheader,dumptree,generate,mkdio,resource,toc,Csio}.c'
|
176
179
|
]
|
177
180
|
cp files, 'ext/',
|
178
181
|
:preserve => true,
|
data/ext/Csio.c
ADDED
@@ -0,0 +1,49 @@
|
|
1
|
+
#include <stdio.h>
|
2
|
+
#include <string.h>
|
3
|
+
#include <stdarg.h>
|
4
|
+
#include "cstring.h"
|
5
|
+
#include "markdown.h"
|
6
|
+
#include "amalloc.h"
|
7
|
+
|
8
|
+
|
9
|
+
/* putc() into a cstring
|
10
|
+
*/
|
11
|
+
void
|
12
|
+
Csputc(int c, Cstring *iot)
|
13
|
+
{
|
14
|
+
EXPAND(*iot) = c;
|
15
|
+
}
|
16
|
+
|
17
|
+
|
18
|
+
/* printf() into a cstring
|
19
|
+
*/
|
20
|
+
int
|
21
|
+
Csprintf(Cstring *iot, char *fmt, ...)
|
22
|
+
{
|
23
|
+
va_list ptr;
|
24
|
+
int siz=100;
|
25
|
+
|
26
|
+
do {
|
27
|
+
RESERVE(*iot, siz);
|
28
|
+
va_start(ptr, fmt);
|
29
|
+
siz = vsnprintf(T(*iot)+S(*iot), ALL(*iot)-S(*iot), fmt, ptr);
|
30
|
+
va_end(ptr);
|
31
|
+
} while ( siz > (ALL(*iot)-S(*iot)) );
|
32
|
+
|
33
|
+
S(*iot) += siz;
|
34
|
+
return siz;
|
35
|
+
}
|
36
|
+
|
37
|
+
|
38
|
+
/* reparse() into a cstring
|
39
|
+
*/
|
40
|
+
void
|
41
|
+
Csreparse(Cstring *iot, char *buf, int size, int flags)
|
42
|
+
{
|
43
|
+
MMIOT f;
|
44
|
+
___mkd_initmmiot(&f, 0);
|
45
|
+
___mkd_reparse(buf, size, 0, &f);
|
46
|
+
___mkd_emblock(&f);
|
47
|
+
SUFFIX(*iot, T(f.out), S(f.out));
|
48
|
+
___mkd_freemmiot(&f, 0);
|
49
|
+
}
|
data/ext/cstring.h
CHANGED
@@ -50,6 +50,7 @@
|
|
50
50
|
*/
|
51
51
|
#define T(x) (x).text
|
52
52
|
#define S(x) (x).size
|
53
|
+
#define ALL(x) (x).alloc
|
53
54
|
|
54
55
|
/* abstract anchor type that defines a list base
|
55
56
|
* with a function that attaches an element to
|
@@ -65,4 +66,8 @@
|
|
65
66
|
|
66
67
|
typedef STRING(char) Cstring;
|
67
68
|
|
69
|
+
extern void Csputc(int, Cstring *);
|
70
|
+
extern int Csprintf(Cstring *, char *, ...);
|
71
|
+
extern void Csreparse(Cstring *, char *, int, int);
|
72
|
+
|
68
73
|
#endif/*_CSTRING_D*/
|
data/ext/extconf.rb
CHANGED
@@ -4,11 +4,5 @@ dir_config('rdiscount')
|
|
4
4
|
|
5
5
|
HAVE_RANDOM = have_func('random')
|
6
6
|
HAVE_SRANDOM = have_func('srandom')
|
7
|
-
HAVE_FUNOPEN = have_func('funopen')
|
8
|
-
HAVE_FOPENCOOKIE = have_func('fopencookie')
|
9
|
-
|
10
|
-
unless HAVE_FUNOPEN || HAVE_FOPENCOOKIE
|
11
|
-
fail "No funopen or fopencookie support available."
|
12
|
-
end
|
13
7
|
|
14
8
|
create_makefile('rdiscount')
|
data/ext/generate.c
CHANGED
@@ -277,10 +277,10 @@ emmatch(MMIOT *f, int go)
|
|
277
277
|
}
|
278
278
|
|
279
279
|
|
280
|
-
/*
|
280
|
+
/* ___mkd_emblock()
|
281
281
|
*/
|
282
|
-
|
283
|
-
|
282
|
+
void
|
283
|
+
___mkd_emblock(MMIOT *f)
|
284
284
|
{
|
285
285
|
int i;
|
286
286
|
block *p;
|
@@ -301,8 +301,8 @@ emblock(MMIOT *f)
|
|
301
301
|
|
302
302
|
/* generate html from a markup fragment
|
303
303
|
*/
|
304
|
-
|
305
|
-
|
304
|
+
void
|
305
|
+
___mkd_reparse(char *bfr, int size, int flags, MMIOT *f)
|
306
306
|
{
|
307
307
|
MMIOT sub;
|
308
308
|
|
@@ -316,7 +316,7 @@ reparse(char *bfr, int size, int flags, MMIOT *f)
|
|
316
316
|
S(sub.in)--;
|
317
317
|
|
318
318
|
text(&sub);
|
319
|
-
|
319
|
+
___mkd_emblock(&sub);
|
320
320
|
|
321
321
|
Qwrite(T(sub.out), S(sub.out), f);
|
322
322
|
|
@@ -497,12 +497,14 @@ linkykey(int image, Footnote *val, MMIOT *f)
|
|
497
497
|
{
|
498
498
|
Footnote *ret;
|
499
499
|
Cstring mylabel;
|
500
|
+
int here;
|
500
501
|
|
501
502
|
memset(val, 0, sizeof *val);
|
502
503
|
|
503
504
|
if ( (T(val->tag) = linkylabel(f, &S(val->tag))) == 0 )
|
504
505
|
return 0;
|
505
506
|
|
507
|
+
here = mmiottell(f);
|
506
508
|
eatspace(f);
|
507
509
|
switch ( pull(f) ) {
|
508
510
|
case '(':
|
@@ -517,14 +519,21 @@ linkykey(int image, Footnote *val, MMIOT *f)
|
|
517
519
|
|
518
520
|
return peek(f,0) == ')';
|
519
521
|
|
520
|
-
case '[':
|
522
|
+
case '[': /* footnote links /as defined in the standard/ */
|
523
|
+
default: /* footnote links -- undocumented extension */
|
521
524
|
/* footnote link */
|
522
525
|
mylabel = val->tag;
|
523
|
-
if ( (
|
524
|
-
|
526
|
+
if ( peek(f,0) == '[' ) {
|
527
|
+
if ( (T(val->tag) = linkylabel(f, &S(val->tag))) == 0 )
|
528
|
+
return 0;
|
525
529
|
|
526
|
-
|
527
|
-
|
530
|
+
if ( !S(val->tag) )
|
531
|
+
val->tag = mylabel;
|
532
|
+
}
|
533
|
+
else if ( f->flags & MKD_1_COMPAT )
|
534
|
+
break;
|
535
|
+
else
|
536
|
+
mmiotseek(f,here);
|
528
537
|
|
529
538
|
ret = bsearch(val, T(*f->footnotes), S(*f->footnotes),
|
530
539
|
sizeof *val, (stfu)__mkd_footsort);
|
@@ -633,12 +642,12 @@ linkylinky(int image, MMIOT *f)
|
|
633
642
|
|
634
643
|
if ( S(link.title) ) {
|
635
644
|
Qstring(" title=\"", f);
|
636
|
-
|
645
|
+
___mkd_reparse(T(link.title), S(link.title), INSIDE_TAG, f);
|
637
646
|
Qchar('"', f);
|
638
647
|
}
|
639
648
|
|
640
649
|
Qstring(tag->text_pfx, f);
|
641
|
-
|
650
|
+
___mkd_reparse(T(link.tag), S(link.tag), tag->flags, f);
|
642
651
|
Qstring(tag->text_sfx, f);
|
643
652
|
}
|
644
653
|
else
|
@@ -885,7 +894,7 @@ smartypants(int c, int *flags, MMIOT *f)
|
|
885
894
|
break;
|
886
895
|
else if ( c == '\'' && peek(f, j+1) == '\'' ) {
|
887
896
|
Qstring("“", f);
|
888
|
-
|
897
|
+
___mkd_reparse(cursor(f)+1, j-2, 0, f);
|
889
898
|
Qstring("”", f);
|
890
899
|
shift(f,j+1);
|
891
900
|
return 1;
|
@@ -951,7 +960,7 @@ text(MMIOT *f)
|
|
951
960
|
++len;
|
952
961
|
}
|
953
962
|
shift(f,len);
|
954
|
-
|
963
|
+
___mkd_reparse(sup, len, 0, f);
|
955
964
|
Qstring("</sup>", f);
|
956
965
|
}
|
957
966
|
break;
|
@@ -1134,6 +1143,7 @@ printblock(Paragraph *pp, MMIOT *f)
|
|
1134
1143
|
push("<br/>\n", 6, f);
|
1135
1144
|
}
|
1136
1145
|
else {
|
1146
|
+
___mkd_tidy(t);
|
1137
1147
|
push(T(t->text), S(t->text), f);
|
1138
1148
|
if ( t->next )
|
1139
1149
|
push("\n", 1, f);
|
@@ -1191,19 +1201,19 @@ printhtml(Line *t, MMIOT *f)
|
|
1191
1201
|
static void
|
1192
1202
|
htmlify(Paragraph *p, char *block, char *arguments, MMIOT *f)
|
1193
1203
|
{
|
1194
|
-
|
1204
|
+
___mkd_emblock(f);
|
1195
1205
|
if ( block )
|
1196
1206
|
Qprintf(f, arguments ? "<%s %s>" : "<%s>", block, arguments);
|
1197
|
-
|
1207
|
+
___mkd_emblock(f);
|
1198
1208
|
|
1199
1209
|
while (( p = display(p, f) )) {
|
1200
|
-
|
1210
|
+
___mkd_emblock(f);
|
1201
1211
|
Qstring("\n\n", f);
|
1202
1212
|
}
|
1203
1213
|
|
1204
1214
|
if ( block )
|
1205
1215
|
Qprintf(f, "</%s>", block);
|
1206
|
-
|
1216
|
+
___mkd_emblock(f);
|
1207
1217
|
}
|
1208
1218
|
|
1209
1219
|
|
@@ -1219,7 +1229,7 @@ definitionlist(Paragraph *p, MMIOT *f)
|
|
1219
1229
|
for ( ; p ; p = p->next) {
|
1220
1230
|
for ( tag = p->text; tag; tag = tag->next ) {
|
1221
1231
|
Qstring("<dt>", f);
|
1222
|
-
|
1232
|
+
___mkd_reparse(T(tag->text), S(tag->text), 0, f);
|
1223
1233
|
Qstring("</dt>\n", f);
|
1224
1234
|
}
|
1225
1235
|
|
@@ -1345,7 +1355,7 @@ mkd_document(Document *p, char **res)
|
|
1345
1355
|
}
|
1346
1356
|
|
1347
1357
|
|
1348
|
-
/* public interface for
|
1358
|
+
/* public interface for ___mkd_reparse()
|
1349
1359
|
*/
|
1350
1360
|
int
|
1351
1361
|
mkd_text(char *bfr, int size, FILE *output, int flags)
|
@@ -1355,8 +1365,8 @@ mkd_text(char *bfr, int size, FILE *output, int flags)
|
|
1355
1365
|
___mkd_initmmiot(&f, 0);
|
1356
1366
|
f.flags = flags & USER_FLAGS;
|
1357
1367
|
|
1358
|
-
|
1359
|
-
|
1368
|
+
___mkd_reparse(bfr, size, 0, &f);
|
1369
|
+
___mkd_emblock(&f);
|
1360
1370
|
if ( flags & CDATA_OUTPUT )
|
1361
1371
|
___mkd_xml(T(f.out), S(f.out), output);
|
1362
1372
|
else
|
data/ext/markdown.c
CHANGED
@@ -124,6 +124,14 @@ skipempty(Line *p)
|
|
124
124
|
}
|
125
125
|
|
126
126
|
|
127
|
+
void
|
128
|
+
___mkd_tidy(Line *t)
|
129
|
+
{
|
130
|
+
while ( S(t->text) && isspace(T(t->text)[S(t->text)-1]) )
|
131
|
+
--S(t->text);
|
132
|
+
}
|
133
|
+
|
134
|
+
|
127
135
|
static char *
|
128
136
|
isopentag(Line *p)
|
129
137
|
{
|
@@ -434,12 +442,6 @@ codeblock(Paragraph *p)
|
|
434
442
|
{
|
435
443
|
Line *t = p->text, *r;
|
436
444
|
|
437
|
-
/* HORRIBLE STANDARDS KLUDGE: the first line of every block
|
438
|
-
* has trailing whitespace trimmed off.
|
439
|
-
*/
|
440
|
-
while ( S(t->text) && isspace(T(t->text)[S(t->text)-1]) )
|
441
|
-
--S(t->text);
|
442
|
-
|
443
445
|
for ( ; t; t = r ) {
|
444
446
|
CLIP(t->text,0,4);
|
445
447
|
t->dle = mkd_firstnonblank(t);
|
@@ -492,12 +494,13 @@ textblock(Paragraph *p, int toplevel)
|
|
492
494
|
{
|
493
495
|
Line *t, *next;
|
494
496
|
|
495
|
-
for ( t = p->text; t ; t = next )
|
497
|
+
for ( t = p->text; t ; t = next ) {
|
496
498
|
if ( ((next = t->next) == 0) || endoftextblock(next, toplevel) ) {
|
497
499
|
p->align = centered(p->text, t);
|
498
500
|
t->next = 0;
|
499
501
|
return next;
|
500
502
|
}
|
503
|
+
}
|
501
504
|
return t;
|
502
505
|
}
|
503
506
|
|
@@ -833,6 +836,14 @@ compile(Line *ptr, int toplevel, MMIOT *f)
|
|
833
836
|
}
|
834
837
|
else if ( iscode(ptr) ) {
|
835
838
|
p = Pp(&d, ptr, CODE);
|
839
|
+
|
840
|
+
if ( f->flags & MKD_1_COMPAT) {
|
841
|
+
/* HORRIBLE STANDARDS KLUDGE: the first line of every block
|
842
|
+
* has trailing whitespace trimmed off.
|
843
|
+
*/
|
844
|
+
___mkd_tidy(p->text);
|
845
|
+
}
|
846
|
+
|
836
847
|
ptr = codeblock(p);
|
837
848
|
}
|
838
849
|
else if ( ishr(ptr) ) {
|
data/ext/markdown.h
CHANGED
@@ -74,6 +74,7 @@ typedef struct mmiot {
|
|
74
74
|
#define NO_PSEUDO_PROTO 0x0040
|
75
75
|
#define CDATA_OUTPUT 0x0080
|
76
76
|
#define TOC 0x1000
|
77
|
+
#define MKD_1_COMPAT 0x2000
|
77
78
|
#define USER_FLAGS 0xF0FF
|
78
79
|
#define EMBEDDED DENY_A|DENY_IMG|NO_PSEUDO_PROTO|CDATA_OUTPUT
|
79
80
|
char *base;
|
@@ -127,5 +128,8 @@ extern void ___mkd_initmmiot(MMIOT *, void *);
|
|
127
128
|
extern void ___mkd_freemmiot(MMIOT *, void *);
|
128
129
|
extern void ___mkd_freeLineRange(Line *, Line *);
|
129
130
|
extern void ___mkd_xml(char *, int, FILE *);
|
131
|
+
extern void ___mkd_reparse(char *, int, int, MMIOT*);
|
132
|
+
extern void ___mkd_emblock(MMIOT*);
|
133
|
+
extern void ___mkd_tidy(Line *);
|
130
134
|
|
131
135
|
#endif/*_MARKDOWN_D*/
|
data/ext/mkdio.h
CHANGED
@@ -54,6 +54,7 @@ extern char markdown_version[];
|
|
54
54
|
#define MKD_NO_EXT 0x0040 /* don't allow pseudo-protocols */
|
55
55
|
#define MKD_CDATA 0x0080 /* generate code for xml ![CDATA[...]] */
|
56
56
|
#define MKD_TOC 0x1000 /* do table-of-contents processing */
|
57
|
+
#define MKD_1_COMPAT 0x2000 /* compatability with MarkdownTest_1.0 */
|
57
58
|
#define MKD_EMBED MKD_NOLINKS|MKD_NOIMAGE|MKD_TAGTEXT
|
58
59
|
|
59
60
|
/* special flags for mkd_in() and mkd_string()
|
data/ext/rdiscount.c
CHANGED
@@ -1,7 +1,6 @@
|
|
1
1
|
#include <stdio.h>
|
2
2
|
#include "ruby.h"
|
3
3
|
#include "mkdio.h"
|
4
|
-
#include "rbstrio.h"
|
5
4
|
|
6
5
|
static VALUE rb_cRDiscount;
|
7
6
|
|
@@ -9,19 +8,25 @@ static VALUE
|
|
9
8
|
rb_rdiscount_to_html(int argc, VALUE *argv, VALUE self)
|
10
9
|
{
|
11
10
|
/* grab char pointer to markdown input text */
|
11
|
+
char *res;
|
12
|
+
int szres;
|
12
13
|
VALUE text = rb_funcall(self, rb_intern("text"), 0);
|
14
|
+
VALUE buf = rb_str_buf_new(1024);
|
13
15
|
Check_Type(text, T_STRING);
|
14
16
|
|
15
|
-
/* allocate a ruby string buffer and wrap it in a stream */
|
16
|
-
VALUE buf = rb_str_buf_new(4096);
|
17
|
-
FILE *stream = rb_str_io_new(buf);
|
18
|
-
|
19
17
|
int flags = rb_rdiscount__get_flags(self);
|
20
18
|
|
21
19
|
MMIOT *doc = mkd_string(RSTRING_PTR(text), RSTRING_LEN(text), flags);
|
22
|
-
markdown(doc, stream, flags);
|
23
20
|
|
24
|
-
|
21
|
+
if ( mkd_compile(doc, flags) ) {
|
22
|
+
szres = mkd_document(doc, &res);
|
23
|
+
|
24
|
+
if ( szres != EOF ) {
|
25
|
+
rb_str_cat(buf, res, szres);
|
26
|
+
rb_str_cat(buf, "\n", 1);
|
27
|
+
}
|
28
|
+
}
|
29
|
+
mkd_cleanup(doc);
|
25
30
|
|
26
31
|
return buf;
|
27
32
|
}
|
@@ -29,6 +34,9 @@ rb_rdiscount_to_html(int argc, VALUE *argv, VALUE self)
|
|
29
34
|
static VALUE
|
30
35
|
rb_rdiscount_toc_content(int argc, VALUE *argv, VALUE self)
|
31
36
|
{
|
37
|
+
char *res;
|
38
|
+
int szres;
|
39
|
+
|
32
40
|
int flags = rb_rdiscount__get_flags(self);
|
33
41
|
|
34
42
|
/* grab char pointer to markdown input text */
|
@@ -37,13 +45,18 @@ rb_rdiscount_toc_content(int argc, VALUE *argv, VALUE self)
|
|
37
45
|
|
38
46
|
/* allocate a ruby string buffer and wrap it in a stream */
|
39
47
|
VALUE buf = rb_str_buf_new(4096);
|
40
|
-
FILE *stream = rb_str_io_new(buf);
|
41
48
|
|
42
49
|
MMIOT *doc = mkd_string(RSTRING_PTR(text), RSTRING_LEN(text), flags);
|
43
|
-
mkd_compile(doc, flags);
|
44
|
-
mkd_generatetoc(doc, stream);
|
45
50
|
|
46
|
-
|
51
|
+
if ( mkd_compile(doc, flags) ) {
|
52
|
+
szres = mkd_toc(doc, &res);
|
53
|
+
|
54
|
+
if ( szres != EOF ) {
|
55
|
+
rb_str_cat(buf, res, szres);
|
56
|
+
rb_str_cat(buf, "\n", 1);
|
57
|
+
}
|
58
|
+
}
|
59
|
+
mkd_cleanup(doc);
|
47
60
|
|
48
61
|
return buf;
|
49
62
|
}
|
data/ext/toc.c
CHANGED
@@ -17,12 +17,16 @@
|
|
17
17
|
/* write an header index
|
18
18
|
*/
|
19
19
|
int
|
20
|
-
|
20
|
+
mkd_toc(Document *p, char **doc)
|
21
21
|
{
|
22
22
|
Paragraph *pp;
|
23
|
+
int last_hnumber = 0;
|
24
|
+
Cstring res;
|
25
|
+
|
26
|
+
CREATE(res);
|
27
|
+
RESERVE(res, 100);
|
23
28
|
|
24
|
-
|
25
|
-
first_hnumber = 0;
|
29
|
+
*doc = 0;
|
26
30
|
|
27
31
|
if ( !(p && p->ctx) ) return -1;
|
28
32
|
if ( ! (p->ctx->flags & TOC) ) return 0;
|
@@ -31,32 +35,52 @@ mkd_generatetoc(Document *p, FILE *output)
|
|
31
35
|
if ( pp->typ == HDR && pp->text ) {
|
32
36
|
|
33
37
|
if ( last_hnumber == pp->hnumber )
|
34
|
-
|
38
|
+
Csprintf(&res, "%*s</li>\n", pp->hnumber, "");
|
35
39
|
else while ( last_hnumber > pp->hnumber ) {
|
36
|
-
|
40
|
+
Csprintf(&res, "%*s</li>\n%*s</ul>\n",
|
37
41
|
last_hnumber, "",
|
38
42
|
last_hnumber-1,"");
|
39
43
|
--last_hnumber;
|
40
44
|
}
|
41
45
|
|
42
46
|
while ( pp->hnumber > last_hnumber ) {
|
43
|
-
|
47
|
+
Csprintf(&res, "\n%*s<ul>\n", pp->hnumber, "");
|
44
48
|
++last_hnumber;
|
45
49
|
}
|
46
|
-
|
47
|
-
mkd_string_to_anchor(T(pp->text->text), S(pp->text->text),
|
48
|
-
|
49
|
-
|
50
|
-
|
50
|
+
Csprintf(&res, "%*s<li><a href=\"#", pp->hnumber, "");
|
51
|
+
mkd_string_to_anchor(T(pp->text->text), S(pp->text->text), Csputc, &res);
|
52
|
+
Csprintf(&res, "\">");
|
53
|
+
Csreparse(&res, T(pp->text->text), S(pp->text->text), 0);
|
54
|
+
Csprintf(&res, "</a>");
|
51
55
|
}
|
52
56
|
}
|
53
57
|
|
54
58
|
while ( last_hnumber > 0 ) {
|
55
|
-
|
59
|
+
Csprintf(&res, "%*s</li>\n%*s</ul>\n",
|
56
60
|
last_hnumber, "", last_hnumber, "");
|
57
61
|
--last_hnumber;
|
58
62
|
}
|
59
|
-
|
60
|
-
|
63
|
+
/* HACK ALERT! HACK ALERT! HACK ALERT! */
|
64
|
+
*doc = T(res); /* we know that a T(Cstring) is a character pointer */
|
65
|
+
/* so we can simply pick it up and carry it away, */
|
66
|
+
return S(res); /* leaving the husk of the Ctring on the stack */
|
67
|
+
/* END HACK ALERT */
|
61
68
|
}
|
62
69
|
|
70
|
+
|
71
|
+
/* write an header index
|
72
|
+
*/
|
73
|
+
int
|
74
|
+
mkd_generatetoc(Document *p, FILE *out)
|
75
|
+
{
|
76
|
+
char *buf = 0;
|
77
|
+
int sz = mkd_toc(p, &buf);
|
78
|
+
int ret = EOF;
|
79
|
+
|
80
|
+
if ( sz > 0 )
|
81
|
+
ret = fwrite(buf, sz, 1, out);
|
82
|
+
|
83
|
+
if ( buf ) free(buf);
|
84
|
+
|
85
|
+
return ret;
|
86
|
+
}
|
data/lib/rdiscount.rb
CHANGED
data/rdiscount.gemspec
CHANGED
@@ -1,8 +1,8 @@
|
|
1
1
|
Gem::Specification.new do |s|
|
2
2
|
s.name = 'rdiscount'
|
3
|
-
s.version = '1.3.
|
3
|
+
s.version = '1.3.4'
|
4
4
|
s.summary = "Fast Implementation of Gruber's Markdown in C"
|
5
|
-
s.date = '2009-
|
5
|
+
s.date = '2009-03-04'
|
6
6
|
s.email = 'r@tomayko.com'
|
7
7
|
s.homepage = 'http://github.com/rtomayko/rdiscount'
|
8
8
|
s.has_rdoc = true
|
@@ -13,6 +13,7 @@ Gem::Specification.new do |s|
|
|
13
13
|
README.markdown
|
14
14
|
Rakefile
|
15
15
|
bin/rdiscount
|
16
|
+
ext/Csio.c
|
16
17
|
ext/amalloc.h
|
17
18
|
ext/config.h
|
18
19
|
ext/cstring.h
|
@@ -24,8 +25,6 @@ Gem::Specification.new do |s|
|
|
24
25
|
ext/markdown.h
|
25
26
|
ext/mkdio.c
|
26
27
|
ext/mkdio.h
|
27
|
-
ext/rbstrio.c
|
28
|
-
ext/rbstrio.h
|
29
28
|
ext/rdiscount.c
|
30
29
|
ext/resource.c
|
31
30
|
ext/toc.c
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rdiscount
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.3.
|
4
|
+
version: 1.3.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ryan Tomayko
|
@@ -10,7 +10,7 @@ autorequire:
|
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
12
|
|
13
|
-
date: 2009-
|
13
|
+
date: 2009-03-04 00:00:00 -08:00
|
14
14
|
default_executable:
|
15
15
|
dependencies: []
|
16
16
|
|
@@ -27,6 +27,7 @@ files:
|
|
27
27
|
- README.markdown
|
28
28
|
- Rakefile
|
29
29
|
- bin/rdiscount
|
30
|
+
- ext/Csio.c
|
30
31
|
- ext/amalloc.h
|
31
32
|
- ext/config.h
|
32
33
|
- ext/cstring.h
|
@@ -38,8 +39,6 @@ files:
|
|
38
39
|
- ext/markdown.h
|
39
40
|
- ext/mkdio.c
|
40
41
|
- ext/mkdio.h
|
41
|
-
- ext/rbstrio.c
|
42
|
-
- ext/rbstrio.h
|
43
42
|
- ext/rdiscount.c
|
44
43
|
- ext/resource.c
|
45
44
|
- ext/toc.c
|
data/ext/rbstrio.c
DELETED
@@ -1,48 +0,0 @@
|
|
1
|
-
#if defined(HAVE_FOPENCOOKIE)
|
2
|
-
# define _GNU_SOURCE
|
3
|
-
#endif
|
4
|
-
|
5
|
-
#include <stdlib.h>
|
6
|
-
#include "rbstrio.h"
|
7
|
-
|
8
|
-
#define INCREMENT 1024
|
9
|
-
|
10
|
-
/* called when data is written to the stream. */
|
11
|
-
static int rb_str_io_write(void *cookie, const char *data, int len) {
|
12
|
-
VALUE buf = (VALUE)cookie;
|
13
|
-
rb_str_cat(buf, data, len);
|
14
|
-
return len;
|
15
|
-
}
|
16
|
-
|
17
|
-
/* called when the stream is closed */
|
18
|
-
static int rb_str_io_close(void *cookie) {
|
19
|
-
VALUE buf = (VALUE)cookie;
|
20
|
-
rb_gc_unregister_address(&buf);
|
21
|
-
return 0;
|
22
|
-
}
|
23
|
-
|
24
|
-
#if defined(HAVE_FOPENCOOKIE)
|
25
|
-
cookie_io_functions_t rb_str_io_functions =
|
26
|
-
{
|
27
|
-
(cookie_read_function_t*)NULL,
|
28
|
-
(cookie_write_function_t*)rb_str_io_write,
|
29
|
-
(cookie_seek_function_t*)NULL,
|
30
|
-
(cookie_close_function_t*)rb_str_io_close
|
31
|
-
};
|
32
|
-
#endif
|
33
|
-
|
34
|
-
/* create a stream backed by a Ruby string. */
|
35
|
-
FILE *rb_str_io_new(VALUE buf) {
|
36
|
-
FILE *rv;
|
37
|
-
Check_Type(buf, T_STRING);
|
38
|
-
#if defined(HAVE_FOPENCOOKIE)
|
39
|
-
rv = fopencookie((void*)buf, "w", rb_str_io_functions);
|
40
|
-
#else
|
41
|
-
rv = funopen((void*)buf, NULL, rb_str_io_write, NULL, rb_str_io_close);
|
42
|
-
#endif
|
43
|
-
/* TODO if (rv == NULL) */
|
44
|
-
rb_gc_register_address(&buf);
|
45
|
-
return rv;
|
46
|
-
}
|
47
|
-
|
48
|
-
/* vim: set ts=4 sw=4: */
|
data/ext/rbstrio.h
DELETED