📄 insmoddp.c
字号:
else
{
SetpDOBegin(&ovs[ovi],1);
SetpDOEnd(&ovs[ovi],0);
SetpType(&ovs[ovi],MULTIFIELD);
SetpValue(&ovs[ovi],ProceduralPrimitiveData(theEnv)->NoParamValue);
}
ovs[ovi].supplementalInfo = slotName;
ovExprs = ovExprs->nextArg->nextArg;
ovs[ovi].next = (ovExprs != NULL) ? &ovs[ovi+1] : NULL;
ovi++;
}
return(ovs);
EvaluateOverridesError:
rm(theEnv,(void *) ovs,(sizeof(DATA_OBJECT) * (*ovCnt)));
*error = TRUE;
return(NULL);
}
/**********************************************************
NAME : DeleteSlotOverrideEvaluations
DESCRIPTION : Deallocates slot override evaluation array
INPUTS : 1) The data object array
2) The number of elements
RETURNS : Nothing useful
SIDE EFFECTS : Deallocates slot override data object
array for modify- and duplicate- instance
NOTES : None
**********************************************************/
static void DeleteSlotOverrideEvaluations(
void *theEnv,
DATA_OBJECT *ovEvals,
int ovCnt)
{
if (ovEvals != NULL)
rm(theEnv,(void *) ovEvals,(sizeof(DATA_OBJECT) * ovCnt));
}
/**********************************************************
NAME : ModifyMsgHandlerSupport
DESCRIPTION : Support routine for DirectModifyMsgHandler
and MsgModifyMsgHandler
Performs a series of slot updates
directly or with messages
INPUTS : 1) A data object buffer to hold the result
2) A flag indicating whether to use
put- messages or direct placement
RETURNS : Nothing useful
SIDE EFFECTS : Slots updated (messages sent)
NOTES : None
**********************************************************/
static void ModifyMsgHandlerSupport(
void *theEnv,
DATA_OBJECT *result,
int msgpass)
{
DATA_OBJECT *slotOverrides,*newval,temp,junk;
EXPRESSION msgExp;
INSTANCE_TYPE *ins;
INSTANCE_SLOT *insSlot;
result->type = SYMBOL;
result->value = EnvFalseSymbol(theEnv);
if (InstanceData(theEnv)->ObjectModDupMsgValid == FALSE)
{
PrintErrorID(theEnv,"INSMODDP",1,FALSE);
EnvPrintRouter(theEnv,WERROR,"Direct/message-modify message valid only in modify-instance.\n");
SetEvaluationError(theEnv,TRUE);
return;
}
InstanceData(theEnv)->ObjectModDupMsgValid = FALSE;
ins = GetActiveInstance(theEnv);
if (ins->garbage)
{
StaleInstanceAddress(theEnv,"modify-instance",0);
SetEvaluationError(theEnv,TRUE);
return;
}
/* =======================================
Retrieve the slot override data objects
passed from ModifyInstance - the slot
name is stored in the supplementalInfo
field - and the next fields are links
======================================= */
slotOverrides = (DATA_OBJECT *) GetNthMessageArgument(theEnv,1)->value;
while (slotOverrides != NULL)
{
/* ===========================================================
No evaluation or error checking needs to be done
since this has already been done by EvaluateSlotOverrides()
=========================================================== */
insSlot = FindInstanceSlot(theEnv,ins,(SYMBOL_HN *) slotOverrides->supplementalInfo);
if (insSlot == NULL)
{
SlotExistError(theEnv,ValueToString(slotOverrides->supplementalInfo),"modify-instance");
SetEvaluationError(theEnv,TRUE);
return;
}
if (msgpass)
{
msgExp.type = slotOverrides->type;
if (msgExp.type != MULTIFIELD)
msgExp.value = slotOverrides->value;
else
msgExp.value = (void *) slotOverrides;
msgExp.argList = NULL;
msgExp.nextArg = NULL;
DirectMessage(theEnv,insSlot->desc->overrideMessage,ins,&temp,&msgExp);
if (EvaluationData(theEnv)->EvaluationError ||
((temp.type == SYMBOL) && (temp.value == EnvFalseSymbol(theEnv))))
return;
}
else
{
if (insSlot->desc->multiple && (slotOverrides->type != MULTIFIELD))
{
temp.type = MULTIFIELD;
temp.value = EnvCreateMultifield(theEnv,1L);
SetDOBegin(temp,1);
SetDOEnd(temp,1);
SetMFType(temp.value,1,(short) slotOverrides->type);
SetMFValue(temp.value,1,slotOverrides->value);
newval = &temp;
}
else
newval = slotOverrides;
if (PutSlotValue(theEnv,ins,insSlot,newval,&junk,"modify-instance") == FALSE)
return;
}
slotOverrides = slotOverrides->next;
}
result->value = EnvTrueSymbol(theEnv);
}
/*************************************************************
NAME : DuplicateMsgHandlerSupport
DESCRIPTION : Support routine for DirectDuplicateMsgHandler
and MsgDuplicateMsgHandler
Performs a series of slot updates
directly or with messages
INPUTS : 1) A data object buffer to hold the result
2) A flag indicating whether to use
put- messages or direct placement
RETURNS : Nothing useful
SIDE EFFECTS : Slots updated (messages sent)
NOTES : None
*************************************************************/
static void DuplicateMsgHandlerSupport(
void *theEnv,
DATA_OBJECT *result,
int msgpass)
{
INSTANCE_TYPE *srcins,*dstins;
SYMBOL_HN *newName;
DATA_OBJECT *slotOverrides;
EXPRESSION *valArg,msgExp;
unsigned i;
int oldMkInsMsgPass;
INSTANCE_SLOT *dstInsSlot;
DATA_OBJECT temp,junk,*newval;
result->type = SYMBOL;
result->value = EnvFalseSymbol(theEnv);
if (InstanceData(theEnv)->ObjectModDupMsgValid == FALSE)
{
PrintErrorID(theEnv,"INSMODDP",2,FALSE);
EnvPrintRouter(theEnv,WERROR,"Direct/message-duplicate message valid only in duplicate-instance.\n");
SetEvaluationError(theEnv,TRUE);
return;
}
InstanceData(theEnv)->ObjectModDupMsgValid = FALSE;
/* ==================================
Grab the slot override expressions
and determine the source instance
and the name of the new instance
================================== */
srcins = GetActiveInstance(theEnv);
newName = (SYMBOL_HN *) GetNthMessageArgument(theEnv,1)->value;
slotOverrides = (DATA_OBJECT *) GetNthMessageArgument(theEnv,2)->value;
if (srcins->garbage)
{
StaleInstanceAddress(theEnv,"duplicate-instance",0);
SetEvaluationError(theEnv,TRUE);
return;
}
if (newName == srcins->name)
{
PrintErrorID(theEnv,"INSMODDP",3,FALSE);
EnvPrintRouter(theEnv,WERROR,"Instance copy must have a different name in duplicate-instance.\n");
SetEvaluationError(theEnv,TRUE);
return;
}
/* ==========================================
Create an uninitialized new instance of
the new name (delete old version - if any)
========================================== */
oldMkInsMsgPass = InstanceData(theEnv)->MkInsMsgPass;
InstanceData(theEnv)->MkInsMsgPass = msgpass;
dstins = BuildInstance(theEnv,newName,srcins->cls,TRUE);
InstanceData(theEnv)->MkInsMsgPass = oldMkInsMsgPass;
if (dstins == NULL)
return;
dstins->busy++;
/* ================================
Place slot overrides directly or
with put- messages
================================ */
while (slotOverrides != NULL)
{
/* ===========================================================
No evaluation or error checking needs to be done
since this has already been done by EvaluateSlotOverrides()
=========================================================== */
dstInsSlot = FindInstanceSlot(theEnv,dstins,(SYMBOL_HN *) slotOverrides->supplementalInfo);
if (dstInsSlot == NULL)
{
SlotExistError(theEnv,ValueToString(slotOverrides->supplementalInfo),
"duplicate-instance");
goto DuplicateError;
}
if (msgpass)
{
msgExp.type = slotOverrides->type;
if (msgExp.type != MULTIFIELD)
msgExp.value = slotOverrides->value;
else
msgExp.value = (void *) slotOverrides;
msgExp.argList = NULL;
msgExp.nextArg = NULL;
DirectMessage(theEnv,dstInsSlot->desc->overrideMessage,dstins,&temp,&msgExp);
if (EvaluationData(theEnv)->EvaluationError ||
((temp.type == SYMBOL) && (temp.value == EnvFalseSymbol(theEnv))))
goto DuplicateError;
}
else
{
if (dstInsSlot->desc->multiple && (slotOverrides->type != MULTIFIELD))
{
temp.type = MULTIFIELD;
temp.value = EnvCreateMultifield(theEnv,1L);
SetDOBegin(temp,1);
SetDOEnd(temp,1);
SetMFType(temp.value,1,(short) slotOverrides->type);
SetMFValue(temp.value,1,slotOverrides->value);
newval = &temp;
}
else
newval = slotOverrides;
if (PutSlotValue(theEnv,dstins,dstInsSlot,newval,&junk,"duplicate-instance") == FALSE)
goto DuplicateError;
}
dstInsSlot->override = TRUE;
slotOverrides = slotOverrides->next;
}
/* =======================================
Copy values from source instance to new
directly or with put- messages
======================================= */
for (i = 0 ; i < dstins->cls->localInstanceSlotCount ; i++)
{
if (dstins->slots[i].override == FALSE)
{
if (msgpass)
{
temp.type = (unsigned short) srcins->slots[i].type;
temp.value = srcins->slots[i].value;
if (temp.type == MULTIFIELD)
{
SetDOBegin(temp,1);
SetDOEnd(temp,GetMFLength(temp.value));
}
valArg = ConvertValueToExpression(theEnv,&temp);
DirectMessage(theEnv,dstins->slots[i].desc->overrideMessage,
dstins,&temp,valArg);
ReturnExpression(theEnv,valArg);
if (EvaluationData(theEnv)->EvaluationError ||
((temp.type == SYMBOL) && (temp.value == EnvFalseSymbol(theEnv))))
goto DuplicateError;
}
else
{
temp.type = (unsigned short) srcins->slots[i].type;
temp.value = srcins->slots[i].value;
if (srcins->slots[i].type == MULTIFIELD)
{
SetDOBegin(temp,1);
SetDOEnd(temp,GetMFLength(srcins->slots[i].value));
}
if (PutSlotValue(theEnv,dstins,&dstins->slots[i],&temp,&junk,"duplicate-instance")
== FALSE)
goto DuplicateError;
}
}
}
/* =======================================
Send init message for message-duplicate
======================================= */
if (msgpass)
{
for (i = 0 ; i < dstins->cls->instanceSlotCount ; i++)
dstins->slotAddresses[i]->override = TRUE;
dstins->initializeInProgress = 1;
DirectMessage(theEnv,MessageHandlerData(theEnv)->INIT_SYMBOL,dstins,result,NULL);
}
dstins->busy--;
if (dstins->garbage)
{
result->type = SYMBOL;
result->value = EnvFalseSymbol(theEnv);
SetEvaluationError(theEnv,TRUE);
}
else
{
result->type = INSTANCE_NAME;
result->value = (void *) GetFullInstanceName(theEnv,dstins);
}
return;
DuplicateError:
dstins->busy--;
QuashInstance(theEnv,dstins);
SetEvaluationError(theEnv,TRUE);
}
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -