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

📄 gcppparser.cpp

📁 一个非常有用的开源代码
💻 CPP
📖 第 1 页 / 共 4 页
字号:
	Advance(); // move past the "class" or "struct"	GCppToken* pTok = GetToken(0);	char szTmp[8];	const char* pName;	int nNameLen;	bool bNoname;	if(pTok->Equals("{"))	{		// no name is specified, so make a random name		GetRandomName(szTmp);		pName = szTmp;		nNameLen = 8;		bNoname = true;	}	else	{		pName = pTok->GetValue();		nNameLen = pTok->GetLength();		Advance();		pTok = GetToken(0);		bNoname = false;	}	// See if the type already exists	GCppType* pType = FindType(pName, nNameLen);	GCppStruct* pStruct;	if(pType)	{		// todo: make sure it's a struct or class as appropriate		pStruct = (GCppStruct*)pType;	}	else	{		// Make a new struct or class		char* pStructName = m_pStringHeap->Add(pName, nNameLen);		if(bClass)			pStruct = new GCppClass(pStructName);		else			pStruct = new GCppStruct(pStructName);		// Add the type to the current scope		GetCurrentScope()->m_pTypes->Add(pStructName, pStruct);		// Set the comment		if(m_pComment)		{			pStruct->m_pComment = m_pComment;			m_pComment = NULL;		}	}	// Parse inheritance and initializers	if(bClass)	{		// Get the parent -- todo: support multiple inherritance		if(pTok->Equals(":"))			{			Advance();			pTok = GetToken(0);			if(pTok->Equals("public"))			{				Advance();				pTok = GetToken(0);			}			GCppType* pParent = FindType(pTok->GetValue(), pTok->GetLength());			if(!pParent)			{				//OnError(pTok, "Parent class not found");			}			// todo: special-case the "Object" class			GCppClass* pClass = (GCppClass*)pStruct;			pClass->SetParent((GCppClass*)pParent); // todo: make sure it's a class			Advance();			pTok = GetToken(0);		}		// Skip interfaces and member initializers		while(!pTok->Equals(";") && !pTok->Equals("{"))		{			Advance();			pTok = GetToken(0);		}	}	// If it's just a type declaration, we're done	if(pTok->Equals(";"))		return pStruct;	// if we're doing a typedef and it's not a '{', we're done	if(bTypeDef)	{		if(!pTok->Equals("{"))			return pStruct;	}	// Parse the scope	if(pTok->Equals("{"))	{		Advance(); // Move past the "{"		GCppFile* pFile = GetCurrentFile();		if(pFile->IsProjectFile() && !bNoname)			pStruct->SetDeclaredInProjectFile();		pStruct->SetSource(pFile->GetFilename(), pFile->GetCurrentLine());		PushScope(pStruct);		if(!ParseScope())			return NULL;	}	// See if it's also a declaration	pTok = GetToken(0);	if(!bTypeDef && !pTok->Equals(";"))	{		GCppDeclaration* pDecl = parseDecl2(pStruct, false, false);		if(!pDecl)			return NULL;		if(pDecl->GetDeclType() == GCppDeclaration::VAR)			GetCurrentScope()->m_pVariables->Add(pDecl->GetName(), pDecl);		else if(pDecl->GetDeclType() == GCppDeclaration::METHOD)			GetCurrentScope()->m_pMethods->Add(pDecl->GetName(), pDecl);		else		{			delete(pDecl);			OnError(GetToken(0), "unexpected declaration type");			return NULL;		}	}	return pStruct;}bool GCppParser::ParseEnum(){	GCppEnum* pEnum = ParseEnum(false);	if(pEnum)		return true;	else		return false;}GCppEnum* GCppParser::ParseEnum(bool bTypeDef){	// Find or make the enum	Advance(); // move past the "enum"	GCppToken* pTok = GetToken(0);	GCppType* pType = NULL;	if(!pTok->Equals("{"))		pType = FindType(pTok->GetValue(), pTok->GetLength());	GCppEnum* pEnum;	bool bNoname = false;	if(pType)	{		// todo: make sure it's an enum		pEnum = (GCppEnum*)pType;		bNoname = !pEnum->IsDeclaredInProjectFile();	}	else	{		// Get a name for the enum		char szTmp[8];		const char* pName;		int nNameLen;		if(pTok->Equals("{"))		{			// no name is specified, so make a random name			GetRandomName(szTmp);			pName = szTmp;			nNameLen = 8;			bNoname = true;		}		else		{			// use the specified name			pName = pTok->GetValue();			nNameLen = pTok->GetLength();			Advance();			bNoname = false;		}		// make the enum		char* pEnumName = m_pStringHeap->Add(pName, nNameLen);		pEnum = new GCppEnum(pEnumName);		// Add the type to the current scope		GetCurrentScope()->m_pTypes->Add(pEnumName, pEnum);		// Set the comment		if(m_pComment)		{			pEnum->m_pComment = m_pComment;			m_pComment = NULL;		}	}	// If it's just a declaration, we're done	pTok = GetToken(0);	if(pTok->Equals(";"))		return pEnum;	// if we're doing a typedef and it's not a '{', we're done	if(bTypeDef)	{		if(!pTok->Equals("{"))			return pEnum;	}	// Just skip the scope--todo: don't skip it	if(pTok->Equals("{"))	{		if(GetCurrentFile()->IsProjectFile() && !bNoname)			pEnum->SetDeclaredInProjectFile();		Advance(); // Move past the "{"		while(true)		{			pTok = GetToken(0);			if(pTok->GetLength() == 0)				break;			if(pTok->Equals("}"))				break;			GAssert(!pTok->Equals("{"), "unexpected '{' inside enum");			Advance();		}		Advance(); // Move past the "}:	}	// See if it's also a declaration	pTok = GetToken(0);	if(!bTypeDef && !pTok->Equals(";"))	{		GCppDeclaration* pDecl = parseDecl2(pEnum, false, false);		if(!pDecl)			return NULL;		if(pDecl->GetDeclType() == GCppDeclaration::VAR)			GetCurrentScope()->m_pVariables->Add(pDecl->GetName(), pDecl);		else if(pDecl->GetDeclType() == GCppDeclaration::METHOD)			GetCurrentScope()->m_pMethods->Add(pDecl->GetName(), pDecl);		else		{			delete(pDecl);			OnError(GetToken(0), "unexpected declaration type");			return NULL;		}	}	return pEnum;}bool GCppParser::ParseFriend(){	Advance(); // Move past the "friend" token	while(true)	{		GCppToken* pTok = GetToken(0);		if(pTok->GetLength() < 1 || pTok->Equals(";"))			break;		Advance();	}	return true;}bool GCppParser::ParseSetAccess(GCppAccess eAccess){	Advance();	GCppToken* pTok = GetToken(0);	if(!pTok->Equals(":"))		return OnError(pTok, "Expected a ':'");	Advance(); // Move past the ':'	GetCurrentScope()->m_eCurrentAccess = eAccess;	return true;}bool GCppParser::ParseMethodModifier(GCppMethodModifier eModifier){	Advance();	m_eMethodModifiers |= eModifier;	return true;}bool GCppParser::ParseVarModifier(GCppVarModifier eModifier){	Advance();	if(eModifier == VM_POINTER && ((m_eVarModifiers & VM_POINTER) != 0))	{		m_eVarModifiers &= (~VM_POINTER);		eModifier = VM_POINTERPOINTER;	}	m_eVarModifiers |= eModifier;	return true;}bool GCppParser::ParseDeclaration(){	GCppDeclaration* pDecl = ParseDecl(false);	if(!pDecl)		return false;	if(pDecl->GetDeclType() == GCppDeclaration::VAR)	{		GetCurrentScope()->m_pVariables->Add(pDecl->GetName(), pDecl);		return true;	}	else if(pDecl->GetDeclType() == GCppDeclaration::METHOD)	{		GetCurrentScope()->m_pMethods->Add(pDecl->GetName(), pDecl);		return true;	}	delete(pDecl);	OnError(GetToken(0), "unexpected declaration type");	return false;}GCppType* GCppParser::ParseTypeRef(bool bParam, bool bTypeDef){	// Skip any type specifiers	GCppToken* pTok = GetToken(0);	if(pTok->Equals("class") ||		pTok->Equals("struct") ||		pTok->Equals("enum"))		Advance();	// Parse any prefix modifiers	while(true)	{		pTok = GetToken(0);		if(pTok->Equals("const"))			ParseVarModifier(VM_CONST);		else if(pTok->Equals("unsigned"))			ParseVarModifier(VM_UNSIGNED);		else			break;	}	// Find the type	pTok = GetToken(0);	GCppType* pType = FindType(pTok->GetValue(), pTok->GetLength());	if(!pType)	{		OnError(pTok, "undeclared identifier");		return NULL;	}	Advance();	if(!bTypeDef)		ParseSuffixModifiers(bParam);	return pType;}void GCppParser::ParseSuffixModifiers(bool bParam){	// Parse any suffix modifiers	while(true)	{		GCppToken* pTok = GetToken(0);		if(bParam && pTok->Equals("&"))			ParseVarModifier(VM_REFERENCE);		else if(pTok->Equals("*"))			ParseVarModifier(VM_POINTER);		else if(pTok->Equals("__cdecl"))			Advance();//		else if(pTok->Equals("near"))//			Advance();//		else if(pTok->Equals("far"))//			Advance();//		else if(pTok->Equals("NEAR"))//			Advance();//		else if(pTok->Equals("FAR"))//			Advance();//		else if(pTok->Equals("POINTER_64"))//			Advance();//		else if(pTok->Equals("APIENTRY"))//			Advance();//		else if(pTok->Equals("NTAPI"))//			Advance();//		else if(pTok->Equals("WINAPI"))//			Advance();//		else if(pTok->Equals("RESTRICTED_POINTER"))//			Advance();//		else if(pTok->Equals("UNALIGNED"))//			Advance();		else			break;	}}GCppDeclaration* GCppParser::ParseDecl(bool bParam){	// See if it's a destructor	bool bDestructor = false;	GCppToken* pTok = GetToken(0);	if(pTok->Equals("~"))	{		bDestructor = true;		Advance();	}	// Parse the type	GCppType* pType = ParseTypeRef(bParam, false);	if(!pType)		return NULL;	return parseDecl2(pType, bParam, bDestructor);}GCppDeclaration* GCppParser::parseDecl2(GCppType* pType, bool bParam, bool bDestructor){	ParseSuffixModifiers(bParam);	// Parse scope specifiers	bool bScopeSpecified = false;	if(GetToken(1)->Equals(":") && GetToken(2)->Equals(":"))	{		GCppToken* pTok = GetToken(0);		GCppType* pType = FindType(pTok->GetValue(), pTok->GetLength());		if(!pType)		{			OnError(pTok, "Unrecognized type");			return NULL;		}		bScopeSpecified = true;		PushScope(pType);	}	// Parse the declaration	GCppDeclaration* pDecl = parseDecl3(pType, bParam, bDestructor);	// Undo any specified scope	if(bScopeSpecified)	{		if(!PopScope())			return NULL;	}	return pDecl;}GCppDeclaration* GCppParser::parseDecl3(GCppType* pType, bool bParam, bool bDestructor){	// See if it's a constructor	bool bConstructor = false;	const char* szName;	GCppToken* pTok = GetToken(0);	if(pTok->Equals("("))	{		if(pType != GetCurrentScope())		{			OnError(pTok, "Constructor name doesn't match type");			return NULL;		}		if(bDestructor)		{			char* pTmp = (char*)alloca(strlen(pType->m_szName) + 2);			strcpy(pTmp, "~");			strcat(pTmp, pType->m_szName);			szName = m_pStringHeap->Add(pTmp);			m_eMethodModifiers |= MM_DESTRUCTOR;		}		else		{			szName = pType->m_szName;			bConstructor = true;			m_eMethodModifiers |= MM_CONSTRUCTOR;		}	}	else if(pTok->GetLength() <= 0 || (bParam && (pTok->Equals(")") || pTok->Equals(",")) || pTok->Equals(":")))	{		szName = "<unnamed>";	}	else	{		szName = m_pStringHeap->Add(pTok->GetValue(), pTok->GetLength());		Advance();	}	pTok = GetToken(0);	// See if it's an array declaration	while(pTok->Equals("["))	{		m_eVarModifiers |= VM_ARRAY;		Advance(); // move past the "["		// Skip the count of elements		while(true)		{			pTok = GetToken(0);			if(pTok->GetLength() <= 0 || pTok->Equals("]"))				break;			Advance();		}		Advance(); // move past the "]"		pTok = GetToken(0);	}	// Swallow any bit specifiers	if(pTok->Equals(":"))	{		Advance(); // Move past the ':'		Advance(); // Move past the bit count		pTok = GetToken(0);	}	// if it's a variable declaration, make it now	if(pTok->Equals(";") ||		pTok->Equals("=") ||		pTok->Equals(",") ||		(bParam && pTok->Equals(")")))	{		// Skip default parameter values		if(bParam && pTok->Equals("="))		{			Advance();			while(true)			{				pTok = GetToken(0);				if(pTok->GetLength() <= 0 || pTok->Equals(",") || pTok->Equals(")"))					break;				Advance();			}		}		// Create the variable declaration		unsigned int eVarModifiers = m_eVarModifiers;		m_eVarModifiers = 0;		GCppVariable* pNewVar = new GCppVariable(pType, szName, GetCurrentScope()->m_eCurrentAccess, (GCppVarModifier)eVarModifiers);		GCppFile* pFile = GetCurrentFile();		if(pFile->IsProjectFile())			pNewVar->SetDeclaredInProjectFile();		pNewVar->SetSource(pFile->GetFilename(), pFile->GetCurrentLine());		if(m_pComment)		{			pNewVar->m_pComment = m_pComment;			m_pComment = NULL;		}		return pNewVar;	}	// Move past the "("	if(bParam || !pTok->Equals("("))	{		OnError(pTok, "unexpected token in declaration");		return NULL;	}	Advance(); // Move past the "(" token	// Parse the parameters	unsigned int eMethodModifiers = m_eMethodModifiers;	Holder<GCppMethod*> hMethod(new GCppMethod(pType, GetCurrentScope(), szName, GetCurrentScope()->m_eCurrentAccess, (GCppMethodModifier)eMethodModifiers));	GCppFile* pFile = GetCurrentFile();	if(m_pComment)	{		hMethod.Get()->m_pComment = m_pComment;		m_pComment = NULL;	}	if(pFile->IsProjectFile())		hMethod.Get()->SetDeclaredInProjectFile();	hMethod.Get()->SetSource(pFile->GetFilename(), pFile->GetCurrentLine());	m_eMethodModifiers = 0;	while(true)	{		pTok = GetToken(0);		if(pTok->Equals(")"))

⌨️ 快捷键说明

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