This commit is contained in:
arcolinuxz 2024-06-25 11:31:02 +02:00
parent b09f56fa6c
commit 92433c3100
10 changed files with 332 additions and 196 deletions

View file

@ -72,9 +72,9 @@ case "$SESSION" in
start_in_tty start_in_tty
;; ;;
*) *)
# anything here is an unknown session, most likely AKM will fail to load # anything here is an unknown session, fallback to XDG_SESSION_TYPE
echo "[INFO]: Display = $DISPLAY" echo "[INFO]: Display = $DISPLAY"
echo "[INFO]: Session could not be verified ... falling back to use XDG_SESSION_TYPE" echo "[WARN]: Session could not be verified, using XDG_SESSION_TYPE"
case "$XDG_SESSION_TYPE" in case "$XDG_SESSION_TYPE" in
"wayland") "wayland")

View file

@ -57,7 +57,7 @@ box#vbox_header{
} }
box#hbox_warning{ box#hbox_warning{
background-color: #4c8bf5; background-color: #004085;
color: white; color: white;
font-family: 'Noto Sans', 'Helvetica', sans-serif; font-family: 'Noto Sans', 'Helvetica', sans-serif;
padding: 5px 5px 5px 5px; padding: 5px 5px 5px 5px;
@ -72,7 +72,7 @@ label#label_notify_revealer{
label#label_active_kernel { label#label_active_kernel {
font-family: 'Noto Sans', 'Helvetica', sans-serif; font-family: 'Noto Sans', 'Helvetica', sans-serif;
font-size: 11px; font-size: 12px;
} }
label#label_stack_kernel { label#label_stack_kernel {

View file

@ -1,6 +1,5 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import os import os
import gi import gi
import signal import signal
import libs.functions as fn import libs.functions as fn
@ -18,8 +17,9 @@ app_name = "Arch Linux Kernel Manager"
app_version = "${app_version}" app_version = "${app_version}"
app_name_dir = "archlinux-kernel-manager" app_name_dir = "archlinux-kernel-manager"
app_id = "com.arcolinux.kernelmanager" app_id = "com.arcolinux.kernelmanager"
lock_file = "/tmp/akm.lock" lock_file = "/tmp/.akm.lock"
pid_file = "/tmp/akm.pid" progress_lock_file = "/tmp/.akm-progress.lock"
pid_file = "/tmp/.akm.pid"
class Main(Gtk.Application): class Main(Gtk.Application):
@ -61,6 +61,8 @@ class Main(Gtk.Application):
os.remove(lock_file) os.remove(lock_file)
if os.path.exists(pid_file): if os.path.exists(pid_file):
os.remove(pid_file) os.remove(pid_file)
if os.path.exists(progress_lock_file):
os.remove(progress_lock_file)
def signal_handler(sig, frame): def signal_handler(sig, frame):

View file

@ -1,4 +1,4 @@
# Store kernel data taken from # Store kernel data from ALA, pacman sync db
import datetime import datetime
from datetime import datetime from datetime import datetime

View file

@ -14,6 +14,7 @@ import datetime
import psutil import psutil
import queue import queue
import pathlib import pathlib
import locale
import tomlkit import tomlkit
from tomlkit import dumps, load from tomlkit import dumps, load
from datetime import timedelta from datetime import timedelta
@ -26,17 +27,17 @@ from libs.Kernel import Kernel, InstalledKernel, CommunityKernel
gi.require_version("Gtk", "4.0") gi.require_version("Gtk", "4.0")
from gi.repository import GLib from gi.repository import GLib
base_dir = os.path.abspath(os.path.join(os.path.dirname(__file__), "..")) base_dir = os.path.abspath(os.path.join(os.path.dirname(__file__), ".."))
latest_archlinux_package_search_url = ( latest_archlinux_package_search_url = (
"https://archlinux.org/packages/search/json?name=${PACKAGE_NAME}" "https://archlinux.org/packages/search/json?name=${PACKAGE_NAME}"
) )
archlinux_mirror_archive_url = "https://archive.archlinux.org" archlinux_mirror_archive_url = "https://archive.archlinux.org"
headers = {"Content-Type": "text/plain;charset=UTF-8"} headers = {
"Content-Type": "text/plain;charset=UTF-8",
"User-Agent": "Mozilla/5.0 (Linux x86_64) Gecko Firefox",
}
dist_id = distro.id()
dist_name = distro.name()
cache_days = 5 cache_days = 5
fetched_kernels_dict = {} fetched_kernels_dict = {}
@ -102,6 +103,11 @@ ch.setFormatter(formatter)
# add ch to logger # add ch to logger
logger.addHandler(ch) logger.addHandler(ch)
# set locale
locale.setlocale(locale.LC_ALL, "C.utf8")
locale_env = os.environ
locale_env["LC_ALL"] = "C.utf8"
# ===================================================== # =====================================================
# CHECK FOR KERNEL UPDATES # CHECK FOR KERNEL UPDATES
@ -274,12 +280,17 @@ def permissions(dst):
shell=False, shell=False,
stdout=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
env=locale_env,
) )
for x in groups.stdout.decode().split(" "): for x in groups.stdout.decode().split(" "):
if "gid" in x: if "gid" in x:
g = x.split("(")[1] g = x.split("(")[1]
group = g.replace(")", "").strip() group = g.replace(")", "").strip()
subprocess.call(["chown", "-R", sudo_username + ":" + group, dst], shell=False) subprocess.call(
["chown", "-R", sudo_username + ":" + group, dst],
shell=False,
env=locale_env,
)
except Exception as e: except Exception as e:
logger.error("Exception in permissions(): %s" % e) logger.error("Exception in permissions(): %s" % e)
@ -422,6 +433,7 @@ def install_archive_kernel(self):
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -592,13 +604,13 @@ def read_cache(self):
# any kernels older than 2 years # any kernels older than 2 years
# (currently linux v4.x or earlier) are deemed eol so ignore them # (currently linux v4.x or earlier) are deemed eol so ignore them
# if ( if (
# datetime.datetime.now().year datetime.datetime.now().year
# - datetime.datetime.strptime( - datetime.datetime.strptime(
# k["last_modified"], "%d-%b-%Y %H:%M" k["last_modified"], "%d-%b-%Y %H:%M"
# ).year ).year
# <= 2 <= 2
# ): ):
cached_kernels_list.append( cached_kernels_list.append(
Kernel( Kernel(
k["name"], k["name"],
@ -634,24 +646,29 @@ def read_cache(self):
# get latest versions of the official kernels # get latest versions of the official kernels
def get_latest_versions(self): def get_latest_versions(self):
try: logger.info("Getting latest kernel information")
kernel_versions = {} kernel_versions = {}
try:
for kernel in supported_kernels_dict: for kernel in supported_kernels_dict:
check_cmd_str = ["pacman", "-Si", kernel] check_cmd_str = ["pacman", "-Si", kernel]
process_kernel_query = subprocess.Popen( with subprocess.Popen(
check_cmd_str, check_cmd_str,
shell=False,
stdout=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.PIPE, stderr=subprocess.STDOUT,
bufsize=1,
universal_newlines=True,
env=locale_env,
) as process:
while True:
if process.poll() is not None:
break
for line in process.stdout:
if line.strip().replace(" ", "").startswith("Version:"):
kernel_versions[kernel] = (
line.strip().replace(" ", "").split("Version:")[1]
) )
out, err = process_kernel_query.communicate(timeout=process_timeout)
if process_kernel_query.returncode == 0:
for line in out.decode("utf-8").splitlines():
if line.startswith("Version :"):
kernel_versions[kernel] = line.split("Version :")[1]
break break
self.kernel_versions_queue.put(kernel_versions) self.kernel_versions_queue.put(kernel_versions)
@ -721,7 +738,6 @@ def parse_archive_html(response, linux_kernel):
def wait_for_response(response_queue): def wait_for_response(response_queue):
while True: while True:
# time.sleep(0.1)
items = response_queue.get() items = response_queue.get()
# error break from loop # error break from loop
@ -782,15 +798,11 @@ def get_official_kernels(self):
for kernel in response_content: for kernel in response_content:
parse_archive_html(response_content[kernel], kernel) parse_archive_html(response_content[kernel], kernel)
if len(fetched_kernels_dict) > 0: # and self.refresh_cache is True: if len(fetched_kernels_dict) > 0:
write_cache() write_cache()
read_cache(self) read_cache(self)
self.queue_kernels.put(cached_kernels_list) self.queue_kernels.put(cached_kernels_list)
# elif self.refresh_cache is False:
# logger.info("Cache already processed")
# read_cache(self)
# self.queue_kernels.put(cached_kernels_list)
else: else:
logger.error("Failed to retrieve Linux Kernel list") logger.error("Failed to retrieve Linux Kernel list")
@ -887,18 +899,22 @@ def check_kernel_installed(name):
check_cmd_str = ["pacman", "-Q", name] check_cmd_str = ["pacman", "-Q", name]
logger.debug("Running cmd = %s" % check_cmd_str) logger.debug("Running cmd = %s" % check_cmd_str)
process_kernel_query = subprocess.Popen( process_kernel_query = subprocess.Popen(
check_cmd_str, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE check_cmd_str,
shell=False,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
env=locale_env,
) )
out, err = process_kernel_query.communicate(timeout=process_timeout) out, err = process_kernel_query.communicate(timeout=process_timeout)
logger.debug(out.decode("utf-8"))
if process_kernel_query.returncode == 0: if process_kernel_query.returncode == 0:
for line in out.decode("utf-8").splitlines(): for line in out.decode("utf-8").splitlines():
if line.split(" ")[0] == name: if line.split(" ")[0] == name:
# logger.debug("Kernel installed")
return True return True
else: else:
# logger.debug("Kernel is not installed")
return False return False
return False return False
@ -971,6 +987,7 @@ def uninstall(self):
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -1069,6 +1086,7 @@ def get_community_kernels(self):
shell=False, shell=False,
stdout=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.PIPE, stderr=subprocess.PIPE,
env=locale_env,
) )
out, err = process_kernel_query.communicate(timeout=process_timeout) out, err = process_kernel_query.communicate(timeout=process_timeout)
version = None version = None
@ -1139,6 +1157,7 @@ def install_community_kernel(self):
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -1159,8 +1178,6 @@ def install_community_kernel(self):
error = True error = True
if check_kernel_installed(self.kernel.name) and error is False: if check_kernel_installed(self.kernel.name) and error is False:
logger.info("Kernel = installed")
self.kernel_state_queue.put((0, "install", self.kernel.name)) self.kernel_state_queue.put((0, "install", self.kernel.name))
event = "%s [INFO]: Installation of %s completed\n" % ( event = "%s [INFO]: Installation of %s completed\n" % (
@ -1171,8 +1188,6 @@ def install_community_kernel(self):
self.messages_queue.put(event) self.messages_queue.put(event)
else: else:
logger.error("Kernel = install failed")
self.kernel_state_queue.put((1, "install", self.kernel.name)) self.kernel_state_queue.put((1, "install", self.kernel.name))
event = "%s [ERROR]: Installation of %s failed\n" % ( event = "%s [ERROR]: Installation of %s failed\n" % (
@ -1213,6 +1228,7 @@ def get_pacman_repos():
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -1233,8 +1249,13 @@ def get_installed_kernel_info(package_name):
query_str = ["pacman", "-Qi", package_name] query_str = ["pacman", "-Qi", package_name]
try: try:
process_kernel_query = subprocess.Popen( process_kernel_query = subprocess.Popen(
query_str, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE query_str,
shell=False,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
env=locale_env,
) )
out, err = process_kernel_query.communicate(timeout=process_timeout) out, err = process_kernel_query.communicate(timeout=process_timeout)
install_size = None install_size = None
@ -1264,16 +1285,21 @@ def get_installed_kernels():
installed_kernels = [] installed_kernels = []
try: try:
process_kernel_query = subprocess.Popen( with subprocess.Popen(
query_str, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE query_str,
) shell=False,
stdout=subprocess.PIPE,
out, err = process_kernel_query.communicate(timeout=process_timeout) stderr=subprocess.PIPE,
if process_kernel_query.returncode == 0: universal_newlines=True,
for line in out.decode("utf-8").splitlines(): env=locale_env,
) as process:
while True:
if process.poll() is not None:
break
for line in process.stdout:
if line.lower().strip().startswith("linux"): if line.lower().strip().startswith("linux"):
package_name = line.split(" ")[0] package_name = line.split(" ")[0].strip()
package_version = line.split(" ")[1] package_version = line.split(" ")[1].strip()
if ( if (
package_name in supported_kernels_dict package_name in supported_kernels_dict
@ -1290,10 +1316,10 @@ def get_installed_kernels():
) )
installed_kernels.append(installed_kernel) installed_kernels.append(installed_kernel)
return installed_kernels
except Exception as e: except Exception as e:
logger.error("Exception in get_installed_kernels(): %s" % e) logger.error("Exception in get_installed_kernels(): %s" % e)
finally:
return installed_kernels
# ====================================================================== # ======================================================================
@ -1307,7 +1333,11 @@ def get_active_kernel():
try: try:
process_kernel_query = subprocess.Popen( process_kernel_query = subprocess.Popen(
query_str, shell=False, stdout=subprocess.PIPE, stderr=subprocess.PIPE query_str,
shell=False,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
env=locale_env,
) )
out, err = process_kernel_query.communicate(timeout=process_timeout) out, err = process_kernel_query.communicate(timeout=process_timeout)
@ -1339,6 +1369,7 @@ def sync_package_db():
stdout=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
timeout=process_timeout, timeout=process_timeout,
env=locale_env,
) )
if process_sync.returncode == 0: if process_sync.returncode == 0:
@ -1367,6 +1398,7 @@ def get_boot_loader():
timeout=process_timeout, timeout=process_timeout,
universal_newlines=True, universal_newlines=True,
bufsize=1, bufsize=1,
env=locale_env,
) )
if process.returncode == 0: if process.returncode == 0:
@ -1376,9 +1408,14 @@ def get_boot_loader():
if "grub" in product.lower(): if "grub" in product.lower():
logger.info("bootctl product reports booted with grub") logger.info("bootctl product reports booted with grub")
return "grub" return "grub"
if "systemd-boot" in product.lower(): elif "systemd-boot" in product.lower():
logger.info("bootcl product reports booted with systemd-boot") logger.info("bootctl product reports booted with systemd-boot")
return "systemd-boot" return "systemd-boot"
else:
# "n/a" in product
logger.info("bootctl product reports n/a, using default grub")
return "grub"
elif line.strip().startswith("Not booted with EFI"): # noqa elif line.strip().startswith("Not booted with EFI"): # noqa
# bios # bios
logger.info( logger.info(
@ -1411,6 +1448,7 @@ def get_kernel_version(kernel):
timeout=process_timeout, timeout=process_timeout,
universal_newlines=True, universal_newlines=True,
bufsize=1, bufsize=1,
env=locale_env,
) )
if process.returncode == 0: if process.returncode == 0:
@ -1440,14 +1478,20 @@ def get_kernel_version(kernel):
def run_process(self): def run_process(self):
error = False error = False
self.stdout_lines = []
logger.debug("Running process = %s" % " ".join(self.cmd)) logger.debug("Running process = %s" % " ".join(self.cmd))
event = "%s [INFO]: Running %s\n" % (
datetime.datetime.now().strftime("%Y-%m-%d-%H-%M-%S"),
" ".join(self.cmd),
)
self.messages_queue.put(event)
with subprocess.Popen( with subprocess.Popen(
self.cmd, self.cmd,
stdout=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -1458,9 +1502,8 @@ def run_process(self):
print(line.strip()) print(line.strip())
for log in self.stdout_lines: for log in self.stdout_lines:
if "error" in log or "errors" in log: if "error" in log or "errors" in log or "failed" in log:
self.errors_found = True self.errors_found = True
error = True error = True
if error is True: if error is True:
@ -1485,29 +1528,49 @@ def run_process(self):
# grub - grub-mkconfig /boot/grub/grub.cfg # grub - grub-mkconfig /boot/grub/grub.cfg
# systemd-boot - bootctl update # systemd-boot - bootctl update
def update_bootloader(self): def update_bootloader(self):
logger.info("Updating bootloader")
cmds = [] cmds = []
error = False error = False
self.stdout_lines = [] self.stdout_lines = []
if self.action == "install": if self.action == "install":
image = "images/48x48/akm-install.png" image = "images/48x48/akm-install.png"
if self.installed_kernel_version is not None: if self.installed_kernel_version is not None:
for self.cmd in [ for self.cmd in [
["kernel-install", "add-all"], # ["kernel-install", "add-all", "--verbose"],
["kernel-install", "remove", self.installed_kernel_version], [
"kernel-install",
"add",
self.installed_kernel_version,
"/lib/modules/%s/vmlinuz" % self.installed_kernel_version,
],
[
"kernel-install",
"remove",
self.installed_kernel_version,
],
]: ]:
run_process(self) run_process(self)
else: else:
self.cmd = ["kernel-install", "add-all"] # self.cmd = ["kernel-install", "add-all", "--verbose"].
self.installed_kernel_version = get_kernel_version(self.kernel.name)
self.cmd = [
"kernel-install",
"add",
self.installed_kernel_version,
"/lib/modules/%s/vmlinuz" % self.installed_kernel_version,
]
run_process(self) run_process(self)
else: else:
image = "images/48x48/akm-remove.png" image = "images/48x48/akm-remove.png"
if self.installed_kernel_version is not None: if self.installed_kernel_version is not None:
self.cmd = ["kernel-install", "remove", self.installed_kernel_version] self.cmd = [
"kernel-install",
"remove",
self.installed_kernel_version,
]
run_process(self) run_process(self)
try: try:
@ -1559,6 +1622,7 @@ def update_bootloader(self):
stderr=subprocess.STDOUT, stderr=subprocess.STDOUT,
bufsize=1, bufsize=1,
universal_newlines=True, universal_newlines=True,
env=locale_env,
) as process: ) as process:
while True: while True:
if process.poll() is not None: if process.poll() is not None:
@ -1661,10 +1725,14 @@ def update_bootloader(self):
image, image,
priority=GLib.PRIORITY_DEFAULT, priority=GLib.PRIORITY_DEFAULT,
) )
if os.path.exists(self.lockfile):
os.unlink(self.lockfile)
# else: # else:
# logger.error("Bootloader update cannot continue, failed to set command.") # logger.error("Bootloader update cannot continue, failed to set command.")
except Exception as e: except Exception as e:
logger.error("Exception in update_bootloader(): %s" % e) logger.error("Exception in update_bootloader(): %s" % e)
if os.path.exists(self.lockfile):
os.unlink(self.lockfile)
# ====================================================================== # ======================================================================

View file

@ -54,7 +54,6 @@ class FlowBox(Gtk.FlowBox):
def flowbox_community(self): def flowbox_community(self):
for community_kernel in self.kernel: for community_kernel in self.kernel:
self.kernels.append(community_kernel) self.kernels.append(community_kernel)
self.kernel_count += 1 self.kernel_count += 1
if len(self.kernels) > 0: if len(self.kernels) > 0:

View file

@ -135,7 +135,7 @@ class KernelStack:
label_active_installed_kernel.set_selectable(True) label_active_installed_kernel.set_selectable(True)
label_active_installed_kernel.set_markup( label_active_installed_kernel.set_markup(
"<b>Active kernel:</b> %s" % self.manager_gui.active_kernel "Active kernel: <b>%s</b>" % self.manager_gui.active_kernel
) )
label_active_installed_kernel.set_halign(Gtk.Align.START) label_active_installed_kernel.set_halign(Gtk.Align.START)
self.manager_gui.vbox_active_installed_kernel.append( self.manager_gui.vbox_active_installed_kernel.append(
@ -235,7 +235,7 @@ class KernelStack:
label_active_kernel.set_name("label_active_kernel") label_active_kernel.set_name("label_active_kernel")
label_active_kernel.set_selectable(True) label_active_kernel.set_selectable(True)
label_active_kernel.set_markup( label_active_kernel.set_markup(
"<b>Active kernel:</b> %s" % self.manager_gui.active_kernel "Active kernel: <b>%s</b>" % self.manager_gui.active_kernel
) )
label_active_kernel.set_halign(Gtk.Align.START) label_active_kernel.set_halign(Gtk.Align.START)
@ -250,7 +250,7 @@ class KernelStack:
self.flowbox_stacks.append(self.flowbox_official_kernel) self.flowbox_stacks.append(self.flowbox_official_kernel)
vbox_flowbox = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=12) vbox_flowbox = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=0)
vbox_flowbox.set_name("vbox_flowbox_%s" % kernel) vbox_flowbox.set_name("vbox_flowbox_%s" % kernel)
# vbox_flowbox.set_halign(align=Gtk.Align.FILL) # vbox_flowbox.set_halign(align=Gtk.Align.FILL)
vbox_flowbox.append(self.flowbox_official_kernel) vbox_flowbox.append(self.flowbox_official_kernel)
@ -424,7 +424,7 @@ class KernelStack:
label_active_kernel.set_name("label_active_kernel") label_active_kernel.set_name("label_active_kernel")
label_active_kernel.set_selectable(True) label_active_kernel.set_selectable(True)
label_active_kernel.set_markup( label_active_kernel.set_markup(
"<b>Active kernel:</b> %s" % self.manager_gui.active_kernel "Active kernel: <b>%s</b>" % self.manager_gui.active_kernel
) )
label_active_kernel.set_halign(Gtk.Align.START) label_active_kernel.set_halign(Gtk.Align.START)
@ -464,8 +464,16 @@ class KernelStack:
label_warning = Gtk.Label(xalign=0, yalign=0) label_warning = Gtk.Label(xalign=0, yalign=0)
label_warning.set_name("label_community_warning") label_warning.set_name("label_community_warning")
if len(self.manager_gui.community_kernels) == 0:
label_warning.set_markup( label_warning.set_markup(
f"These are user produced content\n" f"<b>Cannot find any supported unofficial pacman repository's</b>\n"
f"<b>Add the Chaotic-AUR pacman repository to access Community based kernels</b>"
)
else:
label_warning.set_markup(
f"These kernels are user produced content\n"
f"These kernels may not work on your hardware\n"
f"<b>Any use of the provided files is at your own risk</b>" f"<b>Any use of the provided files is at your own risk</b>"
) )
@ -477,6 +485,21 @@ class KernelStack:
if stack_child is not None: if stack_child is not None:
for stack_widget in stack_child: for stack_widget in stack_child:
if stack_widget.get_name() == "hbox_warning":
for w in stack_widget:
if w.get_name() == "label_community_warning":
if len(self.manager_gui.community_kernels) == 0:
w.set_markup(
f"<b>Cannot find any supported unofficial pacman repository's</b>\n"
f"<b>Add the Chaotic-AUR pacman repository to access Community based kernels</b>"
)
else:
w.set_markup(
f"These kernels are user produced content\n"
f"These kernels may not work on your hardware\n"
f"<b>Any use of the provided files is at your own risk</b>"
)
break
if stack_widget.get_name() == "label_stack_count": if stack_widget.get_name() == "label_stack_count":
stack_widget.set_markup( stack_widget.set_markup(
"<i>%s Available kernels</i>" "<i>%s Available kernels</i>"
@ -495,22 +518,18 @@ class KernelStack:
vbox_flowbox = scrolled_window_community.get_child().get_child() vbox_flowbox = scrolled_window_community.get_child().get_child()
for widget in vbox_flowbox: for widget in vbox_flowbox:
if widget.get_name() != "vbox_no_community":
widget.remove_all() widget.remove_all()
else:
# scrolled_window_community.hide()
# vbox_search_entry = Gtk.Box(
# orientation=Gtk.Orientation.VERTICAL, spacing=5
# )
#
# vbox_search_entry.append(search_entry_community)
# widget.append(vbox_search_entry)
if len(self.manager_gui.community_kernels) > 0: if len(self.manager_gui.community_kernels) > 0:
# widget.hide()
for box_widget in widget:
box_widget.hide()
vbox_search_entry = Gtk.Box(
orientation=Gtk.Orientation.VERTICAL, spacing=5
)
vbox_search_entry.append(search_entry_community)
# widget.append(hbox_warning)
widget.append(vbox_search_entry)
self.flowbox_community = FlowBox( self.flowbox_community = FlowBox(
self.manager_gui.community_kernels, self.manager_gui.community_kernels,
self.manager_gui.active_kernel, self.manager_gui.active_kernel,
@ -519,13 +538,13 @@ class KernelStack:
) )
vbox_flowbox.append(self.flowbox_community) vbox_flowbox.append(self.flowbox_community)
while self.manager_gui.default_context.pending(): # while self.manager_gui.default_context.pending():
# fn.time.sleep(0.1) # # fn.time.sleep(0.1)
self.manager_gui.default_context.iteration(True) # self.manager_gui.default_context.iteration(True)
else: else:
self.flowbox_community = None self.flowbox_community = None
vbox_flowbox = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=12) vbox_flowbox = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=0)
# vbox_flowbox.set_halign(align=Gtk.Align.FILL) # vbox_flowbox.set_halign(align=Gtk.Align.FILL)
if len(self.manager_gui.community_kernels) == 0: if len(self.manager_gui.community_kernels) == 0:
@ -619,6 +638,7 @@ class KernelStack:
if vbox_search_entry is not None: if vbox_search_entry is not None:
vbox_kernels.append(vbox_search_entry) vbox_kernels.append(vbox_search_entry)
vbox_kernels.append(hbox_sep_kernels) vbox_kernels.append(hbox_sep_kernels)
scrolled_window_community.set_child(vbox_flowbox) scrolled_window_community.set_child(vbox_flowbox)

View file

@ -29,6 +29,7 @@ class ManagerGUI(Gtk.ApplicationWindow):
self.app_version = "dev" self.app_version = "dev"
fn.logger.info("Version = %s" % self.app_version) fn.logger.info("Version = %s" % self.app_version)
fn.logger.info("Distro = %s" % fn.distro.id())
self.set_title(app_name) self.set_title(app_name)
self.set_resizable(True) self.set_resizable(True)
@ -47,6 +48,20 @@ class ManagerGUI(Gtk.ApplicationWindow):
# community kernels queue for threading # community kernels queue for threading
self.queue_community_kernels = fn.Queue() self.queue_community_kernels = fn.Queue()
self.splash_screen = SplashScreen(app_name)
while self.default_context.pending():
fn.time.sleep(0.1)
self.default_context.iteration(True)
try:
fn.Thread(
target=self.wait_for_gui_load,
daemon=True,
).start()
except Exception as e:
fn.logger.error(e)
hbox_notify_revealer = Gtk.Box( hbox_notify_revealer = Gtk.Box(
orientation=Gtk.Orientation.HORIZONTAL, spacing=20 orientation=Gtk.Orientation.HORIZONTAL, spacing=20
) )
@ -62,19 +77,9 @@ class ManagerGUI(Gtk.ApplicationWindow):
hbox_notify_revealer.append(self.label_notify_revealer) hbox_notify_revealer.append(self.label_notify_revealer)
self.splash_screen = SplashScreen(app_name) # while self.default_context.pending():
# fn.time.sleep(0.1)
try: # self.default_context.iteration(True)
fn.Thread(
target=self.wait_for_gui_load,
daemon=True,
).start()
except Exception as e:
fn.logger.error(e)
while self.default_context.pending():
fn.time.sleep(0.1)
self.default_context.iteration(True)
self.bootloader = None self.bootloader = None
self.bootloader_grub_cfg = None self.bootloader_grub_cfg = None
@ -276,30 +281,6 @@ class ManagerGUI(Gtk.ApplicationWindow):
self.official_kernels = self.queue_kernels.get() self.official_kernels = self.queue_kernels.get()
self.queue_kernels.task_done() self.queue_kernels.task_done()
fn.logger.info("Starting pacman db synchronization thread")
self.queue_load_progress.put("Starting pacman db synchronization")
self.pacman_db_sync()
fn.logger.info("Starting get community kernels thread")
self.queue_load_progress.put("Getting community based Linux kernels")
try:
thread_get_community_kernels = fn.Thread(
name=fn.thread_get_community_kernels,
target=fn.get_community_kernels,
daemon=True,
args=(self,),
)
thread_get_community_kernels.start()
except Exception as e:
fn.logger.error("Exception in thread_get_community_kernels: %s" % e)
finally:
self.community_kernels = self.queue_community_kernels.get()
self.queue_community_kernels.task_done()
# ===================================================== # =====================================================
# PACMAN DB SYNC # PACMAN DB SYNC
# ===================================================== # =====================================================
@ -339,8 +320,9 @@ class ManagerGUI(Gtk.ApplicationWindow):
# keep splash screen open, until main gui is loaded # keep splash screen open, until main gui is loaded
def wait_for_gui_load(self): def wait_for_gui_load(self):
while True: while True:
fn.time.sleep(0.2) # fn.time.sleep(0.2)
status = self.queue_load_progress.get() status = self.queue_load_progress.get()
if status == 1: if status == 1:
GLib.idle_add( GLib.idle_add(
self.splash_screen.destroy, self.splash_screen.destroy,
@ -385,6 +367,26 @@ class ManagerGUI(Gtk.ApplicationWindow):
self.start_get_kernels_threads() self.start_get_kernels_threads()
self.pacman_db_sync()
fn.logger.debug("Adding community kernels to UI")
try:
thread_get_community_kernels = fn.Thread(
name=fn.thread_get_community_kernels,
target=fn.get_community_kernels,
daemon=True,
args=(self,),
)
thread_get_community_kernels.start()
except Exception as e:
fn.logger.error("Exception in thread_get_community_kernels: %s" % e)
finally:
self.community_kernels = self.queue_community_kernels.get()
self.queue_community_kernels.task_done()
self.installed_kernels = fn.get_installed_kernels() self.installed_kernels = fn.get_installed_kernels()
self.label_notify_revealer.set_text("Refreshing official kernels") self.label_notify_revealer.set_text("Refreshing official kernels")
@ -499,8 +501,35 @@ class ManagerGUI(Gtk.ApplicationWindow):
# add official kernel flowbox # add official kernel flowbox
fn.logger.debug("Adding official kernels to UI") fn.logger.debug("Adding official kernels to UI")
self.kernel_stack.add_official_kernels_to_stack(reload=False) self.kernel_stack.add_official_kernels_to_stack(reload=False)
# fn.logger.debug("Adding community kernels to UI")
# self.kernel_stack.add_community_kernels_to_stack(reload=False)
self.queue_load_progress.put(1)
fn.logger.info("Starting pacman db synchronization")
self.pacman_db_sync()
fn.logger.debug("Adding community kernels to UI")
try:
thread_get_community_kernels = fn.Thread(
name=fn.thread_get_community_kernels,
target=fn.get_community_kernels,
daemon=True,
args=(self,),
)
thread_get_community_kernels.start()
except Exception as e:
fn.logger.error("Exception in thread_get_community_kernels: %s" % e)
finally:
self.community_kernels = self.queue_community_kernels.get()
self.queue_community_kernels.task_done()
fn.logger.debug("Adding community kernels to UI") fn.logger.debug("Adding community kernels to UI")
self.kernel_stack.add_community_kernels_to_stack(reload=False) self.kernel_stack.add_community_kernels_to_stack(reload=False)
@ -510,7 +539,4 @@ class ManagerGUI(Gtk.ApplicationWindow):
while self.default_context.pending(): while self.default_context.pending():
self.default_context.iteration(True) self.default_context.iteration(True)
fn.time.sleep(0.3) fn.time.sleep(0.1)
self.queue_load_progress.put(1)
fn.logger.info("Kernel manager UI loaded")

View file

@ -1,3 +1,4 @@
import random
import sys import sys
import gi import gi
import os import os
@ -26,7 +27,7 @@ class ProgressWindow(Gtk.Window):
self.set_title(title=title) self.set_title(title=title)
self.set_modal(modal=True) self.set_modal(modal=True)
self.set_resizable(True) self.set_resizable(True)
self.set_size_request(700, 400) self.set_size_request(700, 300)
self.connect("close-request", self.on_close) self.connect("close-request", self.on_close)
self.textview = textview self.textview = textview
@ -34,9 +35,19 @@ class ProgressWindow(Gtk.Window):
self.kernel_state_queue = fn.Queue() self.kernel_state_queue = fn.Queue()
self.messages_queue = fn.Queue() self.messages_queue = fn.Queue()
# create temp file to lock the close button
self.lockfile = "/tmp/.akm-progress.lock"
if os.path.exists(self.lockfile):
os.unlink(self.lockfile)
with open(self.lockfile, "w") as f:
f.write("")
self.kernel = kernel self.kernel = kernel
self.timeout_id = None self.timeout_id = None
self.errors_found = False self.errors_found = False
self.restore_kernel = None
self.action = action self.action = action
self.switch = switch self.switch = switch
@ -164,10 +175,10 @@ class ProgressWindow(Gtk.Window):
) )
self.hbox_spinner = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=5) self.hbox_spinner = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=5)
self.hbox_spinner.append(self.label_spinner_progress)
self.hbox_spinner.append(self.spinner) self.hbox_spinner.append(self.spinner)
self.hbox_spinner.append(self.label_spinner_progress)
vbox_padding = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=20) vbox_padding = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=5)
vbox_padding.set_valign(Gtk.Align.END) vbox_padding.set_valign(Gtk.Align.END)
label_padding = Gtk.Label(xalign=0, yalign=0) label_padding = Gtk.Label(xalign=0, yalign=0)
@ -220,7 +231,7 @@ class ProgressWindow(Gtk.Window):
vbox_progress.append(self.scrolled_window) vbox_progress.append(self.scrolled_window)
vbox_progress.append(self.hbox_spinner) vbox_progress.append(self.hbox_spinner)
vbox_progress.append(self.label_status) vbox_progress.append(self.label_status)
vbox_progress.append(vbox_padding) # vbox_progress.append(vbox_padding)
vbox_progress.append(hbox_button_close) vbox_progress.append(hbox_button_close)
self.present() self.present()
@ -401,7 +412,7 @@ class ProgressWindow(Gtk.Window):
self.timeout_id = GLib.timeout_add(3000, self.timeout) self.timeout_id = GLib.timeout_add(3000, self.timeout)
def on_button_close_response(self, widget): def on_button_close_response(self, widget):
if fn.check_pacman_process(self): if fn.check_pacman_process(self) or os.path.exists(self.lockfile):
mw = MessageWindow( mw = MessageWindow(
title="Pacman process running", title="Pacman process running",
message="Pacman is busy processing a transaction .. please wait", message="Pacman is busy processing a transaction .. please wait",
@ -415,7 +426,7 @@ class ProgressWindow(Gtk.Window):
self.destroy() self.destroy()
def on_close(self, data): def on_close(self, data):
if fn.check_pacman_process(self): if fn.check_pacman_process(self) or os.path.exists(self.lockfile):
mw = MessageWindow( mw = MessageWindow(
title="Pacman process running", title="Pacman process running",
message="Pacman is busy processing a transaction .. please wait", message="Pacman is busy processing a transaction .. please wait",
@ -468,6 +479,11 @@ class ProgressWindow(Gtk.Window):
# undo action here if action == install # undo action here if action == install
if (
action == "install"
and self.restore_kernel is not None
and self.source == "official"
):
event = ( event = (
"%s<b> [INFO]: Attempting to undo previous Linux package changes</b>\n" "%s<b> [INFO]: Attempting to undo previous Linux package changes</b>\n"
% ( % (
@ -479,7 +495,6 @@ class ProgressWindow(Gtk.Window):
self.messages_queue.put(event) self.messages_queue.put(event)
if action == "install" and self.restore_kernel is not None:
self.restore = True self.restore = True
fn.logger.info( fn.logger.info(
"Installation failed, attempting removal of previous Linux package changes" "Installation failed, attempting removal of previous Linux package changes"
@ -523,9 +538,14 @@ class ProgressWindow(Gtk.Window):
f"<span foreground='orange'><b>Kernel %s failed - see logs above</b></span>\n" f"<span foreground='orange'><b>Kernel %s failed - see logs above</b></span>\n"
% action % action
) )
else:
self.spinner.set_spinning(False)
self.hbox_spinner.hide()
self.set_title("Kernel installation failed")
self.label_title.set_markup("<b>Install failed</b>")
# self.spinner.set_spinning(False)
# self.hbox_spinner.hide()
# #
# self.label_progress_window_desc.set_markup( # self.label_progress_window_desc.set_markup(
# f"<b>This window can be now closed</b>\n" # f"<b>This window can be now closed</b>\n"
@ -597,6 +617,8 @@ class ProgressWindow(Gtk.Window):
break break
except Exception as e: except Exception as e:
fn.logger.error("Exception in check_kernel_state(): %s" % e) fn.logger.error("Exception in check_kernel_state(): %s" % e)
if os.path.exists(self.lockfile):
os.unlink(self.lockfile)
finally: finally:
self.kernel_state_queue.task_done() self.kernel_state_queue.task_done()

View file

@ -180,8 +180,6 @@ class SettingsWindow(Gtk.Window):
vbox_community_warning = Gtk.Box( vbox_community_warning = Gtk.Box(
orientation=Gtk.Orientation.VERTICAL, spacing=10 orientation=Gtk.Orientation.VERTICAL, spacing=10
) )
vbox_community_warning.set_name("box")
image_warning = Gtk.Image.new_from_file( image_warning = Gtk.Image.new_from_file(
os.path.join(base_dir, "images/48x48/akm-warning.png") os.path.join(base_dir, "images/48x48/akm-warning.png")
) )
@ -190,14 +188,15 @@ class SettingsWindow(Gtk.Window):
image_warning.set_halign(Gtk.Align.START) image_warning.set_halign(Gtk.Align.START)
hbox_warning = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=5) hbox_warning = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=5)
hbox_warning.set_name("box") hbox_warning.set_name("hbox_warning")
hbox_warning.append(image_warning) hbox_warning.append(image_warning)
label_pacman_no_community = Gtk.Label(xalign=0, yalign=0) label_pacman_no_community = Gtk.Label(xalign=0, yalign=0)
label_pacman_no_community.set_name("label_community_warning")
label_pacman_no_community.set_markup( label_pacman_no_community.set_markup(
f"<b>Cannot find any supported unofficial pacman repository's</b>\n" f"<b>Cannot find any supported unofficial pacman repository's</b>\n"
f"Add unofficial pacman repository's to use community based kernels" f"<b>Add the Chaotic-AUR pacman repository to access Community based kernels</b>"
) )
hbox_warning.append(label_pacman_no_community) hbox_warning.append(label_pacman_no_community)
@ -459,7 +458,7 @@ class SettingsWindow(Gtk.Window):
while True: while True:
self.kernel_versions = self.kernel_versions_queue.get() self.kernel_versions = self.kernel_versions_queue.get()
if self.kernel_versions is not None: if self.kernel_versions is not None and len(self.kernel_versions) > 0:
break break
self.kernel_versions_queue.task_done() self.kernel_versions_queue.task_done()