Taylor Bockman 6 years ago
parent
commit
4c12c857ff
  1. 1
      Cargo.toml
  2. 2
      src/lib.rs
  3. 27
      src/parser.rs
  4. 1
      tests/options.rs
  5. 43
      tests/parser.rs

1
Cargo.toml

@ -10,3 +10,4 @@ categories = ["games", "game-engines", "api-bindings", "config", "development-to
license = "GPL-3.0"
[dependencies]
"either" = "1.4.0"

2
src/lib.rs

@ -7,6 +7,8 @@
// IMPLEMENT OPTION SENDING.
// ALSO CHANGE COMMANDS TO HAVE A CONSTANTS SUBMODULE LIKE OPTIONS
extern crate either;
pub mod commands;
pub mod options;
pub mod parser;

27
src/parser.rs

@ -1,10 +1,15 @@
//! Parser contains the command parser for handling receiving commands from the GUI
use std::collections::HashMap;
use commands;
use either::Either;
pub use either::Left;
pub use either::Right;
/// Token represents a parsable token in the string sent via STDIN from the GUI
#[derive(Debug)]
#[derive(Debug, Eq, PartialEq)]
pub enum Token {
UCI,
DEBUG,
@ -38,13 +43,25 @@ pub struct Parser {}
/// --------- ---- ---- ----- --
/// Token arg val arg val
///
/// debug on
/// ----- --
/// Token val
///
///
/// The user is still responsible for knowing what to look for in the hashmap but this structure makes it far
/// easier to work with commands. Some commands don't have arguments, in that case the args will be None.
#[derive(Debug)]
#[derive(Debug, PartialEq)]
pub struct TokenResult {
token: Token,
args: Option<HashMap<&'static str, CommandValue>>,
args: Either<Option<HashMap<&'static str, CommandValue>>, &'static str>,
}
impl TokenResult {
/// Intantiates a new TokenResult
pub fn new(token: Token, args: Either<Option<HashMap<&'static str, CommandValue>>, &'static str>>) -> TokenResult {
TokenResult { token, args }
}
}
impl Parser {
@ -56,7 +73,7 @@ impl Parser {
/// Parses a single string from the GUI and turns it into a neatly packaged TokenResult for processing
/// by the engine.
pub fn parse(s: &str) -> Result<TokenResult, &'static str> {
pub fn parse(&self, s: &str) -> Result<TokenResult, &'static str> {
// TODO: Remove the /n from the end
@ -67,7 +84,7 @@ impl Parser {
// remove this when it's working
Err("lol")
Ok(TokenResult::new(Token::SETOPTION, Left(Some(HashMap::new()))))
}
}

1
tests/options.rs

@ -1,6 +1,5 @@
extern crate uci;
use uci::Engine;
use uci::options::constants;
use uci::options::{ EngineOption, EngineOptionType, EngineOptionDataType, EngineOptionData };

43
tests/parser.rs

@ -13,14 +13,14 @@ use uci::parser;
#[test]
fn parse_setoption() {
let s = "setoption name Hash value 32\n";
let expected = parser::TokenResult {
token: parser::Token::SETOPTION,
args: Some(
let expected = parser::TokenResult::new(
parser::Token::SETOPTION,
parser::Left(Some(
[
("name", parser::CommandValue::Text(String::from("Hash"))),
("value", parser::CommandValue::Int(32)),
].iter().cloned().collect()),
};
].iter().cloned().collect())
));
let p = parser::Parser::new();
@ -33,6 +33,39 @@ fn parse_setoption() {
}
#[test]
fn parse_uci() {
let s = "uci\n";
let expected = parser::TokenResult::new(
parser::Token::UCI, parser::Left(None);
let p = parser::Parser::new();
match p.parse(s) {
Ok(r) => {
assert_eq!(r, expected);
}
Err(_) => panic!("failed to parse uci as expected")
}
}
#[test]
fn parse_debug() {
let s = "debug on\n";
let expected = parser::TokenResult::new(
parser::Token::DEBUG, parser::Right("on")
);
let p = parser::Parser::new();
match p.parse(s) {
Ok(r) => {
assert_eq!(r, expected);
}
Err(_) => panic!("failed to parse uci as expected")
}
}
#[test]
fn bad_parse() {
assert_eq!(true, false);
}

Loading…
Cancel
Save