.. _id_generators:

Id Generators
=============

Id generators provide unique identifiers related to the current thread, which can be passed to a function. Currently available generators are ``call_id`` and ``thread_id``.

.. _generators_callid:

Call Id
-------

Similar to traditional compute kernels, SlangPy assigns a unique grid coordinate to each thread. However, while classic compute kernels operate within a fixed 3D grid, SlangPy supports arbitrary dimensionality. The ``call_id`` generator returns the grid coordinate of the current thread within SlangPy's execution model.

Consider the following simple Slang function, which takes and returns an ``int2``:

.. code-block::

    int2 myfunc(int2 value) {
        return value;
    }

We can invoke this function and pass it the ``call_id`` generator as follows:

.. code-block:: python

    # Populate a 4x4 numpy array of int2s with call IDs
    res = np.zeros((4,4,2), dtype=np.int32)
    module.myfunc(spy.call_id(), _result=res)

    #[ [ [0,0], [0,1], [0,2], [0,3] ], [ [1,0], [1,1], [1,2], [1,3] ], ... ]
    print(res)

The ``call_id`` generator provides the grid coordinate of the current thread. As a result, each entry in the numpy array is populated with its corresponding grid coordinate.

When using ``call_id``, ensure that the parameter type matches the dimensionality of the dispatch. In this example, since the dispatch was a 2D kernel, the parameter was an ``int2``.

Note that we explicitly created the numpy array ``res``. This is necessary because the ``call_id`` generator does not define any inherent shape. Without a predefined 4x4 container, SlangPy would have no way to infer the intended dispatch size.

.. _generators_threadid:

Thread Id
---------

In some cases, it is useful to access the actual dispatch thread ID being executed. This can be achieved by using the ``thread_id`` generator:

.. code-block::

    int3 myfunc3d(int3 value) {
        return value;
    }

Passing ``thread_id`` returns the 3D dispatch thread ID for each call:

.. code-block:: python

    # Populate a 4x4 numpy array of int3s with hardware thread IDs
    res = np.zeros((4,4,3), dtype=np.int32)
    module.myfunc3d(spy.thread_id(), _result=res)

    #[ [ [0,0,0], [1,0,0], [2,0,0], [3,0,0] ], [ [4,0,0], [5,0,0], ...
    print(res)

The ``thread_id`` generator can be used with 1D, 2D, or 3D vectors.

Currently, SlangPy maps kernels to a 1D grid on the hardware, meaning that thread IDs will always have the form ``[X,0,0]``. This behavior may be subject to future modifications and user control.

