Skip to content

CL: Printf

Jesse Natalie requested to merge jenatali/mesa:printf into msclc-d3d12

I said I wasn't going to do it, but it was actually really easy and kind of fun.

The OpenCL printf opcode maps to a NIR intrinsic with 2 sources: the first is the format string (a deref to a __constant char*) and the second is a deref of an ad-hoc struct containing the arguments. The struct allows us to preserve all the argument type information. If the driver claims it doesn't support printf, the opcode just returns -1 instead.

The CLOn12 backend lowers this intrinsic to a series of SSBO/UAV writes on a dedicated UAV, starting with an atomic addition to find a location in the buffer, then the format string, and then the args. If the atomic reveals not enough space, -1 is "returned", otherwise 0. The UAV ID for this buffer is reported to the runtime, allowing it to bind an appropriate buffer and read back the data.

On the runtime side, any string pointers are converted from DXIL "pointers" (buffer ID + offset) into actual const char* pointers by just looking up the data that was written into a UAV and bound at that location, since all strings must be inline __constant data. The format string is parsed to determine what data to read, and is converted into a series of CPU-side sprintf ops (emulating vector support mainly), and then finally sent to stdout.

This series is sufficient to pass the OpenCL printf CTS when combined with corresponding runtime changes: https://github.com/microsoft/OpenCLOn12/pull/3.

/cc @bbrezillon @daniels @jekstrand @karolherbst (upstream folks just for the first two commits).

Edited by Jesse Natalie

Merge request reports