Return array type info with FindSendPropInfo (#1548)

This commit is contained in:
Asher Baker 2021-08-01 19:44:18 +01:00 committed by GitHub
parent c6917296d3
commit 296deb95e6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 62 additions and 13 deletions

View File

@ -320,15 +320,20 @@ bool UTIL_FindInSendTable(SendTable *pTable,
sm_sendprop_info_t *info, sm_sendprop_info_t *info,
unsigned int offset) unsigned int offset)
{ {
const char *pname;
int props = pTable->GetNumProps(); int props = pTable->GetNumProps();
SendProp *prop; for (int i = 0; i < props; i++)
for (int i=0; i<props; i++)
{ {
prop = pTable->GetProp(i); SendProp *prop = pTable->GetProp(i);
pname = prop->GetName();
// Skip InsideArray props (SendPropArray / SendPropArray2),
// we'll find them later by their containing array.
if (prop->IsInsideArray()) {
continue;
}
const char *pname = prop->GetName();
SendTable *pInnerTable = prop->GetDataTable(); SendTable *pInnerTable = prop->GetDataTable();
if (pname && strcmp(name, pname) == 0) if (pname && strcmp(name, pname) == 0)
{ {
// get true offset of CUtlVector // get true offset of CUtlVector

View File

@ -825,7 +825,7 @@ static cell_t FindSendPropInfo(IPluginContext *pContext, const cell_t *params)
{ {
char *cls, *prop; char *cls, *prop;
sm_sendprop_info_t info; sm_sendprop_info_t info;
cell_t *pType, *pBits, *pLocal; cell_t *pType, *pBits, *pLocal, *pArraySize;
pContext->LocalToString(params[1], &cls); pContext->LocalToString(params[1], &cls);
pContext->LocalToString(params[2], &prop); pContext->LocalToString(params[2], &prop);
@ -839,7 +839,45 @@ static cell_t FindSendPropInfo(IPluginContext *pContext, const cell_t *params)
pContext->LocalToPhysAddr(params[4], &pBits); pContext->LocalToPhysAddr(params[4], &pBits);
pContext->LocalToPhysAddr(params[5], &pLocal); pContext->LocalToPhysAddr(params[5], &pLocal);
switch (info.prop->GetType()) if (params[0] >= 6) {
pContext->LocalToPhysAddr(params[6], &pArraySize);
*pArraySize = 0;
}
SendProp *pProp = info.prop;
unsigned int actual_offset = info.actual_offset;
// SendPropArray / SendPropArray2
if (pProp->GetType() == DPT_Array && pProp->GetArrayProp())
{
if (pArraySize) {
// This'll only work for SendPropArray
*pArraySize = pProp->GetNumElements();
}
// Use the type / bits / local offset of the real data prop
pProp = pProp->GetArrayProp();
// This is sane as the DPT_Array prop's local offset is always 0
actual_offset += pProp->GetOffset();
}
// Get the local offset now before we might dive into another table
*pLocal = pProp->GetOffset();
// SendPropArray3
SendTable *pTable = pProp->GetDataTable();
if (pProp->GetType() == DPT_DataTable && pTable && pTable->GetNumProps() > 0)
{
if (pArraySize) {
*pArraySize = pTable->GetNumProps();
}
// Use the type / bits of the first data prop
pProp = pTable->GetProp(0);
}
switch (pProp->GetType())
{ {
case DPT_Int: case DPT_Int:
{ {
@ -868,10 +906,9 @@ static cell_t FindSendPropInfo(IPluginContext *pContext, const cell_t *params)
} }
} }
*pBits = info.prop->m_nBits; *pBits = pProp->m_nBits;
*pLocal = info.prop->GetOffset();
return info.actual_offset; return actual_offset;
} }
static void GuessDataPropTypes(typedescription_t *td, cell_t * pSize, cell_t * pType) static void GuessDataPropTypes(typedescription_t *td, cell_t * pSize, cell_t * pType)
@ -1297,6 +1334,11 @@ static cell_t GetEntPropArraySize(IPluginContext *pContext, const cell_t *params
((class_name) ? class_name : "")); ((class_name) ? class_name : ""));
} }
if (info.prop->GetType() == DPT_Array)
{
return info.prop->GetNumElements();
}
if (info.prop->GetType() != DPT_DataTable) if (info.prop->GetType() != DPT_DataTable)
{ {
return 0; return 0;

View File

@ -428,6 +428,7 @@ native int FindSendPropOffs(const char[] cls, const char[] prop);
* for strings. * for strings.
* @param local_offset Optional parameter to store the local offset, as * @param local_offset Optional parameter to store the local offset, as
* FindSendPropOffs() would return. * FindSendPropOffs() would return.
* @param array_size Optional parameter to store array size, 0 if not an array.
* @return On success, returns an absolutely computed offset. * @return On success, returns an absolutely computed offset.
* If no offset is available, 0 is returned. * If no offset is available, 0 is returned.
* If the property is not found, -1 is returned. * If the property is not found, -1 is returned.
@ -436,7 +437,8 @@ native int FindSendPropInfo(const char[] cls,
const char[] prop, const char[] prop,
PropFieldType &type=view_as<PropFieldType>(0), PropFieldType &type=view_as<PropFieldType>(0),
int &num_bits=0, int &num_bits=0,
int &local_offset=0); int &local_offset=0,
int &array_size=0);
/** /**
* Given an entity, finds a datamap property offset. * Given an entity, finds a datamap property offset.
@ -700,7 +702,7 @@ native int SetEntPropString(int entity, PropType type, const char[] prop, const
* @param entity Entity/edict index. * @param entity Entity/edict index.
* @param type Property type. * @param type Property type.
* @param prop Property name. * @param prop Property name.
* @return Size of array (in elements) or 1 if property is not an array. * @return Size of array (in elements) or 0 if property is not an array.
* @error Invalid entity or property not found. * @error Invalid entity or property not found.
*/ */
native int GetEntPropArraySize(int entity, PropType type, const char[] prop); native int GetEntPropArraySize(int entity, PropType type, const char[] prop);