From 58f098318f6a17c1cdbed1d4ae46fd8026518a56 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Sat, 14 Sep 2024 12:38:24 +0200 Subject: [PATCH 1/9] remove unused functions --- src/Utility/LinuxDistro.vala | 44 --------------------------------- src/Utility/TeeJee.Process.vala | 17 ------------- 2 files changed, 61 deletions(-) diff --git a/src/Utility/LinuxDistro.vala b/src/Utility/LinuxDistro.vala index 8f60659a..8fa13d34 100644 --- a/src/Utility/LinuxDistro.vala +++ b/src/Utility/LinuxDistro.vala @@ -152,50 +152,6 @@ public class LinuxDistro : GLib.Object{ return info; } - public static string get_running_desktop_name(){ - - /* Return the names of the current Desktop environment */ - - int pid = -1; - - pid = get_pid_by_name("cinnamon"); - if (pid > 0){ - return "Cinnamon"; - } - - pid = get_pid_by_name("xfdesktop"); - if (pid > 0){ - return "Xfce"; - } - - pid = get_pid_by_name("lxsession"); - if (pid > 0){ - return "LXDE"; - } - - pid = get_pid_by_name("gnome-shell"); - if (pid > 0){ - return "Gnome"; - } - - pid = get_pid_by_name("wingpanel"); - if (pid > 0){ - return "Elementary"; - } - - pid = get_pid_by_name("unity-panel-service"); - if (pid > 0){ - return "Unity"; - } - - pid = get_pid_by_name("plasma-desktop"); - if (pid > 0){ - return "KDE"; - } - - return "Unknown"; - } - public string dist_type { owned get{ diff --git a/src/Utility/TeeJee.Process.vala b/src/Utility/TeeJee.Process.vala index 1f55311b..a07bfdfa 100644 --- a/src/Utility/TeeJee.Process.vala +++ b/src/Utility/TeeJee.Process.vala @@ -272,23 +272,6 @@ namespace TeeJee.ProcessHelper{ } } - // dep: pidof, TODO: Rewrite using /proc - public int get_pid_by_name (string name){ - - /* Get the process ID for a process with given name */ - - string std_out, std_err; - exec_sync("pidof \"%s\"".printf(name), out std_out, out std_err); - - if (std_out != null){ - string[] arr = std_out.split ("\n"); - if (arr.length > 0){ - return int.parse (arr[0]); - } - } - - return -1; - } // dep: ps TODO: Rewrite using /proc public bool process_is_running(long pid){ From e3e24c0f915e8f29876ded83d809b1111ceba808 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Sat, 14 Sep 2024 12:38:55 +0200 Subject: [PATCH 2/9] make AppLock check the application name and dont use ps --- src/Utility/AppLock.vala | 2 +- src/Utility/TeeJee.Process.vala | 25 +++++++++---------------- 2 files changed, 10 insertions(+), 17 deletions(-) diff --git a/src/Utility/AppLock.vala b/src/Utility/AppLock.vala index c1f509e3..667b16e3 100644 --- a/src/Utility/AppLock.vala +++ b/src/Utility/AppLock.vala @@ -45,7 +45,7 @@ public class AppLock : GLib.Object { lock_message = txt.split(";")[1].strip(); long pid = long.parse(process_id); - if (process_is_running(pid)){ + if (get_process_exe_name(pid).contains("timeshift")){ log_msg(_("Another instance of this application is running") + " (PID=%ld)".printf(pid)); return false; diff --git a/src/Utility/TeeJee.Process.vala b/src/Utility/TeeJee.Process.vala index a07bfdfa..347be784 100644 --- a/src/Utility/TeeJee.Process.vala +++ b/src/Utility/TeeJee.Process.vala @@ -272,27 +272,20 @@ namespace TeeJee.ProcessHelper{ } } - - // dep: ps TODO: Rewrite using /proc - public bool process_is_running(long pid){ - - /* Checks if given process is running */ - - string cmd = ""; - string std_out; - string std_err; - int ret_val; - + // return the name of the executeable of a given pid or self if pid is <= 0 + // returns an empty string on error or if the pid could not be found + public string get_process_exe_name(long pid = -1){ try{ - cmd = "ps --pid %ld".printf(pid); - Process.spawn_command_line_sync(cmd, out std_out, out std_err, out ret_val); + string pidStr = (pid <= 0 ? "self" : pid.to_string()); + string path = "/proc/%s/exe".printf(pidStr); + char[] buf = new char[4096]; + Posix.readlink(path, buf); + return GLib.Path.get_basename((string) buf); } catch (Error e) { log_error (e.message); - return false; } - - return (ret_val == 0); + return ""; } // dep: ps TODO: Rewrite using /proc From 635f3282f1faa88cc8672a14a2e2f9c225b2bd07 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Mon, 16 Sep 2024 19:50:49 +0200 Subject: [PATCH 3/9] unify process_kill and process_quit --- src/Utility/TeeJee.Process.vala | 33 +++++++++++++++------------------ 1 file changed, 15 insertions(+), 18 deletions(-) diff --git a/src/Utility/TeeJee.Process.vala b/src/Utility/TeeJee.Process.vala index 347be784..0d7f61b6 100644 --- a/src/Utility/TeeJee.Process.vala +++ b/src/Utility/TeeJee.Process.vala @@ -318,37 +318,34 @@ namespace TeeJee.ProcessHelper{ public void process_quit(Pid process_pid, bool killChildren = true){ - /* Kills specified process and its children (optional). + /* Terminates specified process and its children (optional). * Sends signal SIGTERM to the process to allow it to quit gracefully. * */ - int[] child_pids = get_process_children (process_pid); - Posix.kill (process_pid, Posix.Signal.TERM); - - if (killChildren){ - Pid childPid; - foreach (long pid in child_pids){ - childPid = (Pid) pid; - Posix.kill (childPid, Posix.Signal.TERM); - } - } + process_send_signal(process_pid, Posix.Signal.TERM, killChildren); } - public void process_kill(Pid process_pid, bool killChildren = true){ + public void process_kill(Pid process_pid, bool killChildren = true) { /* Kills specified process and its children (optional). * Sends signal SIGKILL to the process to kill it forcefully. * It is recommended to use the function process_quit() instead. * */ - int[] child_pids = get_process_children (process_pid); - Posix.kill (process_pid, Posix.Signal.KILL); + process_send_signal(process_pid, Posix.Signal.KILL, killChildren); + } + + public void process_send_signal(Pid process_pid, Posix.Signal sig, bool children = true) { - if (killChildren){ - Pid childPid; + /* Sends a signal to a process and its children (optional). */ + + // get the childs before sending the signal, as the childs might not be accessible afterwards + int[] child_pids = get_process_children (process_pid); + Posix.kill (process_pid, sig); + + if (children){ foreach (long pid in child_pids){ - childPid = (Pid) pid; - Posix.kill (childPid, Posix.Signal.KILL); + Posix.kill ((Pid) pid, sig); } } } From dcef55b108f9c9ad61990fa2fc9645321da40b3a Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Sun, 15 Sep 2024 20:55:20 +0200 Subject: [PATCH 4/9] remove dependency to wc --- src/Core/Main.vala | 7 +------ src/Utility/RsyncTask.vala | 2 +- src/Utility/TeeJee.FileSystem.vala | 28 ++++++++++++++++++++++------ 3 files changed, 24 insertions(+), 13 deletions(-) diff --git a/src/Core/Main.vala b/src/Core/Main.vala index fe72628c..83eb0d0d 100644 --- a/src/Core/Main.vala +++ b/src/Core/Main.vala @@ -3922,12 +3922,7 @@ public class Main : GLib.Object{ ret_val = exec_script_sync(cmd, out std_out, out std_err); if (ret_val == 0){ required_space = long.parse(std_out.replace(",","").strip()); - - cmd = "wc -l '%s'".printf(escape_single_quote(file_log)); - ret_val = exec_script_sync(cmd, out std_out, out std_err); - if (ret_val == 0){ - file_count = long.parse(std_out.split(" ")[0].strip()); - } + file_count = file_line_count(file_log) ?? 0; thr_success = true; } diff --git a/src/Utility/RsyncTask.vala b/src/Utility/RsyncTask.vala index 16ae179e..e43e3b66 100644 --- a/src/Utility/RsyncTask.vala +++ b/src/Utility/RsyncTask.vala @@ -289,7 +289,7 @@ public class RsyncTask : AsyncTask{ log_debug("log_file = %s".printf(log_file)); prg_count = 0; - prg_count_total = file_line_count(log_file); + prg_count_total = file_line_count(log_file) ?? 0; try { string line; diff --git a/src/Utility/TeeJee.FileSystem.vala b/src/Utility/TeeJee.FileSystem.vala index 13226add..36098e0a 100644 --- a/src/Utility/TeeJee.FileSystem.vala +++ b/src/Utility/TeeJee.FileSystem.vala @@ -88,12 +88,28 @@ namespace TeeJee.FileSystem{ } } - public int64 file_line_count (string file_path){ - /* Count number of lines in text file */ - string cmd = "wc -l '%s'".printf(escape_single_quote(file_path)); - string std_out, std_err; - exec_sync(cmd, out std_out, out std_err); - return long.parse(std_out.split("\t")[0]); + public int64? file_line_count (string file_path){ + /* Count number of lines in text file returns null on error */ + + try { + long line_nums = 0; + char symbol; + + File file = File.new_for_path(file_path); + FileInputStream inStream = file.read(); + BufferedInputStream bis = new BufferedInputStream.sized(inStream, (size_t) (1 * MiB)); + while((symbol = (char) bis.read_byte()) != -1) { + if(symbol == '\n') { + line_nums ++; + } + } + bis.close(); + return line_nums; + } catch(Error e) { + log_error (e.message); + log_error(_("Failed to read file") + ": %s".printf(file_path)); + } + return null; } public string? file_read (string file_path){ From 46cce1b5a867db14647f96dbc92f39bffb59d380 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Sun, 15 Sep 2024 21:46:29 +0200 Subject: [PATCH 5/9] remove dependency to ps --- src/Utility/AsyncTask.vala | 4 +- src/Utility/TeeJee.Process.vala | 71 ++++++++++++++++++++++++--------- 2 files changed, 53 insertions(+), 22 deletions(-) diff --git a/src/Utility/AsyncTask.vala b/src/Utility/AsyncTask.vala index b2475542..96c4fbec 100644 --- a/src/Utility/AsyncTask.vala +++ b/src/Utility/AsyncTask.vala @@ -394,9 +394,7 @@ public abstract class AsyncTask : GLib.Object{ if (status == AppStatus.RUNNING) { process_set_priority (child_pid, prio); - Pid sub_child_pid; - foreach (long pid in get_process_children (child_pid)) { - sub_child_pid = (Pid) pid; + foreach (Pid sub_child_pid in get_process_children (child_pid)) { process_set_priority (sub_child_pid, prio); } } diff --git a/src/Utility/TeeJee.Process.vala b/src/Utility/TeeJee.Process.vala index 0d7f61b6..8673e6d1 100644 --- a/src/Utility/TeeJee.Process.vala +++ b/src/Utility/TeeJee.Process.vala @@ -288,30 +288,63 @@ namespace TeeJee.ProcessHelper{ return ""; } - // dep: ps TODO: Rewrite using /proc - public int[] get_process_children (Pid parent_pid){ + public Pid[] get_process_children (Pid parent_pid){ - /* Returns the list of child processes spawned by given process */ + /* Returns the list of child processes owned by a given process */ - string std_out, std_err; - exec_sync("ps --ppid %d".printf(parent_pid), out std_out, out std_err); + // no explicit check for the existence of /proc/ as this might be a time-of-check-time-of-use bug. + File procfs = File.new_for_path("/proc/"); - int pid; - int[] procList = {}; - string[] arr; + try { + FileEnumerator enumerator = procfs.enumerate_children(FileAttribute.STANDARD_NAME, FileQueryInfoFlags.NOFOLLOW_SYMLINKS); + FileInfo info; + Pid[] childList = {}; + while ((info = enumerator.next_file()) != null) { + if(info.get_file_type() != FileType.DIRECTORY) { + // only interested in directorys + continue; + } - foreach (string line in std_out.split ("\n")){ - arr = line.strip().split (" "); - if (arr.length < 1) { continue; } + string name = info.get_name(); - pid = 0; - pid = int.parse (arr[0]); + uint64 pid; + if(!uint64.try_parse(name, out pid)) { + // make sure to not access any other directorys that may be present in /proc for some reason + continue; + } - if (pid != 0){ - procList += pid; + string? fileCont = file_read("/proc/%s/stat".printf(name)); + if(fileCont == null) { + // stat file of pid might not be readable (because of permissions or the process died since we got its pid) + continue; + } + + // the format of the stat file is documented in man 5 proc + // it begging is: pid (comm) status ppid ... + + // the process name could contain a space or ) and confuse the parsing. + // so we make sure to take the last ) and only parse the stuff after that. + int index = fileCont.last_index_of_char(')'); + string parseline = fileCont.substring(index); + string[] splitted = parseline.split(" ", 4); // we are not interested in the part after ppid so just leave it a big string + if(splitted.length != 4) { + // format of stat file is not matching - should never happen + log_error("can not parse state of %ld".printf((long) pid)); + continue; + } + + uint64 ppid = uint64.parse(splitted[2]); + if(ppid != 0 && ppid == parent_pid) { + // the process is a child of the target parent process + childList += (Pid) pid; + } } + return childList; + } catch (Error e) { + log_error(e.message); + log_error(_("Failed to get child processes of %ld").printf(parent_pid)); } - return procList; + return {}; } // manage process --------------------------------- @@ -340,12 +373,12 @@ namespace TeeJee.ProcessHelper{ /* Sends a signal to a process and its children (optional). */ // get the childs before sending the signal, as the childs might not be accessible afterwards - int[] child_pids = get_process_children (process_pid); + Pid[] child_pids = get_process_children (process_pid); Posix.kill (process_pid, sig); if (children){ - foreach (long pid in child_pids){ - Posix.kill ((Pid) pid, sig); + foreach (Pid pid in child_pids){ + Posix.kill (pid, sig); } } } From d9e2398990d31d9f06835d2ae4c424027a1ab908 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Tue, 17 Sep 2024 23:07:55 +0200 Subject: [PATCH 6/9] recursive delete --- src/Core/SnapshotRepo.vala | 72 ++++++++++++++++++++------------------ 1 file changed, 37 insertions(+), 35 deletions(-) diff --git a/src/Core/SnapshotRepo.vala b/src/Core/SnapshotRepo.vala index ba270f00..620620e7 100644 --- a/src/Core/SnapshotRepo.vala +++ b/src/Core/SnapshotRepo.vala @@ -882,46 +882,48 @@ public class SnapshotRepo : GLib.Object{ return thr_success; } - private void delete_directory_thread(){ - string cmd = ""; - string std_out; - string std_err; - int ret_val; - - try{ - var f = File.new_for_path(thr_args1); - if(f.query_exists()){ - cmd = "rm -rf \"%s\"".printf(thr_args1); - - if (LOG_COMMANDS) { log_debug(cmd); } - - Process.spawn_command_line_sync(cmd, out std_out, out std_err, out ret_val); + public static bool delete_directory_recursive(string dir) { + File f = File.new_for_path(dir); + if(f.query_exists()) { + try { + FileEnumerator enumerator = f.enumerate_children(FileAttribute.STANDARD_NAME, FileQueryInfoFlags.NOFOLLOW_SYMLINKS); + FileInfo info; + while ((info = enumerator.next_file()) != null) { + string name = info.get_name(); + if(info.get_file_type() == FileType.DIRECTORY) { + + // ignore . and .. + if(name == "." || name == "..") { + continue; + } - if (ret_val != 0){ - log_error(_("Failed to remove") + ": '%s'".printf(thr_args1)); - thr_success = false; - thr_running = false; - return; - } - else{ - log_msg(_("Removed") + ": '%s'".printf(thr_args1)); - thr_success = true; - thr_running = false; - return; + if(!delete_directory_recursive(dir + "/" + name)) { + return false; + } + } else { + File file = File.new_for_path(dir + "/" + name); + file.delete(); + } } - } - else{ - log_error(_("Directory not found") + ": '%s'".printf(thr_args1)); - thr_success = true; - thr_running = false; + f.delete(); + } catch(Error err) { + log_error("Can not enumerate folder '%s'".printf(dir)); + return false; } } - catch(Error e){ - log_error (e.message); - thr_success = false; - thr_running = false; - return; + return true; + } + + private void delete_directory_thread(){ + thr_success = delete_directory_recursive(thr_args1); + + if (thr_success) { + log_msg(_("Removed") + ": '%s'".printf(thr_args1)); + } else{ + log_error(_("Failed to remove") + ": '%s'".printf(thr_args1)); } + + thr_running = false; } // symlinks ---------------------------------------- From 91c85a6118559d2d3c1a44b13f547de9fb9cab61 Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Wed, 18 Sep 2024 19:18:39 +0200 Subject: [PATCH 7/9] remoe rm dependency --- src/Core/Main.vala | 14 +++--- src/Core/SnapshotRepo.vala | 34 +------------- src/Utility/DeleteFileTask.vala | 9 ++-- src/Utility/TeeJee.FileSystem.vala | 71 +++++++++++++++++++++++------- 4 files changed, 66 insertions(+), 62 deletions(-) diff --git a/src/Core/Main.vala b/src/Core/Main.vala index 83eb0d0d..069b8537 100644 --- a/src/Core/Main.vala +++ b/src/Core/Main.vala @@ -206,7 +206,7 @@ public class Main : GLib.Object{ } check_and_remove_timeshift_btrfs(); - + // init log ------------------ try { @@ -4375,11 +4375,8 @@ public class Main : GLib.Object{ string cmd = "umount '%s'".printf(escape_single_quote(mdir2)); int retval = exec_sync(cmd); - - string cmd2 = "rmdir '%s'".printf(escape_single_quote(mdir2)); - int retval2 = exec_sync(cmd2); - - if (retval2 != 0){ + + if (retval != 0){ log_debug("E: Failed to unmount"); log_debug("Ret=%d".printf(retval)); //ignore @@ -4387,6 +4384,11 @@ public class Main : GLib.Object{ else{ log_debug("Unmounted successfully"); } + + // delete directory + if(!dir_empty_delete(mdir2)) { + log_debug("E: Failed to delete %s".printf(mdir2)); + } } } } diff --git a/src/Core/SnapshotRepo.vala b/src/Core/SnapshotRepo.vala index 620620e7..192a85f2 100644 --- a/src/Core/SnapshotRepo.vala +++ b/src/Core/SnapshotRepo.vala @@ -882,40 +882,8 @@ public class SnapshotRepo : GLib.Object{ return thr_success; } - public static bool delete_directory_recursive(string dir) { - File f = File.new_for_path(dir); - if(f.query_exists()) { - try { - FileEnumerator enumerator = f.enumerate_children(FileAttribute.STANDARD_NAME, FileQueryInfoFlags.NOFOLLOW_SYMLINKS); - FileInfo info; - while ((info = enumerator.next_file()) != null) { - string name = info.get_name(); - if(info.get_file_type() == FileType.DIRECTORY) { - - // ignore . and .. - if(name == "." || name == "..") { - continue; - } - - if(!delete_directory_recursive(dir + "/" + name)) { - return false; - } - } else { - File file = File.new_for_path(dir + "/" + name); - file.delete(); - } - } - f.delete(); - } catch(Error err) { - log_error("Can not enumerate folder '%s'".printf(dir)); - return false; - } - } - return true; - } - private void delete_directory_thread(){ - thr_success = delete_directory_recursive(thr_args1); + thr_success = TeeJee.FileSystem.dir_delete_recursive(thr_args1); if (thr_success) { log_msg(_("Removed") + ": '%s'".printf(thr_args1)); diff --git a/src/Utility/DeleteFileTask.vala b/src/Utility/DeleteFileTask.vala index f0fdfd53..0381ab96 100644 --- a/src/Utility/DeleteFileTask.vala +++ b/src/Utility/DeleteFileTask.vala @@ -69,7 +69,7 @@ public class DeleteFileTask : AsyncTask{ log_error (e.message); } } - + public void prepare() { string script_text = build_script(); log_debug(script_text); @@ -113,13 +113,10 @@ public class DeleteFileTask : AsyncTask{ cmd += " '%s/'".printf(escape_single_quote(dest_path)); } else{ - cmd += "rm"; + cmd += "rm -rf"; if (verbose){ - cmd += " -rfv"; - } - else{ - cmd += " -rf"; + cmd += "v"; } cmd += " '%s'".printf(escape_single_quote(dest_path)); diff --git a/src/Utility/TeeJee.FileSystem.vala b/src/Utility/TeeJee.FileSystem.vala index 36098e0a..302c8a62 100644 --- a/src/Utility/TeeJee.FileSystem.vala +++ b/src/Utility/TeeJee.FileSystem.vala @@ -298,33 +298,70 @@ namespace TeeJee.FileSystem{ } } - public bool dir_delete (string dir_path, bool show_message = false){ - - /* Recursively deletes directory along with contents */ - - if (!dir_exists(dir_path)){ - return true; + // delete an empty directory + public static bool dir_empty_delete(string path) { + File dirf = File.new_for_path(path); + try { + if (dirf.query_file_type(FileQueryInfoFlags.NONE) == FileType.DIRECTORY) { + return dirf.delete(); // only succeeds, if the dir is empty + } + } catch(Error ioe) { + if(ioe.matches(IOError.quark(), IOError.NOT_FOUND)) { + // directory does not exist + return true; + } } + return false; + } + + public static bool dir_delete_recursive(string dir) { + File f = File.new_for_path(dir); + if(f.query_exists()) { + try { + FileEnumerator enumerator = f.enumerate_children(FileAttribute.STANDARD_NAME, FileQueryInfoFlags.NOFOLLOW_SYMLINKS); + FileInfo info; + while ((info = enumerator.next_file()) != null) { + string name = info.get_name(); + if(info.get_file_type() == FileType.DIRECTORY) { + + // ignore . and .. + if(name == "." || name == "..") { + continue; + } + + if(!dir_delete_recursive(dir + "/" + name)) { + return false; + } + } else { + File file = File.new_for_path(dir + "/" + name); + file.delete(); + } + } + f.delete(); + } catch(Error err) { + log_error(_("Can not enumerate folder %s").printf(dir)); + return false; + } + } + return true; + } + + public bool dir_delete(string dir_path, bool show_message = false) { - string cmd = "rm -rf '%s'".printf(escape_single_quote(dir_path)); - - log_debug(cmd); - - string std_out, std_err; - int status = exec_sync(cmd, out std_out, out std_err); + /* Recursively deletes directory along with contents */ + bool status = dir_delete_recursive(dir_path); + if (show_message){ - if (status == 0){ + if (status){ log_msg(_("Deleted directory") + ": %s".printf(dir_path)); } else{ log_error(_("Failed to delete directory") + ": %s".printf(dir_path)); - log_error(std_out); - log_error(std_err); } } - return (status == 0); + return status; } public bool dir_is_empty (string dir_path){ @@ -336,7 +373,7 @@ namespace TeeJee.FileSystem{ var dir = File.parse_name (dir_path); if (dir.query_exists()) { FileInfo info; - var enu = dir.enumerate_children ("%s".printf(FileAttribute.STANDARD_NAME), 0); + var enu = dir.enumerate_children (FileAttribute.STANDARD_NAME, 0); while ((info = enu.next_file()) != null) { is_empty = false; break; From 31fe95963bb7864d4077d3ac9085270f6525c5ef Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Thu, 19 Sep 2024 17:52:25 +0200 Subject: [PATCH 8/9] symlinktest --- src/Core/SnapshotRepo.vala | 31 ++++++++++++------------------- 1 file changed, 12 insertions(+), 19 deletions(-) diff --git a/src/Core/SnapshotRepo.vala b/src/Core/SnapshotRepo.vala index 192a85f2..13c5dfe8 100644 --- a/src/Core/SnapshotRepo.vala +++ b/src/Core/SnapshotRepo.vala @@ -897,11 +897,6 @@ public class SnapshotRepo : GLib.Object{ // symlinks ---------------------------------------- public void create_symlinks(){ - string cmd = ""; - string std_out; - string std_err; - int ret_val; - cleanup_symlink_dir("boot"); cleanup_symlink_dir("hourly"); cleanup_symlink_dir("daily"); @@ -909,21 +904,19 @@ public class SnapshotRepo : GLib.Object{ cleanup_symlink_dir("monthly"); cleanup_symlink_dir("ondemand"); - string path; - - foreach(var bak in snapshots){ - foreach(string tag in bak.tags){ - - path = "%s-%s".printf(snapshots_path, tag); - cmd = "ln --symbolic \"../snapshots/%s\" -t \"%s\"".printf(bak.name, path); - if (LOG_COMMANDS) { log_debug(cmd); } - - ret_val = exec_sync(cmd, out std_out, out std_err); - if (ret_val != 0){ - log_error (std_err); - log_error(_("Failed to create symlinks") + ": snapshots-%s".printf(tag)); - return; + foreach(Snapshot bak in snapshots){ + foreach(string tag in bak.tags) { + string linkTarget = "%s-%s/%s".printf(snapshots_path, tag, bak.name); + string linkValue = "../snapshots/" + bak.name; + try { + File f = File.new_for_path(linkTarget); + if (!f.make_symbolic_link(linkValue)) { + log_error(_("Failed to create symlinks") + ": %s".printf(linkTarget)); + } + } catch(Error e) { + log_debug(e.message); + log_error(_("Failed to create symlinks") + ": %s".printf(linkTarget)); } } } From 05c2c1c3ff71225f3203dcbdf0563f679d5faabf Mon Sep 17 00:00:00 2001 From: ygerlach <100762533+ygerlach@users.noreply.github.com> Date: Thu, 19 Sep 2024 18:36:03 +0200 Subject: [PATCH 9/9] remove another use of rm --- src/Core/SnapshotRepo.vala | 24 +++++------------------- src/Utility/TeeJee.FileSystem.vala | 8 ++++---- 2 files changed, 9 insertions(+), 23 deletions(-) diff --git a/src/Core/SnapshotRepo.vala b/src/Core/SnapshotRepo.vala index 13c5dfe8..321835b8 100644 --- a/src/Core/SnapshotRepo.vala +++ b/src/Core/SnapshotRepo.vala @@ -925,32 +925,18 @@ public class SnapshotRepo : GLib.Object{ } public void cleanup_symlink_dir(string tag){ - string cmd = ""; - string std_out; - string std_err; - int ret_val; - try{ string path = "%s-%s".printf(snapshots_path, tag); - var f = File.new_for_path(path); - if (f.query_exists()){ - cmd = "rm -rf \"%s\"".printf(path + "/"); - - if (LOG_COMMANDS) { log_debug(cmd); } - - Process.spawn_command_line_sync(cmd, out std_out, out std_err, out ret_val); - if (ret_val != 0){ - log_error (std_err); - log_error(_("Failed to delete symlinks") + ": 'snapshots-%s'".printf(tag)); - return; - } + if(!TeeJee.FileSystem.dir_delete_recursive(path)) { + log_error(_("Failed to delete symlinks") + ": '%s'".printf(path)); } + File f = File.new_for_path(path); f.make_directory_with_parents(); } catch (Error e) { - log_error (e.message); - } + log_error (e.message); + } } } diff --git a/src/Utility/TeeJee.FileSystem.vala b/src/Utility/TeeJee.FileSystem.vala index 302c8a62..125c0c7b 100644 --- a/src/Utility/TeeJee.FileSystem.vala +++ b/src/Utility/TeeJee.FileSystem.vala @@ -346,10 +346,10 @@ namespace TeeJee.FileSystem{ return true; } - public bool dir_delete(string dir_path, bool show_message = false) { - + public static bool dir_delete(string dir_path, bool show_message = false) { + /* Recursively deletes directory along with contents */ - + bool status = dir_delete_recursive(dir_path); if (show_message){ @@ -360,7 +360,7 @@ namespace TeeJee.FileSystem{ log_error(_("Failed to delete directory") + ": %s".printf(dir_path)); } } - + return status; }