Skip to content

Commit faeb95b

Browse files
danielsndislogical
authored andcommitted
Add aws_byte_buf_reset() function (awslabs#342)
1 parent bd391e1 commit faeb95b

File tree

8 files changed

+129
-9
lines changed

8 files changed

+129
-9
lines changed
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License"). You may not use
4+
# this file except in compliance with the License. A copy of the License is
5+
# located at
6+
#
7+
# http://aws.amazon.com/apache2.0/
8+
#
9+
# or in the "license" file accompanying this file. This file is distributed on an
10+
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
11+
# implied. See the License for the specific language governing permissions and
12+
# limitations under the License.
13+
14+
###########
15+
include ../Makefile.aws_byte_buf
16+
UNWINDSET += memset_impl.0:$(shell echo $$(($(MAX_BUFFER_SIZE) + 1)))
17+
18+
CBMCFLAGS +=
19+
20+
DEPENDENCIES += $(HELPERDIR)/source/make_common_data_structures.c
21+
DEPENDENCIES += $(HELPERDIR)/source/proof_allocators.c
22+
DEPENDENCIES += $(HELPERDIR)/source/utils.c
23+
DEPENDENCIES += $(HELPERDIR)/stubs/error.c
24+
DEPENDENCIES += $(HELPERDIR)/stubs/memset_override.c
25+
DEPENDENCIES += $(SRCDIR)/source/byte_buf.c
26+
DEPENDENCIES += $(SRCDIR)/source/common.c
27+
28+
ENTRY = aws_byte_buf_reset_harness
29+
###########
30+
31+
include ../Makefile.common
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/*
2+
* Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License").
5+
* You may not use this file except in compliance with the License.
6+
* A copy of the License is located at
7+
*
8+
* http://aws.amazon.com/apache2.0
9+
*
10+
* or in the "license" file accompanying this file. This file is distributed
11+
* on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
12+
* express or implied. See the License for the specific language governing
13+
* permissions and limitations under the License.
14+
*/
15+
16+
#include <aws/common/byte_buf.h>
17+
#include <proof_helpers/make_common_data_structures.h>
18+
#include <proof_helpers/utils.h>
19+
20+
void aws_byte_buf_reset_harness() {
21+
struct aws_byte_buf buf;
22+
23+
__CPROVER_assume(aws_byte_buf_is_bounded(&buf, MAX_BUFFER_SIZE));
24+
ensure_byte_buf_has_allocated_buffer_member(&buf);
25+
__CPROVER_assume(aws_byte_buf_is_valid(&buf));
26+
27+
struct aws_byte_buf old = buf;
28+
bool zero_contents;
29+
aws_byte_buf_reset(&buf, zero_contents);
30+
assert(buf.len == 0);
31+
assert(buf.allocator == old.allocator);
32+
assert(buf.buffer == old.buffer);
33+
assert(buf.capacity == old.capacity);
34+
if (zero_contents) {
35+
assert_all_bytes_are(buf.buffer, 0, buf.capacity);
36+
}
37+
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
jobos: ubuntu16
2+
cbmcflags: "--bounds-check;--div-by-zero-check;--float-overflow-check;--nan-check;--pointer-check;--pointer-overflow-check;--signed-overflow-check;--undefined-shift-check;--unsigned-overflow-check;--unwind;1;--unwinding-assertions;--unwindset;memset_impl.0:11;--object-bits;8"
3+
goto: aws_byte_buf_reset_harness.goto
4+
expected: "SUCCESSFUL"

include/aws/common/byte_buf.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,13 @@ void aws_byte_buf_clean_up(struct aws_byte_buf *buf);
162162
AWS_COMMON_API
163163
void aws_byte_buf_clean_up_secure(struct aws_byte_buf *buf);
164164

165+
/**
166+
* Resets the len of the buffer to 0, but does not free the memory. The buffer can then be reused.
167+
* Optionally zeroes the contents, if the "zero_contents" flag is true.
168+
*/
169+
AWS_COMMON_API
170+
void aws_byte_buf_reset(struct aws_byte_buf *buf, bool zero_contents);
171+
165172
/**
166173
* Sets all bytes of buffer to zero and resets len to zero.
167174
*/

source/byte_buf.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,13 @@ bool aws_byte_cursor_is_valid(const struct aws_byte_cursor *cursor) {
7474
((cursor->len == 0) || (cursor->len > 0 && cursor->ptr && AWS_MEM_IS_WRITABLE(cursor->ptr, cursor->len)));
7575
}
7676

77+
void aws_byte_buf_reset(struct aws_byte_buf *buf, bool zero_contents) {
78+
if (zero_contents) {
79+
aws_byte_buf_secure_zero(buf);
80+
}
81+
buf->len = 0;
82+
}
83+
7784
void aws_byte_buf_clean_up(struct aws_byte_buf *buf) {
7885
AWS_PRECONDITION(aws_byte_buf_is_valid(buf));
7986
if (buf->allocator && buf->buffer) {

tests/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -221,6 +221,7 @@ add_test_case(test_byte_buf_append_lookup_success)
221221
add_test_case(test_byte_buf_append_lookup_failure)
222222
add_test_case(test_byte_buf_reserve)
223223
add_test_case(test_byte_buf_reserve_relative)
224+
add_test_case(test_byte_buf_reset)
224225
add_test_case(test_byte_cursor_compare_lexical)
225226
add_test_case(test_byte_cursor_compare_lookup)
226227

tests/byte_buf_test.c

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -591,6 +591,47 @@ static int s_test_byte_buf_append_lookup_success(struct aws_allocator *allocator
591591
}
592592
AWS_TEST_CASE(test_byte_buf_append_lookup_success, s_test_byte_buf_append_lookup_success)
593593

594+
static int s_test_reset_body(struct aws_byte_buf *buffer) {
595+
struct aws_byte_cursor to_lower_cursor = aws_byte_cursor_from_c_str((char *)s_to_lower_test->bytes);
596+
597+
ASSERT_TRUE(
598+
aws_byte_buf_append_with_lookup(buffer, &to_lower_cursor, aws_lookup_table_to_lower_get()) == AWS_OP_SUCCESS);
599+
ASSERT_TRUE(buffer->len == s_to_lower_test->len);
600+
for (size_t i = 0; i < s_to_lower_test->len; ++i) {
601+
uint8_t value = buffer->buffer[i];
602+
ASSERT_TRUE(value > 'Z' || value < 'A');
603+
}
604+
return 0;
605+
}
606+
static int s_test_byte_buf_reset(struct aws_allocator *allocator, void *ctx) {
607+
(void)ctx;
608+
609+
struct aws_byte_buf buffer;
610+
aws_byte_buf_init(&buffer, allocator, s_to_lower_test->len);
611+
ASSERT_SUCCESS(s_test_reset_body(&buffer));
612+
613+
size_t old_cap = buffer.capacity;
614+
aws_byte_buf_reset(&buffer, false);
615+
ASSERT_TRUE(buffer.len == 0);
616+
ASSERT_TRUE(buffer.capacity == old_cap);
617+
ASSERT_SUCCESS(s_test_reset_body(&buffer));
618+
619+
old_cap = buffer.capacity;
620+
aws_byte_buf_reset(&buffer, true);
621+
ASSERT_TRUE(buffer.len == 0);
622+
ASSERT_TRUE(buffer.capacity == old_cap);
623+
for (size_t i = 0; i < buffer.capacity; i++) {
624+
ASSERT_TRUE(buffer.buffer[i] == 0);
625+
}
626+
ASSERT_SUCCESS(s_test_reset_body(&buffer));
627+
628+
aws_byte_buf_clean_up(&buffer);
629+
/* check that reset succeeds even on an empty buffer */
630+
aws_byte_buf_reset(&buffer, true);
631+
return 0;
632+
}
633+
AWS_TEST_CASE(test_byte_buf_reset, s_test_byte_buf_reset)
634+
594635
static int s_test_byte_buf_append_lookup_failure(struct aws_allocator *allocator, void *ctx) {
595636
(void)ctx;
596637

tests/encoding_test.c

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,6 @@ static int s_run_hex_encoding_test_case(
4040
memset(allocation.buffer, 0xdd, allocation.capacity);
4141

4242
struct aws_byte_buf output = aws_byte_buf_from_empty_array(allocation.buffer + 1, output_size);
43-
output.len = 0;
4443

4544
ASSERT_SUCCESS(aws_hex_encode(&to_encode, &output), "encode call should have succeeded");
4645

@@ -69,12 +68,7 @@ static int s_run_hex_encoding_test_case(
6968
memset(allocation.buffer, 0xdd, allocation.capacity);
7069

7170
ASSERT_INT_EQUALS(test_str_size - 1, output_size, "Output size on string should be %d", test_str_size - 1);
72-
73-
output.capacity = output_size;
74-
if (output.capacity == 0) {
75-
output.buffer = NULL;
76-
}
77-
output.len = 0;
71+
aws_byte_buf_reset(&output, false);
7872

7973
struct aws_byte_cursor expected_buf = aws_byte_cursor_from_array(expected, expected_size - 1);
8074
ASSERT_SUCCESS(aws_hex_decode(&expected_buf, &output), "decode call should have succeeded");
@@ -314,7 +308,6 @@ static int s_run_base64_encoding_test_case(
314308
memset(allocation.buffer, 0xdd, allocation.capacity);
315309

316310
struct aws_byte_buf output = aws_byte_buf_from_empty_array(allocation.buffer + 1, output_size);
317-
output.len = 0;
318311

319312
ASSERT_SUCCESS(aws_base64_encode(&to_encode, &output), "encode call should have succeeded");
320313

@@ -349,7 +342,6 @@ static int s_run_base64_encoding_test_case(
349342
memset(allocation.buffer, 0xdd, allocation.capacity);
350343

351344
output = aws_byte_buf_from_empty_array(allocation.buffer + 1, output_size);
352-
output.len = 0;
353345

354346
struct aws_byte_cursor expected_buf = aws_byte_cursor_from_array(expected, expected_size - 1);
355347
ASSERT_SUCCESS(aws_base64_decode(&expected_buf, &output), "decode call should have succeeded");

0 commit comments

Comments
 (0)