From afde078a1e31a2c6f275626fc89dcfa75b3fa223 Mon Sep 17 00:00:00 2001 From: ShaharNaveh <50263213+ShaharNaveh@users.noreply.github.com> Date: Tue, 3 Feb 2026 10:30:48 +0200 Subject: [PATCH 1/4] Use `num_enum` crate for oparg types --- Cargo.lock | 1 + crates/compiler-core/Cargo.toml | 1 + .../compiler-core/src/bytecode/instruction.rs | 6 +- crates/compiler-core/src/bytecode/oparg.rs | 609 ++++++++---------- 4 files changed, 282 insertions(+), 335 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 480207932ae..ee6419bd262 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3162,6 +3162,7 @@ dependencies = [ "lz4_flex", "malachite-bigint", "num-complex", + "num_enum", "ruff_source_file", "rustpython-wtf8", ] diff --git a/crates/compiler-core/Cargo.toml b/crates/compiler-core/Cargo.toml index f4e619b95a4..6a03f02c24f 100644 --- a/crates/compiler-core/Cargo.toml +++ b/crates/compiler-core/Cargo.toml @@ -17,6 +17,7 @@ bitflags = { workspace = true } itertools = { workspace = true } malachite-bigint = { workspace = true } num-complex = { workspace = true } +num_enum = { workspace = true } lz4_flex = "0.12" diff --git a/crates/compiler-core/src/bytecode/instruction.rs b/crates/compiler-core/src/bytecode/instruction.rs index ee36220b538..99080c95a68 100644 --- a/crates/compiler-core/src/bytecode/instruction.rs +++ b/crates/compiler-core/src/bytecode/instruction.rs @@ -1247,7 +1247,7 @@ impl Arg { #[inline] pub fn new(arg: T) -> (Self, OpArg) { - (Self(PhantomData), OpArg(arg.to_op_arg())) + (Self(PhantomData), OpArg(arg.into())) } #[inline] @@ -1265,7 +1265,7 @@ impl Arg { #[inline(always)] pub fn try_get(self, arg: OpArg) -> Result { - T::from_op_arg(arg.0) + T::try_from(arg.0).map_err(|_| MarshalError::InvalidBytecode) } /// # Safety @@ -1273,7 +1273,7 @@ impl Arg { #[inline(always)] pub unsafe fn get_unchecked(self, arg: OpArg) -> T { // SAFETY: requirements forwarded from caller - unsafe { T::from_op_arg(arg.0).unwrap_unchecked() } + unsafe { T::try_from(arg.0).unwrap_unchecked() } } } diff --git a/crates/compiler-core/src/bytecode/oparg.rs b/crates/compiler-core/src/bytecode/oparg.rs index 724fd6fcd10..c8125d7aaec 100644 --- a/crates/compiler-core/src/bytecode/oparg.rs +++ b/crates/compiler-core/src/bytecode/oparg.rs @@ -1,17 +1,14 @@ use bitflags::bitflags; +use num_enum::{IntoPrimitive, TryFromPrimitive}; -use core::{fmt, num::NonZeroU8}; +use core::fmt; use crate::{ bytecode::{CodeUnit, instruction::Instruction}, marshal::MarshalError, }; -pub trait OpArgType: Copy { - fn from_op_arg(x: u32) -> Result; - - fn to_op_arg(self) -> u32; -} +pub trait OpArgType: Copy + Into + TryFrom {} /// Opcode argument that may be extended by a prior ExtendedArg. #[derive(Copy, Clone, PartialEq, Eq)] @@ -112,8 +109,9 @@ impl OpArgState { /// ## See also /// /// - [CPython FVC_* flags](https://github.com/python/cpython/blob/8183fa5e3f78ca6ab862de7fb8b14f3d929421e0/Include/ceval.h#L129-L132) -#[repr(u8)] -#[derive(Copy, Clone, Debug, Hash, PartialEq, Eq)] +#[derive(Clone, Copy, Debug, Eq, Hash, IntoPrimitive, PartialEq, TryFromPrimitive)] +#[num_enum(error_type(name = MarshalError, constructor = new_invalid_bytecode))] +#[repr(u32)] pub enum ConvertValueOparg { /// No conversion. /// @@ -121,6 +119,8 @@ pub enum ConvertValueOparg { /// f"{x}" /// f"{x:4}" /// ``` + // Ruff `ConversionFlag::None` is `-1i8`, when its converted to `u8` its value is `u8::MAX`. + #[num_enum(alternatives = [255])] None = 0, /// Converts by calling `str()`. /// @@ -159,28 +159,11 @@ impl fmt::Display for ConvertValueOparg { } } -impl OpArgType for ConvertValueOparg { - #[inline] - fn from_op_arg(x: u32) -> Result { - Ok(match x { - // Ruff `ConversionFlag::None` is `-1i8`, - // when its converted to `u8` its value is `u8::MAX` - 0 | 255 => Self::None, - 1 => Self::Str, - 2 => Self::Repr, - 3 => Self::Ascii, - _ => return Err(MarshalError::InvalidBytecode), - }) - } - - #[inline] - fn to_op_arg(self) -> u32 { - self as u32 - } -} +impl OpArgType for ConvertValueOparg {} /// Resume type for the RESUME instruction -#[derive(Copy, Clone, Debug, Hash, PartialEq, Eq)] +#[derive(Copy, Clone, Debug, Hash, PartialEq, Eq, IntoPrimitive, TryFromPrimitive)] +#[num_enum(error_type(name = MarshalError, constructor = new_invalid_bytecode))] #[repr(u32)] pub enum ResumeType { AtFuncStart = 0, @@ -189,145 +172,105 @@ pub enum ResumeType { AfterAwait = 3, } -impl OpArgType for u32 { - #[inline(always)] - fn from_op_arg(x: u32) -> Result { - Ok(x) - } +pub type NameIdx = u32; - #[inline(always)] - fn to_op_arg(self) -> u32 { - self +impl OpArgType for u32 {} +//impl OpArgType for bool {} + +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Ord, PartialOrd)] +#[repr(transparent)] +pub struct Label(pub u32); + +impl Label { + pub const fn new(value: u32) -> Self { + Self(value) } } -impl OpArgType for bool { - #[inline(always)] - fn from_op_arg(x: u32) -> Result { - Ok(x != 0) +impl From for Label { + fn from(value: u32) -> Self { + Self::new(value) } +} - #[inline(always)] - fn to_op_arg(self) -> u32 { - self as u32 +impl From