@@ -26,15 +26,28 @@ codegenJavaScript
26 -> FilePath
26 -> FilePath
27 -> OutputType
27 -> OutputType
29−codegenJavaScript definitions filename outputType = do
29+codegenJavaScript definitions filename outputType =
30− let def = map (first translateNamespace) definitions
31− let output = idrRuntime ++ concatMap (translateModule Nothing) def ++ "\nMain.main()"
32 writeFile filename output
30 writeFile filename output
32+ def = map (first translateNamespace) definitions
35+ mainLoop = intercalate "\n" [ "\nfunction main() {"
36+ , createTrampoline "Main.main()" ++ ";"
41+ output = concat [ idrRuntime
42+ , concatMap (translateModule Nothing) def
34idrRuntime :: String
46idrRuntime :: String
35idrRuntime =
47idrRuntime =
36 createModule Nothing idrNamespace $ concat
48 createModule Nothing idrNamespace $ concat
37 [ "__IDR__.IntType = { type: 'IntType' };"
49 [ "__IDR__.IntType = { type: 'IntType' };"
50+ , "__IDR__.Tailcall = function(f) { this.f = f };"
38 , "__IDR__.Con = function(i,name,vars)"
51 , "__IDR__.Con = function(i,name,vars)"
39 , "{this.i = i;this.name = name;this.vars = vars;};"
52 , "{this.i = i;this.name = name;this.vars = vars;};"
@@ -165,13 +178,16 @@ translateExpression _ (SConst cst) =
165translateExpression _ (SV var) =
178translateExpression _ (SV var) =
166 translateVariableName var
179 translateVariableName var
168−translateExpression modname (SApp tc name vars) =
181+translateExpression modname (SApp False name vars) =
169− concat (intersperse "." $ translateNamespace name)
182+ createTrampoline $ translateFunctionCall name vars
171− ++ translateName name
184+translateExpression modname (SApp True name vars) =
186+ ++ "throw new __IDR__.Tailcall("
172− ++ "("
187+ ++ "function(){\n"
173− ++ intercalate "," (map translateVariableName vars)
188+ ++ "return " ++ translateFunctionCall name vars
174− ++ ")"
190+ ++ "\n})()"
176translateExpression _ (SOp op vars)
192translateExpression _ (SOp op vars)
177 | LPlus <- op
193 | LPlus <- op
@@ -284,14 +300,10 @@ translateExpression _ (SCon i name vars) =
286translateExpression modname (SUpdate var e) =
302translateExpression modname (SUpdate var e) =
287− "(function(){\nreturn ("
288− ++ translateVariableName var
289− ++ " = " ++ translateExpression modname e
303+ translateVariableName var ++ " = " ++ translateExpression modname e
292translateExpression modname (SProj var i) =
305translateExpression modname (SProj var i) =
293− "(function(){\nreturn "
294− ++ translateVariableName var ++ ".vars[" ++ show i ++"];\n})()"
306+ translateVariableName var ++ ".vars[" ++ show i ++"]"
296translateExpression _ SNothing = "null"
308translateExpression _ SNothing = "null"
@@ -324,3 +336,28 @@ createIfBlock cond e =
324 "if (" ++ cond ++") {\n"
336 "if (" ++ cond ++") {\n"
325 ++ "return " ++ e
337 ++ "return " ++ e
326 ++ ";\n}"
338 ++ ";\n}"
340+createTrampoline call =
342+ ++ "var __f = function(){return " ++ call ++ "};\n"
343+ ++ "while (__f) {\ntry {\n"
347+ ++ "\n} catch(ex) {\n"
348+ ++ "if (ex instanceof __IDR__.Tailcall) {\n"
357+translateFunctionCall name vars =
358+ concat (intersperse "." $ translateNamespace name)
360+ ++ translateName name
362+ ++ intercalate "," (map translateVariableName vars)