diff --git a/.gitignore b/.gitignore index c6e3df55..2ee3c973 100644 --- a/.gitignore +++ b/.gitignore @@ -7,7 +7,9 @@ ext/redcloth_scan/*.class ext/redcloth_scan/*.java lib/*.bundle lib/*.so +lib/*.jar doc/rdoc/* tmp/* pkg/* .DS_Store +*.log diff --git a/Rakefile b/Rakefile index b138b7e9..016ffce8 100644 --- a/Rakefile +++ b/Rakefile @@ -291,9 +291,17 @@ namespace "jruby" do Dir.chdir "ext/redcloth_scan" do compile_java("RedclothScanService.java", "redcloth_scan.jar") end + cp "ext/redcloth_scan/redcloth_scan.jar", "lib" end - JRUBY_PKG_DIR = "pkg-jruby" + desc "Run all the tests using JRuby" + Rake::TestTask.new(:test => [:redcloth_scan_java]) do |t| + t.libs << "test" + t.test_files = FileList['test/test_*.rb'] + t.verbose = true + end + + JRUBY_PKG_DIR = "pkg-jruby" desc "Package up the JRuby distribution." file JRUBY_PKG_DIR => [:ragel_java, :package] do diff --git a/ext/redcloth_scan/redcloth_common.java.rl b/ext/redcloth_scan/redcloth_common.java.rl index 8fe10548..5bf90b89 100644 --- a/ext/redcloth_scan/redcloth_common.java.rl +++ b/ext/redcloth_scan/redcloth_common.java.rl @@ -4,12 +4,12 @@ action A { reg = p; } action B { bck = p; } - action T { STORE(text); } - action X { CLEAR_REGS(); reg = NULL; } + action T { STORE("text"); } + action X { CLEAR_REGS(); reg = -1; } action cat { CAT(block); } action esc { rb_str_cat_escaped(self, block, ts, te); } action esc_pre { rb_str_cat_escaped_for_preformatted(self, block, ts, te); } - action ignore { rb_str_append(block, rb_funcall(self, rb_intern("ignore"), 1, regs)); } + action ignore { ((RubyString)block).append(self.callMethod(runtime.getCurrentContext(), "ignore", regs)); } # simple LF = ( '\n' ) ; @@ -17,28 +17,28 @@ EOF = 0 ; # textile modifiers - A_LEFT = "<" %{ ASET(align, left) } ; - A_RIGHT = ">" %{ ASET(align, right) } ; - A_JUSTIFIED = "<>" %{ ASET(align, justify) } ; - A_CENTER = "=" %{ ASET(align, center) } ; - A_PADLEFT = "(" >A %{ AINC(padding-left) } ; - A_PADRIGHT = ")" >A %{ AINC(padding-right) } ; + A_LEFT = "<" %{ ASET("align", "left"); } ; + A_RIGHT = ">" %{ ASET("align", "right"); } ; + A_JUSTIFIED = "<>" %{ ASET("align", "justify"); } ; + A_CENTER = "=" %{ ASET("align", "center"); } ; + A_PADLEFT = "(" >A %{ AINC("padding-left"); } ; + A_PADRIGHT = ")" >A %{ AINC("padding-right"); } ; A_HLGN = ( A_LEFT | A_RIGHT | A_JUSTIFIED | A_CENTER | A_PADLEFT | A_PADRIGHT ) ; A_LIMIT = ( A_LEFT | A_CENTER | A_RIGHT ) ; - A_VLGN = ( "-" %{ ASET(vertical-align, middle) } | "^" %{ ASET(vertical-align, top) } | "~" %{ ASET(vertical-align, bottom) } ) ; - C_CLAS = ( "(" ( [^)#]+ >A %{ STORE(class) } )? ("#" [^)]+ >A %{STORE(id)} )? ")" ) ; - C_LNGE = ( "[" [^\]]+ >A %{ STORE(lang) } "]" ) ; - C_STYL = ( "{" [^}]+ >A %{ STORE(style) } "}" ) ; - S_CSPN = ( "\\" [0-9]+ >A %{ STORE(colspan) } ) ; - S_RSPN = ( "/" [0-9]+ >A %{ STORE(rowspan) } ) ; - D_HEADER = "_" %{ ASET(th, true) } ; + A_VLGN = ( "-" %{ ASET("vertical-align", "middle"); } | "^" %{ ASET("vertical-align", "top"); } | "~" %{ ASET("vertical-align", "bottom"); } ) ; + C_CLAS = ( "(" ( [^)#]+ >A %{ STORE("class"); } )? ("#" [^)]+ >A %{STORE("id");} )? ")" ) ; + C_LNGE = ( "[" [^\]]+ >A %{ STORE("lang"); } "]" ) ; + C_STYL = ( "{" [^}]+ >A %{ STORE("style"); } "}" ) ; + S_CSPN = ( "\\" [0-9]+ >A %{ STORE("colspan"); } ) ; + S_RSPN = ( "/" [0-9]+ >A %{ STORE("rowspan"); } ) ; + D_HEADER = "_" %{ ASET("th", "true"); } ; A = ( ( A_HLGN | A_VLGN )* ) ; A2 = ( A_LIMIT? ) ; S = ( S_CSPN | S_RSPN )* ; C = ( C_CLAS | C_STYL | C_LNGE )* ; D = ( D_HEADER ) ; N_CONT = "_" %{ list_continue = 1; }; - N_NUM = digit+ >A %{ STORE(start) }; + N_NUM = digit+ >A %{ STORE("start"); }; N = ( N_CONT | N_NUM )? ; PUNCT = ( "!" | '"' | "#" | "$" | "%" | "&" | "'" | "," | "-" | "." | "/" | ":" | ";" | "=" | "?" | "\\" | "^" | "`" | "|" | "~" | "[" | "]" | "(" | ")" | "<" ) ; dotspace = ("." " "*) ; @@ -105,7 +105,7 @@ uri = (target | absolute_uri | absolute_path | rel_path) ; # common - title = ( '(' default+ >A %{ STORE(title) } :> ')' ) ; + title = ( '(' default+ >A %{ STORE("title"); } :> ')' ) ; word = ( alnum | safe | " " ) ; mspace = ( ( " " | "\t" | LF )+ ) -- LF{2} ; mtext = ( chars (mspace chars)* ) ; diff --git a/ext/redcloth_scan/redcloth_scan.java.rl b/ext/redcloth_scan/redcloth_scan.java.rl index 8d5ebef8..9b1ce6cd 100644 --- a/ext/redcloth_scan/redcloth_scan.java.rl +++ b/ext/redcloth_scan/redcloth_scan.java.rl @@ -10,7 +10,9 @@ import org.jruby.RubyClass; import org.jruby.RubyHash; import org.jruby.RubyModule; import org.jruby.RubyNumeric; +import org.jruby.RubyObject; import org.jruby.RubyString; +import org.jruby.anno.JRubyMethod; import org.jruby.runtime.Block; import org.jruby.runtime.CallbackFactory; import org.jruby.runtime.builtin.IRubyObject; @@ -19,31 +21,32 @@ import org.jruby.runtime.load.BasicLibraryService; public class RedclothScanService implements BasicLibraryService { + private static class Transformer { %%{ machine redcloth_scan; include redcloth_common "redcloth_common.java.rl"; - action extend { extend = rb_hash_aref(regs, ID2SYM(rb_intern("type"))); } + action extend { extend = ((RubyHash)regs).fastARef(runtime.newSymbol("type")); } # blocks notextile_tag_start = "" ; notextile_tag_end = "" LF? ; noparagraph_line_start = " "+ ; - notextile_block_start = ( "notextile" >A %{ STORE(type) } A C :> "." ( "." %extend | "" ) " "+ ) ; + notextile_block_start = ( "notextile" >A %{ STORE("type"); } A C :> "." ( "." %extend | "" ) " "+ ) ; pre_tag_start = "]* ">" (space* "")? ; pre_tag_end = ("" space*)? "" LF? ; - pre_block_start = ( "pre" >A %{ STORE(type) } A C :> "." ( "." %extend | "" ) " "+ ) ; - bc_start = ( "bc" >A %{ STORE(type) } A C :> "." ( "." %extend | "" ) " "+ ) ; - bq_start = ( "bq" >A %{ STORE(type) } A C :> "." ( "." %extend | "" ) ( ":" %A uri %{ STORE(cite) } )? " "+ ) ; + pre_block_start = ( "pre" >A %{ STORE("type"); } A C :> "." ( "." %extend | "" ) " "+ ) ; + bc_start = ( "bc" >A %{ STORE("type"); } A C :> "." ( "." %extend | "" ) " "+ ) ; + bq_start = ( "bq" >A %{ STORE("type"); } A C :> "." ( "." %extend | "" ) ( ":" %A uri %{ STORE("cite"); } )? " "+ ) ; non_ac_btype = ( "bq" | "bc" | "pre" | "notextile" ); btype = (alpha alnum*) -- (non_ac_btype | "fn" digit+); - block_start = ( btype >A %{ STORE(type) } A C :> "." ( "." %extend | "" ) " "+ ) >B %{ STORE_B(fallback) }; + block_start = ( btype >A %{ STORE("type"); } A C :> "." ( "." %extend | "" ) " "+ ) >B %{ STORE_B("fallback"); }; all_btypes = btype | non_ac_btype; next_block_start = ( all_btypes A_noactions C_noactions :> "."+ " " ) >A @{ p = reg - 1; } ; double_return = LF{2,} ; block_end = ( double_return | EOF ); - ftype = ( "fn" >A %{ STORE(type) } digit+ >A %{ STORE(id) } ) ; + ftype = ( "fn" >A %{ STORE("type"); } digit+ >A %{ STORE("id"); } ) ; footnote_start = ( ftype A C :> dotspace ) ; ul = "*" %{nest++; list_type = "ul";}; ol = "#" %{nest++; list_type = "ol";}; @@ -52,14 +55,14 @@ public class RedclothScanService implements BasicLibraryService { list_start = ( ul_start | ol_start ) >{nest = 0;} ; dt_start = "-" . " "+ ; dd_start = ":=" ; - long_dd = dd_start " "* LF %{ ADD_BLOCK(); ASET(type, dd); } any+ >A %{ TRANSFORM(text) } :>> "=:" ; + long_dd = dd_start " "* LF %{ ADD_BLOCK(); ASET("type", "dd"); } any+ >A %{ TRANSFORM("text"); } :>> "=:" ; dl_start = (dt_start mtext (LF dt_start mtext)* " "* dd_start) ; blank_line = LF; - link_alias = ( "[" >{ ASET(type, ignore) } %A chars %T "]" %A uri %{ STORE_URL(href); } ) ; + link_alias = ( "[" >{ ASET("type", "ignore"); } %A chars %T "]" %A uri %{ STORE_URL("href"); } ) ; # image lookahead - IMG_A_LEFT = "<" %{ ASET(float, left) } ; - IMG_A_RIGHT = ">" %{ ASET(float, right) } ; + IMG_A_LEFT = "<" %{ ASET("float", "left"); } ; + IMG_A_RIGHT = ">" %{ ASET("float", "right"); } ; aligned_image = ( "["? "!" (IMG_A_LEFT | IMG_A_RIGHT) ) >A @{ p = reg - 1; } ; # html blocks @@ -67,8 +70,8 @@ public class RedclothScanService implements BasicLibraryService { block_start_tag = "<" BlockTagName space+ AttrSet* (AttrEnd)? ">" | "<" BlockTagName ">"; block_empty_tag = "<" BlockTagName space+ AttrSet* (AttrEnd)? "/>" | "<" BlockTagName "/>" ; block_end_tag = "" ; - html_start = indent >B %{STORE_B(indent_before_start)} block_start_tag >B %{STORE_B(start_tag)} indent >B %{STORE_B(indent_after_start)} ; - html_end = indent >B %{STORE_B(indent_before_end)} block_end_tag >B %{STORE_B(end_tag)} (indent LF?) >B %{STORE_B(indent_after_end)} ; + html_start = indent >B %{STORE_B("indent_before_start");} block_start_tag >B %{STORE_B("start_tag");} indent >B %{STORE_B("indent_after_start");} ; + html_end = indent >B %{STORE_B("indent_before_end");} block_end_tag >B %{STORE_B("end_tag");} (indent LF?) >B %{STORE_B("indent_after_end");} ; standalone_html = indent (block_start_tag | block_empty_tag | block_end_tag) indent LF+; html_end_terminating_block = ( LF indent block_end_tag ) >A @{ p = reg - 1; } ; @@ -76,15 +79,15 @@ public class RedclothScanService implements BasicLibraryService { para = ( default+ ) -- LF ; btext = para ( LF{2} )? ; tddef = ( D? S A C :> dotspace ) ; - td = ( tddef? btext >A %T :> "|" >{PASS(table, text, td);} ) >X ; + td = ( tddef? btext >A %T :> "|" >{PASS(table, "text", "td");} ) >X ; trdef = ( A C :> dotspace ) ; - tr = ( trdef? "|" %{INLINE(table, tr_open);} td+ ) >X %{INLINE(table, tr_close);} ; + tr = ( trdef? "|" %{INLINE(table, "tr_open");} td+ ) >X %{INLINE(table, "tr_close");} ; trows = ( tr (LF >X tr)* ) ; tdef = ( "table" >X A C :> dotspace LF ) ; - table = ( tdef? trows >{table = rb_str_new2(""); INLINE(table, table_open);} ) >{ reg = NULL; } ; + table = ( tdef? trows >{table = RubyString.newEmptyString(runtime); INLINE(table, "table_open");} ) >{ reg = -1; } ; # info - redcloth_version = ("RedCloth" >A ("::" | " " ) "VERSION"i ":"? " ")? %{STORE(prefix)} "RedCloth::VERSION" (LF* EOF | double_return) ; + redcloth_version = ("RedCloth" >A ("::" | " " ) "VERSION"i ":"? " ")? %{STORE("prefix");} "RedCloth::VERSION" (LF* EOF | double_return) ; pre_tag := |* pre_tag_end { CAT(block); DONE(block); fgoto main; }; @@ -97,7 +100,7 @@ public class RedclothScanService implements BasicLibraryService { fgoto main; }; double_return { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCKCODE(); fgoto main; } else { @@ -105,7 +108,7 @@ public class RedclothScanService implements BasicLibraryService { } }; double_return next_block_start { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCKCODE(); fgoto main; } else { @@ -118,8 +121,8 @@ public class RedclothScanService implements BasicLibraryService { *|; script_tag := |* - script_tag_end { CAT(block); ASET(type, ignore); ADD_BLOCK(); fgoto main; }; - EOF { ASET(type, ignore); ADD_BLOCK(); fgoto main; }; + script_tag_end { CAT(block); ASET("type", "ignore"); ADD_BLOCK(); fgoto main; }; + EOF { ASET("type", "ignore"); ADD_BLOCK(); fgoto main; }; default => cat; *|; @@ -139,7 +142,7 @@ public class RedclothScanService implements BasicLibraryService { fgoto main; }; double_return { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); CAT(html); fgoto main; @@ -150,7 +153,7 @@ public class RedclothScanService implements BasicLibraryService { } }; double_return next_block_start { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); CAT(html); fgoto main; @@ -172,15 +175,15 @@ public class RedclothScanService implements BasicLibraryService { bc := |* EOF { ADD_BLOCKCODE(); - INLINE(html, bc_close); - plain_block = rb_str_new2("p"); + INLINE(html, "bc_close"); + plain_block = runtime.newString("p"); fgoto main; }; double_return { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCKCODE(); - INLINE(html, bc_close); - plain_block = rb_str_new2("p"); + INLINE(html, "bc_close"); + plain_block = runtime.newString("p"); fgoto main; } else { ADD_EXTENDED_BLOCKCODE(); @@ -188,16 +191,16 @@ public class RedclothScanService implements BasicLibraryService { } }; double_return next_block_start { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCKCODE(); - INLINE(html, bc_close); - plain_block = rb_str_new2("p"); + INLINE(html, "bc_close"); + plain_block = runtime.newString("p"); fgoto main; } else { ADD_EXTENDED_BLOCKCODE(); CAT(html); - INLINE(html, bc_close); - plain_block = rb_str_new2("p"); + INLINE(html, "bc_close"); + plain_block = runtime.newString("p"); END_EXTENDED(); fgoto main; } @@ -208,38 +211,38 @@ public class RedclothScanService implements BasicLibraryService { bq := |* EOF { ADD_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); fgoto main; }; double_return { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); fgoto main; } else { ADD_EXTENDED_BLOCK(); } }; double_return next_block_start { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); fgoto main; } else { ADD_EXTENDED_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); END_EXTENDED(); fgoto main; } }; html_end_terminating_block { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); fgoto main; } else { ADD_EXTENDED_BLOCK(); - INLINE(html, bq_close); + INLINE(html, "bq_close"); END_EXTENDED(); fgoto main; } @@ -253,7 +256,7 @@ public class RedclothScanService implements BasicLibraryService { fgoto main; }; double_return { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); fgoto main; } else { @@ -261,7 +264,7 @@ public class RedclothScanService implements BasicLibraryService { } }; double_return next_block_start { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); fgoto main; } else { @@ -271,7 +274,7 @@ public class RedclothScanService implements BasicLibraryService { } }; html_end_terminating_block { - if (NIL_P(extend)) { + if (extend.isNil()) { ADD_BLOCK(); fgoto main; } else { @@ -282,7 +285,7 @@ public class RedclothScanService implements BasicLibraryService { }; LF list_start { ADD_BLOCK(); - list_layout = rb_ary_new(); + list_layout = runtime.newArray(); LIST_ITEM(); fgoto list; }; @@ -302,37 +305,37 @@ public class RedclothScanService implements BasicLibraryService { *|; dl := |* - LF dt_start { ADD_BLOCK(); ASET(type, dt); }; - dd_start { ADD_BLOCK(); ASET(type, dd); }; - long_dd { INLINE(html, dd); CLEAR_REGS(); }; - block_end { ADD_BLOCK(); INLINE(html, dl_close); fgoto main; }; + LF dt_start { ADD_BLOCK(); ASET("type", "dt"); }; + dd_start { ADD_BLOCK(); ASET("type", "dd"); }; + long_dd { INLINE(html, "dd"); CLEAR_REGS(); }; + block_end { ADD_BLOCK(); INLINE(html, "dl_close"); fgoto main; }; default => cat; *|; main := |* - noparagraph_line_start { ASET(type, ignored_line); fgoto noparagraph_line; }; - notextile_tag_start { ASET(type, notextile); fgoto notextile_tag; }; - notextile_block_start { ASET(type, notextile); fgoto notextile_block; }; + noparagraph_line_start { ASET("type", "ignored_line"); fgoto noparagraph_line; }; + notextile_tag_start { ASET("type", "notextile"); fgoto notextile_tag; }; + notextile_block_start { ASET("type", "notextile"); fgoto notextile_block; }; script_tag_start { CAT(block); fgoto script_tag; }; - pre_tag_start { ASET(type, notextile); CAT(block); fgoto pre_tag; }; + pre_tag_start { ASET("type", "notextile"); CAT(block); fgoto pre_tag; }; pre_block_start { fgoto pre_block; }; - standalone_html { ASET(type, html); CAT(block); ADD_BLOCK(); }; - html_start { ASET(type, html_block); fgoto html; }; - bc_start { INLINE(html, bc_open); ASET(type, code); plain_block = rb_str_new2("code"); fgoto bc; }; - bq_start { INLINE(html, bq_open); ASET(type, p); fgoto bq; }; + standalone_html { ASET("type", "html"); CAT(block); ADD_BLOCK(); }; + html_start { ASET("type", "html_block"); fgoto html; }; + bc_start { INLINE(html, "bc_open"); ASET("type", "code"); plain_block = runtime.newString("code"); fgoto bc; }; + bq_start { INLINE(html, "bq_open"); ASET("type", "p"); fgoto bq; }; block_start { fgoto block; }; footnote_start { fgoto footnote; }; - list_start { list_layout = rb_ary_new(); LIST_ITEM(); fgoto list; }; - dl_start { p = ts; INLINE(html, dl_open); ASET(type, dt); fgoto dl; }; - table { INLINE(table, table_close); DONE(table); fgoto block; }; - link_alias { rb_hash_aset(refs_found, rb_hash_aref(regs, ID2SYM(rb_intern("text"))), rb_hash_aref(regs, ID2SYM(rb_intern("href")))); DONE(block); }; - aligned_image { rb_hash_aset(regs, ID2SYM(rb_intern("type")), plain_block); fgoto block; }; - redcloth_version { INLINE(html, redcloth_version); }; + list_start { list_layout = runtime.newArray(); LIST_ITEM(); fgoto list; }; + dl_start { p = ts; INLINE(html, "dl_open"); ASET("type", "dt"); fgoto dl; }; + table { INLINE(table, "table_close"); DONE(table); fgoto block; }; + link_alias { ((RubyHash)refs_found).fastASet(((RubyHash)regs).fastARef(runtime.newSymbol("text")), ((RubyHash)regs).fastARef(runtime.newSymbol("href"))); DONE(block); }; + aligned_image { ((RubyHash)regs).fastASet(runtime.newSymbol("type"), plain_block); fgoto block; }; + redcloth_version { INLINE(html, "redcloth_version"); }; blank_line => cat; default { CLEAR_REGS(); - rb_hash_aset(regs, ID2SYM(rb_intern("type")), plain_block); + ((RubyHash)regs).fastASet(runtime.newSymbol("type"), plain_block); CAT(block); fgoto block; }; @@ -342,12 +345,204 @@ public class RedclothScanService implements BasicLibraryService { }%% %% write data nofinal; + public void CLEAR(IRubyObject obj) { + if(block == obj) { + block = RubyString.newEmptyString(runtime); + } else if(html == obj) { + html = RubyString.newEmptyString(runtime); + } else if(table == obj) { + table = RubyString.newEmptyString(runtime); + } + } -public boolean basicLoad(final Ruby runtime) throws IOException { - Init_redcloth_scan(runtime); - return true; -} + public void ADD_BLOCK() { + ((RubyString)html).append(red_block(self, regs, block, refs)); + extend = runtime.getNil(); + CLEAR(block); + CLEAR_REGS(); + } -public static void Init_redcloth_scan(Ruby runtime) { -} + public void CLEAR_REGS() { + regs = RubyHash.newHash(runtime); + } + + public void CAT(IRubyObject H) { + ((RubyString)H).cat(data, ts, te-ts); + } + + public void INLINE(IRubyObject H, String T) { + ((RubyString)H).append(self.callMethod(runtime.getCurrentContext(), T, regs)); + } + + public void DONE(IRubyObject H) { + ((RubyString)html).append(H); + CLEAR(H); + CLEAR_REGS(); + } + + public void ADD_EXTENDED_BLOCK() { + ((RubyString)html).append(red_block(self, regs, block, refs)); + CLEAR(block); + } + + public void ADD_BLOCKCODE() { + ((RubyString)html).append(red_blockcode(self, regs, block)); + CLEAR(block); + CLEAR_REGS(); + } + + public void ADD_EXTENDED_BLOCKCODE() { + ((RubyString)html).append(red_blockcode(self, regs, block)); + CLEAR(block); + } + + public void AINC(String T) { + red_inc(regs, runtime.newSymbol(T)); + } + + public void END_EXTENDED() { + extend = runtime.getNil(); + CLEAR_REGS(); + } + + public void ASET(String T, String V) { + ((RubyHash)regs).fastASet(runtime.newSymbol(T), runtime.newString(V)); + } + + public void STORE(String T) { + if(p > reg && reg >= ts) { + IRubyObject str = RubyString.newString(runtime, data, reg, p-reg); + ((RubyHash)regs).fastASet(runtime.newSymbol(T), str); + } else { + ((RubyHash)regs).fastASet(runtime.newSymbol(T), runtime.getNil()); + } + } + + public void STORE_B(String T) { + if(p > bck && bck >= ts) { + IRubyObject str = RubyString.newString(runtime, data, bck, p-bck); + ((RubyHash)regs).fastASet(runtime.newSymbol(T), str); + } else { + ((RubyHash)regs).fastASet(runtime.newSymbol(T), runtime.getNil()); + } + } + + private IRubyObject self; + private byte[] data; + private int p, pe; + private IRubyObject refs; + + private Ruby runtime; + private int orig_p, orig_pe; + private int cs, act, nest; + private int ts = -1; + private int te = -1; + private int reg = -1; + private int bck = -1; + private int eof = -1; + + private IRubyObject html; + private IRubyObject table; + private IRubyObject block; + private IRubyObject regs; + + private IRubyObject list_layout; + private String list_type = null; + private IRubyObject list_index; + private int list_continue = 0; + private IRubyObject plain_block; + private IRubyObject extend; + private IRubyObject refs_found; + + public Transformer(IRubyObject self, byte[] data, int p, int pe, IRubyObject refs) { + this.self = self; + this.data = data; + this.p = p; + this.pe = pe; + this.refs = refs; + + runtime = self.getRuntime(); + orig_p = p; + orig_pe = pe; + + html = RubyString.newEmptyString(runtime); + table = RubyString.newEmptyString(runtime); + block = RubyString.newEmptyString(runtime); + CLEAR_REGS(); + + list_layout = runtime.getNil(); + list_index = runtime.newArray(); + plain_block = runtime.newString("p"); + extend = runtime.getNil(); + refs_found = RubyHash.newHash(runtime); + } + + public IRubyObject transform() { + %% write init; + + %% write exec; + if(((RubyString)block).getByteList().realSize > 0) { +// ADD_BLOCK(); + } + + if(refs.isNil() && !refs_found.callMethod(runtime.getCurrentContext(), "empty?").isTrue()) { + return RedclothScanService.transform(self, data, orig_p, orig_pe, refs_found); + } else { + self.callMethod(self.getRuntime().getCurrentContext(), "after_transform", html); + return html; + } + } + } + + public static IRubyObject transform(IRubyObject self, byte[] data, int p, int pe, IRubyObject refs) { + return new Transformer(self, data, p, pe, refs).transform(); + } + + public static IRubyObject inline2(IRubyObject workingCopy, IRubyObject self, RubyHash hash) { + return workingCopy.getRuntime().getNil(); + } + + public static IRubyObject transform2(IRubyObject self, IRubyObject str) { + RubyString ss = str.convertToString(); + ss.cat((byte)'\n'); + self.callMethod(self.getRuntime().getCurrentContext(), "before_transform", ss); + return transform(self, ss.getByteList().bytes(), ss.getByteList().begin, ss.getByteList().realSize, self.getRuntime().getNil()); + } + + @JRubyMethod + public static IRubyObject to(IRubyObject self, IRubyObject formatter) { + Ruby runtime = self.getRuntime(); + self.callMethod(runtime.getCurrentContext(), "delete!", runtime.newString("\r")); + IRubyObject workingCopy = self.rbClone(); + + ((RubyObject)workingCopy).extend(new IRubyObject[]{formatter}); + + if(workingCopy.callMethod(runtime.getCurrentContext(), "lite_mode").isTrue()) { + return inline2(workingCopy, self, RubyHash.newHash(runtime)); + } else { + return transform2(workingCopy, self); + } + } + + @JRubyMethod(rest=true) + public static IRubyObject html_esc(IRubyObject self, IRubyObject[] args) { + return self.getRuntime().getNil(); + } + + @JRubyMethod + public static IRubyObject latex_esc(IRubyObject self, IRubyObject str) { + return self.getRuntime().getNil(); + } + + public boolean basicLoad(final Ruby runtime) throws IOException { + Init_redcloth_scan(runtime); + return true; + } + + public static void Init_redcloth_scan(Ruby runtime) { + RubyModule mRedCloth = runtime.defineModule("RedCloth"); + RubyClass super_RedCloth = mRedCloth.defineClassUnder("TextileDoc", runtime.getString(), runtime.getString().getAllocator()); + super_RedCloth.defineAnnotatedMethods(RedclothScanService.class); + super_RedCloth.defineClassUnder("ParseError",runtime.getClass("Exception"),runtime.getClass("Exception").getAllocator()); + } }