Skip to content

Commit 11d3f37

Browse files
committed
Add decode test for reserve capacity
There are new mutants in the reserve function for both VecDecoder and ByteVecDecoder. Add two new tests to check the functionality of reserve and kill the mutants.
1 parent 7c5a5a9 commit 11d3f37

File tree

1 file changed

+95
-0
lines changed

1 file changed

+95
-0
lines changed

consensus_encoding/src/decode/decoders.rs

Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1174,6 +1174,52 @@ mod tests {
11741174
decode_byte_vec_multi_byte_length_prefix, [0xff; 256], two_fifty_six_bytes_encoded();
11751175
}
11761176

1177+
#[test]
1178+
#[cfg(feature = "alloc")]
1179+
fn byte_vec_decoder_reserves_in_batches() {
1180+
// A small number of extra bytes so we extend exactly by the remainder
1181+
// instead of another full batch.
1182+
let tail_length: usize = 11;
1183+
1184+
let total_len = MAX_VECTOR_ALLOCATE + tail_length;
1185+
let total_len_le = u32::try_from(total_len).expect("total_len fits u32").to_le_bytes();
1186+
let mut decoder = ByteVecDecoder::new();
1187+
1188+
let mut prefix = vec![0xFE]; // total_len_le is a compact size of four bytes.
1189+
prefix.extend_from_slice(&total_len_le);
1190+
prefix.push(0xAA);
1191+
let mut prefix_slice = prefix.as_slice();
1192+
decoder.push_bytes(&mut prefix_slice).expect("length plus first element");
1193+
assert!(prefix_slice.is_empty());
1194+
1195+
assert_eq!(decoder.buffer.capacity(), MAX_VECTOR_ALLOCATE);
1196+
assert_eq!(decoder.buffer.len(), 1);
1197+
assert_eq!(decoder.buffer[0], 0xAA);
1198+
1199+
let fill = vec![0xBB; MAX_VECTOR_ALLOCATE - 1];
1200+
let mut fill_slice = fill.as_slice();
1201+
decoder.push_bytes(&mut fill_slice).expect("fills to batch boundary, full capacity");
1202+
assert!(fill_slice.is_empty());
1203+
1204+
assert_eq!(decoder.buffer.capacity(), MAX_VECTOR_ALLOCATE);
1205+
assert_eq!(decoder.buffer.len(), MAX_VECTOR_ALLOCATE);
1206+
assert_eq!(decoder.buffer[MAX_VECTOR_ALLOCATE - 1], 0xBB);
1207+
1208+
let mut tail = vec![0xCC];
1209+
tail.extend([0xDD].repeat(tail_length - 1));
1210+
let mut tail_slice = tail.as_slice();
1211+
decoder.push_bytes(&mut tail_slice).expect("fills the remaining bytes");
1212+
assert!(tail_slice.is_empty());
1213+
1214+
assert_eq!(decoder.buffer.capacity(), MAX_VECTOR_ALLOCATE + tail_length);
1215+
assert_eq!(decoder.buffer.len(), total_len);
1216+
assert_eq!(decoder.buffer[MAX_VECTOR_ALLOCATE], 0xCC);
1217+
1218+
let result = decoder.end().unwrap();
1219+
assert_eq!(result.len(), total_len);
1220+
assert_eq!(result[total_len - 1 ], 0xDD);
1221+
}
1222+
11771223
#[cfg(feature = "alloc")]
11781224
#[derive(Clone, Debug, PartialEq, Eq)]
11791225
pub struct Inner(u32);
@@ -1283,6 +1329,55 @@ mod tests {
12831329
assert_eq!(got, want);
12841330
}
12851331

1332+
#[test]
1333+
#[cfg(feature = "alloc")]
1334+
fn vec_decoder_reserves_in_batches() {
1335+
// A small number of extra elements so we extend exactly by the remainder
1336+
// instead of another full batch.
1337+
let tail_length: usize = 11;
1338+
1339+
let element_size = core::mem::size_of::<Inner>();
1340+
let batch_length = MAX_VECTOR_ALLOCATE / element_size;
1341+
assert!(batch_length > 1);
1342+
let total_len = batch_length + tail_length;
1343+
let total_len_le = u32::try_from(total_len).expect("total_len fits u32").to_le_bytes();
1344+
let mut decoder = Test::decoder();
1345+
1346+
let mut prefix = vec![0xFE]; // total_len_le is a compact size of four bytes.
1347+
prefix.extend_from_slice(&total_len_le);
1348+
prefix.extend_from_slice(&0xAA_u32.to_le_bytes());
1349+
let mut prefix_slice = prefix.as_slice();
1350+
decoder.push_bytes(&mut prefix_slice).expect("length plus first element");
1351+
assert!(prefix_slice.is_empty());
1352+
1353+
assert_eq!(decoder.0.buffer.capacity(), batch_length);
1354+
assert_eq!(decoder.0.buffer.len(), 1);
1355+
assert_eq!(decoder.0.buffer[0], Inner(0xAA));
1356+
1357+
let fill = 0xBB_u32.to_le_bytes().repeat(batch_length - 1);
1358+
let mut fill_slice = fill.as_slice();
1359+
decoder.push_bytes(&mut fill_slice).expect("fills to batch boundary, full capacity");
1360+
assert!(fill_slice.is_empty());
1361+
1362+
assert_eq!(decoder.0.buffer.capacity(), batch_length);
1363+
assert_eq!(decoder.0.buffer.len(), batch_length);
1364+
assert_eq!(decoder.0.buffer[batch_length - 1], Inner(0xBB));
1365+
1366+
let mut tail = 0xCC_u32.to_le_bytes().to_vec();
1367+
tail.extend(0xDD_u32.to_le_bytes().repeat(tail_length - 1));
1368+
let mut tail_slice = tail.as_slice();
1369+
decoder.push_bytes(&mut tail_slice).expect("fills the remaining bytes");
1370+
assert!(tail_slice.is_empty());
1371+
1372+
assert_eq!(decoder.0.buffer.capacity(), batch_length + tail_length);
1373+
assert_eq!(decoder.0.buffer.len(), total_len);
1374+
assert_eq!(decoder.0.buffer[batch_length], Inner(0xCC));
1375+
1376+
let Test(result) = decoder.end().unwrap();
1377+
assert_eq!(result.len(), total_len);
1378+
assert_eq!(result[total_len - 1 ], Inner(0xDD));
1379+
}
1380+
12861381
#[cfg(feature = "alloc")]
12871382
fn two_fifty_six_elements() -> Test {
12881383
Test(iter::repeat(Inner(0xDEAD_BEEF)).take(256).collect())

0 commit comments

Comments
 (0)