summaryrefslogtreecommitdiffstats
path: root/sftp-client.c
diff options
context:
space:
mode:
authorDamien Miller <djm@mindrot.org>2013-12-07 00:31:08 +0100
committerDamien Miller <djm@mindrot.org>2013-12-07 00:31:08 +0100
commit393920745fd328d3fe07f739a3cf7e1e6db45b60 (patch)
tree75c73ad0f58ede2b906c185ce83305519c067eb7 /sftp-client.c
parent - djm@cvs.openbsd.org 2013/12/05 01:16:41 (diff)
downloadopenssh-393920745fd328d3fe07f739a3cf7e1e6db45b60.tar.xz
openssh-393920745fd328d3fe07f739a3cf7e1e6db45b60.zip
- djm@cvs.openbsd.org 2013/12/05 22:59:45
[sftp-client.c] fix memory leak in error path in do_readdir(); pointed out by Loganaden Velvindron @ AfriNIC in bz#2163
Diffstat (limited to '')
-rw-r--r--sftp-client.c42
1 files changed, 21 insertions, 21 deletions
diff --git a/sftp-client.c b/sftp-client.c
index 246e94982..1eb821086 100644
--- a/sftp-client.c
+++ b/sftp-client.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: sftp-client.c,v 1.110 2013/12/04 04:20:01 djm Exp $ */
+/* $OpenBSD: sftp-client.c,v 1.111 2013/12/05 22:59:45 djm Exp $ */
/*
* Copyright (c) 2001-2004 Damien Miller <djm@openbsd.org>
*
@@ -460,6 +460,10 @@ do_lsreaddir(struct sftp_conn *conn, char *path, int print_flag,
Buffer msg;
u_int count, type, id, handle_len, i, expected_id, ents = 0;
char *handle;
+ int status = SSH2_FX_FAILURE;
+
+ if (dir)
+ *dir = NULL;
id = conn->msg_id++;
@@ -506,20 +510,12 @@ do_lsreaddir(struct sftp_conn *conn, char *path, int print_flag,
fatal("ID mismatch (%u != %u)", id, expected_id);
if (type == SSH2_FXP_STATUS) {
- int status = buffer_get_int(&msg);
-
+ status = buffer_get_int(&msg);
debug3("Received SSH2_FXP_STATUS %d", status);
-
- if (status == SSH2_FX_EOF) {
+ if (status == SSH2_FX_EOF)
break;
- } else {
- error("Couldn't read directory: %s",
- fx2txt(status));
- do_close(conn, handle, handle_len);
- free(handle);
- buffer_free(&msg);
- return(status);
- }
+ error("Couldn't read directory: %s", fx2txt(status));
+ goto out;
} else if (type != SSH2_FXP_NAME)
fatal("Expected SSH2_FXP_NAME(%u) packet, got %u",
SSH2_FXP_NAME, type);
@@ -547,10 +543,7 @@ do_lsreaddir(struct sftp_conn *conn, char *path, int print_flag,
if (strchr(filename, '/') != NULL) {
error("Server sent suspect path \"%s\" "
"during readdir of \"%s\"", filename, path);
- goto next;
- }
-
- if (dir) {
+ } else if (dir) {
*dir = xrealloc(*dir, ents + 2, sizeof(**dir));
(*dir)[ents] = xcalloc(1, sizeof(***dir));
(*dir)[ents]->filename = xstrdup(filename);
@@ -558,24 +551,29 @@ do_lsreaddir(struct sftp_conn *conn, char *path, int print_flag,
memcpy(&(*dir)[ents]->a, a, sizeof(*a));
(*dir)[++ents] = NULL;
}
- next:
free(filename);
free(longname);
}
}
+ status = 0;
+ out:
buffer_free(&msg);
do_close(conn, handle, handle_len);
free(handle);
- /* Don't return partial matches on interrupt */
- if (interrupted && dir != NULL && *dir != NULL) {
+ if (status != 0 && dir != NULL) {
+ /* Don't return results on error */
+ free_sftp_dirents(*dir);
+ *dir = NULL;
+ } else if (interrupted && dir != NULL && *dir != NULL) {
+ /* Don't return partial matches on interrupt */
free_sftp_dirents(*dir);
*dir = xcalloc(1, sizeof(**dir));
**dir = NULL;
}
- return 0;
+ return status;
}
int
@@ -588,6 +586,8 @@ void free_sftp_dirents(SFTP_DIRENT **s)
{
int i;
+ if (s == NULL)
+ return;
for (i = 0; s[i]; i++) {
free(s[i]->filename);
free(s[i]->longname);