rust-cpython: remove useless Option<$leaked> from py_shared_iterator
We no longer need to carefully drop the iterator when it's consumed. Mutation
is allowed even if the iterator exists.
There's a minor behavior change: next(iter) may return/raise something other
than StopIteration if it's called after the iterator has been fully consumed,
and if the Rust object isn't a FusedIterator.
--- a/rust/hg-cpython/src/ref_sharing.rs Sat Oct 12 20:26:38 2019 +0900
+++ b/rust/hg-cpython/src/ref_sharing.rs Sat Oct 12 20:48:30 2019 +0900
@@ -570,25 +570,14 @@
$success_type: ty
) => {
py_class!(pub class $name |py| {
- data inner: RefCell<Option<$leaked>>;
+ data inner: RefCell<$leaked>;
def __next__(&self) -> PyResult<$success_type> {
- let mut inner_opt = self.inner(py).borrow_mut();
- if let Some(leaked) = inner_opt.as_mut() {
- let mut iter = leaked.try_borrow_mut(py)?;
- match iter.next() {
- None => {
- drop(iter);
- // replace Some(inner) by None, drop $leaked
- inner_opt.take();
- Ok(None)
- }
- Some(res) => {
- $success_func(py, res)
- }
- }
- } else {
- Ok(None)
+ let mut leaked = self.inner(py).borrow_mut();
+ let mut iter = leaked.try_borrow_mut(py)?;
+ match iter.next() {
+ None => Ok(None),
+ Some(res) => $success_func(py, res),
}
}
@@ -604,7 +593,7 @@
) -> PyResult<Self> {
Self::create_instance(
py,
- RefCell::new(Some(leaked)),
+ RefCell::new(leaked),
)
}
}