{ open Lexing open Irc_parser open Irc_types type state = Header | Command | Params let state = ref Header let init () = state := Header (* this -must- be called before trying to lex a complete line *) } let letter = [^' '] let digit = ['0'-'9'] rule param = parse | ':'((letter|' ')* as s) { STRING s } | (letter+) as s { STRING s } | [' ']+ { param lexbuf } | eof { EOL } and command = parse | (digit digit digit) as num { COMMAND (Numeric (int_of_string num)) } | "JOIN" { COMMAND JOIN } | "PART" { COMMAND PART } | "MODE" { COMMAND MODE } | "TOPIC" { COMMAND TOPIC } | "NAMES" { COMMAND NAMES } | "LIST" { COMMAND LIST } | "INVITE" { COMMAND INVITE } | "KICK" { COMMAND KICK } | "PRIVMSG" { COMMAND PRIVMSG } | "NOTICE" { COMMAND NOTICE } | "QUIT" { COMMAND QUIT } | "PING" { COMMAND PING } | eof { EOL } and message = parse | ':'((letter+) as s) { if !state = Header then state := Command; STRING s } | [' ']* { if !state = Header || !state = Command then begin state := Params; command lexbuf end else begin state := Params; param lexbuf end } | eof { EOL }