Source

ocaml-lib / monad / sumonad_parser.ml

Full commit

(* Dcg cursors can be used as states *)
class type state =
object ('self)
  method look : string -> bool
  method get : Str.regexp -> string option
  method eof : bool
  method shift : string -> 'self
  method coord : int * int (* line, column *)
end

let look (w : string) : string sumonad = sudef (
  let state = sustate in
  if state#look w
  then begin sustate <- state#shift w; return w end
  else error (`KwdExpected (w, state#coord)))

let get ?(name = "") (re : Str.regexp) : string sumonad = sudef (
  let state = sustate in
  match state#get re with
    | Some w -> sustate <- state#shift w; return w
    | None ->
      if name=""
      then fail
      else error (`WordExpected (name, state#coord)))

let eof : unit sumonad = sudef (
  let state = sustate in
  if state#eof
  then return ()
  else error (`EofExpected state#coord))

let get_coord : (int*int) sumonad = sudef (
  let state = sustate in
  return (state#coord))