diff options
Diffstat (limited to 'ssh_api.c')
-rw-r--r-- | ssh_api.c | 44 |
1 files changed, 29 insertions, 15 deletions
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssh_api.c,v 1.15 2019/01/21 10:38:54 djm Exp $ */ | 1 | /* $OpenBSD: ssh_api.c,v 1.18 2019/09/13 04:36:43 dtucker Exp $ */ |
2 | /* | 2 | /* |
3 | * Copyright (c) 2012 Markus Friedl. All rights reserved. | 3 | * Copyright (c) 2012 Markus Friedl. All rights reserved. |
4 | * | 4 | * |
@@ -17,6 +17,11 @@ | |||
17 | 17 | ||
18 | #include "includes.h" | 18 | #include "includes.h" |
19 | 19 | ||
20 | #include <sys/types.h> | ||
21 | |||
22 | #include <stdio.h> | ||
23 | #include <stdlib.h> | ||
24 | |||
20 | #include "ssh_api.h" | 25 | #include "ssh_api.h" |
21 | #include "compat.h" | 26 | #include "compat.h" |
22 | #include "log.h" | 27 | #include "log.h" |
@@ -50,7 +55,10 @@ int _ssh_host_key_sign(struct ssh *, struct sshkey *, struct sshkey *, | |||
50 | int use_privsep = 0; | 55 | int use_privsep = 0; |
51 | int mm_sshkey_sign(struct sshkey *, u_char **, u_int *, | 56 | int mm_sshkey_sign(struct sshkey *, u_char **, u_int *, |
52 | u_char *, u_int, char *, u_int); | 57 | u_char *, u_int, char *, u_int); |
58 | |||
59 | #ifdef WITH_OPENSSL | ||
53 | DH *mm_choose_dh(int, int, int); | 60 | DH *mm_choose_dh(int, int, int); |
61 | #endif | ||
54 | 62 | ||
55 | /* Define these two variables here so that they are part of the library */ | 63 | /* Define these two variables here so that they are part of the library */ |
56 | u_char *session_id2 = NULL; | 64 | u_char *session_id2 = NULL; |
@@ -63,11 +71,13 @@ mm_sshkey_sign(struct sshkey *key, u_char **sigp, u_int *lenp, | |||
63 | return (-1); | 71 | return (-1); |
64 | } | 72 | } |
65 | 73 | ||
74 | #ifdef WITH_OPENSSL | ||
66 | DH * | 75 | DH * |
67 | mm_choose_dh(int min, int nbits, int max) | 76 | mm_choose_dh(int min, int nbits, int max) |
68 | { | 77 | { |
69 | return (NULL); | 78 | return (NULL); |
70 | } | 79 | } |
80 | #endif | ||
71 | 81 | ||
72 | /* API */ | 82 | /* API */ |
73 | 83 | ||
@@ -320,8 +330,8 @@ _ssh_read_banner(struct ssh *ssh, struct sshbuf *banner) | |||
320 | const char *mismatch = "Protocol mismatch.\r\n"; | 330 | const char *mismatch = "Protocol mismatch.\r\n"; |
321 | const u_char *s = sshbuf_ptr(input); | 331 | const u_char *s = sshbuf_ptr(input); |
322 | u_char c; | 332 | u_char c; |
323 | char *cp, *remote_version; | 333 | char *cp = NULL, *remote_version = NULL; |
324 | int r, remote_major, remote_minor, expect_nl; | 334 | int r = 0, remote_major, remote_minor, expect_nl; |
325 | size_t n, j; | 335 | size_t n, j; |
326 | 336 | ||
327 | for (j = n = 0;;) { | 337 | for (j = n = 0;;) { |
@@ -347,10 +357,8 @@ _ssh_read_banner(struct ssh *ssh, struct sshbuf *banner) | |||
347 | if (sshbuf_len(banner) >= 4 && | 357 | if (sshbuf_len(banner) >= 4 && |
348 | memcmp(sshbuf_ptr(banner), "SSH-", 4) == 0) | 358 | memcmp(sshbuf_ptr(banner), "SSH-", 4) == 0) |
349 | break; | 359 | break; |
350 | if ((cp = sshbuf_dup_string(banner)) == NULL) | 360 | debug("%s: %.*s", __func__, (int)sshbuf_len(banner), |
351 | return SSH_ERR_ALLOC_FAIL; | 361 | sshbuf_ptr(banner)); |
352 | debug("%s: %s", __func__, cp); | ||
353 | free(cp); | ||
354 | /* Accept lines before banner only on client */ | 362 | /* Accept lines before banner only on client */ |
355 | if (ssh->kex->server || ++n > SSH_MAX_PRE_BANNER_LINES) { | 363 | if (ssh->kex->server || ++n > SSH_MAX_PRE_BANNER_LINES) { |
356 | bad: | 364 | bad: |
@@ -363,19 +371,22 @@ _ssh_read_banner(struct ssh *ssh, struct sshbuf *banner) | |||
363 | if ((r = sshbuf_consume(input, j)) != 0) | 371 | if ((r = sshbuf_consume(input, j)) != 0) |
364 | return r; | 372 | return r; |
365 | 373 | ||
366 | if ((cp = sshbuf_dup_string(banner)) == NULL) | ||
367 | return SSH_ERR_ALLOC_FAIL; | ||
368 | /* XXX remote version must be the same size as banner for sscanf */ | 374 | /* XXX remote version must be the same size as banner for sscanf */ |
369 | if ((remote_version = calloc(1, sshbuf_len(banner))) == NULL) | 375 | if ((cp = sshbuf_dup_string(banner)) == NULL || |
370 | return SSH_ERR_ALLOC_FAIL; | 376 | (remote_version = calloc(1, sshbuf_len(banner))) == NULL) { |
377 | r = SSH_ERR_ALLOC_FAIL; | ||
378 | goto out; | ||
379 | } | ||
371 | 380 | ||
372 | /* | 381 | /* |
373 | * Check that the versions match. In future this might accept | 382 | * Check that the versions match. In future this might accept |
374 | * several versions and set appropriate flags to handle them. | 383 | * several versions and set appropriate flags to handle them. |
375 | */ | 384 | */ |
376 | if (sscanf(cp, "SSH-%d.%d-%[^\n]\n", | 385 | if (sscanf(cp, "SSH-%d.%d-%[^\n]\n", |
377 | &remote_major, &remote_minor, remote_version) != 3) | 386 | &remote_major, &remote_minor, remote_version) != 3) { |
378 | return SSH_ERR_INVALID_FORMAT; | 387 | r = SSH_ERR_INVALID_FORMAT; |
388 | goto out; | ||
389 | } | ||
379 | debug("Remote protocol version %d.%d, remote software version %.100s", | 390 | debug("Remote protocol version %d.%d, remote software version %.100s", |
380 | remote_major, remote_minor, remote_version); | 391 | remote_major, remote_minor, remote_version); |
381 | 392 | ||
@@ -385,10 +396,13 @@ _ssh_read_banner(struct ssh *ssh, struct sshbuf *banner) | |||
385 | remote_minor = 0; | 396 | remote_minor = 0; |
386 | } | 397 | } |
387 | if (remote_major != 2) | 398 | if (remote_major != 2) |
388 | return SSH_ERR_PROTOCOL_MISMATCH; | 399 | r = SSH_ERR_PROTOCOL_MISMATCH; |
400 | |||
389 | debug("Remote version string %.100s", cp); | 401 | debug("Remote version string %.100s", cp); |
402 | out: | ||
390 | free(cp); | 403 | free(cp); |
391 | return 0; | 404 | free(remote_version); |
405 | return r; | ||
392 | } | 406 | } |
393 | 407 | ||
394 | /* Send our own protocol version identification. */ | 408 | /* Send our own protocol version identification. */ |