Bugzilla – Attachment 3179 Details for
Bug 2906
Need something like 'Match finalpass'
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Match final
bz2906.diff (text/plain), 10.22 KB, created by
Damien Miller
on 2018-09-21 14:17:32 AEST
(
hide
)
Description:
Match final
Filename:
MIME Type:
Creator:
Damien Miller
Created:
2018-09-21 14:17:32 AEST
Size:
10.22 KB
patch
obsolete
>commit d1467538cbe8d42a53a02925d4f44ce499d4606a >Author: Damien Miller <djm@mindrot.org> >Date: Fri Sep 21 14:14:39 2018 +1000 > > Match final > >diff --git a/readconf.c b/readconf.c >index c4f8e19..017884f 100644 >--- a/readconf.c >+++ b/readconf.c >@@ -118,10 +118,11 @@ > > static int read_config_file_depth(const char *filename, struct passwd *pw, > const char *host, const char *original_host, Options *options, >- int flags, int *activep, int depth); >+ int flags, int *activep, int *want_final_pass, int depth); > static int process_config_line_depth(Options *options, struct passwd *pw, > const char *host, const char *original_host, char *line, >- const char *filename, int linenum, int *activep, int flags, int depth); >+ const char *filename, int linenum, int *activep, int flags, >+ int *want_final_pass, int depth); > > /* Keyword tokens. */ > >@@ -524,8 +525,8 @@ execute_in_shell(const char *cmd) > */ > static int > match_cfg_line(Options *options, char **condition, struct passwd *pw, >- const char *host_arg, const char *original_host, int post_canon, >- const char *filename, int linenum) >+ const char *host_arg, const char *original_host, int final_pass, >+ int *want_final_pass, const char *filename, int linenum) > { > char *arg, *oattrib, *attrib, *cmd, *cp = *condition, *host, *criteria; > const char *ruser; >@@ -539,7 +540,7 @@ match_cfg_line(Options *options, char **condition, struct passwd *pw, > */ > port = options->port <= 0 ? default_ssh_port() : options->port; > ruser = options->user == NULL ? pw->pw_name : options->user; >- if (post_canon) { >+ if (final_pass) { > host = xstrdup(options->hostname); > } else if (options->hostname != NULL) { > /* NB. Please keep in sync with ssh.c:main() */ >@@ -571,8 +572,16 @@ match_cfg_line(Options *options, char **condition, struct passwd *pw, > goto out; > } > attributes++; >- if (strcasecmp(attrib, "canonical") == 0) { >- r = !!post_canon; /* force bitmask member to boolean */ >+ if (strcasecmp(attrib, "canonical") == 0 || >+ strcasecmp(attrib, "final") == 0) { >+ /* >+ * If the config requests "Match final" then remember >+ * this so we can perform a second pass later. >+ */ >+ if (strcasecmp(attrib, "final") == 0 && >+ want_final_pass != NULL) >+ *want_final_pass = 1; >+ r = !!final_pass; /* force bitmask member to boolean */ > if (r == (negate ? 1 : 0)) > this_result = result = 0; > debug3("%.200s line %d: %smatched '%s'", >@@ -809,14 +818,14 @@ process_config_line(Options *options, struct passwd *pw, const char *host, > int linenum, int *activep, int flags) > { > return process_config_line_depth(options, pw, host, original_host, >- line, filename, linenum, activep, flags, 0); >+ line, filename, linenum, activep, flags, NULL, 0); > } > > #define WHITESPACE " \t\r\n" > static int > process_config_line_depth(Options *options, struct passwd *pw, const char *host, > const char *original_host, char *line, const char *filename, >- int linenum, int *activep, int flags, int depth) >+ int linenum, int *activep, int flags, int *want_final_pass, int depth) > { > char *s, **charptr, *endofnumber, *keyword, *arg, *arg2; > char **cpptr, fwdarg[256]; >@@ -1315,7 +1324,8 @@ parse_keytypes: > fatal("Host directive not supported as a command-line " > "option"); > value = match_cfg_line(options, &s, pw, host, original_host, >- flags & SSHCONF_POSTCANON, filename, linenum); >+ flags & SSHCONF_FINAL, want_final_pass, >+ filename, linenum); > if (value < 0) > fatal("%.200s line %d: Bad Match condition", filename, > linenum); >@@ -1524,7 +1534,7 @@ parse_keytypes: > pw, host, original_host, options, > flags | SSHCONF_CHECKPERM | > (oactive ? 0 : SSHCONF_NEVERMATCH), >- activep, depth + 1); >+ activep, want_final_pass, depth + 1); > if (r != 1 && errno != ENOENT) { > fatal("Can't open user config file " > "%.100s: %.100s", gl.gl_pathv[i], >@@ -1716,19 +1726,20 @@ parse_keytypes: > */ > int > read_config_file(const char *filename, struct passwd *pw, const char *host, >- const char *original_host, Options *options, int flags) >+ const char *original_host, Options *options, int flags, >+ int *want_final_pass) > { > int active = 1; > > return read_config_file_depth(filename, pw, host, original_host, >- options, flags, &active, 0); >+ options, flags, &active, want_final_pass, 0); > } > > #define READCONF_MAX_DEPTH 16 > static int > read_config_file_depth(const char *filename, struct passwd *pw, > const char *host, const char *original_host, Options *options, >- int flags, int *activep, int depth) >+ int flags, int *activep, int *want_final_pass, int depth) > { > FILE *f; > char *line = NULL; >@@ -1763,7 +1774,8 @@ read_config_file_depth(const char *filename, struct passwd *pw, > /* Update line number counter. */ > linenum++; > if (process_config_line_depth(options, pw, host, original_host, >- line, filename, linenum, activep, flags, depth) != 0) >+ line, filename, linenum, activep, flags, want_final_pass, >+ depth) != 0) > bad_options++; > } > free(line); >diff --git a/readconf.h b/readconf.h >index fc7e382..1a4f97d 100644 >--- a/readconf.h >+++ b/readconf.h >@@ -185,7 +185,7 @@ typedef struct { > > #define SSHCONF_CHECKPERM 1 /* check permissions on config file */ > #define SSHCONF_USERCONF 2 /* user provided config file not system */ >-#define SSHCONF_POSTCANON 4 /* After hostname canonicalisation */ >+#define SSHCONF_FINAL 4 /* Final pass over config, after canon. */ > #define SSHCONF_NEVERMATCH 8 /* Match/Host never matches; internal only */ > > #define SSH_UPDATE_HOSTKEYS_NO 0 >@@ -203,7 +203,7 @@ void fill_default_options_for_canonicalization(Options *); > int process_config_line(Options *, struct passwd *, const char *, > const char *, char *, const char *, int, int *, int); > int read_config_file(const char *, struct passwd *, const char *, >- const char *, Options *, int); >+ const char *, Options *, int, int *); > int parse_forward(struct Forward *, const char *, int, int); > int parse_jump(const char *, Options *, int); > int parse_ssh_uri(const char *, char **, char **, int *); >diff --git a/ssh.c b/ssh.c >index d96fba9..a2efb62 100644 >--- a/ssh.c >+++ b/ssh.c >@@ -511,7 +511,8 @@ check_load(int r, const char *path, const char *message) > * file if the user specifies a config file on the command line. > */ > static void >-process_config_files(const char *host_name, struct passwd *pw, int post_canon) >+process_config_files(const char *host_name, struct passwd *pw, int final_pass, >+ int *want_final_pass) > { > char buf[PATH_MAX]; > int r; >@@ -519,7 +520,8 @@ process_config_files(const char *host_name, struct passwd *pw, int post_canon) > if (config != NULL) { > if (strcasecmp(config, "none") != 0 && > !read_config_file(config, pw, host, host_name, &options, >- SSHCONF_USERCONF | (post_canon ? SSHCONF_POSTCANON : 0))) >+ SSHCONF_USERCONF | (final_pass ? SSHCONF_FINAL : 0), >+ want_final_pass)) > fatal("Can't open user config file %.100s: " > "%.100s", config, strerror(errno)); > } else { >@@ -528,12 +530,12 @@ process_config_files(const char *host_name, struct passwd *pw, int post_canon) > if (r > 0 && (size_t)r < sizeof(buf)) > (void)read_config_file(buf, pw, host, host_name, > &options, SSHCONF_CHECKPERM | SSHCONF_USERCONF | >- (post_canon ? SSHCONF_POSTCANON : 0)); >+ (final_pass ? SSHCONF_FINAL : 0), want_final_pass); > > /* Read systemwide configuration file after user config. */ > (void)read_config_file(_PATH_HOST_CONFIG_FILE, pw, > host, host_name, &options, >- post_canon ? SSHCONF_POSTCANON : 0); >+ final_pass ? SSHCONF_FINAL : 0, want_final_pass); > } > } > >@@ -565,7 +567,7 @@ main(int ac, char **av) > { > struct ssh *ssh = NULL; > int i, r, opt, exit_status, use_syslog, direct, timeout_ms; >- int was_addr, config_test = 0, opt_terminated = 0; >+ int was_addr, config_test = 0, opt_terminated = 0, want_final_pass = 0; > char *p, *cp, *line, *argv0, buf[PATH_MAX], *logfile; > char cname[NI_MAXHOST]; > struct stat st; >@@ -1068,7 +1070,9 @@ main(int ac, char **av) > ); > > /* Parse the configuration files */ >- process_config_files(host_arg, pw, 0); >+ process_config_files(host_arg, pw, 0, &want_final_pass); >+ if (want_final_pass) >+ debug("configuration requests final Match pass"); > > /* Hostname canonicalisation needs a few options filled. */ > fill_default_options_for_canonicalization(&options); >@@ -1125,12 +1129,17 @@ main(int ac, char **av) > * If canonicalisation is enabled then re-parse the configuration > * files as new stanzas may match. > */ >- if (options.canonicalize_hostname != 0) { >- debug("Re-reading configuration after hostname " >- "canonicalisation"); >+ if (options.canonicalize_hostname != 0 && !want_final_pass) { >+ debug("hostname canonicalisation enabled, " >+ "will re-parse configuration"); >+ want_final_pass = 1; >+ } >+ >+ if (want_final_pass) { >+ debug("re-parsing configuration"); > free(options.hostname); > options.hostname = xstrdup(host); >- process_config_files(host_arg, pw, 1); >+ process_config_files(host_arg, pw, 1, NULL); > /* > * Address resolution happens early with canonicalisation > * enabled and the port number may have changed since, so >diff --git a/ssh_config.5 b/ssh_config.5 >index 1bf1834..3167dc1 100644 >--- a/ssh_config.5 >+++ b/ssh_config.5 >@@ -139,6 +139,7 @@ or the single token > which always matches. > The available criteria keywords are: > .Cm canonical , >+.Cm final , > .Cm exec , > .Cm host , > .Cm originalhost , >@@ -148,12 +149,15 @@ and > The > .Cm all > criteria must appear alone or immediately after >-.Cm canonical . >+.Cm canonical >+or >+.Cm final . > Other criteria may be combined arbitrarily. > All criteria but > .Cm all >-and > .Cm canonical >+and >+.Cm final > require an argument. > Criteria may be negated by prepending an exclamation mark > .Pq Sq !\& . >@@ -166,6 +170,20 @@ after hostname canonicalization (see the > option.) > This may be useful to specify conditions that work with canonical host > names only. >+.Pp >+The >+.Cm final >+keyword requests that the configuration be re-parsed (regardless of whether >+.Cm CanonicalizeHostname >+is enabled), and matches only during this final pass. >+If >+.Cm CanonicalizeHostname >+is enabled, then >+.Cm canonical >+and >+.Cm final >+match during the same pass. >+.Pp > The > .Cm exec > keyword executes the specified command under the user's shell.
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 2906
: 3179