diff options
author | djm@openbsd.org <djm@openbsd.org> | 2018-11-23 05:08:07 +0000 |
---|---|---|
committer | Damien Miller <djm@mindrot.org> | 2018-11-23 16:09:12 +1100 |
commit | 9e34e0c59ab04514f9de9934a772283f7f372afe (patch) | |
tree | 4306e1438b1efe0283b635d4d4ed1256cff0fe59 /ssh.c | |
parent | 4da58d58736b065b1182b563d10ad6765d811c6d (diff) |
upstream: add a ssh_config "Match final" predicate
Matches in same pass as "Match canonical" but doesn't require
hostname canonicalisation be enabled. bz#2906 ok markus
OpenBSD-Commit-ID: fba1dfe9f6e0cabcd0e2b3be13f7a434199beffa
Diffstat (limited to 'ssh.c')
-rw-r--r-- | ssh.c | 31 |
1 files changed, 20 insertions, 11 deletions
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssh.c,v 1.495 2018/10/23 05:56:35 djm Exp $ */ | 1 | /* $OpenBSD: ssh.c,v 1.496 2018/11/23 05:08:07 djm Exp $ */ |
2 | /* | 2 | /* |
3 | * Author: Tatu Ylonen <ylo@cs.hut.fi> | 3 | * Author: Tatu Ylonen <ylo@cs.hut.fi> |
4 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland | 4 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland |
@@ -527,7 +527,8 @@ check_load(int r, const char *path, const char *message) | |||
527 | * file if the user specifies a config file on the command line. | 527 | * file if the user specifies a config file on the command line. |
528 | */ | 528 | */ |
529 | static void | 529 | static void |
530 | process_config_files(const char *host_name, struct passwd *pw, int post_canon) | 530 | process_config_files(const char *host_name, struct passwd *pw, int final_pass, |
531 | int *want_final_pass) | ||
531 | { | 532 | { |
532 | char buf[PATH_MAX]; | 533 | char buf[PATH_MAX]; |
533 | int r; | 534 | int r; |
@@ -535,7 +536,8 @@ process_config_files(const char *host_name, struct passwd *pw, int post_canon) | |||
535 | if (config != NULL) { | 536 | if (config != NULL) { |
536 | if (strcasecmp(config, "none") != 0 && | 537 | if (strcasecmp(config, "none") != 0 && |
537 | !read_config_file(config, pw, host, host_name, &options, | 538 | !read_config_file(config, pw, host, host_name, &options, |
538 | SSHCONF_USERCONF | (post_canon ? SSHCONF_POSTCANON : 0))) | 539 | SSHCONF_USERCONF | (final_pass ? SSHCONF_FINAL : 0), |
540 | want_final_pass)) | ||
539 | fatal("Can't open user config file %.100s: " | 541 | fatal("Can't open user config file %.100s: " |
540 | "%.100s", config, strerror(errno)); | 542 | "%.100s", config, strerror(errno)); |
541 | } else { | 543 | } else { |
@@ -544,12 +546,12 @@ process_config_files(const char *host_name, struct passwd *pw, int post_canon) | |||
544 | if (r > 0 && (size_t)r < sizeof(buf)) | 546 | if (r > 0 && (size_t)r < sizeof(buf)) |
545 | (void)read_config_file(buf, pw, host, host_name, | 547 | (void)read_config_file(buf, pw, host, host_name, |
546 | &options, SSHCONF_CHECKPERM | SSHCONF_USERCONF | | 548 | &options, SSHCONF_CHECKPERM | SSHCONF_USERCONF | |
547 | (post_canon ? SSHCONF_POSTCANON : 0)); | 549 | (final_pass ? SSHCONF_FINAL : 0), want_final_pass); |
548 | 550 | ||
549 | /* Read systemwide configuration file after user config. */ | 551 | /* Read systemwide configuration file after user config. */ |
550 | (void)read_config_file(_PATH_HOST_CONFIG_FILE, pw, | 552 | (void)read_config_file(_PATH_HOST_CONFIG_FILE, pw, |
551 | host, host_name, &options, | 553 | host, host_name, &options, |
552 | post_canon ? SSHCONF_POSTCANON : 0); | 554 | final_pass ? SSHCONF_FINAL : 0, want_final_pass); |
553 | } | 555 | } |
554 | } | 556 | } |
555 | 557 | ||
@@ -581,7 +583,7 @@ main(int ac, char **av) | |||
581 | { | 583 | { |
582 | struct ssh *ssh = NULL; | 584 | struct ssh *ssh = NULL; |
583 | int i, r, opt, exit_status, use_syslog, direct, timeout_ms; | 585 | int i, r, opt, exit_status, use_syslog, direct, timeout_ms; |
584 | int was_addr, config_test = 0, opt_terminated = 0; | 586 | int was_addr, config_test = 0, opt_terminated = 0, want_final_pass = 0; |
585 | char *p, *cp, *line, *argv0, buf[PATH_MAX], *logfile; | 587 | char *p, *cp, *line, *argv0, buf[PATH_MAX], *logfile; |
586 | char cname[NI_MAXHOST]; | 588 | char cname[NI_MAXHOST]; |
587 | struct stat st; | 589 | struct stat st; |
@@ -1089,7 +1091,9 @@ main(int ac, char **av) | |||
1089 | ); | 1091 | ); |
1090 | 1092 | ||
1091 | /* Parse the configuration files */ | 1093 | /* Parse the configuration files */ |
1092 | process_config_files(host_arg, pw, 0); | 1094 | process_config_files(host_arg, pw, 0, &want_final_pass); |
1095 | if (want_final_pass) | ||
1096 | debug("configuration requests final Match pass"); | ||
1093 | 1097 | ||
1094 | /* Hostname canonicalisation needs a few options filled. */ | 1098 | /* Hostname canonicalisation needs a few options filled. */ |
1095 | fill_default_options_for_canonicalization(&options); | 1099 | fill_default_options_for_canonicalization(&options); |
@@ -1146,12 +1150,17 @@ main(int ac, char **av) | |||
1146 | * If canonicalisation is enabled then re-parse the configuration | 1150 | * If canonicalisation is enabled then re-parse the configuration |
1147 | * files as new stanzas may match. | 1151 | * files as new stanzas may match. |
1148 | */ | 1152 | */ |
1149 | if (options.canonicalize_hostname != 0) { | 1153 | if (options.canonicalize_hostname != 0 && !want_final_pass) { |
1150 | debug("Re-reading configuration after hostname " | 1154 | debug("hostname canonicalisation enabled, " |
1151 | "canonicalisation"); | 1155 | "will re-parse configuration"); |
1156 | want_final_pass = 1; | ||
1157 | } | ||
1158 | |||
1159 | if (want_final_pass) { | ||
1160 | debug("re-parsing configuration"); | ||
1152 | free(options.hostname); | 1161 | free(options.hostname); |
1153 | options.hostname = xstrdup(host); | 1162 | options.hostname = xstrdup(host); |
1154 | process_config_files(host_arg, pw, 1); | 1163 | process_config_files(host_arg, pw, 1, NULL); |
1155 | /* | 1164 | /* |
1156 | * Address resolution happens early with canonicalisation | 1165 | * Address resolution happens early with canonicalisation |
1157 | * enabled and the port number may have changed since, so | 1166 | * enabled and the port number may have changed since, so |