Skip to content

Commit 4f10fde

Browse files
committed
Fix iter protocol now try use sequence protocol is no iter slot
1 parent c9bec8c commit 4f10fde

2 files changed

Lines changed: 16 additions & 6 deletions

File tree

‎vm/src/protocol/iter.rs‎

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
use crate::{
22
builtins::iter::PySequenceIterator,
33
function::{IntoPyObject, IntoPyResult},
4+
protocol::PySequence,
45
PyObjectRef, PyObjectWrap, PyResult, PyValue, TryFromObject, TypeProtocol, VirtualMachine,
56
};
67
use std::borrow::Borrow;
@@ -120,11 +121,14 @@ impl TryFromObject for PyIter<PyObjectRef> {
120121
)))
121122
}
122123
} else {
123-
// TODO: __getitem__ method lookup must be replaced by sequence protocol checking
124-
vm.get_method_or_type_error(iter_target.clone(), "__getitem__", || {
125-
format!("'{}' object is not iterable", iter_target.class().name())
126-
})?;
127-
Ok(Self(PySequenceIterator::new(iter_target).into_object(vm)))
124+
if PySequence::check(&iter_target, vm) {
125+
Ok(Self(PySequenceIterator::new(iter_target).into_object(vm)))
126+
} else {
127+
Err(vm.new_type_error(format!(
128+
"'{}' object is not iterable",
129+
iter_target.class().name()
130+
)))
131+
}
128132
}
129133
}
130134
}

‎vm/src/protocol/sequence.rs‎

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,13 @@ impl PySequence {
3737
return false;
3838
}
3939
cls.mro_find_map(|x| x.slots.as_sequence.load())
40-
.map(|f| f(obj, vm).item.is_some())
40+
.map(|f| {
41+
// FIXME: we may avoid the check if we assume all the builtins
42+
// implement fn item() for the sequence protocol
43+
// all the python class must has __getitem__ if they ident as
44+
// sequence protocol implemented
45+
f(obj, vm).item.is_some()
46+
})
4147
.unwrap_or(false)
4248
}
4349

0 commit comments

Comments
 (0)