From 9d3b693cfaaadfd0830b000ba64b4f1509a75bc0 Mon Sep 17 00:00:00 2001 From: Brian Fiete Date: Fri, 1 Jan 2021 16:39:04 -0800 Subject: [PATCH] Fixed some const vector and static vector issues --- IDEHelper/Backend/BeIRCodeGen.cpp | 18 ++ IDEHelper/Compiler/BfIRBuilder.cpp | 360 +++++++++++++++-------------- IDEHelper/Compiler/BfIRBuilder.h | 1 + IDEHelper/Compiler/BfIRCodeGen.cpp | 5 + 4 files changed, 206 insertions(+), 178 deletions(-) diff --git a/IDEHelper/Backend/BeIRCodeGen.cpp b/IDEHelper/Backend/BeIRCodeGen.cpp index 664e01f5..b417b7db 100644 --- a/IDEHelper/Backend/BeIRCodeGen.cpp +++ b/IDEHelper/Backend/BeIRCodeGen.cpp @@ -816,6 +816,17 @@ void BeIRCodeGen::Read(BeValue*& beValue) values.push_back(lastValue); } } + else if (type->IsVector()) + { + auto vecType = (BeVectorType*)type; + int fillCount = (int)(vecType->mLength - values.size()); + if (fillCount > 0) + { + auto lastValue = values.back(); + for (int i = 0; i < fillCount; i++) + values.push_back(lastValue); + } + } else { BF_ASSERT(type->IsStruct()); @@ -835,8 +846,15 @@ void BeIRCodeGen::Read(BeValue*& beValue) auto memberType = constant->GetType(); BF_ASSERT(memberType == arrayType->mElementType); } + else if (type->IsVector()) + { + auto vecType = (BeVectorType*)type; + auto memberType = constant->GetType(); + BF_ASSERT(memberType == vecType->mElementType); + } else { + BF_ASSERT(type->IsStruct()); auto structType = (BeStructType*)type; auto memberType = constant->GetType(); BF_ASSERT(memberType == structType->mMembers[i].mType); diff --git a/IDEHelper/Compiler/BfIRBuilder.cpp b/IDEHelper/Compiler/BfIRBuilder.cpp index 91f11e30..2429812b 100644 --- a/IDEHelper/Compiler/BfIRBuilder.cpp +++ b/IDEHelper/Compiler/BfIRBuilder.cpp @@ -3084,6 +3084,186 @@ bool BfIRBuilder::WantsDbgDefinition(BfType* type) return false; } +void BfIRBuilder::CreateTypeDefinition_Data(BfModule* populateModule, BfTypeInstance* typeInstance, bool forceDbgDefine) +{ + auto typeDef = typeInstance->mTypeDef; + +#ifdef BFIR_RENTRY_CHECK + ReEntryCheck reEntryCheck(&mDefReentrySet, type); +#endif + + bool isGlobalContainer = typeDef->IsGlobalsContainer(); + + auto diForwardDecl = DbgGetTypeInst(typeInstance); + llvm::SmallVector irFieldTypes; + if ((!typeInstance->IsTypedPrimitive()) && (typeInstance->mBaseType != NULL)) + { + irFieldTypes.push_back(MapTypeInst(typeInstance->mBaseType, BfIRPopulateType_Eventually_Full)); + } + + llvm::SmallVector diFieldTypes; + + bool isPacked = false; + bool isUnion = false; + bool isCRepr = false; + + if (typeInstance->IsBoxed()) + { + auto boxedType = (BfBoxedType*)typeInstance; + BF_ASSERT(!boxedType->mFieldInstances.IsEmpty()); + + auto& fieldInst = boxedType->mFieldInstances.back(); + auto elementType = fieldInst.mResolvedType; + populateModule->PopulateType(elementType, BfPopulateType_Data); + + if (!elementType->IsValuelessType()) + { + irFieldTypes.push_back(MapType(elementType, elementType->IsValueType() ? BfIRPopulateType_Eventually_Full : BfIRPopulateType_Declaration)); + } + } + else + { + isCRepr = typeInstance->mIsCRepr; + isPacked = typeInstance->mIsPacked; + isUnion = typeInstance->mIsUnion; + } + + BfSizedVector orderedFields; + + bool isPayloadEnum = (typeInstance->IsEnum()) && (!typeInstance->IsTypedPrimitive()); + for (auto& fieldInstanceRef : typeInstance->mFieldInstances) + { + auto fieldInstance = &fieldInstanceRef; + if (!fieldInstance->mFieldIncluded) + continue; + auto fieldDef = fieldInstance->GetFieldDef(); + + if ((fieldInstance->mResolvedType == NULL) || (typeInstance->IsBoxed())) + continue; + + if ((fieldDef != NULL) && (fieldDef->mIsStatic)) + continue; // Just create type first - we may contain a static reference to ourselves, creating an dependency loop + + auto resolvedFieldType = fieldInstance->GetResolvedType(); + + mModule->PopulateType(resolvedFieldType, BfPopulateType_Declaration); + BfIRType resolvedFieldIRType = MapType(resolvedFieldType); + BfIRMDNode resolvedFieldDIType; + + if ((fieldDef != NULL) && (resolvedFieldType->IsStruct())) + PopulateType(resolvedFieldType, BfIRPopulateType_Eventually_Full); + + if ((fieldDef == NULL) && (typeInstance->IsPayloadEnum())) + { + orderedFields.push_back(fieldInstance); + } + + if ((!typeInstance->IsBoxed()) && (fieldDef != NULL)) + { + bool useForUnion = false; + + BF_ASSERT(!fieldInstance->mIsEnumPayloadCase); + + if ((!fieldDef->mIsStatic) && (!resolvedFieldType->IsValuelessType())) + { + if (!isUnion) + { + BF_ASSERT(resolvedFieldIRType.mId != -1); + //irFieldTypes.push_back(resolvedFieldIRType); + + if (fieldInstance->mDataIdx != -1) + { + while (fieldInstance->mDataIdx >= (int)orderedFields.size()) + orderedFields.push_back(NULL); + orderedFields[fieldInstance->mDataIdx] = fieldInstance; + } + + } + } + } + } + + int dataPos = 0; + if (typeInstance->mBaseType != NULL) + dataPos = typeInstance->mBaseType->mInstSize; + + int unionSize = 0; + if (typeInstance->mIsUnion) + { + auto unionInnerType = typeInstance->GetUnionInnerType(); + irFieldTypes.push_back(MapType(unionInnerType, unionInnerType->IsValueType() ? BfIRPopulateType_Eventually_Full : BfIRPopulateType_Declaration)); + unionSize = unionInnerType->mSize; + dataPos += unionSize; + } + + for (int fieldIdx = 0; fieldIdx < (int)orderedFields.size(); fieldIdx++) + { + auto fieldInstance = orderedFields[fieldIdx]; + if (fieldInstance == NULL) + continue; + + auto resolvedFieldType = fieldInstance->GetResolvedType(); + + BfIRType resolvedFieldIRType = MapType(resolvedFieldType); + + //bool needsExplicitAlignment = !isCRepr || resolvedFieldType->NeedsExplicitAlignment(); + bool needsExplicitAlignment = true; + if (!needsExplicitAlignment) + { + int alignSize = resolvedFieldType->mAlign; + dataPos = (dataPos + (alignSize - 1)) & ~(alignSize - 1); + } + + if (fieldInstance->mDataOffset > dataPos) + { + int fillSize = fieldInstance->mDataOffset - dataPos; + auto byteType = mModule->GetPrimitiveType(BfTypeCode_Int8); + auto arrType = GetSizedArrayType(MapType(byteType), fillSize); + irFieldTypes.push_back(arrType); + dataPos = fieldInstance->mDataOffset; + } + dataPos += fieldInstance->mDataSize; + + BF_ASSERT((int)irFieldTypes.size() == fieldInstance->mDataIdx); + irFieldTypes.push_back(resolvedFieldIRType); + + if ((isCRepr) && (needsExplicitAlignment) && (fieldIdx == (int)orderedFields.size() - 1)) + { + // Add explicit padding at end to enforce the "aligned size" + int endPad = typeInstance->mInstSize - dataPos; + if (endPad > 0) + { + auto byteType = mModule->GetPrimitiveType(BfTypeCode_Int8); + auto arrType = GetSizedArrayType(MapType(byteType), endPad); + irFieldTypes.push_back(arrType); + dataPos += endPad; + } + } + } + + if (typeInstance->mIsUnion) + { + + } + else if ((typeInstance->IsEnum()) && (typeInstance->IsStruct())) + { + BF_FATAL("Shouldn't happen"); + + // Just an empty placeholder + auto byteType = GetPrimitiveType(BfTypeCode_UInt8); + auto rawDataType = GetSizedArrayType(byteType, 0); + irFieldTypes.push_back(rawDataType); + } + + if (!typeInstance->IsTypedPrimitive()) + StructSetBody(MapTypeInst(typeInstance), irFieldTypes, /*isPacked || !isCRepr*/true); + + if (typeInstance->IsNullable()) + { + BF_ASSERT(irFieldTypes.size() <= 3); + } +} + void BfIRBuilder::CreateTypeDefinition(BfType* type, bool forceDbgDefine) { auto populateModule = mModule->mContext->mUnreifiedModule; @@ -3124,183 +3304,12 @@ void BfIRBuilder::CreateTypeDefinition(BfType* type, bool forceDbgDefine) bool underlyingIsVector = false; typeInstance->GetUnderlyingArray(underlyingArrayType, underlyingArraySize, underlyingIsVector); if (underlyingArraySize > 0) - return; - - auto typeDef = typeInstance->mTypeDef; - -#ifdef BFIR_RENTRY_CHECK - ReEntryCheck reEntryCheck(&mDefReentrySet, type); -#endif - - bool isGlobalContainer = typeDef->IsGlobalsContainer(); - - auto diForwardDecl = DbgGetTypeInst(typeInstance); - llvm::SmallVector irFieldTypes; - if ((!typeInstance->IsTypedPrimitive()) && (typeInstance->mBaseType != NULL)) - { - irFieldTypes.push_back(MapTypeInst(typeInstance->mBaseType, BfIRPopulateType_Eventually_Full)); - } - - llvm::SmallVector diFieldTypes; - - bool isPacked = false; - bool isUnion = false; - bool isCRepr = false; - - if (typeInstance->IsBoxed()) { - auto boxedType = (BfBoxedType*)typeInstance; - BF_ASSERT(!boxedType->mFieldInstances.IsEmpty()); - - auto& fieldInst = boxedType->mFieldInstances.back(); - auto elementType = fieldInst.mResolvedType; - populateModule->PopulateType(elementType, BfPopulateType_Data); - - if (!elementType->IsValuelessType()) - { - irFieldTypes.push_back(MapType(elementType, elementType->IsValueType() ? BfIRPopulateType_Eventually_Full : BfIRPopulateType_Declaration)); - } + // Don't populate data } else { - isCRepr = typeInstance->mIsCRepr; - isPacked = typeInstance->mIsPacked; - isUnion = typeInstance->mIsUnion; - } - - BfSizedVector orderedFields; - - bool isPayloadEnum = (typeInstance->IsEnum()) && (!typeInstance->IsTypedPrimitive()); - for (auto& fieldInstanceRef : typeInstance->mFieldInstances) - { - auto fieldInstance = &fieldInstanceRef; - if (!fieldInstance->mFieldIncluded) - continue; - auto fieldDef = fieldInstance->GetFieldDef(); - - if ((fieldInstance->mResolvedType == NULL) || (typeInstance->IsBoxed())) - continue; - - if ((fieldDef != NULL) && (fieldDef->mIsStatic)) - continue; // Just create type first - we may contain a static reference to ourselves, creating an dependency loop - - auto resolvedFieldType = fieldInstance->GetResolvedType(); - - mModule->PopulateType(resolvedFieldType, BfPopulateType_Declaration); - BfIRType resolvedFieldIRType = MapType(resolvedFieldType); - BfIRMDNode resolvedFieldDIType; - - if ((fieldDef != NULL) && (resolvedFieldType->IsStruct())) - PopulateType(resolvedFieldType, BfIRPopulateType_Eventually_Full); - - if ((fieldDef == NULL) && (typeInstance->IsPayloadEnum())) - { - orderedFields.push_back(fieldInstance); - } - - if ((!typeInstance->IsBoxed()) && (fieldDef != NULL)) - { - bool useForUnion = false; - - BF_ASSERT(!fieldInstance->mIsEnumPayloadCase); - - if ((!fieldDef->mIsStatic) && (!resolvedFieldType->IsValuelessType())) - { - if (!isUnion) - { - BF_ASSERT(resolvedFieldIRType.mId != -1); - //irFieldTypes.push_back(resolvedFieldIRType); - - if (fieldInstance->mDataIdx != -1) - { - while (fieldInstance->mDataIdx >= (int)orderedFields.size()) - orderedFields.push_back(NULL); - orderedFields[fieldInstance->mDataIdx] = fieldInstance; - } - - } - } - } - } - - int dataPos = 0; - if (typeInstance->mBaseType != NULL) - dataPos = typeInstance->mBaseType->mInstSize; - - int unionSize = 0; - if (typeInstance->mIsUnion) - { - auto unionInnerType = typeInstance->GetUnionInnerType(); - irFieldTypes.push_back(MapType(unionInnerType, unionInnerType->IsValueType() ? BfIRPopulateType_Eventually_Full : BfIRPopulateType_Declaration)); - unionSize = unionInnerType->mSize; - dataPos += unionSize; - } - - for (int fieldIdx = 0; fieldIdx < (int)orderedFields.size(); fieldIdx++) - { - auto fieldInstance = orderedFields[fieldIdx]; - if (fieldInstance == NULL) - continue; - - auto resolvedFieldType = fieldInstance->GetResolvedType(); - - BfIRType resolvedFieldIRType = MapType(resolvedFieldType); - - //bool needsExplicitAlignment = !isCRepr || resolvedFieldType->NeedsExplicitAlignment(); - bool needsExplicitAlignment = true; - if (!needsExplicitAlignment) - { - int alignSize = resolvedFieldType->mAlign; - dataPos = (dataPos + (alignSize - 1)) & ~(alignSize - 1); - } - - if (fieldInstance->mDataOffset > dataPos) - { - int fillSize = fieldInstance->mDataOffset - dataPos; - auto byteType = mModule->GetPrimitiveType(BfTypeCode_Int8); - auto arrType = GetSizedArrayType(MapType(byteType), fillSize); - irFieldTypes.push_back(arrType); - dataPos = fieldInstance->mDataOffset; - } - dataPos += fieldInstance->mDataSize; - - BF_ASSERT((int)irFieldTypes.size() == fieldInstance->mDataIdx); - irFieldTypes.push_back(resolvedFieldIRType); - - if ((isCRepr) && (needsExplicitAlignment) && (fieldIdx == (int)orderedFields.size() - 1)) - { - // Add explicit padding at end to enforce the "aligned size" - int endPad = typeInstance->mInstSize - dataPos; - if (endPad > 0) - { - auto byteType = mModule->GetPrimitiveType(BfTypeCode_Int8); - auto arrType = GetSizedArrayType(MapType(byteType), endPad); - irFieldTypes.push_back(arrType); - dataPos += endPad; - } - } - } - - if (typeInstance->mIsUnion) - { - - } - else if ((typeInstance->IsEnum()) && (typeInstance->IsStruct())) - { - BF_FATAL("Shouldn't happen"); - - // Just an empty placeholder - auto byteType = GetPrimitiveType(BfTypeCode_UInt8); - auto rawDataType = GetSizedArrayType(byteType, 0); - irFieldTypes.push_back(rawDataType); - } - - if (!typeInstance->IsTypedPrimitive()) - StructSetBody(MapTypeInst(typeInstance), irFieldTypes, /*isPacked || !isCRepr*/true); - - if (typeInstance->IsNullable()) - { - BF_ASSERT(irFieldTypes.size() <= 3); + CreateTypeDefinition_Data(populateModule, typeInstance, forceDbgDefine); } for (auto& fieldInstanceRef : typeInstance->mFieldInstances) @@ -4682,11 +4691,6 @@ BfIRFunction BfIRBuilder::CreateFunction(BfIRFunctionType funcType, BfIRLinkageT NEW_CMD_INSERTED_IRVALUE; mFunctionMap[name] = retVal; - if ((mModule->mIsConstModule) && (name.Contains("Dbg_"))) - { - NOP; - } - //BfLogSys(mModule->mSystem, "BfIRBuilder::CreateFunction: %d %s Module:%p\n", retVal.mId, name.c_str(), mModule); return retVal; diff --git a/IDEHelper/Compiler/BfIRBuilder.h b/IDEHelper/Compiler/BfIRBuilder.h index 83bdf55c..c854f663 100644 --- a/IDEHelper/Compiler/BfIRBuilder.h +++ b/IDEHelper/Compiler/BfIRBuilder.h @@ -1025,6 +1025,7 @@ public: void CreateDbgTypeDefinition(BfType* type); bool WantsDbgDefinition(BfType * type); void CreateTypeDeclaration(BfType* type, bool forceDbgDefine); + void CreateTypeDefinition_Data(BfModule* populateModule, BfTypeInstance* typeInstance, bool forceDbgDefine); void CreateTypeDefinition(BfType* type, bool forceDbgDefine); void ReplaceDITemporaryTypes(); void PushDbgLoc(BfTypeInstance* typeInst); diff --git a/IDEHelper/Compiler/BfIRCodeGen.cpp b/IDEHelper/Compiler/BfIRCodeGen.cpp index 6f293c8e..79ca27c1 100644 --- a/IDEHelper/Compiler/BfIRCodeGen.cpp +++ b/IDEHelper/Compiler/BfIRCodeGen.cpp @@ -923,8 +923,13 @@ void BfIRCodeGen::Read(llvm::Value*& llvmValue, BfIRCodeGenEntry** codeGenEntry) { llvmValue = llvm::ConstantStruct::get(structType, values); } + else if (auto vecType = llvm::dyn_cast(type)) + { + llvmValue = llvm::ConstantVector::get(values); + } else { + llvmValue = NULL; Fail("Bad type"); }