Skip to content

Enable path tracer GPU support via SYCL-OpenCL backend #71

@juanchuletas

Description

@juanchuletas

Summary

The path tracer (pathTracer_CookTorrance) has no texture sampling path for OpenCL devices. sampled_image_handle requires ext_oneapi_bindless_images support, which OpenCL does not implement (no priority per the SYCL bindless images spec). This issue introduces fungt::GPUTexture as the fallback texture type for OpenCL backends, and adds NVIDIA support via the SYCL backend compiled with the CUDA target. NVIDIA supports SYCL bindless images fully via its CUDA implementation and takes the existing bindless path with no fallback needed.

Description

The path tracer is currently broken on Intel UHD 630 because OpenCL has no support for ext_oneapi_bindless_images. The fix introduces fungt::GPUTexture, a POD struct holding a USM device pointer and dimensions, as the fallback texture type for devices where device.has(sycl::aspect::ext_oneapi_bindless_images) returns false at runtime.

NVIDIA GPUs running the SYCL-CUDA target support bindless images natively and take the existing sampled_image_handle path. No buffer fallback is needed for NVIDIA. The only change required for NVIDIA support is compiling the SYCL backend with -fsycl-targets=nvptx64-nvidia-cuda,spir64.

SYCLTexture now queries bindless support in its constructor and dispatches to either loadBindlessTexture or loadBufferTexture accordingly. Space::sendTexturesToRender routes to either setSyclTextureHandles or setGPUBufferTextures on the renderer based on hasBindlessSupport(). pathTracer_CookTorrance is untouched, the sampleTexture2D overload on GPUTexture handles the buffer path transparently.

Requirements

Core Functionality

  • fungt::GPUTexture struct: float* data, int width, int height, USM device pointer, POD
  • sampleTexture2D(const GPUTexture&, float u, float v): manual bilinear filter, clamp-to-edge, returns Vec3
  • SYCLTexture: query device.has(aspect::ext_oneapi_bindless_images) in constructor, set m_useBindlessImages
  • SYCLTexture::loadBufferTexture: stbi pixel data converted to float, uploaded via malloc_device + memcpy
  • SYCLTexture::getBufferTextures: returns std::vector<GPUTexture> with device pointers
  • SYCL_Renderer::setGPUBufferTextures: allocates GPUTexture* on device, uploads struct array
  • SYCL_Renderer::RenderScene: branches on m_useBindlessImage, passes correct pointer to kernel

NVIDIA Support

  • SYCL backend compiled with -fsycl-targets=nvptx64-nvidia-cuda,spir64
  • NVIDIA takes the existing bindless path at runtime via ext_oneapi_bindless_images on CUDA
  • Single binary selects Intel or NVIDIA device at runtime via flib::sycl_handler::select_device

Technical Considerations

SYCL bindless images are supported on NVIDIA (CUDA backend) and Intel Arc (Level Zero). OpenCL has no implementation and no planned support. The runtime query device.has(sycl::aspect::ext_oneapi_bindless_images) is the only correct way to distinguish capable from non-capable devices, this cannot be determined at compile time.

GPUTexture is POD with a USM device pointer, valid under both OpenCL and SYCL-CUDA. pathTracer_CookTorrance is untouched. The sampleTexture2D overload on GPUTexture implements bilinear filtering in pure pointer arithmetic with no API calls, compiling correctly under any target.

Acceptance Criteria

  • Path tracer runs on Intel UHD 630 via OpenCL using GPUTexture buffer path
  • Path tracer runs on NVIDIA GPU via SYCL-CUDA using sampled_image_handle bindless path
  • Path tracer runs on Intel Arc via Level Zero using sampled_image_handle bindless path
  • Single binary selects device at runtime, no recompilation needed to switch between Intel and NVIDIA
  • pathTracer_CookTorrance compiles unchanged
  • sampleTexture2D<GPUTexture> produces correct bilinear output

Metadata

Metadata

Assignees

Labels

enhancementNew feature or request

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions