Add struct inheritance in cpp mode

This commit is contained in:
drmortalwombat 2023-06-18 10:20:50 +02:00
parent b8478348ed
commit 37416a61cb
4 changed files with 50 additions and 14 deletions

View File

@ -794,7 +794,7 @@ bool Declaration::IsSubType(const Declaration* dec) const
if (mType != dec->mType)
return false;
if (mSize != dec->mSize)
if (mType != DT_TYPE_STRUCT && mSize != dec->mSize)
return false;
if (mStripe != dec->mStripe)
return false;
@ -810,7 +810,15 @@ bool Declaration::IsSubType(const Declaration* dec) const
else if (mType == DT_TYPE_BOOL || mType == DT_TYPE_FLOAT || mType == DT_TYPE_VOID)
return true;
else if (mType == DT_TYPE_STRUCT || mType == DT_TYPE_ENUM)
return mScope == dec->mScope || (mIdent == dec->mIdent && mSize == dec->mSize);
{
if (mScope == dec->mScope || (mIdent == dec->mIdent && mSize == dec->mSize))
return true;
if (dec->mBase)
return IsSubType(dec->mBase);
return false;
}
else if (mType == DT_TYPE_UNION)
return false;
else if (mType == DT_TYPE_ARRAY)
@ -964,7 +972,7 @@ bool Declaration::IsSameValue(const Declaration* dec) const
bool Declaration::CanAssign(const Declaration* fromType) const
{
if (mType == DT_TYPE_REFERENCE)
return fromType->IsSubType(mBase);
return mBase->IsSubType(fromType);
else if (fromType->mType == DT_TYPE_REFERENCE)
return this->CanAssign(fromType->mBase);
@ -976,7 +984,13 @@ bool Declaration::CanAssign(const Declaration* fromType) const
return true;
}
else if (mType == DT_TYPE_STRUCT && fromType->mType == DT_TYPE_STRUCT)
return mScope == fromType->mScope || (mIdent == fromType->mIdent && mSize == fromType->mSize);
{
if (mScope == fromType->mScope || (mIdent == fromType->mIdent && mSize == fromType->mSize))
return true;
if (fromType->mBase)
return this->CanAssign(fromType->mBase);
return false;
}
else if (mType == DT_TYPE_POINTER)
{
if (fromType->mType == DT_TYPE_POINTER || fromType->mType == DT_TYPE_ARRAY)

View File

@ -71,6 +71,7 @@ enum ErrorID
ERRR_STRIPE_REQUIRES_FIXED_SIZE_ARRAY,
ERRR_CANNOT_FIND_BANK_OF_EXPRESSION,
ERRO_NOT_A_NAMESPACE,
ERRO_NOT_A_BASE_CLASS,
ERRR_STACK_OVERFLOW,
ERRR_INVALID_NUMBER,

View File

@ -77,6 +77,11 @@ InterCodeGenerator::ExValue InterCodeGenerator::CoerceType(InterCodeProcedure* p
return v;
}
else if (type->mType == DT_TYPE_STRUCT && type->mBase->IsSubType(v.mType))
{
v.mType = type;
return v;
}
if (v.mType->IsIntegerType() && type->mType == DT_TYPE_FLOAT)
{
@ -936,15 +941,15 @@ InterCodeGenerator::ExValue InterCodeGenerator::TranslateInline(Declaration* pro
cins->mSrc[0].mType = IT_POINTER;
cins->mSrc[0].mTemp = vr.mTemp;
cins->mSrc[0].mMemory = IM_INDIRECT;
cins->mSrc[0].mOperandSize = vr.mType->mSize;
cins->mSrc[0].mOperandSize = vp.mType->mSize;
cins->mSrc[0].mStride = vr.mType->mStripe;
cins->mSrc[1].mType = IT_POINTER;
cins->mSrc[1].mTemp = ains->mDst.mTemp;
cins->mSrc[1].mMemory = IM_INDIRECT;
cins->mSrc[1].mOperandSize = vr.mType->mSize;
cins->mSrc[1].mOperandSize = vp.mType->mSize;
cins->mConst.mOperandSize = vr.mType->mSize;
cins->mConst.mOperandSize = vp.mType->mSize;
block->Append(cins);
}
}
@ -2636,15 +2641,15 @@ InterCodeGenerator::ExValue InterCodeGenerator::TranslateExpression(Declaration*
cins->mSrc[0].mType = IT_POINTER;
cins->mSrc[0].mTemp = vr.mTemp;
cins->mSrc[0].mMemory = IM_INDIRECT;
cins->mSrc[0].mOperandSize = vr.mType->mSize;
cins->mSrc[0].mOperandSize = vp.mType->mSize;
cins->mSrc[0].mStride = vr.mType->mStripe;
cins->mSrc[1].mOperandSize = vr.mType->mSize;
cins->mSrc[1].mOperandSize = vp.mType->mSize;
cins->mSrc[1].mType = IT_POINTER;
cins->mSrc[1].mTemp = ains->mDst.mTemp;
cins->mSrc[1].mMemory = IM_INDIRECT;
cins->mConst.mOperandSize = vr.mType->mSize;
cins->mConst.mOperandSize = vp.mType->mSize;
block->Append(cins);
}
@ -2969,15 +2974,15 @@ InterCodeGenerator::ExValue InterCodeGenerator::TranslateExpression(Declaration*
cins->mSrc[0].mType = IT_POINTER;
cins->mSrc[0].mTemp = vr.mTemp;
cins->mSrc[0].mMemory = IM_INDIRECT;
cins->mSrc[0].mOperandSize = vr.mType->mSize;
cins->mSrc[0].mOperandSize = procType->mBase->mSize;
cins->mSrc[0].mStride = vr.mType->mStripe;
cins->mSrc[1].mOperandSize = vr.mType->mSize;
cins->mSrc[1].mOperandSize = procType->mBase->mSize;
cins->mSrc[1].mType = IT_POINTER;
cins->mSrc[1].mTemp = ains->mDst.mTemp;
cins->mSrc[1].mMemory = IM_INDIRECT;
cins->mConst.mOperandSize = vr.mType->mSize;
cins->mConst.mOperandSize = procType->mBase->mSize;
block->Append(cins);
}
else

View File

@ -39,7 +39,7 @@ Declaration* Parser::ParseStructDeclaration(uint64 flags, DecType dt)
structName = mScanner->mTokenIdent;
mScanner->NextToken();
Declaration* edec = mScope->Lookup(structName);
if (edec && mScanner->mToken != TK_OPEN_BRACE)
if (edec && mScanner->mToken != TK_OPEN_BRACE && mScanner->mToken != TK_COLON)
{
dec = edec;
}
@ -67,6 +67,22 @@ Declaration* Parser::ParseStructDeclaration(uint64 flags, DecType dt)
dec->mScope = new DeclarationScope(nullptr, SLEVEL_CLASS);
}
if ((mCompilerOptions & COPT_CPLUSPLUS) && mScanner->mToken == TK_COLON)
{
mScanner->NextToken();
Declaration* pdec = ParseQualIdent();
if (pdec)
{
if (pdec->mType == DT_TYPE_STRUCT)
{
dec->mBase = pdec;
dec->mSize = pdec->mSize;
}
else
mErrors->Error(mScanner->mLocation, ERRO_NOT_A_BASE_CLASS, "Not a base class", dec->mIdent);
}
}
if (mScanner->mToken == TK_OPEN_BRACE)
{
mScanner->NextToken();