aboutsummaryrefslogtreecommitdiffstats
path: root/share
diff options
context:
space:
mode:
authorIvan Komissarov <abbapoh@gmail.com>2021-04-24 02:20:06 +0300
committerIvan Komissarov <abbapoh@gmail.com>2021-04-24 02:20:06 +0300
commita8bbaf016dc3092f6f6ad0c4a333e595da665983 (patch)
tree6b1b74bbca7850ed75da01cba5a72618f3cfa94b /share
parent001bf31623c02ba8249dd066777d014d546eb7f9 (diff)
parent2f6eecdc96fcd693cecef8011d8f9500c7872fc7 (diff)
Merge branch '1.19' into master
Diffstat (limited to 'share')
-rw-r--r--share/CMakeLists.txt5
-rw-r--r--share/qbs/imports/qbs/Probes/ClangClProbe.qbs17
-rw-r--r--share/qbs/imports/qbs/Probes/MsvcProbe.qbs5
-rw-r--r--share/qbs/module-providers/Qt/templates/android_support.qbs80
-rw-r--r--share/qbs/module-providers/Qt/templates/qml.js25
-rw-r--r--share/qbs/module-providers/Qt/templates/qml.qbs2
-rw-r--r--share/qbs/modules/Android/sdk/utils.js3
-rw-r--r--share/qbs/modules/codesign/CodeSignModule.qbs6
-rw-r--r--share/qbs/modules/codesign/apple.qbs16
-rw-r--r--share/qbs/modules/codesign/codesign.js119
-rw-r--r--share/qbs/modules/codesign/signtool.qbs94
-rw-r--r--share/qbs/modules/cpp/CppModule.qbs2
-rw-r--r--share/qbs/modules/cpp/iar.js12
-rw-r--r--share/qbs/modules/cpp/iar.qbs6
-rw-r--r--share/qbs/modules/cpp/keil.js92
-rw-r--r--share/qbs/modules/cpp/keil.qbs6
-rw-r--r--share/qbs/modules/cpp/msvc.js7
-rw-r--r--share/qbs/modules/cpp/sdcc.js156
-rw-r--r--share/qbs/modules/cpp/sdcc.qbs5
-rw-r--r--share/qbs/modules/cpp/windows-clang-cl.qbs1
-rw-r--r--share/qbs/modules/cpp/windows-msvc-base.qbs29
-rw-r--r--share/qbs/modules/cpp/windows-msvc.qbs1
22 files changed, 575 insertions, 114 deletions
diff --git a/share/CMakeLists.txt b/share/CMakeLists.txt
index f607e0a85..bde65d450 100644
--- a/share/CMakeLists.txt
+++ b/share/CMakeLists.txt
@@ -36,8 +36,7 @@ get_update_path_command(UPDATE_PATH_COMMAND)
get_target_property(_QBS_OUTPUT_DIR qbs RUNTIME_OUTPUT_DIRECTORY)
add_custom_target(
BuildQbsResources ALL
- COMMAND ${UPDATE_PATH_COMMAND}
- COMMAND ${_QBS_OUTPUT_DIR}/qbs
+ COMMAND ${CMAKE_COMMAND} -E env "${UPDATE_PATH_COMMAND}" ${_QBS_OUTPUT_DIR}/qbs
resolve
--settings-dir ${PROJECT_BINARY_DIR}/settings
-f ${PROJECT_SOURCE_DIR}/qbs.qbs
@@ -47,7 +46,7 @@ add_custom_target(
project.withCode:false
project.withDocumentation:false
profile:none
- COMMAND ${_QBS_OUTPUT_DIR}/qbs
+ COMMAND ${CMAKE_COMMAND} -E env "${UPDATE_PATH_COMMAND}" ${_QBS_OUTPUT_DIR}/qbs
build
--settings-dir ${PROJECT_BINARY_DIR}/settings
-f ${PROJECT_SOURCE_DIR}/qbs.qbs
diff --git a/share/qbs/imports/qbs/Probes/ClangClProbe.qbs b/share/qbs/imports/qbs/Probes/ClangClProbe.qbs
index 8205e92fa..658da8a9f 100644
--- a/share/qbs/imports/qbs/Probes/ClangClProbe.qbs
+++ b/share/qbs/imports/qbs/Probes/ClangClProbe.qbs
@@ -42,6 +42,7 @@ PathProbe {
property string preferredArchitecture
property string _nullDevice: qbs.nullDevice
property string _pathListSeparator: qbs.pathListSeparator
+ property string winSdkVersion
// Outputs
property int versionMajor
@@ -58,9 +59,21 @@ PathProbe {
languages = ["c"];
var info = languages.contains("c")
- ? Utilities.clangClCompilerInfo(compilerFilePath, preferredArchitecture, vcvarsallFilePath, "c") : {};
+ ? Utilities.clangClCompilerInfo(
+ compilerFilePath,
+ preferredArchitecture,
+ vcvarsallFilePath,
+ "c",
+ winSdkVersion)
+ : {};
var infoCpp = languages.contains("cpp")
- ? Utilities.clangClCompilerInfo(compilerFilePath, preferredArchitecture, vcvarsallFilePath, "cpp") : {};
+ ? Utilities.clangClCompilerInfo(
+ compilerFilePath,
+ preferredArchitecture,
+ vcvarsallFilePath,
+ "cpp",
+ winSdkVersion)
+ : {};
found = (!languages.contains("c") ||
(!!info && !!info.macros && !!info.buildEnvironment))
&& (!languages.contains("cpp") ||
diff --git a/share/qbs/imports/qbs/Probes/MsvcProbe.qbs b/share/qbs/imports/qbs/Probes/MsvcProbe.qbs
index 2d5faecdd..d3624e010 100644
--- a/share/qbs/imports/qbs/Probes/MsvcProbe.qbs
+++ b/share/qbs/imports/qbs/Probes/MsvcProbe.qbs
@@ -38,6 +38,7 @@ PathProbe {
property string compilerFilePath
property stringList enableDefinesByLanguage
property string preferredArchitecture
+ property string winSdkVersion
// Outputs
property string architecture
@@ -54,9 +55,9 @@ PathProbe {
languages = ["c"];
var info = languages.contains("c")
- ? Utilities.msvcCompilerInfo(compilerFilePath, "c") : {};
+ ? Utilities.msvcCompilerInfo(compilerFilePath, "c", winSdkVersion) : {};
var infoCpp = languages.contains("cpp")
- ? Utilities.msvcCompilerInfo(compilerFilePath, "cpp") : {};
+ ? Utilities.msvcCompilerInfo(compilerFilePath, "cpp", winSdkVersion) : {};
found = (!languages.contains("c") ||
(!!info && !!info.macros && !!info.buildEnvironment))
&& (!languages.contains("cpp") ||
diff --git a/share/qbs/module-providers/Qt/templates/android_support.qbs b/share/qbs/module-providers/Qt/templates/android_support.qbs
index 87c980448..68a29bb95 100644
--- a/share/qbs/module-providers/Qt/templates/android_support.qbs
+++ b/share/qbs/module-providers/Qt/templates/android_support.qbs
@@ -4,6 +4,7 @@ import qbs.ModUtils
import qbs.TextFile
import qbs.Utilities
import qbs.Process
+import qbs.Xml
Module {
version: @version@
@@ -35,6 +36,10 @@ Module {
property bool _multiAbi: Utilities.versionCompare(version, "5.14") >= 0
+ // QTBUG-87288: correct QtNetwork jar dependencies for 5.15.0 < Qt < 5.15.3
+ property bool _correctQtNetworkDependencies: Utilities.versionCompare(version, "5.15.0") > 0 &&
+ Utilities.versionCompare(version, "5.15.3") < 0
+
Depends { name: "Android.sdk"; condition: _enableSdkSupport }
Depends { name: "Android.ndk"; condition: _enableNdkSupport }
Depends { name: "java"; condition: _enableSdkSupport }
@@ -355,8 +360,6 @@ Module {
var moveCmd = new JavaScriptCommand();
moveCmd.description = "processing androiddeployqt outout";
moveCmd.sourceCode = function() {
- File.move(product.Qt.android_support._deployQtOutDir + "/AndroidManifest.xml",
- outputs["android.manifest_final"][0].filePath);
var libsDir = product.Qt.android_support._deployQtOutDir + "/libs";
var libDir = product.Android.sdk.packageContentsDir + "/lib";
var listFilePath = outputs["android.deployqt_list"][0].filePath;
@@ -400,7 +403,78 @@ Module {
File.remove(oldLibs[i]);
}
};
- return [copyCmd, androidDeployQtCmd, moveCmd];
+
+ var correctingCmd = new JavaScriptCommand();
+ if (product.Qt.android_support._correctQtNetworkDependencies) {
+ correctingCmd.description = "correcting network jar dependency";
+ correctingCmd.sourceCode = function() {
+ var findNetworkLib = function() {
+ var libsDir = product.Android.sdk.packageContentsDir + "/lib";
+ var dirList = File.directoryEntries(libsDir, File.Dirs |
+ File.NoDotAndDotDot);
+ for (var i = 0; i < dirList.length; ++i) {
+ var archDir = FileInfo.joinPaths(libsDir, dirList[i]);
+ var fileList = File.directoryEntries(archDir, File.Files);
+ if (fileList) {
+ for (var j = 0; j < fileList.length; ++j) {
+ if (fileList[j].contains("libQt5Network")) {
+ return true;
+ }
+ }
+ }
+ }
+ return false;
+ }
+
+ if (findNetworkLib()) {
+ var manifestData = new Xml.DomDocument();
+ var manifestFilePath = product.Qt.android_support._deployQtOutDir +
+ "/AndroidManifest.xml"
+ manifestData.load(manifestFilePath);
+
+ var rootElem = manifestData.documentElement();
+ if (!rootElem || !rootElem.isElement() || rootElem.tagName() != "manifest")
+ throw "No manifest tag found in '" + manifestFilePath + "'.";
+ var appElem = rootElem.firstChild("application");
+ if (!appElem || !appElem.isElement() || appElem.tagName() != "application")
+ throw "No application tag found in '" + manifestFilePath + "'.";
+ var activityElem = appElem.firstChild("activity");
+ if (!activityElem || !activityElem.isElement() ||
+ activityElem.tagName() != "activity")
+ throw "No activity tag found in '" + manifestFilePath + "'.";
+ var metaDataElem = activityElem.firstChild("meta-data");
+ while (metaDataElem && metaDataElem.isElement()) {
+ if (metaDataElem.attribute("android:name") ==
+ "android.app.load_local_jars" ) {
+ var value = metaDataElem.attribute("android:value");
+ var fileName = "QtAndroidNetwork.jar";
+ metaDataElem.setAttribute("android:value", value + ":jar/" +
+ fileName);
+ var jarFilePath = FileInfo.joinPaths(
+ product.Qt.android_support._qtInstallDir, "jar",
+ fileName);
+ var targetFilePath = FileInfo.joinPaths(product.java.classFilesDir,
+ fileName);
+ File.copy(jarFilePath, targetFilePath);
+ break;
+ }
+ metaDataElem = metaDataElem.nextSibling("meta-data");
+ }
+ manifestData.save(outputs["android.manifest_final"][0].filePath, 4);
+ } else {
+ File.move(product.Qt.android_support._deployQtOutDir + "/AndroidManifest.xml",
+ outputs["android.manifest_final"][0].filePath);
+ }
+ };
+ } else {
+ correctingCmd.description = "copying manifest";
+ correctingCmd.sourceCode = function() {
+ File.move(product.Qt.android_support._deployQtOutDir + "/AndroidManifest.xml",
+ outputs["android.manifest_final"][0].filePath);
+ }
+ }
+
+ return [copyCmd, androidDeployQtCmd, moveCmd, correctingCmd];
}
}
diff --git a/share/qbs/module-providers/Qt/templates/qml.js b/share/qbs/module-providers/Qt/templates/qml.js
index df69034fe..e48c9230e 100644
--- a/share/qbs/module-providers/Qt/templates/qml.js
+++ b/share/qbs/module-providers/Qt/templates/qml.js
@@ -3,14 +3,31 @@ var FileInfo = require("qbs.FileInfo");
var Process = require("qbs.Process");
var TextFile = require("qbs.TextFile");
-function scannerData(scannerFilePath, qmlFiles, qmlPath)
+function scannerData(scannerFilePath, qmlFiles, qmlPath, targetOS)
{
var p;
try {
p = new Process();
- p.exec(scannerFilePath, ["-qmlFiles"].concat(qmlFiles).concat(["-importPath", qmlPath]),
- true);
- return JSON.parse(p.readStdOut());
+ if (!targetOS.contains("windows")) {
+ p.exec(scannerFilePath, ["-qmlFiles"].concat(qmlFiles).concat(["-importPath", qmlPath]),
+ true);
+ return JSON.parse(p.readStdOut());
+ }
+ var data = [];
+ var nextFileIndex = 0;
+ while (nextFileIndex < qmlFiles.length) {
+ var currentFileList = [];
+ var currentFileListStringLength = 0;
+ while (nextFileIndex < qmlFiles.length && currentFileListStringLength < 30000) {
+ var currentFile = qmlFiles[nextFileIndex++];
+ currentFileList.push(currentFile);
+ currentFileListStringLength += currentFile.length;
+ }
+ p.exec(scannerFilePath, ["-qmlFiles"].concat(currentFileList)
+ .concat(["-importPath", qmlPath]), true);
+ data = data.concat(JSON.parse(p.readStdOut()));
+ }
+ return data;
} finally {
if (p)
p.close();
diff --git a/share/qbs/module-providers/Qt/templates/qml.qbs b/share/qbs/module-providers/Qt/templates/qml.qbs
index f608ba4dd..af7b0fb5f 100644
--- a/share/qbs/module-providers/Qt/templates/qml.qbs
+++ b/share/qbs/module-providers/Qt/templates/qml.qbs
@@ -144,7 +144,7 @@ QtModule {
qmlInputs = [];
var scannerData = Qml.scannerData(product.Qt.qml.qmlImportScannerFilePath,
qmlInputs.map(function(inp) { return inp.filePath; }),
- product.Qt.qml.qmlPath);
+ product.Qt.qml.qmlPath, product.qbs.targetOS);
var cppFile;
var listFile;
try {
diff --git a/share/qbs/modules/Android/sdk/utils.js b/share/qbs/modules/Android/sdk/utils.js
index 9511ae9de..264ad2da7 100644
--- a/share/qbs/modules/Android/sdk/utils.js
+++ b/share/qbs/modules/Android/sdk/utils.js
@@ -174,7 +174,8 @@ function prepareAapt2CompileResource(project, product, inputs, outputs, input, o
throw "Cannot create directory '" + FileInfo.toNativeSeparators(compilesResourcesDir) +
"'.";
}
- var args = ["compile", input.filePath, "-o", compilesResourcesDir];
+ var args = ["compile", FileInfo.toNativeSeparators(input.filePath),
+ "-o", FileInfo.toNativeSeparators(compilesResourcesDir)];
var cmd = new Command(product.Android.sdk.aaptFilePath, args);
var outputFileName = generateAapt2ResourceFileName(input.filePath);
cmd.description = "compiling resource " + input.fileName + " into " + outputFileName;
diff --git a/share/qbs/modules/codesign/CodeSignModule.qbs b/share/qbs/modules/codesign/CodeSignModule.qbs
index 1951ec374..2115baebf 100644
--- a/share/qbs/modules/codesign/CodeSignModule.qbs
+++ b/share/qbs/modules/codesign/CodeSignModule.qbs
@@ -43,5 +43,11 @@ Module {
property string codesignPath: codesignName
property stringList codesignFlags
+ property string signingTimestamp
+ PropertyOptions {
+ name: "signingTimestamp"
+ description: "URL of the RFC 3161 time stamp server."
+ }
+
property bool _canSignArtifacts: false // whether can sign individual actifacts
}
diff --git a/share/qbs/modules/codesign/apple.qbs b/share/qbs/modules/codesign/apple.qbs
index 06f07d72d..565d29080 100644
--- a/share/qbs/modules/codesign/apple.qbs
+++ b/share/qbs/modules/codesign/apple.qbs
@@ -96,7 +96,7 @@ CodeSignModule {
}
}
- property string signingTimestamp: "none"
+ signingTimestamp: "none"
property string provisioningProfile
PropertyOptions {
@@ -125,7 +125,7 @@ CodeSignModule {
var identities = CodeSign.findSigningIdentities(signingIdentity, teamIdentifier);
if (identities && Object.keys(identities).length > 1) {
throw "Multiple codesigning identities (i.e. certificate and private key pairs) " +
- "matching “" + signingIdentity + "” were found." +
+ "matching '" + signingIdentity + "' were found." +
CodeSign.humanReadableIdentitySummary(identities);
}
@@ -240,17 +240,17 @@ CodeSignModule {
}
});
} else if (uuid) {
- throw "Your build settings specify a provisioning profile with the UUID “"
- + uuid + "”, however, no such provisioning profile was found.";
+ throw "Your build settings specify a provisioning profile with the UUID '"
+ + uuid + "', however, no such provisioning profile was found.";
} else if (product._provisioningProfileRequired) {
var hasProfiles = !!((inputs["codesign.provisioningprofile"] || []).length);
var teamIdentifier = product.teamIdentifier;
var codeSignIdentity = product.signingIdentity;
if (hasProfiles) {
if (codeSignIdentity) {
- console.warn("No provisioning profiles matching the bundle identifier “"
+ console.warn("No provisioning profiles matching the bundle identifier '"
+ product.bundle.identifier
- + "” were found.");
+ + "' were found.");
} else {
console.warn("No provisioning profiles matching an applicable signing "
+ "identity were found.");
@@ -260,13 +260,13 @@ CodeSignModule {
if (teamIdentifier) {
console.warn("No provisioning profiles with a valid signing identity "
+ "(i.e. certificate and private key pair) matching the "
- + "team ID “" + teamIdentifier + "” were found.")
+ + "team ID '" + teamIdentifier + "' were found.")
} else {
console.warn("No provisioning profiles with a valid signing identity "
+ "(i.e. certificate and private key pair) were found.");
}
} else {
- console.warn("No non–expired provisioning profiles were found.");
+ console.warn("No non-expired provisioning profiles were found.");
}
}
}
diff --git a/share/qbs/modules/codesign/codesign.js b/share/qbs/modules/codesign/codesign.js
index bf7e95224..5aa303c9c 100644
--- a/share/qbs/modules/codesign/codesign.js
+++ b/share/qbs/modules/codesign/codesign.js
@@ -202,6 +202,75 @@ function findBestProvisioningProfile(product, files) {
}
}
+/**
+ * Finds out the search paths for the `signtool.exe` utility supplied with
+ * the Windows SDK's.
+ */
+function findBestSignToolSearchPaths(arch) {
+ var searchPaths = [];
+ var keys = [
+ "HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Microsoft SDKs\\Windows",
+ "HKEY_LOCAL_MACHINE\\SOFTWARE\\Wow6432Node\\Microsoft\\Microsoft SDKs\\Windows"
+ ];
+ for (var keyIndex = 0; keyIndex < keys.length; ++keyIndex) {
+ var re = /^v([0-9]+)\.([0-9]+)$/;
+ var groups = Utilities.nativeSettingGroups(keys[keyIndex]).filter(function(version) {
+ return version.match(re);
+ });
+
+ groups.sort(function(a, b) {
+ return Utilities.versionCompare(b.substring(1), a.substring(1));
+ });
+
+ function addSearchPath(searchPath) {
+ if (File.exists(searchPath) && !searchPaths.contains(searchPath)) {
+ searchPaths.push(searchPath);
+ return true;
+ }
+ return false;
+ }
+
+ for (var groupIndex = 0; groupIndex < groups.length; ++groupIndex) {
+ var fullKey = keys[keyIndex] + "\\" + groups[groupIndex];
+ var fullVersion = Utilities.getNativeSetting(fullKey, "ProductVersion");
+ if (fullVersion) {
+ var installRoot = FileInfo.cleanPath(
+ Utilities.getNativeSetting(fullKey, "InstallationFolder"));
+ if (installRoot) {
+ // Try to add the architecture-independent path at first.
+ var searchPath = FileInfo.joinPaths(installRoot, "App Certification Kit");
+ if (!addSearchPath(searchPath)) {
+ // Try to add the architecture-dependent paths at second.
+ var binSearchPath = FileInfo.joinPaths(installRoot, "bin/" + fullVersion);
+ if (!File.exists(binSearchPath)) {
+ binSearchPath += ".0";
+ if (!File.exists(binSearchPath))
+ continue;
+ }
+
+ function kitsArchitectureSubDirectory(arch) {
+ if (arch === "x86")
+ return "x86";
+ else if (arch === "x86_64")
+ return "x64";
+ else if (arch.startsWith("arm64"))
+ return "arm64";
+ else if (arch.startsWith("arm"))
+ return "arm";
+ }
+
+ var archDir = kitsArchitectureSubDirectory(arch);
+ searchPath = FileInfo.joinPaths(binSearchPath, archDir);
+ addSearchPath(searchPath);
+ }
+ }
+ }
+ }
+ }
+
+ return searchPaths;
+}
+
function prepareSign(project, product, inputs, outputs, input, output) {
var cmd, cmds = [];
@@ -243,10 +312,10 @@ function prepareSign(project, product, inputs, outputs, input, output) {
args.push("--force");
args.push("--sign", actualSigningIdentity.SHA1);
- // If signingTimestamp is undefined, do not specify the flag at all -
+ // If signingTimestamp is undefined or empty, do not specify the flag at all -
// this uses the system-specific default behavior
var signingTimestamp = product.codesign.signingTimestamp;
- if (signingTimestamp !== undefined) {
+ if (signingTimestamp) {
// If signingTimestamp is an empty string, specify the flag but do
// not specify a value - this uses a default Apple-provided server
var flag = "--timestamp";
@@ -349,3 +418,49 @@ function createDebugKeyStoreCommandString(keytoolFilePath, keystoreFilePath, key
"CN=Android Debug,O=Android,C=US"];
return Process.shellQuote(keytoolFilePath, args);
}
+
+function prepareSigntool(project, product, inputs, outputs, input, output) {
+ var cmd, cmds = [];
+
+ if (!product.codesign.enableCodeSigning)
+ return cmds;
+
+ var args = ["sign"].concat(product.codesign.codesignFlags || []);
+
+ var subjectName = product.codesign.subjectName;
+ if (subjectName)
+ args.push("/n", subjectName);
+
+ var rootSubjectName = product.codesign.rootSubjectName;
+ if (rootSubjectName)
+ args.push("/r", rootSubjectName);
+
+ var hashAlgorithm = product.codesign.hashAlgorithm;
+ if (hashAlgorithm)
+ args.push("/fd", hashAlgorithm);
+
+ var signingTimestamp = product.codesign.signingTimestamp;
+ if (signingTimestamp)
+ args.push("/tr", signingTimestamp);
+
+ var certificatePath = product.codesign.certificatePath;
+ if (certificatePath)
+ args.push("/f", certificatePath);
+
+ var certificatePassword = product.codesign.certificatePassword;
+ if (certificatePassword)
+ args.push("/p", certificatePassword);
+
+ var crossCertificatePath = product.codesign.crossCertificatePath;
+ if (crossCertificatePath)
+ args.push("/ac", crossCertificatePath);
+
+ var outputArtifact = outputs["codesign.signed_artifact"][0];
+ args.push(outputArtifact.filePath);
+
+ cmd = new Command(product.codesign.codesignPath, args);
+ cmd.description = "signing " + outputArtifact.fileName;
+ cmd.highlight = "linker";
+ cmds.push(cmd);
+ return cmds;
+}
diff --git a/share/qbs/modules/codesign/signtool.qbs b/share/qbs/modules/codesign/signtool.qbs
new file mode 100644
index 000000000..13933c6f6
--- /dev/null
+++ b/share/qbs/modules/codesign/signtool.qbs
@@ -0,0 +1,94 @@
+/****************************************************************************
+**
+** Copyright (C) 2021 Denis Shienkov <denis.shienkov@gmail.com>
+** Contact: http://www.qt.io/licensing
+**
+** This file is part of Qbs.
+**
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms and
+** conditions see http://www.qt.io/terms-conditions. For further information
+** use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+****************************************************************************/
+
+import qbs
+import qbs.File
+import qbs.ModUtils
+import qbs.Probes
+import "codesign.js" as CODESIGN
+
+CodeSignModule {
+ condition: qbs.targetOS.contains("windows") && qbs.hostOS.contains("windows")
+
+ _canSignArtifacts: true
+
+ Probes.BinaryProbe {
+ id: signtoolProbe
+ names: [codesignName]
+ searchPaths: CODESIGN.findBestSignToolSearchPaths(qbs.hostArchitecture)
+ }
+
+ codesignName: "signtool"
+ codesignPath: signtoolProbe.filePath
+
+ property string subjectName
+ PropertyOptions {
+ name: "subjectName"
+ description: "Name of the subject of the signing certificate."
+ }
+
+ property string rootSubjectName
+ PropertyOptions {
+ name: "rootSubjectName"
+ description: "Name of the subject of the root certificate that the signing " +
+ "certificate must chain to."
+ }
+
+ property string hashAlgorithm
+ PropertyOptions {
+ name: "hashAlgorithm"
+ description: "Name of the hash algorithm used on the signing certificate."
+ allowedValues: ["sha1", "sha256", "sha384", "sha512"]
+ }
+
+ property path certificatePath
+ PropertyOptions {
+ name: "certificatePath"
+ description: "Path to the signing certificate PFX file."
+ }
+
+ property path certificatePassword
+ PropertyOptions {
+ name: "certificatePassword"
+ description: "Password to use when opening a certificate PFX file."
+ }
+
+ property path crossCertificatePath
+ PropertyOptions {
+ name: "crossCertificatePath"
+ description: "Path to the additional certificate CER file."
+ }
+
+ validate: {
+ if (enableCodeSigning && !File.exists(codesignPath)) {
+ throw ModUtils.ModuleError("Could not find 'signtool' utility");
+ }
+ }
+}
diff --git a/share/qbs/modules/cpp/CppModule.qbs b/share/qbs/modules/cpp/CppModule.qbs
index 761e8be85..39077bec8 100644
--- a/share/qbs/modules/cpp/CppModule.qbs
+++ b/share/qbs/modules/cpp/CppModule.qbs
@@ -188,6 +188,8 @@ Module {
property string dynamicLibraryImportSuffix: ".lib"
property string objectSuffix: ".o"
property string linkerMapSuffix: ".map"
+ property string compilerListingSuffix: ".lst"
+ property string assemblerListingSuffix: ".lst"
property bool createSymlinks: true
property stringList dynamicLibraries // list of names, will be linked with -lname
property stringList staticLibraries // list of static library files
diff --git a/share/qbs/modules/cpp/iar.js b/share/qbs/modules/cpp/iar.js
index a1f1a9a88..416de7ee2 100644
--- a/share/qbs/modules/cpp/iar.js
+++ b/share/qbs/modules/cpp/iar.js
@@ -612,18 +612,24 @@ function collectLibraryDependencies(product) {
return result;
}
-function compilerOutputArtifacts(input, useListing) {
+function compilerOutputArtifacts(input, isCompilerArtifacts) {
var artifacts = [];
artifacts.push({
fileTags: ["obj"],
filePath: Utilities.getHash(input.baseDir) + "/"
+ input.fileName + input.cpp.objectSuffix
});
- if (useListing) {
+ if (isCompilerArtifacts && input.cpp.generateCompilerListingFiles) {
artifacts.push({
fileTags: ["lst"],
filePath: Utilities.getHash(input.baseDir) + "/"
- + input.fileName + ".lst"
+ + input.fileName + input.cpp.compilerListingSuffix
+ });
+ } else if (!isCompilerArtifacts && input.cpp.generateAssemblerListingFiles) {
+ artifacts.push({
+ fileTags: ["lst"],
+ filePath: Utilities.getHash(input.baseDir) + "/"
+ + input.fileName + input.cpp.assemblerListingSuffix
});
}
return artifacts;
diff --git a/share/qbs/modules/cpp/iar.qbs b/share/qbs/modules/cpp/iar.qbs
index 6c00f8f36..9709695c1 100644
--- a/share/qbs/modules/cpp/iar.qbs
+++ b/share/qbs/modules/cpp/iar.qbs
@@ -99,8 +99,7 @@ CppModule {
id: assembler
inputs: ["asm"]
outputFileTags: ["obj", "lst"]
- outputArtifacts: IAR.compilerOutputArtifacts(
- input, input.cpp.generateAssemblerListingFiles)
+ outputArtifacts: IAR.compilerOutputArtifacts(input, false)
prepare: IAR.prepareAssembler.apply(IAR, arguments)
}
@@ -114,8 +113,7 @@ CppModule {
inputs: ["cpp", "c"]
auxiliaryInputs: ["hpp"]
outputFileTags: ["obj", "lst"]
- outputArtifacts: IAR.compilerOutputArtifacts(
- input, input.cpp.generateCompilerListingFiles)
+ outputArtifacts: IAR.compilerOutputArtifacts(input, true)
prepare: IAR.prepareCompiler.apply(IAR, arguments)
}
diff --git a/share/qbs/modules/cpp/keil.js b/share/qbs/modules/cpp/keil.js
index 567b0ddd3..27e4e12d7 100644
--- a/share/qbs/modules/cpp/keil.js
+++ b/share/qbs/modules/cpp/keil.js
@@ -582,19 +582,24 @@ function filterC166Output(output) {
return filteredLines.join('\n');
};
-function compilerOutputArtifacts(input, useListing) {
+function compilerOutputArtifacts(input, isCompilerArtifacts) {
var artifacts = [];
artifacts.push({
fileTags: ["obj"],
filePath: Utilities.getHash(input.baseDir) + "/"
+ input.fileName + input.cpp.objectSuffix
});
- if (useListing) {
+ if (isCompilerArtifacts && input.cpp.generateCompilerListingFiles) {
artifacts.push({
fileTags: ["lst"],
filePath: Utilities.getHash(input.baseDir) + "/"
- + (isArmCCCompiler(input.cpp.compilerPath) ? input.baseName : input.fileName)
- + ".lst"
+ + input.fileName + input.cpp.compilerListingSuffix
+ });
+ } else if (!isCompilerArtifacts && input.cpp.generateAssemblerListingFiles) {
+ artifacts.push({
+ fileTags: ["lst"],
+ filePath: Utilities.getHash(input.baseDir) + "/"
+ + input.fileName + input.cpp.assemblerListingSuffix
});
}
return artifacts;
@@ -970,24 +975,37 @@ function disassemblerFlags(project, product, input, outputs, explicitlyDependsOn
function linkerFlags(project, product, inputs, outputs) {
var args = [];
+ // Library paths.
+ var libraryPaths = product.cpp.libraryPaths;
+
var architecture = product.qbs.architecture;
if (isMcsArchitecture(architecture) || isC166Architecture(architecture)) {
- // Note: The C51/256/166 linker does not distinguish an object files and
+ // Note: The C51, C251, or C166 linker does not distinguish an object files and
// a libraries, it interpret all this stuff as an input objects,
// so, we need to pass it together in one string.
-
var allObjectPaths = [];
- function addObjectPath(obj) {
- allObjectPaths.push(obj.filePath);
- }
// Inputs.
if (inputs.obj)
- inputs.obj.map(function(obj) { addObjectPath(obj) });
+ inputs.obj.map(function(obj) { allObjectPaths.push(obj.filePath) });
// Library dependencies.
var libraryObjects = collectLibraryDependencies(product);
- libraryObjects.forEach(function(dep) { addObjectPath(dep); })
+ allObjectPaths = allObjectPaths.concat(libraryObjects.map(function(lib) {
+ // Semi-intelligent handling the library paths.
+ // We need to add the full path prefix to the library file if this
+ // file is not absolute or not relative. Reason is that the C51, C251,
+ // and C166 linkers does not support the library paths.
+ var filePath = lib.filePath;
+ if (FileInfo.isAbsolutePath(filePath))
+ return filePath;
+ for (var i = 0; i < libraryPaths.length; ++i) {
+ var fullPath = FileInfo.joinPaths(libraryPaths[i], filePath);
+ if (File.exists(fullPath))
+ return fullPath;
+ }
+ return filePath;
+ }));
// Add all input objects as arguments (application and library object files).
if (allObjectPaths.length > 0)
@@ -1009,8 +1027,6 @@ function linkerFlags(project, product, inputs, outputs) {
// Output.
args.push("--output", outputs.application[0].filePath);
- // Library paths.
- var libraryPaths = product.cpp.libraryPaths;
if (libraryPaths)
args.push("--userlibpath=" + libraryPaths.join(","));
@@ -1084,6 +1100,38 @@ function archiverFlags(project, product, inputs, outputs) {
return args;
}
+// The ARMCLANG compiler does not support generation
+// for the listing files:
+// * https://www.keil.com/support/docs/4152.htm
+// So, we generate the listing files from the object files
+// using the disassembler.
+function generateClangCompilerListing(project, product, inputs, outputs, input, output) {
+ if (isArmClangCompiler(input.cpp.compilerPath) && input.cpp.generateCompilerListingFiles) {
+ var args = disassemblerFlags(project, product, input, outputs, explicitlyDependsOn);
+ var disassemblerPath = input.cpp.disassemblerPath;
+ var cmd = new Command(disassemblerPath, args);
+ cmd.silent = true;
+ return cmd;
+ }
+}
+
+// The ARMCC compiler generates the listing files only in a short form,
+// e.g. to 'module.lst' instead of 'module.{c|cpp}.lst', that complicates
+// the auto-tests. Therefore we need to rename generated listing files
+// with correct unified names.
+function generateArmccCompilerListing(project, product, inputs, outputs, input, output) {
+ if (isArmCCCompiler(input.cpp.compilerPath) && input.cpp.generateCompilerListingFiles) {
+ var listingPath = FileInfo.path(outputs.lst[0].filePath);
+ var cmd = new JavaScriptCommand();
+ cmd.oldListing = FileInfo.joinPaths(listingPath, input.baseName + ".lst");
+ cmd.newListing = FileInfo.joinPaths(
+ listingPath, input.fileName + input.cpp.compilerListingSuffix);
+ cmd.silent = true;
+ cmd.sourceCode = function() { File.move(oldListing, newListing); };
+ return cmd;
+ }
+}
+
function prepareCompiler(project, product, inputs, outputs, input, output, explicitlyDependsOn) {
var cmds = [];
var args = compilerFlags(project, product, input, outputs, explicitlyDependsOn);
@@ -1101,18 +1149,14 @@ function prepareCompiler(project, product, inputs, outputs, input, output, expli
}
cmds.push(cmd);
- // The ARMCLANG compiler does not support generation
- // for the listing files:
- // * https://www.keil.com/support/docs/4152.htm
- // So, we generate the listing files from the object files
- // using the disassembler.
- if (isArmClangCompiler(compilerPath) && input.cpp.generateCompilerListingFiles) {
- args = disassemblerFlags(project, product, input, outputs, explicitlyDependsOn);
- var disassemblerPath = input.cpp.disassemblerPath;
- cmd = new Command(disassemblerPath, args);
- cmd.silent = true;
+ cmd = generateClangCompilerListing(project, product, inputs, outputs, input, output);
+ if (cmd)
cmds.push(cmd);
- }
+
+ cmd = generateArmccCompilerListing(project, product, inputs, outputs, input, output);
+ if (cmd)
+ cmds.push(cmd);
+
return cmds;
}
diff --git a/share/qbs/modules/cpp/keil.qbs b/share/qbs/modules/cpp/keil.qbs
index f1f3b50e8..ea99b589c 100644
--- a/share/qbs/modules/cpp/keil.qbs
+++ b/share/qbs/modules/cpp/keil.qbs
@@ -103,8 +103,7 @@ CppModule {
id: assembler
inputs: ["asm"]
outputFileTags: ["obj", "lst"]
- outputArtifacts: KEIL.compilerOutputArtifacts(
- input, input.cpp.generateAssemblerListingFiles)
+ outputArtifacts: KEIL.compilerOutputArtifacts(input, false)
prepare: KEIL.prepareAssembler.apply(KEIL, arguments)
}
@@ -118,8 +117,7 @@ CppModule {
inputs: ["cpp", "c"]
auxiliaryInputs: ["hpp"]
outputFileTags: ["obj", "lst"]
- outputArtifacts: KEIL.compilerOutputArtifacts(
- input, input.cpp.generateCompilerListingFiles)
+ outputArtifacts: KEIL.compilerOutputArtifacts(input, true)
prepare: KEIL.prepareCompiler.apply(KEIL, arguments)
}
diff --git a/share/qbs/modules/cpp/msvc.js b/share/qbs/modules/cpp/msvc.js
index 566059610..9f3d20282 100644
--- a/share/qbs/modules/cpp/msvc.js
+++ b/share/qbs/modules/cpp/msvc.js
@@ -28,6 +28,7 @@
**
****************************************************************************/
+var Codesign = require("../codesign/codesign.js");
var Cpp = require("cpp.js");
var File = require("qbs.File");
var FileInfo = require("qbs.FileInfo");
@@ -655,6 +656,12 @@ function prepareLinker(project, product, inputs, outputs, input, output) {
commands.push(cmd);
}
+ if (product.cpp.shouldSignArtifacts) {
+ Array.prototype.push.apply(
+ commands, Codesign.prepareSigntool(
+ project, product, inputs, outputs, input, output));
+ }
+
return commands;
}
diff --git a/share/qbs/modules/cpp/sdcc.js b/share/qbs/modules/cpp/sdcc.js
index a47063401..1904f59fc 100644
--- a/share/qbs/modules/cpp/sdcc.js
+++ b/share/qbs/modules/cpp/sdcc.js
@@ -239,7 +239,7 @@ function collectLibraryDependencies(product) {
return result;
}
-function compilerOutputArtifacts(input, useListing) {
+function compilerOutputArtifacts(input, isCompilerArtifacts) {
var obj = {
fileTags: ["obj"],
filePath: Utilities.getHash(input.baseDir) + "/"
@@ -270,11 +270,17 @@ function compilerOutputArtifacts(input, useListing) {
+ input.fileName + ".rst"
};
var artifacts = [obj, asm_adb, asm_src, asm_sym, rst_data];
- if (useListing) {
+ if (isCompilerArtifacts && input.cpp.generateCompilerListingFiles) {
artifacts.push({
fileTags: ["lst"],
filePath: Utilities.getHash(input.baseDir) + "/"
- + input.fileName + ".lst"
+ + input.fileName + input.cpp.compilerListingSuffix
+ });
+ } else if (!isCompilerArtifacts && input.cpp.generateAssemblerListingFiles) {
+ artifacts.push({
+ fileTags: ["lst"],
+ filePath: Utilities.getHash(input.baseDir) + "/"
+ + input.fileName + input.cpp.assemblerListingSuffix
});
}
return artifacts;
@@ -547,14 +553,19 @@ function archiverFlags(project, product, inputs, outputs) {
return args;
}
+function buildLinkerMapFilePath(target, suffix) {
+ return FileInfo.joinPaths(FileInfo.path(target.filePath),
+ FileInfo.completeBaseName(target.fileName) + suffix);
+}
+
// This is the workaround for the SDCC bug on a Windows host:
// * https://sourceforge.net/p/sdcc/bugs/2970/
// We need to replace the '\r\n\' line endings with the'\n' line
// endings for each generated object file.
-function patchObjectFiles(project, product, inputs, outputs, input, output) {
+function patchObjectFile(project, product, inputs, outputs, input, output) {
var isWindows = input.qbs.hostOS.contains("windows");
if (isWindows && input.cpp.debugInformation) {
- cmd = new JavaScriptCommand();
+ var cmd = new JavaScriptCommand();
cmd.objectPath = outputs.obj[0].filePath;
cmd.silent = true;
cmd.sourceCode = function() {
@@ -576,6 +587,85 @@ function patchObjectFiles(project, product, inputs, outputs, input, output) {
}
}
+// It is a workaround which removes the generated linker map file
+// if it is disabled by cpp.generateLinkerMapFile property.
+// Reason is that the SDCC compiler always generates this file,
+// and does not have an option to disable generation for a linker
+// map file. So, we can to remove a listing files only after the
+// linking completes.
+function removeLinkerMapFile(project, product, inputs, outputs, input, output) {
+ if (!product.cpp.generateLinkerMapFile) {
+ var target = outputs.application[0];
+ var cmd = new JavaScriptCommand();
+ cmd.mapFilePath = buildLinkerMapFilePath(target, product.cpp.linkerMapSuffix)
+ cmd.silent = true;
+ cmd.sourceCode = function() { File.remove(mapFilePath); };
+ return cmd;
+ }
+}
+
+// It is a workaround to rename the extension of the output linker
+// map file to the specified one, since the linker generates only
+// files with the '.map' extension.
+function renameLinkerMapFile(project, product, inputs, outputs, input, output) {
+ if (product.cpp.generateLinkerMapFile && (product.cpp.linkerMapSuffix !== ".map")) {
+ var target = outputs.application[0];
+ var cmd = new JavaScriptCommand();
+ cmd.newMapFilePath = buildLinkerMapFilePath(target, product.cpp.linkerMapSuffix);
+ cmd.oldMapFilePath = buildLinkerMapFilePath(target, ".map");
+ cmd.silent = true;
+ cmd.sourceCode = function() { File.move(oldMapFilePath, newMapFilePath); };
+ return cmd;
+ }
+}
+
+// It is a workaround which removes the generated listing files
+// if it is disabled by cpp.generateCompilerListingFiles property
+// or when the cpp.compilerListingSuffix differs with '.lst'.
+// Reason is that the SDCC compiler does not have an option to
+// disable generation for a listing files. Besides, the SDCC
+// compiler use this files and for the linking. So, we can to
+// remove a listing files only after the linking completes.
+function removeCompilerListingFiles(project, product, inputs, outputs, input, output) {
+ var cmd = new JavaScriptCommand();
+ cmd.objects = inputs.obj.map(function(a) { return a; });
+ cmd.silent = true;
+ cmd.sourceCode = function() {
+ objects.forEach(function(object) {
+ if (!object.filePath.endsWith(".c" + object.cpp.objectSuffix))
+ return; // Skip the assembler generated objects.
+ if (!object.cpp.generateCompilerListingFiles
+ || (object.cpp.compilerListingSuffix !== ".lst")) {
+ var listingPath = FileInfo.joinPaths(FileInfo.path(object.filePath),
+ object.completeBaseName + ".lst");
+ File.remove(listingPath);
+ }
+ })
+ };
+ return cmd;
+}
+
+// It is a workaround that duplicates the generated listing files
+// but with desired names. The problem is that the SDCC compiler does
+// not support an options to specify names for the generated listing
+// files. At the same time, the compiler always generates the listing
+// files in the form of 'module.c.lst', which makes it impossible to
+// change the file suffix to a user-specified one. In addition, these
+// files are also somehow used for linking. Thus, we can not rename them
+// on the compiling stage.
+function duplicateCompilerListingFile(project, product, inputs, outputs, input, output) {
+ if (input.cpp.generateCompilerListingFiles
+ && (input.cpp.compilerListingSuffix !== ".lst")) {
+ var cmd = new JavaScriptCommand();
+ cmd.newListing = outputs.lst[0].filePath;
+ cmd.oldListing = FileInfo.joinPaths(FileInfo.path(outputs.lst[0].filePath),
+ outputs.lst[0].completeBaseName + ".lst");
+ cmd.silent = true;
+ cmd.sourceCode = function() { File.copy(oldListing, newListing); };
+ return cmd;
+ }
+}
+
function prepareCompiler(project, product, inputs, outputs, input, output, explicitlyDependsOn) {
var cmds = [];
var args = compilerFlags(project, product, input, outputs, explicitlyDependsOn);
@@ -585,7 +675,11 @@ function prepareCompiler(project, product, inputs, outputs, input, output, expli
cmd.highlight = "compiler";
cmds.push(cmd);
- cmd = patchObjectFiles(project, product, inputs, outputs, input, output);
+ cmd = patchObjectFile(project, product, inputs, outputs, input, output);
+ if (cmd)
+ cmds.push(cmd);
+
+ cmd = duplicateCompilerListingFile(project, product, inputs, outputs, input, output);
if (cmd)
cmds.push(cmd);
@@ -601,7 +695,7 @@ function prepareAssembler(project, product, inputs, outputs, input, output, expl
cmd.highlight = "compiler";
cmds.push(cmd);
- cmd = patchObjectFiles(project, product, inputs, outputs, input, output);
+ cmd = patchObjectFile(project, product, inputs, outputs, input, output);
if (cmd)
cmds.push(cmd);
@@ -610,52 +704,24 @@ function prepareAssembler(project, product, inputs, outputs, input, output, expl
function prepareLinker(project, product, inputs, outputs, input, output) {
var cmds = [];
- var target = outputs.application[0];
var args = linkerFlags(project, product, inputs, outputs);
var linkerPath = effectiveLinkerPath(product);
var cmd = new Command(linkerPath, args);
- cmd.description = "linking " + target.fileName;
+ cmd.description = "linking " + outputs.application[0].fileName;
cmd.highlight = "linker";
cmds.push(cmd);
- // It is a workaround which removes the generated listing files
- // if it is disabled by cpp.generateCompilerListingFiles property.
- // Reason is that the SDCC compiler does not have an option to
- // disable generation for a listing files. Besides, the SDCC
- // compiler use this files and for the linking. So, we can to
- // remove a listing files only after the linking completes.
- if (!product.cpp.generateCompilerListingFiles) {
- cmd = new JavaScriptCommand();
- cmd.objectPaths = inputs.obj.map(function(a) { return a.filePath; });
- cmd.objectSuffix = product.cpp.objectSuffix;
- cmd.silent = true;
- cmd.sourceCode = function() {
- objectPaths.forEach(function(objectPath) {
- if (!objectPath.endsWith(".c" + objectSuffix))
- return; // Skip the assembler objects.
- var listingPath = FileInfo.joinPaths(
- FileInfo.path(objectPath),
- FileInfo.completeBaseName(objectPath) + ".lst");
- File.remove(listingPath);
- });
- };
+ cmd = removeCompilerListingFiles(project, product, inputs, outputs, input, output);
+ if (cmd)
cmds.push(cmd);
- }
- // It is a workaround which removes the generated linker map file
- // if it is disabled by cpp.generateLinkerMapFile property.
- // Reason is that the SDCC compiler always generates this file,
- // and does not have an option to disable generation for a linker
- // map file. So, we can to remove a listing files only after the
- // linking completes.
- if (!product.cpp.generateLinkerMapFile) {
- cmd = new JavaScriptCommand();
- cmd.mapFilePath = FileInfo.joinPaths(
- FileInfo.path(target.filePath),
- FileInfo.completeBaseName(target.fileName) + product.cpp.linkerMapSuffix);
- cmd.silent = true;
- cmd.sourceCode = function() { File.remove(mapFilePath); };
+
+ cmd = renameLinkerMapFile(project, product, inputs, outputs, input, output);
+ if (cmd)
+ cmds.push(cmd);
+
+ cmd = removeLinkerMapFile(project, product, inputs, outputs, input, output);
+ if (cmd)
cmds.push(cmd);
- }
return cmds;
}
diff --git a/share/qbs/modules/cpp/sdcc.qbs b/share/qbs/modules/cpp/sdcc.qbs
index 8b631d4e5..c5a0893d4 100644
--- a/share/qbs/modules/cpp/sdcc.qbs
+++ b/share/qbs/modules/cpp/sdcc.qbs
@@ -100,7 +100,7 @@ CppModule {
id: assembler
inputs: ["asm"]
outputFileTags: ["obj", "asm_adb", "lst", "asm_src", "asm_sym", "rst_data"]
- outputArtifacts: SDCC.compilerOutputArtifacts(input, true)
+ outputArtifacts: SDCC.compilerOutputArtifacts(input, false)
prepare: SDCC.prepareAssembler.apply(SDCC, arguments)
}
@@ -114,8 +114,7 @@ CppModule {
inputs: ["cpp", "c"]
auxiliaryInputs: ["hpp"]
outputFileTags: ["obj", "asm_adb", "lst", "asm_src", "asm_sym", "rst_data"]
- outputArtifacts: SDCC.compilerOutputArtifacts(
- input, input.cpp.generateCompilerListingFiles)
+ outputArtifacts: SDCC.compilerOutputArtifacts(input, true)
prepare: SDCC.prepareCompiler.apply(SDCC, arguments)
}
diff --git a/share/qbs/modules/cpp/windows-clang-cl.qbs b/share/qbs/modules/cpp/windows-clang-cl.qbs
index a34a67ad2..556efb042 100644
--- a/share/qbs/modules/cpp/windows-clang-cl.qbs
+++ b/share/qbs/modules/cpp/windows-clang-cl.qbs
@@ -53,6 +53,7 @@ MsvcBaseModule {
vcvarsallFilePath: vcvarsallPath
enableDefinesByLanguage: enableCompilerDefinesByLanguage
preferredArchitecture: qbs.architecture
+ winSdkVersion: windowsSdkVersion
}
qbs.architecture: clangClProbe.found ? clangClProbe.architecture : original
diff --git a/share/qbs/modules/cpp/windows-msvc-base.qbs b/share/qbs/modules/cpp/windows-msvc-base.qbs
index b25fdf159..c45ec5ec3 100644
--- a/share/qbs/modules/cpp/windows-msvc-base.qbs
+++ b/share/qbs/modules/cpp/windows-msvc-base.qbs
@@ -40,6 +40,8 @@ import 'msvc.js' as MSVC
CppModule {
condition: false
+ Depends { name: "codesign" }
+
windowsApiCharacterSet: "unicode"
platformDefines: {
var defines = base.concat(WindowsUtils.characterSetDefines(windowsApiCharacterSet))
@@ -100,6 +102,8 @@ CppModule {
property var buildEnv
+ readonly property bool shouldSignArtifacts: codesign.enableCodeSigning
+
setupBuildEnvironment: {
for (var key in product.cpp.buildEnv) {
var v = new ModUtils.EnvironmentVariable(key, ';');
@@ -108,6 +112,8 @@ CppModule {
}
}
+ property string windowsSdkVersion
+
Rule {
condition: useCPrecompiledHeader
inputs: ["c_pch_src"]
@@ -162,7 +168,8 @@ CppModule {
if (input.cpp.generateCompilerListingFiles) {
artifacts.push({
fileTags: ["lst"],
- filePath: Utilities.getHash(input.baseDir) + "/" + input.fileName + ".lst"
+ filePath: Utilities.getHash(input.baseDir)
+ + "/" + input.fileName + input.cpp.compilerListingSuffix
});
}
return artifacts;
@@ -189,10 +196,16 @@ CppModule {
inputs: ['obj', 'native.pe.manifest', 'def']
inputsFromDependencies: ['staticlibrary', 'dynamiclibrary_import', "debuginfo_app"]
- outputFileTags: ["application", "debuginfo_app", "mem_map"]
+ outputFileTags: {
+ var tags = ["application", "debuginfo_app", "mem_map"];
+ if (shouldSignArtifacts)
+ tags.push("codesign.signed_artifact");
+ return tags;
+ }
outputArtifacts: {
var app = {
- fileTags: ["application"],
+ fileTags: ["application"].concat(
+ product.cpp.shouldSignArtifacts ? ["codesign.signed_artifact"] : []),
filePath: FileInfo.joinPaths(
product.destinationDirectory,
PathTools.applicationFilePath(product))
@@ -227,11 +240,17 @@ CppModule {
inputs: ['obj', 'native.pe.manifest', 'def']
inputsFromDependencies: ['staticlibrary', 'dynamiclibrary_import', "debuginfo_dll"]
- outputFileTags: ["dynamiclibrary", "dynamiclibrary_import", "debuginfo_dll"]
+ outputFileTags: {
+ var tags = ["dynamiclibrary", "dynamiclibrary_import", "debuginfo_dll"];
+ if (shouldSignArtifacts)
+ tags.push("codesign.signed_artifact");
+ return tags;
+ }
outputArtifacts: {
var artifacts = [
{
- fileTags: ["dynamiclibrary"],
+ fileTags: ["dynamiclibrary"].concat(
+ product.cpp.shouldSignArtifacts ? ["codesign.signed_artifact"] : []),
filePath: product.destinationDirectory + "/" + PathTools.dynamicLibraryFilePath(product)
},
{
diff --git a/share/qbs/modules/cpp/windows-msvc.qbs b/share/qbs/modules/cpp/windows-msvc.qbs
index d5b5baf92..33c5e74c8 100644
--- a/share/qbs/modules/cpp/windows-msvc.qbs
+++ b/share/qbs/modules/cpp/windows-msvc.qbs
@@ -51,6 +51,7 @@ MsvcBaseModule {
compilerFilePath: compilerPath
enableDefinesByLanguage: enableCompilerDefinesByLanguage
preferredArchitecture: qbs.architecture
+ winSdkVersion: windowsSdkVersion
}
qbs.architecture: msvcProbe.found ? msvcProbe.architecture : original