Commits

Anonymous committed 0c17f9b

parsing msg, lex ident

Comments (0)

Files changed (3)

   in
   let num pos c1 = many_iter pos (function '0'..'9'-> true | _ -> false) [c1] in
   let str pos = many_iter pos (fun c -> c <> '"') [] in
-  let word pos c1 = many_iter pos (function 'a'..'z' | 'A'..'Z' -> true | _ -> false) [c1] in
+  let word pos c1 = many_iter pos (function 'a'..'z' | 'A'..'Z' | '0'..'9'-> true | _ -> false) [c1] in
   let rec loop pos l : token list =
     try
       let c, tl = match l with
 type ('l, 'r) either = Inl of 'l | Inr of 'r
 type 'x p = token list -> ('x * token list, err) either
 and err = pos option * string
-let serr = function
-  | None, msg -> "End of file: " ^ msg
-  | Some pos, msg -> spos pos ^ ": " ^ msg
 let err_plus (p1,msg1) (p2,msg2) = match p1, p2 with
 | None, None -> None, msg1 ^ ", " ^ msg2
 | None, _    -> None, msg1
 | _,    None -> None, msg2
 | Some p1, Some p2 ->
-    if p1 = p2 then
-      Some p1, msg1 ^ ", " ^ msg2
-    else if p_lt p1 p2 then
-      (*Some p2, msg2*)
-      Some p2, msg2
-    else
-      Some p1, msg1
-
-  
-  
+    if p1 = p2 then Some p1, msg1 ^ ", " ^ msg2
+    else if p_lt p1 p2 then Some p2, msg2
+    else Some p1, msg1
 
 exception ParseError of err
 
 let return x = fun code -> Inl (x, code)
 
 let many p =
-  let rec local store code = match p code with
-    | Inl (x, ts) -> local (x::store) ts
-    | Inr _ -> List.rev store, code
+  let rec iter store =
+    (p >>= fun x -> iter (x::store)) <|> return (List.rev store)
   in
-  fun code -> Inl (local [] code)
+  iter []
 
-(*let many_and_end p pn =
-  (p >>= fun x -> many_and p pn >>= fun xs,y -> return (x::xs, y))
-    <|> *)
+(* for debug msg *)
+let many_and_end p pn =
+  let rec iter store =
+    (p >>= fun x -> iter (x::store)) <|> (pn >>= fun y -> return (List.rev store, y))
+  in
+  iter []
+
 
 let opt p = fun code -> match p code with
   | Inl (x, ts) -> Inl (Some x, ts)
 
 let relation = expr >>= fun e1 -> rel_op >>= fun rop -> expr >>= fun e2 -> return (rop, e1, e2)
 
-let rec statlist code = begin statement() >>= fun s1 -> many (token Semicolon >> statement()) >>=
-  fun ss -> return (s1::ss) end code
+let rec statlist code = begin statement() >>= fun s1 ->
+  many (token Semicolon >> statement()) >>= fun ss -> return (s1::ss)
+end code
+and statlist_end () = statement() >>= fun s ->
+  many_and_end (token Semicolon >> statement()) (token (Reserved End)) >>= fun (ss,_) ->
+    return (s::ss)
 and statement () = (ident >>= fun s -> token Assign >> expr >>= fun e -> return (SAssign (s, e)))
   <|> (token (Reserved If) >> relation >>= fun r -> token (Reserved Then) >> statlist >>=
-	 fun ts -> else_stats() >>= fun es -> token (Reserved End) >> return (SIf(r,ts,es)))
-  <|> (token (Reserved While) >> relation >>= fun r -> token (Reserved Do) >> statlist >>=
-	 fun ss -> token (Reserved End) >> return (SWhile(r, ss)))
+    fun ts -> else_stats() >>= fun es -> token (Reserved End) >> return (SIf(r,ts,es)))
+  <|> (token (Reserved While) >> relation >>= fun r -> token (Reserved Do) >> statlist_end() >>=
+    fun ss -> return (SWhile (r, ss)))
   <|> (ident >>= fun s -> token P_Open >> literal >>= fun l -> token P_Close >> return (SCall (s, l)))
 and else_stats () = token (Reserved Else) >> statlist <|> return []
 
 let parse_module = token (Reserved Module) >> ident >>= fun s -> token Semicolon >>
-  vdecl >>= fun decls -> token (Reserved Begin) >> statlist >>= fun ss ->
-  token (Reserved End) >> ident >> token Dot >> return (Pg (s, decls, ss))
+  vdecl >>= fun decls -> token (Reserved Begin) >> statlist_end() >>= fun ss ->
+    ident >> token Dot >> return (Pg (s, decls, ss))
 
 let parse ts =
   match parse_module ts with

samples/test.prim

-MODULE test;
+MODULE test4;
 VAR
   i, j, k: INT;
   hoge : STRING;
   hoge := "hello";
   WriteStr(hoge);
   i := 3;
-  i := 3;
+  j := 5;
   IF i = 1 THEN
     WHILE i <= 100 DO
       WriteStr("mmm");
       i := i+1
     END
   ELSE
-    WriteStr(ng);
-  END;
+    WriteStr(ng)
+  END
 END test.