// keep track of the state we already had
String targetSoFar = context.m_targetBoundedName;
String thisSoFar = context.m_thisBoundedName;
boolean targetWithRuntimeCheckSoFar = context.m_targetWithRuntimeCheck;
TObjectIntHashMap exprIndexToTargetIndexSoFar = (TObjectIntHashMap) context.m_exprIndexToTargetIndex.clone();
context.resetRuntimeState();
Boolean match = referenced.matchUndeterministic(context);
// merge the state
if (context.m_targetBoundedName == null) {
context.m_targetBoundedName = targetSoFar;
} else if (targetSoFar != null) {
if (node.jjtGetNumChildren() == 1) {
String referenceCallArg = ((ASTArgParameter) node.jjtGetChild(0)).getTypePattern().getPattern();
if (!targetSoFar.equals(referenceCallArg)) {
throw new UnsupportedOperationException("should not occur");
}
}
}
if (context.m_thisBoundedName == null) {
context.m_thisBoundedName = thisSoFar;
} else if (thisSoFar != null) {
if (node.jjtGetNumChildren() == 1) {
String referenceCallArg = ((ASTArgParameter) node.jjtGetChild(0)).getTypePattern().getPattern();
if (!thisSoFar.equals(referenceCallArg)) {
throw new UnsupportedOperationException("should not occur");
}
}
}
if (!context.m_targetWithRuntimeCheck) {
// restore
context.m_targetWithRuntimeCheck = targetWithRuntimeCheckSoFar;
}
if (context.m_exprIndexToTargetIndex.isEmpty()) {
// restore
context.m_exprIndexToTargetIndex = exprIndexToTargetIndexSoFar;
} else if (!exprIndexToTargetIndexSoFar.isEmpty()) {
//should merge ?
throw new UnsupportedOperationException("should not occur");
}
// update the this and target bounded name from this last visit as well as args
TObjectIntHashMap exprToTargetArgIndexes = new TObjectIntHashMap();
for (int i = 0; i < node.jjtGetNumChildren(); i++) {
String referenceCallArg = ((ASTArgParameter) node.jjtGetChild(i)).getTypePattern().getPattern();
String referentArg = expressionInfo.getArgumentNameAtIndex(i);
if (referentArg.equals(context.m_targetBoundedName)) {
context.m_targetBoundedName = referenceCallArg;
assertIsInstanceOf(
expressionInfo.getArgumentType(referentArg),
m_expressionInfo.getArgumentType(referenceCallArg)
);
} else if (referentArg.equals(context.m_thisBoundedName)) {
context.m_thisBoundedName = referenceCallArg;
assertIsInstanceOf(
expressionInfo.getArgumentType(referentArg),
m_expressionInfo.getArgumentType(referenceCallArg)
);
} else {
int adviceArgIndex = i;
if (context.m_exprIndexToTargetIndex.containsKey(referentArg)) {
int targetArgIndex = context.m_exprIndexToTargetIndex.get(referentArg);
exprToTargetArgIndexes.put(referenceCallArg, targetArgIndex);
}
}
}
// merge with index found so far (inlined args() f.e.)
Object[] soFar = exprIndexToTargetIndexSoFar.keys();
for (int i = 0; i < soFar.length; i++) {
String name = (String) soFar[i];
if (!exprToTargetArgIndexes.containsKey(name)) {
exprToTargetArgIndexes.put(name, exprIndexToTargetIndexSoFar.get(name));
}
}
context.m_exprIndexToTargetIndex = exprToTargetArgIndexes;
return match;
}