gramatica 0.2.1

A compiler compiler for Rust implementing Earley's parser.
Documentation

extern crate gramatica;

use std::cmp::Ordering;
use std::io::BufRead;
use gramatica::{Associativity,EarleyKind,State,Parser,ParsingTablesTrait,AmbiguityInfo};

// see http://www.rfc-editor.org/rfc/rfc3986.txt
// also https://stackoverflow.com/questions/6243051/how-to-pass-an-array-within-a-query-string

#[derive(Clone,Debug,PartialEq)]
enum HierKind
{
	Authority(),
	Absolute(),
	Rootless(),
	Empty,
}


re_terminal!(Digit(char),"[0-9]");
re_terminal!(AtoF(char),"[a-fA-F]");
re_terminal!(GtoZnoV(char),"[g-uw-zG-UW-Z]");
re_terminal!(V,"[vV]");
//re_terminal!(Scheme(String),"[a-zA-Z]([a-zA-Z0-9.-])*");// ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
//re_terminal!(UserInfo(String),"([a-zA-Z0-9:])*");//FIXME *( unreserved / pct-encoded / sub-delims / ":" )
//re_terminal!(RegName(String),"([a-zA-Z0-9])*");//FIXME *( unreserved / pct-encoded / sub-delims )
//re_terminal!(Port(String),"[0-9]*");//*DIGIT
//re_terminal!(IPvFuture(String),"v[0-9A-F]\\.[a-zA-Z0-9:]");//FIXME "v" 1*HEXDIG "." 1*( unreserved / sub-delims / ":" )
//re_terminal!(IPv6Address(String),"::");//FIXME buff
////re_terminal!(IPv4Address(String),"\\.\\.\\.");
//re_terminal!(DecOctet(String),"[0-9]|[1-9][0-9]|1[0-9][0-9]|25[0-5]");

re_terminal!(Dot,"\\.");
re_terminal!(At,"@");
re_terminal!(Colon,":");
re_terminal!(Slash,"/");
re_terminal!(LBracket,"\\[");
re_terminal!(RBracket,"\\]");
re_terminal!(Percent,"%");
re_terminal!(Minus,"-");
re_terminal!(Underscore,"_");
re_terminal!(QuestionMark,"\\?");
re_terminal!(NumberSign,"#");
re_terminal!(Bang,"!");
re_terminal!(Dolar,"\\$");
re_terminal!(Ampersand,"&");
re_terminal!(SingleQuote,"'");
re_terminal!(LPar,"\\(");
re_terminal!(RPar,"\\)");
re_terminal!(Star,"\\*");
re_terminal!(Plus,"\\+");
re_terminal!(Comma,",");
re_terminal!(Semicolon,";");
re_terminal!(Equal,"=");

nonterminal Uri(String,String,Option<>,Option<>)
{
	(Scheme(ref scheme),Colon,HierPart(ref part),MaybeQuery(ref query),MaybeFragment(ref fragment)) =>
		(scheme.clone(),part.clone(),query.clone(),fragment.clone()),
}

nonterminal HierPart(HierKind)
{
	(Slash,Slash,Authority,PathABEmpty) => (),
	(PathAbsolute) => (),
	(PathRootless) => (),
	(PathEmpty) => (),
}

nonterminal Authority
{
	(MaybeUserInfo,Host,MaybePort) => (),
}

nonterminal MaybeUserInfo
{
	() => (),
	(UserInfo,At) => (),
}

nonterminal MaybePort
{
	() => (),
	(Colon,Port) => (),
}

nonterminal Host
{
	(IPLiteral) => (),
	(IPv4Address) => (),
	(RegName) => (),
}

nonterminal Port
{
	() => (),
	(Digit,Port) => (),
}

nonterminal IPLiteral
{
	(LBracket,IPv6Address,RBracket) => (),
	(LBracket,IPvFuture,RBracket) => (),
}

nonterminal IPvFuture
{
	//"v" 1*HEXDIG "." 1*( unreserved / sub-delims / ":" )
	(V,HexDigit,Dot,Unreserved) => (),
	(V,HexDigit,Dot,SubDelims) => (),
	(V,HexDigit,Dot,Colon) => (),
}

nonterminal IPv6Address
{
	(Colon,Colon) => (), //FIXME ????????????
}

nonterminal IPv4Address
{
	(DecOctet,Dot,DecOctet,Dot,DecOctet,Dot,DecOctet) => (),
}

nonterminal DecOctet
{
	(Digit) => (),
	(Digit1to9,Digit) => (),
	(Digit1,Digit,Digit) => (),
	(Digit2,Digit0to4,Digit) => (),
	(Digit2,Digit5,Digit0to5) => (),
}

nonterminal PathABEmpty
{
	() => (),
	(PathABEmpty,Dash,Segment) => (),
}

nonterminal PathAbsolute
{
	(Dash) => (),
	(Dash,SegmentNZ,Segments) => (),
}

nonterminal PathRootless
{
	(SegmentNZ,Segments) => (),
}

nonterminal Segments(Vec<String>)
{
	() => vec![],
	(Segments(ref list),Slash,Segment(ref s)) =>
	{
		let mut new=list.clone();
		new.push(s);
		new
	},
}

nonterminal Segment(String)//*pchar
{
	() => String::new(),
	(Segment(ref a),Pchar(ref b)) => a+b,
}

nonterminal SegmentNZ(String)
{
	(Pchar(ref s)) => s.clone(),
	(SegmentNZ(ref a),Pchar(ref b)) => a+b,
}

nonterminal PChar(String)
{
	(Unreserved(c)) => c.to_string(),
	(PctEncoded(ref s)) => s.clone(),
	(SubDelims(c)) => c.to_string(),
	(Colon) => String::from(":"),
	(At) => String::from("@"),
}

nonterminal Query(String)
{
	() => String::new(),
	(Query(ref a),QueryChar(ref b)) => a+b,
}

nonterminal QueryChar(String)
{
	(PChar(ref s)) => s.clone(),
	(Slash) => String::from("/"),
	(QuestionMark) => String::from("?"),
}

nonterminal PctEncoded(String)
{
	(Percent,HexDigit(a),HexDigit(b)) => format!("%{}{}",a,b),
}

nonterminal HexDigit(char)
{
	(Digit(c)) => c,
	(AtoF(c)) => c,
}

nonterminal Unreserved(char)
{
	(Alpha(c)) => c,
	(Digit(c)) => c,
	(Minus) => '-',
	(Dot) => '.',
	(Underscore) => '_',
}

nonterminal Alpha(char)
{
	(AtoF(c)) => c,
	(GtoZnoV(c)) => c,
	(V) => 'v',
}

nonterminal Reserved(char)
{
	(GenDelims(c)) => c,
	(SubDelims(c)) => c,
}

nonterminal GenDelims(char)
{
	(Colon) => ':',
	(Slash) => '/',
	(QuestionMark) => '?',
	(NumberSign) => '#',
	(LBracket) => '[',
	(RBracket) => ']',
	(At) => '@',
}

nonterminal SubDelims(char)
{
	(Bang) => '!',
	(Dolar) => '$',
	(Ampersand) => '&',
	(SingleQuote) => '\'',
	(LPar) => '(',
	(RPar) => ')',
	(Star) => '*',
	(Plus) => '+',
	(Comma) => ',',
	(Semicolon) => ';',
	(Equal) => '=',
}