use of cx2x.xcodeml.xnode.XfunctionDefinition in project claw-compiler by C2SM-RCM.
the class LoopHoist method analyze.
/**
* @see Transformation#analyze(XcodeProgram, Transformer)
*/
@Override
public boolean analyze(XcodeProgram xcodeml, Transformer transformer) {
int _pragmaDepthLevel = _clawStart.getPragma().depth();
_nestedLevel = _clawStart.getHoistInductionVars().size();
// Find all the group of nested loops that can be part of the hoisting
List<Xnode> statements = XnodeUtil.findDoStatement(_clawStart.getPragma(), _clawEnd.getPragma(), _clawStart.getHoistInductionVars());
if (statements.size() == 0) {
xcodeml.addError("No do statement group meets the criteria of hoisting.", _clawStart.getPragma().lineNo());
return false;
}
for (int i = 0; i < statements.size(); i++) {
Xnode[] group = new Xnode[_nestedLevel];
LoopHoistDoStmtGroup g = new LoopHoistDoStmtGroup(group);
try {
reloadDoStmts(g, statements.get(i));
} catch (IllegalTransformationException e) {
xcodeml.addError("Group " + i + " of do statements do not meet the" + " criteria of loop hoisting (Group index starts at 0).", _clawStart.getPragma().lineNo());
return false;
}
LoopHoistDoStmtGroup crtGroup = new LoopHoistDoStmtGroup(group);
int depth = group[0].depth();
if (depth != _pragmaDepthLevel) {
Xnode tmpIf = group[0].matchAncestor(Xcode.FIFSTATEMENT);
Xnode tmpSelect = group[0].matchAncestor(Xcode.FSELECTCASESTATEMENT);
Xnode tmpDo = group[0].matchAncestor(Xcode.FDOSTATEMENT);
if (tmpIf == null && tmpSelect == null && tmpDo == null) {
xcodeml.addError("Group " + i + " is nested in an unsupported " + "statement for loop hoisting (Group index starts at 0).", _clawStart.getPragma().lineNo());
return false;
}
int ifDepth = (tmpIf != null) ? tmpIf.depth() : Xnode.UNDEF_DEPTH;
int selectDepth = (tmpSelect != null) ? tmpSelect.depth() : Xnode.UNDEF_DEPTH;
int doDepth = (tmpDo != null) ? tmpDo.depth() : Xnode.UNDEF_DEPTH;
if ((_pragmaDepthLevel <= ifDepth || _pragmaDepthLevel <= selectDepth || _pragmaDepthLevel <= doDepth) && (ifDepth < depth || selectDepth < depth || doDepth < depth)) {
crtGroup.setExtraction();
} else {
xcodeml.addError("Group " + i + " is nested in an unsupported " + "statement for loop hoisting or depth is too high " + "(Group index starts at 0).", _clawStart.getPragma().lineNo());
return false;
}
}
_doGroup.add(crtGroup);
}
LoopHoistDoStmtGroup master = _doGroup.get(0);
for (int i = 1; i < _doGroup.size(); ++i) {
LoopHoistDoStmtGroup next = _doGroup.get(i);
for (int j = 0; j < master.getDoStmts().length; ++j) {
// Iteration range are identical, just merge
if (j == 0 && (!XnodeUtil.hasSameIndexRange(master.getDoStmts()[j], next.getDoStmts()[j]) && XnodeUtil.hasSameIndexRangeBesidesLower(master.getDoStmts()[j], next.getDoStmts()[j]))) {
// Iteration range are identical besides lower-bound, if creation
next.setIfStatement();
} else if (!XnodeUtil.hasSameIndexRange(master.getDoStmts()[j], next.getDoStmts()[j])) {
// Iteration range are too different, stop analysis
xcodeml.addError("Iteration range of do statements group " + i + " differs from group 0. Loop hoisting aborted.", _clawStart.getPragma().lineNo());
return false;
}
}
}
// Check reshape mandatory points
if (_clawStart.hasReshapeClause()) {
XfunctionDefinition fctDef = XnodeUtil.findParentFunction(_clawStart.getPragma());
if (fctDef == null) {
xcodeml.addError("Unable to matchSeq the function/subroutine/module " + "definition including the current directive", _clawStart.getPragma().lineNo());
return false;
}
for (ClawReshapeInfo r : _clawStart.getReshapeClauseValues()) {
if (!fctDef.getSymbolTable().contains(r.getArrayName()) || !fctDef.getDeclarationTable().contains(r.getArrayName())) {
// Check in the parent def if present
if (!checkUpperDefinition(fctDef, r.getArrayName())) {
xcodeml.addError(String.format("Reshape variable %s not found in " + "the definition of %s", r.getArrayName(), fctDef.getName().value()), _clawStart.getPragma().lineNo());
return false;
}
}
}
}
return true;
}
Aggregations