/******************************************************************* * Function: ArrayIndexAnalysis::getTypeInfo * Purpose : Get an array dimensions' information * Initial : Nurudeen A. Lameed on July 21, 2009 ******************************************************************** Revisions and bug fixes: */ inline TypeInfo ArrayIndexAnalysis::getTypeInfo(const IIRNode* node, const SymbolExpr* symbol) const { // retrieve the type set TypeInfoMap post = typeInferenceInfo->postTypeMap; TypeSet tSet = (post[node])[symbol]; // look for one with bounds information // if none has the info, return an empty type info. for (TypeSet::const_iterator it = tSet.begin(), iEnd = tSet.end(); it != iEnd; ++it) { TypeInfo typ = *it; if ( typ.getSizeKnown() ) { return *it; } } return TypeInfo(); // return an empty type info }
/******************************************************************* * Function: ArrayIndexAnalysis::flowFunction * Purpose : compute out set from in set based on the type of statement * Initial : Nurudeen A. Lameed on July 21, 2009 ******************************************************************** Revisions and bug fixes: */ FlowSet ArrayIndexAnalysis::flowFunction(const Statement* stmt, const FlowSet& in) { // declare out flow set FlowSet out; // copy in flow set into out flow set out.insert(in.begin(), in.end()); switch(stmt->getStmtType()) { case Statement::ASSIGN: { const AssignStmt* aStmt = dynamic_cast<const AssignStmt*>(stmt); // get the left handsides Expression::ExprVector lhs = aStmt->getLeftExprs(); SymbolExpr* symbol = 0; if (lhs.size() == 1 && lhs[0]->getExprType() == Expression::SYMBOL) { symbol = dynamic_cast<SymbolExpr*>(lhs[0]); } else { // get all left symbols/expressions for (size_t i=0, size = lhs.size(); i < size; ++i) { // update out set, if it is a parameterized expression computeOutSet(lhs[i], out); } } // check the right hand side Expression* rhs = aStmt->getRightExpr(); // is symbol an array/matrix with known size? if ( allMatrixSymbols.find(symbol) != allMatrixSymbols.end() ) // symbol is used as an array ... { // get the type information TypeInfo typ = getTypeInfo(aStmt, symbol); if ( typ.getSizeKnown()) { const TypeInfo::DimVector& dimV = typ.getMatSize(); TypeInfo::DimVector bounds; // remove dimensions with value 1; (e.g. row or column vectors) std::remove_copy_if(dimV.begin(), dimV.end(), std::back_inserter(bounds), equalOne); // update the table arrayBoundsMap[symbol] = bounds; // update the flow set using the bounds updateFlowSet(symbol, bounds, out); } } // update outset (for parameterized expression) computeOutSet(rhs, out); // update outset (for index update if (isIndex(symbol)) { // compute flow set for index update computeOutSet(symbol, rhs, out); } } break; case Statement::EXPR: { // convert the statement to an expression const ExprStmt* aStmt = dynamic_cast<const ExprStmt*>(stmt); // compute out set for the statement computeOutSet(aStmt->getExpression(), out); } break; default: // do nothing; { } } return out; }