⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sdkparse.cpp

📁 ReactOS是一些高手根据Windows XP的内核编写出的类XP。内核实现机理和API函数调用几乎相同。甚至可以兼容XP的程序。喜欢研究系统内核的人可以看一看。
💻 CPP
📖 第 1 页 / 共 2 页
字号:
		char* pStruct = strstr ( p, structs[i] );
		if ( pStruct
			&& pStruct < semi
			&& !__iscsym(pStruct[-1])
			&& !__iscsym(pStruct[strlen(structs[i])]) )
		{
			// make sure there's at most one identifier followed
			// by a {
			pStruct += strlen(structs[i]);
			pStruct = skip_ws ( pStruct );
			if ( __iscsymf(*pStruct) )
			{
				while ( __iscsym(*pStruct) )
					pStruct++;
				pStruct = skip_ws ( pStruct );
			}
			// special exception - C++ classes & stuff
			if ( *pStruct == ':' )
			{
				pStruct = skip_ws ( pStruct + 1 );
				ASSERT ( !strncmp(pStruct,"public",6) || !strncmp(pStruct,"protected",9) || !strncmp(pStruct,"private",7) );
				// skip access:
				while ( __iscsym(*pStruct) )
					pStruct++;
				pStruct = skip_ws ( pStruct );
				// skip base-class-name:
				ASSERT ( __iscsymf(*pStruct) );
				while ( __iscsym(*pStruct) )
					pStruct++;
				pStruct = skip_ws ( pStruct );
			}
			if ( *pStruct == '{' )
				isStruct = true;
			break;
		}
	}

	if ( isStruct )
	{
		end = strchr ( end, ';' );
		if ( !end )
			end = p + strlen(p);
		else
			end++;
	}
	else
	{
		char* p2 = skip_ws ( end );
		if ( *p2 == ';' )
			end = p2 + 1;
	}
	return end;
}

int skip_declspec ( const vector<string>& tokens, int off )
{
	if ( tokens[off] == "__declspec" )
	{
		off++;
		TOKASSERT ( tokens[off] == "(" );
		off++;
		int parens = 1;
		while ( parens )
		{
			if ( tokens[off] == "(" )
				parens++;
			else if ( tokens[off] == ")" )
				parens--;
			off++;
		}
	}
	return off;
}

Type identify ( const vector<string>& tokens, int off )
{
	off = skip_declspec ( tokens, off );
	/*if ( tokens.size() > off+4 )
	{
		if ( tokens[off+4] == "PCONTROLDISPATCHER" )
			_CrtDbgBreak();
	}*/
	/*if ( tokens.size() > off+1 )
	{
		if ( tokens[off+1] == "_OSVERSIONINFOEXA" )
			_CrtDbgBreak();
	}*/
	if ( tokens[off] == "__asm__" )
		return T_IGNORED_STATEMENT;
	else if ( tokens[off] == "return" )
		return T_IGNORED_STATEMENT;
	else if ( tokens[off] == "typedef_tident" )
		return T_TIDENT;
	else if ( tokens[off] == "if" )
		return T_IF;
	else if ( tokens[off] == "while" )
		return T_WHILE;
	else if ( tokens[off] == "do" )
		return T_DO;
	int openparens = 0;
	int closeparens = 0;
	int brackets = 0;
	for ( int i = off; i < tokens.size(); i++ )
	{
		if ( tokens[i] == "(" && !brackets )
			openparens++;
		else if ( tokens[i] == ")" && !brackets && openparens == 1 )
			closeparens++;
		else if ( tokens[i] == "{" )
			brackets++;
		else if ( (tokens[i] == "struct" || tokens[i] == "union") && !openparens )
		{
			for ( int j = i + 1; j < tokens.size(); j++ )
			{
				if ( tokens[j] == "{" )
					return T_STRUCT;
				else if ( tokens[j] == "(" || tokens[j] == ";" || tokens[j] == "*" )
					break;
			}
		}
		else if ( tokens[i] == ";" )
			break;
		else if ( tokens[i] == "__attribute__" )
			break;
	}
	if ( openparens > 1 && closeparens )
		return T_FUNCTION_PTR;
	else if ( openparens >= 1 )
		return T_FUNCTION;
	return T_VARIABLE;
}

Type process ( const string& element, vector<string>& names, bool& isTypedef, vector<string>& dependencies )
{
	names.resize ( 0 );
	isTypedef = false;
	dependencies.resize ( 0 );

	vector<string> tokens;

	tokenize ( element, tokens );

	// now let's do the classification...
	int i = 0;
	if ( tokens[i] == "typedef" )
	{
		isTypedef = true;
		i++;
	}

	Type t = identify ( tokens, i );

	parse_type ( t, tokens, i, names, dependencies );

	return t;
}

int parse_type ( Type t, const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	switch ( t )
	{
	case T_IGNORED_STATEMENT:
		return parse_ignored_statement ( tokens, off, names, dependencies );
	case T_TIDENT:
		return parse_tident ( tokens, off, names, dependencies );
	case T_VARIABLE:
		return parse_variable ( tokens, off, names, dependencies );
	case T_STRUCT:
		return parse_struct ( tokens, off, names, dependencies );
	case T_FUNCTION:
		return parse_function ( tokens, off, names, dependencies );
	case T_FUNCTION_PTR:
		return parse_function_ptr ( tokens, off, names, dependencies );
	case T_IF:
	case T_WHILE:
		return parse_ifwhile ( tokens, off, names, dependencies );
	case T_DO:
		return parse_do ( tokens, off, names, dependencies );
	default:
		TOKASSERT(!"unidentified type in parse_type()");
		return 0;
	}
}

void name ( const string& ident, vector<string>& names )
{
	if ( !__iscsymf ( ident[0] ) )
		return;
	if ( iskeyword ( ident ) )
		return;
	for ( int i = 0; i < names.size(); i++ )
	{
		if ( names[i] == ident )
			return;
	}
	names.push_back ( ident );
}

void depend ( const string& ident, vector<string>& dependencies )
{
	if ( !__iscsymf ( ident[0] ) )
		return;
	if ( iskeyword ( ident ) )
		return;
	for ( int i = 0; i < dependencies.size(); i++ )
	{
		if ( dependencies[i] == ident )
			return;
	}
	dependencies.push_back ( ident );
}

int parse_ignored_statement ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	off++;
	while ( tokens[off] != ";" )
		off++;
	ASSERT ( tokens[off] == ";" );
	return off + 1;
}

int parse_tident ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	TOKASSERT ( tokens[off] == "typedef_tident" );
	TOKASSERT ( tokens[off+1] == "(" && tokens[off+3] == ")" );
	names.push_back ( tokens[off+2] );
	dependencies.push_back ( "typedef_tident" );
	return off + 4;
}

int parse_variable ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	// NOTE - Test with bitfields, I think this code will actually handle them properly...
	if ( tokens[off] == ";" )
		return off + 1;
	depend ( tokens[off++], dependencies );
	int done = tokens.size();
	while ( off < tokens.size() && tokens[off] != ";" )
		name ( tokens[off++], names );
	TOKASSERT ( off < tokens.size() && tokens[off] == ";" );
	return off + 1;
}

int parse_struct ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	int done = tokens.size();

	//if ( tokens[off+1] == "_LARGE_INTEGER" )
	//	_CrtDbgBreak();

	while ( off < done && tokens[off] != "struct" && tokens[off] != "union" )
		depend ( tokens[off++], dependencies );

	TOKASSERT ( tokens[off] == "struct" || tokens[off] == "union" );
	if ( tokens[off] != "struct" && tokens[off] != "union" )
		return off;
	off++;

	if ( tokens[off] != "{" )
		name ( tokens[off++], names );

	if ( tokens[off] == ":" )
	{
		off++;
		TOKASSERT ( tokens[off] == "public" || tokens[off] == "protected" || tokens[off] == "private" );
		off++;
		depend ( tokens[off++], dependencies );
	}

	TOKASSERT ( tokens[off] == "{" );
	off++;

	// skip through body of struct - noting any dependencies
	int indent = 1;
	//if ( off >= done ) _CrtDbgBreak();
	while ( off < done && tokens[off] != "}" )
	{
		vector<string> fauxnames;
		Type t = identify ( tokens, off );
		off = parse_type ( t, tokens, off, fauxnames, dependencies );
		//if ( off >= done ) _CrtDbgBreak();
	}

	// process any trailing dependencies/names...
	while ( tokens[off] != ";" )
	{
		TOKASSERT ( off+1 < done );
		if ( tokens[off+1] == "," || tokens[off+1] == ";" )
			name ( tokens[off], names );
		else
			depend ( tokens[off], dependencies );
		off++;
	}

	TOKASSERT ( tokens[off] == ";" );
	off++;

	return off;
}

int parse_param ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	if ( tokens[off] == ")" )
		return off;
	// special-case check for function pointer params
	int done = off;
	int parens = 1;
	bool fptr = false;
	for ( ;; )
	{
		if ( tokens[done] == "," && parens == 1 )
			break;
		if ( tokens[done] == ")" )
		{
			if ( parens == 1 )
				break;
			else
				parens--;
		}
		if ( tokens[done] == "(" )
			parens++;
		if ( tokens[done] == "*" && tokens[done-1] == "(" )
			fptr = true;
		done++;
	}
	if ( !fptr )
		done--;
	while ( off < done )
		depend ( tokens[off++], dependencies );
	if ( !fptr )
		name ( tokens[off++], names );
	return off;
}

int parse_function ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	vector<string> fauxnames;

	off = skip_declspec ( tokens, off );

	while ( tokens[off+1] != "(" )
		depend ( tokens[off++], dependencies );
	name ( tokens[off++], names );

	TOKASSERT ( tokens[off] == "(" );

	while ( tokens[off] != ")" )
	{
		off++;
		off = parse_param ( tokens, off, fauxnames, dependencies );
		TOKASSERT ( tokens[off] == "," || tokens[off] == ")" );
	}

	off++;

	// check for "attributes"
	if ( tokens[off] == "__attribute__" )
	{
		off++;
		TOKASSERT ( tokens[off] == "(" );
		off++;
		int parens = 1;
		while ( parens )
		{
			if ( tokens[off] == "(" )
				parens++;
			else if ( tokens[off] == ")" )
				parens--;
			off++;
		}
	}

	// is this just a function *declaration* ?
	if ( tokens[off] == ";" )
		return off;

	// we have a function body...
	TOKASSERT ( tokens[off] == "{" );
	off++;

	while ( tokens[off] != "}" )
	{
		Type t = identify ( tokens, off );
		if ( t == T_VARIABLE )
			off = parse_type ( t, tokens, off, fauxnames, dependencies );
		else
		{
			while ( tokens[off] != ";" )
				off++;
			TOKASSERT ( tokens[off] == ";" );
			off++;
		}
	}

	TOKASSERT ( tokens[off] == "}" );
	off++;

	return off;
}

int parse_function_ptr ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	off = skip_declspec ( tokens, off );

	while ( tokens[off] != "(" )
		depend ( tokens[off++], dependencies );

	TOKASSERT ( tokens[off] == "(" );
	off++;

	while ( tokens[off+1] != ")" )
		depend ( tokens[off++], dependencies );
	name ( tokens[off++], names );

	TOKASSERT ( tokens[off] == ")" );

	off++;

	TOKASSERT ( tokens[off] == "(" );

	while ( tokens[off] != ")" )
	{
		off++;
		vector<string> fauxnames;
		off = parse_param ( tokens, off, fauxnames, dependencies );
		TOKASSERT ( tokens[off] == "," || tokens[off] == ")" );
	}

	off++;
	TOKASSERT ( tokens[off] == ";" );
	off++;
	return off;
}

int parse_ifwhile ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	TOKASSERT ( tokens[off] == "if" || tokens[off] == "while" );
	off++;

	TOKASSERT ( tokens[off] == "(" );
	off++;

	TOKASSERT ( tokens[off] != ")" );
	while ( tokens[off] != ")" )
		off++;

	if ( tokens[off] == "{" )
	{
		while ( tokens[off] != "}" )
		{
			Type t = identify ( tokens, off );
			off = parse_type ( t, tokens, off, names, dependencies );
		}
		off++;
	}
	return off;
}

int parse_do ( const vector<string>& tokens, int off, vector<string>& names, vector<string>& dependencies )
{
	TOKASSERT ( tokens[off] == "do" );
	off++;

	if ( tokens[off] != "{" )
	{
		Type t = identify ( tokens, off );
		off = parse_type ( t, tokens, off, names, dependencies );
	}
	else
	{
		while ( tokens[off] != "}" )
		{
			Type t = identify ( tokens, off );
			off = parse_type ( t, tokens, off, names, dependencies );
		}
	}

	TOKASSERT ( tokens[off] == "while" );
	off++;

	TOKASSERT ( tokens[off] == "(" );
	while ( tokens[off] != ")" )
		off++;

	TOKASSERT ( tokens[off] == ")" );
	off++;

	TOKASSERT ( tokens[off] == ";" );
	off++;

	return off;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -