summaryrefslogtreecommitdiff
path: root/sshbuf.c
diff options
context:
space:
mode:
Diffstat (limited to 'sshbuf.c')
-rw-r--r--sshbuf.c76
1 files changed, 43 insertions, 33 deletions
diff --git a/sshbuf.c b/sshbuf.c
index 91cbd067c..cbf7ed4a4 100644
--- a/sshbuf.c
+++ b/sshbuf.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: sshbuf.c,v 1.7 2016/09/12 01:22:38 deraadt Exp $ */ 1/* $OpenBSD: sshbuf.c,v 1.8 2016/11/25 23:22:04 djm Exp $ */
2/* 2/*
3 * Copyright (c) 2011 Damien Miller 3 * Copyright (c) 2011 Damien Miller
4 * 4 *
@@ -316,16 +316,13 @@ sshbuf_check_reserve(const struct sshbuf *buf, size_t len)
316} 316}
317 317
318int 318int
319sshbuf_reserve(struct sshbuf *buf, size_t len, u_char **dpp) 319sshbuf_allocate(struct sshbuf *buf, size_t len)
320{ 320{
321 size_t rlen, need; 321 size_t rlen, need;
322 u_char *dp; 322 u_char *dp;
323 int r; 323 int r;
324 324
325 if (dpp != NULL) 325 SSHBUF_DBG(("allocate buf = %p len = %zu", buf, len));
326 *dpp = NULL;
327
328 SSHBUF_DBG(("reserve buf = %p len = %zu", buf, len));
329 if ((r = sshbuf_check_reserve(buf, len)) != 0) 326 if ((r = sshbuf_check_reserve(buf, len)) != 0)
330 return r; 327 return r;
331 /* 328 /*
@@ -333,36 +330,49 @@ sshbuf_reserve(struct sshbuf *buf, size_t len, u_char **dpp)
333 * then pack the buffer, zeroing buf->off. 330 * then pack the buffer, zeroing buf->off.
334 */ 331 */
335 sshbuf_maybe_pack(buf, buf->size + len > buf->max_size); 332 sshbuf_maybe_pack(buf, buf->size + len > buf->max_size);
336 SSHBUF_TELL("reserve"); 333 SSHBUF_TELL("allocate");
337 if (len + buf->size > buf->alloc) { 334 if (len + buf->size <= buf->alloc)
338 /* 335 return 0; /* already have it. */
339 * Prefer to alloc in SSHBUF_SIZE_INC units, but 336
340 * allocate less if doing so would overflow max_size. 337 /*
341 */ 338 * Prefer to alloc in SSHBUF_SIZE_INC units, but
342 need = len + buf->size - buf->alloc; 339 * allocate less if doing so would overflow max_size.
343 rlen = ROUNDUP(buf->alloc + need, SSHBUF_SIZE_INC); 340 */
344 SSHBUF_DBG(("need %zu initial rlen %zu", need, rlen)); 341 need = len + buf->size - buf->alloc;
345 if (rlen > buf->max_size) 342 rlen = ROUNDUP(buf->alloc + need, SSHBUF_SIZE_INC);
346 rlen = buf->alloc + need; 343 SSHBUF_DBG(("need %zu initial rlen %zu", need, rlen));
347 SSHBUF_DBG(("adjusted rlen %zu", rlen)); 344 if (rlen > buf->max_size)
348 if ((dp = realloc(buf->d, rlen)) == NULL) { 345 rlen = buf->alloc + need;
349 SSHBUF_DBG(("realloc fail")); 346 SSHBUF_DBG(("adjusted rlen %zu", rlen));
350 if (dpp != NULL) 347 if ((dp = realloc(buf->d, rlen)) == NULL) {
351 *dpp = NULL; 348 SSHBUF_DBG(("realloc fail"));
352 return SSH_ERR_ALLOC_FAIL; 349 return SSH_ERR_ALLOC_FAIL;
353 } 350 }
354 buf->alloc = rlen; 351 buf->alloc = rlen;
355 buf->cd = buf->d = dp; 352 buf->cd = buf->d = dp;
356 if ((r = sshbuf_check_reserve(buf, len)) < 0) { 353 if ((r = sshbuf_check_reserve(buf, len)) < 0) {
357 /* shouldn't fail */ 354 /* shouldn't fail */
358 if (dpp != NULL) 355 return r;
359 *dpp = NULL;
360 return r;
361 }
362 } 356 }
357 SSHBUF_TELL("done");
358 return 0;
359}
360
361int
362sshbuf_reserve(struct sshbuf *buf, size_t len, u_char **dpp)
363{
364 u_char *dp;
365 int r;
366
367 if (dpp != NULL)
368 *dpp = NULL;
369
370 SSHBUF_DBG(("reserve buf = %p len = %zu", buf, len));
371 if ((r = sshbuf_allocate(buf, len)) != 0)
372 return r;
373
363 dp = buf->d + buf->size; 374 dp = buf->d + buf->size;
364 buf->size += len; 375 buf->size += len;
365 SSHBUF_TELL("done");
366 if (dpp != NULL) 376 if (dpp != NULL)
367 *dpp = dp; 377 *dpp = dp;
368 return 0; 378 return 0;