aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xprojects/11/JackCompilerbin284352 -> 284520 bytes
-rw-r--r--projects/11/JackCompiler.hs73
-rw-r--r--projects/11/JackCompiler.obin408776 -> 409680 bytes
-rw-r--r--projects/11/Pong/Ball.vm18
-rw-r--r--projects/11/Pong/Bat.vm4
5 files changed, 42 insertions, 53 deletions
diff --git a/projects/11/JackCompiler b/projects/11/JackCompiler
index 39d2d13..2dc9b98 100755
--- a/projects/11/JackCompiler
+++ b/projects/11/JackCompiler
Binary files differ
diff --git a/projects/11/JackCompiler.hs b/projects/11/JackCompiler.hs
index 025fe12..bf3acfe 100644
--- a/projects/11/JackCompiler.hs
+++ b/projects/11/JackCompiler.hs
@@ -1,6 +1,6 @@
-- Jack Compiler, as the coursework of Project 11 of Nand2Tetris course.
-- Author: Yuchen Pei (me@ypei.me)
--- Date: 2018-01-12
+-- Date: 2018-01-15
{-# LANGUAGE FlexibleContexts #-}
import Text.Parsec.Prim
import Text.Parsec.Char
@@ -66,7 +66,6 @@ alphaNumUnderscoredot = '.':alphaNumUnderscore
parse' parser = parse parser ""
---jack xs = parse' (many jSpace >> jClass) (replCrWithNl xs)
jackReader = parse' (many jSpace >> jClass)
jClass :: JackParser JClass
@@ -322,9 +321,9 @@ buildSRTable xs = Map.fromList $ mconcat $ go <$> xs where
(cName ++ "." ++ sName, (kind, (ty, nArgs))) where
nArgs = length args + if kind == "method" then 1 else 0
-buildLTable :: [JTypeAndId] -> [JTypeAndId] -> Table
-buildLTable args lcls =
- (go "argument" args 0 Map.empty) `Map.union` (go "local" lcls 0 Map.empty) where
+buildLTable :: Bool -> [JTypeAndId] -> [JTypeAndId] -> Table
+buildLTable isMethod args lcls =
+ (go "argument" args (if isMethod then 1 else 0) Map.empty) `Map.union` (go "local" lcls 0 Map.empty) where
go _ [] _ t = t
go kind ((ty, name):xs) n t = go kind xs (n + 1) $ Map.insert name (ty, (kind, n)) t
@@ -348,8 +347,8 @@ vSubroutineDec cName t u n sub =
vStatement t s u cName sName 0 stmts where
JSubroutineDec (JSubroutineHeader _ (_, sName) args) (JSubroutineBody lcls stmts) = sub
nLcls = length lcls
- s = buildLTable args lcls
kind = fst $ u Map.! (cName ++ "." ++ sName)
+ s = buildLTable (kind == "method") args lcls
kindSpec = if kind == "constructor"
then vNew n
else if kind == "method"
@@ -364,8 +363,9 @@ vSubroutineDec cName t u n sub =
vStatement _ _ _ _ _ _ [] = ""
-vStatement t s u cName name n ((JLetStatment var exp):stmts) =
-- vExpression: push the result of exp; vPopToVar: pop to the var addr
+
+vStatement t s u cName name n ((JLetStatment var exp):stmts) =
vExpression t s u cName exp ++ vPopToVar t s u cName var ++ vStatement t s u cName name n stmts
vStatement t s u cName name n ((JIfStatement cond thenStmts elseStmts):stmts) =
@@ -459,7 +459,6 @@ vSubroutineCall t s u cName (JSubroutineCall name name' args) =
then name ++ "." ++ fromJust name'
else getType t s name ++ "." ++ fromJust name'
-- u is the SRTable
- --hello = trace (cName ++ " " ++ name ++ " " ++ show name') ""
(method, nArgs) =
if fst (u Map.! name'') == "method"
then if name' == Nothing
@@ -489,7 +488,30 @@ vPush xs n = "push " ++ xs ++ " " ++ show n ++ "\n"
vPop xs n = "pop " ++ xs ++ " " ++ show n ++ "\n"
--- testing
+-- IO
+
+-- reader of system subroutines' headers
+jClasses :: JackParser [JClass]
+jClasses = many (try $ many jSpace >> jClass)
+
+sysSubroutineTable :: IO Table
+sysSubroutineTable = do
+ x <- readFile "./systemsub.txt"
+ return $ buildSRTable $ head $ rights [parse' jClasses x]
+
+main = do
+ dir <- head <$> getArgs
+ filesWODir <- filter isJackFile <$> listDirectory dir
+ let jackFiles = (dir++) <$> filesWODir
+ codes <- sequence $ readFile <$> jackFiles
+ initTable <- sysSubroutineTable
+ zipWithM writeFile (chExt <$> jackFiles) (jackCompiler initTable codes)
+ where isJackFile xs = drop (length xs - 5) xs == ".jack"
+ chExt xs = take (length xs - 4) xs ++ "vm"
+ --}
+
+
+--testing
testCompiler :: [[Char]] -> IO ()
testCompiler xs = do
@@ -513,37 +535,4 @@ testReader = do
--test reader writer x = let Right y = parse' reader x in writer y
--test' x = let Right y = parse' jStatement x in vStatement Map.empty Map.empty Map.empty "" 0 [y]
-{--
-fst3 (x, y, z) = x
-snd3 (x, y, z) = y
-trd3 (x, y, z) = z
---}
-
-{--
-replCrWithNl :: [Char] -> [Char]
-replCrWithNl = fmap cr2nl
- where cr2nl '\r' = '\n'
- cr2nl c = c
- --}
-
--- IO
-
--- reader of system subroutines' headers
-jClasses :: JackParser [JClass]
-jClasses = many (try $ many jSpace >> jClass)
-
-sysSubroutineTable :: IO Table
-sysSubroutineTable = do
- x <- readFile "./systemsub.txt"
- return $ buildSRTable $ head $ rights [parse' jClasses x]
-main = do
- dir <- head <$> getArgs
- filesWODir <- filter isJackFile <$> listDirectory dir
- let jackFiles = (dir++) <$> filesWODir
- codes <- sequence $ readFile <$> jackFiles
- initTable <- sysSubroutineTable
- zipWithM writeFile (chExt <$> jackFiles) (jackCompiler initTable codes)
- where isJackFile xs = drop (length xs - 5) xs == ".jack"
- chExt xs = take (length xs - 4) xs ++ "vm"
- --}
diff --git a/projects/11/JackCompiler.o b/projects/11/JackCompiler.o
index a3cf3d3..49a6ac5 100644
--- a/projects/11/JackCompiler.o
+++ b/projects/11/JackCompiler.o
Binary files differ
diff --git a/projects/11/Pong/Ball.vm b/projects/11/Pong/Ball.vm
index b8154eb..9d7b984 100644
--- a/projects/11/Pong/Ball.vm
+++ b/projects/11/Pong/Ball.vm
@@ -86,11 +86,11 @@ return
function Ball.setDestination 3
push argument 0
pop pointer 0
-push argument 0
+push argument 1
push this 0
sub
pop this 2
-push argument 1
+push argument 2
push this 1
sub
pop this 3
@@ -114,21 +114,21 @@ pop local 0
push local 2
pop local 1
push this 1
-push argument 1
+push argument 2
lt
pop this 8
push this 0
-push argument 0
+push argument 1
lt
pop this 9
goto setDestination.Endif0
label setDestination.Else0
push this 0
-push argument 0
+push argument 1
lt
pop this 8
push this 1
-push argument 1
+push argument 2
lt
pop this 9
label setDestination.Endif0
@@ -300,7 +300,7 @@ push this 3
push constant 10
call Math.divide 2
pop local 3
-push argument 0
+push argument 1
push constant 0
eq
not
@@ -313,14 +313,14 @@ push this 2
push constant 0
lt
not
-push argument 0
+push argument 1
push constant 1
eq
and
push this 2
push constant 0
lt
-push argument 0
+push argument 1
push constant 1
neg
eq
diff --git a/projects/11/Pong/Bat.vm b/projects/11/Pong/Bat.vm
index 23b4033..77acfe4 100644
--- a/projects/11/Pong/Bat.vm
+++ b/projects/11/Pong/Bat.vm
@@ -66,7 +66,7 @@ return
function Bat.setDirection 0
push argument 0
pop pointer 0
-push argument 0
+push argument 1
pop this 4
push constant 0
return
@@ -88,7 +88,7 @@ pop pointer 0
push pointer 0
call Bat.hide 1
pop temp 0
-push argument 0
+push argument 1
pop this 2
push pointer 0
call Bat.show 1