From 3e3fed9c180d8f447fa24c853eb9986abcc0d03d Mon Sep 17 00:00:00 2001 From: Nikolay Kim Date: Fri, 23 Jun 2017 13:42:46 -0700 Subject: [PATCH] remove True and False python methods --- src/objects/boolobject.rs | 17 +++++----- src/python.rs | 38 ++++++++--------------- src/pythonrun.rs | 65 +++++++++++++++++++++++++++------------ 3 files changed, 66 insertions(+), 54 deletions(-) diff --git a/src/objects/boolobject.rs b/src/objects/boolobject.rs index fd5b13c0..66a6f170 100644 --- a/src/objects/boolobject.rs +++ b/src/objects/boolobject.rs @@ -32,8 +32,7 @@ impl ToPyObject for bool { fn to_object(&self, py: Python) -> PyObject { unsafe { PyObject::from_borrowed_ptr( - py, - if *self { ffi::Py_True() } else { ffi::Py_False() }) + py, if *self { ffi::Py_True() } else { ffi::Py_False() }) } } @@ -64,7 +63,7 @@ pyobject_extract!(py, obj to bool => { #[cfg(test)] mod test { use python::Python; - use objects::PyInstance; + use objects::{PyBool, PyInstance}; use conversion::ToPyObject; use objectprotocol::ObjectProtocol; @@ -72,19 +71,19 @@ mod test { fn test_true() { let gil = Python::acquire_gil(); let py = gil.python(); - assert!(py.True().is_true()); - let t: &PyInstance = py.True().into(); + assert!(PyBool::new(py, true).is_true()); + let t: &PyInstance = PyBool::new(py, true).into(); assert_eq!(true, t.extract().unwrap()); - assert!(true.to_object(py) == py.True().into()); + assert!(true.to_object(py) == PyBool::new(py, true).into()); } #[test] fn test_false() { let gil = Python::acquire_gil(); let py = gil.python(); - assert!(!py.False().is_true()); - let t: &PyInstance = py.False().into(); + assert!(!PyBool::new(py, false).is_true()); + let t: &PyInstance = PyBool::new(py, false).into(); assert_eq!(false, t.extract().unwrap()); - assert!(false.to_object(py) == py.False().into()); + assert!(false.to_object(py) == PyBool::new(py, false).into()); } } diff --git a/src/python.rs b/src/python.rs index 2db3a2bc..ec6cb30c 100644 --- a/src/python.rs +++ b/src/python.rs @@ -11,7 +11,7 @@ use ffi; use typeob::{PyTypeInfo, PyTypeObject, PyObjectAlloc}; use instance::{Py, PyToken}; use pointer::PyObject; -use objects::{PyInstance, PyType, PyBool, PyDict, PyModule}; +use objects::{PyInstance, PyType, PyDict, PyModule}; use err::{PyErr, PyResult, PyDowncastError, ToPyErr}; use pythonrun::{self, GILGuard}; @@ -213,20 +213,6 @@ impl<'p> Python<'p> { unsafe { PyObject::from_borrowed_ptr(self, ffi::Py_None()) } } - /// Gets the Python builtin value `True`. - #[allow(non_snake_case)] // the Python keyword starts with uppercase - #[inline] - pub fn True(self) -> &'p PyBool { - PyBool::new(self, true) - } - - /// Gets the Python builtin value `False`. - #[allow(non_snake_case)] // the Python keyword starts with uppercase - #[inline] - pub fn False(self) -> &'p PyBool { - PyBool::new(self, false) - } - /// Gets the Python builtin value `NotImplemented`. #[allow(non_snake_case)] // the Python keyword starts with uppercase #[inline] @@ -281,7 +267,7 @@ impl<'p> Python<'p> { where D: PyDowncastFrom { unsafe { - let p = pythonrun::register(self, obj); + let p = pythonrun::register_owned(self, obj); ::downcast_from(p) } } @@ -289,7 +275,7 @@ impl<'p> Python<'p> { pub unsafe fn cast_as(self, obj: PyObject) -> &'p D where D: PyDowncastFrom { - let p = pythonrun::register(self, obj); + let p = pythonrun::register_owned(self, obj); ::unchecked_downcast_from(p) } @@ -297,7 +283,7 @@ impl<'p> Python<'p> { where D: PyDowncastFrom { let obj = PyObject::from_owned_ptr_or_panic(self, ptr); - let p = pythonrun::register(self, obj); + let p = pythonrun::register_owned(self, obj); ::unchecked_downcast_from(p) } @@ -306,7 +292,7 @@ impl<'p> Python<'p> { { let obj = PyObject::from_owned_ptr_or_err(self, ptr)?; unsafe { - let p = pythonrun::register(self, obj); + let p = pythonrun::register_owned(self, obj); Ok(::unchecked_downcast_from(p)) } } @@ -319,7 +305,7 @@ impl<'p> Python<'p> { } else { unsafe { let obj = PyObject::from_owned_ptr(self, ptr); - let p = pythonrun::register(self, obj); + let p = pythonrun::register_owned(self, obj); Some(::unchecked_downcast_from(p)) } } @@ -329,7 +315,7 @@ impl<'p> Python<'p> { where D: PyDowncastFrom { let obj = PyObject::from_borrowed_ptr(self, ptr); - let p = pythonrun::register(self, obj); + let p = pythonrun::register_borrowed(self, obj); ::unchecked_downcast_from(p) } @@ -338,7 +324,7 @@ impl<'p> Python<'p> { where D: PyDowncastFrom { let obj = PyObject::from_borrowed_ptr_or_err(self, ptr)?; - let p = pythonrun::register(self, obj); + let p = pythonrun::register_borrowed(self, obj); Ok(::unchecked_downcast_from(p)) } @@ -350,7 +336,7 @@ impl<'p> Python<'p> { None } else { let obj = PyObject::from_borrowed_ptr(self, ptr); - let p = pythonrun::register(self, obj); + let p = pythonrun::register_borrowed(self, obj); Some(::unchecked_downcast_from(p)) } } @@ -359,13 +345,13 @@ impl<'p> Python<'p> { where D: PyDowncastFrom { let obj = PyObject::from_borrowed_ptr(self, ptr); - let p = pythonrun::register(self, obj); + let p = pythonrun::register_borrowed(self, obj); ::unchecked_mut_downcast_from(p) } pub fn track_object(self, obj: PyObject) -> &'p PyInstance { - unsafe { pythonrun::register(self, obj) } + unsafe { pythonrun::register_owned(self, obj) } } } @@ -405,7 +391,7 @@ mod test { fn test_is_instance() { let gil = Python::acquire_gil(); let py = gil.python(); - assert!(py.is_instance::(py.True().into()).unwrap()); + assert!(py.is_instance::(PyBool::new(py, true).into()).unwrap()); let list = PyList::new(py, &[1, 2, 3, 4]); assert!(!py.is_instance::(list.as_ref()).unwrap()); assert!(py.is_instance::(list.as_ref()).unwrap()); diff --git a/src/pythonrun.rs b/src/pythonrun.rs index 3dd83ea6..a5c6b25d 100644 --- a/src/pythonrun.rs +++ b/src/pythonrun.rs @@ -69,7 +69,8 @@ pub fn prepare_freethreaded_python() { pub fn prepare_pyo3_library() { START_PYO3.call_once(|| unsafe { // initialize release pool - POOL = Box::into_raw(Box::new(Vec::with_capacity(250))); + OWNED = Box::into_raw(Box::new(Vec::with_capacity(250))); + BORROWED = Box::into_raw(Box::new(Vec::with_capacity(250))); }); } @@ -86,7 +87,8 @@ pub fn prepare_pyo3_library() { /// ``` #[must_use] pub struct GILGuard { - pos: usize, + owned: usize, + borrowed: usize, gstate: ffi::PyGILState_STATE, // hack to opt out of Send on stable rust, which doesn't // have negative impls @@ -97,25 +99,30 @@ pub struct GILGuard { impl Drop for GILGuard { fn drop(&mut self) { unsafe { - drain(self.pos); + drain(self.owned, self.borrowed); ffi::PyGILState_Release(self.gstate); } } } -static mut POOL: *mut Vec = 0 as *mut _; +static mut OWNED: *mut Vec = 0 as *mut _; +static mut BORROWED: *mut Vec = 0 as *mut _; pub struct Pool { - pos: usize, + owned: usize, + borrowed: usize, no_send: marker::PhantomData>, } impl Pool { #[inline] pub unsafe fn new() -> Pool { - let pool: &'static mut Vec = mem::transmute(POOL); - Pool{ pos: pool.len(), no_send: marker::PhantomData } + let owned: &'static mut Vec = mem::transmute(OWNED); + let borrowed: &'static mut Vec = mem::transmute(BORROWED); + Pool{ owned: owned.len(), + borrowed: borrowed.len(), + no_send: marker::PhantomData } } // /// Retrieves the marker type that proves that the GIL was acquired. // #[inline] @@ -127,27 +134,43 @@ impl Pool { impl Drop for Pool { fn drop(&mut self) { unsafe { - drain(self.pos); + drain(self.owned, self.borrowed); } } } -pub unsafe fn register<'p>(_py: Python<'p>, obj: PyObject) -> &'p PyInstance { - let pool: &'static mut Vec = mem::transmute(POOL); +pub unsafe fn register_owned<'p>(_py: Python<'p>, obj: PyObject) -> &'p PyInstance { + let pool: &'static mut Vec = mem::transmute(OWNED); pool.push(obj); mem::transmute(&pool[pool.len()-1]) } -pub unsafe fn drain(pos: usize) { - let pool: &'static mut Vec = mem::transmute(POOL); +pub unsafe fn register_borrowed<'p>(_py: Python<'p>, obj: PyObject) -> &'p PyInstance { + let pool: &'static mut Vec = mem::transmute(BORROWED); + pool.push(obj); + mem::transmute(&pool[pool.len()-1]) +} - let len = pool.len(); - if pos < len { - for ob in &mut pool[pos..len] { +pub unsafe fn drain(owned: usize, borrowed: usize) { + let owned_pool: &'static mut Vec = mem::transmute(OWNED); + + let len = owned_pool.len(); + if owned < len { + for ob in &mut owned_pool[owned..len] { ffi::Py_DECREF(ob.as_ptr()); } - pool.set_len(pos); + owned_pool.set_len(owned); } + + let borrowed_pool: &'static mut Vec = mem::transmute(BORROWED); + let len = borrowed_pool.len(); + if borrowed < len { + for ob in &mut borrowed_pool[borrowed..len] { + ffi::Py_DECREF(ob.as_ptr()); + } + borrowed_pool.set_len(borrowed); + } + } @@ -157,13 +180,17 @@ impl GILGuard { /// If the Python runtime is not already initialized, this function will initialize it. /// See [prepare_freethreaded_python()](fn.prepare_freethreaded_python.html) for details. pub fn acquire() -> GILGuard { - ::pythonrun::prepare_freethreaded_python(); + prepare_freethreaded_python(); unsafe { let gstate = ffi::PyGILState_Ensure(); // acquire GIL - let pool: &'static mut Vec = mem::transmute(POOL); + let owned: &'static mut Vec = mem::transmute(OWNED); + let borrowed: &'static mut Vec = mem::transmute(BORROWED); - GILGuard { pos: pool.len(), gstate: gstate, no_send: marker::PhantomData } + GILGuard { owned: owned.len(), + borrowed: borrowed.len(), + gstate: gstate, + no_send: marker::PhantomData } } }