Home | History | Annotate | Download | only in MC
      1 //===- SearchDirs.cpp -----------------------------------------------------===//
      2 //
      3 //                     The MCLinker Project
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 #include <mcld/MC/SearchDirs.h>
     10 #include <mcld/MC/MCLDDirectory.h>
     11 #include <mcld/Support/FileSystem.h>
     12 
     13 using namespace mcld;
     14 
     15 //===----------------------------------------------------------------------===//
     16 // Non-member functions
     17 static void SpecToFilename(const std::string& pSpec, std::string& pFile)
     18 {
     19   pFile = "lib";
     20   pFile += pSpec;
     21 }
     22 
     23 //===----------------------------------------------------------------------===//
     24 // SearchDirs
     25 SearchDirs::SearchDirs()
     26 {
     27   // a magic number 8, no why.
     28   // please prove it or change it
     29   m_DirList.reserve(8);
     30 }
     31 
     32 SearchDirs::~SearchDirs()
     33 {
     34   iterator dir, dirEnd = end();
     35   for (dir = begin(); dir!=dirEnd; ++dir) {
     36     delete (*dir);
     37   }
     38 }
     39 
     40 void SearchDirs::add(const MCLDDirectory& pDirectory)
     41 {
     42   m_DirList.push_back(new MCLDDirectory(pDirectory));
     43 }
     44 
     45 mcld::sys::fs::Path* SearchDirs::find(const std::string& pNamespec, mcld::Input::Type pType)
     46 {
     47   assert(Input::DynObj == pType || Input::Archive == pType);
     48 
     49   std::string file;
     50   SpecToFilename(pNamespec, file);
     51   // for all MCLDDirectorys
     52   DirList::iterator mcld_dir, mcld_dir_end = m_DirList.end();
     53   for (mcld_dir=m_DirList.begin(); mcld_dir!=mcld_dir_end; ++mcld_dir) {
     54     // for all entries in MCLDDirectory
     55     MCLDDirectory::iterator entry = (*mcld_dir)->begin();
     56     MCLDDirectory::iterator enEnd = (*mcld_dir)->end();
     57 
     58     switch(pType) {
     59       case Input::DynObj: {
     60         while (entry!=enEnd) {
     61           if (file == entry.path()->stem().native() ) {
     62             if(mcld::sys::fs::detail::shared_library_extension == entry.path()->extension().native()) {
     63               return entry.path();
     64             }
     65           }
     66           ++entry;
     67         }
     68       }
     69       /** Fall through **/
     70       case Input::Archive : {
     71         entry = (*mcld_dir)->begin();
     72         enEnd = (*mcld_dir)->end();
     73         while ( entry!=enEnd ) {
     74           if (file == entry.path()->stem().native() &&
     75             mcld::sys::fs::detail::static_library_extension == entry.path()->extension().native()) {
     76             return entry.path();
     77           }
     78           ++entry;
     79         }
     80       }
     81       default:
     82         break;
     83     } // end of switch
     84   } // end of while
     85   return NULL;
     86 }
     87 
     88