Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 6 additions & 5 deletions appimagebuilder/commands/setup_runtime.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,15 @@ def id(self):

def __call__(self, *args, **kwargs):
apprun_version = self.context.recipe.AppDir.runtime.version() or "v2.0.0"
apprun_version = version.parse(apprun_version)
if apprun_version == "continuous":
apprun_version = version.parse("v2.0.0")
else:
apprun_version = version.parse(apprun_version.split("-")[0])
runtime_setup = None
if (
version.parse("v2.0.0") <= apprun_version < version.parse("v3.0.0")
) or apprun_version == version.parse("continuous"):
if version.parse("v2.0.0") <= apprun_version < version.parse("v3.0.0"):
runtime_setup = AppRunV2Setup(self.context, self._finder)

if not runtime_setup and version.parse("v3.0.0-devel") <= apprun_version < version.parse("v4.0.0"):
if not runtime_setup and version.parse("v3.0.0") <= apprun_version < version.parse("v4.0.0"):
runtime_setup = AppRunV3Setup(self.context)

if not runtime_setup:
Expand Down
4 changes: 3 additions & 1 deletion appimagebuilder/modules/deploy/apt/deploy.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,8 +66,10 @@ def _resolve_packages_to_deploy(self, include_patterns, exclude_patterns):
required_packages = set(self.apt_venv.search_packages(include_patterns))
excluded_packages = excluded_packages.difference(required_packages)
self.apt_venv.set_installed_packages(excluded_packages)
# lists packages to be installed including dependencies
# lists packages to be installed including dependencies, without explicitly excluded packages
# if a dependency is required to be deployed, please include it in the include list
deploy_list = set(self.apt_venv.resolve_packages(include_patterns))
deploy_list = deploy_list.difference(excluded_packages)

return deploy_list

Expand Down
2 changes: 1 addition & 1 deletion appimagebuilder/modules/setup/apprun_2/apprun2.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ def __init__(self, context: Context, finder: Finder):
self.main_exec = recipe.AppDir.app_info.exec()
self.main_exec_args = recipe.AppDir.app_info.exec_args() or "$@"
self.apprun_version = recipe.AppDir.runtime.version() or "v2.0.0"
self.apprun_debug = recipe.AppDir.runtime.debug()
self.apprun_debug = (recipe.AppDir.runtime.debug().strip().lower() == "true") or False
user_env_input = recipe.AppDir.runtime.env() or {}
self.user_env = self.parse_env_input(user_env_input)
self.apprun_arch = set(recipe.AppDir.runtime.arch() or [])
Expand Down
2 changes: 1 addition & 1 deletion appimagebuilder/modules/setup/apprun_3/app_dir_info.py
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ def read_file_info(entry: pathlib.Path):
if file_info.is_elf:
file_info.interpreter = binary.interpreter
file_info.machine_type = binary.header.machine_type
soname = binary.get(lief.ELF.DYNAMIC_TAGS.SONAME)
soname = binary.get(lief.ELF.DynamicEntry.TAG.SONAME)
# store only the string representation of the soname
if soname:
file_info.soname = soname.name
Expand Down
21 changes: 15 additions & 6 deletions appimagebuilder/modules/setup/apprun_3/apprun3.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
from appimagebuilder.modules.setup.apprun_3.helpers.glibstcpp_module import AppRun3GLibStdCppSetupHelper
from appimagebuilder.modules.setup.apprun_3.helpers.gstreamer import AppRun3GStreamer
from appimagebuilder.modules.setup.apprun_3.helpers.python import AppRun3Python
from appimagebuilder.modules.setup.apprun_3.helpers.mime import AppRun3MIME
from appimagebuilder.modules.setup.apprun_3.helpers.qt import AppRun3QtSetup


Expand Down Expand Up @@ -100,6 +101,10 @@ def _deploy_libapprun_hooks_so(self, arch):

libapprun_so_path = self.context.binaries_resolver.resolve_hooks_library(arch)

libapprun_so_target_path = self.get_hooks_library_target_path(arch)
shutil.copy(libapprun_so_path, libapprun_so_target_path)

def get_hooks_library_target_path(self, arch):
libapprun_so_target_dir = self._find_libapprun_hooks_so_target_dir(arch)

# provide a target dir if none was found
Expand All @@ -109,7 +114,7 @@ def _deploy_libapprun_hooks_so(self, arch):

# copy the libapprun_hooks.so to the target dir
libapprun_so_target_path = libapprun_so_target_dir / "libapprun_hooks.so"
shutil.copy(libapprun_so_path, libapprun_so_target_path)
return libapprun_so_target_path

def _find_libapprun_hooks_so_target_dir(self, arch):
"""Finds a suitable directory for the libapprun_hooks.so"""
Expand All @@ -122,9 +127,12 @@ def _find_libapprun_hooks_so_target_dir(self, arch):
]
# find dedicated folder for the architecture
for base_dir in base_dirs:
for entry in base_dir.iterdir():
if entry.is_dir() and arch in entry.name:
return entry
try:
for entry in base_dir.iterdir():
if entry.is_dir() and arch in entry.name:
return entry
except FileNotFoundError: # /usr/lib64 is often omitted
pass

return None

Expand All @@ -142,7 +150,7 @@ def _deploy_apprun_config(self):

path_env = self._find_dirs_containing_executable_files()
self.context.runtime_env["PATH"] = ":".join(path_env) + ":$PATH"
self.context.runtime_env["LD_PRELOAD"] = "libapprun_hooks.so:$LD_PRELOAD"
self.context.runtime_env["LD_PRELOAD"] = str(self.get_hooks_library_target_path(self.context.main_arch))+":$LD_PRELOAD"

self._set_user_defined_env_vars()

Expand Down Expand Up @@ -303,7 +311,7 @@ def _patch_script_shebang(self, entry: AppDirFileInfo):
f.write(chunk)
logging.info("Patched script shebang: %s", entry.__str__())
else:
logging.warning("Script interpreter not found in AppDir: %s", rel_interpreter_path)
logging.warning("Script interpreter for %s not found in AppDir: %s", entry.path.__str__(), rel_interpreter_path)

def _find_dirs_containing_executable_files(self):
"""Finds the dirs containing executable files"""
Expand Down Expand Up @@ -332,6 +340,7 @@ def _run_setup_helpers(self):
AppRun3GdkPixbuf(self.context),
AppRun3GStreamer(self.context),
AppRun3Python(self.context),
AppRun3MIME(self.context),
]

for helper in helpers:
Expand Down
2 changes: 1 addition & 1 deletion appimagebuilder/modules/setup/apprun_3/apprun3_context.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ class AppRun3Context:
def __init__(self, build_context: Context):
self.build_context = build_context
self.modules_dir = build_context.app_dir / "opt"
self.debug = build_context.recipe.AppDir.runtime.debug() or False
self.debug = (build_context.recipe.AppDir.runtime.debug().strip().lower() == "true") or False
self.path_mappings = build_context.recipe.AppDir.runtime.path_mappings() or []

# init AppRun binaries resolver
Expand Down
15 changes: 9 additions & 6 deletions appimagebuilder/modules/setup/apprun_3/helpers/glibc_module.py
Original file line number Diff line number Diff line change
Expand Up @@ -60,16 +60,16 @@ def _patch_binaries_interpreter_path(self):
for file in self.context.app_dir.files.values():
if file.interpreter and not self._is_file_in_a_module(file) and not file.path.is_symlink():
binary = lief.parse(file.path.__str__())
self._patch_binary_interpreter_path(binary)
self._patch_binary_interpreter_path(binary, file.path.__str__())

def _patch_binary_interpreter_path(self, binary):
def _patch_binary_interpreter_path(self, binary, output):
"""Patch the interpreter of a binary making it relative"""

interpreter = binary.interpreter
new_interpreter = interpreter.lstrip("/")

binary.interpreter = new_interpreter
binary.write(binary.name)
binary.write(output)

def _extract_library_paths_from_glibc_module_files(self):
"""Extracts library paths from glibc module files"""
Expand Down Expand Up @@ -132,9 +132,12 @@ def _find_bundled_glibc_version(self):
# compare with current major version and update if necessary
if version_name and version_name.startswith("GLIBC_"):
version_value = version_name.split("_")[1]
parsed_version = packaging.version.parse(version_value)
if parsed_version > major_version:
major_version = parsed_version
try:
parsed_version = packaging.version.parse(version_value)
if parsed_version > major_version:
major_version = parsed_version
except Exception:
pass

if major_version == packaging.version.parse("0.0.0"):
raise Exception("Could not find glibc library in module files")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ def _generate_glibstdcpp_module_config(self, libstdcpp_version, library_paths):
def _extract_libstdcpp_version(self):
version = None
for entry in self._glibstdcpp_module_files:
if entry.soname == 'libstdc++.so.6':
if entry.soname == 'libstdc++.so.6' and not entry.path.is_symlink():
# extract libstdc++ version from file name
version = entry.path.name.split('.so.')[-1]
break
Expand Down
29 changes: 29 additions & 0 deletions appimagebuilder/modules/setup/apprun_3/helpers/mime.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# Copyright 2020 Alexis Lopez Zubieta
#
# Permission is hereby granted, free of charge, to any person obtaining a
# copy of this software and associated documentation files (the "Software"),
# to deal in the Software without restriction, including without limitation the
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
# sell copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
import logging
import shutil
import subprocess

from appimagebuilder.modules.setup.apprun_3.helpers.base_helper import AppRun3Helper


class AppRun3MIME(AppRun3Helper):
def run(self):
path = self.context.app_dir.path / "usr" / "share" / "mime"
if path.is_dir():
bin_path = shutil.which("update-mime-database")
if not bin_path:
raise RuntimeError("Missing 'update-mime-database' executable")

subprocess.run([bin_path, path])

print("Updated MIME database")
2 changes: 1 addition & 1 deletion appimagebuilder/modules/setup/apprun_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ def is_binary_a_shared_library(binary):

# read soname from ELF header
if binary:
soname = binary.get(lief.ELF.DYNAMIC_TAGS.SONAME)
soname = binary.get(lief.ELF.DynamicEntry.TAG.SONAME)
return soname is not None

return False
Expand Down
2 changes: 1 addition & 1 deletion appimagebuilder/recipe/schema.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ def __init__(self):
}

self.v1_runtime = {
Optional("debug"): bool,
Optional("debug"): str,
Optional("version"): str,
Optional("path_mappings"): [str],
Optional("arch"): [Or("gnueabihf", "x86_64", "i386", "aarch64")],
Expand Down
6 changes: 3 additions & 3 deletions requirements.txt
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
arpy==2.3.0
certifi==2023.7.22
cffi==1.16.0
cffi==1.17.1
charset-normalizer==3.3.0
configparser==6.0.0
contextlib2==21.6.0
Expand All @@ -13,8 +13,8 @@ filelock==3.12.4
idna==3.4
jsonpath-rw==1.4.0
libconf==2.0.1
lief==0.12.2
packaging==23.2
lief==0.16.4
packaging==24.2
PGPy==0.6.0
pipenv==2023.10.3
platformdirs==3.11.0
Expand Down
2 changes: 1 addition & 1 deletion tests/recipe/test_validator.py
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ def test_validate_appdir(self):
},
"arch": ["i386", "x86_64", "aarch64", "gnueabihf"],
"preserve": ["usr/bin/example"],
"debug": False,
"debug": "False",
},
"files": {"include": ["/one", "/two"], "exclude": ["three", "four"]},
"test": {
Expand Down