summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Source/CMakeLists.txt2
-rw-r--r--Source/cmQtAutoGeneratorCommon.cxx166
-rw-r--r--Source/cmQtAutoGeneratorCommon.h29
-rw-r--r--Source/cmQtAutoGeneratorInitializer.cxx186
-rw-r--r--Source/cmQtAutoGenerators.cxx12
5 files changed, 229 insertions, 166 deletions
diff --git a/Source/CMakeLists.txt b/Source/CMakeLists.txt
index 76b98fc..5f2cbc3 100644
--- a/Source/CMakeLists.txt
+++ b/Source/CMakeLists.txt
@@ -344,6 +344,8 @@ set(SRCS
cmPropertyDefinitionMap.h
cmPropertyMap.cxx
cmPropertyMap.h
+ cmQtAutoGeneratorCommon.cxx
+ cmQtAutoGeneratorCommon.h
cmQtAutoGeneratorInitializer.cxx
cmQtAutoGeneratorInitializer.h
cmQtAutoGenerators.cxx
diff --git a/Source/cmQtAutoGeneratorCommon.cxx b/Source/cmQtAutoGeneratorCommon.cxx
new file mode 100644
index 0000000..c42f71d
--- /dev/null
+++ b/Source/cmQtAutoGeneratorCommon.cxx
@@ -0,0 +1,166 @@
+/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
+ file Copyright.txt or https://cmake.org/licensing for details. */
+#include "cmQtAutoGeneratorCommon.h"
+#include "cmAlgorithms.h"
+#include "cmSystemTools.h"
+
+#include <cmsys/FStream.hxx>
+#include <cmsys/RegularExpression.hxx>
+
+#include <sstream>
+
+// - Static functions
+
+static std::string utilStripCR(std::string const& line)
+{
+ // Strip CR characters rcc may have printed (possibly more than one!).
+ std::string::size_type cr = line.find('\r');
+ if (cr != line.npos) {
+ return line.substr(0, cr);
+ }
+ return line;
+}
+
+/// @brief Reads the resource files list from from a .qrc file - Qt4 version
+/// @return True if the .qrc file was successfully parsed
+static bool RccListInputsQt4(const std::string& fileName,
+ std::vector<std::string>& files)
+{
+ // Qrc file directory
+ std::string qrcDir(cmsys::SystemTools::GetFilenamePath(fileName));
+ if (!qrcDir.empty()) {
+ qrcDir += '/';
+ }
+
+ // Read file into string
+ std::string qrcContents;
+ {
+ std::ostringstream stream;
+ stream << cmsys::ifstream(fileName).rdbuf();
+ qrcContents = stream.str();
+ }
+
+ cmsys::RegularExpression fileMatchRegex("(<file[^<]+)");
+ cmsys::RegularExpression fileReplaceRegex("(^<file[^>]*>)");
+
+ size_t offset = 0;
+ while (fileMatchRegex.find(qrcContents.c_str() + offset)) {
+ std::string qrcEntry = fileMatchRegex.match(1);
+ offset += qrcEntry.size();
+ {
+ fileReplaceRegex.find(qrcEntry);
+ std::string tag = fileReplaceRegex.match(1);
+ qrcEntry = qrcEntry.substr(tag.size());
+ }
+ if (!cmSystemTools::FileIsFullPath(qrcEntry.c_str())) {
+ qrcEntry = qrcDir + qrcEntry;
+ }
+ files.push_back(qrcEntry);
+ }
+ return true;
+}
+
+/// @brief Reads the resource files list from from a .qrc file - Qt5 version
+/// @return True if the .qrc file was successfully parsed
+static bool RccListInputsQt5(const std::string& rccCommand,
+ const std::string& fileName,
+ std::vector<std::string>& files)
+{
+ if (rccCommand.empty()) {
+ cmSystemTools::Error("AutoRcc: Error: rcc executable not available\n");
+ return false;
+ }
+
+ // Read rcc features
+ bool hasDashDashList = false;
+ {
+ std::vector<std::string> command;
+ command.push_back(rccCommand);
+ command.push_back("--help");
+ std::string rccStdOut;
+ std::string rccStdErr;
+ int retVal = 0;
+ bool result =
+ cmSystemTools::RunSingleCommand(command, &rccStdOut, &rccStdErr, &retVal,
+ CM_NULLPTR, cmSystemTools::OUTPUT_NONE);
+ if (result && retVal == 0 &&
+ rccStdOut.find("--list") != std::string::npos) {
+ hasDashDashList = true;
+ }
+ }
+
+ // Run rcc list command
+ bool result = false;
+ int retVal = 0;
+ std::string rccStdOut;
+ std::string rccStdErr;
+ {
+ std::vector<std::string> command;
+ command.push_back(rccCommand);
+ command.push_back(hasDashDashList ? "--list" : "-list");
+ command.push_back(fileName);
+ result =
+ cmSystemTools::RunSingleCommand(command, &rccStdOut, &rccStdErr, &retVal,
+ CM_NULLPTR, cmSystemTools::OUTPUT_NONE);
+ }
+ if (!result || retVal) {
+ std::ostringstream err;
+ err << "AUTOGEN: error: Rcc list process for " << fileName << " failed:\n"
+ << rccStdOut << "\n"
+ << rccStdErr << std::endl;
+ cmSystemTools::Error(err.str().c_str());
+ return false;
+ }
+
+ // Parse rcc std output
+ {
+ std::istringstream ostr(rccStdOut);
+ std::string oline;
+ while (std::getline(ostr, oline)) {
+ oline = utilStripCR(oline);
+ if (!oline.empty()) {
+ files.push_back(oline);
+ }
+ }
+ }
+ // Parse rcc error output
+ {
+ std::istringstream estr(rccStdErr);
+ std::string eline;
+ while (std::getline(estr, eline)) {
+ eline = utilStripCR(eline);
+ if (cmHasLiteralPrefix(eline, "RCC: Error in")) {
+ static std::string searchString = "Cannot find file '";
+
+ std::string::size_type pos = eline.find(searchString);
+ if (pos == std::string::npos) {
+ std::ostringstream err;
+ err << "AUTOGEN: error: Rcc lists unparsable output " << eline
+ << std::endl;
+ cmSystemTools::Error(err.str().c_str());
+ return false;
+ }
+ pos += searchString.length();
+ std::string::size_type sz = eline.size() - pos - 1;
+ files.push_back(eline.substr(pos, sz));
+ }
+ }
+ }
+
+ return true;
+}
+
+// - Class definitions
+
+const char* cmQtAutoGeneratorCommon::listSep = "@list_sep@";
+
+bool cmQtAutoGeneratorCommon::RccListInputs(const std::string& qtMajorVersion,
+ const std::string& rccCommand,
+ const std::string& fileName,
+ std::vector<std::string>& files)
+{
+ if (qtMajorVersion == "4") {
+ return RccListInputsQt4(fileName, files);
+ }
+ return RccListInputsQt5(rccCommand, fileName, files);
+}
diff --git a/Source/cmQtAutoGeneratorCommon.h b/Source/cmQtAutoGeneratorCommon.h
new file mode 100644
index 0000000..48abacb
--- /dev/null
+++ b/Source/cmQtAutoGeneratorCommon.h
@@ -0,0 +1,29 @@
+/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
+ file Copyright.txt or https://cmake.org/licensing for details. */
+#ifndef cmQtAutoGeneratorCommon_h
+#define cmQtAutoGeneratorCommon_h
+
+#include <cmConfigure.h> // IWYU pragma: keep
+#include <string>
+#include <vector>
+
+class cmGeneratorTarget;
+class cmLocalGenerator;
+
+class cmQtAutoGeneratorCommon
+{
+ // - Types and statics
+public:
+ static const char* listSep;
+
+public:
+ /// @brief Reads the resource files list from from a .qrc file
+ /// @arg fileName Must be the absolute path of the .qrc file
+ /// @return True if the rcc file was successfully parsed
+ static bool RccListInputs(const std::string& qtMajorVersion,
+ const std::string& rccCommand,
+ const std::string& fileName,
+ std::vector<std::string>& files);
+};
+
+#endif
diff --git a/Source/cmQtAutoGeneratorInitializer.cxx b/Source/cmQtAutoGeneratorInitializer.cxx
index a45b3d5..3a7951a 100644
--- a/Source/cmQtAutoGeneratorInitializer.cxx
+++ b/Source/cmQtAutoGeneratorInitializer.cxx
@@ -1,6 +1,7 @@
/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
file Copyright.txt or https://cmake.org/licensing for details. */
#include "cmQtAutoGeneratorInitializer.h"
+#include "cmQtAutoGeneratorCommon.h"
#include "cmAlgorithms.h"
#include "cmCustomCommandLines.h"
@@ -44,16 +45,6 @@ static void utilCopyTargetProperty(cmTarget* destinationTarget,
}
}
-static std::string utilStripCR(std::string const& line)
-{
- // Strip CR characters rcc may have printed (possibly more than one!).
- std::string::size_type cr = line.find('\r');
- if (cr != line.npos) {
- return line.substr(0, cr);
- }
- return line;
-}
-
static std::string GetSafeProperty(cmGeneratorTarget const* target,
const char* key)
{
@@ -361,7 +352,8 @@ static void UicSetupAutoTarget(
uiFileFiles.push_back(absFile);
{
std::string opts = sf->GetProperty("AUTOUIC_OPTIONS");
- cmSystemTools::ReplaceString(opts, ";", "@list_sep@");
+ cmSystemTools::ReplaceString(opts, ";",
+ cmQtAutoGeneratorCommon::listSep);
uiFileOptions.push_back(opts);
}
}
@@ -469,146 +461,12 @@ static void RccMergeOptions(std::vector<std::string>& opts,
opts.insert(opts.end(), extraOpts.begin(), extraOpts.end());
}
-/// @brief Reads the resource files list from from a .qrc file - Qt5 version
-/// @return True if the .qrc file was successfully parsed
-static bool RccListInputsQt5(cmSourceFile* sf, cmGeneratorTarget const* target,
- std::vector<std::string>& depends)
-{
- const std::string rccCommand = RccGetExecutable(target, "5");
- if (rccCommand.empty()) {
- cmSystemTools::Error("AUTOGEN: error: rcc executable not available\n");
- return false;
- }
-
- bool hasDashDashList = false;
- // Read rcc features
- {
- std::vector<std::string> command;
- command.push_back(rccCommand);
- command.push_back("--help");
- std::string rccStdOut;
- std::string rccStdErr;
- int retVal = 0;
- bool result =
- cmSystemTools::RunSingleCommand(command, &rccStdOut, &rccStdErr, &retVal,
- CM_NULLPTR, cmSystemTools::OUTPUT_NONE);
- if (result && retVal == 0 &&
- rccStdOut.find("--list") != std::string::npos) {
- hasDashDashList = true;
- }
- }
- // Run rcc list command
- std::vector<std::string> command;
- command.push_back(rccCommand);
- command.push_back(hasDashDashList ? "--list" : "-list");
-
- std::string absFile = cmsys::SystemTools::GetRealPath(sf->GetFullPath());
- command.push_back(absFile);
-
- std::string rccStdOut;
- std::string rccStdErr;
- int retVal = 0;
- bool result =
- cmSystemTools::RunSingleCommand(command, &rccStdOut, &rccStdErr, &retVal,
- CM_NULLPTR, cmSystemTools::OUTPUT_NONE);
- if (!result || retVal) {
- std::ostringstream err;
- err << "AUTOGEN: error: Rcc list process for " << sf->GetFullPath()
- << " failed:\n"
- << rccStdOut << "\n"
- << rccStdErr << std::endl;
- cmSystemTools::Error(err.str().c_str());
- return false;
- }
-
- // Parse rcc list output
- {
- std::istringstream ostr(rccStdOut);
- std::string oline;
- while (std::getline(ostr, oline)) {
- oline = utilStripCR(oline);
- if (!oline.empty()) {
- depends.push_back(oline);
- }
- }
- }
-
- {
- std::istringstream estr(rccStdErr);
- std::string eline;
- while (std::getline(estr, eline)) {
- eline = utilStripCR(eline);
- if (cmHasLiteralPrefix(eline, "RCC: Error in")) {
- static std::string searchString = "Cannot find file '";
-
- std::string::size_type pos = eline.find(searchString);
- if (pos == std::string::npos) {
- std::ostringstream err;
- err << "AUTOGEN: error: Rcc lists unparsable output " << eline
- << std::endl;
- cmSystemTools::Error(err.str().c_str());
- return false;
- }
- pos += searchString.length();
- std::string::size_type sz = eline.size() - pos - 1;
- depends.push_back(eline.substr(pos, sz));
- }
- }
- }
-
- return true;
-}
-
-/// @brief Reads the resource files list from from a .qrc file - Qt4 version
-/// @return True if the .qrc file was successfully parsed
-static bool RccListInputsQt4(cmSourceFile* sf,
- std::vector<std::string>& depends)
-{
- // Read file into string
- std::string qrcContents;
- {
- std::ostringstream stream;
- stream << cmsys::ifstream(sf->GetFullPath().c_str()).rdbuf();
- qrcContents = stream.str();
- }
-
- cmsys::RegularExpression fileMatchRegex("(<file[^<]+)");
- cmsys::RegularExpression fileReplaceRegex("(^<file[^>]*>)");
-
- size_t offset = 0;
- while (fileMatchRegex.find(qrcContents.c_str() + offset)) {
- std::string qrcEntry = fileMatchRegex.match(1);
- offset += qrcEntry.size();
- {
- fileReplaceRegex.find(qrcEntry);
- std::string tag = fileReplaceRegex.match(1);
- qrcEntry = qrcEntry.substr(tag.size());
- }
- if (!cmSystemTools::FileIsFullPath(qrcEntry.c_str())) {
- qrcEntry = sf->GetLocation().GetDirectory() + "/" + qrcEntry;
- }
- depends.push_back(qrcEntry);
- }
- return true;
-}
-
-/// @brief Reads the resource files list from from a .qrc file
-/// @return True if the rcc file was successfully parsed
-static bool RccListInputs(const std::string& qtMajorVersion, cmSourceFile* sf,
- cmGeneratorTarget const* target,
- std::vector<std::string>& depends)
-{
- if (qtMajorVersion == "5") {
- return RccListInputsQt5(sf, target, depends);
- }
- return RccListInputsQt4(sf, depends);
-}
-
static void RccSetupAutoTarget(cmGeneratorTarget const* target,
const std::string& qtMajorVersion)
{
cmMakefile* makefile = target->Target->GetMakefile();
const bool qtMajorVersion5 = (qtMajorVersion == "5");
+ const std::string rccCommand = RccGetExecutable(target, qtMajorVersion);
std::vector<std::string> _rcc_files;
std::vector<std::string> _rcc_inputs;
std::vector<std::string> rccFileFiles;
@@ -636,9 +494,10 @@ static void RccSetupAutoTarget(cmGeneratorTarget const* target,
{
std::string entriesList;
if (!cmSystemTools::IsOn(sf->GetPropertyForUser("GENERATED"))) {
- std::vector<std::string> depends;
- if (RccListInputs(qtMajorVersion, sf, target, depends)) {
- entriesList = cmJoin(depends, "@list_sep@");
+ std::vector<std::string> files;
+ if (cmQtAutoGeneratorCommon::RccListInputs(
+ qtMajorVersion, rccCommand, absFile, files)) {
+ entriesList = cmJoin(files, cmQtAutoGeneratorCommon::listSep);
} else {
return;
}
@@ -657,19 +516,19 @@ static void RccSetupAutoTarget(cmGeneratorTarget const* target,
// Only store non empty options lists
if (!rccOptions.empty()) {
rccFileFiles.push_back(absFile);
- rccFileOptions.push_back(cmJoin(rccOptions, "@list_sep@"));
+ rccFileOptions.push_back(
+ cmJoin(rccOptions, cmQtAutoGeneratorCommon::listSep));
}
}
}
}
}
+ AddDefinitionEscaped(makefile, "_qt_rcc_executable", rccCommand);
AddDefinitionEscaped(makefile, "_rcc_files", _rcc_files);
AddDefinitionEscaped(makefile, "_rcc_inputs", _rcc_inputs);
AddDefinitionEscaped(makefile, "_rcc_options_files", rccFileFiles);
AddDefinitionEscaped(makefile, "_rcc_options_options", rccFileOptions);
- AddDefinitionEscaped(makefile, "_qt_rcc_executable",
- RccGetExecutable(target, qtMajorVersion));
}
void cmQtAutoGeneratorInitializer::InitializeAutogenSources(
@@ -696,6 +555,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget(
const std::string workingDirectory =
cmSystemTools::CollapseFullPath("", makefile->GetCurrentBinaryDirectory());
const std::string qtMajorVersion = GetQtMajorVersion(target);
+ const std::string rccCommand = RccGetExecutable(target, qtMajorVersion);
std::vector<std::string> autogenOutputFiles;
// Remove old settings on cleanup
@@ -825,20 +685,22 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget(
target->AddSource(rccOutputFile);
// Register rcc output file as generated
autogenOutputFiles.push_back(rccOutputFile);
- }
- if (lg->GetGlobalGenerator()->GetName() == "Ninja"
+
+ if (lg->GetGlobalGenerator()->GetName() == "Ninja"
#if defined(_WIN32) && !defined(__CYGWIN__)
- || usePRE_BUILD
+ || usePRE_BUILD
#endif
- ) {
- if (!cmSystemTools::IsOn(sf->GetPropertyForUser("GENERATED"))) {
- RccListInputs(qtMajorVersion, sf, target, depends);
+ ) {
+ if (!cmSystemTools::IsOn(sf->GetPropertyForUser("GENERATED"))) {
+ cmQtAutoGeneratorCommon::RccListInputs(
+ qtMajorVersion, rccCommand, absFile, depends);
#if defined(_WIN32) && !defined(__CYGWIN__)
- // Cannot use PRE_BUILD because the resource files themselves
- // may not be sources within the target so VS may not know the
- // target needs to re-build at all.
- usePRE_BUILD = false;
+ // Cannot use PRE_BUILD because the resource files themselves
+ // may not be sources within the target so VS may not know the
+ // target needs to re-build at all.
+ usePRE_BUILD = false;
#endif
+ }
}
}
}
diff --git a/Source/cmQtAutoGenerators.cxx b/Source/cmQtAutoGenerators.cxx
index c83f9a9..bc9c511 100644
--- a/Source/cmQtAutoGenerators.cxx
+++ b/Source/cmQtAutoGenerators.cxx
@@ -1,6 +1,7 @@
/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
file Copyright.txt or https://cmake.org/licensing for details. */
#include "cmQtAutoGenerators.h"
+#include "cmQtAutoGeneratorCommon.h"
#include <algorithm>
#include <assert.h>
@@ -178,7 +179,7 @@ static std::string JoinOptionsMap(
for (std::map<std::string, std::string>::const_iterator it = opts.begin();
it != opts.end(); ++it) {
if (it != opts.begin()) {
- result += "@list_sep@";
+ result += cmQtAutoGeneratorCommon::listSep;
}
result += it->first;
result += "===";
@@ -424,7 +425,8 @@ bool cmQtAutoGenerators::ReadAutogenInfoFile(
fileIt = uicFilesVec.begin(),
optionIt = uicOptionsVec.begin();
fileIt != uicFilesVec.end(); ++fileIt, ++optionIt) {
- cmSystemTools::ReplaceString(*optionIt, "@list_sep@", ";");
+ cmSystemTools::ReplaceString(*optionIt,
+ cmQtAutoGeneratorCommon::listSep, ";");
this->UicOptions[*fileIt] = *optionIt;
}
} else {
@@ -453,7 +455,8 @@ bool cmQtAutoGenerators::ReadAutogenInfoFile(
for (std::vector<std::string>::iterator fileIt = rccFilesVec.begin(),
optionIt = rccOptionsVec.begin();
fileIt != rccFilesVec.end(); ++fileIt, ++optionIt) {
- cmSystemTools::ReplaceString(*optionIt, "@list_sep@", ";");
+ cmSystemTools::ReplaceString(*optionIt,
+ cmQtAutoGeneratorCommon::listSep, ";");
this->RccOptions[*fileIt] = *optionIt;
}
}
@@ -475,7 +478,8 @@ bool cmQtAutoGenerators::ReadAutogenInfoFile(
fileIt = this->RccSources.begin(),
inputIt = rccInputLists.begin();
fileIt != this->RccSources.end(); ++fileIt, ++inputIt) {
- cmSystemTools::ReplaceString(*inputIt, "@list_sep@", ";");
+ cmSystemTools::ReplaceString(*inputIt,
+ cmQtAutoGeneratorCommon::listSep, ";");
std::vector<std::string> rccInputFiles;
cmSystemTools::ExpandListArgument(*inputIt, rccInputFiles);
this->RccInputs[*fileIt] = rccInputFiles;