   #! is the getter word for that register with stack effect
   #! ( cpu -- value ). The second item is the setter word with
   #! stack effect ( value cpu -- ).
-  "AF" token  
-  "BC" token <|>
-  "DE" token <|>
-  "HL" token <|>
-  "SP" token <|> [ register-lookup ] <@ ;
+  <EBNF
+    main=("AF" | "BC" | "DE" | "HL" | "SP") => [[ register-lookup ]]
+  EBNF> ;
 
 : all-registers ( -- parser )
   #! Return a parser that can parse the format
   #! for 8 bit or 16 bit registers. 
-  8-bit-registers 16-bit-registers <|> ;
+  [ 16-bit-registers , 8-bit-registers , ] choice* ;
 
 : indirect ( parser -- parser )
   #! Given a parser, return a parser which parses the original
   #! wrapped in brackets, representing an indirect reference.
   #! eg. BC -> (BC). The value of the original parser is left in
   #! the parse tree.
-  "(" token swap &> ")" token <& ;
+  "(" ")" surrounded-by ;
 
 : generate-instruction ( vector string -- quot )
   #! Generate the quotation for an instruction, given the instruction in 

  #! Return a parser for then instruction identified by the token. 
  #! The parser return parses the token only and expects no additional
  #! arguments to the instruction.
  token [ [ { } clone , , \ generate-instruction , ] [ ] make ] <@ ;

: complex-instruction ( type token -- parser )
  #! Return a parser for an instruction identified by the token. 
  #! The instruction is expected to take additional arguments by 
  #! being combined with other parsers. Then 'type' is used for a lookup
  #! in a pattern hashtable to return the instruction quotation pattern.
  token swap [ nip [ , \ generate-instruction , ] [ ] make ] curry <@ ;

: NOP-instruction ( -- parser )
  "NOP" simple-instruction ;

: RET-NN-instruction ( -- parser )  
  "RET-NN" "RET" complex-instruction  
  "nn" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-0-instruction ( -- parser )  
  "RST-0" "RST" complex-instruction  
  "0" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-8-instruction ( -- parser )  
  "RST-8" "RST" complex-instruction  
  "8" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-10H-instruction ( -- parser )  
  "RST-10H" "RST" complex-instruction  
  "10H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-18H-instruction ( -- parser )  
  "RST-18H" "RST" complex-instruction  
  "18H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-20H-instruction ( -- parser )  
  "RST-20H" "RST" complex-instruction  
  "20H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-28H-instruction ( -- parser )  
  "RST-28H" "RST" complex-instruction  
  "28H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-30H-instruction ( -- parser )  
  "RST-30H" "RST" complex-instruction  
  "30H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: RST-38H-instruction ( -- parser )  
  "RST-38H" "RST" complex-instruction  
  "38H" token sp <&
  just [ { } clone swap curry  ] <@ ;

: JP-NN-instruction ( -- parser )  
  "JP-NN" "JP" complex-instruction  
  "nn" token sp <&
  just [ { } clone swap curry  ] <@ ;

: JP-F|FF,NN-instruction ( -- parser )
  "JP-F|FF,NN" "JP" complex-instruction  
  all-flags sp <&> 
  ",nn" token <&
  just [ first2 swap curry ] <@ ;

: JP-(RR)-instruction ( -- parser )
  "JP-(RR)" "JP" complex-instruction  
  16-bit-registers indirect sp <&>
  just [ first2 swap curry ] <@ ;

: CALL-NN-instruction ( -- parser )  
  "CALL-NN" "CALL" complex-instruction  
  "nn" token sp <&
  just [ { } clone swap curry  ] <@ ;

: CALL-F|FF,NN-instruction ( -- parser )
  "CALL-F|FF,NN" "CALL" complex-instruction  
  all-flags sp <&> 
  ",nn" token <&
  just [ first2 swap curry ] <@ ;

: RLCA-instruction ( -- parser )
  "RLCA" simple-instruction ;

! See http://factorcode.org/license.txt for BSD license.
!
USING: accessors kernel math sequences words arrays io io.files
math.parser assocs quotations parser lexer
peg peg.ebnf peg.parsers tools.time io.encodings.binary sequences.deep
symbols combinators fry namespaces ;
IN: cpu.8080.emulator

TUPLE: cpu b c d e f h l a pc sp halted? last-interrupt cycles ram ;
