@@ -1780,32 +1780,33 @@ static const char *get_frequency(enum schedule_priority schedule)
1780
1780
* * If $GIT_TEST_MAINT_SCHEDULER is set, return true.
1781
1781
* In this case, the *cmd value is read as input.
1782
1782
*
1783
- * * if the input value * cmd is the key of one of the comma-separated list
1784
- * item, then *is_available is set to true and *cmd is modified and becomes
1783
+ * * if the input value cmd is the key of one of the comma-separated list
1784
+ * item, then *is_available is set to true and *out is set to
1785
1785
* the mock command.
1786
1786
*
1787
1787
* * if the input value *cmd isn’t the key of any of the comma-separated list
1788
- * item, then *is_available is set to false.
1788
+ * item, then *is_available is set to false and *out is set to the original
1789
+ * command.
1789
1790
*
1790
1791
* Ex.:
1791
1792
* GIT_TEST_MAINT_SCHEDULER not set
1792
1793
* +-------+-------------------------------------------------+
1793
1794
* | Input | Output |
1794
- * | *cmd | return code | *cmd | *is_available |
1795
+ * | *cmd | return code | *out | *is_available |
1795
1796
* +-------+-------------+-------------------+---------------+
1796
- * | "foo" | false | "foo" (unchanged) | (unchanged) |
1797
+ * | "foo" | false | NULL | (unchanged) |
1797
1798
* +-------+-------------+-------------------+---------------+
1798
1799
*
1799
1800
* GIT_TEST_MAINT_SCHEDULER set to “foo:./mock_foo.sh,bar:./mock_bar.sh”
1800
1801
* +-------+-------------------------------------------------+
1801
1802
* | Input | Output |
1802
- * | *cmd | return code | *cmd | *is_available |
1803
+ * | *cmd | return code | *out | *is_available |
1803
1804
* +-------+-------------+-------------------+---------------+
1804
1805
* | "foo" | true | "./mock.foo.sh" | true |
1805
- * | "qux" | true | "qux" (unchanged ) | false |
1806
+ * | "qux" | true | "qux" (allocated ) | false |
1806
1807
* +-------+-------------+-------------------+---------------+
1807
1808
*/
1808
- static int get_schedule_cmd (const char * * cmd , int * is_available )
1809
+ static int get_schedule_cmd (const char * cmd , int * is_available , char * * out )
1809
1810
{
1810
1811
char * testing = xstrdup_or_null (getenv ("GIT_TEST_MAINT_SCHEDULER" ));
1811
1812
struct string_list_item * item ;
@@ -1824,16 +1825,22 @@ static int get_schedule_cmd(const char **cmd, int *is_available)
1824
1825
if (string_list_split_in_place (& pair , item -> string , ":" , 2 ) != 2 )
1825
1826
continue ;
1826
1827
1827
- if (!strcmp (* cmd , pair .items [0 ].string )) {
1828
- * cmd = pair .items [1 ].string ;
1828
+ if (!strcmp (cmd , pair .items [0 ].string )) {
1829
+ if (out )
1830
+ * out = xstrdup (pair .items [1 ].string );
1829
1831
if (is_available )
1830
1832
* is_available = 1 ;
1831
- string_list_clear (& list , 0 );
1832
- UNLEAK (testing );
1833
- return 1 ;
1833
+ string_list_clear (& pair , 0 );
1834
+ goto out ;
1834
1835
}
1836
+
1837
+ string_list_clear (& pair , 0 );
1835
1838
}
1836
1839
1840
+ if (out )
1841
+ * out = xstrdup (cmd );
1842
+
1843
+ out :
1837
1844
string_list_clear (& list , 0 );
1838
1845
free (testing );
1839
1846
return 1 ;
@@ -1850,9 +1857,8 @@ static int get_random_minute(void)
1850
1857
1851
1858
static int is_launchctl_available (void )
1852
1859
{
1853
- const char * cmd = "launchctl" ;
1854
1860
int is_available ;
1855
- if (get_schedule_cmd (& cmd , & is_available ))
1861
+ if (get_schedule_cmd ("launchctl" , & is_available , NULL ))
1856
1862
return is_available ;
1857
1863
1858
1864
#ifdef __APPLE__
@@ -1890,12 +1896,12 @@ static char *launchctl_get_uid(void)
1890
1896
1891
1897
static int launchctl_boot_plist (int enable , const char * filename )
1892
1898
{
1893
- const char * cmd = "launchctl" ;
1899
+ char * cmd ;
1894
1900
int result ;
1895
1901
struct child_process child = CHILD_PROCESS_INIT ;
1896
1902
char * uid = launchctl_get_uid ();
1897
1903
1898
- get_schedule_cmd (& cmd , NULL );
1904
+ get_schedule_cmd ("launchctl" , NULL , & cmd );
1899
1905
strvec_split (& child .args , cmd );
1900
1906
strvec_pushl (& child .args , enable ? "bootstrap" : "bootout" , uid ,
1901
1907
filename , NULL );
@@ -1908,6 +1914,7 @@ static int launchctl_boot_plist(int enable, const char *filename)
1908
1914
1909
1915
result = finish_command (& child );
1910
1916
1917
+ free (cmd );
1911
1918
free (uid );
1912
1919
return result ;
1913
1920
}
@@ -1959,10 +1966,10 @@ static int launchctl_schedule_plist(const char *exec_path, enum schedule_priorit
1959
1966
static unsigned long lock_file_timeout_ms = ULONG_MAX ;
1960
1967
struct strbuf plist = STRBUF_INIT , plist2 = STRBUF_INIT ;
1961
1968
struct stat st ;
1962
- const char * cmd = "launchctl" ;
1969
+ char * cmd ;
1963
1970
int minute = get_random_minute ();
1964
1971
1965
- get_schedule_cmd (& cmd , NULL );
1972
+ get_schedule_cmd ("launchctl" , NULL , & cmd );
1966
1973
preamble = "<?xml version=\"1.0\"?>\n"
1967
1974
"<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">\n"
1968
1975
"<plist version=\"1.0\">"
@@ -2052,6 +2059,7 @@ static int launchctl_schedule_plist(const char *exec_path, enum schedule_priorit
2052
2059
2053
2060
free (filename );
2054
2061
free (name );
2062
+ free (cmd );
2055
2063
strbuf_release (& plist );
2056
2064
strbuf_release (& plist2 );
2057
2065
return 0 ;
@@ -2076,9 +2084,8 @@ static int launchctl_update_schedule(int run_maintenance, int fd UNUSED)
2076
2084
2077
2085
static int is_schtasks_available (void )
2078
2086
{
2079
- const char * cmd = "schtasks" ;
2080
2087
int is_available ;
2081
- if (get_schedule_cmd (& cmd , & is_available ))
2088
+ if (get_schedule_cmd ("schtasks" , & is_available , NULL ))
2082
2089
return is_available ;
2083
2090
2084
2091
#ifdef GIT_WINDOWS_NATIVE
@@ -2097,15 +2104,16 @@ static char *schtasks_task_name(const char *frequency)
2097
2104
2098
2105
static int schtasks_remove_task (enum schedule_priority schedule )
2099
2106
{
2100
- const char * cmd = "schtasks" ;
2107
+ char * cmd ;
2101
2108
struct child_process child = CHILD_PROCESS_INIT ;
2102
2109
const char * frequency = get_frequency (schedule );
2103
2110
char * name = schtasks_task_name (frequency );
2104
2111
2105
- get_schedule_cmd (& cmd , NULL );
2112
+ get_schedule_cmd ("schtasks" , NULL , & cmd );
2106
2113
strvec_split (& child .args , cmd );
2107
2114
strvec_pushl (& child .args , "/delete" , "/tn" , name , "/f" , NULL );
2108
2115
free (name );
2116
+ free (cmd );
2109
2117
2110
2118
return run_command (& child );
2111
2119
}
@@ -2119,7 +2127,7 @@ static int schtasks_remove_tasks(void)
2119
2127
2120
2128
static int schtasks_schedule_task (const char * exec_path , enum schedule_priority schedule )
2121
2129
{
2122
- const char * cmd = "schtasks" ;
2130
+ char * cmd ;
2123
2131
int result ;
2124
2132
struct child_process child = CHILD_PROCESS_INIT ;
2125
2133
const char * xml ;
@@ -2129,7 +2137,7 @@ static int schtasks_schedule_task(const char *exec_path, enum schedule_priority
2129
2137
struct strbuf tfilename = STRBUF_INIT ;
2130
2138
int minute = get_random_minute ();
2131
2139
2132
- get_schedule_cmd (& cmd , NULL );
2140
+ get_schedule_cmd ("schtasks" , NULL , & cmd );
2133
2141
2134
2142
strbuf_addf (& tfilename , "%s/schedule_%s_XXXXXX" ,
2135
2143
get_git_common_dir (), frequency );
@@ -2235,6 +2243,7 @@ static int schtasks_schedule_task(const char *exec_path, enum schedule_priority
2235
2243
2236
2244
delete_tempfile (& tfile );
2237
2245
free (name );
2246
+ free (cmd );
2238
2247
return result ;
2239
2248
}
2240
2249
@@ -2276,29 +2285,36 @@ static int check_crontab_process(const char *cmd)
2276
2285
2277
2286
static int is_crontab_available (void )
2278
2287
{
2279
- const char * cmd = "crontab" ;
2288
+ char * cmd ;
2280
2289
int is_available ;
2290
+ int ret ;
2281
2291
2282
- if (get_schedule_cmd (& cmd , & is_available ))
2283
- return is_available ;
2292
+ if (get_schedule_cmd ("crontab" , & is_available , & cmd )) {
2293
+ ret = is_available ;
2294
+ goto out ;
2295
+ }
2284
2296
2285
2297
#ifdef __APPLE__
2286
2298
/*
2287
2299
* macOS has cron, but it requires special permissions and will
2288
2300
* create a UI alert when attempting to run this command.
2289
2301
*/
2290
- return 0 ;
2302
+ ret = 0 ;
2291
2303
#else
2292
- return check_crontab_process (cmd );
2304
+ ret = check_crontab_process (cmd );
2293
2305
#endif
2306
+
2307
+ out :
2308
+ free (cmd );
2309
+ return ret ;
2294
2310
}
2295
2311
2296
2312
#define BEGIN_LINE "# BEGIN GIT MAINTENANCE SCHEDULE"
2297
2313
#define END_LINE "# END GIT MAINTENANCE SCHEDULE"
2298
2314
2299
2315
static int crontab_update_schedule (int run_maintenance , int fd )
2300
2316
{
2301
- const char * cmd = "crontab" ;
2317
+ char * cmd ;
2302
2318
int result = 0 ;
2303
2319
int in_old_region = 0 ;
2304
2320
struct child_process crontab_list = CHILD_PROCESS_INIT ;
@@ -2308,15 +2324,17 @@ static int crontab_update_schedule(int run_maintenance, int fd)
2308
2324
struct tempfile * tmpedit = NULL ;
2309
2325
int minute = get_random_minute ();
2310
2326
2311
- get_schedule_cmd (& cmd , NULL );
2327
+ get_schedule_cmd ("crontab" , NULL , & cmd );
2312
2328
strvec_split (& crontab_list .args , cmd );
2313
2329
strvec_push (& crontab_list .args , "-l" );
2314
2330
crontab_list .in = -1 ;
2315
2331
crontab_list .out = dup (fd );
2316
2332
crontab_list .git_cmd = 0 ;
2317
2333
2318
- if (start_command (& crontab_list ))
2319
- return error (_ ("failed to run 'crontab -l'; your system might not support 'cron'" ));
2334
+ if (start_command (& crontab_list )) {
2335
+ result = error (_ ("failed to run 'crontab -l'; your system might not support 'cron'" ));
2336
+ goto out ;
2337
+ }
2320
2338
2321
2339
/* Ignore exit code, as an empty crontab will return error. */
2322
2340
finish_command (& crontab_list );
@@ -2386,8 +2404,10 @@ static int crontab_update_schedule(int run_maintenance, int fd)
2386
2404
result = error (_ ("'crontab' died" ));
2387
2405
else
2388
2406
fclose (cron_list );
2407
+
2389
2408
out :
2390
2409
delete_tempfile (& tmpedit );
2410
+ free (cmd );
2391
2411
return result ;
2392
2412
}
2393
2413
@@ -2410,10 +2430,9 @@ static int real_is_systemd_timer_available(void)
2410
2430
2411
2431
static int is_systemd_timer_available (void )
2412
2432
{
2413
- const char * cmd = "systemctl" ;
2414
2433
int is_available ;
2415
2434
2416
- if (get_schedule_cmd (& cmd , & is_available ))
2435
+ if (get_schedule_cmd ("systemctl" , & is_available , NULL ))
2417
2436
return is_available ;
2418
2437
2419
2438
return real_is_systemd_timer_available ();
@@ -2594,9 +2613,10 @@ static int systemd_timer_enable_unit(int enable,
2594
2613
enum schedule_priority schedule ,
2595
2614
int minute )
2596
2615
{
2597
- const char * cmd = "systemctl" ;
2616
+ char * cmd = NULL ;
2598
2617
struct child_process child = CHILD_PROCESS_INIT ;
2599
2618
const char * frequency = get_frequency (schedule );
2619
+ int ret ;
2600
2620
2601
2621
/*
2602
2622
* Disabling the systemd unit while it is already disabled makes
@@ -2607,30 +2627,43 @@ static int systemd_timer_enable_unit(int enable,
2607
2627
* On the other hand, enabling a systemd unit which is already enabled
2608
2628
* produces no error.
2609
2629
*/
2610
- if (!enable )
2630
+ if (!enable ) {
2611
2631
child .no_stderr = 1 ;
2612
- else if (systemd_timer_write_timer_file (schedule , minute ))
2613
- return -1 ;
2632
+ } else if (systemd_timer_write_timer_file (schedule , minute )) {
2633
+ ret = -1 ;
2634
+ goto out ;
2635
+ }
2614
2636
2615
- get_schedule_cmd (& cmd , NULL );
2637
+ get_schedule_cmd ("systemctl" , NULL , & cmd );
2616
2638
strvec_split (& child .args , cmd );
2617
2639
strvec_pushl (& child .args , "--user" , enable ? "enable" : "disable" ,
2618
2640
"--now" , NULL );
2619
2641
strvec_pushf (& child .args , SYSTEMD_UNIT_FORMAT , frequency , "timer" );
2620
2642
2621
- if (start_command (& child ))
2622
- return error (_ ("failed to start systemctl" ));
2623
- if (finish_command (& child ))
2643
+ if (start_command (& child )) {
2644
+ ret = error (_ ("failed to start systemctl" ));
2645
+ goto out ;
2646
+ }
2647
+
2648
+ if (finish_command (& child )) {
2624
2649
/*
2625
2650
* Disabling an already disabled systemd unit makes
2626
2651
* systemctl fail.
2627
2652
* Let's ignore this failure.
2628
2653
*
2629
2654
* Enabling an enabled systemd unit doesn't fail.
2630
2655
*/
2631
- if (enable )
2632
- return error (_ ("failed to run systemctl" ));
2633
- return 0 ;
2656
+ if (enable ) {
2657
+ ret = error (_ ("failed to run systemctl" ));
2658
+ goto out ;
2659
+ }
2660
+ }
2661
+
2662
+ ret = 0 ;
2663
+
2664
+ out :
2665
+ free (cmd );
2666
+ return ret ;
2634
2667
}
2635
2668
2636
2669
/*
0 commit comments