diff options
author | Colin Watson <cjwatson@debian.org> | 2013-09-14 23:42:11 +0100 |
---|---|---|
committer | Colin Watson <cjwatson@debian.org> | 2013-09-14 23:42:11 +0100 |
commit | 327155e6824b3ee13837bdde04e4eb47e147ff46 (patch) | |
tree | 8f8743122403c7a2e6ed919156711fb1520c657f /misc.c | |
parent | 0334ce32304e9ba2a10ee5ca49ca6e8ff3ba6cf4 (diff) | |
parent | 74e339b8f8936bc0d985e053a076d0c9b5e9ea51 (diff) |
* New upstream release (http://www.openssh.com/txt/release-6.3).
- sftp(1): add support for resuming partial downloads using the "reget"
command and on the sftp commandline or on the "get" commandline using
the "-a" (append) option (closes: #158590).
- ssh(1): add an "IgnoreUnknown" configuration option to selectively
suppress errors arising from unknown configuration directives (closes:
#436052).
- sftp(1): update progressmeter when data is acknowledged, not when it's
sent (partially addresses #708372).
- ssh(1): do not fatally exit when attempting to cleanup multiplexing-
created channels that are incompletely opened (closes: #651357).
Diffstat (limited to 'misc.c')
-rw-r--r-- | misc.c | 59 |
1 files changed, 39 insertions, 20 deletions
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: misc.c,v 1.86 2011/09/05 05:59:08 djm Exp $ */ | 1 | /* $OpenBSD: misc.c,v 1.91 2013/07/12 00:43:50 djm Exp $ */ |
2 | /* | 2 | /* |
3 | * Copyright (c) 2000 Markus Friedl. All rights reserved. | 3 | * Copyright (c) 2000 Markus Friedl. All rights reserved. |
4 | * Copyright (c) 2005,2006 Damien Miller. All rights reserved. | 4 | * Copyright (c) 2005,2006 Damien Miller. All rights reserved. |
@@ -129,7 +129,7 @@ unset_nonblock(int fd) | |||
129 | const char * | 129 | const char * |
130 | ssh_gai_strerror(int gaierr) | 130 | ssh_gai_strerror(int gaierr) |
131 | { | 131 | { |
132 | if (gaierr == EAI_SYSTEM) | 132 | if (gaierr == EAI_SYSTEM && errno != 0) |
133 | return strerror(errno); | 133 | return strerror(errno); |
134 | return gai_strerror(gaierr); | 134 | return gai_strerror(gaierr); |
135 | } | 135 | } |
@@ -208,16 +208,18 @@ pwcopy(struct passwd *pw) | |||
208 | 208 | ||
209 | copy->pw_name = xstrdup(pw->pw_name); | 209 | copy->pw_name = xstrdup(pw->pw_name); |
210 | copy->pw_passwd = xstrdup(pw->pw_passwd); | 210 | copy->pw_passwd = xstrdup(pw->pw_passwd); |
211 | #ifdef HAVE_STRUCT_PASSWD_PW_GECOS | ||
211 | copy->pw_gecos = xstrdup(pw->pw_gecos); | 212 | copy->pw_gecos = xstrdup(pw->pw_gecos); |
213 | #endif | ||
212 | copy->pw_uid = pw->pw_uid; | 214 | copy->pw_uid = pw->pw_uid; |
213 | copy->pw_gid = pw->pw_gid; | 215 | copy->pw_gid = pw->pw_gid; |
214 | #ifdef HAVE_PW_EXPIRE_IN_PASSWD | 216 | #ifdef HAVE_STRUCT_PASSWD_PW_EXPIRE |
215 | copy->pw_expire = pw->pw_expire; | 217 | copy->pw_expire = pw->pw_expire; |
216 | #endif | 218 | #endif |
217 | #ifdef HAVE_PW_CHANGE_IN_PASSWD | 219 | #ifdef HAVE_STRUCT_PASSWD_PW_CHANGE |
218 | copy->pw_change = pw->pw_change; | 220 | copy->pw_change = pw->pw_change; |
219 | #endif | 221 | #endif |
220 | #ifdef HAVE_PW_CLASS_IN_PASSWD | 222 | #ifdef HAVE_STRUCT_PASSWD_PW_CLASS |
221 | copy->pw_class = xstrdup(pw->pw_class); | 223 | copy->pw_class = xstrdup(pw->pw_class); |
222 | #endif | 224 | #endif |
223 | copy->pw_dir = xstrdup(pw->pw_dir); | 225 | copy->pw_dir = xstrdup(pw->pw_dir); |
@@ -253,13 +255,13 @@ a2tun(const char *s, int *remote) | |||
253 | *remote = SSH_TUNID_ANY; | 255 | *remote = SSH_TUNID_ANY; |
254 | sp = xstrdup(s); | 256 | sp = xstrdup(s); |
255 | if ((ep = strchr(sp, ':')) == NULL) { | 257 | if ((ep = strchr(sp, ':')) == NULL) { |
256 | xfree(sp); | 258 | free(sp); |
257 | return (a2tun(s, NULL)); | 259 | return (a2tun(s, NULL)); |
258 | } | 260 | } |
259 | ep[0] = '\0'; ep++; | 261 | ep[0] = '\0'; ep++; |
260 | *remote = a2tun(ep, NULL); | 262 | *remote = a2tun(ep, NULL); |
261 | tun = a2tun(sp, NULL); | 263 | tun = a2tun(sp, NULL); |
262 | xfree(sp); | 264 | free(sp); |
263 | return (*remote == SSH_TUNID_ERR ? *remote : tun); | 265 | return (*remote == SSH_TUNID_ERR ? *remote : tun); |
264 | } | 266 | } |
265 | 267 | ||
@@ -492,7 +494,7 @@ replacearg(arglist *args, u_int which, char *fmt, ...) | |||
492 | if (which >= args->num) | 494 | if (which >= args->num) |
493 | fatal("replacearg: tried to replace invalid arg %d >= %d", | 495 | fatal("replacearg: tried to replace invalid arg %d >= %d", |
494 | which, args->num); | 496 | which, args->num); |
495 | xfree(args->list[which]); | 497 | free(args->list[which]); |
496 | args->list[which] = cp; | 498 | args->list[which] = cp; |
497 | } | 499 | } |
498 | 500 | ||
@@ -503,8 +505,8 @@ freeargs(arglist *args) | |||
503 | 505 | ||
504 | if (args->list != NULL) { | 506 | if (args->list != NULL) { |
505 | for (i = 0; i < args->num; i++) | 507 | for (i = 0; i < args->num; i++) |
506 | xfree(args->list[i]); | 508 | free(args->list[i]); |
507 | xfree(args->list); | 509 | free(args->list); |
508 | args->nalloc = args->num = 0; | 510 | args->nalloc = args->num = 0; |
509 | args->list = NULL; | 511 | args->list = NULL; |
510 | } | 512 | } |
@@ -517,8 +519,8 @@ freeargs(arglist *args) | |||
517 | char * | 519 | char * |
518 | tilde_expand_filename(const char *filename, uid_t uid) | 520 | tilde_expand_filename(const char *filename, uid_t uid) |
519 | { | 521 | { |
520 | const char *path; | 522 | const char *path, *sep; |
521 | char user[128], ret[MAXPATHLEN]; | 523 | char user[128], *ret; |
522 | struct passwd *pw; | 524 | struct passwd *pw; |
523 | u_int len, slash; | 525 | u_int len, slash; |
524 | 526 | ||
@@ -538,22 +540,21 @@ tilde_expand_filename(const char *filename, uid_t uid) | |||
538 | } else if ((pw = getpwuid(uid)) == NULL) /* ~/path */ | 540 | } else if ((pw = getpwuid(uid)) == NULL) /* ~/path */ |
539 | fatal("tilde_expand_filename: No such uid %ld", (long)uid); | 541 | fatal("tilde_expand_filename: No such uid %ld", (long)uid); |
540 | 542 | ||
541 | if (strlcpy(ret, pw->pw_dir, sizeof(ret)) >= sizeof(ret)) | ||
542 | fatal("tilde_expand_filename: Path too long"); | ||
543 | |||
544 | /* Make sure directory has a trailing '/' */ | 543 | /* Make sure directory has a trailing '/' */ |
545 | len = strlen(pw->pw_dir); | 544 | len = strlen(pw->pw_dir); |
546 | if ((len == 0 || pw->pw_dir[len - 1] != '/') && | 545 | if (len == 0 || pw->pw_dir[len - 1] != '/') |
547 | strlcat(ret, "/", sizeof(ret)) >= sizeof(ret)) | 546 | sep = "/"; |
548 | fatal("tilde_expand_filename: Path too long"); | 547 | else |
548 | sep = ""; | ||
549 | 549 | ||
550 | /* Skip leading '/' from specified path */ | 550 | /* Skip leading '/' from specified path */ |
551 | if (path != NULL) | 551 | if (path != NULL) |
552 | filename = path + 1; | 552 | filename = path + 1; |
553 | if (strlcat(ret, filename, sizeof(ret)) >= sizeof(ret)) | 553 | |
554 | if (xasprintf(&ret, "%s%s%s", pw->pw_dir, sep, filename) >= MAXPATHLEN) | ||
554 | fatal("tilde_expand_filename: Path too long"); | 555 | fatal("tilde_expand_filename: Path too long"); |
555 | 556 | ||
556 | return (xstrdup(ret)); | 557 | return (ret); |
557 | } | 558 | } |
558 | 559 | ||
559 | /* | 560 | /* |
@@ -920,6 +921,24 @@ ms_to_timeval(struct timeval *tv, int ms) | |||
920 | tv->tv_usec = (ms % 1000) * 1000; | 921 | tv->tv_usec = (ms % 1000) * 1000; |
921 | } | 922 | } |
922 | 923 | ||
924 | time_t | ||
925 | monotime(void) | ||
926 | { | ||
927 | #if defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_MONOTONIC) | ||
928 | struct timespec ts; | ||
929 | static int gettime_failed = 0; | ||
930 | |||
931 | if (!gettime_failed) { | ||
932 | if (clock_gettime(CLOCK_MONOTONIC, &ts) == 0) | ||
933 | return (ts.tv_sec); | ||
934 | debug3("clock_gettime: %s", strerror(errno)); | ||
935 | gettime_failed = 1; | ||
936 | } | ||
937 | #endif | ||
938 | |||
939 | return time(NULL); | ||
940 | } | ||
941 | |||
923 | void | 942 | void |
924 | bandwidth_limit_init(struct bwlimit *bw, u_int64_t kbps, size_t buflen) | 943 | bandwidth_limit_init(struct bwlimit *bw, u_int64_t kbps, size_t buflen) |
925 | { | 944 | { |