Skip to content

Commit 882f220

Browse files
committed
Initial commit
0 parents  commit 882f220

10 files changed

+226
-0
lines changed

Diff for: .gitignore

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
*build*/
2+
.idea/

Diff for: .gitmodules

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
[submodule "lib/linuxdeploy"]
2+
path = lib/linuxdeploy
3+
url = https://github.com/TheAssassin/linuxdeploy

Diff for: CMakeLists.txt

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
cmake_minimum_required(VERSION 3.6)
2+
project(linuxdeploy-plugin-qt)
3+
4+
set(CMAKE_CXX_STANDARD 11)
5+
set(CMAKE_CXX_STANDARD_REQUIRED ON)
6+
7+
add_subdirectory(lib)
8+
add_subdirectory(src)

Diff for: LICENSE.txt

+19
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
Copyright 2018 TheAssassin
2+
3+
Permission is hereby granted, free of charge, to any person obtaining a copy
4+
of this software and associated documentation files (the "Software"), to deal
5+
in the Software without restriction, including without limitation the rights
6+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7+
copies of the Software, and to permit persons to whom the Software is
8+
furnished to do so, subject to the following conditions:
9+
10+
The above copyright notice and this permission notice shall be included in all
11+
copies or substantial portions of the Software.
12+
13+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
19+
SOFTWARE.

Diff for: README.md

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# linuxdeploy-plugin-qt
2+
3+
Plugin for linuxdeploy to bundle Qt dependencies of applications and libraries.
4+
5+
***More information will follow soon!***

Diff for: lib/CMakeLists.txt

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
add_subdirectory(linuxdeploy EXCLUDE_FROM_ALL)

Diff for: lib/linuxdeploy

Submodule linuxdeploy added at 030b213

Diff for: src/CMakeLists.txt

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
add_executable(linuxdeploy-plugin-qt main.cpp qt-modules.h)
2+
target_link_libraries(linuxdeploy-plugin-qt linuxdeploy_core args)

Diff for: src/main.cpp

+107
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
// system includes
2+
#include <iostream>
3+
#include <set>
4+
#include <sstream>
5+
#include <string>
6+
#include <vector>
7+
8+
// library includes
9+
#include <boost/filesystem.hpp>
10+
#include <linuxdeploy/core/appdir.h>
11+
#include <linuxdeploy/core/elf.h>
12+
#include <linuxdeploy/core/log.h>
13+
#include <args.hxx>
14+
15+
// local includes
16+
#include "qt-modules.h"
17+
18+
namespace bf = boost::filesystem;
19+
20+
using namespace linuxdeploy::core;
21+
using namespace linuxdeploy::core::log;
22+
23+
static ldLog ldQtLog() {
24+
return ldLog() << "linuxdeploy-plugin-qt:";
25+
}
26+
27+
std::string join(const std::vector<std::string>& list) {
28+
std::stringstream rv;
29+
30+
if (!list.empty()) {
31+
rv << list[0];
32+
33+
std::for_each(list.begin() + 1, list.end(), [&rv](const std::string& s) {
34+
rv << " " << s;
35+
});
36+
}
37+
38+
return rv.str();
39+
}
40+
41+
int main(const int argc, const char* const* argv) {
42+
args::ArgumentParser parser("linuxdeploy Qt plugin", "Bundles Qt resources. For use with an existing AppDir, created by linuxdeploy.");
43+
44+
args::ValueFlag<bf::path> appDirPath(parser, "appdir path", "Path to an existing AppDir", {"appdir"});
45+
46+
try {
47+
parser.ParseCLI(argc, argv);
48+
} catch (const args::ParseError&) {
49+
std::cerr << parser;
50+
return 1;
51+
}
52+
53+
if (!appDirPath) {
54+
ldQtLog() << LD_ERROR << "--appdir parameter required" << std::endl;
55+
std::cout << std::endl << parser;
56+
return 1;
57+
}
58+
59+
if (!bf::is_directory(appDirPath.Get())) {
60+
ldQtLog() << LD_ERROR << "No such directory:" << appDirPath.Get() << std::endl;
61+
return 1;
62+
}
63+
64+
appdir::AppDir appDir(appDirPath.Get());
65+
66+
// check which libraries and plugins the binaries and libraries depend on
67+
std::set<std::string> libraryNames;
68+
for (const auto& path : appDir.listExecutables()) {
69+
try {
70+
for (const auto& dependency : elf::ElfFile(path).traceDynamicDependencies()) {
71+
libraryNames.insert(dependency.filename().string());
72+
}
73+
} catch (const elf::ElfFileParseError& e) {
74+
ldQtLog() << LD_DEBUG << "Failed to parse file as ELF file:" << path << std::endl;
75+
}
76+
}
77+
78+
// check for Qt modules
79+
std::vector<QtModule> foundQtModules;
80+
81+
std::copy_if(QtModules.begin(), QtModules.end(), std::back_inserter(foundQtModules), [&libraryNames](const QtModule& module) {
82+
return std::find_if(libraryNames.begin(), libraryNames.end(), [&module](const std::string& libraryFileName) {
83+
const auto& libraryPrefix = module.libraryFilePrefix;
84+
return strncmp(libraryFileName.c_str(), libraryPrefix.c_str(), libraryPrefix.size()) == 0;
85+
}) != libraryNames.end();
86+
});
87+
88+
{
89+
std::vector<std::string> moduleNames;
90+
std::for_each(foundQtModules.begin(), foundQtModules.end(), [&moduleNames](const QtModule& module) {
91+
moduleNames.push_back(module.name);
92+
moduleNames.push_back(module.name);
93+
moduleNames.push_back(module.name);
94+
});
95+
ldQtLog() << "Found Qt modules:" << join(moduleNames) << std::endl;
96+
}
97+
98+
for (const auto& module : foundQtModules) {
99+
ldQtLog() << "-- Deploying module:" << module.name << "--" << std::endl;
100+
101+
// TODO: add if statements for all plugins that require special treatment
102+
103+
ldQtLog() << "Nothing to do for module:" << module.name << std::endl;
104+
}
105+
106+
ldQtLog() << "Done!" << std::endl;
107+
}

Diff for: src/qt-modules.h

+78
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
// system includes
2+
#include <string>
3+
#include <tuple>
4+
#include <vector>
5+
6+
#pragma once
7+
8+
class QtModule {
9+
public:
10+
const std::string name;
11+
const std::string libraryFilePrefix;
12+
const std::string pluginGroup;
13+
14+
public:
15+
QtModule(std::string name, std::string libraryFilePrefix, std::string pluginGroup) :
16+
name(std::move(name)), libraryFilePrefix(std::move(libraryFilePrefix)), pluginGroup(std::move(pluginGroup)) {}
17+
};
18+
19+
static const std::vector<QtModule> QtModules = {
20+
{"3danimation", "libQt53DAnimation", ""},
21+
{"3dcore", "libQt53DCore", ""},
22+
{"3dextras", "libQt53DExtras", ""},
23+
{"3dinput", "libQt53DInput", ""},
24+
{"3dlogic", "libQt53DLogic", ""},
25+
{"3dquickanimation", "libQt53DQuickAnimation", ""},
26+
{"3dquickextras", "libQt53DQuickExtras", ""},
27+
{"3dquickinput", "libQt53DQuickInput", ""},
28+
{"3dquickrender", "libQt53DQuickRender", ""},
29+
{"3dquickscene2d", "libQt53DQuickScene2D", ""},
30+
{"3dquick", "libQt53DQuick", ""},
31+
{"bluetooth", "libQt5Bluetooth", ""},
32+
{"concurrent", "libQt5Concurrent", ""},
33+
{"core", "libQt5Core", ""},
34+
{"dbus", "libQt5DBus", ""},
35+
{"designercomponents", "libQt5DesignerComponents", ""},
36+
{"designer", "libQt5Designer", ""},
37+
{"gamepad", "libQt5Gamepad", ""},
38+
{"gui", "libQt5Gui", ""},
39+
{"help", "libQt5Help", ""},
40+
{"location", "libQt5Location", ""},
41+
{"multimediagsttools", "libQt5MultimediaGstTools", ""},
42+
{"multimediaquick", "libQt5MultimediaQuick", ""},
43+
{"multimedia", "libQt5Multimedia", ""},
44+
{"multimediawidgets", "libQt5MultimediaWidgets", ""},
45+
{"network", "libQt5Network", ""},
46+
{"nfc", "libQt5Nfc", ""},
47+
{"opengl", "libQt5OpenGL", ""},
48+
{"positioning", "libQt5Positioning", ""},
49+
{"printsupport", "libQt5PrintSupport", ""},
50+
{"qml", "libQt5Qml", ""},
51+
{"quickcontrols2", "libQt5QuickControls2", ""},
52+
{"quickparticles", "libQt5QuickParticles", ""},
53+
{"quick", "libQt5Quick", ""},
54+
{"quicktemplates2", "libQt5QuickTemplates2", ""},
55+
{"quicktest", "libQt5QuickTest", ""},
56+
{"quickwidgets", "libQt5QuickWidgets", ""},
57+
{"remoteobjects", "libQt5RemoteObjects", ""},
58+
{"script", "libQt5Script", ""},
59+
{"scripttools", "libQt5ScriptTools", ""},
60+
{"scxml", "libQt5Scxml", ""},
61+
{"sensors", "libQt5Sensors", ""},
62+
{"serialbus", "libQt5SerialBus", ""},
63+
{"serialport", "libQt5SerialPort", ""},
64+
{"sql", "libQt5Sql", ""},
65+
{"svg", "libQt5Svg", ""},
66+
{"test", "libQt5Test", ""},
67+
{"texttospeech", "libQt5TextToSpeech", ""},
68+
{"webchannel", "libQt5WebChannel", ""},
69+
{"webenginecore", "libQt5WebEngineCore", ""},
70+
{"webengine", "libQt5WebEngine", ""},
71+
{"webenginewidgets", "libQt5WebEngineWidgets", ""},
72+
{"websockets", "libQt5WebSockets", ""},
73+
{"widgets", "libQt5Widgets", ""},
74+
{"x11extras", "libQt5X11Extras", ""},
75+
{"xcbqpa", "libQt5XcbQpa", ""},
76+
{"xmlpatterns", "libQt5XmlPatterns", ""},
77+
{"xml", "libQt5Xml", ""},
78+
};

0 commit comments

Comments
 (0)