Match canonical static builtin profiler labels and metadata

Normalize the raw builtin receiver instead of its call-argument accessor.
Snapshot static method module metadata at construction, matching CPython,
so explicit module mutation and deletion remain observable. Avoid a
profiler-time fallback that would obscure deleted metadata.

Correct float.__getformat__ to CPython's classmethod calling convention,
including subclass binding, rather than special-casing its profiler label.

Assisted-by: dot:GPT-6.1
This commit is contained in:
youknowdot committed 2026-10-21 22:04:06 +09:00
1 parent 52f23593e2
commit 94f8b2b778
3 files changed
+28 -4

No files matched your search

+6 -2
View File
@@ -305,8 +305,12 @@ impl Py<PyFloat> {
})
}
#[pystaticmethod]
fn __getformat__(typestr: PyUtf8StrRef, vm: &VirtualMachine) -> PyResult<String> {
#[pyclassmethod]
fn __getformat__(
_cls: PyTypeRef,
typestr: PyUtf8StrRef,
vm: &VirtualMachine,
) -> PyResult<String> {
if !matches!(typestr.as_str(), "double" | "float") {
return Err(
vm.new_value_error("__getformat__() argument 1 must be 'double' or 'float'")
+15 -1
View File
@@ -7,6 +7,7 @@ use crate::{
},
class::PyClassDef,
function::{FuncArgs, IntoPyNativeFn, PyNativeFn, SigArg},
types::PyTypeFlags,
};
bitflags::bitflags! {
@@ -294,8 +295,21 @@ impl PyMethodDef {
class: &'static Py<PyType>,
) -> PyRef<PyNativeFunction> {
debug_assert!(self.flags.contains(PyMethodFlags::STATIC));
// Match PyCFunction_NewEx(meth, type, type_module(type)): snapshot
// module metadata here so later mutation/deletion remains observable.
let module = if class.slots.flags.has_feature(PyTypeFlags::HEAPTYPE) {
class.attributes.get(ctx.intern_str("__module__"))
} else {
let name = class.slot_name();
let module = name
.rsplit_once('.')
.map_or("builtins", |(module, _)| module);
Some(ctx.intern_str(module).to_owned().into())
};
// m_self is the type; STATIC skips prepending it on call.
self.build_bound_function(ctx, class.to_owned().into())
let function = self.build_bound_function(ctx, class.to_owned().into());
drop(function.module.store(module));
function
}
/// Concatenate method groups. A pending body is copied from `docs`, then cleared.
+7 -1
View File
@@ -456,8 +456,14 @@ mod _lsprof {
Self::Function(function) => function,
};
let name = function.value.name;
// CPython normalizes the raw m_self, including STATIC's hidden
// type receiver, rather than its call-argument accessor.
let receiver = function
.zelf
.as_deref()
.or(function.module_object.as_deref());
let module = function.module.load_owned();
let label = if let Some(receiver) = function.get_self() {
let label = if let Some(receiver) = receiver {
if let Some(descriptor) = receiver.class().get_attr(vm.ctx.intern_str(name))
&& let Ok(label) = descriptor.repr(vm)
{