コード例 #1
0
ファイル: fold.cpp プロジェクト: omnigoat/sooty
void sooty::lexing::detail::fold_impl(std::set<base_lexer_ptr> visited_nodes, const base_lexer_ptr& lhs, const base_lexer_ptr& rhs)
{
	if (!lhs || !rhs)
		return;
	
	if (visited_nodes.find(lhs) != visited_nodes.end())
		return;
	visited_nodes.insert(lhs);
	
	if (lhs->type == base_lexer::lexer_type::marker) {
		fold_impl(visited_nodes, lhs->on_success, rhs);
	}
	else if (rhs->type == base_lexer::lexer_type::marker) {
		base_lexer_ptr saved_lhs = clone_tree(lhs);
		*lhs = *rhs;
		fold_impl(visited_nodes, lhs->on_success, saved_lhs);
	}
	// if lhs is partially equivalent to rhs, then we need to try rhs
	// if it fails, but try the one /after/ rhs if it succeeds
	else if ( partially_equivalent(lhs, rhs) )
	{
		if (lhs->on_failure)
			append_failure(lhs->on_failure, rhs);
		else
			lhs->on_failure = rhs;
		
		if (lhs->on_success)
			fold_impl(visited_nodes, lhs->on_success, rhs->on_success);
		else
			lhs->on_success = rhs->on_success;
	}
	// rhs is partially equivalent to lhs, which means that we have to
	// test rhs first, *then* lhs.
	else if ( partially_equivalent(rhs, lhs) )
	{
		base_lexer_ptr lhs_copy = clone_tree(lhs);
		*lhs = *rhs;
		visited_nodes.erase(lhs);
		fold_impl(visited_nodes, lhs, lhs_copy);
	}
	else if ( equivalent(lhs, rhs) )
	{
		if (lhs->on_success)
			fold_impl(visited_nodes, lhs->on_success, rhs->on_success);
		else {
			lhs->on_success = rhs->on_success;
			if (lhs->on_failure) {
				append_failure(lhs->on_success, lhs->on_failure);
				lhs->on_failure = base_lexer_ptr();
			}
		}
	}
	else {
		if (lhs->on_failure)
			fold_impl(visited_nodes, lhs->on_failure, rhs);
		else
			lhs->on_failure = rhs;
	}
}
コード例 #2
0
ファイル: codegen.c プロジェクト: mushrom/cminus
parse_node_t *clone_tree( parse_node_t *tokens ){
	parse_node_t *ret = NULL;

	if ( tokens ){
		ret = malloc( sizeof( *tokens ));
		*ret = *tokens;

		ret->down = clone_tree( ret->down );
		ret->next = clone_tree( ret->next );

		if ( ret->data )
			ret->data = strdup( ret->data );
	}

	return ret;
}
コード例 #3
0
ファイル: lexer.hpp プロジェクト: omnigoat/sooty
		lexer operator [](semantic_action action) const {
			static char _ = 0;
			detail::base_lexer_ptr marker(new detail::base_lexer(detail::base_lexer::lexer_type::marker, _, _));
			detail::base_lexer_ptr actor(new detail::base_lexer(detail::base_lexer::lexer_type::actor, _, _));
			actor->action = action;
			++_;
			append_success(marker, clone_tree(this->base_lexer));
			append_success(marker, actor);
			return lexer(marker);
		}
コード例 #4
0
ファイル: lexer.hpp プロジェクト: omnigoat/sooty
		lexer operator * () const {
			detail::base_lexer_ptr new_lhs = clone_tree(this->base_lexer);
			detail::zero_or_more(new_lhs);
			return lexer(new_lhs);
		}