Skip to content

Commit

Permalink
Add some definition nodes
Browse files Browse the repository at this point in the history
  • Loading branch information
adambeynon committed Oct 22, 2013
1 parent 49e6195 commit 4e9d955
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 82 deletions.
64 changes: 64 additions & 0 deletions lib/opal/nodes/definitions.rb
Expand Up @@ -3,6 +3,14 @@
module Opal
class Parser

class SvalueNode < Node
children :value

def compile
push @parser.process(value, @level)
end
end

# :scope nodes are actually inside scopes (e.g. :module, :class).
# These are not actually the scopes themselves.
class ScopeNode < Node
Expand Down Expand Up @@ -174,5 +182,61 @@ def find_inline_yield(stmt)
end
end
end

class WhileNode < Node
children :test, :body

def compile
with_temp do |redo_var|
test_code = @parser.js_truthy(test)

@parser.in_while do
while_loop[:closure] = true if wrap_in_closure?
while_loop[:redo_var] = redo_var

body_code = stmt(body)

if uses_redo?
push "#{redo_var} = false; #{while_open}#{redo_var} || "
push test_code
push while_close
else
push while_open, test_code, while_close
end

push "#{redo_var} = false;" if uses_redo?
line body_code, "}"
end
end

wrap '(function() {', '; return nil; })()' if wrap_in_closure?
end

def while_open
"while ("
end

def while_close
") {"
end

def uses_redo?
while_loop[:use_redo]
end

def wrap_in_closure?
expr? or recv?
end
end

class UntilNode < WhileNode
def while_open
"while (!("
end

def while_close
")) {"
end
end
end
end
85 changes: 3 additions & 82 deletions lib/opal/parser.rb
Expand Up @@ -104,13 +104,16 @@ def add_handler(klass, *types)
add_handler ClassNode, :class

# definitions
add_handler SvalueNode, :svalue
add_handler UndefNode, :undef
add_handler AliasNode, :alias
add_handler BeginNode, :begin
add_handler ParenNode, :paren
add_handler RescueModNode, :rescue_mod
add_handler BlockNode, :block
add_handler ScopeNode, :scope
add_handler WhileNode, :while
add_handler UntilNode, :until

# Final generated javascript for this parser
attr_reader :result
Expand Down Expand Up @@ -967,84 +970,6 @@ def process_array(sexp, level)
code
end

# s(:while, exp, block, true)
def process_while(sexp, level)
expr, stmt = sexp
redo_var = @scope.new_temp
code = []

stmt_level = if level == :expr or level == :recv
:stmt_closure
else
:stmt
end

code << js_truthy(expr) << f("){", sexp)
pre = "while ("

in_while do
@while_loop[:closure] = true if stmt_level == :stmt_closure
@while_loop[:redo_var] = redo_var
body = process(stmt, :stmt)

if @while_loop[:use_redo]
pre = "#{redo_var}=false;" + pre + "#{redo_var} || "
code << f("#{redo_var}=false;", sexp)
end

code << body
end

code << f("}", sexp)
code.unshift f(pre, sexp)
@scope.queue_temp redo_var

if stmt_level == :stmt_closure
code.unshift f("(function() {", sexp)
code.push f("; return nil; }).call(self)", sexp)
end

code
end

def process_until(exp, level)
expr, stmt = exp
redo_var = @scope.new_temp
stmt_level = if level == :expr or level == :recv
:stmt_closure
else
:stmt
end

code = []
pre = "while (!("
code << js_truthy(expr) << f(")) {", exp)

in_while do
@while_loop[:closure] = true if stmt_level == :stmt_closure
@while_loop[:redo_var] = redo_var
body = process(stmt, :stmt)

if @while_loop[:use_redo]
pre = "#{redo_var}=false;" + pre + "#{redo_var} || "
code << f("#{redo_var}=false;", exp)
end

code << body
end

code << f("}", exp)
code.unshift f(pre, exp)
@scope.queue_temp redo_var

if stmt_level == :stmt_closure
code.unshift f("(function() {", exp)
code << f("; return nil; }).call(self)", exp)
end

code
end

def process_masgn(sexp, level)
lhs, rhs = sexp
tmp = @scope.new_temp
Expand Down Expand Up @@ -1097,10 +1022,6 @@ def process_masgn(sexp, level)
code
end

def process_svalue(sexp, level)
process sexp[0], level
end

# s(:if, test, truthy, falsy)
def process_if(sexp, level)
test, truthy, falsy = sexp
Expand Down

0 comments on commit 4e9d955

Please sign in to comment.