diff --git a/derive-impl/src/pyclass.rs b/derive-impl/src/pyclass.rs index 8ef479976..6477111dc 100644 --- a/derive-impl/src/pyclass.rs +++ b/derive-impl/src/pyclass.rs @@ -702,7 +702,9 @@ where let slot_name = slot_ident.to_string(); let tokens = { const NON_ATOMIC_SLOTS: &[&str] = &["as_buffer"]; - const POINTER_SLOTS: &[&str] = &["as_number", "as_sequence", "as_mapping"]; + const POINTER_SLOTS: &[&str] = &["as_sequence", "as_mapping"]; + const STATIC_SLOTS: &[&str] = &["as_number"]; + if NON_ATOMIC_SLOTS.contains(&slot_name.as_str()) { quote_spanned! { span => slots.#slot_ident = Some(Self::#ident as _); @@ -711,6 +713,10 @@ where quote_spanned! { span => slots.#slot_ident.store(Some(PointerSlot::from(Self::#ident()))); } + } else if STATIC_SLOTS.contains(&&slot_name.as_str()) { + quote_spanned! { span => + slots.#slot_ident = Self::#ident(); + } } else { quote_spanned! { span => slots.#slot_ident.store(Some(Self::#ident as _)); diff --git a/vm/src/protocol/number.rs b/vm/src/protocol/number.rs index c0a530818..050b3837b 100644 --- a/vm/src/protocol/number.rs +++ b/vm/src/protocol/number.rs @@ -197,6 +197,11 @@ impl PyNumberMethods { matrix_multiply: None, inplace_matrix_multiply: None, }; + + pub fn not_implemented() -> &'static PyNumberMethods { + static GLOBAL_NOT_IMPLEMENTED: PyNumberMethods = PyNumberMethods::NOT_IMPLEMENTED; + &GLOBAL_NOT_IMPLEMENTED + } } #[derive(Copy, Clone)] diff --git a/vm/src/types/slot.rs b/vm/src/types/slot.rs index f298419f4..b3c056877 100644 --- a/vm/src/types/slot.rs +++ b/vm/src/types/slot.rs @@ -27,7 +27,6 @@ macro_rules! atomic_func { // The corresponding field in CPython is `tp_` prefixed. // e.g. name -> tp_name -#[derive(Default)] #[non_exhaustive] pub struct PyTypeSlots { /// # Safety @@ -41,7 +40,10 @@ pub struct PyTypeSlots { // Methods to implement standard operations // Method suites for standard classes - pub as_number: AtomicCell>>, + /// # Safety + /// use only when initializing + /// use slot number for protocol + pub(crate) as_number: &'static PyNumberMethods, pub as_sequence: AtomicCell>>, pub as_mapping: AtomicCell>>, @@ -93,6 +95,36 @@ pub struct PyTypeSlots { pub number: PyNumberSlots, } +impl Default for PyTypeSlots { + fn default() -> Self { + Self { + name: Default::default(), + basicsize: Default::default(), + as_number: PyNumberMethods::not_implemented(), + as_sequence: Default::default(), + as_mapping: Default::default(), + hash: Default::default(), + call: Default::default(), + repr: Default::default(), + getattro: Default::default(), + setattro: Default::default(), + as_buffer: Default::default(), + richcompare: Default::default(), + iter: Default::default(), + iternext: Default::default(), + flags: Default::default(), + doc: Default::default(), + descr_get: Default::default(), + descr_set: Default::default(), + init: Default::default(), + new: Default::default(), + del: Default::default(), + member_count: Default::default(), + number: Default::default(), + } + } +} + impl PyTypeSlots { pub fn new(name: &'static str, flags: PyTypeFlags) -> Self { Self {