From c244361b8ae743bcb326b9a1a168f2fdcab491e8 Mon Sep 17 00:00:00 2001 From: dec05eba Date: Wed, 13 Dec 2017 19:58:58 +0100 Subject: Change linking order for pkg-config Linking should be added in the order of dependencies. Modified linking logic to check global lib dir if pkg-config fails (missing package, pkg-config is not installed or any other reason), also required for Windows. --- backend/ninja/Ninja.cpp | 104 ++++++++++++++++++++++++++---------------------- backend/ninja/Ninja.hpp | 2 +- 2 files changed, 57 insertions(+), 49 deletions(-) (limited to 'backend/ninja') diff --git a/backend/ninja/Ninja.cpp b/backend/ninja/Ninja.cpp index 87dd873..ede150c 100644 --- a/backend/ninja/Ninja.cpp +++ b/backend/ninja/Ninja.cpp @@ -81,70 +81,79 @@ namespace backend // TODO: First check if pkg-config is installed. If it's not, only check dependencies that exists in the dependencies sub directory. // If pkg-config is installed and dependency is not installed, check in dependencies sub directory. - Result Ninja::getLinkerFlags(const vector &dependencies, LinkerFlagCallbackFunc linkerFlagCallbackFunc) const + Result Ninja::getLinkerFlags(const vector &dependencies, LinkerFlagCallbackFunc linkerFlagCallbackFunc) const { - if(dependencies.empty()) return Result::Ok(""); + if(dependencies.empty()) return Result::Ok(true); string globalLibDir = getHomeDir(); globalLibDir += "/.sibs/lib"; Result createGlobalLibDirResult = createDirectoryRecursive(globalLibDir.c_str()); if(createGlobalLibDirResult.isErr()) - return Result::Err(createGlobalLibDirResult); + return createGlobalLibDirResult; - string globalLibLinkerFlags; - vector pkgConfigDependencies; - for(const sibs::Dependency &dependency : dependencies) + vector pkgConfigDependencies; + vector globalLibDependencies; + for(const Dependency &dependency : dependencies) { Result pkgConfigDependencyValidation = validatePkgConfigPackageVersionExists(dependency); if(pkgConfigDependencyValidation.isOk()) { - pkgConfigDependencies.push_back(dependency.name); + pkgConfigDependencies.push_back(dependency); } else { - printf("%s, trying global lib\n", pkgConfigDependencyValidation.getErrMsg().c_str()); - Result globalLibLinkerFlagsResult = GlobalLib::getStaticLibsLinkerFlags(globalLibDir, dependency.name, dependency.version, linkerFlagCallbackFunc); - if(globalLibLinkerFlagsResult.isErr()) - { - if(globalLibLinkerFlagsResult.getErrorCode() == GlobalLib::DependencyError::DEPENDENCY_NOT_FOUND || globalLibLinkerFlagsResult.getErrorCode() == GlobalLib::DependencyError::DEPENDENCY_VERSION_NO_MATCH) - { - printf("Dependency not found in global lib, trying to download from github\n"); - // TODO: Download several dependencies at the same time by adding them to a list - // and then iterate them and download them all using several threads. - - // TODO: If return error is invalid url, then the message should be converted to - // invalid package name/version. A check should be done if it is the name or version - // that is invalid. - Result downloadDependencyResult = GlobalLib::downloadDependency(dependency); - if(downloadDependencyResult.isErr()) - return Result::Err(downloadDependencyResult.getErrMsg()); - - globalLibLinkerFlagsResult = GlobalLib::getStaticLibsLinkerFlags(globalLibDir, dependency.name, dependency.version, linkerFlagCallbackFunc); - if(globalLibLinkerFlagsResult.isErr()) - return globalLibLinkerFlagsResult; - } - else - { - return globalLibLinkerFlagsResult; - } - } - - globalLibLinkerFlags += " '"; - globalLibLinkerFlags += globalLibLinkerFlagsResult.unwrap(); - globalLibLinkerFlags += "'"; + globalLibDependencies.push_back(dependency); } } Result pkgConfigLinkerFlagsResult = PkgConfig::getDynamicLibsLinkerFlags(pkgConfigDependencies); if(pkgConfigLinkerFlagsResult.isErr()) - return pkgConfigLinkerFlagsResult; + { + printf("%s, using global lib...\n", pkgConfigLinkerFlagsResult.getErrMsg().c_str()); + globalLibDependencies.reserve(globalLibDependencies.size() + pkgConfigDependencies.size()); + for(const Dependency &pkgConfigDependency : pkgConfigDependencies) + { + globalLibDependencies.push_back(pkgConfigDependency); + } + pkgConfigDependencies.clear(); + } + else + { + if(!pkgConfigLinkerFlagsResult.unwrap().empty()) + linkerFlagCallbackFunc(pkgConfigLinkerFlagsResult.unwrap()); + } - if(!pkgConfigLinkerFlagsResult.unwrap().empty()) - linkerFlagCallbackFunc(pkgConfigLinkerFlagsResult.unwrap()); + for(const Dependency &globalLibDependency : globalLibDependencies) + { + printf("Dependency %s is missing from pkg-config, trying global lib\n", globalLibDependency.name.c_str()); + Result globalLibLinkerFlagsResult = GlobalLib::getStaticLibsLinkerFlags(globalLibDir, globalLibDependency.name, globalLibDependency.version, linkerFlagCallbackFunc); + if(globalLibLinkerFlagsResult.isErr()) + { + if(globalLibLinkerFlagsResult.getErrorCode() == GlobalLib::DependencyError::DEPENDENCY_NOT_FOUND || globalLibLinkerFlagsResult.getErrorCode() == GlobalLib::DependencyError::DEPENDENCY_VERSION_NO_MATCH) + { + printf("Dependency not found in global lib, trying to download from github\n"); + // TODO: Download several dependencies at the same time by adding them to a list + // and then iterate them and download them all using several threads. + + // TODO: If return error is invalid url, then the message should be converted to + // invalid package name/version. A check should be done if it is the name or version + // that is invalid. + Result downloadDependencyResult = GlobalLib::downloadDependency(globalLibDependency); + if(downloadDependencyResult.isErr()) + return downloadDependencyResult; + + globalLibLinkerFlagsResult = GlobalLib::getStaticLibsLinkerFlags(globalLibDir, globalLibDependency.name, globalLibDependency.version, linkerFlagCallbackFunc); + if(globalLibLinkerFlagsResult.isErr()) + return Result::Err(globalLibLinkerFlagsResult); + } + else + { + return Result::Err(globalLibLinkerFlagsResult); + } + } + } - string allLinkerFlags = pkgConfigLinkerFlagsResult.unwrap(); - allLinkerFlags += globalLibLinkerFlags; - return Result::Ok(allLinkerFlags); + return Result::Ok(true); } Result Ninja::createBuildFile(const std::string &packageName, const vector &dependencies, const char *savePath, LinkerFlagCallbackFunc linkerFlagCallbackFunc) @@ -223,11 +232,10 @@ namespace backend case LibraryType::EXECUTABLE: { string allLinkerFlags; - Result linkerFlags = getLinkerFlags(dependencies, [&allLinkerFlags](const string &linkerFlag) + Result linkerFlags = getLinkerFlags(dependencies, [&allLinkerFlags](const string &linkerFlag) { - allLinkerFlags += " '"; + allLinkerFlags += " "; allLinkerFlags += linkerFlag; - allLinkerFlags += "'"; }); if(linkerFlags.isErr()) return Result::Err(linkerFlags.getErrMsg()); @@ -245,9 +253,9 @@ namespace backend case LibraryType::STATIC: { string allLinkerFlags; - Result linkerFlags = getLinkerFlags(dependencies, linkerFlagCallbackFunc); + Result linkerFlags = getLinkerFlags(dependencies, linkerFlagCallbackFunc); if(linkerFlags.isErr()) - return Result::Err(linkerFlags.getErrMsg()); + return linkerFlags; result += "build "; result += packageName; diff --git a/backend/ninja/Ninja.hpp b/backend/ninja/Ninja.hpp index 3ccee1e..b82139c 100644 --- a/backend/ninja/Ninja.hpp +++ b/backend/ninja/Ninja.hpp @@ -29,7 +29,7 @@ namespace backend sibs::Result build(const char *buildFilePath); private: bool containsSourceFile(const char *filepath) const; - sibs::Result getLinkerFlags(const std::vector &dependencies, sibs::LinkerFlagCallbackFunc linkerFlagCallbackFunc) const; + sibs::Result getLinkerFlags(const std::vector &dependencies, sibs::LinkerFlagCallbackFunc linkerFlagCallbackFunc) const; private: std::vector sourceFiles; LibraryType libraryType; -- cgit v1.2.3