From patchwork Mon Mar 18 15:07:19 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Gautier X-Patchwork-Id: 13595434 Received: from taslin.fdn.fr (taslin.fdn.fr [80.67.169.77]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E52F850249 for ; Mon, 18 Mar 2024 15:17:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=80.67.169.77 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; cv=none; b=s09ncG/EbVrPFrxvCrpRaGitZ4bQnGfqu0zIF9GMhV/P5lRlfQDkrOcK4UQVCNZF5xLeGxJKySP9Zr3aSZ/ZxSsgvp+XCjxKMHSuM7TPOeMWj+rYD2YF86ZHOdxkc82jwN+AKB6Xx+0vi+oCNTlPc2YkgRKLEysx3CelQu9ubpI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; c=relaxed/simple; bh=Zgf9TjZBXz90VbT4PjK0EYxYjjsyXTqxReI1a7hd6ws=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=KeZoFYkoZ004rUB+Ql9KdaW7s16usREjjKPI6NUH1/J0jajHGYlUtOP596gnlqPTRuyiM2SPjuCL6GiFvqJetyo+1uPNhuTcak6QA/DBJBMqo/dxzs6ec+bjgmVsk8Oz6jO/tnw6U9yqYTkXL32p1M80x2rMIqPLtjU+fxF00PQ= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name; spf=pass smtp.mailfrom=max.gautier.name; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b=f0SrQw6Y; arc=none smtp.client-ip=80.67.169.77 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b="f0SrQw6Y" Received: from localhost (unknown [IPv6:2001:910:10ee:0:fc9:9524:11d1:7aa4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by taslin.fdn.fr (Postfix) with ESMTPSA id BF4F4602BD; Mon, 18 Mar 2024 16:17:49 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=max.gautier.name; s=fdn; t=1710775069; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=79Y8p58BN7UgijTeitJ6k+H+iUyLmmD/AC2uZd04frk=; b=f0SrQw6Ym4cuMF0Fbe4TtgxmlbBJSIiv4BoMJJ+wjUXuS+XmeUEwG3sXDciwUVdZys76h1 1s4ExvsPkj0Rb+eX30fBl32qvITGKxkqLoRCEWuC+Q/Qc3S6SkM5VB6bbUxz15p63V8ovY MtPdnZD5X13FVeZa7dXH2aGVHIuhaNDPg47XR857sOXpzyxcUHx5y9aPTn6owTHoLfQlgf dxxLNWHHmU4G+xKwgh5fxayUBHEuitC9rAtNacWA3vM0RLRXSpIO+psXosHrGEv0NJE61+ nzN/a/QiZCZ8zhFKZg9eOmoLGLytXlCnpwkgM+Dg3CWiNC78jJvJH0pV6ldMkA== From: Max Gautier To: git@vger.kernel.org Cc: =?utf-8?b?TMOpbmHDr2MgSHVhcmQ=?= , Max Gautier Subject: [RFC PATCH 1/5] maintenance: package systemd units Date: Mon, 18 Mar 2024 16:07:19 +0100 Message-ID: <20240318151701.26644-3-mg@max.gautier.name> X-Mailer: git-send-email 2.44.0 In-Reply-To: <20240318151701.26644-2-mg@max.gautier.name> References: <20240318151701.26644-2-mg@max.gautier.name> Precedence: bulk X-Mailing-List: git@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Signed-off-by: Max Gautier --- Makefile | 4 ++++ systemd/user/git-maintenance@.service | 16 ++++++++++++++++ systemd/user/git-maintenance@.timer | 9 +++++++++ 3 files changed, 29 insertions(+) create mode 100644 systemd/user/git-maintenance@.service create mode 100644 systemd/user/git-maintenance@.timer diff --git a/Makefile b/Makefile index 4e255c81f2..276b4373c6 100644 --- a/Makefile +++ b/Makefile @@ -619,6 +619,7 @@ htmldir = $(prefix)/share/doc/git-doc ETC_GITCONFIG = $(sysconfdir)/gitconfig ETC_GITATTRIBUTES = $(sysconfdir)/gitattributes lib = lib +libdir = $(prefix)/lib # DESTDIR = pathsep = : @@ -1328,6 +1329,8 @@ BUILTIN_OBJS += builtin/verify-tag.o BUILTIN_OBJS += builtin/worktree.o BUILTIN_OBJS += builtin/write-tree.o +SYSTEMD_USER_UNITS := $(wildcard systemd/user/*) + # THIRD_PARTY_SOURCES is a list of patterns compatible with the # $(filter) and $(filter-out) family of functions. They specify source # files which are taken from some third-party source where we want to be @@ -3469,6 +3472,7 @@ install: all $(INSTALL) -m 644 $(SCRIPT_LIB) '$(DESTDIR_SQ)$(gitexec_instdir_SQ)' $(INSTALL) $(INSTALL_STRIP) $(install_bindir_xprograms) '$(DESTDIR_SQ)$(bindir_SQ)' $(INSTALL) $(BINDIR_PROGRAMS_NO_X) '$(DESTDIR_SQ)$(bindir_SQ)' + $(INSTALL) -Dm 644 -t '$(DESTDIR_SQ)$(libdir)/systemd/user' $(SYSTEMD_USER_UNITS) ifdef MSVC # We DO NOT install the individual foo.o.pdb files because they diff --git a/systemd/user/git-maintenance@.service b/systemd/user/git-maintenance@.service new file mode 100644 index 0000000000..87ac0c86e6 --- /dev/null +++ b/systemd/user/git-maintenance@.service @@ -0,0 +1,16 @@ +[Unit] +Description=Optimize Git repositories data + +[Service] +Type=oneshot +ExecStart=git for-each-repo --config=maintenance.repo \ + maintenance run --schedule=%i +LockPersonality=yes +MemoryDenyWriteExecute=yes +NoNewPrivileges=yes +RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 AF_VSOCK +RestrictNamespaces=yes +RestrictRealtime=yes +RestrictSUIDSGID=yes +SystemCallArchitectures=native +SystemCallFilter=@system-service diff --git a/systemd/user/git-maintenance@.timer b/systemd/user/git-maintenance@.timer new file mode 100644 index 0000000000..40fbc77a62 --- /dev/null +++ b/systemd/user/git-maintenance@.timer @@ -0,0 +1,9 @@ +[Unit] +Description=Optimize Git repositories data + +[Timer] +OnCalendar=%i +Persistent=true + +[Install] +WantedBy=timers.target From patchwork Mon Mar 18 15:07:20 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Gautier X-Patchwork-Id: 13595435 Received: from taslin.fdn.fr (taslin.fdn.fr [80.67.169.77]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E53A95025A for ; Mon, 18 Mar 2024 15:17:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=80.67.169.77 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; cv=none; b=r7jEAVICdHnWmXyWx5j/fsXn2nno20mTGrbQJLjamKglm/6bAFAHW0HKyfR/KdzaMqGCkQp/lWeZZLGwLdZhW/Q3MuzGzalngv/KYvApgHmUJKkALSKTpemcv2tVSY+9w3YYewjCJ6L/csYnh78CA4WWVq0n1bT2bV20LGg8deQ= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; c=relaxed/simple; bh=1BsXbTaDlKvzIFO4QQuoq9BKtOXcTbpTbxBsq08BXHU=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Rt4CKAMRBP5jw1b3drqeS/FnSJe9a3srwjHrGd/aAvq6L0Iv7skp0HHBGvdFych2fmzCS4DUwWoD0cW5MuvIlHHj6JhVEi2AsPlkr7teI8cp6r/wAiWs0Axvdu5HERwDCEkeFwShopF2Wter5KSmQPYju/MNJ/syh5eu728TIF0= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name; spf=pass smtp.mailfrom=max.gautier.name; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b=n5DPJMko; arc=none smtp.client-ip=80.67.169.77 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b="n5DPJMko" Received: from localhost (unknown [IPv6:2001:910:10ee:0:fc9:9524:11d1:7aa4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by taslin.fdn.fr (Postfix) with ESMTPSA id 1CE14602E7; Mon, 18 Mar 2024 16:17:50 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=max.gautier.name; s=fdn; t=1710775070; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=HknJ9NjDjqfl1sLk00t/bka3r/aYktT7hZyGtAU1Pz4=; b=n5DPJMko9gud0MVe/veeghqeLGBot1BbJ9cYiU1g/7Pkk9p4dC0aW1Z5u18AXqAvDcYk9R O3rWfA4/jdjaQgUQHpTd+aSMhFvh4COCav9x9ly2zhRXbKqtoJMKDN2l0aGcZ2C6GFsKHz 1tHQicxaDw9Y3fOsJXRyZAiVwuM6C9cGRqv6aB2TXcFtjLOAKLSugvCRmR1cWTOaWMlYP4 y9U38z2L8kZ20r6nwk6c+c2UHpeh+yHq7UMcC8JcA3RfpDHBdUfxRvKFLqWY3Hk3AcYUR1 paPlB2JCdVX7kAowmJ70D8rjJ/QU8fCwvlyxTc+j0omgz9HpFiFTb+uK8CjWuw== From: Max Gautier To: git@vger.kernel.org Cc: =?utf-8?b?TMOpbmHDr2MgSHVhcmQ=?= , Max Gautier Subject: [RFC PATCH 2/5] maintenance: add fixed random delay to systemd timers Date: Mon, 18 Mar 2024 16:07:20 +0100 Message-ID: <20240318151701.26644-4-mg@max.gautier.name> X-Mailer: git-send-email 2.44.0 In-Reply-To: <20240318151701.26644-2-mg@max.gautier.name> References: <20240318151701.26644-2-mg@max.gautier.name> Precedence: bulk X-Mailing-List: git@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Ensures that: - git maintenance timers have a fixed time interval between execution. - the three timers are not executed at the same time. This is intended to implement an alternative to the two followings commits: c97ec0378b (maintenance: fix systemd schedule overlaps, 2023-08-10) daa787010c (maintenance: use random minute in systemd scheduler, 2023-08-10) Instead of manually adding a specific minute (which is reset on each invocation of `git maintenance start`), we use systemd timers RandomizedDelaySec and FixedRandomDelay functionalities. From man systemd.timer: >FixedRandomDelay= > Takes a boolean argument. When enabled, the randomized offset > specified by RandomizedDelaySec= is reused for all firings of the > same timer. For a given timer unit, **the offset depends on the > machine ID, user identifier and timer name**, which means that it is > stable between restarts of the manager. This effectively creates a > fixed offset for an individual timer, reducing the jitter in > firings of this timer, while still avoiding firing at the same time > as other similarly configured timers. -> which is exactly the use case for git-maintenance timers. Signed-off-by: Max Gautier --- systemd/user/git-maintenance@.service | 1 + systemd/user/git-maintenance@.timer | 3 +++ 2 files changed, 4 insertions(+) diff --git a/systemd/user/git-maintenance@.service b/systemd/user/git-maintenance@.service index 87ac0c86e6..f949e1a217 100644 --- a/systemd/user/git-maintenance@.service +++ b/systemd/user/git-maintenance@.service @@ -1,5 +1,6 @@ [Unit] Description=Optimize Git repositories data +Documentation=man:git-maintenance(1) [Service] Type=oneshot diff --git a/systemd/user/git-maintenance@.timer b/systemd/user/git-maintenance@.timer index 40fbc77a62..667c5998ba 100644 --- a/systemd/user/git-maintenance@.timer +++ b/systemd/user/git-maintenance@.timer @@ -1,9 +1,12 @@ [Unit] Description=Optimize Git repositories data +Documentation=man:git-maintenance(1) [Timer] OnCalendar=%i Persistent=true +RandomizedDelaySec=1800 +FixedRandomDelay=true [Install] WantedBy=timers.target From patchwork Mon Mar 18 15:07:21 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Gautier X-Patchwork-Id: 13595433 Received: from taslin.fdn.fr (taslin.fdn.fr [80.67.169.77]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E53E75025C for ; Mon, 18 Mar 2024 15:17:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=80.67.169.77 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; cv=none; b=Z/7zfVgcnmNvZV7lpixsI74Jj5AGlEXPdHc9pUG6A59fNlzdCaAwcfMoiwF+pDtPfYazOcY5H1lhkNx87MorHtXbmmRfz2NYuuPZgTRbik1jrlQjl+9/H49Sj5wyvAKnfQYlAW9skEGujdbeCuuOUnxS5fh3b4E5OMpIrAWGjbQ= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; c=relaxed/simple; bh=hQJdyI1FW3/O2gdS25cOQ26XZBJfL1yC/YMG3bMCQwo=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Eb7UC4BPk4jzojTpBjdzH5LrZ+WnZwqhQ0xHX4lf5/+yEfkDzO+RdwUoWMPEc2K/Apuz8shjKHeRP5tBHcv9OGr17I7B6lva//EEraNIBzPndGEHGkg5K/6eVwSVP666FZZQFSexRdUvSrxEAhw0Wzf2IhulZ+ttVZ0evFmTpyU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name; spf=pass smtp.mailfrom=max.gautier.name; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b=0UlRJ5P4; arc=none smtp.client-ip=80.67.169.77 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b="0UlRJ5P4" Received: from localhost (unknown [IPv6:2001:910:10ee:0:fc9:9524:11d1:7aa4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by taslin.fdn.fr (Postfix) with ESMTPSA id 7A589602E8; Mon, 18 Mar 2024 16:17:50 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=max.gautier.name; s=fdn; t=1710775070; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=DQCSqWFeEerRsW+ShSca65VwwQFftW4dsUYORqM4KEk=; b=0UlRJ5P4UWGeqHzIQhMjLbHQIELeXP52MoIwA/AjYsU7AWKDNWeMrYwfFv7uKABXT3HONb 8FuQGfGtRVKb1AO5XhCtUr7R6YXjmXvNfJdI/nmTt+wtZWqQQ3mDWYNYdFxdzDlY+KJs20 4QcULf4FPMswMch5XejmdGWB+FYnyZFqcAw1PidrOrNqxGbXqTlVmodsODyBv/qhQrZHKa ua6Hb1zrGRzXz5CeNyDJCgo2c7QaZ4rnBhlIBxwCAFLcLv6Uqo0nTppncschqEzBYJ8AAo CHbuhK85xXcFAN0VbDPvnHPFcWP/9N19vRiZW7t5ga6RpiQBm/125/SPQRpgfg== From: Max Gautier To: git@vger.kernel.org Cc: =?utf-8?b?TMOpbmHDr2MgSHVhcmQ=?= , Max Gautier Subject: [RFC PATCH 3/5] maintenance: use packaged systemd units Date: Mon, 18 Mar 2024 16:07:21 +0100 Message-ID: <20240318151701.26644-5-mg@max.gautier.name> X-Mailer: git-send-email 2.44.0 In-Reply-To: <20240318151701.26644-2-mg@max.gautier.name> References: <20240318151701.26644-2-mg@max.gautier.name> Precedence: bulk X-Mailing-List: git@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 - Remove the code writing the units - Simplify calling systemctl - systemctl does not error out when disabling units which aren't enabled, nor when enabling already enabled units - call systemctl only once, with all the units. - Add clean-up code for leftover units in $XDG_CONFIG_HOME created by previous versions of git, taking care of preserving actual user override (by checking the start of the file). Signed-off-by: Max Gautier --- builtin/gc.c | 293 ++++++++------------------------------------------- 1 file changed, 45 insertions(+), 248 deletions(-) diff --git a/builtin/gc.c b/builtin/gc.c index cb80ced6cb..981db8e297 100644 --- a/builtin/gc.c +++ b/builtin/gc.c @@ -2308,276 +2308,73 @@ static char *xdg_config_home_systemd(const char *filename) return xdg_config_home_for("systemd/user", filename); } -#define SYSTEMD_UNIT_FORMAT "git-maintenance@%s.%s" - -static int systemd_timer_delete_timer_file(enum schedule_priority priority) -{ - int ret = 0; - const char *frequency = get_frequency(priority); - char *local_timer_name = xstrfmt(SYSTEMD_UNIT_FORMAT, frequency, "timer"); - char *filename = xdg_config_home_systemd(local_timer_name); - - if (unlink(filename) && !is_missing_file_error(errno)) - ret = error_errno(_("failed to delete '%s'"), filename); - - free(filename); - free(local_timer_name); - return ret; -} - -static int systemd_timer_delete_service_template(void) -{ - int ret = 0; - char *local_service_name = xstrfmt(SYSTEMD_UNIT_FORMAT, "", "service"); - char *filename = xdg_config_home_systemd(local_service_name); - if (unlink(filename) && !is_missing_file_error(errno)) - ret = error_errno(_("failed to delete '%s'"), filename); - - free(filename); - free(local_service_name); - return ret; -} - -/* - * Write the schedule information into a git-maintenance@.timer - * file using a custom minute. This timer file cannot use the templating - * system, so we generate a specific file for each. - */ -static int systemd_timer_write_timer_file(enum schedule_priority schedule, - int minute) -{ - int res = -1; - char *filename; - FILE *file; - const char *unit; - char *schedule_pattern = NULL; - const char *frequency = get_frequency(schedule); - char *local_timer_name = xstrfmt(SYSTEMD_UNIT_FORMAT, frequency, "timer"); - - filename = xdg_config_home_systemd(local_timer_name); - - if (safe_create_leading_directories(filename)) { - error(_("failed to create directories for '%s'"), filename); - goto error; - } - file = fopen_or_warn(filename, "w"); - if (!file) - goto error; - - switch (schedule) { - case SCHEDULE_HOURLY: - schedule_pattern = xstrfmt("*-*-* 1..23:%02d:00", minute); - break; - - case SCHEDULE_DAILY: - schedule_pattern = xstrfmt("Tue..Sun *-*-* 0:%02d:00", minute); - break; - - case SCHEDULE_WEEKLY: - schedule_pattern = xstrfmt("Mon 0:%02d:00", minute); - break; - - default: - BUG("Unhandled schedule_priority"); - } - - unit = "# This file was created and is maintained by Git.\n" - "# Any edits made in this file might be replaced in the future\n" - "# by a Git command.\n" - "\n" - "[Unit]\n" - "Description=Optimize Git repositories data\n" - "\n" - "[Timer]\n" - "OnCalendar=%s\n" - "Persistent=true\n" - "\n" - "[Install]\n" - "WantedBy=timers.target\n"; - if (fprintf(file, unit, schedule_pattern) < 0) { - error(_("failed to write to '%s'"), filename); - fclose(file); - goto error; - } - if (fclose(file) == EOF) { - error_errno(_("failed to flush '%s'"), filename); - goto error; - } - - res = 0; - -error: - free(schedule_pattern); - free(local_timer_name); - free(filename); - return res; -} - -/* - * No matter the schedule, we use the same service and can make use of the - * templating system. When installing git-maintenance@.timer, - * systemd will notice that git-maintenance@.service exists as a template - * and will use this file and insert the into the template at - * the position of "%i". - */ -static int systemd_timer_write_service_template(const char *exec_path) -{ - int res = -1; - char *filename; - FILE *file; - const char *unit; - char *local_service_name = xstrfmt(SYSTEMD_UNIT_FORMAT, "", "service"); - - filename = xdg_config_home_systemd(local_service_name); - if (safe_create_leading_directories(filename)) { - error(_("failed to create directories for '%s'"), filename); - goto error; - } - file = fopen_or_warn(filename, "w"); - if (!file) - goto error; - - unit = "# This file was created and is maintained by Git.\n" - "# Any edits made in this file might be replaced in the future\n" - "# by a Git command.\n" - "\n" - "[Unit]\n" - "Description=Optimize Git repositories data\n" - "\n" - "[Service]\n" - "Type=oneshot\n" - "ExecStart=\"%s/git\" --exec-path=\"%s\" for-each-repo --config=maintenance.repo maintenance run --schedule=%%i\n" - "LockPersonality=yes\n" - "MemoryDenyWriteExecute=yes\n" - "NoNewPrivileges=yes\n" - "RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 AF_VSOCK\n" - "RestrictNamespaces=yes\n" - "RestrictRealtime=yes\n" - "RestrictSUIDSGID=yes\n" - "SystemCallArchitectures=native\n" - "SystemCallFilter=@system-service\n"; - if (fprintf(file, unit, exec_path, exec_path) < 0) { - error(_("failed to write to '%s'"), filename); - fclose(file); - goto error; - } - if (fclose(file) == EOF) { - error_errno(_("failed to flush '%s'"), filename); - goto error; - } - - res = 0; - -error: - free(local_service_name); - free(filename); - return res; -} - -static int systemd_timer_enable_unit(int enable, - enum schedule_priority schedule, - int minute) +static int systemd_set_units_state(int enable) { const char *cmd = "systemctl"; struct child_process child = CHILD_PROCESS_INIT; - const char *frequency = get_frequency(schedule); - - /* - * Disabling the systemd unit while it is already disabled makes - * systemctl print an error. - * Let's ignore it since it means we already are in the expected state: - * the unit is disabled. - * - * On the other hand, enabling a systemd unit which is already enabled - * produces no error. - */ - if (!enable) - child.no_stderr = 1; - else if (systemd_timer_write_timer_file(schedule, minute)) - return -1; get_schedule_cmd(&cmd, NULL); strvec_split(&child.args, cmd); - strvec_pushl(&child.args, "--user", enable ? "enable" : "disable", - "--now", NULL); - strvec_pushf(&child.args, SYSTEMD_UNIT_FORMAT, frequency, "timer"); + + strvec_pushl(&child.args, "--user", "--force", "--now", + enable ? "enable" : "disable", + "git-maintenance@hourly.timer", + "git-maintenance@daily.timer", + "git-maintenance@weekly.timer", NULL); + /* + ** --force override existing conflicting symlinks + ** We need it because the units have changed location (~/.config -> + ** /usr/lib) + */ if (start_command(&child)) return error(_("failed to start systemctl")); if (finish_command(&child)) - /* - * Disabling an already disabled systemd unit makes - * systemctl fail. - * Let's ignore this failure. - * - * Enabling an enabled systemd unit doesn't fail. - */ - if (enable) - return error(_("failed to run systemctl")); + return error(_("failed to run systemctl")); return 0; } -/* - * A previous version of Git wrote the timer units as template files. - * Clean these up, if they exist. - */ -static void systemd_timer_delete_stale_timer_templates(void) +static void systemd_delete_user_unit(char const *unit) { - char *timer_template_name = xstrfmt(SYSTEMD_UNIT_FORMAT, "", "timer"); - char *filename = xdg_config_home_systemd(timer_template_name); + char const file_start_stale[] = "# This file was created and is" + " maintained by Git."; + char file_start_user[sizeof(file_start_stale)] = {'\0'}; + + char *filename = xdg_config_home_systemd(unit); + int handle = open(filename, O_RDONLY); - if (unlink(filename) && !is_missing_file_error(errno)) + /* + ** Check this is actually our file and we're not removing a legitimate + ** user override. + */ + if (handle == -1 && !is_missing_file_error(errno)) warning(_("failed to delete '%s'"), filename); + else { + read(handle, file_start_user, sizeof(file_start_stale) - 1); + close(handle); + if (strcmp(file_start_stale, file_start_user) == 0) { + if (unlink(filename) == 0) + warning(_("deleted stale unit file '%s'"), filename); + else if (!is_missing_file_error(errno)) + warning(_("failed to delete '%s'"), filename); + } + } free(filename); - free(timer_template_name); -} - -static int systemd_timer_delete_unit_files(void) -{ - systemd_timer_delete_stale_timer_templates(); - - /* Purposefully not short-circuited to make sure all are called. */ - return systemd_timer_delete_timer_file(SCHEDULE_HOURLY) | - systemd_timer_delete_timer_file(SCHEDULE_DAILY) | - systemd_timer_delete_timer_file(SCHEDULE_WEEKLY) | - systemd_timer_delete_service_template(); -} - -static int systemd_timer_delete_units(void) -{ - int minute = get_random_minute(); - /* Purposefully not short-circuited to make sure all are called. */ - return systemd_timer_enable_unit(0, SCHEDULE_HOURLY, minute) | - systemd_timer_enable_unit(0, SCHEDULE_DAILY, minute) | - systemd_timer_enable_unit(0, SCHEDULE_WEEKLY, minute) | - systemd_timer_delete_unit_files(); -} - -static int systemd_timer_setup_units(void) -{ - int minute = get_random_minute(); - const char *exec_path = git_exec_path(); - - int ret = systemd_timer_write_service_template(exec_path) || - systemd_timer_enable_unit(1, SCHEDULE_HOURLY, minute) || - systemd_timer_enable_unit(1, SCHEDULE_DAILY, minute) || - systemd_timer_enable_unit(1, SCHEDULE_WEEKLY, minute); - - if (ret) - systemd_timer_delete_units(); - else - systemd_timer_delete_stale_timer_templates(); - - return ret; } static int systemd_timer_update_schedule(int run_maintenance, int fd UNUSED) { - if (run_maintenance) - return systemd_timer_setup_units(); - else - return systemd_timer_delete_units(); + /* + * A previous version of Git wrote the units in the user configuration + * directory. Clean these up, if they exist. + */ + systemd_delete_user_unit("git-maintenance@hourly.timer"); + systemd_delete_user_unit("git-maintenance@daily.timer"); + systemd_delete_user_unit("git-maintenance@weekly.timer"); + systemd_delete_user_unit("git-maintenance@.timer"); + systemd_delete_user_unit("git-maintenance@.service"); + return systemd_set_units_state(run_maintenance); } enum scheduler { From patchwork Mon Mar 18 15:07:22 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Gautier X-Patchwork-Id: 13595436 Received: from taslin.fdn.fr (taslin.fdn.fr [80.67.169.77]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E537350251 for ; Mon, 18 Mar 2024 15:17:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=80.67.169.77 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; cv=none; b=i6nC9a79AcnsmoBIDPZc48S7Re2CvnVm+juoZEubdM0cnqEDMKd7OtlPH9uCJthS6iDA2hXoBcVFVdShKgXarnUeJdap7FIg9cSssCDo4XJIKneBOjyhdUSsTUslMQW6Q4/svHtL/TAxlw0/fyt4mpegik/h/ZO6aRqMgvlYeIA= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775077; c=relaxed/simple; bh=22sMZ+QC/TBhlZ+GCFTA9dmPAv2p+PUO9SUQl5NRbYk=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=DOCL4N0Zbd2++1tMyc0xzpStc73fUHGCMBzxxVFIJZI5XYF8GYkaGmDJXr80cPm/W+CY3R/Mj3RBaxlW//eKrS6dKpMUqpQmviIwsqd55S7FA3dY1Mlul4cykH4nsyfmxaGNTFLZARcJv5QbkRiYEWYLpDphp1dYwwtvfgFw3sY= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name; spf=pass smtp.mailfrom=max.gautier.name; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b=DbyJpIJD; arc=none smtp.client-ip=80.67.169.77 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b="DbyJpIJD" Received: from localhost (unknown [IPv6:2001:910:10ee:0:fc9:9524:11d1:7aa4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by taslin.fdn.fr (Postfix) with ESMTPSA id D9344602E9; Mon, 18 Mar 2024 16:17:50 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=max.gautier.name; s=fdn; t=1710775070; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=ocZS4h1d9puN0KkDFHiEFjLOzjn7MTNjmGGNmcKalX4=; b=DbyJpIJDWtIoB8iSY04glQBrQGJQgf+5j0/+ushXsHbudiHGhWrScWxFckqjmNgSvrWQIL akLljUB53PEs17IENn2Ew7yucv1imVZdYBh6krnqlFKBea62Zc8lKiqW1u73ZleDVoV+IB jO3LL0SmfEm6FH0BCdGt2xliv9kil+ekEKbpGuIykr5o4LH+B8eN9ZmHeEqeaPPEBElibu 89bbj1iXSF976zd3aOXdRyXk8cTQPHM5l8uc9FOsfuG1OuPL8bFwR0wBGOhf6qnGnLImfP 52Tm7XiaDJIfhMwMGIR8GrRUbKu0o4a3Vebo/dtJm3+EaQYkWCkMJKgRD28mCA== From: Max Gautier To: git@vger.kernel.org Cc: =?utf-8?b?TMOpbmHDr2MgSHVhcmQ=?= , Max Gautier Subject: [RFC PATCH 4/5] maintenance: update systemd scheduler docs Date: Mon, 18 Mar 2024 16:07:22 +0100 Message-ID: <20240318151701.26644-6-mg@max.gautier.name> X-Mailer: git-send-email 2.44.0 In-Reply-To: <20240318151701.26644-2-mg@max.gautier.name> References: <20240318151701.26644-2-mg@max.gautier.name> Precedence: bulk X-Mailing-List: git@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Signed-off-by: Max Gautier --- Documentation/git-maintenance.txt | 33 +++++++++++++++---------------- 1 file changed, 16 insertions(+), 17 deletions(-) diff --git a/Documentation/git-maintenance.txt b/Documentation/git-maintenance.txt index 51d0f7e94b..6511c3f3f1 100644 --- a/Documentation/git-maintenance.txt +++ b/Documentation/git-maintenance.txt @@ -304,10 +304,9 @@ distributions, systemd timers are superseding it. If user systemd timers are available, they will be used as a replacement of `cron`. -In this case, `git maintenance start` will create user systemd timer units -and start the timers. The current list of user-scheduled tasks can be found -by running `systemctl --user list-timers`. The timers written by `git -maintenance start` are similar to this: +In this case, `git maintenance start` will enable user systemd timer units +and start them. The current list of user-scheduled tasks can be found by +running `systemctl --user list-timers`. These timers are similar to this: ----------------------------------------------------------------------- $ systemctl --user list-timers @@ -317,25 +316,25 @@ Fri 2021-04-30 00:00:00 CEST 5h 42min left Thu 2021-04-29 00:00:11 CEST 18h ago Mon 2021-05-03 00:00:00 CEST 3 days left Mon 2021-04-26 00:00:11 CEST 3 days ago git-maintenance@weekly.timer git-maintenance@weekly.service ----------------------------------------------------------------------- -One timer is registered for each `--schedule=` option. +One timer instance is enabled for each `--schedule=` option. -The definition of the systemd units can be inspected in the following files: +The definition of the systemd units can be inspected this way: ----------------------------------------------------------------------- -~/.config/systemd/user/git-maintenance@.timer -~/.config/systemd/user/git-maintenance@.service -~/.config/systemd/user/timers.target.wants/git-maintenance@hourly.timer -~/.config/systemd/user/timers.target.wants/git-maintenance@daily.timer -~/.config/systemd/user/timers.target.wants/git-maintenance@weekly.timer +$ systemctl cat --user git-maintenance@.timer +$ systemctl cat --user git-maintenance@.service ----------------------------------------------------------------------- -`git maintenance start` will overwrite these files and start the timer -again with `systemctl --user`, so any customization should be done by -creating a drop-in file, i.e. a `.conf` suffixed file in the -`~/.config/systemd/user/git-maintenance@.service.d` directory. +Customization of the timer or service can be performed with the usual systemd +tooling: +----------------------------------------------------------------------- +$ systemctl edit --user git-maintenance@.timer # all the timers +$ systemctl edit --user git-maintenance@hourly.timer # the hourly timer +$ systemctl edit --user git-maintenance@.service # all the services +$ systemctl edit --user git-maintenance@hourly.service # the hourly run +----------------------------------------------------------------------- -`git maintenance stop` will stop the user systemd timers and delete -the above mentioned files. +`git maintenance stop` will disable and stop the user systemd timers. For more details, see `systemd.timer(5)`. From patchwork Mon Mar 18 15:07:23 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Gautier X-Patchwork-Id: 13595437 Received: from taslin.fdn.fr (taslin.fdn.fr [80.67.169.77]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 899E2524B5 for ; Mon, 18 Mar 2024 15:17:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=80.67.169.77 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775080; cv=none; b=EtxHMYNlLB8XCtIMADAWQrtFDvQlTNoGtGqWcXRHVDB4V8SF2zqAXzYTauIqeUTwvgnDLfQwJhRi7ULl7TdcC0tdHqlpTNkyiPh27+kZao2RHbXkRvrdoI3IJr3FMLOuWaioRowWSefepJejDNOg5r7EqtchTZMBc8XXulri7iU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1710775080; c=relaxed/simple; bh=Tf/fl2n1Y0XpAglZm4wPJCXiKVlGqlRFJEv7y4THzqI=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=DdaeOaSIu0JwQY9SykxsmgczonAEJJIKP2zf7VNjiJ41h4UMU0QXhP2vy+y2Q+v30VikixnrfRIp96xuQDaA27aJSn/trRlOvg0/O54ptmXYAWWD6FYwrMYTWDR+7BAoLHf0i3WnR9EwpvZPgL8CZirynb8+1tKO2I1WxcYvTDA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name; spf=pass smtp.mailfrom=max.gautier.name; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b=sy8+2IWb; arc=none smtp.client-ip=80.67.169.77 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=max.gautier.name Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=max.gautier.name header.i=@max.gautier.name header.b="sy8+2IWb" Received: from localhost (unknown [IPv6:2001:910:10ee:0:fc9:9524:11d1:7aa4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by taslin.fdn.fr (Postfix) with ESMTPSA id 350AE602EB; Mon, 18 Mar 2024 16:17:51 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=max.gautier.name; s=fdn; t=1710775071; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=Sotbr++pnaTGjpXsOGQZ4VlAGybpbc4NEfF1utfySDo=; b=sy8+2IWbjJ8KJoi8QUB8XM4R2cGSS7LUWxcoETNPwl2oKgzlU14/nGnzdvFEMJysJD7MO2 dleQrfyiWQ4cPUDQjvAvYcVpQaun2MiFAVqHn5vvTjZYm/hVc3k54lx5x+da/ZFEGYspYB gOa7JdzAWxasmJWFNmjKLQPG37pcz1tclX9twkhatVe/B4jGai/oAGx4nHXpp7I1RlmeDY +LkfbRxZeRKA9DgxmcdeMNZ7Z9GpMk1YxLmFhIU0Ipv0Dz2vlhBDuD4CpzvMggU/2/vv4l 4B03Z1iRZ1AYT9lCbqNXk+P45FB0HcsC9i50KKG5WqVjFEHCv7ApMNhlp3kV+Q== From: Max Gautier To: git@vger.kernel.org Cc: =?utf-8?b?TMOpbmHDr2MgSHVhcmQ=?= , Max Gautier Subject: [RFC PATCH 5/5] DON'T APPLY YET: maintenance: remove cleanup code Date: Mon, 18 Mar 2024 16:07:23 +0100 Message-ID: <20240318151701.26644-7-mg@max.gautier.name> X-Mailer: git-send-email 2.44.0 In-Reply-To: <20240318151701.26644-2-mg@max.gautier.name> References: <20240318151701.26644-2-mg@max.gautier.name> Precedence: bulk X-Mailing-List: git@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 This removes code to remove old git-maintenance systemd timer and service user units which were written in $XDG_CONFIG_HOME by git previous versions. Signed-off-by: Max Gautier --- builtin/gc.c | 54 +++------------------------------------------------- 1 file changed, 3 insertions(+), 51 deletions(-) diff --git a/builtin/gc.c b/builtin/gc.c index 981db8e297..6ac184eaf5 100644 --- a/builtin/gc.c +++ b/builtin/gc.c @@ -2303,12 +2303,7 @@ static int is_systemd_timer_available(void) return real_is_systemd_timer_available(); } -static char *xdg_config_home_systemd(const char *filename) -{ - return xdg_config_home_for("systemd/user", filename); -} - -static int systemd_set_units_state(int enable) +static int systemd_set_units_state(int run_maintenance, int fd UNUSED) { const char *cmd = "systemctl"; struct child_process child = CHILD_PROCESS_INIT; @@ -2317,7 +2312,7 @@ static int systemd_set_units_state(int enable) strvec_split(&child.args, cmd); strvec_pushl(&child.args, "--user", "--force", "--now", - enable ? "enable" : "disable", + run_maintenance ? "enable" : "disable", "git-maintenance@hourly.timer", "git-maintenance@daily.timer", "git-maintenance@weekly.timer", NULL); @@ -2334,49 +2329,6 @@ static int systemd_set_units_state(int enable) return 0; } -static void systemd_delete_user_unit(char const *unit) -{ - char const file_start_stale[] = "# This file was created and is" - " maintained by Git."; - char file_start_user[sizeof(file_start_stale)] = {'\0'}; - - char *filename = xdg_config_home_systemd(unit); - int handle = open(filename, O_RDONLY); - - /* - ** Check this is actually our file and we're not removing a legitimate - ** user override. - */ - if (handle == -1 && !is_missing_file_error(errno)) - warning(_("failed to delete '%s'"), filename); - else { - read(handle, file_start_user, sizeof(file_start_stale) - 1); - close(handle); - if (strcmp(file_start_stale, file_start_user) == 0) { - if (unlink(filename) == 0) - warning(_("deleted stale unit file '%s'"), filename); - else if (!is_missing_file_error(errno)) - warning(_("failed to delete '%s'"), filename); - } - } - - free(filename); -} - -static int systemd_timer_update_schedule(int run_maintenance, int fd UNUSED) -{ - /* - * A previous version of Git wrote the units in the user configuration - * directory. Clean these up, if they exist. - */ - systemd_delete_user_unit("git-maintenance@hourly.timer"); - systemd_delete_user_unit("git-maintenance@daily.timer"); - systemd_delete_user_unit("git-maintenance@weekly.timer"); - systemd_delete_user_unit("git-maintenance@.timer"); - systemd_delete_user_unit("git-maintenance@.service"); - return systemd_set_units_state(run_maintenance); -} - enum scheduler { SCHEDULER_INVALID = -1, SCHEDULER_AUTO, @@ -2399,7 +2351,7 @@ static const struct { [SCHEDULER_SYSTEMD] = { .name = "systemctl", .is_available = is_systemd_timer_available, - .update_schedule = systemd_timer_update_schedule, + .update_schedule = systemd_set_units_state, }, [SCHEDULER_LAUNCHCTL] = { .name = "launchctl",