Add Call_PushNullVector and Call_PushNullString
Be able to push NULL_[VECTOR|STRING] to a forward or direct function call. The callee can check the parameter using the IsNullVector/IsNullString natives.
This commit is contained in:
@@ -273,7 +273,26 @@ int CForward::Execute(cell_t *result, IForwardFilter *filter)
|
||||
*/
|
||||
if (type == Param_String)
|
||||
{
|
||||
err = func->PushStringEx((char *)param->byref.orig_addr, param->byref.cells, param->byref.sz_flags, param->byref.flags);
|
||||
// If NULL_STRING was pushed, push the reference to the pubvar of the callee instead.
|
||||
if (param->isnull)
|
||||
{
|
||||
IPluginRuntime *runtime = func->GetParentRuntime();
|
||||
uint32_t null_string_idx;
|
||||
err = runtime->FindPubvarByName("NULL_STRING", &null_string_idx);
|
||||
|
||||
if (!err)
|
||||
{
|
||||
cell_t null_string;
|
||||
err = runtime->GetPubvarAddrs(null_string_idx, &null_string, nullptr);
|
||||
|
||||
if (!err)
|
||||
err = func->PushCell(null_string);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
err = func->PushStringEx((char *)param->byref.orig_addr, param->byref.cells, param->byref.sz_flags, param->byref.flags);
|
||||
}
|
||||
}
|
||||
else if (type == Param_Float || type == Param_Cell)
|
||||
{
|
||||
@@ -281,7 +300,26 @@ int CForward::Execute(cell_t *result, IForwardFilter *filter)
|
||||
}
|
||||
else
|
||||
{
|
||||
err = func->PushArray(param->byref.orig_addr, param->byref.cells, param->byref.flags);
|
||||
// If NULL_VECTOR was pushed, push the reference to the pubvar of the callee instead.
|
||||
if (param->isnull && type == Param_Array)
|
||||
{
|
||||
IPluginRuntime *runtime = func->GetParentRuntime();
|
||||
uint32_t null_vector_idx;
|
||||
err = runtime->FindPubvarByName("NULL_VECTOR", &null_vector_idx);
|
||||
|
||||
if (!err)
|
||||
{
|
||||
cell_t null_vector;
|
||||
err = runtime->GetPubvarAddrs(null_vector_idx, &null_vector, nullptr);
|
||||
|
||||
if (!err)
|
||||
err = func->PushCell(null_vector);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
err = func->PushArray(param->byref.orig_addr, param->byref.cells, param->byref.flags);
|
||||
}
|
||||
assert(type == Param_Array || type == Param_FloatByRef || type == Param_CellByRef);
|
||||
}
|
||||
}
|
||||
@@ -400,6 +438,7 @@ int CForward::PushCell(cell_t cell)
|
||||
m_params[m_curparam].pushedas = Param_Cell;
|
||||
}
|
||||
|
||||
m_params[m_curparam].isnull = false;
|
||||
m_params[m_curparam++].val = cell;
|
||||
|
||||
return SP_ERROR_NONE;
|
||||
@@ -423,6 +462,7 @@ int CForward::PushFloat(float number)
|
||||
m_params[m_curparam].pushedas = Param_Float;
|
||||
}
|
||||
|
||||
m_params[m_curparam].isnull = false;
|
||||
m_params[m_curparam++].val = *(cell_t *)&number;
|
||||
|
||||
return SP_ERROR_NONE;
|
||||
@@ -481,6 +521,7 @@ void CForward::_Int_PushArray(cell_t *inarray, unsigned int cells, int flags)
|
||||
m_params[m_curparam].byref.cells = cells;
|
||||
m_params[m_curparam].byref.flags = flags;
|
||||
m_params[m_curparam].byref.orig_addr = inarray;
|
||||
m_params[m_curparam].isnull = false;
|
||||
}
|
||||
|
||||
int CForward::PushArray(cell_t *inarray, unsigned int cells, int flags)
|
||||
@@ -520,6 +561,7 @@ void CForward::_Int_PushString(cell_t *inarray, unsigned int cells, int sz_flags
|
||||
m_params[m_curparam].byref.flags = cp_flags;
|
||||
m_params[m_curparam].byref.orig_addr = inarray;
|
||||
m_params[m_curparam].byref.sz_flags = sz_flags;
|
||||
m_params[m_curparam].isnull = false;
|
||||
}
|
||||
|
||||
int CForward::PushString(const char *string)
|
||||
@@ -570,6 +612,52 @@ int CForward::PushStringEx(char *buffer, size_t length, int sz_flags, int cp_fla
|
||||
return SP_ERROR_NONE;
|
||||
}
|
||||
|
||||
int CForward::PushNullString()
|
||||
{
|
||||
if (m_curparam < m_numparams)
|
||||
{
|
||||
if (m_types[m_curparam] == Param_Any)
|
||||
{
|
||||
m_params[m_curparam].pushedas = Param_String;
|
||||
} else if (m_types[m_curparam] != Param_String) {
|
||||
return SetError(SP_ERROR_PARAM);
|
||||
}
|
||||
} else {
|
||||
if (!m_varargs || m_numparams > SP_MAX_EXEC_PARAMS)
|
||||
{
|
||||
return SetError(SP_ERROR_PARAMS_MAX);
|
||||
}
|
||||
m_params[m_curparam].pushedas = Param_String;
|
||||
}
|
||||
|
||||
m_params[m_curparam++].isnull = true;
|
||||
|
||||
return SP_ERROR_NONE;
|
||||
}
|
||||
|
||||
int CForward::PushNullVector()
|
||||
{
|
||||
if (m_curparam < m_numparams)
|
||||
{
|
||||
if (m_types[m_curparam] == Param_Any)
|
||||
{
|
||||
m_params[m_curparam].pushedas = Param_Array;
|
||||
} else if (m_types[m_curparam] != Param_Array) {
|
||||
return SetError(SP_ERROR_PARAM);
|
||||
}
|
||||
} else {
|
||||
if (!m_varargs || m_numparams > SP_MAX_EXEC_PARAMS)
|
||||
{
|
||||
return SetError(SP_ERROR_PARAMS_MAX);
|
||||
}
|
||||
m_params[m_curparam].pushedas = Param_Array;
|
||||
}
|
||||
|
||||
m_params[m_curparam++].isnull = true;
|
||||
|
||||
return SP_ERROR_NONE;
|
||||
}
|
||||
|
||||
void CForward::Cancel()
|
||||
{
|
||||
if (!m_curparam)
|
||||
|
||||
Reference in New Issue
Block a user