From c165c396de879b24f19c3a942a32795a8be351d7 Mon Sep 17 00:00:00 2001 From: Andreas Schneider Date: Thu, 23 Feb 2017 16:22:04 +0100 Subject: [PATCH] buffer: Create ssh_buffer_validate_length() This functions allows if a given length can be obtained from the buffer. Signed-off-by: Andreas Schneider --- include/libssh/buffer.h | 2 ++ src/buffer.c | 32 ++++++++++++++++++++++++++++---- 2 files changed, 30 insertions(+), 4 deletions(-) diff --git a/include/libssh/buffer.h b/include/libssh/buffer.h index d4cb071b..81d9452b 100644 --- a/include/libssh/buffer.h +++ b/include/libssh/buffer.h @@ -48,6 +48,8 @@ int ssh_buffer_add_u16(ssh_buffer buffer, uint16_t data); int ssh_buffer_add_u32(ssh_buffer buffer, uint32_t data); int ssh_buffer_add_u64(ssh_buffer buffer, uint64_t data); +int ssh_buffer_validate_length(struct ssh_buffer_struct *buffer, size_t len); + int ssh_buffer_pack_va(struct ssh_buffer_struct *buffer, const char *format, int argc, diff --git a/src/buffer.c b/src/buffer.c index 61b07e9a..db21b345 100644 --- a/src/buffer.c +++ b/src/buffer.c @@ -521,13 +521,17 @@ uint32_t ssh_buffer_pass_bytes_end(struct ssh_buffer_struct *buffer, uint32_t le * * @returns 0 if there is not enough data in buffer, len otherwise. */ -uint32_t ssh_buffer_get_data(struct ssh_buffer_struct *buffer, void *data, uint32_t len){ +uint32_t ssh_buffer_get_data(struct ssh_buffer_struct *buffer, void *data, uint32_t len) +{ + int rc; + /* * Check for a integer overflow first, then check if not enough data is in * the buffer. */ - if (buffer->pos + len < len || buffer->pos + len > buffer->used) { - return 0; + rc = ssh_buffer_validate_length(buffer, len); + if (rc != SSH_OK) { + return 0; } memcpy(data,buffer->data+buffer->pos,len); buffer->pos+=len; @@ -580,6 +584,24 @@ int ssh_buffer_get_u64(struct ssh_buffer_struct *buffer, uint64_t *data){ return ssh_buffer_get_data(buffer,data,sizeof(uint64_t)); } +/** + * @brief Valdiates that the given length can be obtained from the buffer. + * + * @param[in] buffer The buffer to read from. + * + * @param[in] len The length to be checked. + * + * @return SSH_OK if the length is valid, SSH_ERROR otherwise. + */ +int ssh_buffer_validate_length(struct ssh_buffer_struct *buffer, size_t len) +{ + if (buffer->pos + len < len || buffer->pos + len > buffer->used) { + return SSH_ERROR; + } + + return SSH_OK; +} + /** * @internal * @@ -593,13 +615,15 @@ struct ssh_string_struct *ssh_buffer_get_ssh_string(struct ssh_buffer_struct *bu uint32_t stringlen; uint32_t hostlen; struct ssh_string_struct *str = NULL; + int rc; if (ssh_buffer_get_u32(buffer, &stringlen) == 0) { return NULL; } hostlen = ntohl(stringlen); /* verify if there is enough space in buffer to get it */ - if (buffer->pos + hostlen < hostlen || buffer->pos + hostlen > buffer->used) { + rc = ssh_buffer_validate_length(buffer, hostlen); + if (rc != SSH_OK) { return NULL; /* it is indeed */ } str = ssh_string_new(hostlen);