/*
 * RTEFromStringLexer.cpp
 *
 *  Created on: Nov 23, 2013
 *      Author: Jan Travnicek
 */

#include "RTEFromStringLexer.h"

namespace rte {

RTEFromStringLexer::Token RTEFromStringLexer::next(std::istream& input) {
	RTEFromStringLexer::Token token;
	token.type = TokenType::ERROR;
	token.value = "";
	token.raw = "";
	char character;

L0:
	character = input.get();
	if ( input.eof ( ) || character == EOF ) {
		token.type = TokenType::TEOF;
		return token;
	} else if ( ext::isspace ( character ) ) {
		token.raw += character;
		goto L0;
	} else if(character == '(') {
		token.type = TokenType::LPAR;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == ')') {
		token.type = TokenType::RPAR;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == '+') {
		token.type = TokenType::PLUS;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == '*') {
		token.type = TokenType::STAR;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == '.') {
		token.type = TokenType::DOT;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == ',') {
		token.type = TokenType::COMMA;
		token.value += character;
		token.raw += character;
		return token;
	} else if(character == '#') {
		token.value += character;
		token.raw += character;
		goto L1;
	} else if ( ( character >= '0' ) && ( character <= '9' ) ) {
		token.type = TokenType::RANK;
		token.value += character;
		token.raw += character;
		goto L2;
	} else {
		input.clear ( );
		input.unget ( );
		putback(input, token);
		token.raw = "";
		token.type = TokenType::ERROR;
		return token;
	}
L1:
	character = input.get();
	if(input.eof()) {
		token.type = TokenType::TEOF;
		return token;
	} else if(character == '0') {
		token.type = TokenType::EMPTY;
		token.value += character;
		token.raw += character;
		return token;
	} else {
		input.clear ( );
		input.unget ( );
		putback(input, token);
		token.raw = "";
		token.type = TokenType::ERROR;
		return token;
	}
L2:	character = input.get ( );

	if ( input.eof ( ) ) {
		return token;
	} else if ( ( character >= '0' ) && ( character <= '9' ) ) {
		token.value += character;
		token.raw += character;
		goto L2;
	} else {
		input.clear ( );
		input.unget ( );
		return token;
	}
}

} /* namespace rte */
