ManagerFIAliasAliasMap.cpp

Go to the documentation of this file.
00001 
00016 #include "ManagerFIAliasAliasMap.hpp"
00017 #include <Utils/Util.hpp>
00018 
00019 
00020 namespace OA {
00021   namespace Alias {
00022 
00023 static bool debug = false;
00024 
00027 ManagerFIAliasAliasMap::ManagerFIAliasAliasMap(OA_ptr<AliasIRInterface> _ir) 
00028    : ManagerFIAlias(_ir)
00029 {
00030     OA_DEBUG_CTRL_MACRO("DEBUG_ManagerFIAliasAliasMap:ALL", debug);
00031 }
00032 
00033 OA_ptr<Alias::InterAliasMap> 
00034 ManagerFIAliasAliasMap::performAnalysis( OA_ptr<IRProcIterator> procIter,
00035                                          FIAliasImplement implement )
00036 {
00037     // create an empty InterAliasMap
00038     mInterAliasMap = new InterAliasMap();
00039 
00040     // Invoke the ManagerFIAlias routine to create the alias sets
00041     // within the union-find universe.
00042     OA_ptr<UnionFindUniverse> ufset = performFIAlias(procIter, implement);
00043 
00044     // Depending on the implementation of FIAlias, only a 
00045     // subset of the defined procedures may have been analyzed.
00046     OA_ptr<IRProcIterator> analyzedProcIter = getAnalyzedProcIter();
00047 
00048     // Convert the uion-find universe to equiv sets.
00049     buildAliasMaps(ufset,analyzedProcIter);
00050 
00051     return mInterAliasMap;
00052 }
00053 
00054 
00055 void
00056 ManagerFIAliasAliasMap::buildAliasMaps( OA_ptr<UnionFindUniverse> ufset,
00057                                         OA_ptr<IRProcIterator> procIter )
00058 {
00059     if (debug) { std::cout << "=========== Building AliasMap ========" 
00060                            << std::endl; }
00061 
00063     std::map<ProcHandle, std::map<int,int> > setIdToAliasMapId;
00064     std::set<int> allufsetIDs;
00065 
00066     // loop all the mres and get a set of mres for each ufset
00067     std::map<OA_ptr<MemRefExpr>,int>::iterator mreMapIter;
00068     for (mreMapIter=mMREToID.begin(); mreMapIter!=mMREToID.end();
00069          mreMapIter++ )
00070     {
00071         OA_ptr<MemRefExpr> mre = mreMapIter->first;
00072 
00073         // only map those MREs that do not involve an addressOf operation
00074         if(mre->isaRefOp()) {
00075            OA_ptr<RefOp> refop = mre.convert<RefOp>();
00076            if(refop->isaAddressOf()) { continue; }
00077         }
00078  
00079         int setID = ufset->Find(mMREToID[mre]);
00080         // record which mres are associated with this ufset
00081         allufsetIDs.insert(setID);
00082         
00083     }
00084 
00085     // iterate over all procedures and determine the set of fixed
00086     // locations for each set within each procedure
00087     for (procIter->reset();  procIter->isValid(); (*procIter)++ ) {
00088       ProcHandle proc = procIter->current();
00089       if (debug) {
00090         std::cout << "proc = " << mIR->toString(proc) << std::endl;
00091       }
00092       std::map<int,bool> foundNonVisibleRef;
00093       std::map<int,bool> foundVisibleFixedLoc;
00094       std::map<int,int>  LocsetIdToAliasMapId;
00095 
00096       // create an alias map for this procedure
00097       OA_ptr<AliasMap> aliasMap;
00098       aliasMap = new AliasMap(proc);
00099 
00100       // visit all of the MREs in the program being analyzed
00101       for (mreMapIter=mMREToID.begin(); mreMapIter!=mMREToID.end();
00102            mreMapIter++ )
00103       {
00104           OA_ptr<MemRefExpr> mre = mreMapIter->first;
00105           if (debug) {
00106               std::cout << "\tmre = ";
00107               mre->dump(std::cout);
00108               mre->output(*mIR);
00109           }
00110           
00111           if(mre->isaAddressOf()) {
00112               if (debug) {
00113                   std::cout << "\taddressOf so skipping this MRE" << std::endl;
00114               }
00115               continue; 
00116           }
00117  
00118           int ufsetID = ufset->Find(mMREToID[mre]);
00119           if (debug) {
00120               std::cout << "\tufsetID = " << ufsetID << std::endl;
00121           }
00122 
00123           // if the base is visible then could be a FixedLoc,
00124           // InvisibleLoc, or just a MRE involving a deref to a
00125           // visible variable or UnnamedLoc
00126           VisibleBaseVisitor mreVisitor(mIR, proc);
00127           mre->acceptVisitor(mreVisitor);
00128           if (mreVisitor.isBaseVisible()) {
00129 
00130             if (debug) {
00131               std::cout << "\tmre has a visible base" << std::endl;
00132             }
00133             
00134             if (LocsetIdToAliasMapId.find(ufsetID)
00135                 ==LocsetIdToAliasMapId.end() )
00136             {
00137               LocsetIdToAliasMapId[ufsetID] = aliasMap->makeEmptySet();
00138             }
00139             int aliasMapSetId = LocsetIdToAliasMapId[ufsetID];
00140             // Determine if the MRE is a fixed location
00141             FixedLocationVisitor visitor(mIR, proc, aliasMap);
00142             mre->acceptVisitor(visitor);
00143             OA_ptr<LocSetIterator> locSetIterPtr = 
00144                 visitor.getDirectRefLocIterator();
00145 
00146             // if found a fixed location 
00147             if (locSetIterPtr->isValid()) {
00148                 foundVisibleFixedLoc[ufsetID] = true;
00149 
00150                 // put all the fixed locations into the locset
00151                 for (; locSetIterPtr->isValid(); ++(*locSetIterPtr) ) {
00152                   OA_ptr<Location> directRefLoc = (locSetIterPtr->current());
00153                   if (debug) {
00154                       std::cout << "Location: directRefLoc = ";
00155                       directRefLoc->output(*mIR);
00156                   }
00157           
00158                   aliasMap->addLocation( directRefLoc, aliasMapSetId );
00159                   
00160                   if(directRefLoc->isaSubSet()) {
00161                      OA_ptr<LocSubSet> locSubSet;
00162                      locSubSet = directRefLoc.convert<LocSubSet>();          
00163                      OA_ptr<Location> baseLoc;
00164                      baseLoc = locSubSet->getBaseLoc();
00165                      aliasMap->removeBaseLoc(baseLoc, aliasMapSetId );
00166                   } 
00167                 }
00168 
00169             // did not find a fixed location so see if we have an invisible
00170             } else {
00171                 InvisibleLocationVisitor invVisitor(mIR, proc, 
00172                                                     mProcToFormalSet[proc]);
00173                 mre->acceptVisitor(invVisitor);
00174                 if (invVisitor.isInvisibleRef()) {
00175                     OA_ptr<Location> visitorloc 
00176                          = invVisitor.getInvisibleRefLoc();
00177                     if (debug) {
00178                         std::cout << "Location: invloc = ";
00179                         visitorloc->output(*mIR);
00180                     }
00181                     aliasMap->addLocation( visitorloc, aliasMapSetId );
00182                 }
00183             } 
00184 
00185             // whether we found a location for this mre or not
00186             // map this mre to the aliasMapSet 
00187             // the base of the memrefexpr is visible in this procedure
00188             if (LocsetIdToAliasMapId.find(ufsetID)
00189                 !=LocsetIdToAliasMapId.end() )
00190             {
00191                 int aliasMapSetId = LocsetIdToAliasMapId[ufsetID];
00192                 aliasMap->mapMemRefToMapSet(mre,
00193                                             LocsetIdToAliasMapId[ufsetID]);
00194             }
00195 
00196           // If the base is not visible then we need to keep any invisible
00197           // locs that are found in the same ufset
00198           } else {
00199 
00200               foundNonVisibleRef[ufsetID] = true;
00201           }
00202 
00203       } // loop over MREs in program being analyzed
00204 
00205       // do some cleanup wrt to InvisibleLocs
00206       // for each ufset, remove all of the InvisibleLocs
00207       // if there was no invisible references but
00208       // there was a visible fixed location
00209       for (std::set<int>::iterator setIter=allufsetIDs.begin();
00210            setIter!=allufsetIDs.end(); setIter++)
00211       {
00212           if (foundVisibleFixedLoc[*setIter] == true
00213               && foundNonVisibleRef[*setIter] == false )
00214           {
00215             int aliasMapSetId = LocsetIdToAliasMapId[*setIter];
00216             aliasMap->removeInvisibleLocs(aliasMapSetId);
00217           }
00218       }
00219       setIdToAliasMapId[proc] = LocsetIdToAliasMapId;
00220       // store off the aliasmap for this procedure
00221       mInterAliasMap->mapProcToAliasMap(proc,aliasMap);
00222 
00223     } // iterate over all procedures
00224 
00225     // iterate over all of the mem ref handles
00226     // with the goal being to map the mem ref handles to alias sets
00227     std::set<OA_ptr<MemRefExpr> > multiFixLocMRESet;
00228     std::map<MemRefHandle,ProcHandle>::iterator refprocIter;
00229     for (refprocIter=mMemRefHandleToProc.begin();
00230          refprocIter!=mMemRefHandleToProc.end(); refprocIter++ )
00231     {
00232         MemRefHandle memref = refprocIter->first;
00233         ProcHandle proc = refprocIter->second;
00234 
00235         if (debug) {
00236           std::cout << "\nMapping MemRefHandle: " << mIR->toString(memref)
00237                     << std::endl;
00238         }
00239 
00240         // get alias map for this procedure
00241         OA_ptr<AliasMap> aliasMap = mInterAliasMap->getAliasMapResults(proc);
00242 
00243         // loop over MREs for the given memref
00244         OA_ptr<MemRefExprIterator> mreIterPtr 
00245             = mIR->getMemRefExprIterator(memref);
00246       
00247         // for each mem-ref-expr associated with this memref
00248         for (; mreIterPtr->isValid(); (*mreIterPtr)++) {
00249             OA_ptr<OA::MemRefExpr> mre = mreIterPtr->current();
00250 
00251             if (debug) {
00252               std::cout << "\n\tFound MemRefExpr: ";
00253               mre->output(*mIR);
00254               std::cout << std::endl;
00255             }
00256 
00257             // only map those MREs that do not involve an addressOf operation
00258             // if (mre->hasAddressTaken()) { continue; }
00259             if(mre->isaRefOp()) {
00260                OA_ptr<RefOp> refop = mre.convert<RefOp>();
00261                if(refop->isaAddressOf()) { continue; }
00262             }
00263 
00264             // map the mem ref handle to the set that mre is in
00265             int ufsetID = ufset->Find(mMREToID[mre]);
00266 
00267             // if we have no location associated with this
00268             // ufsetID within this proc, then there won't be an
00269             // alias map associated with it yet
00270             // therefore we need to map this mre and memrefhandle
00271             // to the zeroth AliasMap set and store that information
00272             // for this ufsetID and proc
00273             if (setIdToAliasMapId[proc].find(ufsetID)
00274                 ==setIdToAliasMapId[proc].end() )
00275             {
00276                 setIdToAliasMapId[proc][ufsetID] = 0;
00277             }
00278 
00279             // now assign the memref to the set within the alias map.
00280             aliasMap->mapMemRefToMapSet(memref, 
00281                                         setIdToAliasMapId[proc][ufsetID] );
00282 
00283             // BK (7/26/07) making NamedRef's and local UnnamedRefs
00284             // be within a MUSTALIAS set
00285 
00286             if ( multiFixLocMRESet.find(mre) !=  multiFixLocMRESet.end()) {
00287               // cannot make a new aliasMap set for an mre with multiple
00288               // fixed locations, because more than one location added to
00289               // an AliasMap set will cause the set to be MayAlias anyway
00290               if (debug) {
00291                 std::cout << "\n\t\tFound multiFixLocMRE, continuing ...\n";
00292               }
00293               continue;
00294             }
00295 
00296             bool isLocalUnnamed = false;
00297             if (mre->isaUnnamed()) {
00298               if (debug) {
00299                 std::cout << "\t\tUnnamedRef";
00300               }
00301               OA_ptr<UnnamedRef> uRef = mre.convert<UnnamedRef>();
00302               if (uRef->isLocal() && (uRef->getProcHandle()==proc)) {
00303                 isLocalUnnamed = true;
00304                 if (debug) {
00305                   if (isLocalUnnamed) {
00306                     std::cout << " Local\n";
00307                   } else {
00308                     std::cout << " non-Local\n";
00309                   }
00310                 }
00311               }
00312             }
00313             if (mre->isaNamed() || isLocalUnnamed) {
00314               // get current aliasMap setId for this mre
00315               int aliasSetMapId = aliasMap->getMapSetId(mre);
00316               
00317               if (debug) {
00318                 if (!isLocalUnnamed) {
00319                   std::cout << "\t\tNamedRef\n";
00320                 }
00321                 std::cout << "\t\t\tMapSetId = " << aliasSetMapId
00322                           << "  isMust = " << aliasMap->isMust(aliasSetMapId)
00323                           << std::endl;
00324               }
00325 
00326               // if not MUSTALIAS, create new aliasMap set and populate it
00327               if (!aliasMap->isMust(aliasSetMapId)) {
00328                 if (debug) {
00329                   std::cout << "Found NamedRef or local UnnamedRef as MayAlias: ";
00330                   mre->output(*mIR);
00331                   std::cout << std::endl;
00332                 }
00333                 
00334                 // 1) add any fixed locs (only if there is exactly one fixed loc)
00335                 FixedLocationVisitor visitor(mIR, proc, aliasMap);
00336                 mre->acceptVisitor(visitor);
00337                 OA_ptr<LocSetIterator> locSetIterPtr = 
00338                   visitor.getDirectRefLocIterator();
00339                 
00340                 // if found a fixed location 
00341                 if (locSetIterPtr->isValid()) {
00342                   
00343                   // get first fixed loc and look for more
00344                   OA_ptr<Location> directRefLoc = locSetIterPtr->current();
00345                   // incrememt fixedLocIter
00346                   ++(*locSetIterPtr);
00347                   
00348                   // if there is more than one fixed location for this mre,
00349                   if (locSetIterPtr->isValid()) {
00350                     // add this mre to the multiFixLocMRESet and move on
00351                     multiFixLocMRESet.insert(mre);
00352                     if (debug) {
00353                       std::cout << "&*&*&*&* Warning: "
00354                                 << "found more than one fixed loc for mre";
00355                     }
00356                     continue; // go to next mre for this memref
00357                   }
00358                   
00359                   // only one fixed loc, just process it:
00360                   // 0) get a new MustAlias set
00361                   aliasSetMapId = aliasMap->makeEmptySet();
00362                   // 1) add fixed location to new MustAlias set
00363                   aliasMap->addLocation( directRefLoc, aliasSetMapId);
00364                   if (debug) {
00365                     std::cout << "only MustAlias Location: directRefLoc = ";
00366                     directRefLoc->output(*mIR);
00367                     std::cout << "\tremapping to set id: " << aliasSetMapId
00368                               << std::endl;
00369                   }
00370                   // 2) map the mre and memref to new MustAlias set
00371                   aliasMap->mapMemRefToMapSet(mre, aliasSetMapId);
00372                   aliasMap->mapMemRefToMapSet(memref, aliasSetMapId);
00373                   
00374                 } // end of if mre has a fixed location
00375                 
00376               }// end of if (!isMust)
00377               else {
00378 
00379                 // still need to map the memref to this aliasMap for mre
00380                 aliasMap->mapMemRefToMapSet(memref, aliasSetMapId);
00381               }
00382 
00383             } // end of if NamedRef or local UnnamedRef   
00384         }  // end of mre loop
00385     } // over memrefhandles
00386 }
00387 
00388   } // end of namespace Alias
00389 } // end of namespace OA