From bbe0de32340289407e8d0770ce95f274c448e8be Mon Sep 17 00:00:00 2001 From: Joerg Bornemann Date: Wed, 14 May 2014 12:21:04 +0200 Subject: make product.buildDirectory available in Probe item As a consequence product.name is evaluated very early and cannot depend on module properties and such. Autotests that used product.name as verification script had to be adjusted accordingly. Task-number: QBS-393 Change-Id: I62ae1a92313af54d9eb15e88b7457388584f7556 Reviewed-by: Christian Kandeler --- src/lib/corelib/language/language.cpp | 5 +++- src/lib/corelib/language/moduleloader.cpp | 33 ++++++++++++++++------ src/lib/corelib/language/moduleloader.h | 4 ++- src/lib/corelib/language/projectresolver.cpp | 14 ++++----- src/lib/corelib/language/projectresolver.h | 1 + .../testdata/profilevaluesandoverriddenvalues.qbs | 5 ++-- 6 files changed, 42 insertions(+), 20 deletions(-) (limited to 'src/lib/corelib/language') diff --git a/src/lib/corelib/language/language.cpp b/src/lib/corelib/language/language.cpp index 10c387970..4974a3e68 100644 --- a/src/lib/corelib/language/language.cpp +++ b/src/lib/corelib/language/language.cpp @@ -814,9 +814,12 @@ QStringList ResolvedProduct::generatedFiles(const QString &baseFile, const FileT QString ResolvedProduct::buildDirectory() const { - return topLevelProject()->buildDirectory + QLatin1Char('/') + name; + const QString result = productProperties.value(QLatin1String("buildDirectory")).toString(); + QBS_CHECK(!result.isEmpty()); + return result; } + ResolvedProject::ResolvedProject() : enabled(true), m_topLevelProject(0) { } diff --git a/src/lib/corelib/language/moduleloader.cpp b/src/lib/corelib/language/moduleloader.cpp index 4890a2eae..3860ddcd9 100644 --- a/src/lib/corelib/language/moduleloader.cpp +++ b/src/lib/corelib/language/moduleloader.cpp @@ -128,7 +128,8 @@ ModuleLoaderResult ModuleLoader::load(const SetupProjectParameters ¶meters) root->setProperty(QLatin1String("sourceDirectory"), VariantValue::create(QFileInfo(root->file()->filePath()).absolutePath())); root->setProperty(QLatin1String("buildDirectory"), VariantValue::create(buildDirectory)); - handleProject(&result, root, QSet() << QDir::cleanPath(parameters.projectFilePath())); + handleProject(&result, root, buildDirectory, + QSet() << QDir::cleanPath(parameters.projectFilePath())); result.root = root; result.qbsFiles = m_reader->filesRead(); return result; @@ -202,12 +203,13 @@ private: }; void ModuleLoader::handleProject(ModuleLoaderResult *loadResult, Item *item, - const QSet &referencedFilePaths) + const QString &buildDirectory, const QSet &referencedFilePaths) { if (!checkItemCondition(item)) return; ProjectContext projectContext; projectContext.result = loadResult; + projectContext.buildDirectory = buildDirectory; projectContext.localModuleSearchPath = FileInfo::resolvePath(item->file()->dirPath(), moduleSearchSubDir); @@ -232,7 +234,7 @@ void ModuleLoader::handleProject(ModuleLoaderResult *loadResult, Item *item, handleSubProject(&projectContext, child, referencedFilePaths); } else if (child->typeName() == QLatin1String("Project")) { copyProperties(item, child); - handleProject(loadResult, child, referencedFilePaths); + handleProject(loadResult, child, buildDirectory, referencedFilePaths); } } @@ -271,7 +273,7 @@ void ModuleLoader::handleProject(ModuleLoaderResult *loadResult, Item *item, handleProduct(&projectContext, subItem); } else if (subItem->typeName() == QLatin1String("Project")) { copyProperties(item, subItem); - handleProject(loadResult, subItem, + handleProject(loadResult, subItem, buildDirectory, QSet(referencedFilePaths) << absReferencePath); } else { throw ErrorInfo(Tr::tr("The top-level item of a file in a \"references\" list must be " @@ -294,9 +296,7 @@ void ModuleLoader::handleProduct(ProjectContext *projectContext, Item *item) if (m_logger.traceEnabled()) m_logger.qbsTrace() << "[MODLDR] handleProduct " << item->file()->filePath(); - item->setProperty(QLatin1String("sourceDirectory"), - VariantValue::create(QFileInfo(item->file()->filePath()).absolutePath())); - + initProductProperties(projectContext, item); ProductContext productContext; productContext.project = projectContext; bool extraSearchPathsSet = false; @@ -339,6 +339,23 @@ void ModuleLoader::handleProduct(ProjectContext *projectContext, Item *item) m_reader->popExtraSearchPaths(); } +void ModuleLoader::initProductProperties(const ProjectContext *project, Item *item) +{ + QString productName = m_evaluator->stringValue(item, QLatin1String("name")); + if (productName.isEmpty()) { + productName = FileInfo::completeBaseName(item->file()->filePath()); + item->setProperty(QLatin1String("name"), VariantValue::create(productName)); + } + + item->setProperty(QLatin1String("buildDirectory"), + VariantValue::create( + FileInfo::resolvePath(project->buildDirectory, productName))); + + item->setProperty(QLatin1String("sourceDirectory"), + VariantValue::create( + QFileInfo(item->file()->filePath()).absolutePath())); +} + void ModuleLoader::handleSubProject(ModuleLoader::ProjectContext *projectContext, Item *item, const QSet &referencedFilePaths) { @@ -387,7 +404,7 @@ void ModuleLoader::handleSubProject(ModuleLoader::ProjectContext *projectContext Item::addChild(item, loadedItem); item->setScope(projectContext->scope); - handleProject(projectContext->result, loadedItem, + handleProject(projectContext->result, loadedItem, projectContext->buildDirectory, QSet(referencedFilePaths) << subProjectFilePath); } diff --git a/src/lib/corelib/language/moduleloader.h b/src/lib/corelib/language/moduleloader.h index c368dbf40..5df1747fc 100644 --- a/src/lib/corelib/language/moduleloader.h +++ b/src/lib/corelib/language/moduleloader.h @@ -123,6 +123,7 @@ private: { public: ModuleLoaderResult *result; + QString buildDirectory; QString localModuleSearchPath; }; @@ -145,9 +146,10 @@ private: typedef QPair ProductDependencyResult; typedef QList ProductDependencyResults; - void handleProject(ModuleLoaderResult *loadResult, Item *item, + void handleProject(ModuleLoaderResult *loadResult, Item *item, const QString &buildDirectory, const QSet &referencedFilePaths); void handleProduct(ProjectContext *projectContext, Item *item); + void initProductProperties(const ProjectContext *project, Item *item); void handleSubProject(ProjectContext *projectContext, Item *item, const QSet &referencedFilePaths); void createAdditionalModuleInstancesInProduct(ProductContext *productContext); diff --git a/src/lib/corelib/language/projectresolver.cpp b/src/lib/corelib/language/projectresolver.cpp index b559454d5..346658bf2 100644 --- a/src/lib/corelib/language/projectresolver.cpp +++ b/src/lib/corelib/language/projectresolver.cpp @@ -280,13 +280,10 @@ void ProjectResolver::resolveProduct(Item *item, ProjectContext *projectContext) projectContext->project->products += product; productContext.product = product; product->name = m_evaluator->stringValue(item, QLatin1String("name")); - if (product->name.isEmpty()) { - product->name = FileInfo::completeBaseName(item->file()->filePath()); - item->setProperty(QLatin1String("name"), VariantValue::create(product->name)); - } m_logger.qbsTrace() << "[PR] resolveProduct " << product->name; - item->setProperty(QLatin1String("buildDirectory"), - VariantValue::create(product->buildDirectory())); + + // product->buildDirectory() isn't valid yet, because the productProperties map is not ready. + productContext.buildDirectory = m_evaluator->stringValue(item, QLatin1String("buildDirectory")); if (std::find_if(item->modules().begin(), item->modules().end(), ModuleNameEquals(product->name)) != item->modules().end()) { @@ -314,8 +311,9 @@ void ProjectResolver::resolveProduct(Item *item, ProjectContext *projectContext) product->sourceDirectory = m_evaluator->stringValue(item, QLatin1String("sourceDirectory")); const QString destDirKey = QLatin1String("destinationDirectory"); product->destinationDirectory = m_evaluator->stringValue(item, destDirKey); + if (product->destinationDirectory.isEmpty()) { - product->destinationDirectory = product->buildDirectory(); + product->destinationDirectory = productContext.buildDirectory; } else { product->destinationDirectory = FileInfo::resolvePath( product->topLevelProject()->buildDirectory, @@ -747,7 +745,7 @@ void ProjectResolver::resolveTransformer(Item *item, ProjectContext *projectCont if (Q_UNLIKELY(fileName.isEmpty())) throw ErrorInfo(Tr::tr("Artifact fileName must not be empty.")); artifact->absoluteFilePath - = FileInfo::resolvePath(m_productContext->product->buildDirectory(), fileName); + = FileInfo::resolvePath(m_productContext->buildDirectory, fileName); artifact->fileTags = m_evaluator->fileTagsValue(child, QLatin1String("fileTags")); if (artifact->fileTags.isEmpty()) artifact->fileTags.insert(unknownFileTag()); diff --git a/src/lib/corelib/language/projectresolver.h b/src/lib/corelib/language/projectresolver.h index 636fd7299..fa6569cd5 100644 --- a/src/lib/corelib/language/projectresolver.h +++ b/src/lib/corelib/language/projectresolver.h @@ -77,6 +77,7 @@ private: struct ProductContext { ResolvedProductPtr product; + QString buildDirectory; FileTags additionalFileTags; Item *item; }; diff --git a/src/lib/corelib/language/testdata/profilevaluesandoverriddenvalues.qbs b/src/lib/corelib/language/testdata/profilevaluesandoverriddenvalues.qbs index cc1b7b2a2..0ba76c6f6 100644 --- a/src/lib/corelib/language/testdata/profilevaluesandoverriddenvalues.qbs +++ b/src/lib/corelib/language/testdata/profilevaluesandoverriddenvalues.qbs @@ -2,14 +2,15 @@ import qbs 1.0 Project { Application { - name: { + name: "product1" + type: { if (!(dummy.cFlags instanceof Array)) throw new Error("dummy.cFlags: Array type expected."); if (!(dummy.cxxFlags instanceof Array)) throw new Error("dummy.cxxFlags: Array type expected."); if (!(dummy.defines instanceof Array)) throw new Error("dummy.defines: Array type expected."); - return "product1"; + return "application"; } Depends { name: "dummy" } // dummy.cxxFlags is set via profile and is not overridden -- cgit v1.2.3