diff --git a/CHANGELOG.md b/CHANGELOG.md index 520cf6d5..b8374485 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ Version 1.5.0 Bug fixes --------- +* Padding arrays with another array via `pad` no longer loops indefinitely. * `set_bit` for bit-flags with negative index now works correctly. * Misnamed `params` field `name` in the JSON output of `Engine::gen_fn_metadata_to_json` is fixed (was incorrectly named `type`). diff --git a/src/packages/array_basic.rs b/src/packages/array_basic.rs index 52b1e16c..857572ad 100644 --- a/src/packages/array_basic.rs +++ b/src/packages/array_basic.rs @@ -102,14 +102,30 @@ pub mod array_functions { let check_sizes = false; if check_sizes { - let arr = mem::take(array); - let mut arr = Dynamic::from_array(arr); + let mut arr_len = array.len(); + let mut arr = Dynamic::from_array(mem::take(array)); - while array.len() < len { - arr.write_lock::().unwrap().push(item.clone()); + #[cfg(not(feature = "unchecked"))] + let (mut a1, mut m1, mut s1) = Engine::calc_data_sizes(&arr, true); + #[cfg(not(feature = "unchecked"))] + let (a2, m2, s2) = Engine::calc_data_sizes(&item, true); - #[cfg(not(feature = "unchecked"))] - _ctx.engine().ensure_data_size_within_limits(&arr)?; + { + let mut guard = arr.write_lock::().unwrap(); + + while arr_len < len { + #[cfg(not(feature = "unchecked"))] + { + a1 += a2; + m1 += m2; + s1 += s2; + + _ctx.engine() + .raise_err_if_over_data_size_limit((a1, m1, s1), Position::NONE)?; + } + guard.push(item.clone()); + arr_len += 1; + } } *array = arr.into_array().unwrap(); diff --git a/tests/arrays.rs b/tests/arrays.rs index 096be4de..e0dc764d 100644 --- a/tests/arrays.rs +++ b/tests/arrays.rs @@ -22,6 +22,18 @@ fn test_arrays() -> Result<(), Box> { assert_eq!(engine.eval::("let y = [1, 2, 3]; y[-3]")?, 1); assert!(engine.eval::("let y = [1, 2, 3]; 2 in y")?); assert_eq!(engine.eval::("let y = [1, 2, 3]; y += 4; y[3]")?, 4); + assert_eq!( + engine.eval::("let y = [1, 2, 3]; pad(y, 5, 42); len(y)")?, + 5 + ); + assert_eq!( + engine.eval::("let y = [1, 2, 3]; pad(y, 5, [42]); len(y)")?, + 5 + ); + assert_eq!( + engine.eval::("let y = [1, 2, 3]; pad(y, 5, [42, 999, 123]); y[4][0]")?, + 42 + ); assert_eq!( engine .eval::("let y = [1, 2, 3]; y[1] += 4; y")?