Skip to content
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
cut down the number of errors by ~75% by porting changes over from re…
…factorings

Signed-off-by: Ashwin Naren <arihant2math@gmail.com>
  • Loading branch information
arihant2math committed Jan 23, 2025
commit 0fdd5a8c5ff9727aa92a159a5ee10257c6739806
56 changes: 20 additions & 36 deletions vm/src/stdlib/ctypes/array.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,28 +4,25 @@ use super::{
};
use crate::builtins::{
self,
memory::{try_buffer_from_object, Buffer},
slice::PySlice,
PyBytes, PyInt, PyList, PyRange, PyStr, PyType, PyTypeRef,
};
use crate::common::lock::{PyRwLock, PyRwLockReadGuard, PyRwLockWriteGuard};
use crate::function::OptionalArg;
use crate::pyobject::{
IdProtocol, ItemProtocol, PyIterable, PyObjectRef, PyRef, PyResult, PyValue, StaticType, TryFromObject,
TypeProtocol,
};
use crate::function::{Either, OptionalArg};
use crate::sliceable::SequenceIndex;
use crate::slots::BufferProtocol;
use crate::stdlib::ctypes::basics::{
default_from_param, generic_get_buffer, get_size, BorrowValue as BorrowValueCData,
BorrowValueMut, PyCData, PyCDataFunctions, PyCDataMethods, PyCDataSequenceMethods, RawBuffer,
};
use crate::utils::Either;
use crate::VirtualMachine;
use crate::{AsObject, Context, PyObjectRef, PyRef, PyResult, TryFromObject, VirtualMachine};
use rustpython_vm::object::PyPayload;
use num_traits::Signed;
use std::convert::TryInto;
use std::fmt;
use widestring::WideCString;
use crate::class::StaticType;
use crate::convert::IntoObject;
use crate::protocol::PyBuffer;

// TODO: make sure that this is correct wrt windows and unix wstr
fn slice_to_obj(ty: &str, b: &[u8], vm: &VirtualMachine) -> PyResult {
Expand Down Expand Up @@ -127,7 +124,7 @@ fn set_array_value(
}

if vm.isinstance(&obj, &self_cls)? {
let o_buffer = try_buffer_from_object(vm, &obj)?;
let o_buffer = PyBuffer::try_from_object(vm, &obj)?;
let src_buffer = o_buffer.obj_bytes();

assert!(dst_buffer.len() == size && src_buffer.len() >= size);
Expand Down Expand Up @@ -318,18 +315,6 @@ impl fmt::Debug for PyCArray {
}
}

impl PyValue for PyCArrayMeta {
fn class(_vm: &VirtualMachine) -> &PyTypeRef {
Self::static_type()
}
}

impl PyValue for PyCArray {
fn class(_vm: &VirtualMachine) -> &PyTypeRef {
Self::static_type()
}
}

impl<'a> BorrowValueCData<'a> for PyCArray {
fn borrow_value(&'a self) -> PyRwLockReadGuard<'a, RawBuffer> {
self._buffer.read()
Expand Down Expand Up @@ -407,7 +392,7 @@ impl PyCDataMethods for PyCArrayMeta {
}
}

#[pyimpl(with(PyCDataMethods), flags(BASETYPE))]
#[pyclass(with(PyCDataMethods), flags(BASETYPE))]
impl PyCArrayMeta {
#[pyslot]
fn tp_new(cls: PyTypeRef, vm: &VirtualMachine) -> PyResult {
Expand All @@ -433,7 +418,7 @@ impl PyCArrayMeta {
}
}

#[pyimpl(flags(BASETYPE), with(BufferProtocol, PyCDataFunctions))]
#[pyclass(flags(BASETYPE), with(BufferProtocol, PyCDataFunctions))]
impl PyCArray {
#[pymethod(magic)]
pub fn init(zelf: PyRef<Self>, value: OptionalArg, vm: &VirtualMachine) -> PyResult<()> {
Expand Down Expand Up @@ -463,11 +448,11 @@ impl PyCArray {
})
}

#[pyproperty]
#[pygetset(magic)]
pub fn value(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult {
// TODO: make sure that this is correct
let obj = zelf.as_object();
let buffer = try_buffer_from_object(vm, obj)?;
let buffer = PyBuffer::try_from_object(vm, &obj)?;

let res = if zelf._type_._type_ == "u" {
vm.new_pyobj(
Expand Down Expand Up @@ -519,10 +504,10 @@ impl PyCArray {
Ok(res)
}

#[pyproperty(setter)]
#[pygetset(magic, setter)]
fn set_value(zelf: PyRef<Self>, value: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
let obj = zelf.as_object();
let buffer = try_buffer_from_object(vm, obj)?;
let buffer = PyBuffer::try_from_object(vm, &obj)?;
let my_size = buffer.get_options().len;
let mut bytes = buffer.obj_bytes_mut();

Expand Down Expand Up @@ -582,24 +567,23 @@ impl PyCArray {
Ok(())
}

#[pyproperty]
#[pygetset(magic)]
fn raw(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyBytes> {
// zelf._type_ == "c"

let obj = zelf.as_object();
let buffer = try_buffer_from_object(vm, obj)?;
let buffer = PyBuffer::try_from_object(vm, obj)?;
let buffer_vec = buffer.obj_bytes().to_vec();

Ok(PyBytes::from(buffer_vec))
}

#[pyproperty(setter)]
#[pygetset(magic, setter)]
fn set_raw(zelf: PyRef<Self>, value: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
let obj = zelf.as_object();
let my_buffer = try_buffer_from_object(vm, obj)?;
let my_buffer = PyBuffer::try_from_object(vm, zelf)?;
let my_size = my_buffer.get_options().len;

let new_value = try_buffer_from_object(vm, &value)?;
let new_value = PyBuffer::try_from_object(vm, &value)?;
let new_size = new_value.get_options().len;

// byte string zelf._type_ == "c"
Expand All @@ -620,7 +604,7 @@ impl PyCArray {

#[pymethod(magic)]
fn getitem(zelf: PyRef<Self>, k_or_idx: SequenceIndex, vm: &VirtualMachine) -> PyResult {
let buffer = try_buffer_from_object(vm, zelf.as_object())?;
let buffer = PyBuffer::try_from_object(vm, zelf.as_object())?;
let buffer_size = buffer.get_options().len;
let buffer_bytes = buffer.obj_bytes();
let size = buffer_size / zelf._length_;
Expand Down Expand Up @@ -649,7 +633,7 @@ impl PyCArray {
obj: PyObjectRef,
vm: &VirtualMachine,
) -> PyResult<()> {
let buffer = try_buffer_from_object(vm, zelf.as_object())?;
let buffer = PyBuffer::try_from_object(vm, zelf.as_object())?;
let buffer_size = buffer.get_options().len;
let mut buffer_bytes = buffer.obj_bytes_mut();

Expand Down
69 changes: 32 additions & 37 deletions vm/src/stdlib/ctypes/basics.rs
Original file line number Diff line number Diff line change
@@ -1,43 +1,38 @@
use std::{fmt, mem, os::raw::*, ptr, slice};
use std::{fmt, os::raw::*, ptr, slice};

use widestring::WideChar;

use crate::builtins::int::PyInt;
use crate::builtins::memory::{try_buffer_from_object, Buffer, BufferOptions};
use crate::builtins::pystr::PyStrRef;
use crate::builtins::pytype::PyTypeRef;
use crate::common::borrow::{BorrowedValue, BorrowedValueMut};
use crate::common::lock::{PyRwLock, PyRwLockReadGuard, PyRwLockWriteGuard};
use crate::function::OptionalArg;
use crate::pyobject::{
PyObjectRef, PyRef, PyResult, PyValue, StaticType, TryFromObject, TypeProtocol,
};
use crate::slots::BufferProtocol;
use crate::utils::Either;
use crate::VirtualMachine;
use crate::{PyObjectRef, PyPayload, PyRef, PyResult, VirtualMachine};

use crate::stdlib::ctypes::array::make_array_with_length;
use crate::stdlib::ctypes::dll::dlsym;
use crate::stdlib::ctypes::primitive::{new_simple_type, PyCSimple};

use crate::builtins::PyTypeRef;
use crate::protocol::PyBuffer;
use crossbeam_utils::atomic::AtomicCell;

pub fn get_size(ty: &str) -> usize {
match ty {
"u" => mem::size_of::<WideChar>(),
"c" | "b" => mem::size_of::<c_schar>(),
"h" => mem::size_of::<c_short>(),
"H" => mem::size_of::<c_short>(),
"i" => mem::size_of::<c_int>(),
"I" => mem::size_of::<c_uint>(),
"l" => mem::size_of::<c_long>(),
"q" => mem::size_of::<c_longlong>(),
"L" => mem::size_of::<c_ulong>(),
"Q" => mem::size_of::<c_ulonglong>(),
"f" => mem::size_of::<c_float>(),
"d" | "g" => mem::size_of::<c_double>(),
"?" | "B" => mem::size_of::<c_uchar>(),
"P" | "z" | "Z" => mem::size_of::<usize>(),
"u" => size_of::<WideChar>(),
"c" | "b" => size_of::<c_schar>(),
"h" => size_of::<c_short>(),
"H" => size_of::<c_short>(),
"i" => size_of::<c_int>(),
"I" => size_of::<c_uint>(),
"l" => size_of::<c_long>(),
"q" => size_of::<c_longlong>(),
"L" => size_of::<c_ulong>(),
"Q" => size_of::<c_ulonglong>(),
"f" => size_of::<c_float>(),
"d" | "g" => size_of::<c_double>(),
"?" | "B" => size_of::<c_uchar>(),
"P" | "z" | "Z" => size_of::<usize>(),
_ => unreachable!(),
}
}
Expand Down Expand Up @@ -85,7 +80,7 @@ fn buffer_copy(
Ok(attr) => {
match bool::try_from_object(vm, attr) {
Ok(b) if !b => {
let buffer = try_buffer_from_object(vm, &obj)?;
let buffer = PyBuffer::try_from_object(vm, &obj)?;
let opts = buffer.get_options().clone();

// TODO: Fix the way the size of stored
Expand Down Expand Up @@ -145,7 +140,7 @@ fn buffer_copy(

pub fn default_from_param<T>(zelf: PyRef<T>, value: PyObjectRef, vm: &VirtualMachine) -> PyResult
where
T: PyCDataMethods + PyValue,
T: PyCDataMethods + PyPayload,
{
//TODO: check if this behaves like it should
let cls = zelf.as_object().clone_class();
Expand All @@ -161,8 +156,8 @@ where
)))
}
}
#[pyimpl]
pub trait PyCDataFunctions: PyValue {
#[pyclass]
pub trait PyCDataFunctions: PyPayload {
#[pymethod]
fn size_of_instances(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult<usize>;

Expand All @@ -175,8 +170,8 @@ pub trait PyCDataFunctions: PyValue {
#[pymethod]
fn address_of(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult;
}
#[pyimpl]
pub trait PyCDataMethods: PyValue {
#[pyclass]
pub trait PyCDataMethods: PyPayload {
// A lot of the logic goes in this trait
// There's also other traits that should have different implementations for some functions
// present here
Expand Down Expand Up @@ -253,8 +248,8 @@ pub trait PyCDataMethods: PyValue {
}
}

#[pyimpl]
pub trait PyCDataSequenceMethods: PyValue {
#[pyclass]
pub trait PyCDataSequenceMethods: PyPayload {
// CDataType_as_sequence methods are default for all *Type_Type
// Basically the sq_repeat slot is CDataType_repeat
// which transforms into a Array
Expand All @@ -276,7 +271,7 @@ pub trait PyCDataSequenceMethods: PyValue {

pub fn generic_get_buffer<T>(zelf: &PyRef<T>, vm: &VirtualMachine) -> PyResult<Box<dyn Buffer>>
where
for<'a> T: PyValue + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
for<'a> T: PyPayload + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
{
if let Ok(buffer) = vm.get_attribute(zelf.as_object().clone(), "_buffer") {
if let Ok(_buffer) = buffer.downcast_exact::<RawBuffer>(vm) {
Expand Down Expand Up @@ -325,7 +320,7 @@ impl BufferProtocol for PyCData {
// This trait will be used by all types
impl<T> Buffer for PyCBuffer<T>
where
for<'a> T: PyValue + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
for<'a> T: PyPayload + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
{
fn obj_bytes(&self) -> BorrowedValue<[u8]> {
PyRwLockReadGuard::map(self.data.borrow_value(), |x| unsafe {
Expand All @@ -351,7 +346,7 @@ where
#[derive(Debug)]
pub struct PyCBuffer<T>
where
for<'a> T: PyValue + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
for<'a> T: PyPayload + fmt::Debug + BorrowValue<'a> + BorrowValueMut<'a>,
{
pub data: PyRef<T>,
pub options: BufferOptions,
Expand All @@ -369,7 +364,7 @@ impl fmt::Debug for RawBuffer {
}
}

impl PyValue for RawBuffer {
impl PyPayload for RawBuffer {
fn class(vm: &VirtualMachine) -> &PyTypeRef {
&vm.ctx.types.object_type
}
Expand All @@ -393,7 +388,7 @@ impl fmt::Debug for PyCData {
}
}

impl PyValue for PyCData {
impl PyPayload for PyCData {
fn class(_vm: &VirtualMachine) -> &PyTypeRef {
Self::static_type()
}
Expand All @@ -411,7 +406,7 @@ impl PyCData {
}
}

#[pyimpl(flags(BASETYPE), with(BufferProtocol))]
#[pyclass(flags(BASETYPE), with(BufferProtocol))]
impl PyCData {
// PyCData_methods
#[pymethod(magic)]
Expand Down
1 change: 0 additions & 1 deletion vm/src/stdlib/ctypes/dll.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ pub(crate) use _ctypes::*;
pub(crate) mod _ctypes {
use crate::builtins::pystr::PyStrRef;
use crate::builtins::PyIntRef;
use crate::pyobject::{PyResult, TryFromObject};
use crate::VirtualMachine;

use super::super::shared_lib::libcache;
Expand Down
19 changes: 8 additions & 11 deletions vm/src/stdlib/ctypes/function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,16 +9,13 @@ use crate::builtins::{PyInt, PyTypeRef};
use crate::common::lock::PyRwLock;

use crate::function::FuncArgs;
use crate::pyobject::{
PyObjectRef, PyRef, PyResult, PyValue, StaticType, TryFromObject, TypeProtocol,
};
use crate::VirtualMachine;
use crate::{PyObjectRef, PyPayload, PyRef, PyResult, VirtualMachine};

use crate::stdlib::ctypes::basics::PyCData;
use crate::stdlib::ctypes::primitive::PyCSimple;

use crate::slots::Callable;
use crate::stdlib::ctypes::dll::dlsym;
use crate::types::Callable;

macro_rules! ffi_type {
($name: ident) => {
Expand Down Expand Up @@ -257,26 +254,26 @@ impl fmt::Debug for PyCFuncPtr {
}
}

impl PyValue for PyCFuncPtr {
impl PyPayload for PyCFuncPtr {
fn class(_vm: &VirtualMachine) -> &PyTypeRef {
Self::static_type()
}
}

#[pyimpl(with(Callable), flags(BASETYPE))]
#[pyclass(with(Callable), flags(BASETYPE))]
impl PyCFuncPtr {
#[pyproperty(name = "_argtypes_")]
#[pygetset(name = "_argtypes_")]
fn argtypes(&self, vm: &VirtualMachine) -> PyObjectRef {
vm.ctx
.new_list(unsafe { &*self._argtypes_.as_ptr() }.clone())
}

#[pyproperty(name = "_restype_")]
#[pygetset(name = "_restype_")]
fn restype(&self, _vm: &VirtualMachine) -> PyObjectRef {
unsafe { &*self._restype_.as_ptr() }.clone()
}

#[pyproperty(name = "_argtypes_", setter)]
#[pygetset(name = "_argtypes_", setter)]
fn set_argtypes(&self, argtypes: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
if vm
.isinstance(&argtypes, &vm.ctx.types.list_type)
Expand Down Expand Up @@ -322,7 +319,7 @@ impl PyCFuncPtr {
Ok(())
}

#[pyproperty(name = "_restype_", setter)]
#[pygetset(name = "_restype_", setter)]
fn set_restype(&self, restype: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
match vm.isinstance(&restype, PyCSimple::static_type()) {
// TODO: checks related to _type_ are temporary
Expand Down
Loading