Skip to content

Commit

Permalink
Merge pull request #78 from Spuckwaffel/development
Browse files Browse the repository at this point in the history
1.11 Stable Release
  • Loading branch information
Spuckwaffel authored Jul 20, 2024
2 parents 0f14dd7 + 1c135b9 commit db2b29f
Show file tree
Hide file tree
Showing 13 changed files with 415 additions and 75 deletions.
61 changes: 34 additions & 27 deletions UEDumper/Engine/Core/Core.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -626,6 +626,24 @@ void EngineCore::cookMemberArray(EngineStructs::Struct & eStruct)
eStruct.cookedMembers.clear();


auto checkRealMemberSize = [&](EngineStructs::Member* currentMember)
{
//set the real size
if (!currentMember->type.isPointer())
{
if (const auto classObject = getInfoOfObject(currentMember->type.name))
{
if (classObject->type == ObjectInfo::OI_Struct || classObject->type == ObjectInfo::OI_Class)
{
const auto cclass = static_cast<EngineStructs::Struct*>(classObject->target);
if(!cclass->noFixedSize)
currentMember->size = cclass->maxSize * (currentMember->arrayDim <= 0 ? 1 : currentMember->arrayDim);
}
}
}
};


auto genUnknownMember = [&](int from, int to, int special)
{
EngineStructs::Member unknown;
Expand Down Expand Up @@ -808,18 +826,7 @@ void EngineCore::cookMemberArray(EngineStructs::Struct & eStruct)
//0x7 [0x2]


//set the real size
if(!currentMember.type.isPointer())
{
if (const auto classObject = getInfoOfObject(currentMember.type.name))
{
if (classObject->type == ObjectInfo::OI_Struct || classObject->type == ObjectInfo::OI_Class)
{
const auto cclass = static_cast<EngineStructs::Struct*>(classObject->target);
currentMember.size = cclass->maxSize * (currentMember.arrayDim <= 0 ? 1 : currentMember.arrayDim);
}
}
}
checkRealMemberSize(&currentMember);


if (nextMember.offset - (currentMember.offset + currentMember.size) > 0)
Expand All @@ -835,7 +842,8 @@ void EngineCore::cookMemberArray(EngineStructs::Struct & eStruct)
}
//add the last member
eStruct.cookedMembers.push_back(std::pair(true, eStruct.definedMembers.size() - 1));
const auto& last = eStruct.getMemberForIndex(eStruct.cookedMembers.size() - 1);
auto last = eStruct.getMemberForIndex(eStruct.cookedMembers.size() - 1);
checkRealMemberSize(last);
if (last->offset + last->size < eStruct.maxSize)
genUnknownMember(last->offset + last->size, eStruct.maxSize, 7);
}
Expand Down Expand Up @@ -1010,7 +1018,7 @@ void EngineCore::generatePackages(int64_t& finishedPackages, int64_t& totalPacka
for (auto& enu : package.enums) {
if (usedNames.contains(enu.cppName)) {
windows::LogWindow::Log(windows::LogWindow::logLevels::LOGLEVEL_WARNING, "CORE", "Enum redefinitio in package %s! %s has already been defined in package %s", package.packageName.c_str(), enu.cppName.c_str(), usedNames[enu.cppName].c_str());
printf("Enum redefinition in package %s! %s has already been defined in package %s\n", enu.cppName.c_str(), usedNames[enu.cppName].c_str());
printf("Enum redefinition in package %s! %s has already been defined in package %s\n", package.packageName.c_str(), enu.cppName.c_str(), usedNames[enu.cppName].c_str());
}
usedNames.insert({ enu.cppName, package.packageName });
}
Expand Down Expand Up @@ -1269,7 +1277,7 @@ void EngineCore::finishPackages()
for (auto& name : struc->superNames)
{
const auto info = getInfoOfObject(name);
if (!info || !info->valid)
if (!info || !info->valid || (info->type != ObjectInfo::OI_Class && info->type != ObjectInfo::OI_Struct))
continue;
//get the super struct
auto superStruc = static_cast<EngineStructs::Struct*>(info->target);
Expand Down Expand Up @@ -1328,6 +1336,8 @@ void EngineCore::finishPackages()

for (auto& subtype : var.type.subTypes)
{
if (!subtype.clickable)
continue;
const auto subInfo = getInfoOfObject(subtype.name);
if (!subInfo || !subInfo->valid)
continue;
Expand All @@ -1336,18 +1346,16 @@ void EngineCore::finishPackages()

if (subtype.propertyType != PropertyType::ObjectProperty && subtype.propertyType != PropertyType::ClassProperty)
{
//casting is fine even if its a enum as owningpackage is the first package
const auto targetStruc = static_cast<EngineStructs::Struct*>(subInfo->target);
if (targetStruc->owningPackage->index != package.index)
package.dependencyPackages.insert(targetStruc->owningPackage);
const auto targetPack = subInfo->type == ObjectInfo::OI_Enum ? static_cast<EngineStructs::Enum*>(subInfo->target)->owningPackage : static_cast<EngineStructs::Struct*>(subInfo->target)->owningPackage;
if (targetPack->index != package.index)
package.dependencyPackages.insert(targetPack);
}
}

const auto targetPack = info->type == ObjectInfo::OI_Enum ? static_cast<EngineStructs::Enum*>(info->target)->owningPackage : static_cast<EngineStructs::Struct*>(info->target)->owningPackage;
if (targetPack->index != package.index)
package.dependencyPackages.insert(targetPack);

//casting is fine even if its a enum as owningpackage is the first package
const auto targetStruc = static_cast<EngineStructs::Struct*>(info->target);
if (targetStruc->owningPackage->index != package.index)
package.dependencyPackages.insert(targetStruc->owningPackage);
}
}

Expand All @@ -1363,10 +1371,9 @@ void EngineCore::finishPackages()
{
type.info = info;

//casting is fine even if its a enum as owningpackage is the first package
const auto targetStruc = static_cast<EngineStructs::Struct*>(info->target);
if (targetStruc->owningPackage->index != package.index)
package.dependencyPackages.insert(targetStruc->owningPackage);
const auto targetPack = info->type == ObjectInfo::OI_Enum ? static_cast<EngineStructs::Enum*>(info->target)->owningPackage : static_cast<EngineStructs::Struct*>(info->target)->owningPackage;
if (targetPack->index != package.index)
package.dependencyPackages.insert(targetPack);
}
}
};
Expand Down
1 change: 1 addition & 0 deletions UEDumper/Engine/Core/EngineStructs.h
Original file line number Diff line number Diff line change
Expand Up @@ -340,6 +340,7 @@ namespace EngineStructs
std::vector<Struct*> superOfOthers{}; //all the structs that use this class as a super
bool inherited = false; //if the struct is inherited
int maxSize = 0; //the maximum size this struct is "allowed" to have, as size is not accurate due to padding and trailing
bool noFixedSize = false; // if this boolean is true, the current struct or class has no specific fixed size, meaning it can change (template classes)
int minAlignment = 0; //minimal alignment defined by ue
int size = 0; //propertiesSize, possibly wrong, use maxSize
int unknownCount = 0; //keep track of all missed vars, only used for the package viewer to edit unknowndata
Expand Down
2 changes: 1 addition & 1 deletion UEDumper/Engine/Core/ObjectsManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,7 @@ class ObjectsManager
#ifdef _DEBUG
if (gamePtr < 0x100) {
// if your pointer is less than 0x100, it's likely invalid and there's a bug. Check your structs
DebugBreak();
//DebugBreak();
}
#endif
if(!gUObjectManager.linkedUObjectPtrs.contains(gamePtr))
Expand Down
114 changes: 114 additions & 0 deletions UEDumper/Engine/Generation/BasicType.h
Original file line number Diff line number Diff line change
Expand Up @@ -292,6 +292,120 @@ class TEnumAsByte

definedStructs.push_back(dStruct);

dStruct.name = "FWeakObjectPtr";
dStruct.definition =
R"(
class FWeakObjectPtr
{
public:
int32_t ObjectIndex;
int32_t ObjectSerialNumber;
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TWeakObjectPtr";
dStruct.definition =
R"(
template<typename UEType>
class TWeakObjectPtr : public FWeakObjectPtr
{
public:
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TPersistentObjectPtr";
dStruct.definition =
R"(
template<typename TObjectID>
class TPersistentObjectPtr
{
public:
FWeakObjectPtr WeakPtr;
int32_t TagAtLastTest;
TObjectID ObjectID;
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "FUniqueObjectGuid";
dStruct.definition =
R"(
class FUniqueObjectGuid final
{
public:
uint32_t A;
uint32_t B;
uint32_t C;
uint32_t D;
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TLazyObjectPtr";
dStruct.definition =
R"(
template<typename UEType>
class TLazyObjectPtr : public TPersistentObjectPtr<FUniqueObjectGuid>
{
public:
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "FSoftObjectPath_";
dStruct.definition =
R"(
struct FSoftObjectPath_
{
public:
FName AssetPathName;
FString SubPathString;
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "FSoftObjectPtr";
dStruct.definition =
R"(
class FSoftObjectPtr : public TPersistentObjectPtr<FSoftObjectPath_>
{
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TSoftObjectPtr";
dStruct.definition =
R"(
template<typename UEType>
class TSoftObjectPtr : public FSoftObjectPtr
{
public:
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TSoftClassPtr";
dStruct.definition =
R"(
template<typename UEType>
class TSoftClassPtr : public FSoftObjectPtr
{
public:
};
)";

definedStructs.push_back(dStruct);

dStruct.name = "TPair";
dStruct.definition =
R"(
Expand Down
4 changes: 2 additions & 2 deletions UEDumper/Engine/Generation/MDK.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ void MDKGeneration::generatePackage(std::ofstream& stream, const EngineStructs::

}

const static std::unordered_set<std::string> reservedNames{ "float", "int", "bool", "double", "long", "char", "TRUE", "FALSE" };
const static std::unordered_set<std::string> reservedNames{ "float", "int", "bool", "double", "long", "char", "TRUE", "FALSE", "try" };

if (std::isdigit(result[0])) result = "_" + result;
if (reservedNames.contains(result)) result += "0";
Expand Down Expand Up @@ -240,7 +240,7 @@ void MDKGeneration::generatePackage(std::ofstream& stream, const EngineStructs::
{
stream << "/// Enum " << enu.fullName << std::endl;
char buf[100] = { 0 };
sprintf_s(buf, "Size: 0x%02d", enu.members.size());
sprintf_s(buf, "Size: 0x%02lld", enu.members.size());
stream << "/// " << buf << std::endl;
stream << "enum class " << generateValidVarName(enu.cppName) << " : " << enu.type << std::endl;
stream << "{" << std::endl;
Expand Down
10 changes: 8 additions & 2 deletions UEDumper/Engine/Generation/SDK.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,7 @@ void SDKGeneration::generatePackage(

}

const static std::unordered_set<std::string> reservedNames{ "float", "int", "bool", "double", "long", "char", "TRUE", "FALSE" };
const static std::unordered_set<std::string> reservedNames{ "float", "int", "bool", "double", "long", "char", "TRUE", "FALSE", "try" };

if (std::isdigit(result[0])) result = "_" + result;
if (reservedNames.contains(result)) result += "0";
Expand Down Expand Up @@ -260,7 +260,7 @@ void SDKGeneration::generatePackage(
if(struc->size == 1 && struc->maxSize == 0)
actualSize = 1;

sprintf_s(buf, "static_assert(sizeof(%s) == 0x%04X); // %d bytes (0x%06X - 0x%06X)", generateValidVarName(struc->cppName).c_str(), actualSize, struc->maxSize, struc->getInheritedSize(), actualSize);
sprintf_s(buf, "static_assert(sizeof(%s) == 0x%04llX); // %d bytes (0x%06X - 0x%06llX)", generateValidVarName(struc->cppName).c_str(), actualSize, struc->maxSize, struc->getInheritedSize(), actualSize);
stream << buf << std::endl;
}
};
Expand Down Expand Up @@ -503,8 +503,14 @@ void SDKGeneration::generatePackage(

//first we generate enums

std::unordered_set<std::string> definedEnums;

for (const auto& enu : package.enums)
{
if (definedEnums.contains(enu.cppName))
continue;
definedEnums.insert(enu.cppName);

stream << "/// Enum " << enu.fullName << std::endl;
char buf[100] = { 0 };
sprintf_s(buf, "Size: 0x%02d (%d bytes)", enu.size, enu.size);
Expand Down
4 changes: 2 additions & 2 deletions UEDumper/Engine/Generation/packageSorter.h
Original file line number Diff line number Diff line change
Expand Up @@ -345,10 +345,10 @@ inline std::vector<MergedPackage*> sortPackages(int& progressDone, int& totalPro
windows::LogWindow::Log(windows::LogWindow::logLevels::LOGLEVEL_INFO, "MDK GEN", "Reordering packages");
std::vector<MergedPackage*> orderedPackages;

const float one_thousand = 1000;
constexpr auto one_thousand = 1000;
// Max number of iterations before we give up
// Using some very large number - it's to prevent infinite loops, not break too early before convergence
const auto maxIterations = 20 * one_thousand;
constexpr auto maxIterations = 20 * one_thousand;
progressDone = 0;
totalProgress = maxIterations; // Note: we may converge before this and end up with a Microsoft style progress bar that magically jumps to 100% while (didReordering && progressDone < totalProgress);

Expand Down
27 changes: 22 additions & 5 deletions UEDumper/Engine/UEClasses/UnrealClasses.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -191,16 +191,18 @@ std::string UObject::getSecondPackageName() const
bool UObject::IsA(const UClass* staticClass) const
{
if (!ClassPrivate) return false;
UClass* oldSup = nullptr;
for (auto super = getClass(); super; super = super->getSuper<UClass>())
{
if (!super)
if (!super || oldSup == super)
return false;
std::string fullname = super->getFullName();
if (super == staticClass)
{
//printf("%s\n", fullname.c_str());
return true;
}
oldSup = super;
}
return false;

Expand Down Expand Up @@ -443,6 +445,16 @@ fieldType UProperty::getType()
if (const auto cast = castTo<UObjectPropertyBase>(); cast->getPropertyClass())
return{ true, PropertyType::WeakObjectProperty, UObjectPropertyBase::weakTypeName(), cast->getSubTypes() };
};
if (IsA<USoftObjectProperty>())
{
if (const auto cast = castTo<UObjectPropertyBase>(); cast->getPropertyClass())
return{ true, PropertyType::SoftObjectProperty, UObjectPropertyBase::softTypeName(), cast->getSubTypes() };
};
if (IsA<ULazyObjectProperty>())
{
if (const auto cast = castTo<UObjectPropertyBase>(); cast->getPropertyClass())
return{ true, PropertyType::LazyObjectProperty, UObjectPropertyBase::lazyTypeName(), cast->getSubTypes() };
};
if (IsA<UObjectPropertyBase>())
{
if (const auto cast = castTo<UObjectPropertyBase>(); cast->getPropertyClass())
Expand Down Expand Up @@ -565,6 +577,11 @@ UClass* UWeakObjectProperty::staticClass()
return ObjectsManager::findObject<UClass>("/Script/CoreUObject.WeakObjectProperty");
}

UClass* USoftObjectProperty::staticClass()
{
return ObjectsManager::findObject<UClass>("/Script/CoreUObject.SoftObjectProperty");
}

UProperty* UInterfaceProperty::getInterfaceClass() const
{
UREADORNULL(UProperty, InterfaceClass)
Expand All @@ -575,10 +592,10 @@ UClass* UInterfaceProperty::staticClass()
return ObjectsManager::findObject<UClass>("/Script/CoreUObject.InterfaceProperty");
}

std::string UWeakObjectProperty::typeName()
{
return "struct TWeakObjectPtr<struct " + castTo<UStructProperty>()->typeName() + ">";
}
//std::string UWeakObjectProperty::typeName()
//{
// return "struct TWeakObjectPtr<struct " + castTo<UStructProperty>()->typeName() + ">";
//}

UClass* UClassProperty::getMetaClass() const
{
Expand Down
Loading

0 comments on commit db2b29f

Please sign in to comment.