fix bool tests

This commit is contained in:
Folkert 2020-09-30 21:49:33 +02:00
parent f3b317cab6
commit d46fb7bfb6
2 changed files with 96 additions and 19 deletions

View file

@ -19,7 +19,7 @@ mod gen_list {
#[test] #[test]
fn roc_list_construction() { fn roc_list_construction() {
let list = RocList::from_slice(&[true, false]); let list = RocList::from_slice(&vec![1i64; 23]);
assert_eq!(&list, &list); assert_eq!(&list, &list);
} }
@ -36,19 +36,93 @@ mod gen_list {
#[test] #[test]
fn int_list_literal() { fn int_list_literal() {
assert_evals_to!("[ 12, 9 ]", RocList::from_slice(&[12, 9]), RocList<i64>); assert_evals_to!("[ 12, 9 ]", RocList::from_slice(&[12, 9]), RocList<i64>);
assert_evals_to!(
"[ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 ]",
RocList::from_slice(&(vec![1i64; 23])),
RocList<i64>
);
} }
#[test] #[test]
fn bool_list_literal() { fn bool_list_literal() {
// NOTE: make sure to explicitly declare the elements to be of type bool, or
// use both True and False; only using one of them causes the list to in practice be
// of type `List [ True ]` or `List [ False ]`, those are tag unions with one constructor
// and not fields, and don't have a runtime representation.
assert_evals_to!(
indoc!(
r#"
false : Bool
false = False
[ false ]
"#
),
RocList::from_slice(&(vec![false; 1])),
RocList<bool>
);
assert_evals_to!( assert_evals_to!(
"[ True, False, True ]", "[ True, False, True ]",
RocList::from_slice(&[true, false, true]), RocList::from_slice(&[true, false, true]),
RocList<bool> RocList<bool>
); );
assert_evals_to!(
indoc!(
r#"
false : Bool
false = False
[false ]
"#
),
RocList::from_slice(&(vec![false; 1])),
RocList<bool>
);
assert_evals_to!(
indoc!(
r#"
true : Bool
true = True
List.repeat 23 true
"#
),
RocList::from_slice(&(vec![true; 23])),
RocList<bool>
);
assert_evals_to!(
indoc!(
r#"
true : Bool
true = True
List.repeat 23 { x: true, y: true }
"#
),
RocList::from_slice(&(vec![[true, true]; 23])),
RocList<[bool; 2]>
);
assert_evals_to!(
indoc!(
r#"
true : Bool
true = True
List.repeat 23 { x: true, y: true, a: true, b: true, c: true, d : true, e: true, f: true }
"#
),
RocList::from_slice(&(vec![[true, true, true, true, true, true, true, true]; 23])),
RocList<[bool; 8]>
);
} }
#[test] #[test]
fn various_list_literals() { fn variously_sized_list_literals() {
assert_evals_to!("[]", RocList::from_slice(&[]), RocList<i64>); assert_evals_to!("[]", RocList::from_slice(&[]), RocList<i64>);
assert_evals_to!("[1]", RocList::from_slice(&[1]), RocList<i64>); assert_evals_to!("[1]", RocList::from_slice(&[1]), RocList<i64>);
assert_evals_to!("[1, 2]", RocList::from_slice(&[1, 2]), RocList<i64>); assert_evals_to!("[1, 2]", RocList::from_slice(&[1, 2]), RocList<i64>);
@ -63,13 +137,6 @@ mod gen_list {
RocList::from_slice(&[1, 2, 3, 4, 5]), RocList::from_slice(&[1, 2, 3, 4, 5]),
RocList<i64> RocList<i64>
); );
/*
assert_evals_to!(
"[ True, False, True ]",
RocList::from_slice(&[true, false, true]),
RocList<bool>
);
*/
} }
#[test] #[test]

View file

@ -126,12 +126,18 @@ impl<T> RocList<T> {
let ptr = slice.as_ptr(); let ptr = slice.as_ptr();
let element_bytes = capacity * core::mem::size_of::<T>(); let element_bytes = capacity * core::mem::size_of::<T>();
let num_bytes = core::mem::size_of::<usize>() + element_bytes;
// we must round up to the nearest multiple of 16 let padding = {
// otherwise we get segfault / double free issues if core::mem::align_of::<T>() <= core::mem::align_of::<usize>() {
let padding = 16 - (num_bytes % 16); // aligned on usize (8 bytes on 64-bit systems)
let num_bytes = num_bytes + padding; 0
} else {
// aligned on 2*usize (16 bytes on 64-bit systems)
core::mem::size_of::<usize>()
}
};
let num_bytes = core::mem::size_of::<usize>() + padding + element_bytes;
let elements = unsafe { let elements = unsafe {
let raw_ptr = libc::malloc(num_bytes); let raw_ptr = libc::malloc(num_bytes);
@ -142,11 +148,15 @@ impl<T> RocList<T> {
let raw_ptr = Self::get_element_ptr(raw_ptr as *mut T); let raw_ptr = Self::get_element_ptr(raw_ptr as *mut T);
libc::memcpy( {
raw_ptr as *mut libc::c_void, // NOTE: using a memcpy here causes weird issues
ptr as *mut libc::c_void, let target_ptr = raw_ptr as *mut T;
num_bytes, let source_ptr = ptr as *const T;
); let length = slice.len() as isize;
for index in 0..length {
*target_ptr.offset(index) = *source_ptr.offset(index);
}
}
raw_ptr as *mut T raw_ptr as *mut T
}; };