LLVM API Documentation
00001 //===- lib/Linker/Linker.cpp - Basic Linker functionality ----------------===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file was developed by Reid Spencer and is distributed under the 00006 // University of Illinois Open Source License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file contains basic Linker functionality that all usages will need. 00011 // 00012 //===----------------------------------------------------------------------===// 00013 00014 #include "llvm/Linker.h" 00015 #include "llvm/Module.h" 00016 #include "llvm/Bytecode/Reader.h" 00017 #include "llvm/Config/config.h" 00018 #include <iostream> 00019 00020 using namespace llvm; 00021 00022 Linker::Linker(const std::string& progname, const std::string& modname, unsigned flags) 00023 : Composite(0) 00024 , LibPaths() 00025 , Flags(flags) 00026 , Error() 00027 , ProgramName(progname) 00028 { 00029 Composite = new Module(modname); 00030 } 00031 00032 Linker::Linker(const std::string& progname, Module* aModule, unsigned flags) 00033 : Composite(aModule) 00034 , LibPaths() 00035 , Flags(flags) 00036 , Error() 00037 , ProgramName(progname) 00038 { 00039 } 00040 00041 Linker::~Linker() { 00042 delete Composite; 00043 } 00044 00045 bool 00046 Linker::error(const std::string& message) { 00047 Error = message; 00048 if (!(Flags&QuietErrors)) { 00049 std::cerr << ProgramName << ": error: " << message << "\n"; 00050 } 00051 return true; 00052 } 00053 00054 bool 00055 Linker::warning(const std::string& message) { 00056 Error = message; 00057 if (!(Flags&QuietErrors)) { 00058 std::cerr << ProgramName << ": warning: " << message << "\n"; 00059 } 00060 return false; 00061 } 00062 00063 void 00064 Linker::verbose(const std::string& message) { 00065 if (Flags&Verbose) { 00066 std::cerr << " " << message << "\n"; 00067 } 00068 } 00069 00070 void 00071 Linker::addPath(const sys::Path& path) { 00072 LibPaths.push_back(path); 00073 } 00074 00075 void 00076 Linker::addPaths(const std::vector<std::string>& paths) { 00077 for (unsigned i = 0; i != paths.size(); ++i) { 00078 sys::Path aPath; 00079 aPath.set(paths[i]); 00080 LibPaths.push_back(aPath); 00081 } 00082 } 00083 00084 void 00085 Linker::addSystemPaths() { 00086 sys::Path::GetBytecodeLibraryPaths(LibPaths); 00087 LibPaths.insert(LibPaths.begin(),sys::Path("./")); 00088 } 00089 00090 Module* 00091 Linker::releaseModule() { 00092 Module* result = Composite; 00093 LibPaths.clear(); 00094 Error.clear(); 00095 Composite = 0; 00096 Flags = 0; 00097 return result; 00098 } 00099 00100 // LoadObject - Read in and parse the bytecode file named by FN and return the 00101 // module it contains (wrapped in an auto_ptr), or auto_ptr<Module>() and set 00102 // Error if an error occurs. 00103 std::auto_ptr<Module> 00104 Linker::LoadObject(const sys::Path &FN) { 00105 std::string ParseErrorMessage; 00106 Module *Result = ParseBytecodeFile(FN.toString(), &ParseErrorMessage); 00107 if (Result) 00108 return std::auto_ptr<Module>(Result); 00109 Error = "Bytecode file '" + FN.toString() + "' could not be loaded"; 00110 if (ParseErrorMessage.size()) 00111 Error += ": " + ParseErrorMessage; 00112 return std::auto_ptr<Module>(); 00113 } 00114 00115 // IsLibrary - Determine if "Name" is a library in "Directory". Return 00116 // a non-empty sys::Path if its found, an empty one otherwise. 00117 static inline sys::Path IsLibrary(const std::string& Name, 00118 const sys::Path& Directory) { 00119 00120 sys::Path FullPath(Directory); 00121 00122 // Make sure the directory actually is a directory in the file system. 00123 if (FullPath.isDirectory()) 00124 { 00125 // Try the libX.a form 00126 FullPath.appendComponent("lib" + Name); 00127 FullPath.appendSuffix("a"); 00128 if (FullPath.isArchive()) 00129 return FullPath; 00130 00131 // Try the libX.bca form 00132 FullPath.eraseSuffix(); 00133 FullPath.appendSuffix("bca"); 00134 if (FullPath.isArchive()) 00135 return FullPath; 00136 00137 // Try the libX.so (or .dylib) form 00138 FullPath.eraseSuffix(); 00139 FullPath.appendSuffix(&(LTDL_SHLIB_EXT[1])); 00140 if (FullPath.isDynamicLibrary()) // Native shared library? 00141 return FullPath; 00142 if (FullPath.isBytecodeFile()) // .so file containing bytecode? 00143 return FullPath; 00144 00145 // Not found .. fall through 00146 } 00147 00148 // Indicate that the library was not found in the directory. 00149 FullPath.clear(); 00150 return FullPath; 00151 } 00152 00153 /// FindLib - Try to convert Filename into the name of a file that we can open, 00154 /// if it does not already name a file we can open, by first trying to open 00155 /// Filename, then libFilename.[suffix] for each of a set of several common 00156 /// library suffixes, in each of the directories in LibPaths. Returns an empty 00157 /// Path if no matching file can be found. 00158 /// 00159 sys::Path 00160 Linker::FindLib(const std::string &Filename) { 00161 // Determine if the pathname can be found as it stands. 00162 sys::Path FilePath(Filename); 00163 if (FilePath.canRead() && 00164 (FilePath.isArchive() || FilePath.isDynamicLibrary())) 00165 return FilePath; 00166 00167 // Iterate over the directories in Paths to see if we can find the library 00168 // there. 00169 for (unsigned Index = 0; Index != LibPaths.size(); ++Index) { 00170 sys::Path Directory(LibPaths[Index]); 00171 sys::Path FullPath = IsLibrary(Filename,Directory); 00172 if (!FullPath.isEmpty()) 00173 return FullPath; 00174 } 00175 return sys::Path(); 00176 }