From 7339bdb32d9b7b52298b340291d70b475a7be58c Mon Sep 17 00:00:00 2001 From: lntuition Date: Sun, 29 Sep 2019 19:34:22 +0900 Subject: [PATCH 1/2] Add testcase for int.from_bytes --- tests/snippets/ints.py | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/tests/snippets/ints.py b/tests/snippets/ints.py index 39923aba8..75a96e6d1 100644 --- a/tests/snippets/ints.py +++ b/tests/snippets/ints.py @@ -161,9 +161,20 @@ assert int.from_bytes(b'\xfc\x00', byteorder='big', signed=False) == 64512 assert int.from_bytes(bytes=b'\xfc\x00', byteorder='big', signed=True) == -1024 assert int.from_bytes(bytes=b'\xfc\x00', byteorder='big', signed=False) == 64512 +assert int.from_bytes([255, 0, 0], 'big') == 16711680 +assert int.from_bytes([255, 0, 0], 'little') == 255 +assert int.from_bytes([255, 0, 0], 'big', signed=False) == 16711680 +assert int.from_bytes([255, 0, 0], 'big', signed=True) == -65536 + with assert_raises(ValueError): int.from_bytes(b'\x00\x10', 'something') +with assert_raises(ValueError): + int.from_bytes([256, 0, 0], 'big') + +with assert_raises(TypeError): + int.from_bytes(['something', 0, 0], 'big') + assert (1024).to_bytes(4, 'big') == b'\x00\x00\x04\x00' assert (1024).to_bytes(2, 'little') == b'\x00\x04' assert (1024).to_bytes(4, byteorder='big') == b'\x00\x00\x04\x00' From c1d7723b521bc271511e70fb7ae076e3483e73af Mon Sep 17 00:00:00 2001 From: lntuition Date: Sun, 29 Sep 2019 19:35:26 +0900 Subject: [PATCH 2/2] Add logic to check array.array byte like object Add byte like list check function to objlist And check byte like object in objbyteinner After apply this patch, We can handle array.array byte like object Fixed: #1437 --- vm/src/obj/objbyteinner.rs | 2 ++ vm/src/obj/objlist.rs | 28 ++++++++++++++++++++++++++-- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/vm/src/obj/objbyteinner.rs b/vm/src/obj/objbyteinner.rs index fe69b4420..e402bed31 100644 --- a/vm/src/obj/objbyteinner.rs +++ b/vm/src/obj/objbyteinner.rs @@ -26,6 +26,7 @@ use num_traits::ToPrimitive; use super::objbytearray::PyByteArray; use super::objbytes::PyBytes; +use super::objlist::PyList; use super::objmemory::PyMemoryView; use super::objsequence; @@ -47,6 +48,7 @@ impl TryFromObject for PyByteInner { k @ PyMemoryView => Ok(PyByteInner { elements: k.get_obj_value().unwrap() }), + l @ PyList => l.get_byte_inner(vm), obj => Err(vm.new_type_error(format!( "a bytes-like object is required, not {}", obj.class() diff --git a/vm/src/obj/objlist.rs b/vm/src/obj/objlist.rs index caf174e46..abb9dd93f 100644 --- a/vm/src/obj/objlist.rs +++ b/vm/src/obj/objlist.rs @@ -9,12 +9,13 @@ use num_traits::{One, Signed, ToPrimitive, Zero}; use crate::function::OptionalArg; use crate::pyobject::{ IdProtocol, PyClassImpl, PyContext, PyIterable, PyObjectRef, PyRef, PyResult, PyValue, - TryFromObject, + TryFromObject, TypeProtocol, }; use crate::vm::{ReprGuard, VirtualMachine}; use super::objbool; -//use super::objint; +use super::objbyteinner; +use super::objint::PyIntRef; use super::objiter; use super::objsequence::{ get_elements_list, get_item, seq_equal, seq_ge, seq_gt, seq_le, seq_lt, seq_mul, SequenceIndex, @@ -96,6 +97,29 @@ impl PyList { start..stop } + + pub fn get_byte_inner(&self, vm: &VirtualMachine) -> PyResult { + let mut elements = Vec::::with_capacity(self.get_len()); + for elem in self.elements.borrow().iter() { + match PyIntRef::try_from_object(vm, elem.clone()) { + Ok(result) => match result.as_bigint().to_u8() { + Some(result) => elements.push(result), + None => { + return Err( + vm.new_value_error("bytes must be in range (0, 256)".to_string()) + ) + } + }, + _ => { + return Err(vm.new_type_error(format!( + "'{}' object cannot be interpreted as an integer", + elem.class().name + ))) + } + } + } + Ok(objbyteinner::PyByteInner { elements }) + } } #[derive(FromArgs)]