PyObjectRef -> &PyObj, &PyRef<T> -> &Py<T>

This commit is contained in:
Noa
2021-10-18 16:01:17 -05:00
committed by Jeong YunWon
parent e5a1c3b137
commit 8dd18d97be
85 changed files with 3350 additions and 1716 deletions

View File

@@ -401,7 +401,7 @@ class ExtendModuleVisitor(EmitVisitor):
def visitModule(self, mod):
depth = 0
self.emit("pub fn extend_module_nodes(vm: &VirtualMachine, module: &PyObjectRef) {", depth)
self.emit("pub fn extend_module_nodes(vm: &VirtualMachine, module: &crate::PyObj) {", depth)
self.emit("extend_module!(vm, module, {", depth + 1)
for dfn in mod.dfns:
self.visit(dfn, depth + 2)

View File

@@ -76,7 +76,7 @@ pub fn impl_pymodule(attr: AttributeArgs, module_item: Item) -> Result<TokenStre
parse_quote! {
pub(crate) fn extend_module(
vm: &::rustpython_vm::VirtualMachine,
module: &::rustpython_vm::PyObjectRef,
module: &::rustpython_vm::PyObj,
) {
#module_extend_items
}

View File

@@ -88,7 +88,7 @@ impl<'vm> ShellHelper<'vm> {
} else {
// we need to get a variable based off of globals/builtins
let globals = str_iter_method(self.globals.as_object().clone(), "keys").ok()?;
let globals = str_iter_method(self.globals.as_object().incref(), "keys").ok()?;
let builtins = str_iter_method(self.vm.builtins.clone(), "__dir__").ok()?;
(first, globals, Some(builtins))
};

View File

@@ -28,8 +28,8 @@ mod array {
AsBuffer, AsMapping, Comparable, Constructor, IterNext, IterNextIterable, Iterable,
PyComparisonOp,
},
IdProtocol, PyComparisonValue, PyObjectRef, PyRef, PyResult, PyValue, TryFromObject,
TypeProtocol, VirtualMachine,
IdProtocol, Py, PyComparisonValue, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TryFromObject, TypeProtocol, VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
use itertools::Itertools;
@@ -1111,7 +1111,7 @@ mod array {
let iter = Iterator::zip(array_a.iter(vm), array_b.iter(vm));
for (a, b) in iter {
if !vm.bool_eq(&a?, &b?)? {
if !vm.bool_eq(&*a?, &*b?)? {
return Ok(false);
}
}
@@ -1167,8 +1167,8 @@ mod array {
impl Comparable for PyArray {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -1195,8 +1195,12 @@ mod array {
for (a, b) in iter {
let ret = match op {
PyComparisonOp::Lt | PyComparisonOp::Le => vm.bool_seq_lt(&a?, &b?)?,
PyComparisonOp::Gt | PyComparisonOp::Ge => vm.bool_seq_gt(&a?, &b?)?,
PyComparisonOp::Lt | PyComparisonOp::Le => {
vm.bool_seq_lt(&*a?, &*b?)?
}
PyComparisonOp::Gt | PyComparisonOp::Ge => {
vm.bool_seq_gt(&*a?, &*b?)?
}
_ => unreachable!(),
};
if let Some(v) = ret {
@@ -1214,11 +1218,11 @@ mod array {
}
impl AsBuffer for PyArray {
fn as_buffer(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
fn as_buffer(zelf: &Py<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
let array = zelf.read();
let buf = PyBuffer::new(
zelf.as_object().clone(),
PyArrayBufferInternal(zelf.clone()),
zelf.as_object().incref(),
PyArrayBufferInternal(zelf.incref()),
BufferOptions {
readonly: false,
len: array.len(),
@@ -1253,7 +1257,7 @@ mod array {
}
impl AsMapping for PyArray {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -1322,7 +1326,7 @@ mod array {
impl IterNextIterable for PyArrayIter {}
impl IterNext for PyArrayIter {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let pos = zelf.position.fetch_add(1);
let r = if let Some(item) = zelf.array.read().getitem_by_idx(pos, vm)? {
PyIterReturn::Return(item)

View File

@@ -105,7 +105,7 @@ mod _bisect {
while lo < hi {
// Handles issue 13496.
let mid = (lo + hi) / 2;
if x.rich_compare_bool(&a.get_item(mid, vm)?, Lt, vm)? {
if x.rich_compare_bool(&*a.get_item(mid, vm)?, Lt, vm)? {
hi = mid;
} else {
lo = mid + 1;

View File

@@ -16,7 +16,7 @@ mod _csv {
match_class,
protocol::{PyIter, PyIterReturn},
types::{IterNext, IterNextIterable},
PyObjectRef, PyRef, PyResult, PyValue, TryFromObject, TypeProtocol, VirtualMachine,
Py, PyObjectRef, PyResult, PyValue, TryFromObject, TypeProtocol, VirtualMachine,
};
use itertools::{self, Itertools};
use std::fmt;
@@ -172,7 +172,7 @@ mod _csv {
impl Reader {}
impl IterNextIterable for Reader {}
impl IterNext for Reader {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let string = match zelf.iter.next(vm)? {
PyIterReturn::Return(obj) => obj,
PyIterReturn::StopIteration(v) => return Ok(PyIterReturn::StopIteration(v)),

View File

@@ -9,7 +9,7 @@ mod _json {
function::{IntoPyObject, IntoPyResult, OptionalArg},
protocol::PyIterReturn,
types::{Callable, Constructor},
IdProtocol, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
IdProtocol, Py, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
use num_bigint::BigInt;
use std::str::FromStr;
@@ -195,7 +195,7 @@ mod _json {
impl Callable for JsonScanner {
type Args = (PyStrRef, isize);
fn call(zelf: &PyRef<Self>, (pystr, idx): Self::Args, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &Py<Self>, (pystr, idx): Self::Args, vm: &VirtualMachine) -> PyResult {
if idx < 0 {
return Err(vm.new_value_error("idx cannot be negative".to_owned()));
}
@@ -204,7 +204,7 @@ mod _json {
if idx > 0 && chars.nth(idx - 1).is_none() {
PyIterReturn::StopIteration(Some(vm.ctx.new_int(idx).into())).into_pyresult(vm)
} else {
zelf.parse(chars.as_str(), pystr.clone(), idx, zelf.clone().into(), vm)
zelf.parse(chars.as_str(), pystr.clone(), idx, zelf.incref().into(), vm)
.and_then(|x| x.into_pyresult(vm))
}
}

View File

@@ -6,7 +6,7 @@ mod math {
builtins::{try_bigint_to_f64, try_f64_to_bigint, PyFloat, PyInt, PyIntRef},
function::{ArgIntoFloat, ArgIterable, OptionalArg, PosArgs},
utils::Either,
PyObjectRef, PyRef, PyResult, PySequence, TypeProtocol, VirtualMachine,
PyObj, PyObjectRef, PyRef, PyResult, PySequence, TypeProtocol, VirtualMachine,
};
use num_bigint::BigInt;
use num_traits::{One, Signed, Zero};
@@ -408,8 +408,8 @@ mod math {
}
}
fn try_magic_method(func_name: &str, vm: &VirtualMachine, value: &PyObjectRef) -> PyResult {
let method = vm.get_method_or_type_error(value.clone(), func_name, || {
fn try_magic_method(func_name: &str, vm: &VirtualMachine, value: &PyObj) -> PyResult {
let method = vm.get_method_or_type_error(value.incref(), func_name, || {
format!(
"type '{}' doesn't define '{}' method",
value.class().name(),

View File

@@ -5,7 +5,7 @@ mod resource {
use crate::vm::{
function::{IntoPyException, IntoPyObject},
stdlib::os,
PyObjectRef, PyResult, PyStructSequence, TryFromBorrowedObject, VirtualMachine,
PyObj, PyObjectRef, PyResult, PyStructSequence, TryFromBorrowedObject, VirtualMachine,
};
use std::{io, mem};
@@ -113,7 +113,7 @@ mod resource {
struct Limits(libc::rlimit);
impl TryFromBorrowedObject for Limits {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
let seq = vm.extract_elements::<libc::rlim_t>(obj)?;
match *seq {
[cur, max] => Ok(Self(libc::rlimit {

View File

@@ -802,7 +802,7 @@ mod _ssl {
stream: PyRwLock::new(stream),
socket_type,
server_hostname: args.server_hostname,
owner: PyRwLock::new(args.owner.as_ref().map(PyWeak::downgrade)),
owner: PyRwLock::new(args.owner.as_ref().map(|o| PyWeak::downgrade(o))),
})
}
}

View File

@@ -259,7 +259,7 @@ impl PyAsyncGenASend {
impl IterNextIterable for PyAsyncGenASend {}
impl IterNext for PyAsyncGenASend {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
PyIterReturn::from_pyresult(zelf.send(vm.ctx.none(), vm), vm)
}
}
@@ -405,7 +405,7 @@ impl PyAsyncGenAThrow {
impl IterNextIterable for PyAsyncGenAThrow {}
impl IterNext for PyAsyncGenAThrow {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
PyIterReturn::from_pyresult(zelf.send(vm.ctx.none(), vm), vm)
}
}

View File

@@ -96,7 +96,7 @@ impl PyBuiltinFunction {
impl Callable for PyBuiltinFunction {
type Args = FuncArgs;
#[inline]
fn call(zelf: &PyRef<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
(zelf.value.func)(vm, args)
}
}
@@ -193,7 +193,7 @@ impl GetDescriptor for PyBuiltinMethod {
impl Callable for PyBuiltinMethod {
type Args = FuncArgs;
#[inline]
fn call(zelf: &PyRef<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
(zelf.value.func)(vm, args)
}
}

View File

@@ -28,7 +28,7 @@ use crate::{
IterNextIterable, Iterable, PyComparisonOp, Unconstructible, Unhashable,
},
utils::Either,
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef,
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef,
PyResult, PyValue, TypeProtocol, VirtualMachine,
};
use bstr::ByteSlice;
@@ -290,7 +290,7 @@ impl PyByteArray {
}
}
fn irepeat(zelf: &PyRef<Self>, n: usize, vm: &VirtualMachine) -> PyResult<()> {
fn irepeat(zelf: &crate::Py<Self>, n: usize, vm: &VirtualMachine) -> PyResult<()> {
if n == 1 {
return Ok(());
}
@@ -696,8 +696,8 @@ impl PyByteArray {
impl Comparable for PyByteArray {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -709,10 +709,10 @@ impl Comparable for PyByteArray {
}
impl AsBuffer for PyByteArray {
fn as_buffer(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
fn as_buffer(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
let buffer = PyBuffer::new(
zelf.as_object().clone(),
zelf.clone(),
zelf.as_object().incref(),
zelf.incref(),
BufferOptions {
readonly: false,
len: zelf.len(),
@@ -756,7 +756,7 @@ impl<'a> BufferResizeGuard<'a> for PyByteArray {
}
impl AsMapping for PyByteArray {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -801,7 +801,7 @@ impl Iterable for PyByteArray {
}
}
// fn set_value(obj: &PyObjectRef, value: Vec<u8>) {
// fn set_value(obj: &crate::PyObj, value: Vec<u8>) {
// obj.borrow_mut().kind = PyObjectPayload::Bytes { value };
// }
@@ -841,7 +841,7 @@ impl Unconstructible for PyByteArrayIterator {}
impl IterNextIterable for PyByteArrayIterator {}
impl IterNext for PyByteArrayIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|bytearray, pos| {
let buf = bytearray.borrow_buf();
Ok(match buf.get(pos) {

View File

@@ -16,8 +16,8 @@ use crate::{
IterNextIterable, Iterable, PyComparisonOp, Unconstructible,
},
utils::Either,
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue,
TryFromBorrowedObject, TypeProtocol, VirtualMachine,
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef, PyResult,
PyValue, TryFromBorrowedObject, TypeProtocol, VirtualMachine,
};
use bstr::ByteSlice;
use rustpython_common::{
@@ -542,10 +542,10 @@ impl PyBytes {
}
impl AsBuffer for PyBytes {
fn as_buffer(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
fn as_buffer(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyBuffer> {
let buf = PyBuffer::new(
zelf.as_object().clone(),
zelf.clone(),
zelf.as_object().incref(),
zelf.incref(),
BufferOptions {
len: zelf.len(),
..Default::default()
@@ -569,7 +569,7 @@ impl BufferInternal for PyRef<PyBytes> {
}
impl AsMapping for PyBytes {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -600,15 +600,15 @@ impl AsMapping for PyBytes {
impl Hashable for PyBytes {
#[inline]
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
Ok(zelf.inner.hash(vm))
}
}
impl Comparable for PyBytes {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -676,7 +676,7 @@ impl Unconstructible for PyBytesIterator {}
impl IterNextIterable for PyBytesIterator {}
impl IterNext for PyBytesIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|bytes, pos| {
Ok(match bytes.as_bytes().get(pos) {
Some(&x) => PyIterReturn::Return(vm.ctx.new_int(x).into()),
@@ -687,7 +687,7 @@ impl IterNext for PyBytesIterator {
}
impl TryFromBorrowedObject for PyBytes {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
PyBytesInner::try_from_borrowed_object(vm, obj).map(|x| x.into())
}
}

View File

@@ -28,7 +28,7 @@ pub struct PyConstant(pub PyObjectRef);
// Ellipsis(PyObjectRef),
// }
fn borrow_obj_constant(obj: &PyObjectRef) -> BorrowedConstant<PyConstant> {
fn borrow_obj_constant(obj: &crate::PyObj) -> BorrowedConstant<PyConstant> {
match_class!(match obj {
ref i @ super::int::PyInt => {
let value = i.as_bigint();
@@ -53,7 +53,7 @@ fn borrow_obj_constant(obj: &PyObjectRef) -> BorrowedConstant<PyConstant> {
}
ref t @ super::tuple::PyTuple => {
BorrowedConstant::Tuple {
elements: Box::new(t.as_slice().iter().map(borrow_obj_constant)),
elements: Box::new(t.as_slice().iter().map(|o| borrow_obj_constant(o))),
}
}
super::singletons::PyNone => BorrowedConstant::None,

View File

@@ -4,8 +4,8 @@ use crate::{
types::{Comparable, Constructor, Hashable, PyComparisonOp},
IdProtocol,
PyArithmeticValue::{self, *},
PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol,
VirtualMachine,
PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TypeProtocol, VirtualMachine,
};
use num_complex::Complex64;
use num_traits::Zero;
@@ -73,7 +73,7 @@ pub fn init(context: &PyContext) {
PyComplex::extend_class(context, &context.types.complex_type);
}
fn to_op_complex(value: &PyObjectRef, vm: &VirtualMachine) -> PyResult<Option<Complex64>> {
fn to_op_complex(value: &crate::PyObj, vm: &VirtualMachine) -> PyResult<Option<Complex64>> {
let r = if let Some(complex) = value.payload_if_subclass::<PyComplex>(vm) {
Some(complex.value)
} else {
@@ -409,8 +409,8 @@ impl PyComplex {
impl Comparable for PyComplex {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -431,7 +431,7 @@ impl Comparable for PyComplex {
impl Hashable for PyComplex {
#[inline]
fn hash(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
fn hash(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
Ok(hash::hash_complex(&zelf.value))
}
}

View File

@@ -107,8 +107,8 @@ impl Unconstructible for PyCoroutine {}
impl IterNextIterable for PyCoroutine {}
impl IterNext for PyCoroutine {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.clone(), vm.ctx.none(), vm)
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.incref(), vm.ctx.none(), vm)
}
}
@@ -146,8 +146,8 @@ impl PyCoroutineWrapper {
impl IterNextIterable for PyCoroutineWrapper {}
impl IterNext for PyCoroutineWrapper {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.clone(), vm.ctx.none(), vm)
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.incref(), vm.ctx.none(), vm)
}
}

View File

@@ -15,7 +15,7 @@ use crate::{
vm::{ReprGuard, VirtualMachine},
IdProtocol, ItemProtocol,
PyArithmeticValue::*,
PyAttributes, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef,
PyAttributes, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef,
PyResult, PyValue, TypeProtocol,
};
use rustpython_common::lock::PyMutex;
@@ -159,8 +159,8 @@ impl PyDict {
}
fn inner_cmp(
zelf: &PyRef<Self>,
other: &PyDictRef,
zelf: &crate::Py<Self>,
other: &crate::Py<PyDict>,
op: PyComparisonOp,
item: bool,
vm: &VirtualMachine,
@@ -262,7 +262,7 @@ impl PyDict {
/// Set item variant which can be called with multiple
/// key types, such as str to name a notable one.
fn inner_setitem_fast<K: DictKey>(
fn inner_setitem_fast<K: DictKey + IntoPyObject>(
&self,
key: K,
value: PyObjectRef,
@@ -416,7 +416,7 @@ impl PyDict {
}
impl AsMapping for PyDict {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -450,8 +450,8 @@ impl AsMapping for PyDict {
impl Comparable for PyDict {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -470,7 +470,7 @@ impl Iterable for PyDict {
}
}
impl PyDictRef {
impl crate::Py<PyDict> {
#[inline]
fn exact_dict(&self, vm: &VirtualMachine) -> bool {
self.class().is(&vm.ctx.types.dict_type)
@@ -478,7 +478,7 @@ impl PyDictRef {
/// Return an optional inner item, or an error (can be key error as well)
#[inline]
fn inner_getitem_option<K: DictKey>(
fn inner_getitem_option<K: DictKey + IntoPyObject>(
&self,
key: K,
exact: bool,
@@ -489,7 +489,7 @@ impl PyDictRef {
}
if !exact {
if let Some(method_or_err) = vm.get_method(self.clone().into(), "__missing__") {
if let Some(method_or_err) = vm.get_method(self.incref().into(), "__missing__") {
let method = method_or_err?;
return vm.invoke(&method, (key,)).map(Some);
}
@@ -498,7 +498,7 @@ impl PyDictRef {
}
/// Take a python dictionary and convert it to attributes.
pub fn to_attributes(self) -> PyAttributes {
pub fn to_attributes(&self) -> PyAttributes {
let mut attrs = PyAttributes::default();
for (key, value) in self {
let key: PyStrRef = key.downcast().expect("dict has non-string keys");
@@ -572,9 +572,9 @@ impl PyDictRef {
}
}
impl<K> ItemProtocol<K> for PyDictRef
impl<K> ItemProtocol<K> for crate::Py<PyDict>
where
K: DictKey,
K: DictKey + IntoPyObject,
{
fn get_item(&self, key: K, vm: &VirtualMachine) -> PyResult {
self.as_object().get_item(key, vm)
@@ -599,6 +599,23 @@ where
}
}
impl<K> ItemProtocol<K> for PyDictRef
where
K: DictKey + IntoPyObject,
{
fn get_item(&self, key: K, vm: &VirtualMachine) -> PyResult {
(**self).get_item(key, vm)
}
fn set_item(&self, key: K, value: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
(**self).set_item(key, value, vm)
}
fn del_item(&self, key: K, vm: &VirtualMachine) -> PyResult<()> {
(**self).del_item(key, vm)
}
}
// Implement IntoIterator so that we can easily iterate dictionaries from rust code.
impl IntoIterator for PyDictRef {
type Item = (PyObjectRef, PyObjectRef);
@@ -618,6 +635,15 @@ impl IntoIterator for &PyDictRef {
}
}
impl IntoIterator for &crate::Py<PyDict> {
type Item = (PyObjectRef, PyObjectRef);
type IntoIter = DictIter;
fn into_iter(self) -> Self::IntoIter {
DictIter::new(self.incref())
}
}
pub struct DictIter {
dict: PyDictRef,
position: usize,
@@ -717,8 +743,8 @@ macro_rules! dict_view {
impl Comparable for $name {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -781,7 +807,7 @@ macro_rules! dict_view {
impl IterNextIterable for $iter_name {}
impl IterNext for $iter_name {
#[allow(clippy::redundant_closure_call)]
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut internal = zelf.internal.lock();
if let IterStatus::Active(dict) = &internal.status {
if dict.entries.has_changed_size(&zelf.size) {
@@ -842,7 +868,7 @@ macro_rules! dict_view {
impl IterNextIterable for $reverse_iter_name {}
impl IterNext for $reverse_iter_name {
#[allow(clippy::redundant_closure_call)]
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut internal = zelf.internal.lock();
if let IterStatus::Active(dict) = &internal.status {
if dict.entries.has_changed_size(&zelf.size) {

View File

@@ -4,7 +4,7 @@ use crate::{
function::{IntoPyObject, OptionalArg},
protocol::{PyIter, PyIterReturn},
types::{Constructor, IterNext, IterNextIterable},
ItemProtocol, PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
ItemProtocol, PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
use num_bigint::BigInt;
use num_traits::Zero;
@@ -51,7 +51,7 @@ impl PyEnumerate {}
impl IterNextIterable for PyEnumerate {}
impl IterNext for PyEnumerate {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let next_obj = match zelf.iterator.next(vm)? {
PyIterReturn::StopIteration(v) => return Ok(PyIterReturn::StopIteration(v)),
PyIterReturn::Return(obj) => obj,
@@ -110,7 +110,7 @@ impl PyReverseSequenceIterator {
impl IterNextIterable for PyReverseSequenceIterator {}
impl IterNext for PyReverseSequenceIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal
.lock()
.rev_next(|obj, pos| PyIterReturn::from_getitem_result(obj.get_item(pos, vm), vm))

View File

@@ -2,7 +2,7 @@ use super::PyTypeRef;
use crate::{
protocol::{PyIter, PyIterReturn},
types::{Constructor, IterNext, IterNextIterable},
PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
/// filter(function or None, iterable) --> filter object
@@ -39,7 +39,7 @@ impl PyFilter {}
impl IterNextIterable for PyFilter {}
impl IterNext for PyFilter {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let predicate = &zelf.predicate;
loop {
let next_obj = match zelf.iterator.next(vm)? {

View File

@@ -6,7 +6,7 @@ use crate::{
types::{Comparable, Constructor, Hashable, PyComparisonOp},
IdProtocol,
PyArithmeticValue::{self, *},
PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue,
PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TryFromObject, TypeProtocol, VirtualMachine,
};
use num_bigint::{BigInt, ToBigInt};
@@ -50,12 +50,12 @@ impl From<f64> for PyFloat {
}
}
impl PyObjectRef {
impl PyObj {
pub fn try_to_f64(&self, vm: &VirtualMachine) -> PyResult<Option<f64>> {
if let Some(float) = self.payload_if_exact::<PyFloat>(vm) {
return Ok(Some(float.value));
}
if let Some(method) = vm.get_method(self.clone(), "__float__") {
if let Some(method) = vm.get_method(self.incref(), "__float__") {
let result = vm.invoke(&method?, ())?;
// TODO: returning strict subclasses of float in __float__ is deprecated
return match result.payload::<PyFloat>() {
@@ -66,20 +66,20 @@ impl PyObjectRef {
))),
};
}
if let Some(r) = vm.to_index_opt(self.clone()).transpose()? {
if let Some(r) = vm.to_index_opt(self.incref()).transpose()? {
return Ok(Some(try_bigint_to_f64(r.as_bigint(), vm)?));
}
Ok(None)
}
}
pub fn try_float(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<f64> {
pub fn try_float(obj: &crate::PyObj, vm: &VirtualMachine) -> PyResult<f64> {
obj.try_to_f64(vm)?.ok_or_else(|| {
vm.new_type_error(format!("must be real number, not {}", obj.class().name()))
})
}
pub(crate) fn to_op_float(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<Option<f64>> {
pub(crate) fn to_op_float(obj: &PyObj, vm: &VirtualMachine) -> PyResult<Option<f64>> {
let v = if let Some(float) = obj.payload_if_subclass::<PyFloat>(vm) {
Some(float.value)
} else if let Some(int) = obj.payload_if_subclass::<PyInt>(vm) {
@@ -493,8 +493,8 @@ impl PyFloat {
impl Comparable for PyFloat {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -534,13 +534,13 @@ impl Comparable for PyFloat {
impl Hashable for PyFloat {
#[inline]
fn hash(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
fn hash(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
Ok(hash::hash_float(zelf.to_f64()))
}
}
// Retrieve inner float value:
pub(crate) fn get_value(obj: &PyObjectRef) -> f64 {
pub(crate) fn get_value(obj: &crate::PyObj) -> f64 {
obj.payload::<PyFloat>().unwrap().value
}

View File

@@ -13,7 +13,7 @@ use crate::{
protocol::PyMapping,
scope::Scope,
types::{Callable, Comparable, Constructor, GetAttr, GetDescriptor, PyComparisonOp},
IdProtocol, ItemProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef,
IdProtocol, ItemProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef,
PyResult, PyValue, TypeProtocol, VirtualMachine,
};
#[cfg(feature = "jit")]
@@ -379,7 +379,7 @@ impl PyFunction {
fn repr(zelf: PyRef<Self>, vm: &VirtualMachine) -> String {
let qualname = zelf
.as_object()
.clone()
.incref()
.get_attr("__qualname__", vm)
.ok()
.and_then(|qualname_attr| qualname_attr.downcast::<PyStr>().ok())
@@ -422,7 +422,7 @@ impl GetDescriptor for PyFunction {
impl Callable for PyFunction {
type Args = FuncArgs;
#[inline]
fn call(zelf: &PyRef<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
zelf.invoke(args, vm)
}
}
@@ -437,7 +437,7 @@ pub struct PyBoundMethod {
impl Callable for PyBoundMethod {
type Args = FuncArgs;
#[inline]
fn call(zelf: &PyRef<Self>, mut args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, mut args: FuncArgs, vm: &VirtualMachine) -> PyResult {
args.prepend_arg(zelf.object.clone());
vm.invoke(&zelf.function, args)
}
@@ -445,8 +445,8 @@ impl Callable for PyBoundMethod {
impl Comparable for PyBoundMethod {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
_vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {

View File

@@ -2,8 +2,7 @@ use crate::{
builtins::{float, int, pybool, PyBaseExceptionRef, PyDictRef, PyFunction, PyStrRef},
bytecode::CodeFlags,
function::{FuncArgs, IntoPyObject},
IdProtocol, ItemProtocol, PyObjectRef, PyRef, PyResult, TryFromObject, TypeProtocol,
VirtualMachine,
IdProtocol, ItemProtocol, PyObjectRef, PyResult, TryFromObject, TypeProtocol, VirtualMachine,
};
use num_traits::ToPrimitive;
use rustpython_jit::{AbiValue, Args, CompiledCode, JitArgumentError, JitType};
@@ -63,7 +62,10 @@ fn get_jit_arg_type(dict: &PyDictRef, name: &str, vm: &VirtualMachine) -> PyResu
}
}
pub fn get_jit_arg_types(func: &PyRef<PyFunction>, vm: &VirtualMachine) -> PyResult<Vec<JitType>> {
pub fn get_jit_arg_types(
func: &crate::Py<PyFunction>,
vm: &VirtualMachine,
) -> PyResult<Vec<JitType>> {
let arg_names = func.code.arg_names();
if func
@@ -81,7 +83,7 @@ pub fn get_jit_arg_types(func: &PyRef<PyFunction>, vm: &VirtualMachine) -> PyRes
return Ok(Vec::new());
}
let func_obj: PyObjectRef = func.clone().into();
let func_obj: PyObjectRef = func.as_ref().incref();
let annotations = func_obj.get_attr("__annotations__", vm)?;
if vm.is_none(&annotations) {
Err(new_jit_error(
@@ -105,7 +107,7 @@ pub fn get_jit_arg_types(func: &PyRef<PyFunction>, vm: &VirtualMachine) -> PyRes
}
}
fn get_jit_value(vm: &VirtualMachine, obj: &PyObjectRef) -> Result<AbiValue, ArgsError> {
fn get_jit_value(vm: &VirtualMachine, obj: &crate::PyObj) -> Result<AbiValue, ArgsError> {
// This does exact type checks as subclasses of int/float can't be passed to jitted functions
let cls = obj.class();
if cls.is(&vm.ctx.types.int_type) {

View File

@@ -99,8 +99,8 @@ impl Unconstructible for PyGenerator {}
impl IterNextIterable for PyGenerator {}
impl IterNext for PyGenerator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.clone(), vm.ctx.none(), vm)
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
Self::send(zelf.incref(), vm.ctx.none(), vm)
}
}

View File

@@ -99,7 +99,7 @@ impl PyGenericAlias {
Ok(format!(
"{}[{}]",
repr_item(self.origin.as_object().clone(), vm)?,
repr_item(self.origin.as_object().incref(), vm)?,
self.args
.as_slice()
.iter()
@@ -111,17 +111,17 @@ impl PyGenericAlias {
#[pyproperty(magic)]
fn parameters(&self) -> PyObjectRef {
self.parameters.as_object().clone()
self.parameters.as_object().incref()
}
#[pyproperty(magic)]
fn args(&self) -> PyObjectRef {
self.args.as_object().clone()
self.args.as_object().incref()
}
#[pyproperty(magic)]
fn origin(&self) -> PyObjectRef {
self.origin.as_object().clone()
self.origin.as_object().incref()
}
#[pymethod(magic)]
@@ -166,7 +166,7 @@ fn make_parameters(args: &PyTupleRef, vm: &VirtualMachine) -> PyTupleRef {
impl Hashable for PyGenericAlias {
#[inline]
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<hash::PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<hash::PyHash> {
Ok(zelf.origin.as_object().hash(vm)? ^ zelf.args.as_object().hash(vm)?)
}
}
@@ -175,7 +175,7 @@ impl GetAttr for PyGenericAlias {
fn getattro(zelf: PyRef<Self>, attr: PyStrRef, vm: &VirtualMachine) -> PyResult {
for exc in ATTR_EXCEPTIONS.iter() {
if *(*exc) == attr.to_string() {
return vm.generic_getattribute(zelf.as_object().clone(), attr);
return vm.generic_getattribute(zelf.as_object().incref(), attr);
}
}
zelf.origin().get_attr(attr, vm)

View File

@@ -6,8 +6,8 @@ use crate::{
function::{ArgIntoBool, IntoPyObject, IntoPyResult, OptionalArg, OptionalOption},
try_value_from_borrowed_object,
types::{Comparable, Constructor, Hashable, PyComparisonOp},
IdProtocol, PyArithmeticValue, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef,
PyResult, PyValue, TryFromBorrowedObject, TypeProtocol, VirtualMachine,
IdProtocol, PyArithmeticValue, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef,
PyRef, PyResult, PyValue, TryFromBorrowedObject, TypeProtocol, VirtualMachine,
};
use bstr::ByteSlice;
use num_bigint::{BigInt, BigUint, Sign};
@@ -63,7 +63,7 @@ impl PyValue for PyInt {
vm.ctx.new_int(self.value).into()
}
fn special_retrieve(vm: &VirtualMachine, obj: &PyObjectRef) -> Option<PyResult<PyRef<Self>>> {
fn special_retrieve(vm: &VirtualMachine, obj: &PyObj) -> Option<PyResult<PyRef<Self>>> {
Some(vm.to_index(obj))
}
}
@@ -83,7 +83,7 @@ impl_into_pyobject_int!(isize i8 i16 i32 i64 i128 usize u8 u16 u32 u64 u128 BigI
macro_rules! impl_try_from_object_int {
($(($t:ty, $to_prim:ident),)*) => {$(
impl TryFromBorrowedObject for $t {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
try_value_from_borrowed_object(vm, obj, |int: &PyInt| {
int.try_to_primitive(vm)
})
@@ -716,8 +716,8 @@ impl PyInt {
impl Comparable for PyInt {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -730,7 +730,7 @@ impl Comparable for PyInt {
impl Hashable for PyInt {
#[inline]
fn hash(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
fn hash(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<hash::PyHash> {
Ok(hash::hash_bigint(zelf.as_bigint()))
}
}
@@ -759,10 +759,10 @@ struct IntToByteArgs {
signed: OptionalArg<ArgIntoBool>,
}
fn try_int_radix(obj: &PyObjectRef, base: u32, vm: &VirtualMachine) -> PyResult<BigInt> {
fn try_int_radix(obj: &crate::PyObj, base: u32, vm: &VirtualMachine) -> PyResult<BigInt> {
debug_assert!(base == 0 || (2..=36).contains(&base));
let opt = match_class!(match obj.clone() {
let opt = match_class!(match obj.incref() {
string @ PyStr => {
let s = string.as_str();
bytes_to_int(s.as_bytes(), base)
@@ -898,7 +898,7 @@ fn detect_base(c: &u8) -> Option<u32> {
}
// Retrieve inner int value:
pub(crate) fn get_value(obj: &PyObjectRef) -> &BigInt {
pub(crate) fn get_value(obj: &crate::PyObj) -> &BigInt {
&obj.payload::<PyInt>().unwrap().value
}
@@ -910,8 +910,8 @@ fn i2f(int: &BigInt) -> Option<f64> {
int.to_f64().filter(|f| f.is_finite())
}
pub(crate) fn try_int(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<BigInt> {
fn try_convert(obj: &PyObjectRef, lit: &[u8], vm: &VirtualMachine) -> PyResult<BigInt> {
pub(crate) fn try_int(obj: &crate::PyObj, vm: &VirtualMachine) -> PyResult<BigInt> {
fn try_convert(obj: &crate::PyObj, lit: &[u8], vm: &VirtualMachine) -> PyResult<BigInt> {
let base = 10;
match bytes_to_int(lit, base) {
Some(i) => Ok(i),
@@ -936,7 +936,7 @@ pub(crate) fn try_int(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<BigInt
}
// call __int__, then __index__, then __trunc__ (converting the __trunc__ result via __index__ if needed)
// TODO: using __int__ is deprecated and removed in Python 3.10
if let Some(method) = vm.get_method(obj.clone(), "__int__") {
if let Some(method) = vm.get_method(obj.incref(), "__int__") {
let result = vm.invoke(&method?, ())?;
return match result.payload::<PyInt>() {
Some(int_obj) => Ok(int_obj.as_bigint().clone()),
@@ -947,10 +947,10 @@ pub(crate) fn try_int(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<BigInt
};
}
// TODO: returning strict subclasses of int in __index__ is deprecated
if let Some(r) = vm.to_index_opt(obj.clone()).transpose()? {
if let Some(r) = vm.to_index_opt(obj.incref()).transpose()? {
return Ok(r.as_bigint().clone());
}
if let Some(method) = vm.get_method(obj.clone(), "__trunc__") {
if let Some(method) = vm.get_method(obj.incref(), "__trunc__") {
let result = vm.invoke(&method?, ())?;
return vm
.to_index_opt(result.clone())

View File

@@ -7,7 +7,7 @@ use crate::{
function::ArgCallable,
protocol::PyIterReturn,
types::{IterNext, IterNextIterable},
ItemProtocol, PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
ItemProtocol, PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
use rustpython_common::{
lock::{PyMutex, PyRwLock, PyRwLockUpgradableReadGuard},
@@ -69,7 +69,7 @@ impl<T> PositionIterInternal<T> {
where
F: FnOnce(&T) -> PyObjectRef,
{
let iter = builtins_iter(vm).clone();
let iter = builtins_iter(vm).incref();
self._reduce(iter, f, vm)
}
@@ -77,7 +77,7 @@ impl<T> PositionIterInternal<T> {
where
F: FnOnce(&T) -> PyObjectRef,
{
let reversed = builtins_reversed(vm).clone();
let reversed = builtins_reversed(vm).incref();
self._reduce(reversed, f, vm)
}
@@ -143,14 +143,14 @@ impl<T> PositionIterInternal<T> {
}
}
pub fn builtins_iter(vm: &VirtualMachine) -> &PyObjectRef {
pub fn builtins_iter(vm: &VirtualMachine) -> &crate::PyObj {
static_cell! {
static INSTANCE: PyObjectRef;
}
INSTANCE.get_or_init(|| vm.builtins.clone().get_attr("iter", vm).unwrap())
}
pub fn builtins_reversed(vm: &VirtualMachine) -> &PyObjectRef {
pub fn builtins_reversed(vm: &VirtualMachine) -> &crate::PyObj {
static_cell! {
static INSTANCE: PyObjectRef;
}
@@ -202,7 +202,7 @@ impl PySequenceIterator {
impl IterNextIterable for PySequenceIterator {}
impl IterNext for PySequenceIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal
.lock()
.next(|obj, pos| PyIterReturn::from_getitem_result(obj.get_item(pos, vm), vm))
@@ -234,7 +234,7 @@ impl PyCallableIterator {
impl IterNextIterable for PyCallableIterator {}
impl IterNext for PyCallableIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let status = zelf.status.upgradable_read();
if let IterStatus::Active(callable) = &*status {
let ret = callable.invoke((), vm)?;

View File

@@ -14,8 +14,8 @@ use crate::{
},
utils::Either,
vm::{ReprGuard, VirtualMachine},
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObjectPtr, PyObjectRef,
PyRef, PyResult, PyValue, TryFromObject, TypeProtocol,
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef,
PyResult, PyValue, TryFromObject, TypeProtocol,
};
use std::fmt;
use std::iter::FromIterator;
@@ -259,7 +259,7 @@ impl PyList {
fn _iter_equal<F: FnMut(), const SHORT: bool>(
&self,
needle: &PyObjectRef,
needle: &PyObj,
range: Range<usize>,
mut f: F,
vm: &VirtualMachine,
@@ -305,8 +305,8 @@ impl PyList {
drop(elem_cls);
fn cmp(
elem: PyObjectPtr,
needle: PyObjectPtr,
elem: &PyObj,
needle: &PyObj,
elem_cmp: RichCompareFunc,
needle_cmp: RichCompareFunc,
vm: &VirtualMachine,
@@ -329,20 +329,14 @@ impl PyList {
if elem_cmp as usize == richcompare_wrapper as usize {
let elem = elem.clone();
drop(guard);
PyObjectPtr::with((&elem, needle), |(elem, needle)| {
cmp(elem, needle, elem_cmp, needle_cmp, vm)
})?
cmp(&elem, needle, elem_cmp, needle_cmp, vm)?
} else {
let eq = PyObjectPtr::with((elem, needle), |(elem, needle)| {
cmp(elem, needle, elem_cmp, needle_cmp, vm)
})?;
let eq = cmp(elem, needle, elem_cmp, needle_cmp, vm)?;
borrower = Some(guard);
eq
}
} else {
match PyObjectPtr::with((elem, needle), |(elem, needle)| {
needle_cmp(needle, elem, PyComparisonOp::Eq, vm)
})? {
match needle_cmp(needle, elem, PyComparisonOp::Eq, vm)? {
Either::B(PyComparisonValue::Implemented(value)) => {
drop(elem_cls);
borrower = Some(guard);
@@ -360,8 +354,8 @@ impl PyList {
drop(elem_cls);
fn cmp(
elem: PyObjectPtr,
needle: PyObjectPtr,
elem: &PyObj,
needle: &PyObj,
elem_cmp: RichCompareFunc,
vm: &VirtualMachine,
) -> PyResult<bool> {
@@ -377,13 +371,9 @@ impl PyList {
if elem_cmp as usize == richcompare_wrapper as usize {
let elem = elem.clone();
drop(guard);
PyObjectPtr::with((&elem, needle), |(elem, needle)| {
cmp(elem, needle, elem_cmp, vm)
})?
cmp(&elem, needle, elem_cmp, vm)?
} else {
let eq = PyObjectPtr::with((elem, needle), |(elem, needle)| {
cmp(elem, needle, elem_cmp, vm)
})?;
let eq = cmp(elem, needle, elem_cmp, vm)?;
borrower = Some(guard);
eq
}
@@ -407,7 +397,7 @@ impl PyList {
fn foreach_equal<F: FnMut()>(
&self,
needle: &PyObjectRef,
needle: &crate::PyObj,
f: F,
vm: &VirtualMachine,
) -> PyResult<()> {
@@ -417,7 +407,7 @@ impl PyList {
fn find_equal(
&self,
needle: &PyObjectRef,
needle: &crate::PyObj,
range: Range<usize>,
vm: &VirtualMachine,
) -> PyResult<usize> {
@@ -552,7 +542,7 @@ impl PyList {
}
impl AsMapping for PyList {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -595,8 +585,8 @@ impl Iterable for PyList {
impl Comparable for PyList {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -676,7 +666,7 @@ impl Unconstructible for PyListIterator {}
impl IterNextIterable for PyListIterator {}
impl IterNext for PyListIterator {
fn next(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|list, pos| {
let vec = list.borrow_vec();
Ok(match vec.get(pos) {
@@ -724,7 +714,7 @@ impl Unconstructible for PyListReverseIterator {}
impl IterNextIterable for PyListReverseIterator {}
impl IterNext for PyListReverseIterator {
fn next(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().rev_next(|list, pos| {
let vec = list.borrow_vec();
Ok(match vec.get(pos) {

View File

@@ -3,7 +3,7 @@ use crate::{
function::PosArgs,
protocol::{PyIter, PyIterReturn},
types::{Constructor, IterNext, IterNextIterable},
PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
/// map(func, *iterables) --> map object
@@ -37,7 +37,7 @@ impl PyMap {
#[pymethod(magic)]
fn length_hint(&self, vm: &VirtualMachine) -> PyResult<usize> {
self.iterators.iter().try_fold(0, |prev, cur| {
let cur = vm.length_hint(cur.as_ref().clone())?.unwrap_or(0);
let cur = vm.length_hint(cur.as_ref().incref())?.unwrap_or(0);
let max = std::cmp::max(prev, cur);
Ok(max)
})
@@ -46,7 +46,7 @@ impl PyMap {
impl IterNextIterable for PyMap {}
impl IterNext for PyMap {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut next_objs = Vec::new();
for iterator in zelf.iterators.iter() {
let item = match iterator.next(vm)? {

View File

@@ -151,7 +151,7 @@ impl PyMappingProxy {
}
impl AsMapping for PyMappingProxy {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: None,
subscript: Some(Self::subscript),

View File

@@ -13,7 +13,7 @@ use crate::{
stdlib::pystruct::FormatSpec,
types::{AsBuffer, AsMapping, Comparable, Constructor, Hashable, PyComparisonOp},
utils::Either,
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef,
IdProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef,
PyResult, PyValue, TryFromBorrowedObject, TryFromObject, TypeProtocol, VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
@@ -480,7 +480,7 @@ impl PyMemoryView {
self.try_not_released(vm).map(|_| self.buffer.options.len)
}
fn to_bytes_vec(zelf: &PyRef<Self>) -> Vec<u8> {
fn to_bytes_vec(zelf: &crate::Py<Self>) -> Vec<u8> {
if let Some(bytes) = zelf.as_contiguous() {
bytes.to_vec()
} else {
@@ -531,7 +531,7 @@ impl PyMemoryView {
released: AtomicCell::new(false),
format_spec: zelf.format_spec.clone(),
hash: OnceCell::new(),
..*zelf
..**zelf
}
.validate()
.into_ref(vm))
@@ -601,13 +601,13 @@ impl PyMemoryView {
released: AtomicCell::new(false),
format_spec,
hash: OnceCell::new(),
..*zelf
..**zelf
}
.validate()
.into_ref(vm))
}
fn eq(zelf: &PyRef<Self>, other: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
fn eq(zelf: &crate::Py<Self>, other: &PyObj, vm: &VirtualMachine) -> PyResult<bool> {
if zelf.is(other) {
return Ok(true);
}
@@ -677,13 +677,13 @@ impl PyMemoryView {
}
impl AsBuffer for PyMemoryView {
fn as_buffer(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyBuffer> {
fn as_buffer(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyBuffer> {
if zelf.released.load() {
Err(vm.new_value_error("operation forbidden on released memoryview object".to_owned()))
} else {
Ok(PyBuffer::new(
zelf.as_object().clone(),
zelf.clone(),
zelf.as_object().incref(),
zelf.incref(),
zelf.buffer.options.clone(),
))
}
@@ -737,7 +737,7 @@ impl BufferInternal for PyRef<PyMemoryView> {
}
impl AsMapping for PyMemoryView {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -773,8 +773,8 @@ impl AsMapping for PyMemoryView {
impl Comparable for PyMemoryView {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -794,7 +794,7 @@ impl Comparable for PyMemoryView {
}
impl Hashable for PyMemoryView {
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
zelf.hash
.get_or_try_init(|| {
zelf.try_not_released(vm)?;

View File

@@ -68,7 +68,7 @@ impl PyModule {
fn name(zelf: PyRef<Self>, vm: &VirtualMachine) -> Option<String> {
vm.generic_getattribute_opt(
zelf.as_object().clone(),
zelf.as_object().incref(),
PyStr::from("__name__").into_ref(vm),
None,
)
@@ -97,7 +97,7 @@ impl PyModule {
impl GetAttr for PyModule {
fn getattro(zelf: PyRef<Self>, name: PyStrRef, vm: &VirtualMachine) -> PyResult {
if let Some(attr) =
vm.generic_getattribute_opt(zelf.as_object().clone(), name.clone(), None)?
vm.generic_getattribute_opt(zelf.as_object().incref(), name.clone(), None)?
{
return Ok(attr);
}

View File

@@ -4,7 +4,7 @@ use crate::{
function::FuncArgs,
types::{Comparable, Constructor, PyComparisonOp},
vm::ReprGuard,
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue,
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyRef, PyResult, PyValue,
TypeProtocol, VirtualMachine,
};
@@ -80,8 +80,8 @@ impl PyNamespace {
impl Comparable for PyNamespace {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {

View File

@@ -2,8 +2,8 @@ use super::{PyDict, PyDictRef, PyList, PyStr, PyStrRef, PyType, PyTypeRef};
use crate::common::hash::PyHash;
use crate::{
function::FuncArgs, types::PyComparisonOp, utils::Either, IdProtocol, ItemProtocol,
PyArithmeticValue, PyAttributes, PyClassImpl, PyComparisonValue, PyContext, PyObject,
PyObjectPtr, PyObjectRef, PyResult, PyValue, TypeProtocol, VirtualMachine,
PyArithmeticValue, PyAttributes, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObject,
PyObjectRef, PyResult, PyValue, TypeProtocol, VirtualMachine,
};
/// object()
@@ -39,18 +39,18 @@ impl PyBaseObject {
#[pyslot]
fn slot_richcompare(
zelf: PyObjectPtr,
other: PyObjectPtr,
zelf: &PyObj,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<Either<PyObjectRef, PyComparisonValue>> {
Self::cmp(&*zelf, &*other, op, vm).map(Either::B)
Self::cmp(zelf, other, op, vm).map(Either::B)
}
#[inline(always)]
fn cmp(
zelf: &PyObjectRef,
other: &PyObjectRef,
zelf: &PyObj,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -67,9 +67,7 @@ impl PyBaseObject {
.class()
.mro_find_map(|cls| cls.slots.richcompare.load())
.unwrap();
let value = match PyObjectPtr::with((zelf, other), |(zelf, other)| {
cmp(zelf, other, PyComparisonOp::Eq, vm)
})? {
let value = match cmp(zelf, other, PyComparisonOp::Eq, vm)? {
Either::A(obj) => PyArithmeticValue::from_object(vm, obj)
.map(|obj| obj.try_to_bool(vm))
.transpose()?,
@@ -161,7 +159,7 @@ impl PyBaseObject {
#[pyslot]
fn slot_setattro(
obj: PyObjectPtr,
obj: &PyObj,
attr_name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
@@ -298,14 +296,14 @@ impl PyBaseObject {
}
#[pyslot]
fn slot_hash(zelf: PyObjectPtr, _vm: &VirtualMachine) -> PyResult<PyHash> {
fn slot_hash(zelf: &PyObj, _vm: &VirtualMachine) -> PyResult<PyHash> {
Ok(zelf.get_id() as _)
}
/// Return hash(self).
#[pymethod(magic)]
fn hash(zelf: PyObjectRef, vm: &VirtualMachine) -> PyResult<PyHash> {
zelf.with_ptr(|zelf| Self::slot_hash(zelf, vm))
Self::slot_hash(&zelf, vm)
}
}
@@ -320,7 +318,7 @@ pub fn object_set_dict(obj: PyObjectRef, dict: PyDictRef, vm: &VirtualMachine) -
#[cfg_attr(feature = "flame-it", flame)]
pub(crate) fn setattr(
obj: &PyObjectRef,
obj: &PyObj,
attr_name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
@@ -330,7 +328,7 @@ pub(crate) fn setattr(
if let Some(attr) = obj.get_class_attr(attr_name.as_str()) {
let descr_set = attr.class().mro_find_map(|cls| cls.slots.descr_set.load());
if let Some(descriptor) = descr_set {
return descriptor(attr, obj.clone(), value, vm);
return descriptor(attr, obj.to_owned(), value, vm);
}
}

View File

@@ -2,8 +2,8 @@ use super::{PyInt, PyStrRef, PyTypeRef};
use crate::{
function::{IntoPyObject, OptionalArg},
types::Constructor,
IdProtocol, PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, TryFromBorrowedObject,
TypeProtocol, VirtualMachine,
IdProtocol, PyClassImpl, PyContext, PyObj, PyObjectRef, PyResult, PyValue,
TryFromBorrowedObject, TypeProtocol, VirtualMachine,
};
use num_bigint::Sign;
use num_traits::Zero;
@@ -16,7 +16,7 @@ impl IntoPyObject for bool {
}
impl TryFromBorrowedObject for bool {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<bool> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<bool> {
if obj.isinstance(&vm.ctx.types.int_type) {
Ok(get_value(obj))
} else {
@@ -166,7 +166,7 @@ pub(crate) fn init(context: &PyContext) {
PyBool::extend_class(context, &context.types.bool_type);
}
// pub fn not(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<bool> {
// pub fn not(vm: &VirtualMachine, obj: &crate::PyObj) -> PyResult<bool> {
// if obj.isinstance(&vm.ctx.types.bool_type) {
// let value = get_value(obj);
// Ok(!value)
@@ -176,10 +176,10 @@ pub(crate) fn init(context: &PyContext) {
// }
// Retrieve inner int value:
pub(crate) fn get_value(obj: &PyObjectRef) -> bool {
pub(crate) fn get_value(obj: &PyObj) -> bool {
!obj.payload::<PyInt>().unwrap().as_bigint().is_zero()
}
fn get_py_int(obj: &PyObjectRef) -> &PyInt {
fn get_py_int(obj: &crate::PyObj) -> &PyInt {
obj.payload::<PyInt>().unwrap()
}

View File

@@ -14,8 +14,8 @@ use crate::{
Unconstructible,
},
utils::Either,
IdProtocol, ItemProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef,
PyRef, PyResult, PyValue, TypeProtocol, VirtualMachine,
IdProtocol, ItemProtocol, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj,
PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol, VirtualMachine,
};
use ascii::{AsciiStr, AsciiString};
use bstr::ByteSlice;
@@ -247,7 +247,7 @@ impl Unconstructible for PyStrIterator {}
impl IterNextIterable for PyStrIterator {}
impl IterNext for PyStrIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut internal = zelf.internal.lock();
if let IterStatus::Active(s) = &internal.0.status {
@@ -1216,15 +1216,15 @@ impl PyStrRef {
impl Hashable for PyStr {
#[inline]
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<hash::PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<hash::PyHash> {
Ok(zelf.hash(vm))
}
}
impl Comparable for PyStr {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
_vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {

View File

@@ -144,7 +144,7 @@ impl GetAttr for PySuper {
descr.clone(),
// Only pass 'obj' param if this is instance-mode super (See https://bugs.python.org/issue743267)
if obj.is(&start_type) { None } else { Some(obj) },
Some(start_type.as_object().clone()),
Some(start_type.as_object().incref()),
)
.unwrap_or(Ok(descr));
}

View File

@@ -130,7 +130,7 @@ impl PyType {
}
pub fn iter_mro(&self) -> impl Iterator<Item = &PyType> + DoubleEndedIterator {
std::iter::once(self).chain(self.mro.iter().map(|cls| cls.deref()))
std::iter::once(self).chain(self.mro.iter().map(|cls| -> &PyType { cls }))
}
pub(crate) fn mro_find_map<F, R>(&self, f: F) -> Option<R>
@@ -225,14 +225,14 @@ impl PyType {
#[pyproperty(name = "__mro__")]
fn get_mro(zelf: PyRef<Self>) -> PyTuple {
let elements: Vec<PyObjectRef> = zelf.iter_mro().map(|x| x.as_object().clone()).collect();
let elements: Vec<PyObjectRef> = zelf.iter_mro().map(|x| x.as_object().incref()).collect();
PyTuple::new_unchecked(elements.into_boxed_slice())
}
#[pyproperty(magic)]
fn bases(&self, vm: &VirtualMachine) -> PyTupleRef {
vm.ctx
.new_tuple(self.bases.iter().map(|x| x.as_object().clone()).collect())
.new_tuple(self.bases.iter().map(|x| x.as_object().incref()).collect())
}
#[pyproperty(magic)]
@@ -605,7 +605,7 @@ impl GetAttr for PyType {
impl SetAttr for PyType {
fn setattro(
zelf: &PyRef<Self>,
zelf: &crate::Py<Self>,
attr_name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
@@ -613,7 +613,7 @@ impl SetAttr for PyType {
if let Some(attr) = zelf.get_class_attr(attr_name.as_str()) {
let descr_set = attr.class().mro_find_map(|cls| cls.slots.descr_set.load());
if let Some(descriptor) = descr_set {
return descriptor(attr, zelf.clone().into(), value, vm);
return descriptor(attr, zelf.incref().into(), value, vm);
}
}
let assign = value.is_some();
@@ -640,9 +640,9 @@ impl SetAttr for PyType {
impl Callable for PyType {
type Args = FuncArgs;
fn call(zelf: &PyRef<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
vm_trace!("type_call: {:?}", zelf);
let obj = call_slot_new(zelf.clone(), zelf.clone(), args.clone(), vm)?;
let obj = call_slot_new(zelf.incref(), zelf.incref(), args.clone(), vm)?;
if (zelf.is(&vm.ctx.types.type_type) && args.kwargs.is_empty()) || !obj.isinstance(zelf) {
return Ok(obj);

View File

@@ -8,7 +8,7 @@ use crate::{
AsMapping, Comparable, Constructor, Hashable, IterNext, IterNextIterable, Iterable,
PyComparisonOp, Unconstructible,
},
IdProtocol, IntoPyRef, PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue,
IdProtocol, IntoPyRef, PyClassImpl, PyContext, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TryFromObject, TypeProtocol, VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
@@ -35,8 +35,8 @@ fn iter_search(
) -> PyResult<usize> {
let mut count = 0;
let iter = obj.get_iter(vm)?;
for element in iter.iter_without_hint(vm)? {
if vm.bool_eq(&item, &element?)? {
for element in iter.iter_without_hint::<PyObjectRef>(vm)? {
if vm.bool_eq(&item, &*element?)? {
match flag {
SearchType::Index => return Ok(count),
SearchType::Contains => return Ok(1),
@@ -167,7 +167,7 @@ impl PyRange {
}
}
// pub fn get_value(obj: &PyObjectRef) -> PyRange {
// pub fn get_value(obj: &crate::PyObj) -> PyRange {
// obj.payload::<PyRange>().unwrap().clone()
// }
@@ -296,7 +296,7 @@ impl PyRange {
fn reduce(&self, vm: &VirtualMachine) -> (PyTypeRef, PyTupleRef) {
let range_paramters: Vec<PyObjectRef> = vec![&self.start, &self.stop, &self.step]
.iter()
.map(|x| x.as_object().clone())
.map(|x| x.as_object().incref())
.collect();
let range_paramters_tuple = vm.ctx.new_tuple(range_paramters);
(vm.ctx.types.range_type.clone(), range_paramters_tuple)
@@ -377,7 +377,7 @@ impl PyRange {
}
impl AsMapping for PyRange {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -407,7 +407,7 @@ impl AsMapping for PyRange {
}
impl Hashable for PyRange {
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
let length = zelf.compute_length();
let elements = if length.is_zero() {
[vm.ctx.new_int(length).into(), vm.ctx.none(), vm.ctx.none()]
@@ -430,8 +430,8 @@ impl Hashable for PyRange {
impl Comparable for PyRange {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
_vm: &VirtualMachine,
) -> PyResult<crate::PyComparisonValue> {
@@ -550,7 +550,7 @@ impl Unconstructible for PyLongRangeIterator {}
impl IterNextIterable for PyLongRangeIterator {}
impl IterNext for PyLongRangeIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// TODO: In pathological case (index == usize::MAX) this can wrap around
// (since fetch_add wraps). This would result in the iterator spinning again
// from the beginning.
@@ -616,7 +616,7 @@ impl Unconstructible for PyRangeIterator {}
impl IterNextIterable for PyRangeIterator {}
impl IterNext for PyRangeIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// TODO: In pathological case (index == usize::MAX) this can wrap around
// (since fetch_add wraps). This would result in the iterator spinning again
// from the beginning.
@@ -638,7 +638,7 @@ fn range_iter_reduce(
index: usize,
vm: &VirtualMachine,
) -> PyResult<PyTupleRef> {
let iter = builtins_iter(vm).clone();
let iter = builtins_iter(vm).incref();
let stop = start.clone() + length * step.clone();
let range = PyRange {
start: PyInt::from(start).into_ref(vm),

View File

@@ -12,8 +12,8 @@ use crate::{
Unconstructible, Unhashable,
},
vm::{ReprGuard, VirtualMachine},
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue,
TryFromObject, TypeProtocol,
IdProtocol, PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef, PyResult,
PyValue, TryFromObject, TypeProtocol,
};
use std::{fmt, ops::Deref};
@@ -96,7 +96,7 @@ impl PySetInner {
}
}
fn contains(&self, needle: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
fn contains(&self, needle: &crate::PyObj, vm: &VirtualMachine) -> PyResult<bool> {
self.retry_op_with_frozenset(needle, vm, |needle, vm| self.content.contains(vm, needle))
}
@@ -180,7 +180,7 @@ impl PySetInner {
fn issuperset(&self, other: ArgIterable, vm: &VirtualMachine) -> PyResult<bool> {
for item in other.iter(vm)? {
if !self.contains(&item?, vm)? {
if !self.contains(&*item?, vm)? {
return Ok(false);
}
}
@@ -194,7 +194,7 @@ impl PySetInner {
fn isdisjoint(&self, other: ArgIterable, vm: &VirtualMachine) -> PyResult<bool> {
for item in other.iter(vm)? {
if self.contains(&item?, vm)? {
if self.contains(&*item?, vm)? {
return Ok(false);
}
}
@@ -242,10 +242,10 @@ impl PySetInner {
}
fn remove(&self, item: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
self.retry_op_with_frozenset(&item, vm, |item, vm| self.content.delete(vm, item.clone()))
self.retry_op_with_frozenset(&item, vm, |item, vm| self.content.delete(vm, item.incref()))
}
fn discard(&self, item: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
fn discard(&self, item: &crate::PyObj, vm: &VirtualMachine) -> PyResult<bool> {
self.retry_op_with_frozenset(item, vm, |item, vm| self.content.delete_if_exists(vm, item))
}
@@ -328,12 +328,12 @@ impl PySetInner {
// on failure to convert and restores item in KeyError on failure (remove).
fn retry_op_with_frozenset<T, F>(
&self,
item: &PyObjectRef,
item: &crate::PyObj,
vm: &VirtualMachine,
op: F,
) -> PyResult<T>
where
F: Fn(&PyObjectRef, &VirtualMachine) -> PyResult<T>,
F: Fn(&crate::PyObj, &VirtualMachine) -> PyResult<T>,
{
op(item, vm).or_else(|original_err| {
item.payload_if_subclass::<PySet>(vm)
@@ -350,7 +350,7 @@ impl PySetInner {
// If operation raised KeyError, report original set (set.remove)
.map_err(|op_err| {
if op_err.isinstance(&vm.ctx.exceptions.key_error) {
vm.new_key_error(item.clone())
vm.new_key_error(item.incref())
} else {
op_err
}
@@ -360,7 +360,7 @@ impl PySetInner {
}
}
fn extract_set(obj: &PyObjectRef) -> Option<&PySetInner> {
fn extract_set(obj: &PyObj) -> Option<&PySetInner> {
match_class!(match obj {
ref set @ PySet => Some(&set.inner),
ref frozen @ PyFrozenSet => Some(&frozen.inner),
@@ -369,7 +369,7 @@ fn extract_set(obj: &PyObjectRef) -> Option<&PySetInner> {
}
fn reduce_set(
zelf: &PyObjectRef,
zelf: &crate::PyObj,
vm: &VirtualMachine,
) -> PyResult<(PyTypeRef, PyTupleRef, Option<PyDictRef>)> {
Ok((
@@ -556,7 +556,7 @@ impl PySet {
#[pymethod(magic)]
fn ior(zelf: PyRef<Self>, iterable: SetIterable, vm: &VirtualMachine) -> PyResult {
zelf.inner.update(iterable.iterable, vm)?;
Ok(zelf.as_object().clone())
Ok(zelf.as_object().incref())
}
#[pymethod]
@@ -578,7 +578,7 @@ impl PySet {
#[pymethod(magic)]
fn iand(zelf: PyRef<Self>, iterable: SetIterable, vm: &VirtualMachine) -> PyResult {
zelf.inner.intersection_update(iterable.iterable, vm)?;
Ok(zelf.as_object().clone())
Ok(zelf.as_object().incref())
}
#[pymethod]
@@ -590,7 +590,7 @@ impl PySet {
#[pymethod(magic)]
fn isub(zelf: PyRef<Self>, iterable: SetIterable, vm: &VirtualMachine) -> PyResult {
zelf.inner.difference_update(iterable.iterable, vm)?;
Ok(zelf.as_object().clone())
Ok(zelf.as_object().incref())
}
#[pymethod]
@@ -607,7 +607,7 @@ impl PySet {
fn ixor(zelf: PyRef<Self>, iterable: SetIterable, vm: &VirtualMachine) -> PyResult {
zelf.inner
.symmetric_difference_update(iterable.iterable, vm)?;
Ok(zelf.as_object().clone())
Ok(zelf.as_object().incref())
}
#[pymethod(magic)]
@@ -615,14 +615,14 @@ impl PySet {
zelf: PyRef<Self>,
vm: &VirtualMachine,
) -> PyResult<(PyTypeRef, PyTupleRef, Option<PyDictRef>)> {
reduce_set(&zelf.into(), vm)
reduce_set(zelf.as_ref(), vm)
}
}
impl Comparable for PySet {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -806,21 +806,21 @@ impl PyFrozenSet {
zelf: PyRef<Self>,
vm: &VirtualMachine,
) -> PyResult<(PyTypeRef, PyTupleRef, Option<PyDictRef>)> {
reduce_set(&zelf.into(), vm)
reduce_set(zelf.as_ref(), vm)
}
}
impl Hashable for PyFrozenSet {
#[inline]
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
zelf.inner.hash(vm)
}
}
impl Comparable for PyFrozenSet {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -887,7 +887,7 @@ impl PySetIterator {
fn reduce(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult<(PyObjectRef, (PyObjectRef,))> {
let internal = zelf.internal.lock();
Ok((
builtins_iter(vm).clone(),
builtins_iter(vm).incref(),
(vm.ctx
.new_list(match &internal.status {
IterStatus::Exhausted => vec![],
@@ -903,7 +903,7 @@ impl Unconstructible for PySetIterator {}
impl IterNextIterable for PySetIterator {}
impl IterNext for PySetIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut internal = zelf.internal.lock();
if let IterStatus::Active(dict) = &internal.status {
if dict.has_changed_size(&zelf.size) {

View File

@@ -3,8 +3,8 @@ use super::{PyInt, PyIntRef, PyTupleRef, PyTypeRef};
use crate::{
function::{FuncArgs, IntoPyObject, OptionalArg},
types::{Comparable, Constructor, Hashable, PyComparisonOp, Unhashable},
PyClassImpl, PyComparisonValue, PyContext, PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol,
VirtualMachine,
PyClassImpl, PyComparisonValue, PyContext, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TypeProtocol, VirtualMachine,
};
use num_bigint::{BigInt, ToBigInt};
use num_traits::{One, Signed, ToPrimitive, Zero};
@@ -31,7 +31,7 @@ impl PySlice {
self.start.clone().into_pyobject(vm)
}
fn start_ref<'a>(&'a self, vm: &'a VirtualMachine) -> &'a PyObjectRef {
fn start_ref<'a>(&'a self, vm: &'a VirtualMachine) -> &'a crate::PyObj {
match &self.start {
Some(v) => v,
None => vm.ctx.none.as_object(),
@@ -48,7 +48,7 @@ impl PySlice {
self.step.clone().into_pyobject(vm)
}
fn step_ref<'a>(&'a self, vm: &'a VirtualMachine) -> &'a PyObjectRef {
fn step_ref<'a>(&'a self, vm: &'a VirtualMachine) -> &'a crate::PyObj {
match &self.step {
Some(v) => v,
None => vm.ctx.none.as_object(),
@@ -197,8 +197,8 @@ impl PySlice {
impl Comparable for PySlice {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -334,11 +334,11 @@ impl SaturatedSlice {
// Go from PyObjectRef to isize w/o overflow error, out of range values are substituted by
// isize::MIN or isize::MAX depending on type and value of step.
// Equivalent to PyNumber_AsSsize_t with err equal to None.
fn to_isize_index(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Option<isize>> {
fn to_isize_index(vm: &VirtualMachine, obj: &crate::PyObj) -> PyResult<Option<isize>> {
if vm.is_none(obj) {
return Ok(None);
}
let result = vm.to_index_opt(obj.clone()).unwrap_or_else(|| {
let result = vm.to_index_opt(obj.incref()).unwrap_or_else(|| {
Err(vm.new_type_error(
"slice indices must be integers or None or have an __index__ method".to_owned(),
))

View File

@@ -12,7 +12,7 @@ use crate::{
},
utils::Either,
vm::{ReprGuard, VirtualMachine},
IdProtocol, PyArithmeticValue, PyClassDef, PyClassImpl, PyComparisonValue, PyContext,
IdProtocol, PyArithmeticValue, PyClassDef, PyClassImpl, PyComparisonValue, PyContext, PyObj,
PyObjectRef, PyRef, PyResult, PyValue, TransmuteFromObject, TryFromObject, TypeProtocol,
};
use rustpython_common::lock::PyMutex;
@@ -306,7 +306,7 @@ impl PyTuple {
}
impl AsMapping for PyTuple {
fn as_mapping(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyMappingMethods {
PyMappingMethods {
length: Some(Self::length),
subscript: Some(Self::subscript),
@@ -337,15 +337,15 @@ impl AsMapping for PyTuple {
impl Hashable for PyTuple {
#[inline]
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
crate::utils::hash_iter(zelf.elements.iter(), vm)
}
}
impl Comparable for PyTuple {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -405,7 +405,7 @@ impl Unconstructible for PyTupleIterator {}
impl IterNextIterable for PyTupleIterator {}
impl IterNext for PyTupleIterator {
fn next(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|tuple, pos| {
Ok(if let Some(ret) = tuple.as_slice().get(pos) {
PyIterReturn::Return(ret.clone())

View File

@@ -2,7 +2,7 @@ use super::{PyStrRef, PyTypeRef, PyWeak};
use crate::{
function::OptionalArg,
types::{Constructor, SetAttr},
PyClassImpl, PyContext, PyObjectRef, PyRef, PyResult, PyValue, VirtualMachine,
PyClassImpl, PyContext, PyObjectRef, PyResult, PyValue, VirtualMachine,
};
#[pyclass(module = false, name = "weakproxy")]
@@ -60,7 +60,7 @@ impl PyWeakProxy {
impl SetAttr for PyWeakProxy {
fn setattro(
zelf: &PyRef<Self>,
zelf: &crate::Py<Self>,
attr_name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,

View File

@@ -3,7 +3,7 @@ use crate::common::hash::PyHash;
use crate::{
function::OptionalArg,
types::{Callable, Comparable, Constructor, Hashable, PyComparisonOp},
IdProtocol, PyClassImpl, PyContext, PyObjectRef, PyObjectWeak, PyRef, PyResult, PyValue,
IdProtocol, PyClassImpl, PyContext, PyObj, PyObjectRef, PyObjectWeak, PyRef, PyResult, PyValue,
TypeProtocol, VirtualMachine,
};
@@ -17,9 +17,9 @@ pub struct PyWeak {
}
impl PyWeak {
pub fn downgrade(obj: &PyObjectRef) -> PyWeak {
pub fn downgrade(obj: &PyObj) -> PyWeak {
PyWeak {
referent: PyObjectRef::downgrade(obj),
referent: obj.downgrade(),
hash: AtomicCell::new(None),
}
}
@@ -46,7 +46,7 @@ impl PyValue for PyWeak {
impl Callable for PyWeak {
type Args = ();
#[inline]
fn call(zelf: &PyRef<Self>, _: Self::Args, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, _: Self::Args, vm: &VirtualMachine) -> PyResult {
Ok(vm.unwrap_or_none(zelf.upgrade()))
}
}
@@ -86,7 +86,7 @@ impl PyWeak {
}
impl Hashable for PyWeak {
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
match zelf.hash.load() {
Some(hash) => Ok(hash),
None => {
@@ -103,8 +103,8 @@ impl Hashable for PyWeak {
impl Comparable for PyWeak {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<crate::PyComparisonValue> {

View File

@@ -67,7 +67,7 @@ impl PyZip {
impl IterNextIterable for PyZip {}
impl IterNext for PyZip {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if zelf.iterators.is_empty() {
return Ok(PyIterReturn::StopIteration(None));
}

View File

@@ -9,7 +9,7 @@ use crate::{
sliceable::PySliceableSequence,
types::PyComparisonOp,
utils::Either,
IdProtocol, PyComparisonValue, PyObjectRef, PyResult, PyValue, TryFromBorrowedObject,
IdProtocol, PyComparisonValue, PyObj, PyObjectRef, PyResult, PyValue, TryFromBorrowedObject,
VirtualMachine,
};
use bstr::ByteSlice;
@@ -30,7 +30,7 @@ impl From<Vec<u8>> for PyBytesInner {
}
impl TryFromBorrowedObject for PyBytesInner {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
bytes_from_object(vm, obj).map(Self::from)
}
}
@@ -258,12 +258,7 @@ impl PyBytesInner {
self.elements.is_empty()
}
pub fn cmp(
&self,
other: &PyObjectRef,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyComparisonValue {
pub fn cmp(&self, other: &PyObj, op: PyComparisonOp, vm: &VirtualMachine) -> PyComparisonValue {
// TODO: bytes can compare with any object implemented buffer protocol
// but not memoryview, and not equal if compare with unicode str(PyStr)
PyComparisonValue::from_option(
@@ -1183,7 +1178,7 @@ pub const fn is_py_ascii_whitespace(b: u8) -> bool {
matches!(b, b'\t' | b'\n' | b'\x0C' | b'\r' | b' ' | b'\x0B')
}
pub fn bytes_from_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Vec<u8>> {
pub fn bytes_from_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Vec<u8>> {
if let Ok(elements) = obj.try_bytes_like(vm, |bytes| bytes.to_vec()) {
return Ok(elements);
}
@@ -1197,7 +1192,7 @@ pub fn bytes_from_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Vec
))
}
pub fn value_from_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<u8> {
pub fn value_from_object(vm: &VirtualMachine, obj: &crate::PyObj) -> PyResult<u8> {
vm.to_index(obj)?
.as_bigint()
.to_u8()

View File

@@ -42,11 +42,11 @@ impl PyCodec {
}
#[inline]
pub fn get_encode_func(&self) -> &PyObjectRef {
pub fn get_encode_func(&self) -> &crate::PyObj {
&self.0.as_slice()[0]
}
#[inline]
pub fn get_decode_func(&self) -> &PyObjectRef {
pub fn get_decode_func(&self) -> &crate::PyObj {
&self.0.as_slice()[1]
}
@@ -332,20 +332,20 @@ fn normalize_encoding_name(encoding: &str) -> Cow<'_, str> {
}
// TODO: exceptions with custom payloads
fn extract_unicode_error_range(err: &PyObjectRef, vm: &VirtualMachine) -> PyResult<Range<usize>> {
let start = err.clone().get_attr("start", vm)?;
fn extract_unicode_error_range(err: &crate::PyObj, vm: &VirtualMachine) -> PyResult<Range<usize>> {
let start = err.incref().get_attr("start", vm)?;
let start = start.try_into_value(vm)?;
let end = err.clone().get_attr("end", vm)?;
let end = err.incref().get_attr("end", vm)?;
let end = end.try_into_value(vm)?;
Ok(Range { start, end })
}
#[inline]
fn is_decode_err(err: &PyObjectRef, vm: &VirtualMachine) -> bool {
fn is_decode_err(err: &crate::PyObj, vm: &VirtualMachine) -> bool {
err.isinstance(&vm.ctx.exceptions.unicode_decode_error)
}
#[inline]
fn is_encode_ish_err(err: &PyObjectRef, vm: &VirtualMachine) -> bool {
fn is_encode_ish_err(err: &crate::PyObj, vm: &VirtualMachine) -> bool {
err.isinstance(&vm.ctx.exceptions.unicode_encode_error)
|| err.isinstance(&vm.ctx.exceptions.unicode_translate_error)
}

View File

@@ -36,7 +36,7 @@ pub struct Coro {
exception: PyMutex<Option<PyBaseExceptionRef>>, // exc_state
}
fn gen_name(gen: &PyObjectRef, vm: &VirtualMachine) -> &'static str {
fn gen_name(gen: &crate::PyObj, vm: &VirtualMachine) -> &'static str {
let typ = gen.class();
if typ.is(&vm.ctx.types.coroutine_type) {
"coroutine"
@@ -67,7 +67,7 @@ impl Coro {
fn run_with_context<F>(
&self,
gen: &PyObjectRef,
gen: &crate::PyObj,
vm: &VirtualMachine,
func: F,
) -> PyResult<ExecutionResult>
@@ -90,7 +90,7 @@ impl Coro {
pub fn send(
&self,
gen: &PyObjectRef,
gen: &crate::PyObj,
value: PyObjectRef,
vm: &VirtualMachine,
) -> PyResult<PyIterReturn> {
@@ -132,7 +132,7 @@ impl Coro {
}
pub fn throw(
&self,
gen: &PyObjectRef,
gen: &crate::PyObj,
exc_type: PyObjectRef,
exc_val: PyObjectRef,
exc_tb: PyObjectRef,
@@ -146,7 +146,7 @@ impl Coro {
Ok(result?.into_iter_return(vm))
}
pub fn close(&self, gen: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
pub fn close(&self, gen: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if self.closed.load() {
return Ok(());
}
@@ -183,7 +183,7 @@ impl Coro {
pub fn set_name(&self, name: PyStrRef) {
*self.name.lock() = name;
}
pub fn repr(&self, gen: &PyObjectRef, id: usize, vm: &VirtualMachine) -> String {
pub fn repr(&self, gen: &crate::PyObj, id: usize, vm: &VirtualMachine) -> String {
format!(
"<{} object {} at {:#x}>",
gen_name(gen, vm),

View File

@@ -235,7 +235,7 @@ impl<T: Clone> Dict<T> {
/// Store a key
pub fn insert<K>(&self, vm: &VirtualMachine, key: K, value: T) -> PyResult<()>
where
K: DictKey,
K: DictKey + IntoPyObject,
{
let hash = key.key_hash(vm)?;
let _removed = loop {
@@ -337,7 +337,7 @@ impl<T: Clone> Dict<T> {
/// Delete a key
pub fn delete<K>(&self, vm: &VirtualMachine, key: K) -> PyResult<()>
where
K: DictKey,
K: DictKey + IntoPyObject,
{
if self.delete_if_exists(vm, &key)? {
Ok(())
@@ -369,7 +369,7 @@ impl<T: Clone> Dict<T> {
pub fn delete_or_insert(
&self,
vm: &VirtualMachine,
key: &PyObjectRef,
key: &crate::PyObj,
value: T,
) -> PyResult<()> {
let hash = key.key_hash(vm)?;
@@ -384,7 +384,7 @@ impl<T: Clone> Dict<T> {
}
} else {
let mut inner = self.write();
inner.unchecked_push(index_index, hash, key.clone(), value, entry);
inner.unchecked_push(index_index, hash, key.incref(), value, entry);
break None;
}
};
@@ -393,7 +393,7 @@ impl<T: Clone> Dict<T> {
pub fn setdefault<K, F>(&self, vm: &VirtualMachine, key: K, default: F) -> PyResult<T>
where
K: DictKey,
K: DictKey + IntoPyObject,
F: FnOnce() -> T,
{
let hash = key.key_hash(vm)?;
@@ -436,7 +436,7 @@ impl<T: Clone> Dict<T> {
default: F,
) -> PyResult<(PyObjectRef, T)>
where
K: DictKey,
K: DictKey + IntoPyObject,
F: FnOnce() -> T,
{
let hash = key.key_hash(vm)?;
@@ -642,24 +642,53 @@ type LookupResult = (IndexEntry, IndexIndex);
/// the dictionary. Typical usecases are:
/// - PyObjectRef -> arbitrary python type used as key
/// - str -> string reference used as key, this is often used internally
pub trait DictKey: IntoPyObject {
pub trait DictKey {
fn key_hash(&self, vm: &VirtualMachine) -> PyResult<HashValue>;
fn key_is(&self, other: &PyObjectRef) -> bool;
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool>;
fn key_is(&self, other: &crate::PyObj) -> bool;
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool>;
}
/// Implement trait for PyObjectRef such that we can use python objects
/// to index dictionaries.
impl DictKey for PyObjectRef {
#[inline]
fn key_hash(&self, vm: &VirtualMachine) -> PyResult<HashValue> {
(**self).key_hash(vm)
}
#[inline]
fn key_is(&self, other: &crate::PyObj) -> bool {
(**self).key_is(other)
}
#[inline]
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
(**self).key_eq(vm, other_key)
}
}
impl DictKey for &crate::PyObj {
#[inline]
fn key_hash(&self, vm: &VirtualMachine) -> PyResult<HashValue> {
(**self).key_hash(vm)
}
#[inline]
fn key_is(&self, other: &crate::PyObj) -> bool {
(**self).key_is(other)
}
#[inline]
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
(**self).key_eq(vm, other_key)
}
}
impl DictKey for crate::PyObj {
fn key_hash(&self, vm: &VirtualMachine) -> PyResult<HashValue> {
self.hash(vm)
}
fn key_is(&self, other: &PyObjectRef) -> bool {
fn key_is(&self, other: &crate::PyObj) -> bool {
self.is(other)
}
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool> {
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
vm.identical_or_equal(self, other_key)
}
}
@@ -669,11 +698,11 @@ impl DictKey for PyStrRef {
Ok(self.hash(vm))
}
fn key_is(&self, other: &PyObjectRef) -> bool {
fn key_is(&self, other: &crate::PyObj) -> bool {
self.is(other)
}
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool> {
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
if self.is(other_key) {
Ok(true)
} else if let Some(pystr) = str_exact(other_key, vm) {
@@ -688,10 +717,10 @@ impl DictKey for PyRefExact<PyStr> {
fn key_hash(&self, vm: &VirtualMachine) -> PyResult<HashValue> {
(**self).key_hash(vm)
}
fn key_is(&self, other: &PyObjectRef) -> bool {
fn key_is(&self, other: &crate::PyObj) -> bool {
(**self).key_is(other)
}
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool> {
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
(**self).key_eq(vm, other_key)
}
}
@@ -706,13 +735,13 @@ impl DictKey for &str {
Ok(vm.state.hash_secret.hash_str(*self))
}
fn key_is(&self, _other: &PyObjectRef) -> bool {
fn key_is(&self, _other: &crate::PyObj) -> bool {
// No matter who the other pyobject is, we are never the same thing, since
// we are a str, not a pyobject.
false
}
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool> {
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
if let Some(pystr) = str_exact(other_key, vm) {
Ok(pystr.as_str() == *self)
} else {
@@ -728,16 +757,16 @@ impl DictKey for String {
self.as_str().key_hash(vm)
}
fn key_is(&self, other: &PyObjectRef) -> bool {
fn key_is(&self, other: &crate::PyObj) -> bool {
self.as_str().key_is(other)
}
fn key_eq(&self, vm: &VirtualMachine, other_key: &PyObjectRef) -> PyResult<bool> {
fn key_eq(&self, vm: &VirtualMachine, other_key: &crate::PyObj) -> PyResult<bool> {
self.as_str().key_eq(vm, other_key)
}
}
fn str_exact<'a>(obj: &'a PyObjectRef, vm: &VirtualMachine) -> Option<&'a PyStr> {
fn str_exact<'a>(obj: &'a crate::PyObj, vm: &VirtualMachine) -> Option<&'a PyStr> {
if obj.class().is(&vm.ctx.types.str_type) {
obj.payload::<PyStr>()
} else {

View File

@@ -492,7 +492,7 @@ impl PyBaseException {
#[pymethod]
fn with_traceback(zelf: PyRef<Self>, tb: Option<PyTracebackRef>) -> PyResult {
*zelf.traceback.write() = tb;
Ok(zelf.as_object().clone())
Ok(zelf.as_object().incref())
}
#[pymethod(magic)]
@@ -892,7 +892,7 @@ impl serde::Serialize for SerializeException<'_> {
fn serialize<S: serde::Serializer>(&self, s: S) -> Result<S::Ok, S::Error> {
let mut s = s.serialize_seq(None)?;
for tb in self.0.iter() {
s.serialize_element(&*tb)?;
s.serialize_element(&**tb)?;
}
s.end()
}

View File

@@ -875,7 +875,7 @@ impl FormatString {
})
}
pub(crate) fn format_map(&self, dict: &PyObjectRef, vm: &VirtualMachine) -> PyResult<String> {
pub(crate) fn format_map(&self, dict: &crate::PyObj, vm: &VirtualMachine) -> PyResult<String> {
self.format_internal(vm, &mut |field_type| match field_type {
FieldType::Auto | FieldType::Index(_) => {
Err(vm.new_value_error("Format string contains positional fields".to_owned()))

View File

@@ -15,7 +15,7 @@ use crate::{
scope::Scope,
stdlib::builtins,
types::PyComparisonOp,
IdProtocol, ItemProtocol, PyMethod, PyObjectRef, PyObjectWrap, PyRef, PyResult, PyValue,
IdProtocol, ItemProtocol, PyMethod, PyObj, PyObjectRef, PyObjectWrap, PyRef, PyResult, PyValue,
TryFromObject, TypeProtocol, VirtualMachine,
};
use indexmap::IndexMap;
@@ -188,12 +188,12 @@ impl FrameRef {
let fastlocals = self.fastlocals.lock();
for (k, v) in itertools::zip(&map[..j], &**fastlocals) {
if let Some(v) = v {
match locals.as_object().clone().downcast_exact::<PyDict>(vm) {
match locals.as_object().incref().downcast_exact::<PyDict>(vm) {
Ok(d) => d.set_item(k.clone(), v.clone(), vm)?,
Err(o) => o.set_item(k.clone(), v.clone(), vm)?,
};
} else {
let res = match locals.as_object().clone().downcast_exact::<PyDict>(vm) {
let res = match locals.as_object().incref().downcast_exact::<PyDict>(vm) {
Ok(d) => d.del_item(k.clone(), vm),
Err(o) => o.del_item(k.clone(), vm),
};
@@ -209,12 +209,12 @@ impl FrameRef {
let map_to_dict = |keys: &[PyStrRef], values: &[PyCellRef]| {
for (k, v) in itertools::zip(keys, values) {
if let Some(v) = v.get() {
match locals.as_object().clone().downcast_exact::<PyDict>(vm) {
match locals.as_object().incref().downcast_exact::<PyDict>(vm) {
Ok(d) => d.set_item(k.clone(), v, vm)?,
Err(o) => o.set_item(k.clone(), v, vm)?,
};
} else {
let res = match locals.as_object().clone().downcast_exact::<PyDict>(vm) {
let res = match locals.as_object().incref().downcast_exact::<PyDict>(vm) {
Ok(d) => d.del_item(k.clone(), vm),
Err(o) => o.del_item(k.clone(), vm),
};
@@ -268,7 +268,7 @@ impl FrameRef {
}
pub fn yield_from_target(&self) -> Option<PyObjectRef> {
self.with_exec(|exec| exec.yield_from_target().cloned())
self.with_exec(|exec| exec.yield_from_target().map(crate::PyObj::incref))
}
pub fn lasti(&self) -> u32 {
@@ -383,7 +383,7 @@ impl ExecutingFrame<'_> {
}
}
fn yield_from_target(&self) -> Option<&PyObjectRef> {
fn yield_from_target(&self) -> Option<&crate::PyObj> {
if let Some(bytecode::Instruction::YieldFrom) =
self.code.instructions.get(self.lasti() as usize)
{
@@ -409,7 +409,7 @@ impl ExecutingFrame<'_> {
let thrower = if let Some(coro) = self.builtin_coro(gen) {
Some(Either::A(coro))
} else {
vm.get_attribute_opt(gen.clone(), "throw")?.map(Either::B)
vm.get_attribute_opt(gen.incref(), "throw")?.map(Either::B)
};
if let Some(thrower) = thrower {
let ret = match thrower {
@@ -1491,7 +1491,7 @@ impl ExecutingFrame<'_> {
Err(exception)
}
fn builtin_coro<'a>(&self, coro: &'a PyObjectRef) -> Option<&'a Coro> {
fn builtin_coro<'a>(&self, coro: &'a PyObj) -> Option<&'a Coro> {
match_class!(match coro {
ref g @ PyGenerator => Some(g.as_coro()),
ref c @ PyCoroutine => Some(c.as_coro()),
@@ -1501,7 +1501,7 @@ impl ExecutingFrame<'_> {
fn _send(
&self,
gen: &PyObjectRef,
gen: &crate::PyObj,
val: PyObjectRef,
vm: &VirtualMachine,
) -> PyResult<PyIterReturn> {
@@ -1510,7 +1510,7 @@ impl ExecutingFrame<'_> {
// FIXME: turn return type to PyResult<PyIterReturn> then ExecutionResult will be simplified
None if vm.is_none(&val) => PyIter::new(gen).next(vm),
None => {
let meth = gen.clone().get_attr("send", vm)?;
let meth = gen.incref().get_attr("send", vm)?;
PyIterReturn::from_pyresult(vm.invoke(&meth, (val,)), vm)
}
}
@@ -1862,11 +1862,11 @@ impl ExecutingFrame<'_> {
}
fn last_value(&self) -> PyObjectRef {
self.last_value_ref().clone()
self.last_value_ref().incref()
}
#[inline]
fn last_value_ref(&self) -> &PyObjectRef {
fn last_value_ref(&self) -> &crate::PyObj {
match &*self.state.stack {
[.., last] => last,
[] => self.fatal("tried to get top of stack but stack is empty"),

View File

@@ -722,7 +722,7 @@ pub fn single_or_tuple_any<T, F, M>(
where
T: TryFromObject,
F: Fn(&T) -> PyResult<bool>,
M: Fn(&PyObjectRef) -> String,
M: Fn(&crate::PyObj) -> String,
{
match T::try_from_object(vm, obj.clone()) {
Ok(single) => (predicate)(&single),

View File

@@ -17,8 +17,8 @@ impl ArgCallable {
}
}
impl AsRef<PyObjectRef> for ArgCallable {
fn as_ref(&self) -> &PyObjectRef {
impl AsRef<crate::PyObj> for ArgCallable {
fn as_ref(&self) -> &crate::PyObj {
&self.obj
}
}

View File

@@ -2,7 +2,7 @@ use crate::{
builtins::{PyStr, PyStrRef},
common::borrow::{BorrowedValue, BorrowedValueMut},
protocol::PyBuffer,
PyObjectRef, PyResult, TryFromBorrowedObject, TryFromObject, VirtualMachine,
PyObj, PyObjectRef, PyResult, TryFromBorrowedObject, TryFromObject, VirtualMachine,
};
// Python/getargs.c
@@ -11,7 +11,7 @@ use crate::{
#[derive(Debug)]
pub struct ArgBytesLike(PyBuffer);
impl PyObjectRef {
impl PyObj {
pub fn try_bytes_like<R>(
&self,
vm: &VirtualMachine,
@@ -70,7 +70,7 @@ impl From<ArgBytesLike> for PyBuffer {
}
impl TryFromBorrowedObject for ArgBytesLike {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
let buffer = PyBuffer::try_from_borrowed_object(vm, obj)?;
if buffer.options.contiguous {
Ok(Self(buffer))
@@ -112,7 +112,7 @@ impl From<ArgMemoryBuffer> for PyBuffer {
}
impl TryFromBorrowedObject for ArgMemoryBuffer {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
let buffer = PyBuffer::try_from_borrowed_object(vm, obj)?;
if !buffer.options.contiguous {
Err(vm.new_type_error("non-contiguous buffer is not a bytes-like object".to_owned()))

View File

@@ -127,7 +127,7 @@ pub fn import_codeobj(
let attrs = vm.ctx.new_dict();
attrs.set_item("__name__", vm.ctx.new_str(module_name).into(), vm)?;
if set_file_attr {
attrs.set_item("__file__", code_obj.source_path.as_object().clone(), vm)?;
attrs.set_item("__file__", code_obj.source_path.as_object().incref(), vm)?;
}
let module = vm.new_module(module_name, attrs.clone(), None);

View File

@@ -11,7 +11,7 @@ macro_rules! py_module {
macro_rules! extend_module {
( $vm:expr, $module:expr, { $($name:expr => $value:expr),* $(,)? }) => {{
#[allow(unused_variables)]
let module: &$crate::PyObjectRef = &$module;
let module: &$crate::PyObj = &$module;
$(
$vm.__module_set_attr(&module, $name, $value).unwrap();
)*
@@ -205,12 +205,13 @@ macro_rules! flame_guard {
#[macro_export]
macro_rules! class_or_notimplemented {
($t:ty, $obj:expr) => {
match $crate::PyObjectRef::downcast_ref::<$t>($obj) {
($t:ty, $obj:expr) => {{
let a: &$crate::PyObj = &*$obj;
match $crate::PyObj::downcast_ref::<$t>(&a) {
Some(pyref) => pyref,
None => return Ok($crate::PyArithmeticValue::NotImplemented),
}
};
}};
}
#[macro_export]

View File

@@ -3,7 +3,7 @@
use crate::common::borrow::{BorrowedValue, BorrowedValueMut};
use crate::common::rc::PyRc;
use crate::PyThreadingConstraint;
use crate::{PyObjectRef, PyResult, TryFromBorrowedObject, TypeProtocol, VirtualMachine};
use crate::{PyObj, PyObjectRef, PyResult, TryFromBorrowedObject, TypeProtocol, VirtualMachine};
use std::{borrow::Cow, fmt::Debug};
pub trait BufferInternal: Debug + PyThreadingConstraint {
@@ -104,11 +104,11 @@ impl Default for BufferOptions {
}
impl TryFromBorrowedObject for PyBuffer {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self> {
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self> {
let obj_cls = obj.class();
for cls in obj_cls.iter_mro() {
if let Some(f) = cls.slots.as_buffer.as_ref() {
return obj.with_ptr(|obj| f(obj, vm));
return f(obj, vm);
}
}
Err(vm.new_type_error(format!(

View File

@@ -12,10 +12,10 @@ use std::ops::Deref;
#[repr(transparent)]
pub struct PyIter<O = PyObjectRef>(O)
where
O: Borrow<PyObjectRef>;
O: Borrow<crate::PyObj>;
impl PyIter<PyObjectRef> {
pub fn check(obj: &PyObjectRef) -> bool {
pub fn check(obj: &crate::PyObj) -> bool {
obj.class()
.mro_find_map(|x| x.slots.iternext.load())
.is_some()
@@ -24,7 +24,7 @@ impl PyIter<PyObjectRef> {
impl<O> PyIter<O>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
pub fn new(obj: O) -> Self {
Self(obj)
@@ -42,21 +42,21 @@ where
))
})?
};
self.0.borrow().with_ptr(|zelf| iternext(zelf, vm))
iternext(self.0.borrow(), vm)
}
pub fn iter<'a, 'b, U>(
&'b self,
vm: &'a VirtualMachine,
) -> PyResult<PyIterIter<'a, U, &'b PyObjectRef>> {
let length_hint = vm.length_hint(self.as_ref().clone())?;
) -> PyResult<PyIterIter<'a, U, &'b crate::PyObj>> {
let length_hint = vm.length_hint(self.as_ref().incref())?;
Ok(PyIterIter::new(vm, self.0.borrow(), length_hint))
}
pub fn iter_without_hint<'a, 'b, U>(
&'b self,
vm: &'a VirtualMachine,
) -> PyResult<PyIterIter<'a, U, &'b PyObjectRef>> {
) -> PyResult<PyIterIter<'a, U, &'b crate::PyObj>> {
Ok(PyIterIter::new(vm, self.0.borrow(), None))
}
}
@@ -64,7 +64,7 @@ where
impl PyIter<PyObjectRef> {
/// Returns an iterator over this sequence of objects.
pub fn into_iter<U>(self, vm: &VirtualMachine) -> PyResult<PyIterIter<U, PyObjectRef>> {
let length_hint = vm.length_hint(self.as_object().clone())?;
let length_hint = vm.length_hint(self.as_object().incref())?;
Ok(PyIterIter::new(vm, self.0, length_hint))
}
}
@@ -75,20 +75,20 @@ impl PyObjectWrap for PyIter<PyObjectRef> {
}
}
impl<O> AsRef<PyObjectRef> for PyIter<O>
impl<O> AsRef<crate::PyObj> for PyIter<O>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
fn as_ref(&self) -> &PyObjectRef {
fn as_ref(&self) -> &crate::PyObj {
self.0.borrow()
}
}
impl<O> Deref for PyIter<O>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
type Target = PyObjectRef;
type Target = crate::PyObj;
fn deref(&self) -> &Self::Target {
self.0.borrow()
}
@@ -189,7 +189,7 @@ impl IntoPyResult for PyResult<PyIterReturn> {
// Typical rust `Iter` object for `PyIter`
pub struct PyIterIter<'a, T, O = PyObjectRef>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
vm: &'a VirtualMachine,
obj: O, // creating PyIter<O> is zero-cost
@@ -199,7 +199,7 @@ where
impl<'a, T, O> PyIterIter<'a, T, O>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
pub fn new(vm: &'a VirtualMachine, obj: O, length_hint: Option<usize>) -> Self {
Self {
@@ -214,7 +214,7 @@ where
impl<'a, T, O> Iterator for PyIterIter<'a, T, O>
where
T: TryFromObject,
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
type Item = PyResult<T>;

View File

@@ -4,7 +4,8 @@ use crate::{
PyDictRef, PyList,
},
function::IntoPyObject,
IdProtocol, PyObjectRef, PyObjectWrap, PyResult, TryFromObject, TypeProtocol, VirtualMachine,
IdProtocol, PyObj, PyObjectRef, PyObjectWrap, PyResult, TryFromObject, TypeProtocol,
VirtualMachine,
};
use std::borrow::Borrow;
@@ -23,13 +24,13 @@ pub struct PyMappingMethods {
#[repr(transparent)]
pub struct PyMapping<T = PyObjectRef>(T)
where
T: Borrow<PyObjectRef>;
T: Borrow<crate::PyObj>;
impl PyMapping<PyObjectRef> {
pub fn check(obj: &PyObjectRef, vm: &VirtualMachine) -> bool {
pub fn check(obj: &PyObj, vm: &VirtualMachine) -> bool {
obj.class()
.mro_find_map(|x| x.slots.as_mapping.load())
.map(|f| obj.with_ptr(|obj| f(obj, vm)).subscript.is_some())
.map(|f| f(obj, vm).subscript.is_some())
.unwrap_or(false)
}
@@ -37,7 +38,7 @@ impl PyMapping<PyObjectRef> {
let obj_cls = self.0.class();
for cls in obj_cls.iter_mro() {
if let Some(f) = cls.slots.as_mapping.load() {
return self.0.with_ptr(|zelf| f(zelf, vm));
return f(&self.0, vm);
}
}
PyMappingMethods::default()
@@ -46,7 +47,7 @@ impl PyMapping<PyObjectRef> {
impl<T> PyMapping<T>
where
T: Borrow<PyObjectRef>,
T: Borrow<crate::PyObj>,
{
pub fn new(obj: T) -> Self {
Self(obj)
@@ -55,7 +56,7 @@ where
pub fn keys(&self, vm: &VirtualMachine) -> PyResult {
if self.0.borrow().is(&vm.ctx.types.dict_type) {
Ok(
PyDictKeys::new(PyDictRef::try_from_object(vm, self.0.borrow().clone())?)
PyDictKeys::new(PyDictRef::try_from_object(vm, self.0.borrow().incref())?)
.into_pyobject(vm),
)
} else {
@@ -66,7 +67,7 @@ where
pub fn values(&self, vm: &VirtualMachine) -> PyResult {
if self.0.borrow().is(&vm.ctx.types.dict_type) {
Ok(
PyDictValues::new(PyDictRef::try_from_object(vm, self.0.borrow().clone())?)
PyDictValues::new(PyDictRef::try_from_object(vm, self.0.borrow().incref())?)
.into_pyobject(vm),
)
} else {
@@ -75,7 +76,7 @@ where
}
fn method_output_as_list(
obj: &PyObjectRef,
obj: &crate::PyObj,
method_name: &str,
vm: &VirtualMachine,
) -> PyResult {
@@ -103,11 +104,11 @@ impl PyObjectWrap for PyMapping<PyObjectRef> {
}
}
impl<O> AsRef<PyObjectRef> for PyMapping<O>
impl<O> AsRef<crate::PyObj> for PyMapping<O>
where
O: Borrow<PyObjectRef>,
O: Borrow<crate::PyObj>,
{
fn as_ref(&self) -> &PyObjectRef {
fn as_ref(&self) -> &crate::PyObj {
self.0.borrow()
}
}

View File

@@ -10,7 +10,7 @@ use crate::{
pyref_type_error,
types::{Constructor, PyComparisonOp},
utils::Either,
IdProtocol, PyArithmeticValue, PyObjectRef, PyResult, TryFromObject, TypeProtocol,
IdProtocol, PyArithmeticValue, PyObj, PyObjectRef, PyResult, TryFromObject, TypeProtocol,
VirtualMachine,
};
@@ -40,6 +40,66 @@ impl PyObjectRef {
})
}
// PyObject *PyObject_GenericGetDict(PyObject *o, void *context)
// int PyObject_GenericSetDict(PyObject *o, PyObject *value, void *context)
pub fn rich_compare(self, other: Self, opid: PyComparisonOp, vm: &VirtualMachine) -> PyResult {
self._cmp(&other, opid, vm).map(|res| res.into_pyobject(vm))
}
pub fn bytes(self, vm: &VirtualMachine) -> PyResult {
let bytes_type = &vm.ctx.types.bytes_type;
match self.downcast_exact::<PyInt>(vm) {
Ok(int) => Err(pyref_type_error(vm, bytes_type, int.as_object())),
Err(obj) => PyBytes::py_new(
bytes_type.clone(),
ByteInnerNewOptions {
source: OptionalArg::Present(obj),
encoding: OptionalArg::Missing,
errors: OptionalArg::Missing,
},
vm,
),
}
}
// const hash_not_implemented: fn(&crate::PyObj, &VirtualMachine) ->PyResult<PyHash> = crate::types::Unhashable::slot_hash;
pub fn is_true(self, vm: &VirtualMachine) -> PyResult<bool> {
self.try_to_bool(vm)
}
pub fn not(self, vm: &VirtualMachine) -> PyResult<bool> {
self.is_true(vm).map(|x| !x)
}
pub fn length_hint(
self,
defaultvalue: Option<usize>,
vm: &VirtualMachine,
) -> PyResult<Option<usize>> {
Ok(vm.length_hint(self)?.or(defaultvalue))
}
// item protocol
// PyObject *PyObject_GetItem(PyObject *o, PyObject *key)
// int PyObject_SetItem(PyObject *o, PyObject *key, PyObject *v)
// int PyObject_DelItem(PyObject *o, PyObject *key)
// PyObject *PyObject_Dir(PyObject *o)
/// Takes an object and returns an iterator for it.
/// This is typically a new iterator but if the argument is an iterator, this
/// returns itself.
pub fn get_iter(self, vm: &VirtualMachine) -> PyResult<PyIter> {
// PyObject_GetIter
PyIter::try_from_object(vm, self)
}
// PyObject *PyObject_GetAIter(PyObject *o)
}
impl PyObj {
pub fn call_set_attr(
&self,
vm: &VirtualMachine,
@@ -61,7 +121,7 @@ impl PyObjectRef {
))
})?
};
self.with_ptr(|zelf| setattro(zelf, attr_name, attr_value, vm))
setattro(self, attr_name, attr_value, vm)
}
// PyObject *PyObject_GenericGetAttr(PyObject *o, PyObject *name)
@@ -93,12 +153,12 @@ impl PyObjectRef {
vm: &VirtualMachine,
) -> PyResult<Either<PyObjectRef, bool>> {
let swapped = op.swapped();
let call_cmp = |obj: &PyObjectRef, other: &PyObjectRef, op| {
let call_cmp = |obj: &crate::PyObj, other: &crate::PyObj, op| {
let cmp = obj
.class()
.mro_find_map(|cls| cls.slots.richcompare.load())
.unwrap();
let r = match obj.with_ptr(|obj| other.with_ptr(|other| cmp(obj, other, op, vm)))? {
let r = match cmp(obj, other, op, vm)? {
Either::A(obj) => PyArithmeticValue::from_object(vm, obj).map(Either::A),
Either::B(arithmetic) => arithmetic.map(Either::B),
};
@@ -135,14 +195,6 @@ impl PyObjectRef {
_ => Err(vm.new_unsupported_binop_error(self, other, op.operator_token())),
}
}
// PyObject *PyObject_GenericGetDict(PyObject *o, void *context)
// int PyObject_GenericSetDict(PyObject *o, PyObject *value, void *context)
pub fn rich_compare(self, other: Self, opid: PyComparisonOp, vm: &VirtualMachine) -> PyResult {
self._cmp(&other, opid, vm).map(|res| res.into_pyobject(vm))
}
pub fn rich_compare_bool(
&self,
other: &Self,
@@ -168,36 +220,20 @@ impl PyObjectRef {
// Container of the virtual machine state:
pub fn str(&self, vm: &VirtualMachine) -> PyResult<PyStrRef> {
if self.class().is(&vm.ctx.types.str_type) {
Ok(self.clone().downcast().unwrap())
Ok(self.incref().downcast().unwrap())
} else {
let s = vm.call_special_method(self.clone(), "__str__", ())?;
let s = vm.call_special_method(self.incref(), "__str__", ())?;
s.try_into_value(vm)
}
}
pub fn bytes(self, vm: &VirtualMachine) -> PyResult {
let bytes_type = &vm.ctx.types.bytes_type;
match self.downcast_exact::<PyInt>(vm) {
Ok(int) => Err(pyref_type_error(vm, bytes_type, int.as_object())),
Err(obj) => PyBytes::py_new(
bytes_type.clone(),
ByteInnerNewOptions {
source: OptionalArg::Present(obj),
encoding: OptionalArg::Missing,
errors: OptionalArg::Missing,
},
vm,
),
}
}
pub fn is_subclass(&self, cls: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
pub fn is_subclass(&self, cls: &crate::PyObj, vm: &VirtualMachine) -> PyResult<bool> {
vm.issubclass(self, cls)
}
/// Determines if `self` is an instance of `cls`, either directly, indirectly or virtually via
/// the __instancecheck__ magic method.
pub fn is_instance(&self, cls: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
pub fn is_instance(&self, cls: &crate::PyObj, vm: &VirtualMachine) -> PyResult<bool> {
// cpython first does an exact check on the type, although documentation doesn't state that
// https://github.com/python/cpython/blob/a24107b04c1277e3c1105f98aff5bfa3a98b33a0/Objects/abstract.c#L2408
if self.class().is(cls) {
@@ -208,7 +244,7 @@ impl PyObjectRef {
return vm.abstract_isinstance(self, cls);
}
if let Ok(tuple) = PyTupleRef::try_from_object(vm, cls.clone()) {
if let Ok(tuple) = PyTupleRef::try_from_object(vm, cls.incref()) {
for typ in tuple.as_slice().iter() {
if vm.with_recursion("in __instancecheck__", || self.is_instance(typ, vm))? {
return Ok(true);
@@ -217,9 +253,9 @@ impl PyObjectRef {
return Ok(false);
}
if let Ok(meth) = vm.get_special_method(cls.clone(), "__instancecheck__")? {
if let Ok(meth) = vm.get_special_method(cls.incref(), "__instancecheck__")? {
let ret =
vm.with_recursion("in __instancecheck__", || meth.invoke((self.clone(),), vm))?;
vm.with_recursion("in __instancecheck__", || meth.invoke((self.incref(),), vm))?;
return ret.try_to_bool(vm);
}
@@ -231,17 +267,7 @@ impl PyObjectRef {
.class()
.mro_find_map(|cls| cls.slots.hash.load())
.unwrap(); // hash always exist
self.with_ptr(|zelf| hash(zelf, vm))
}
// const hash_not_implemented: fn(&PyObjectRef, &VirtualMachine) ->PyResult<PyHash> = crate::types::Unhashable::slot_hash;
pub fn is_true(self, vm: &VirtualMachine) -> PyResult<bool> {
self.try_to_bool(vm)
}
pub fn not(self, vm: &VirtualMachine) -> PyResult<bool> {
self.is_true(vm).map(|x| !x)
hash(self, vm)
}
// type protocol
@@ -257,29 +283,4 @@ impl PyObjectRef {
)))
})
}
pub fn length_hint(
self,
defaultvalue: Option<usize>,
vm: &VirtualMachine,
) -> PyResult<Option<usize>> {
Ok(vm.length_hint(self)?.or(defaultvalue))
}
// item protocol
// PyObject *PyObject_GetItem(PyObject *o, PyObject *key)
// int PyObject_SetItem(PyObject *o, PyObject *key, PyObject *v)
// int PyObject_DelItem(PyObject *o, PyObject *key)
// PyObject *PyObject_Dir(PyObject *o)
/// Takes an object and returns an iterator for it.
/// This is typically a new iterator but if the argument is an iterator, this
/// returns itself.
pub fn get_iter(self, vm: &VirtualMachine) -> PyResult<PyIter> {
// PyObject_GetIter
PyIter::try_from_object(vm, self)
}
// PyObject *PyObject_GetAIter(PyObject *o)
}

View File

@@ -59,7 +59,7 @@ impl Write for PyWriter<'_> {
}
}
pub fn file_readline(obj: &PyObjectRef, size: Option<usize>, vm: &VirtualMachine) -> PyResult {
pub fn file_readline(obj: &crate::PyObj, size: Option<usize>, vm: &VirtualMachine) -> PyResult {
let args = size.map_or_else(Vec::new, |size| vec![vm.ctx.new_int(size).into()]);
let ret = vm.call_method(obj, "readline", args)?;
let eof_err = || {

View File

@@ -4,13 +4,12 @@ use serde::de::{DeserializeSeed, Visitor};
use serde::ser::{Serialize, SerializeMap, SerializeSeq};
use crate::builtins::{dict::PyDictRef, float, int, list::PyList, pybool, tuple::PyTuple, PyStr};
use crate::VirtualMachine;
use crate::{ItemProtocol, PyObjectRef, TypeProtocol};
use crate::{ItemProtocol, PyObj, PyObjectRef, TypeProtocol, VirtualMachine};
#[inline]
pub fn serialize<S>(
vm: &VirtualMachine,
pyobject: &PyObjectRef,
pyobject: &crate::PyObj,
serializer: S,
) -> Result<S::Ok, S::Error>
where
@@ -33,7 +32,7 @@ where
// We need to have a VM available to serialise a PyObject based on its subclass, so we implement
// PyObject serialisation via a proxy object which holds a reference to a VM
pub struct PyObjectSerializer<'s> {
pyobject: &'s PyObjectRef,
pyobject: &'s PyObj,
vm: &'s VirtualMachine,
}
@@ -86,7 +85,7 @@ impl<'s> serde::Serialize for PyObjectSerializer<'s> {
} else if let Some(tuple) = self.pyobject.payload_if_subclass::<PyTuple>(self.vm) {
serialize_seq_elements(serializer, tuple.as_slice())
} else if self.pyobject.isinstance(&self.vm.ctx.types.dict_type) {
let dict: PyDictRef = self.pyobject.clone().downcast().unwrap();
let dict: PyDictRef = self.pyobject.incref().downcast().unwrap();
let pairs: Vec<_> = dict.into_iter().collect();
let mut map = serializer.serialize_map(Some(pairs.len()))?;
for (key, e) in pairs.iter() {

View File

@@ -4,7 +4,7 @@ use crate::common::{
static_cell,
};
pub use crate::pyobjectrc::{
PyObject, PyObjectPtr, PyObjectRef, PyObjectWeak, PyObjectWrap, PyRef, PyWeakRef,
Py, PyObj, PyObject, PyObjectRef, PyObjectWeak, PyObjectWrap, PyRef, PyWeakRef,
};
use crate::{
builtins::{
@@ -53,8 +53,13 @@ pub type PyResult<T = PyObjectRef> = Result<T, PyBaseExceptionRef>; // A valid v
/// TODO: class attributes should maintain insertion order (use IndexMap here)
pub type PyAttributes = HashMap<String, PyObjectRef, ahash::RandomState>;
// TODO: remove this impl
// TODO: remove these 2 impls
impl fmt::Display for PyObjectRef {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
(**self).fmt(f)
}
}
impl fmt::Display for PyObj {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "'{}' object", self.class().name())
}
@@ -305,7 +310,7 @@ impl Default for PyContext {
pub(crate) fn try_value_from_borrowed_object<T, F, R>(
vm: &VirtualMachine,
obj: &PyObjectRef,
obj: &PyObj,
f: F,
) -> PyResult<R>
where
@@ -340,11 +345,11 @@ where
}
}
}
// the impl Borrow allows to pass PyObjectRef or &PyObjectRef
// the impl Borrow allows to pass PyObjectRef or &PyObj
fn pyref_payload_error(
vm: &VirtualMachine,
class: &PyTypeRef,
obj: impl std::borrow::Borrow<PyObjectRef>,
obj: impl std::borrow::Borrow<PyObj>,
) -> PyBaseExceptionRef {
vm.new_runtime_error(format!(
"Unexpected payload '{}' for type '{}'",
@@ -356,7 +361,7 @@ fn pyref_payload_error(
pub(crate) fn pyref_type_error(
vm: &VirtualMachine,
class: &PyTypeRef,
obj: impl std::borrow::Borrow<PyObjectRef>,
obj: impl std::borrow::Borrow<PyObj>,
) -> PyBaseExceptionRef {
let expected_type = &*class.name();
let actual_class = obj.borrow().class();
@@ -375,6 +380,14 @@ where
fmt::Display::fmt(&**self, f)
}
}
impl<T: fmt::Display> fmt::Display for Py<T>
where
T: PyObjectPayload + fmt::Display,
{
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fmt::Display::fmt(&**self, f)
}
}
pub struct PyRefExact<T: PyObjectPayload> {
obj: PyRef<T>,
@@ -439,6 +452,12 @@ impl<T: PyObjectPayload> IdProtocol for PyRef<T> {
}
}
impl<T: PyObjectPayload> IdProtocol for Py<T> {
fn get_id(&self) -> usize {
self.as_object().get_id()
}
}
impl<'a, T: PyObjectPayload> IdProtocol for PyLease<'a, T> {
fn get_id(&self) -> usize {
self.inner.get_id()
@@ -500,7 +519,7 @@ pub trait TypeProtocol {
/// Determines if `obj` actually an instance of `cls`, this doesn't call __instancecheck__, so only
/// use this if `cls` is known to have not overridden the base __instancecheck__ magic method.
#[inline]
fn isinstance(&self, cls: &PyTypeRef) -> bool {
fn isinstance(&self, cls: &Py<PyType>) -> bool {
self.class().issubclass(cls)
}
}
@@ -513,6 +532,20 @@ impl TypeProtocol for PyObjectRef {
}
}
impl TypeProtocol for PyObj {
fn class(&self) -> PyLease<'_, PyType> {
PyLease {
inner: self.class_lock().read(),
}
}
}
impl<T: PyObjectPayload> TypeProtocol for Py<T> {
fn class(&self) -> PyLease<'_, PyType> {
self.as_object().class()
}
}
impl<T: PyObjectPayload> TypeProtocol for PyRef<T> {
fn class(&self) -> PyLease<'_, PyType> {
self.as_object().class()
@@ -536,18 +569,18 @@ where
fn del_item(&self, key: T, vm: &VirtualMachine) -> PyResult<()>;
}
impl<T> ItemProtocol<T> for PyObjectRef
impl<T> ItemProtocol<T> for PyObj
where
T: IntoPyObject,
{
fn get_item(&self, key: T, vm: &VirtualMachine) -> PyResult {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.clone()) {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.incref()) {
if let Some(getitem) = mapping.methods(vm).subscript {
return getitem(self.clone(), key.into_pyobject(vm), vm);
return getitem(self.incref(), key.into_pyobject(vm), vm);
}
}
match vm.get_special_method(self.clone(), "__getitem__")? {
match vm.get_special_method(self.incref(), "__getitem__")? {
Ok(special_method) => return special_method.invoke((key,), vm),
Err(obj) => {
if obj.isinstance(&vm.ctx.types.type_type) {
@@ -564,13 +597,13 @@ where
}
fn set_item(&self, key: T, value: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.clone()) {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.incref()) {
if let Some(setitem) = mapping.methods(vm).ass_subscript {
return setitem(self.clone(), key.into_pyobject(vm), Some(value), vm);
return setitem(self.incref(), key.into_pyobject(vm), Some(value), vm);
}
}
vm.get_special_method(self.clone(), "__setitem__")?
vm.get_special_method(self.incref(), "__setitem__")?
.map_err(|obj| {
vm.new_type_error(format!(
"'{}' does not support item assignment",
@@ -582,13 +615,13 @@ where
}
fn del_item(&self, key: T, vm: &VirtualMachine) -> PyResult<()> {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.clone()) {
if let Ok(mapping) = PyMapping::try_from_object(vm, self.incref()) {
if let Some(setitem) = mapping.methods(vm).ass_subscript {
return setitem(self.clone(), key.into_pyobject(vm), None, vm);
return setitem(self.incref(), key.into_pyobject(vm), None, vm);
}
}
vm.get_special_method(self.clone(), "__delitem__")?
vm.get_special_method(self.incref(), "__delitem__")?
.map_err(|obj| {
vm.new_type_error(format!(
"'{}' does not support item deletion",
@@ -635,7 +668,7 @@ impl<T: TryFromBorrowedObject> TryFromObject for T {
pub trait TryFromBorrowedObject: Sized {
/// Attempt to convert a Python object to a value of this type.
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<Self>;
fn try_from_borrowed_object(vm: &VirtualMachine, obj: &PyObj) -> PyResult<Self>;
}
impl PyObjectRef {
@@ -661,11 +694,11 @@ impl PyObjectRef {
/// Can only be implemented for types that are `repr(transparent)` over a PyObjectRef `obj`,
/// and logically valid so long as `check(vm, obj)` returns `Ok(())`
pub unsafe trait TransmuteFromObject: Sized {
fn check(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<()>;
fn check(vm: &VirtualMachine, obj: &crate::PyObj) -> PyResult<()>;
}
unsafe impl<T: PyValue> TransmuteFromObject for PyRef<T> {
fn check(vm: &VirtualMachine, obj: &PyObjectRef) -> PyResult<()> {
fn check(vm: &VirtualMachine, obj: &crate::PyObj) -> PyResult<()> {
let class = T::class(vm);
if obj.isinstance(class) {
if obj.payload_is::<T>() {
@@ -706,6 +739,13 @@ impl IntoPyObject for PyObjectRef {
}
}
impl IntoPyObject for &PyObj {
#[inline]
fn into_pyobject(self, _vm: &VirtualMachine) -> PyObjectRef {
self.incref()
}
}
// Allows a built-in function to return any built-in object payload without
// explicitly implementing `IntoPyObject`.
impl<T> IntoPyObject for T
@@ -755,7 +795,7 @@ pub trait PyValue: fmt::Debug + PyThreadingConstraint + Sized + 'static {
}
#[inline(always)]
fn special_retrieve(_vm: &VirtualMachine, _obj: &PyObjectRef) -> Option<PyResult<PyRef<Self>>> {
fn special_retrieve(_vm: &VirtualMachine, _obj: &PyObj) -> Option<PyResult<PyRef<Self>>> {
None
}
@@ -934,7 +974,7 @@ pub trait PyStructSequence: StaticType + PyClassImpl + Sized + 'static {
#[pymethod(magic)]
fn repr(zelf: PyRef<PyTuple>, vm: &VirtualMachine) -> PyResult<String> {
let format_field = |(value, name)| {
let format_field = |(value, name): (&PyObjectRef, _)| {
let s = vm.to_repr(value)?;
Ok(format!("{}={}", name, s))
};

View File

@@ -7,8 +7,8 @@ use crate::{
IdProtocol, PyObjectPayload, TypeProtocol, VirtualMachine,
};
use std::any::TypeId;
use std::borrow::Borrow;
use std::fmt;
use std::marker::PhantomData;
use std::mem::ManuallyDrop;
use std::ops::Deref;
@@ -122,8 +122,6 @@ impl<T> Drop for PyObject<T> {
}
}
type PyObjectRefInner = PyObject<Erased>;
/// The `PyObjectRef` is one of the most used types. It is a reference to a
/// python object. A single python object can have multiple references, and
/// this reference counting is accounted for by this type. Use the `.clone()`
@@ -132,36 +130,51 @@ type PyObjectRefInner = PyObject<Erased>;
#[derive(Clone)]
#[repr(transparent)]
pub struct PyObjectRef {
rc: PyRc<PyObjectRefInner>,
rc: PyRc<PyObj>,
}
#[derive(Clone)]
#[repr(transparent)]
pub struct PyObjectWeak {
weak: PyWeak<PyObjectRefInner>,
weak: PyWeak<PyObj>,
}
#[repr(transparent)]
pub struct PyObj(PyObject<Erased>);
impl Deref for PyObjectRef {
type Target = PyObj;
fn deref(&self) -> &PyObj {
&self.rc
}
}
impl ToOwned for PyObj {
type Owned = PyObjectRef;
#[inline]
fn to_owned(&self) -> Self::Owned {
self.incref()
}
}
pub trait PyObjectWrap
where
Self: AsRef<PyObjectRef>,
Self: AsRef<crate::PyObj>,
{
#[inline(always)]
fn as_object(&self) -> &PyObjectRef {
fn as_object(&self) -> &crate::PyObj {
self.as_ref()
}
fn into_object(self) -> PyObjectRef;
}
/// A marker type that just references a raw python object. Don't use directly, pass as a pointer
/// back to [`PyObjectRef::from_raw`]
pub enum RawPyObject {}
impl PyObjectRef {
pub fn into_raw(this: Self) -> *const RawPyObject {
let ptr = PyRc::as_ptr(&this.rc);
std::mem::forget(this);
ptr.cast()
pub fn into_raw(self) -> *const PyObj {
let ptr = self.as_raw();
std::mem::forget(self);
ptr
}
/// # Safety
@@ -169,48 +182,18 @@ impl PyObjectRef {
/// [`PyObjectRef::into_raw`]. The user is responsible for ensuring that the inner data is not
/// dropped more than once due to mishandling the reference count by calling this function
/// too many times.
pub unsafe fn from_raw(ptr: *const RawPyObject) -> Self {
pub unsafe fn from_raw(ptr: *const PyObj) -> Self {
Self {
rc: PyRc::from_raw(ptr.cast()),
}
}
fn new<T: PyObjectPayload>(value: PyObject<T>) -> Self {
let inner = PyRc::into_raw(PyRc::new(value));
let rc = unsafe { PyRc::from_raw(inner as *const PyObjectRefInner) };
let inner: *const PyObject<T> = PyRc::into_raw(PyRc::new(value));
let rc = unsafe { PyRc::from_raw(inner as *const PyObj) };
Self { rc }
}
pub fn strong_count(this: &Self) -> usize {
PyRc::strong_count(&this.rc)
}
pub fn weak_count(this: &Self) -> usize {
PyRc::weak_count(&this.rc)
}
pub fn downgrade(this: &Self) -> PyObjectWeak {
PyObjectWeak {
weak: PyRc::downgrade(&this.rc),
}
}
pub fn payload_is<T: PyObjectPayload>(&self) -> bool {
self.rc.inner.typeid == TypeId::of::<T>()
}
pub fn payload<T: PyObjectPayload>(&self) -> Option<&T> {
if self.payload_is::<T>() {
// we cast to a PyInner<T> first because we don't know T's exact offset because of
// varying alignment, but once we get a PyInner<T> the compiler can get it for us
let inner =
unsafe { &*(&*self.rc.inner as *const PyInner<Erased> as *const PyInner<T>) };
Some(&inner.payload)
} else {
None
}
}
/// Attempt to downcast this reference to a subclass.
///
/// If the downcast fails, the original ref is returned in as `Err` so
@@ -223,7 +206,7 @@ impl PyObjectRef {
}
}
pub fn downcast_ref<T: PyObjectPayload>(&self) -> Option<&PyRef<T>> {
pub fn downcast_ref<T: PyObjectPayload>(&self) -> Option<&crate::Py<T>> {
if self.payload_is::<T>() {
// SAFETY: just checked that the payload is T, and PyRef is repr(transparent) over
// PyObjectRef
@@ -241,15 +224,11 @@ impl PyObjectRef {
/// # Safety
/// T must be the exact payload type
pub unsafe fn downcast_unchecked_ref<T: PyObjectPayload>(&self) -> &PyRef<T> {
pub unsafe fn downcast_unchecked_ref<T: PyObjectPayload>(&self) -> &crate::Py<T> {
debug_assert!(self.payload_is::<T>());
&*(self as *const PyObjectRef as *const PyRef<T>)
}
pub(crate) fn class_lock(&self) -> &PyRwLock<PyTypeRef> {
&self.rc.inner.typ
}
// ideally we'd be able to define these in pyobject.rs, but method visibility rules are weird
/// Attempt to downcast this reference to the specific class that is associated `T`.
@@ -272,6 +251,47 @@ impl PyObjectRef {
Err(self)
}
}
}
impl PyObj {
#[inline(always)]
pub fn incref(&self) -> PyObjectRef {
self.with_pyobjectref(Clone::clone)
}
#[inline]
fn with_pyobjectref<R>(&self, f: impl FnOnce(&PyObjectRef) -> R) -> R {
// SAFETY: we don't use obj after the real lifetime (self) goes out of scope, we wrap it
// in a ManuallyDrop to prevent double free, and we only pass it by reference
let obj = unsafe { ManuallyDrop::new(PyObjectRef::from_raw(self)) };
f(&obj)
}
pub fn downgrade(&self) -> PyObjectWeak {
PyObjectWeak {
weak: self.with_pyobjectref(|obj| PyRc::downgrade(&obj.rc)),
}
}
pub fn payload_is<T: PyObjectPayload>(&self) -> bool {
self.0.inner.typeid == TypeId::of::<T>()
}
pub fn payload<T: PyObjectPayload>(&self) -> Option<&T> {
if self.payload_is::<T>() {
// we cast to a PyInner<T> first because we don't know T's exact offset because of
// varying alignment, but once we get a PyInner<T> the compiler can get it for us
let inner =
unsafe { &*(&*self.0.inner as *const PyInner<Erased> as *const PyInner<T>) };
Some(&inner.payload)
} else {
None
}
}
pub(crate) fn class_lock(&self) -> &PyRwLock<PyTypeRef> {
&self.0.inner.typ
}
#[inline]
pub fn payload_if_exact<T: PyObjectPayload + crate::PyValue>(
@@ -286,12 +306,12 @@ impl PyObjectRef {
}
pub fn dict(&self) -> Option<PyDictRef> {
self.rc.inner.dict.as_ref().map(|mu| mu.read().clone())
self.0.inner.dict.as_ref().map(|mu| mu.read().clone())
}
/// Set the dict field. Returns `Err(dict)` if this object does not have a dict field
/// in the first place.
pub fn set_dict(&self, dict: PyDictRef) -> Result<(), PyDictRef> {
match self.rc.inner.dict {
match self.0.inner.dict {
Some(ref mu) => {
*mu.write() = dict;
Ok(())
@@ -309,20 +329,53 @@ impl PyObjectRef {
}
}
#[inline]
pub fn with_ptr<'a, F, R>(&'a self, f: F) -> R
where
F: FnOnce(PyObjectPtr<'a>) -> R,
{
unsafe {
// SAFETY: self will be alive until f is done
f(PyObjectPtr::new(self))
pub fn downcast_ref<T: PyObjectPayload>(&self) -> Option<&crate::Py<T>> {
if self.payload_is::<T>() {
// SAFETY: just checked that the payload is T, and PyRef is repr(transparent) over
// PyObjectRef
Some(unsafe { &*(self as *const PyObj as *const Py<T>) })
} else {
None
}
}
/// # Safety
/// T must be the exact payload type
pub unsafe fn downcast_unchecked_ref<T: PyObjectPayload>(&self) -> &crate::Py<T> {
debug_assert!(self.payload_is::<T>());
&*(self as *const PyObj as *const Py<T>)
}
#[inline]
pub fn strong_count(&self) -> usize {
self.with_pyobjectref(|obj| PyRc::strong_count(&obj.rc))
}
#[inline]
pub fn weak_count(&self) -> usize {
self.with_pyobjectref(|obj| PyRc::weak_count(&obj.rc))
}
#[inline]
pub fn as_raw(&self) -> *const PyObj {
self
}
}
impl AsRef<Self> for PyObjectRef {
fn as_ref(&self) -> &Self {
impl Borrow<PyObj> for PyObjectRef {
fn borrow(&self) -> &PyObj {
self
}
}
impl AsRef<PyObj> for PyObjectRef {
fn as_ref(&self) -> &PyObj {
self
}
}
impl AsRef<PyObj> for PyObj {
fn as_ref(&self) -> &PyObj {
self
}
}
@@ -333,9 +386,15 @@ impl IdProtocol for PyObjectRef {
}
}
impl<'a, T: PyObjectPayload> From<&'a PyRef<T>> for &'a PyObjectRef {
fn from(py_ref: &'a PyRef<T>) -> Self {
&py_ref.obj
impl IdProtocol for PyObj {
fn get_id(&self) -> usize {
self as *const PyObj as usize
}
}
impl<'a, T: PyObjectPayload> From<&'a Py<T>> for &'a PyObj {
fn from(py_ref: &'a Py<T>) -> Self {
py_ref.as_object()
}
}
@@ -365,7 +424,7 @@ impl Drop for PyObjectRef {
let zelf = self.clone();
if let Some(slot_del) = self.class().mro_find_map(|cls| cls.slots.del.load()) {
let ret = crate::vm::thread::with_vm(&zelf, |vm| {
if let Err(e) = zelf.with_ptr(|zelf| slot_del(zelf, vm)) {
if let Err(e) = slot_del(&zelf, vm) {
print_del_error(e, &zelf, vm);
}
});
@@ -380,7 +439,7 @@ impl Drop for PyObjectRef {
}
#[cold]
fn print_del_error(e: PyBaseExceptionRef, zelf: &PyObjectRef, vm: &VirtualMachine) {
fn print_del_error(e: PyBaseExceptionRef, zelf: &crate::PyObj, vm: &VirtualMachine) {
// exception in del will be ignored but printed
print!("Exception ignored in: ",);
let del_method = zelf.get_class_attr("__del__").unwrap();
@@ -403,7 +462,8 @@ impl fmt::Debug for PyObjectRef {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
// SAFETY: the vtable contains functions that accept payload types that always match up
// with the payload of the object
unsafe { (self.rc.inner.vtable.debug)(&*self.rc.inner, f) }
let inner = &*self.rc.0.inner;
unsafe { (inner.vtable.debug)(inner, f) }
}
}
@@ -413,6 +473,65 @@ impl fmt::Debug for PyObjectWeak {
}
}
#[repr(transparent)]
pub struct Py<T: PyObjectPayload>(PyInner<T>);
impl<T: PyObjectPayload> Py<T> {
pub fn incref(&self) -> PyRef<T> {
self.with_pyref(Clone::clone)
}
#[inline(always)]
pub fn as_object(&self) -> &PyObj {
unsafe { &*(&self.0 as *const PyInner<T> as *const PyObj) }
}
#[inline]
fn with_pyref<R>(&self, f: impl FnOnce(&PyRef<T>) -> R) -> R {
// SAFETY: we don't use obj after the real lifetime (self) goes out of scope, we wrap it
// in a ManuallyDrop to prevent double free, and we only pass it by reference
let obj = unsafe { ManuallyDrop::new(PyRef::from_raw(self)) };
f(&obj)
}
pub fn downgrade(&self) -> PyWeakRef<T> {
self.with_pyref(|r| PyWeakRef {
weak: PyRc::downgrade(&r.obj),
})
}
}
impl<T: PyObjectPayload> ToOwned for Py<T> {
type Owned = PyRef<T>;
fn to_owned(&self) -> Self::Owned {
self.incref()
}
}
impl<T: PyObjectPayload> Deref for Py<T> {
type Target = T;
fn deref(&self) -> &Self::Target {
&self.0.payload
}
}
impl<T> AsRef<crate::PyObj> for Py<T>
where
T: PyObjectPayload,
{
fn as_ref(&self) -> &PyObj {
self.as_object()
}
}
impl<T: PyObjectPayload> fmt::Debug for Py<T> {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
(**self).fmt(f)
}
}
/// A reference to a Python object.
///
/// Note that a `PyRef<T>` can only deref to a shared / immutable reference.
@@ -425,8 +544,7 @@ impl fmt::Debug for PyObjectWeak {
#[repr(transparent)]
pub struct PyRef<T: PyObjectPayload> {
// invariant: this obj must always have payload of type T
obj: PyObjectRef,
_payload: PhantomData<PyRc<T>>,
obj: PyRc<Py<T>>,
}
impl<T: PyObjectPayload> fmt::Debug for PyRef<T> {
@@ -439,31 +557,22 @@ impl<T: PyObjectPayload> Clone for PyRef<T> {
fn clone(&self) -> Self {
Self {
obj: self.obj.clone(),
_payload: PhantomData,
}
}
}
impl<T: PyObjectPayload> PyRef<T> {
unsafe fn from_raw(raw: *const Py<T>) -> Self {
Self {
obj: PyRc::from_raw(raw),
}
}
/// Safety: payload type of `obj` must be `T`
unsafe fn from_obj_unchecked(obj: PyObjectRef) -> Self {
debug_assert!(obj.payload_is::<T>());
Self {
obj,
_payload: PhantomData,
}
}
#[inline(always)]
pub fn as_object(&self) -> &PyObjectRef {
&self.obj
}
pub fn downgrade(this: &Self) -> PyWeakRef<T> {
PyWeakRef {
weak: PyObjectRef::downgrade(&this.obj),
_payload: PhantomData,
}
let obj = PyRc::from_raw(obj.into_raw() as *const Py<T>);
Self { obj }
}
// ideally we'd be able to define this in pyobject.rs, but method visibility rules are weird
@@ -483,16 +592,25 @@ where
T: PyObjectPayload,
{
fn into_object(self) -> PyObjectRef {
self.obj
unsafe { PyObjectRef::from_raw(PyRc::into_raw(self.obj) as *const PyObj) }
}
}
impl<T> AsRef<PyObjectRef> for PyRef<T>
impl<T> AsRef<crate::PyObj> for PyRef<T>
where
T: PyObjectPayload,
{
fn as_ref(&self) -> &PyObjectRef {
&self.obj
fn as_ref(&self) -> &crate::PyObj {
(**self).as_object()
}
}
impl<T> Borrow<Py<T>> for PyRef<T>
where
T: PyObjectPayload,
{
fn borrow(&self) -> &Py<T> {
self
}
}
@@ -500,28 +618,21 @@ impl<T> Deref for PyRef<T>
where
T: PyObjectPayload,
{
type Target = T;
type Target = Py<T>;
fn deref(&self) -> &T {
// SAFETY: per the invariant on `self.obj`, the payload of the pyobject is always T, so it
// can always be cast to a PyInner<T>
let obj = unsafe { &*(&*self.obj.rc.inner as *const PyInner<Erased> as *const PyInner<T>) };
&obj.payload
fn deref(&self) -> &Py<T> {
&self.obj
}
}
#[repr(transparent)]
pub struct PyWeakRef<T: PyObjectPayload> {
weak: PyObjectWeak,
_payload: PhantomData<PyWeak<T>>,
weak: PyWeak<Py<T>>,
}
impl<T: PyObjectPayload> PyWeakRef<T> {
pub fn upgrade(&self) -> Option<PyRef<T>> {
self.weak.upgrade().map(|obj| unsafe {
// SAFETY: PyWeakRef<T> is only ever created from a PyRef<T>
PyRef::from_obj_unchecked(obj)
})
self.weak.upgrade().map(|obj| PyRef { obj })
}
}
@@ -638,42 +749,6 @@ pub(crate) fn init_type_hierarchy() -> (PyTypeRef, PyTypeRef) {
(type_type, object_type)
}
#[derive(Clone, Copy)]
pub struct PyObjectPtr<'a> {
obj: &'a PyObjectRefInner,
}
impl<'a> PyObjectPtr<'a> {
/// # Safety
///
/// `obj` *MUST* be alive until this ptr is destroyed.
/// Do not directly call this function without helper functions.
unsafe fn new(obj: &PyObjectRef) -> Self {
let obj = std::mem::transmute_copy(obj);
Self { obj }
}
// TODO: make variadic sized tuple generic
pub fn with<F, R>(objs: (&PyObjectRef, &PyObjectRef), f: F) -> R
where
F: FnOnce((PyObjectPtr, PyObjectPtr)) -> R,
{
objs.0
.with_ptr(|obj1| objs.1.with_ptr(|obj2| f((obj1, obj2))))
}
}
impl<'a> Deref for PyObjectPtr<'a> {
type Target = PyObjectRef;
fn deref(&self) -> &Self::Target {
unsafe {
// SAFETY: only when PyObjectRef = PyRc<PyObjectRefInner>
std::mem::transmute(&self.obj)
}
}
}
#[cfg(test)]
mod tests {
use super::*;

View File

@@ -71,19 +71,19 @@ mod _ast {
use super::PY_COMPILE_FLAG_AST_ONLY;
}
fn get_node_field(vm: &VirtualMachine, obj: &PyObjectRef, field: &str, typ: &str) -> PyResult {
vm.get_attribute_opt(obj.clone(), field)?.ok_or_else(|| {
fn get_node_field(vm: &VirtualMachine, obj: &crate::PyObj, field: &str, typ: &str) -> PyResult {
vm.get_attribute_opt(obj.incref(), field)?.ok_or_else(|| {
vm.new_type_error(format!("required field \"{}\" missing from {}", field, typ))
})
}
fn get_node_field_opt(
vm: &VirtualMachine,
obj: &PyObjectRef,
obj: &crate::PyObj,
field: &str,
) -> PyResult<Option<PyObjectRef>> {
Ok(vm
.get_attribute_opt(obj.clone(), field)?
.get_attribute_opt(obj.incref(), field)?
.filter(|obj| !vm.is_none(obj)))
}
@@ -156,7 +156,7 @@ impl<T: NamedNode> Node for ast::Located<T> {
}
}
fn node_add_location(node: &PyObjectRef, location: ast::Location, vm: &VirtualMachine) {
fn node_add_location(node: &crate::PyObj, location: ast::Location, vm: &VirtualMachine) {
let dict = node.dict().unwrap();
dict.set_item("lineno", vm.ctx.new_int(location.row()).into(), vm)
.unwrap();

File diff suppressed because it is too large Load Diff

View File

@@ -588,7 +588,7 @@ mod builtins {
Err(vm.new_unsupported_binop_error(x, y, "pow"))
}),
Some(z) => {
let try_pow_value = |obj: &PyObjectRef,
let try_pow_value = |obj: &crate::PyObj,
args: (PyObjectRef, PyObjectRef, PyObjectRef)|
-> Option<PyResult> {
if let Some(method) = obj.get_class_attr("__pow__") {
@@ -778,7 +778,7 @@ mod builtins {
});
for item in iterable.iter(vm)? {
sum = vm._add(&sum, &item?)?;
sum = vm._add(&sum, &*item?)?;
}
Ok(sum)
}

View File

@@ -89,12 +89,12 @@ mod _codecs {
}
}
#[inline]
fn handler_func(&self) -> PyResult<&PyObjectRef> {
fn handler_func(&self) -> PyResult<&crate::PyObj> {
let vm = self.vm;
self.handler.get_or_try_init(|| {
Ok(self.handler.get_or_try_init(|| {
let errors = self.errors.as_ref().map_or("strict", |s| s.as_str());
vm.state.codec_registry.lookup_error(errors, vm)
})
})?)
}
}
impl encodings::StrBuffer for PyStrRef {
@@ -189,7 +189,7 @@ mod _codecs {
let replace = replace
.downcast_ref::<PyStr>()
.ok_or_else(tuple_err)?
.clone();
.incref();
let restart =
isize::try_from_borrowed_object(vm, restart).map_err(|_| tuple_err())?;
let restart = if restart < 0 {

View File

@@ -17,7 +17,8 @@ mod _collections {
PyComparisonOp, Unhashable,
},
vm::ReprGuard,
PyComparisonValue, PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol, VirtualMachine,
PyComparisonValue, PyObj, PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol,
VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
use itertools::Itertools;
@@ -532,8 +533,8 @@ mod _collections {
impl Comparable for PyDeque {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {
@@ -622,7 +623,7 @@ mod _collections {
impl IterNextIterable for PyDequeIterator {}
impl IterNext for PyDequeIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|deque, pos| {
if zelf.state != deque.state.load() {
return Err(vm.new_runtime_error("Deque mutated during iteration".to_owned()));
@@ -689,7 +690,7 @@ mod _collections {
impl IterNextIterable for PyReverseDequeIterator {}
impl IterNext for PyReverseDequeIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.internal.lock().next(|deque, pos| {
if deque.state.load() != zelf.state {
return Err(vm.new_runtime_error("Deque mutated during iteration".to_owned()));

View File

@@ -89,7 +89,7 @@ mod _io {
types::{Constructor, Destructor, IterNext, Iterable},
utils::Either,
vm::{ReprGuard, VirtualMachine},
IdProtocol, PyContext, PyObjectPtr, PyObjectRef, PyRef, PyResult, PyValue, StaticType,
IdProtocol, PyContext, PyObj, PyObjectRef, PyRef, PyResult, PyValue, StaticType,
TryFromBorrowedObject, TryFromObject, TypeProtocol,
};
use bstr::ByteSlice;
@@ -110,8 +110,8 @@ mod _io {
}
}
fn ensure_unclosed(file: &PyObjectRef, msg: &str, vm: &VirtualMachine) -> PyResult<()> {
if file.clone().get_attr("closed", vm)?.try_to_bool(vm)? {
fn ensure_unclosed(file: &crate::PyObj, msg: &str, vm: &VirtualMachine) -> PyResult<()> {
if file.incref().get_attr("closed", vm)?.try_to_bool(vm)? {
Err(vm.new_value_error(msg.to_owned()))
} else {
Ok(())
@@ -122,7 +122,7 @@ mod _io {
vm.new_exception_msg(UNSUPPORTED_OPERATION.get().unwrap().clone(), msg)
}
fn _unsupported<T>(vm: &VirtualMachine, zelf: &PyObjectRef, operation: &str) -> PyResult<T> {
fn _unsupported<T>(vm: &VirtualMachine, zelf: &crate::PyObj, operation: &str) -> PyResult<T> {
Err(new_unsupported_operation(
vm,
format!("{}.{}() not supported", zelf.class().name(), operation),
@@ -286,10 +286,10 @@ mod _io {
}
}
fn file_closed(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<bool> {
file.clone().get_attr("closed", vm)?.try_to_bool(vm)
fn file_closed(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<bool> {
file.incref().get_attr("closed", vm)?.try_to_bool(vm)
}
fn check_closed(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
fn check_closed(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if file_closed(file, vm)? {
Err(io_closed_error(vm))
} else {
@@ -297,7 +297,7 @@ mod _io {
}
}
fn check_readable(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
fn check_readable(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if vm.call_method(file, "readable", ())?.try_to_bool(vm)? {
Ok(())
} else {
@@ -308,7 +308,7 @@ mod _io {
}
}
fn check_writable(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
fn check_writable(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if vm.call_method(file, "writable", ())?.try_to_bool(vm)? {
Ok(())
} else {
@@ -319,7 +319,7 @@ mod _io {
}
}
fn check_seekable(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
fn check_seekable(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if vm.call_method(file, "seekable", ())?.try_to_bool(vm)? {
Ok(())
} else {
@@ -502,13 +502,13 @@ mod _io {
}
impl Destructor for _IOBase {
fn slot_del(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<()> {
let _ = vm.call_method(&*zelf, "close", ());
fn slot_del(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<()> {
let _ = vm.call_method(zelf, "close", ());
Ok(())
}
#[cold]
fn del(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<()> {
fn del(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<()> {
unreachable!("slot_del is implemented")
}
}
@@ -525,8 +525,8 @@ mod _io {
}
impl IterNext for _IOBase {
fn slot_iternext(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let line = vm.call_method(&*zelf, "readline", ())?;
fn slot_iternext(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let line = vm.call_method(zelf, "readline", ())?;
Ok(if !line.clone().try_to_bool(vm)? {
PyIterReturn::StopIteration(None)
} else {
@@ -534,12 +534,12 @@ mod _io {
})
}
fn next(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(_zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
unreachable!("slot_iternext is implemented")
}
}
pub(super) fn iobase_close(file: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
pub(super) fn iobase_close(file: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if !file_closed(file, vm)? {
let res = vm.call_method(file, "flush", ());
file.set_attr("__closed", vm.new_pyobj(true), vm)?;
@@ -700,7 +700,7 @@ mod _io {
}
impl BufferedData {
fn check_init(&self, vm: &VirtualMachine) -> PyResult<&PyObjectRef> {
fn check_init(&self, vm: &VirtualMachine) -> PyResult<&crate::PyObj> {
if let Some(raw) = &self.raw {
Ok(raw)
} else {
@@ -1353,8 +1353,11 @@ mod _io {
})
}
pub fn repr_fileobj_name(obj: &PyObjectRef, vm: &VirtualMachine) -> PyResult<Option<PyStrRef>> {
let name = match obj.clone().get_attr("name", vm) {
pub fn repr_fileobj_name(
obj: &crate::PyObj,
vm: &VirtualMachine,
) -> PyResult<Option<PyStrRef>> {
let name = match obj.incref().get_attr("name", vm) {
Ok(name) => Some(name),
Err(e)
if e.isinstance(&vm.ctx.exceptions.attribute_error)
@@ -1500,16 +1503,16 @@ mod _io {
fn closed(&self, vm: &VirtualMachine) -> PyResult {
self.lock(vm)?
.check_init(vm)?
.clone()
.incref()
.get_attr("closed", vm)
}
#[pyproperty]
fn name(&self, vm: &VirtualMachine) -> PyResult {
self.lock(vm)?.check_init(vm)?.clone().get_attr("name", vm)
self.lock(vm)?.check_init(vm)?.incref().get_attr("name", vm)
}
#[pyproperty]
fn mode(&self, vm: &VirtualMachine) -> PyResult {
self.lock(vm)?.check_init(vm)?.clone().get_attr("mode", vm)
self.lock(vm)?.check_init(vm)?.incref().get_attr("mode", vm)
}
#[pymethod]
fn fileno(&self, vm: &VirtualMachine) -> PyResult {
@@ -2156,7 +2159,7 @@ mod _io {
set_field!(self.bytes_to_skip, BYTES_TO_SKIP_OFF);
num_bigint::BigUint::from_bytes_le(&buf).into()
}
fn set_decoder_state(&self, decoder: &PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
fn set_decoder_state(&self, decoder: &crate::PyObj, vm: &VirtualMachine) -> PyResult<()> {
if self.start_pos == 0 && self.dec_flags == 0 {
vm.call_method(decoder, "reset", ())?;
} else {
@@ -2340,7 +2343,7 @@ mod _io {
0 => cookie,
// SEEK_CUR
1 => {
if vm.bool_eq(&cookie, &vm.ctx.new_int(0).into())? {
if vm.bool_eq(&cookie, vm.ctx.new_int(0).as_ref())? {
vm.call_method(&textio.buffer, "tell", ())?
} else {
return Err(new_unsupported_operation(
@@ -2351,7 +2354,7 @@ mod _io {
}
// SEEK_END
2 => {
if vm.bool_eq(&cookie, &vm.ctx.new_int(0).into())? {
if vm.bool_eq(&cookie, vm.ctx.new_int(0).as_ref())? {
drop(textio);
vm.call_method(zelf.as_object(), "flush", ())?;
let mut textio = zelf.lock(vm)?;
@@ -2362,7 +2365,7 @@ mod _io {
}
let res = vm.call_method(&textio.buffer, "seek", (0, 2))?;
if let Some((encoder, _)) = &textio.encoder {
let start_of_stream = vm.bool_eq(&res, &vm.ctx.new_int(0).into())?;
let start_of_stream = vm.bool_eq(&res, vm.ctx.new_int(0).as_ref())?;
reset_encoder(encoder, start_of_stream)?;
}
return Ok(res);
@@ -2379,7 +2382,7 @@ mod _io {
}
};
use crate::types::PyComparisonOp;
if cookie.rich_compare_bool(&vm.ctx.new_int(0).into(), PyComparisonOp::Lt, vm)? {
if cookie.rich_compare_bool(vm.ctx.new_int(0).as_ref(), PyComparisonOp::Lt, vm)? {
return Err(
vm.new_value_error(format!("negative seek position {}", vm.to_repr(&cookie)?))
);
@@ -3335,7 +3338,7 @@ mod _io {
len: self.buffer.read().cursor.get_ref().len(),
..Default::default()
};
let buffer = PyBuffer::new(self.as_object().clone(), self, options);
let buffer = PyBuffer::new(self.as_object().incref(), self, options);
let view = PyMemoryView::from_buffer(buffer, vm)?;
Ok(view)
}

View File

@@ -56,7 +56,7 @@ mod decl {
}
impl IterNextIterable for PyItertoolsChain {}
impl IterNext for PyItertoolsChain {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
loop {
let pos = zelf.cur_idx.load();
if pos >= zelf.iterables.len() {
@@ -124,7 +124,7 @@ mod decl {
impl IterNextIterable for PyItertoolsCompress {}
impl IterNext for PyItertoolsCompress {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
loop {
let sel_obj = match zelf.selector.next(vm)? {
PyIterReturn::Return(obj) => obj,
@@ -186,7 +186,7 @@ mod decl {
impl PyItertoolsCount {}
impl IterNextIterable for PyItertoolsCount {}
impl IterNext for PyItertoolsCount {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut cur = zelf.cur.write();
let result = cur.clone();
*cur += &zelf.step;
@@ -220,7 +220,7 @@ mod decl {
impl PyItertoolsCycle {}
impl IterNextIterable for PyItertoolsCycle {}
impl IterNext for PyItertoolsCycle {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let item = if let PyIterReturn::Return(item) = zelf.iter.next(vm)? {
zelf.saved.write().push(item.clone());
item
@@ -311,7 +311,7 @@ mod decl {
impl IterNextIterable for PyItertoolsRepeat {}
impl IterNext for PyItertoolsRepeat {
fn next(zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, _vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if let Some(ref times) = zelf.times {
let mut times = times.write();
if *times == 0 {
@@ -355,7 +355,7 @@ mod decl {
impl PyItertoolsStarmap {}
impl IterNextIterable for PyItertoolsStarmap {}
impl IterNext for PyItertoolsStarmap {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let obj = zelf.iterable.next(vm)?;
let function = &zelf.function;
match obj {
@@ -408,7 +408,7 @@ mod decl {
impl PyItertoolsTakewhile {}
impl IterNextIterable for PyItertoolsTakewhile {}
impl IterNext for PyItertoolsTakewhile {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if zelf.stop_flag.load() {
return Ok(PyIterReturn::StopIteration(None));
}
@@ -472,7 +472,7 @@ mod decl {
impl PyItertoolsDropwhile {}
impl IterNextIterable for PyItertoolsDropwhile {}
impl IterNext for PyItertoolsDropwhile {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let predicate = &zelf.predicate;
let iterable = &zelf.iterable;
@@ -514,7 +514,7 @@ mod decl {
}
impl GroupByState {
fn is_current(&self, grouper: &PyItertoolsGrouperRef) -> bool {
fn is_current(&self, grouper: &crate::Py<PyItertoolsGrouper>) -> bool {
self.grouper
.as_ref()
.and_then(|g| g.upgrade())
@@ -590,7 +590,7 @@ mod decl {
}
impl IterNextIterable for PyItertoolsGroupBy {}
impl IterNext for PyItertoolsGroupBy {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let mut state = zelf.state.lock();
state.grouper = None;
@@ -628,11 +628,11 @@ mod decl {
state.next_group = false;
let grouper = PyItertoolsGrouper {
groupby: zelf.clone(),
groupby: zelf.incref(),
}
.into_ref(vm);
state.grouper = Some(PyRef::downgrade(&grouper));
state.grouper = Some(grouper.downgrade());
Ok(PyIterReturn::Return(
(state.current_key.as_ref().unwrap().clone(), grouper).into_pyobject(vm),
))
@@ -646,13 +646,11 @@ mod decl {
groupby: PyRef<PyItertoolsGroupBy>,
}
type PyItertoolsGrouperRef = PyRef<PyItertoolsGrouper>;
#[pyimpl(with(IterNext))]
impl PyItertoolsGrouper {}
impl IterNextIterable for PyItertoolsGrouper {}
impl IterNext for PyItertoolsGrouper {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let old_key = {
let mut state = zelf.groupby.state.lock();
@@ -785,7 +783,7 @@ mod decl {
impl IterNextIterable for PyItertoolsIslice {}
impl IterNext for PyItertoolsIslice {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
while zelf.cur.load() < zelf.next.load() {
zelf.iterable.next(vm)?;
zelf.cur.fetch_add(1);
@@ -850,7 +848,7 @@ mod decl {
impl PyItertoolsFilterFalse {}
impl IterNextIterable for PyItertoolsFilterFalse {}
impl IterNext for PyItertoolsFilterFalse {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let predicate = &zelf.predicate;
let iterable = &zelf.iterable;
@@ -910,7 +908,7 @@ mod decl {
impl IterNextIterable for PyItertoolsAccumulate {}
impl IterNext for PyItertoolsAccumulate {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let iterable = &zelf.iterable;
let acc_value = zelf.acc_value.read().clone();
@@ -1039,7 +1037,7 @@ mod decl {
}
impl IterNextIterable for PyItertoolsTee {}
impl IterNext for PyItertoolsTee {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let value = match zelf.tee_data.get_item(vm, zelf.index.load())? {
PyIterReturn::Return(obj) => obj,
PyIterReturn::StopIteration(v) => return Ok(PyIterReturn::StopIteration(v)),
@@ -1118,7 +1116,7 @@ mod decl {
}
impl IterNextIterable for PyItertoolsProduct {}
impl IterNext for PyItertoolsProduct {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// stop signal
if zelf.stop.load() {
return Ok(PyIterReturn::StopIteration(None));
@@ -1197,7 +1195,7 @@ mod decl {
impl PyItertoolsCombinations {}
impl IterNextIterable for PyItertoolsCombinations {}
impl IterNext for PyItertoolsCombinations {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// stop signal
if zelf.exhausted.load() {
return Ok(PyIterReturn::StopIteration(None));
@@ -1288,7 +1286,7 @@ mod decl {
impl IterNextIterable for PyItertoolsCombinationsWithReplacement {}
impl IterNext for PyItertoolsCombinationsWithReplacement {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// stop signal
if zelf.exhausted.load() {
return Ok(PyIterReturn::StopIteration(None));
@@ -1396,7 +1394,7 @@ mod decl {
impl PyItertoolsPermutations {}
impl IterNextIterable for PyItertoolsPermutations {}
impl IterNext for PyItertoolsPermutations {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
// stop signal
if zelf.exhausted.load() {
return Ok(PyIterReturn::StopIteration(None));
@@ -1498,7 +1496,7 @@ mod decl {
impl PyItertoolsZipLongest {}
impl IterNextIterable for PyItertoolsZipLongest {}
impl IterNext for PyItertoolsZipLongest {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if zelf.iterators.is_empty() {
return Ok(PyIterReturn::StopIteration(None));
}
@@ -1546,7 +1544,7 @@ mod decl {
impl PyItertoolsPairwise {}
impl IterNextIterable for PyItertoolsPairwise {}
impl IterNext for PyItertoolsPairwise {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let old = match zelf.old.read().clone() {
None => match zelf.iterator.next(vm)? {
PyIterReturn::Return(obj) => obj,

View File

@@ -470,7 +470,7 @@ mod _operator {
fn reduce(zelf: PyRef<Self>, vm: &VirtualMachine) -> PyResult<(PyTypeRef, PyTupleRef)> {
let attrs = vm
.ctx
.new_tuple(zelf.attrs.iter().map(|v| v.as_object()).cloned().collect());
.new_tuple(zelf.attrs.iter().map(|v| v.as_object().incref()).collect());
Ok((zelf.clone_class(), attrs))
}
@@ -494,7 +494,7 @@ mod _operator {
impl Callable for PyAttrGetter {
type Args = PyObjectRef;
fn call(zelf: &PyRef<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
// Handle case where we only have one attribute.
if zelf.attrs.len() == 1 {
return Self::get_single_attr(obj, zelf.attrs[0].as_str(), vm);
@@ -557,7 +557,7 @@ mod _operator {
impl Callable for PyItemGetter {
type Args = PyObjectRef;
fn call(zelf: &PyRef<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
// Handle case where we only have one attribute.
if zelf.items.len() == 1 {
return obj.get_item(zelf.items[0].clone(), vm);
@@ -654,7 +654,7 @@ mod _operator {
impl Callable for PyMethodCaller {
type Args = PyObjectRef;
#[inline]
fn call(zelf: &PyRef<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
fn call(zelf: &crate::Py<Self>, obj: Self::Args, vm: &VirtualMachine) -> PyResult {
vm.call_method(&obj, zelf.name.as_str(), zelf.args.clone())
}
}

View File

@@ -920,7 +920,7 @@ pub(super) mod _os {
}
impl IterNextIterable for ScandirIterator {}
impl IterNext for ScandirIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if zelf.exhausted.load() {
return Ok(PyIterReturn::StopIteration(None));
}
@@ -1370,7 +1370,7 @@ pub(super) mod _os {
let (a, m) = parse_tup(&ns).ok_or_else(|| {
vm.new_type_error("utime: 'ns' must be a tuple of two ints".to_owned())
})?;
let ns_in_sec = vm.ctx.new_int(1_000_000_000).into();
let ns_in_sec: PyObjectRef = vm.ctx.new_int(1_000_000_000).into();
let ns_to_dur = |obj: PyObjectRef| {
let divmod = vm._divmod(&obj, &ns_in_sec)?;
let (div, rem) =
@@ -1746,7 +1746,7 @@ impl<'a> SupportFunc {
}
}
pub fn extend_module(vm: &VirtualMachine, module: &PyObjectRef) {
pub fn extend_module(vm: &VirtualMachine, module: &crate::PyObj) {
_os::extend_module(vm, module);
let support_funcs = _os::support_funcs();
@@ -1754,7 +1754,7 @@ pub fn extend_module(vm: &VirtualMachine, module: &PyObjectRef) {
let supports_dir_fd = PySet::default().into_ref(vm);
let supports_follow_symlinks = PySet::default().into_ref(vm);
for support in support_funcs {
let func_obj = module.clone().get_attr(support.name, vm).unwrap();
let func_obj = module.incref().get_attr(support.name, vm).unwrap();
if support.fd.unwrap_or(false) {
supports_fd.clone().add(func_obj.clone(), vm).unwrap();
}

View File

@@ -20,7 +20,7 @@ pub(crate) mod _struct {
function::{ArgBytesLike, ArgIntoBool, ArgMemoryBuffer, IntoPyObject, PosArgs},
protocol::PyIterReturn,
types::{Constructor, IterNext, IterNextIterable},
PyObjectRef, PyRef, PyResult, PyValue, TryFromObject, TypeProtocol, VirtualMachine,
PyObjectRef, PyResult, PyValue, TryFromObject, TypeProtocol, VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
use half::f16;
@@ -852,7 +852,7 @@ pub(crate) mod _struct {
}
impl IterNextIterable for UnpackIterator {}
impl IterNext for UnpackIterator {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
let size = zelf.format_spec.size;
let offset = zelf.offset.fetch_add(size);
zelf.buffer.with_ref(|buf| {

View File

@@ -11,7 +11,7 @@ mod _sre {
protocol::PyBuffer,
stdlib::sys,
types::{Comparable, Hashable},
ItemProtocol, PyComparisonValue, PyObjectRef, PyRef, PyResult, PyValue,
ItemProtocol, PyComparisonValue, PyObj, PyObjectRef, PyRef, PyResult, PyValue,
TryFromBorrowedObject, TryFromObject, VirtualMachine,
};
use core::str;
@@ -499,7 +499,7 @@ mod _sre {
let list = PyList::from(sublist).into_object(vm);
let join_type = if zelf.isbytes {
let join_type: PyObjectRef = if zelf.isbytes {
vm.ctx.new_bytes(vec![]).into()
} else {
vm.ctx.new_str(ascii!("")).into()
@@ -516,7 +516,7 @@ mod _sre {
}
impl Hashable for Pattern {
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(zelf: &crate::Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash> {
let hash = zelf.pattern.hash(vm)?;
let (_, code, _) = unsafe { zelf.code.align_to::<u8>() };
let hash = hash ^ vm.state.hash_secret.hash_bytes(code);
@@ -528,8 +528,8 @@ mod _sre {
impl Comparable for Pattern {
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &crate::Py<Self>,
other: &PyObj,
op: crate::types::PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue> {

View File

@@ -1,6 +1,4 @@
use crate::{
function::IntoPyObject, ItemProtocol, PyClassImpl, PyObjectRef, PyResult, VirtualMachine,
};
use crate::{function::IntoPyObject, ItemProtocol, PyClassImpl, PyResult, VirtualMachine};
pub(crate) use sys::{MAXSIZE, MULTIARCH};
@@ -335,7 +333,7 @@ mod sys {
#[pyfunction]
fn getrefcount(obj: PyObjectRef) -> usize {
PyObjectRef::strong_count(&obj)
obj.strong_count()
}
#[pyfunction]
@@ -670,7 +668,7 @@ mod sys {
impl WindowsVersion {}
}
pub(crate) fn init_module(vm: &VirtualMachine, module: &PyObjectRef, builtins: &PyObjectRef) {
pub(crate) fn init_module(vm: &VirtualMachine, module: &crate::PyObj, builtins: &crate::PyObj) {
let ctx = &vm.ctx;
let _flags_type = sys::Flags::make_class(ctx);
let _version_info_type = crate::version::VersionInfo::make_class(ctx);
@@ -686,8 +684,8 @@ pub(crate) fn init_module(vm: &VirtualMachine, module: &PyObjectRef, builtins: &
sys::extend_module(vm, module);
let modules = vm.ctx.new_dict();
modules.set_item("sys", module.clone(), vm).unwrap();
modules.set_item("builtins", builtins.clone(), vm).unwrap();
modules.set_item("sys", module.incref(), vm).unwrap();
modules.set_item("builtins", builtins.incref(), vm).unwrap();
extend_module!(vm, module, {
"__doc__" => sys::DOC.to_owned().into_pyobject(vm),
"modules" => modules,

View File

@@ -347,7 +347,7 @@ pub(crate) mod _thread {
impl SetAttr for Local {
fn setattro(
zelf: &PyRef<Self>,
zelf: &crate::Py<Self>,
attr: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,

View File

@@ -33,7 +33,7 @@ mod _weakref {
#[pyfunction]
fn getweakrefcount(obj: PyObjectRef) -> usize {
PyObjectRef::weak_count(&obj)
obj.weak_count()
}
#[pyfunction]

View File

@@ -2,7 +2,7 @@ use crate::{
builtins::{PyStr, PyStrRef},
exceptions::types::PyBaseExceptionRef,
sliceable::PySliceableSequence,
IdProtocol, PyObjectRef, TypeProtocol, VirtualMachine,
IdProtocol, Py, PyObjectRef, TypeProtocol, VirtualMachine,
};
use rustpython_common::str::levenshtein::{levenshtein_distance, MOVE_COST};
use std::iter::ExactSizeIterator;
@@ -17,7 +17,7 @@ fn calculate_suggestions<'a>(
return None;
}
let mut suggestion: Option<&PyStrRef> = None;
let mut suggestion: Option<&Py<PyStr>> = None;
let mut suggestion_distance = usize::MAX;
let name = name.downcast_ref::<PyStr>()?;
@@ -41,17 +41,17 @@ fn calculate_suggestions<'a>(
suggestion_distance = current_distance;
}
}
suggestion.cloned()
suggestion.map(|r| r.incref())
}
pub fn offer_suggestions(exc: &PyBaseExceptionRef, vm: &VirtualMachine) -> Option<PyStrRef> {
if exc.class().is(&vm.ctx.exceptions.attribute_error) {
let name = exc.as_object().clone().get_attr("name", vm).unwrap();
let obj = exc.as_object().clone().get_attr("obj", vm).unwrap();
let name = exc.as_object().incref().get_attr("name", vm).unwrap();
let obj = exc.as_object().incref().get_attr("obj", vm).unwrap();
calculate_suggestions(vm.dir(Some(obj)).ok()?.borrow_vec().iter(), &name)
} else if exc.class().is(&vm.ctx.exceptions.name_error) {
let name = exc.as_object().clone().get_attr("name", vm).unwrap();
let name = exc.as_object().incref().get_attr("name", vm).unwrap();
let mut tb = exc.traceback().unwrap();
while let Some(traceback) = tb.next.clone() {
tb = traceback;

View File

@@ -4,8 +4,8 @@ use crate::{
function::{FromArgs, FuncArgs, IntoPyResult, OptionalArg},
protocol::{PyBuffer, PyIterReturn, PyMappingMethods},
utils::Either,
IdProtocol, PyComparisonValue, PyObjectPtr, PyObjectRef, PyRef, PyResult, PyValue,
TypeProtocol, VirtualMachine,
IdProtocol, Py, PyComparisonValue, PyObj, PyObjectRef, PyRef, PyResult, PyValue, TypeProtocol,
VirtualMachine,
};
use crossbeam_utils::atomic::AtomicCell;
use num_traits::ToPrimitive;
@@ -127,30 +127,30 @@ impl Default for PyTypeFlags {
}
}
pub(crate) type GenericMethod = fn(PyObjectPtr, FuncArgs, &VirtualMachine) -> PyResult;
pub(crate) type AsMappingFunc = fn(PyObjectPtr, &VirtualMachine) -> PyMappingMethods;
pub(crate) type HashFunc = fn(PyObjectPtr, &VirtualMachine) -> PyResult<PyHash>;
pub(crate) type GenericMethod = fn(&PyObj, FuncArgs, &VirtualMachine) -> PyResult;
pub(crate) type AsMappingFunc = fn(&PyObj, &VirtualMachine) -> PyMappingMethods;
pub(crate) type HashFunc = fn(&PyObj, &VirtualMachine) -> PyResult<PyHash>;
// CallFunc = GenericMethod
pub(crate) type GetattroFunc = fn(PyObjectRef, PyStrRef, &VirtualMachine) -> PyResult;
pub(crate) type SetattroFunc =
fn(PyObjectPtr, PyStrRef, Option<PyObjectRef>, &VirtualMachine) -> PyResult<()>;
pub(crate) type AsBufferFunc = fn(PyObjectPtr, &VirtualMachine) -> PyResult<PyBuffer>;
fn(&PyObj, PyStrRef, Option<PyObjectRef>, &VirtualMachine) -> PyResult<()>;
pub(crate) type AsBufferFunc = fn(&PyObj, &VirtualMachine) -> PyResult<PyBuffer>;
pub(crate) type RichCompareFunc = fn(
PyObjectPtr,
PyObjectPtr,
&PyObj,
&PyObj,
PyComparisonOp,
&VirtualMachine,
) -> PyResult<Either<PyObjectRef, PyComparisonValue>>;
pub(crate) type IterFunc = fn(PyObjectRef, &VirtualMachine) -> PyResult;
pub(crate) type IterNextFunc = fn(PyObjectPtr, &VirtualMachine) -> PyResult<PyIterReturn>;
pub(crate) type IterNextFunc = fn(&PyObj, &VirtualMachine) -> PyResult<PyIterReturn>;
pub(crate) type DescrGetFunc =
fn(PyObjectRef, Option<PyObjectRef>, Option<PyObjectRef>, &VirtualMachine) -> PyResult;
pub(crate) type DescrSetFunc =
fn(PyObjectRef, PyObjectRef, Option<PyObjectRef>, &VirtualMachine) -> PyResult<()>;
pub(crate) type NewFunc = fn(PyTypeRef, FuncArgs, &VirtualMachine) -> PyResult;
pub(crate) type DelFunc = fn(PyObjectPtr, &VirtualMachine) -> PyResult<()>;
pub(crate) type DelFunc = fn(&PyObj, &VirtualMachine) -> PyResult<()>;
fn as_mapping_wrapper(zelf: PyObjectPtr, _vm: &VirtualMachine) -> PyMappingMethods {
fn as_mapping_wrapper(zelf: &PyObj, _vm: &VirtualMachine) -> PyMappingMethods {
macro_rules! then_some_closure {
($cond:expr, $closure:expr) => {
if $cond {
@@ -192,16 +192,16 @@ fn as_mapping_wrapper(zelf: PyObjectPtr, _vm: &VirtualMachine) -> PyMappingMetho
}
}
fn hash_wrapper(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyHash> {
let hash_obj = vm.call_special_method((*zelf).clone(), "__hash__", ())?;
fn hash_wrapper(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyHash> {
let hash_obj = vm.call_special_method(zelf.to_owned(), "__hash__", ())?;
match hash_obj.payload_if_subclass::<PyInt>(vm) {
Some(py_int) => Ok(rustpython_common::hash::hash_bigint(py_int.as_bigint())),
None => Err(vm.new_type_error("__hash__ method should return an integer".to_owned())),
}
}
fn call_wrapper(zelf: PyObjectPtr, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
vm.call_special_method((*zelf).clone(), "__call__", args)
fn call_wrapper(zelf: &PyObj, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
vm.call_special_method(zelf.to_owned(), "__call__", args)
}
fn getattro_wrapper(zelf: PyObjectRef, name: PyStrRef, vm: &VirtualMachine) -> PyResult {
@@ -209,12 +209,12 @@ fn getattro_wrapper(zelf: PyObjectRef, name: PyStrRef, vm: &VirtualMachine) -> P
}
fn setattro_wrapper(
zelf: PyObjectPtr,
zelf: &PyObj,
name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
) -> PyResult<()> {
let zelf = (*zelf).clone();
let zelf = zelf.to_owned();
match value {
Some(value) => {
vm.call_special_method(zelf, "__setattr__", (name, value))?;
@@ -227,12 +227,12 @@ fn setattro_wrapper(
}
pub(crate) fn richcompare_wrapper(
zelf: PyObjectPtr,
other: PyObjectPtr,
zelf: &PyObj,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<Either<PyObjectRef, PyComparisonValue>> {
vm.call_special_method((*zelf).clone(), op.method_name(), ((*other).clone(),))
vm.call_special_method(zelf.to_owned(), op.method_name(), (other.to_owned(),))
.map(Either::A)
}
@@ -240,8 +240,8 @@ fn iter_wrapper(zelf: PyObjectRef, vm: &VirtualMachine) -> PyResult {
vm.call_special_method(zelf, "__iter__", ())
}
fn iternext_wrapper(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
PyIterReturn::from_pyresult(vm.call_special_method((*zelf).clone(), "__next__", ()), vm)
fn iternext_wrapper(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
PyIterReturn::from_pyresult(vm.call_special_method(zelf.to_owned(), "__next__", ()), vm)
}
fn descr_get_wrapper(
@@ -268,14 +268,14 @@ fn descr_set_wrapper(
fn new_wrapper(cls: PyTypeRef, mut args: FuncArgs, vm: &VirtualMachine) -> PyResult {
let new = vm
.get_attribute_opt(cls.as_object().clone(), "__new__")?
.get_attribute_opt(cls.as_object().incref(), "__new__")?
.unwrap();
args.prepend_arg(cls.into());
vm.invoke(&new, args)
}
fn del_wrapper(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<()> {
vm.call_special_method((*zelf).clone(), "__del__", ())?;
fn del_wrapper(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<()> {
vm.call_special_method(zelf.to_owned(), "__del__", ())?;
Ok(())
}
@@ -364,7 +364,7 @@ where
pub trait Destructor: PyValue {
#[inline] // for __del__
#[pyslot]
fn slot_del(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<()> {
fn slot_del(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<()> {
if let Some(zelf) = zelf.downcast_ref() {
Self::del(zelf, vm)
} else {
@@ -374,10 +374,10 @@ pub trait Destructor: PyValue {
#[pymethod]
fn __del__(zelf: PyObjectRef, vm: &VirtualMachine) -> PyResult<()> {
zelf.with_ptr(|zelf| Self::slot_del(zelf, vm))
Self::slot_del(&zelf, vm)
}
fn del(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<()>;
fn del(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<()>;
}
#[pyimpl]
@@ -386,7 +386,7 @@ pub trait Callable: PyValue {
#[inline]
#[pyslot]
fn slot_call(zelf: PyObjectPtr, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
fn slot_call(zelf: &PyObj, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
if let Some(zelf) = zelf.downcast_ref() {
Self::call(zelf, args.bind(vm)?, vm)
} else {
@@ -397,9 +397,9 @@ pub trait Callable: PyValue {
#[inline]
#[pymethod]
fn __call__(zelf: PyObjectRef, args: FuncArgs, vm: &VirtualMachine) -> PyResult {
zelf.with_ptr(|zelf| Self::slot_call(zelf, args.bind(vm)?, vm))
Self::slot_call(&zelf, args.bind(vm)?, vm)
}
fn call(zelf: &PyRef<Self>, args: Self::Args, vm: &VirtualMachine) -> PyResult;
fn call(zelf: &Py<Self>, args: Self::Args, vm: &VirtualMachine) -> PyResult;
}
#[pyimpl]
@@ -477,7 +477,7 @@ pub trait GetDescriptor: PyValue {
pub trait Hashable: PyValue {
#[inline]
#[pyslot]
fn slot_hash(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyHash> {
fn slot_hash(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyHash> {
if let Some(zelf) = zelf.downcast_ref() {
Self::hash(zelf, vm)
} else {
@@ -488,10 +488,10 @@ pub trait Hashable: PyValue {
#[inline]
#[pymethod]
fn __hash__(zelf: PyObjectRef, vm: &VirtualMachine) -> PyResult<PyHash> {
zelf.with_ptr(|zelf| Self::slot_hash(zelf, vm))
Self::slot_hash(&zelf, vm)
}
fn hash(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyHash>;
fn hash(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyHash>;
}
pub trait Unhashable: PyValue {}
@@ -500,12 +500,12 @@ impl<T> Hashable for T
where
T: Unhashable,
{
fn slot_hash(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyHash> {
fn slot_hash(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyHash> {
Err(vm.new_type_error(format!("unhashable type: '{}'", zelf.class().name())))
}
#[cold]
fn hash(_zelf: &PyRef<Self>, _vm: &VirtualMachine) -> PyResult<PyHash> {
fn hash(_zelf: &Py<Self>, _vm: &VirtualMachine) -> PyResult<PyHash> {
unreachable!("slot_hash is implemented for unhashable types");
}
}
@@ -515,21 +515,21 @@ pub trait Comparable: PyValue {
#[inline]
#[pyslot]
fn slot_richcompare(
zelf: PyObjectPtr,
other: PyObjectPtr,
zelf: &PyObj,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<Either<PyObjectRef, PyComparisonValue>> {
if let Some(zelf) = zelf.downcast_ref() {
Self::cmp(zelf, &*other, op, vm).map(Either::B)
Self::cmp(zelf, other, op, vm).map(Either::B)
} else {
Err(vm.new_type_error(format!("unexpected payload for {}", op.method_name())))
}
}
fn cmp(
zelf: &PyRef<Self>,
other: &PyObjectRef,
zelf: &Py<Self>,
other: &PyObj,
op: PyComparisonOp,
vm: &VirtualMachine,
) -> PyResult<PyComparisonValue>;
@@ -698,7 +698,7 @@ pub trait GetAttr: PyValue {
}
}
// TODO: make zelf: &PyRef<Self>
// TODO: make zelf: &Py<Self>
fn getattro(zelf: PyRef<Self>, name: PyStrRef, vm: &VirtualMachine) -> PyResult;
#[inline]
@@ -713,7 +713,7 @@ pub trait SetAttr: PyValue {
#[pyslot]
#[inline]
fn slot_setattro(
obj: PyObjectPtr,
obj: &PyObj,
name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
@@ -726,7 +726,7 @@ pub trait SetAttr: PyValue {
}
fn setattro(
zelf: &PyRef<Self>,
zelf: &Py<Self>,
name: PyStrRef,
value: Option<PyObjectRef>,
vm: &VirtualMachine,
@@ -755,21 +755,21 @@ pub trait AsBuffer: PyValue {
// TODO: `flags` parameter
#[inline]
#[pyslot]
fn slot_as_buffer(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyBuffer> {
fn slot_as_buffer(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyBuffer> {
let zelf = zelf
.downcast_ref()
.ok_or_else(|| vm.new_type_error("unexpected payload for as_buffer".to_owned()))?;
Self::as_buffer(zelf, vm)
}
fn as_buffer(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyBuffer>;
fn as_buffer(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyBuffer>;
}
#[pyimpl]
pub trait AsMapping: PyValue {
#[inline]
#[pyslot]
fn slot_as_mapping(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyMappingMethods {
fn slot_as_mapping(zelf: &PyObj, vm: &VirtualMachine) -> PyMappingMethods {
let zelf = unsafe { zelf.downcast_unchecked_ref::<Self>() };
Self::as_mapping(zelf, vm)
}
@@ -786,7 +786,7 @@ pub trait AsMapping: PyValue {
}
#[inline]
fn downcast_ref<'a>(zelf: &'a PyObjectRef, vm: &VirtualMachine) -> PyResult<&'a PyRef<Self>> {
fn downcast_ref<'a>(zelf: &'a PyObj, vm: &VirtualMachine) -> PyResult<&'a Py<Self>> {
zelf.downcast_ref::<Self>().ok_or_else(|| {
vm.new_type_error(format!(
"{} type is required, not {}",
@@ -796,7 +796,7 @@ pub trait AsMapping: PyValue {
})
}
fn as_mapping(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyMappingMethods;
fn as_mapping(zelf: &Py<Self>, vm: &VirtualMachine) -> PyMappingMethods;
fn length(zelf: PyObjectRef, _vm: &VirtualMachine) -> PyResult<usize>;
@@ -829,7 +829,7 @@ pub trait Iterable: PyValue {
#[pyimpl(with(Iterable))]
pub trait IterNext: PyValue + Iterable {
#[pyslot]
fn slot_iternext(zelf: PyObjectPtr, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn slot_iternext(zelf: &PyObj, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
if let Some(zelf) = zelf.downcast_ref() {
Self::next(zelf, vm)
} else {
@@ -837,13 +837,12 @@ pub trait IterNext: PyValue + Iterable {
}
}
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn>;
fn next(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn>;
#[inline]
#[pymethod]
fn __next__(zelf: PyObjectRef, vm: &VirtualMachine) -> PyResult {
zelf.with_ptr(|zelf| Self::slot_iternext(zelf, vm))
.into_pyresult(vm)
Self::slot_iternext(&zelf, vm).into_pyresult(vm)
}
}

View File

@@ -10,8 +10,8 @@ pub enum Either<A, B> {
B(B),
}
impl<A: AsRef<PyObjectRef>, B: AsRef<PyObjectRef>> AsRef<PyObjectRef> for Either<A, B> {
fn as_ref(&self) -> &PyObjectRef {
impl<A: AsRef<crate::PyObj>, B: AsRef<crate::PyObj>> AsRef<crate::PyObj> for Either<A, B> {
fn as_ref(&self) -> &crate::PyObj {
match self {
Either::A(a) => a.as_ref(),
Either::B(b) => b.as_ref(),

View File

@@ -27,7 +27,7 @@ use crate::{
signal::NSIG,
stdlib,
types::PyComparisonOp,
IdProtocol, ItemProtocol, PyArithmeticValue, PyContext, PyLease, PyMethod, PyObject,
IdProtocol, ItemProtocol, PyArithmeticValue, PyContext, PyLease, PyMethod, PyObj, PyObject,
PyObjectRef, PyObjectWrap, PyRef, PyRefExact, PyResult, PyValue, TryFromObject, TypeProtocol,
};
use crossbeam_utils::atomic::AtomicCell;
@@ -71,7 +71,7 @@ struct ExceptionStack {
}
pub(crate) mod thread {
use super::{PyObjectRef, TypeProtocol, VirtualMachine};
use super::{TypeProtocol, VirtualMachine};
use itertools::Itertools;
use std::cell::RefCell;
use std::ptr::NonNull;
@@ -90,7 +90,7 @@ pub(crate) mod thread {
})
}
pub fn with_vm<F, R>(obj: &PyObjectRef, f: F) -> Option<R>
pub fn with_vm<F, R>(obj: &crate::PyObj, f: F) -> Option<R>
where
F: Fn(&VirtualMachine) -> R,
{
@@ -675,7 +675,7 @@ impl VirtualMachine {
name_error
}
pub fn new_unsupported_unary_error(&self, a: &PyObjectRef, op: &str) -> PyBaseExceptionRef {
pub fn new_unsupported_unary_error(&self, a: &crate::PyObj, op: &str) -> PyBaseExceptionRef {
self.new_type_error(format!(
"bad operand type for {}: '{}'",
op,
@@ -685,8 +685,8 @@ impl VirtualMachine {
pub fn new_unsupported_binop_error(
&self,
a: &PyObjectRef,
b: &PyObjectRef,
a: &crate::PyObj,
b: &crate::PyObj,
op: &str,
) -> PyBaseExceptionRef {
self.new_type_error(format!(
@@ -699,9 +699,9 @@ impl VirtualMachine {
pub fn new_unsupported_ternop_error(
&self,
a: &PyObjectRef,
b: &PyObjectRef,
c: &PyObjectRef,
a: &crate::PyObj,
b: &crate::PyObj,
c: &crate::PyObj,
op: &str,
) -> PyBaseExceptionRef {
self.new_type_error(format!(
@@ -883,7 +883,7 @@ impl VirtualMachine {
}
/// Test whether a python object is `None`.
pub fn is_none(&self, obj: &PyObjectRef) -> bool {
pub fn is_none(&self, obj: &crate::PyObj) -> bool {
obj.is(&self.ctx.none)
}
pub fn option_if_none(&self, obj: PyObjectRef) -> Option<PyObjectRef> {
@@ -897,9 +897,9 @@ impl VirtualMachine {
obj.unwrap_or_else(|| self.ctx.none())
}
pub fn to_repr(&self, obj: &PyObjectRef) -> PyResult<PyStrRef> {
pub fn to_repr(&self, obj: &crate::PyObj) -> PyResult<PyStrRef> {
self.with_recursion("while getting the repr of an object", || {
let repr = self.call_special_method(obj.clone(), "__repr__", ())?;
let repr = self.call_special_method(obj.incref(), "__repr__", ())?;
repr.try_into_value(self)
})
}
@@ -918,8 +918,8 @@ impl VirtualMachine {
}),
}
}
pub fn to_index(&self, obj: &PyObjectRef) -> PyResult<PyIntRef> {
self.to_index_opt(obj.clone()).unwrap_or_else(|| {
pub fn to_index(&self, obj: &PyObj) -> PyResult<PyIntRef> {
self.to_index_opt(obj.to_owned()).unwrap_or_else(|| {
Err(self.new_type_error(format!(
"'{}' object cannot be interpreted as an integer",
obj.class().name()
@@ -993,11 +993,11 @@ impl VirtualMachine {
// Equivalent to check_class. Masks Attribute errors (into TypeErrors) and lets everything
// else go through.
fn check_cls<F>(&self, cls: &PyObjectRef, msg: F) -> PyResult
fn check_cls<F>(&self, cls: &crate::PyObj, msg: F) -> PyResult
where
F: Fn() -> String,
{
cls.clone().get_attr("__bases__", self).map_err(|e| {
cls.incref().get_attr("__bases__", self).map_err(|e| {
// Only mask AttributeErrors.
if e.class().is(&self.ctx.exceptions.attribute_error) {
self.new_type_error(msg())
@@ -1007,12 +1007,12 @@ impl VirtualMachine {
})
}
pub fn abstract_isinstance(&self, obj: &PyObjectRef, cls: &PyObjectRef) -> PyResult<bool> {
if let Ok(typ) = PyTypeRef::try_from_object(self, cls.clone()) {
pub fn abstract_isinstance(&self, obj: &crate::PyObj, cls: &crate::PyObj) -> PyResult<bool> {
if let Ok(typ) = PyTypeRef::try_from_object(self, cls.incref()) {
if obj.class().issubclass(typ.clone()) {
Ok(true)
} else if let Ok(icls) =
PyTypeRef::try_from_object(self, obj.clone().get_attr("__class__", self)?)
PyTypeRef::try_from_object(self, obj.incref().get_attr("__class__", self)?)
{
if icls.is(&obj.class()) {
Ok(false)
@@ -1030,7 +1030,7 @@ impl VirtualMachine {
)
})
.and_then(|_| {
let icls = obj.clone().get_attr("__class__", self)?;
let icls: PyObjectRef = obj.incref().get_attr("__class__", self)?;
if self.is_none(&icls) {
Ok(false)
} else {
@@ -1040,7 +1040,7 @@ impl VirtualMachine {
}
}
fn abstract_issubclass(&self, subclass: PyObjectRef, cls: &PyObjectRef) -> PyResult<bool> {
fn abstract_issubclass(&self, subclass: PyObjectRef, cls: &crate::PyObj) -> PyResult<bool> {
let mut derived = subclass;
loop {
if derived.is(cls) {
@@ -1072,10 +1072,10 @@ impl VirtualMachine {
}
}
fn recursive_issubclass(&self, subclass: &PyObjectRef, cls: &PyObjectRef) -> PyResult<bool> {
fn recursive_issubclass(&self, subclass: &crate::PyObj, cls: &crate::PyObj) -> PyResult<bool> {
if let (Ok(subclass), Ok(cls)) = (
PyTypeRef::try_from_object(self, subclass.clone()),
PyTypeRef::try_from_object(self, cls.clone()),
PyTypeRef::try_from_object(self, subclass.incref()),
PyTypeRef::try_from_object(self, cls.incref()),
) {
Ok(subclass.issubclass(cls))
} else {
@@ -1091,13 +1091,13 @@ impl VirtualMachine {
cls.class()
)
}))
.and(self.abstract_issubclass(subclass.clone(), cls))
.and(self.abstract_issubclass(subclass.incref(), cls))
}
}
/// Determines if `subclass` is a subclass of `cls`, either directly, indirectly or virtually
/// via the __subclasscheck__ magic method.
pub fn issubclass(&self, subclass: &PyObjectRef, cls: &PyObjectRef) -> PyResult<bool> {
pub fn issubclass(&self, subclass: &crate::PyObj, cls: &crate::PyObj) -> PyResult<bool> {
if cls.class().is(&self.ctx.types.type_type) {
if subclass.is(cls) {
return Ok(true);
@@ -1105,7 +1105,7 @@ impl VirtualMachine {
return self.recursive_issubclass(subclass, cls);
}
if let Ok(tuple) = PyTupleRef::try_from_object(self, cls.clone()) {
if let Ok(tuple) = PyTupleRef::try_from_object(self, cls.incref()) {
for typ in tuple.as_slice().iter() {
if self.with_recursion("in __subclasscheck__", || self.issubclass(subclass, typ))? {
return Ok(true);
@@ -1114,9 +1114,9 @@ impl VirtualMachine {
return Ok(false);
}
if let Ok(meth) = self.get_special_method(cls.clone(), "__subclasscheck__")? {
if let Ok(meth) = self.get_special_method(cls.incref(), "__subclasscheck__")? {
let ret = self.with_recursion("in __subclasscheck__", || {
meth.invoke((subclass.clone(),), self)
meth.invoke((subclass.incref(),), self)
})?;
return ret.try_to_bool(self);
}
@@ -1151,14 +1151,18 @@ impl VirtualMachine {
}
#[inline]
pub fn call_method<T>(&self, obj: &PyObjectRef, method_name: &str, args: T) -> PyResult
pub fn call_method<T>(&self, obj: &PyObj, method_name: &str, args: T) -> PyResult
where
T: IntoFuncArgs,
{
flame_guard!(format!("call_method({:?})", method_name));
PyMethod::get(obj.clone(), PyStr::from(method_name).into_ref(self), self)?
.invoke(args, self)
PyMethod::get(
obj.to_owned(),
PyStr::from(method_name).into_ref(self),
self,
)?
.invoke(args, self)
}
pub fn dir(&self, obj: Option<PyObjectRef>) -> PyResult<PyList> {
@@ -1197,13 +1201,13 @@ impl VirtualMachine {
.invoke(args, self)
}
fn _invoke(&self, callable: &PyObjectRef, args: FuncArgs) -> PyResult {
fn _invoke(&self, callable: &crate::PyObj, args: FuncArgs) -> PyResult {
vm_trace!("Invoke: {:?} {:?}", callable, args);
let slot_call = callable.class().mro_find_map(|cls| cls.slots.call.load());
match slot_call {
Some(slot_call) => {
self.trace_event(TraceEvent::Call)?;
let result = callable.with_ptr(|zelf| slot_call(zelf, args, self));
let result = slot_call(callable, args, self);
self.trace_event(TraceEvent::Return)?;
result
}
@@ -1217,7 +1221,7 @@ impl VirtualMachine {
#[inline(always)]
pub fn invoke<O, A>(&self, func: &O, args: A) -> PyResult
where
O: AsRef<PyObjectRef>,
O: AsRef<crate::PyObj>,
A: IntoFuncArgs,
{
self._invoke(func.as_ref(), args.into_args(self))
@@ -1233,8 +1237,8 @@ impl VirtualMachine {
}
}
fn _trace_event_inner(&self, event: TraceEvent) -> PyResult<()> {
let trace_func = self.trace_func.borrow().clone();
let profile_func = self.profile_func.borrow().clone();
let trace_func = self.trace_func.borrow().incref();
let profile_func = self.profile_func.borrow().incref();
if self.is_none(&trace_func) && self.is_none(&profile_func) {
return Ok(());
}
@@ -1244,7 +1248,7 @@ impl VirtualMachine {
return Ok(());
}
let frame = frame_ref.unwrap().as_object().clone();
let frame = frame_ref.unwrap().as_object().incref();
let event = self.ctx.new_str(event.to_string()).into();
let args = vec![frame, event, self.ctx.none()];
@@ -1266,7 +1270,7 @@ impl VirtualMachine {
Ok(())
}
pub fn extract_elements_func<T, F>(&self, value: &PyObjectRef, func: F) -> PyResult<Vec<T>>
pub fn extract_elements_func<T, F>(&self, value: &PyObj, func: F) -> PyResult<Vec<T>>
where
F: Fn(PyObjectRef) -> PyResult<T>,
{
@@ -1293,15 +1297,11 @@ impl VirtualMachine {
}
}
pub fn extract_elements<T: TryFromObject>(&self, value: &PyObjectRef) -> PyResult<Vec<T>> {
pub fn extract_elements<T: TryFromObject>(&self, value: &PyObj) -> PyResult<Vec<T>> {
self.extract_elements_func(value, |obj| T::try_from_object(self, obj))
}
pub fn map_iterable_object<F, R>(
&self,
obj: &PyObjectRef,
mut f: F,
) -> PyResult<PyResult<Vec<R>>>
pub fn map_iterable_object<F, R>(&self, obj: &PyObj, mut f: F) -> PyResult<PyResult<Vec<R>>>
where
F: FnMut(PyObjectRef) -> PyResult<R>,
{
@@ -1335,12 +1335,12 @@ impl VirtualMachine {
})
}
fn map_pyiter<F, R>(&self, value: &PyObjectRef, mut f: F) -> PyResult<Vec<R>>
fn map_pyiter<F, R>(&self, value: &PyObj, mut f: F) -> PyResult<Vec<R>>
where
F: FnMut(PyObjectRef) -> PyResult<R>,
{
let iter = value.clone().get_iter(self)?;
let cap = match self.length_hint(value.clone()) {
let iter = value.to_owned().get_iter(self)?;
let cap = match self.length_hint(value.to_owned()) {
Err(e) if e.class().is(&self.ctx.exceptions.runtime_error) => return Err(e),
Ok(Some(value)) => Some(value),
// Use a power of 2 as a default capacity.
@@ -1418,17 +1418,17 @@ impl VirtualMachine {
/// calls `unsupported` to determine fallback value.
pub fn call_or_unsupported<F>(
&self,
obj: &PyObjectRef,
arg: &PyObjectRef,
obj: &crate::PyObj,
arg: &crate::PyObj,
method: &str,
unsupported: F,
) -> PyResult
where
F: Fn(&VirtualMachine, &PyObjectRef, &PyObjectRef) -> PyResult,
F: Fn(&VirtualMachine, &crate::PyObj, &crate::PyObj) -> PyResult,
{
if let Some(method_or_err) = self.get_method(obj.clone(), method) {
if let Some(method_or_err) = self.get_method(obj.incref(), method) {
let method = method_or_err?;
let result = self.invoke(&method, (arg.clone(),))?;
let result = self.invoke(&method, (arg.incref(),))?;
if let PyArithmeticValue::Implemented(x) = PyArithmeticValue::from_object(self, result)
{
return Ok(x);
@@ -1449,11 +1449,11 @@ impl VirtualMachine {
/// 3. If above is not implemented, invokes `unsupported` for the result.
pub fn call_or_reflection(
&self,
lhs: &PyObjectRef,
rhs: &PyObjectRef,
lhs: &crate::PyObj,
rhs: &crate::PyObj,
default: &str,
reflection: &str,
unsupported: fn(&VirtualMachine, &PyObjectRef, &PyObjectRef) -> PyResult,
unsupported: fn(&VirtualMachine, &crate::PyObj, &crate::PyObj) -> PyResult,
) -> PyResult {
// Try to call the default method
self.call_or_unsupported(lhs, rhs, default, move |vm, lhs, rhs| {
@@ -1530,7 +1530,7 @@ impl VirtualMachine {
}
}
pub fn is_callable(&self, obj: &PyObjectRef) -> bool {
pub fn is_callable(&self, obj: &crate::PyObj) -> bool {
obj.class()
.mro_find_map(|cls| cls.slots.call.load())
.is_some()
@@ -1581,13 +1581,13 @@ impl VirtualMachine {
.map(|code| PyCode::new(self.map_codeobj(code)).into_ref(self))
}
pub fn _sub(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _sub(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__sub__", "__rsub__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "-"))
})
}
pub fn _isub(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _isub(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__isub__", |vm, a, b| {
vm.call_or_reflection(a, b, "__sub__", "__rsub__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "-="))
@@ -1595,13 +1595,13 @@ impl VirtualMachine {
})
}
pub fn _add(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _add(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__add__", "__radd__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "+"))
})
}
pub fn _iadd(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _iadd(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__iadd__", |vm, a, b| {
vm.call_or_reflection(a, b, "__add__", "__radd__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "+="))
@@ -1609,13 +1609,13 @@ impl VirtualMachine {
})
}
pub fn _mul(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _mul(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__mul__", "__rmul__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "*"))
})
}
pub fn _imul(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _imul(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__imul__", |vm, a, b| {
vm.call_or_reflection(a, b, "__mul__", "__rmul__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "*="))
@@ -1623,13 +1623,13 @@ impl VirtualMachine {
})
}
pub fn _matmul(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _matmul(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__matmul__", "__rmatmul__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "@"))
})
}
pub fn _imatmul(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _imatmul(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__imatmul__", |vm, a, b| {
vm.call_or_reflection(a, b, "__matmul__", "__rmatmul__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "@="))
@@ -1637,13 +1637,13 @@ impl VirtualMachine {
})
}
pub fn _truediv(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _truediv(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__truediv__", "__rtruediv__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "/"))
})
}
pub fn _itruediv(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _itruediv(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__itruediv__", |vm, a, b| {
vm.call_or_reflection(a, b, "__truediv__", "__rtruediv__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "/="))
@@ -1651,13 +1651,13 @@ impl VirtualMachine {
})
}
pub fn _floordiv(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _floordiv(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__floordiv__", "__rfloordiv__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "//"))
})
}
pub fn _ifloordiv(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _ifloordiv(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__ifloordiv__", |vm, a, b| {
vm.call_or_reflection(a, b, "__floordiv__", "__rfloordiv__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "//="))
@@ -1665,13 +1665,13 @@ impl VirtualMachine {
})
}
pub fn _pow(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _pow(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__pow__", "__rpow__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "**"))
})
}
pub fn _ipow(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _ipow(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__ipow__", |vm, a, b| {
vm.call_or_reflection(a, b, "__pow__", "__rpow__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "**="))
@@ -1679,13 +1679,13 @@ impl VirtualMachine {
})
}
pub fn _mod(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _mod(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__mod__", "__rmod__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "%"))
})
}
pub fn _imod(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _imod(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__imod__", |vm, a, b| {
vm.call_or_reflection(a, b, "__mod__", "__rmod__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "%="))
@@ -1693,19 +1693,19 @@ impl VirtualMachine {
})
}
pub fn _divmod(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _divmod(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__divmod__", "__rdivmod__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "divmod"))
})
}
pub fn _lshift(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _lshift(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__lshift__", "__rlshift__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "<<"))
})
}
pub fn _ilshift(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _ilshift(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__ilshift__", |vm, a, b| {
vm.call_or_reflection(a, b, "__lshift__", "__rlshift__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "<<="))
@@ -1713,13 +1713,13 @@ impl VirtualMachine {
})
}
pub fn _rshift(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _rshift(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__rshift__", "__rrshift__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, ">>"))
})
}
pub fn _irshift(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _irshift(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__irshift__", |vm, a, b| {
vm.call_or_reflection(a, b, "__rshift__", "__rrshift__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, ">>="))
@@ -1727,13 +1727,13 @@ impl VirtualMachine {
})
}
pub fn _xor(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _xor(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__xor__", "__rxor__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "^"))
})
}
pub fn _ixor(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _ixor(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__ixor__", |vm, a, b| {
vm.call_or_reflection(a, b, "__xor__", "__rxor__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "^="))
@@ -1741,13 +1741,13 @@ impl VirtualMachine {
})
}
pub fn _or(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _or(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__or__", "__ror__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "|"))
})
}
pub fn _ior(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _ior(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__ior__", |vm, a, b| {
vm.call_or_reflection(a, b, "__or__", "__ror__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "|="))
@@ -1755,13 +1755,13 @@ impl VirtualMachine {
})
}
pub fn _and(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _and(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_reflection(a, b, "__and__", "__rand__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "&"))
})
}
pub fn _iand(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult {
pub fn _iand(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult {
self.call_or_unsupported(a, b, "__iand__", |vm, a, b| {
vm.call_or_reflection(a, b, "__and__", "__rand__", |vm, a, b| {
Err(vm.new_unsupported_binop_error(a, b, "&="))
@@ -1769,32 +1769,32 @@ impl VirtualMachine {
})
}
pub fn _abs(&self, a: &PyObjectRef) -> PyResult<PyObjectRef> {
self.get_special_method(a.clone(), "__abs__")?
pub fn _abs(&self, a: &crate::PyObj) -> PyResult<PyObjectRef> {
self.get_special_method(a.incref(), "__abs__")?
.map_err(|_| self.new_unsupported_unary_error(a, "abs()"))?
.invoke((), self)
}
pub fn _pos(&self, a: &PyObjectRef) -> PyResult {
self.get_special_method(a.clone(), "__pos__")?
pub fn _pos(&self, a: &crate::PyObj) -> PyResult {
self.get_special_method(a.incref(), "__pos__")?
.map_err(|_| self.new_unsupported_unary_error(a, "unary +"))?
.invoke((), self)
}
pub fn _neg(&self, a: &PyObjectRef) -> PyResult {
self.get_special_method(a.clone(), "__neg__")?
pub fn _neg(&self, a: &crate::PyObj) -> PyResult {
self.get_special_method(a.incref(), "__neg__")?
.map_err(|_| self.new_unsupported_unary_error(a, "unary -"))?
.invoke((), self)
}
pub fn _invert(&self, a: &PyObjectRef) -> PyResult {
self.get_special_method(a.clone(), "__invert__")?
pub fn _invert(&self, a: &crate::PyObj) -> PyResult {
self.get_special_method(a.incref(), "__invert__")?
.map_err(|_| self.new_unsupported_unary_error(a, "unary ~"))?
.invoke((), self)
}
pub fn obj_len_opt(&self, obj: &PyObjectRef) -> Option<PyResult<usize>> {
self.get_special_method(obj.clone(), "__len__")
pub fn obj_len_opt(&self, obj: &crate::PyObj) -> Option<PyResult<usize>> {
self.get_special_method(obj.incref(), "__len__")
.map(Result::ok)
.transpose()
.map(|meth| {
@@ -1962,11 +1962,11 @@ impl VirtualMachine {
}
}
pub fn bool_eq(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult<bool> {
pub fn bool_eq(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult<bool> {
a.rich_compare_bool(b, PyComparisonOp::Eq, self)
}
pub fn identical_or_equal(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult<bool> {
pub fn identical_or_equal(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult<bool> {
if a.is(b) {
Ok(true)
} else {
@@ -1974,7 +1974,7 @@ impl VirtualMachine {
}
}
pub fn bool_seq_lt(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult<Option<bool>> {
pub fn bool_seq_lt(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult<Option<bool>> {
let value = if a.rich_compare_bool(b, PyComparisonOp::Lt, self)? {
Some(true)
} else if !self.bool_eq(a, b)? {
@@ -1985,7 +1985,7 @@ impl VirtualMachine {
Ok(value)
}
pub fn bool_seq_gt(&self, a: &PyObjectRef, b: &PyObjectRef) -> PyResult<Option<bool>> {
pub fn bool_seq_gt(&self, a: &crate::PyObj, b: &crate::PyObj) -> PyResult<Option<bool>> {
let value = if a.rich_compare_bool(b, PyComparisonOp::Gt, self)? {
Some(true)
} else if !self.bool_eq(a, b)? {
@@ -2013,7 +2013,7 @@ impl VirtualMachine {
#[doc(hidden)]
pub fn __module_set_attr(
&self,
module: &PyObjectRef,
module: &crate::PyObj,
attr_name: impl IntoPyStrRef,
attr_value: impl Into<PyObjectRef>,
) -> PyResult<()> {
@@ -2035,7 +2035,10 @@ mod sealed {
}
/// A sealed marker trait for `DictKey` types that always become an exact instance of `str`
pub trait Internable: sealed::SealedInternable + crate::dictdatatype::DictKey {}
pub trait Internable:
sealed::SealedInternable + crate::dictdatatype::DictKey + IntoPyObject
{
}
impl Internable for String {}
@@ -2052,7 +2055,7 @@ pub struct ReprGuard<'vm> {
impl<'vm> ReprGuard<'vm> {
/// Returns None if the guard against 'obj' is still held otherwise returns the guard. The guard
/// which is released if dropped.
pub fn enter(vm: &'vm VirtualMachine, obj: &PyObjectRef) -> Option<Self> {
pub fn enter(vm: &'vm VirtualMachine, obj: &crate::PyObj) -> Option<Self> {
let mut guards = vm.repr_guards.borrow_mut();
// Should this be a flag on the obj itself? putting it in a global variable for now until it
@@ -2174,15 +2177,15 @@ impl PyThread {
#[cfg(test)]
mod tests {
use super::Interpreter;
use crate::builtins::{int, PyStr};
use super::*;
use crate::builtins::int;
use num_bigint::ToBigInt;
#[test]
fn test_add_py_integers() {
Interpreter::default().enter(|vm| {
let a = vm.ctx.new_int(33_i32).into();
let b = vm.ctx.new_int(12_i32).into();
let a: PyObjectRef = vm.ctx.new_int(33_i32).into();
let b: PyObjectRef = vm.ctx.new_int(12_i32).into();
let res = vm._add(&a, &b).unwrap();
let value = int::get_value(&res);
assert_eq!(*value, 45_i32.to_bigint().unwrap());

View File

@@ -9,10 +9,9 @@ use rustpython_vm::{
function::{ArgCallable, IntoPyObject, OptionalArg, OptionalOption, PosArgs},
protocol::PyIterReturn,
types::{IterNext, IterNextIterable},
PyClassImpl, PyObjectRef, PyObjectWrap, PyRef, PyResult, PyValue, TryFromObject,
Py, PyClassImpl, PyObjectRef, PyObjectWrap, PyRef, PyResult, PyValue, TryFromObject,
VirtualMachine,
};
use std::ops::Deref;
use std::{cell, fmt, future};
use wasm_bindgen::{closure::Closure, prelude::*, JsCast};
use wasm_bindgen_futures::{future_to_promise, JsFuture};
@@ -174,7 +173,7 @@ impl PyJsValue {
.value
.dyn_ref::<js_sys::Function>()
.ok_or_else(|| vm.new_type_error("JS value is not callable".to_owned()))?;
let js_args = args.iter().map(|x| x.deref()).collect::<Array>();
let js_args = args.iter().map(|x| -> &PyJsValue { x }).collect::<Array>();
let res = match opts.this {
Some(this) => Reflect::apply(func, &this.value, &js_args),
None => call_func(func, &js_args),
@@ -189,7 +188,7 @@ impl PyJsValue {
args: PosArgs<PyJsValueRef>,
vm: &VirtualMachine,
) -> PyResult<PyJsValue> {
let js_args = args.iter().map(|x| x.deref()).collect::<Array>();
let js_args = args.iter().map(|x| -> &PyJsValue { x }).collect::<Array>();
call_method(&self.value, &name.into_jsvalue(), &js_args)
.map(PyJsValue::new)
.map_err(|err| new_js_error(vm, err))
@@ -210,7 +209,7 @@ impl PyJsValue {
.prototype
.as_ref()
.and_then(|proto| proto.value.dyn_ref::<js_sys::Function>());
let js_args = args.iter().map(|x| x.deref()).collect::<Array>();
let js_args = args.iter().map(|x| -> &PyJsValue { x }).collect::<Array>();
let constructed_result = if let Some(proto) = proto {
Reflect::construct_with_new_target(ctor, &js_args, proto)
} else {
@@ -585,7 +584,7 @@ impl AwaitPromise {
impl IterNextIterable for AwaitPromise {}
impl IterNext for AwaitPromise {
fn next(zelf: &PyRef<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
fn next(zelf: &Py<Self>, vm: &VirtualMachine) -> PyResult<PyIterReturn> {
zelf.send(None, vm)
}
}

View File

@@ -189,7 +189,7 @@ impl WASMVirtualMachine {
pub(crate) fn push_held_rc(&self, obj: PyObjectRef) -> Result<PyObjectWeak, JsValue> {
self.with(|stored_vm| {
let weak = PyObjectRef::downgrade(&obj);
let weak = obj.downgrade();
stored_vm.held_objects.borrow_mut().push(obj);
weak
})