diff --git a/.github/workflows/bleeding-edge.yaml b/.github/workflows/bleeding-edge.yaml
index 3567465440c..dca8c5387f1 100644
--- a/.github/workflows/bleeding-edge.yaml
+++ b/.github/workflows/bleeding-edge.yaml
@@ -50,9 +50,9 @@ jobs:
       run: |
         python -m pip install --upgrade pip
         python -m pip install --upgrade setuptools wheel
-        python -m pip install --pre --only-binary ":all:" numpy matplotlib \
+        python -m pip install --pre --only-binary ":all:" numpy matplotlib Cython \
          --extra-index https://pypi.anaconda.org/scientific-python-nightly-wheels/simple
-        python -m pip install --pre ewah-bool-utils Cython
+        python -m pip install --pre ewah-bool-utils
         python -m pip install git+https://github.com/yt-project/unyt.git
         python -m pip install --pre pytest PyYAML
 
diff --git a/.github/workflows/wheels.yaml b/.github/workflows/wheels.yaml
index cd63fbc1610..d3be9dfd59e 100644
--- a/.github/workflows/wheels.yaml
+++ b/.github/workflows/wheels.yaml
@@ -92,10 +92,9 @@ jobs:
 
       # keep in sync with pyproject.toml
       run: |
-        python -m pip install "Cython>=3.0.3, <3.1"
-        python -m pip install numpy>=1.25
-        python -m pip install ewah-bool-utils>=1.0.2
-        python -m pip install --upgrade wheel
+        python -m pip install Cython>=3.0.3
+        python -m pip install numpy>=2.0.0
+        python -m pip install ewah-bool-utils>=1.2.0
         python -m pip install --upgrade setuptools
     - name: build yt
       shell: bash
diff --git a/pyproject.toml b/pyproject.toml
index ecd0649e755..6dbc76be381 100644
--- a/pyproject.toml
+++ b/pyproject.toml
@@ -2,10 +2,7 @@
 # keep in sync with .github/workflows/wheels.yaml
 requires = [
   "setuptools>=61.2",
-
-  # for the upper pin in Cython
-  # see https://github.com/yt-project/yt/issues/4044
-  "Cython>=3.0.3, <3.1",
+  "Cython>=3.0.3",
   "numpy>=2.0.0",
   "ewah-bool-utils>=1.2.0",
 ]
diff --git a/yt/geometry/particle_deposit.pxd b/yt/geometry/particle_deposit.pxd
index e89fdd9260a..8f16f9af6ef 100644
--- a/yt/geometry/particle_deposit.pxd
+++ b/yt/geometry/particle_deposit.pxd
@@ -14,12 +14,13 @@ import numpy as np
 cimport cython
 from libc.math cimport sqrt
 from libc.stdlib cimport free, malloc
-from numpy.math cimport PI as NPY_PI
 
 from yt.utilities.lib.fp_utils cimport *
 
 from .oct_container cimport Oct, OctreeContainer
 
+cdef extern from "numpy/npy_math.h":
+    double NPY_PI
 
 cdef extern from "platform_dep.h":
     void *alloca(int)
diff --git a/yt/utilities/lib/geometry_utils.pxd b/yt/utilities/lib/geometry_utils.pxd
index 3165bb43149..0b8145a3ba0 100644
--- a/yt/utilities/lib/geometry_utils.pxd
+++ b/yt/utilities/lib/geometry_utils.pxd
@@ -11,12 +11,17 @@ cimport numpy as np
 from libc.float cimport DBL_MANT_DIG
 from libc.math cimport frexp, ldexp, sqrt
 
-DEF ORDER_MAX=20
-DEF INDEX_MAX_64=2097151
-# TODO: Handle error for indices past max
-DEF XSHIFT=2
-DEF YSHIFT=1
-DEF ZSHIFT=0
+cdef enum:
+    ORDER_MAX=20
+
+cdef enum:
+    # TODO: Handle error for indices past max
+    INDEX_MAX_64=2097151
+
+cdef enum:
+    XSHIFT=2
+    YSHIFT=1
+    ZSHIFT=0
 
 @cython.cdivision(True)
 @cython.boundscheck(False)
diff --git a/yt/utilities/lib/geometry_utils.pyx b/yt/utilities/lib/geometry_utils.pyx
index e6eed9af3a2..ad63adf60e2 100644
--- a/yt/utilities/lib/geometry_utils.pyx
+++ b/yt/utilities/lib/geometry_utils.pyx
@@ -23,12 +23,6 @@ from yt.utilities.exceptions import YTDomainOverflow
 
 from yt.utilities.lib.vec3_ops cimport L2_norm, cross, dot, subtract
 
-DEF ORDER_MAX=20
-DEF INDEX_MAX_64=2097151
-DEF XSHIFT=2
-DEF YSHIFT=1
-DEF ZSHIFT=0
-
 cdef extern from "math.h":
     double exp(double x) noexcept nogil
     float expf(float x) noexcept nogil
diff --git a/yt/utilities/lib/image_samplers.pxd b/yt/utilities/lib/image_samplers.pxd
index 9027a902e4f..725ca8a01c6 100644
--- a/yt/utilities/lib/image_samplers.pxd
+++ b/yt/utilities/lib/image_samplers.pxd
@@ -15,7 +15,8 @@ cimport numpy as np
 from .partitioned_grid cimport PartitionedGrid
 from .volume_container cimport VolumeContainer
 
-DEF Nch = 4
+cdef enum:
+    Nch = 4
 
 # NOTE: We don't want to import the field_interpolator_tables here, as it
 # breaks a bunch of C++ interop.  Maybe some day it won't.  So, we just forward
diff --git a/yt/utilities/lib/image_samplers.pyx b/yt/utilities/lib/image_samplers.pyx
index 0ae116e3777..39a247ff63e 100644
--- a/yt/utilities/lib/image_samplers.pyx
+++ b/yt/utilities/lib/image_samplers.pyx
@@ -37,8 +37,6 @@ from ._octree_raytracing cimport RayInfo, _OctreeRayTracing
 cdef extern from "platform_dep.h":
     long int lrint(double x) noexcept nogil
 
-DEF Nch = 4
-
 from cython.parallel import parallel, prange
 
 from cpython.exc cimport PyErr_CheckSignals