//! Get information about all the things using `core` function calls. //! //! Set `INFO_FORMAT_MULTILINE` to `false` for compact printing. extern crate fil_ocl as ocl; use ocl::core::{self, PlatformInfo, DeviceInfo, ContextInfo, CommandQueueInfo, MemInfo, ImageInfo, SamplerInfo, ProgramInfo, ProgramBuildInfo, KernelInfo, KernelArgInfo, KernelWorkGroupInfo, EventInfo, ProfilingInfo, Status}; use ocl::{Platform, Device, Context, Queue, Buffer, Image, Sampler, Program, Kernel, Event, EventList, SpatialDims}; const WORK_SIZE: [usize; 3] = [1024, 64, 16]; const INFO_FORMAT_MULTILINE: bool = true; static SRC: &'static str = r#" __kernel void multiply(float coeff, __global float* buffer) { buffer[get_global_id(0)] *= coeff; } "#; /// Convert the info or error to a string for printing: macro_rules! to_string { ( $ expr : expr ) => { match $expr { Ok(info) => info.to_string(), Err(err) => { match err.api_status() { Some(Status::CL_KERNEL_ARG_INFO_NOT_AVAILABLE) => "Not available".into(), _ => err.to_string(), } }, } }; } fn print_platform_device(plat_idx: usize, platform: Platform, device_idx: usize, device: Device) -> ocl::Result<()> { let work_dims = SpatialDims::from(WORK_SIZE); let context = Context::builder().platform(platform).devices(device).build()?; let program = Program::builder() .devices(device) .src(SRC) .build(&context)?; let queue = Queue::new(&context, device, Some(core::QUEUE_PROFILING_ENABLE))?; let buffer = Buffer::::builder() .queue(queue.clone()) .len(work_dims) .build()?; let image = Image::::builder() .dims(work_dims) .queue(queue.clone()) .build()?; let sampler = Sampler::with_defaults(&context)?; let kernel = Kernel::builder() .name("multiply") .program(&program) .queue(queue.clone()) .global_work_size(work_dims) .arg(10.0f32) .arg(&buffer) .build()?; let mut event_list = EventList::new(); unsafe { kernel.cmd().enew(&mut event_list).enq()?; } event_list.wait_for()?; let mut event = Event::empty(); buffer.cmd().write(&vec![0.0; work_dims.to_len()]).enew(&mut event).enq()?; event.wait_for()?; let device_version = device.version()?; println!("############### OpenCL Platform-Device Full Info ################"); print!("\n"); let (begin, delim, end) = if INFO_FORMAT_MULTILINE { ("\n", "\n", "\n") } else { ("{ ", ", ", " }") }; // ################################################## // #################### PLATFORM #################### // ################################################## println!("Platform [{}]:{b}\ Profile: {}{d}\ Version: {}{d}\ Name: {}{d}\ Vendor: {}{d}\ Extensions: {}{e}\ ", plat_idx, to_string!(core::get_platform_info(platform, PlatformInfo::Profile)), to_string!(core::get_platform_info(platform, PlatformInfo::Version)), to_string!(core::get_platform_info(platform, PlatformInfo::Name)), to_string!(core::get_platform_info(platform, PlatformInfo::Vendor)), to_string!(core::get_platform_info(platform, PlatformInfo::Extensions)), b = begin, d = delim, e = end, ); // ################################################## // #################### DEVICES ##################### // ################################################## debug_assert!(context.devices().len() == 1); println!("Device [{}]: {b}\ Type: {}{d}\ VendorId: {}{d}\ MaxComputeUnits: {}{d}\ MaxWorkItemDimensions: {}{d}\ MaxWorkGroupSize: {}{d}\ MaxWorkItemSizes: {}{d}\ PreferredVectorWidthChar: {}{d}\ PreferredVectorWidthShort: {}{d}\ PreferredVectorWidthInt: {}{d}\ PreferredVectorWidthLong: {}{d}\ PreferredVectorWidthFloat: {}{d}\ PreferredVectorWidthDouble: {}{d}\ MaxClockFrequency: {}{d}\ AddressBits: {}{d}\ MaxReadImageArgs: {}{d}\ MaxWriteImageArgs: {}{d}\ MaxMemAllocSize: {}{d}\ Image2dMaxWidth: {}{d}\ Image2dMaxHeight: {}{d}\ Image3dMaxWidth: {}{d}\ Image3dMaxHeight: {}{d}\ Image3dMaxDepth: {}{d}\ ImageSupport: {}{d}\ MaxParameterSize: {}{d}\ MaxSamplers: {}{d}\ MemBaseAddrAlign: {}{d}\ MinDataTypeAlignSize: {}{d}\ SingleFpConfig: {}{d}\ GlobalMemCacheType: {}{d}\ GlobalMemCachelineSize: {}{d}\ GlobalMemCacheSize: {}{d}\ GlobalMemSize: {}{d}\ MaxConstantBufferSize: {}{d}\ MaxConstantArgs: {}{d}\ LocalMemType: {}{d}\ LocalMemSize: {}{d}\ ErrorCorrectionSupport: {}{d}\ ProfilingTimerResolution: {}{d}\ EndianLittle: {}{d}\ Available: {}{d}\ CompilerAvailable: {}{d}\ ExecutionCapabilities: {}{d}\ QueueProperties: {}{d}\ Name: {}{d}\ Vendor: {}{d}\ DriverVersion: {}{d}\ Profile: {}{d}\ Version: {}{d}\ Extensions: {}{d}\ Platform: {}{d}\ DoubleFpConfig: {}{d}\ HalfFpConfig: {}{d}\ PreferredVectorWidthHalf: {}{d}\ HostUnifiedMemory: {}{d}\ NativeVectorWidthChar: {}{d}\ NativeVectorWidthShort: {}{d}\ NativeVectorWidthInt: {}{d}\ NativeVectorWidthLong: {}{d}\ NativeVectorWidthFloat: {}{d}\ NativeVectorWidthDouble: {}{d}\ NativeVectorWidthHalf: {}{d}\ OpenclCVersion: {}{d}\ LinkerAvailable: {}{d}\ BuiltInKernels: {}{d}\ ImageMaxBufferSize: {}{d}\ ImageMaxArraySize: {}{d}\ ParentDevice: {}{d}\ PartitionMaxSubDevices: {}{d}\ PartitionProperties: {}{d}\ PartitionAffinityDomain: {}{d}\ PartitionType: {}{d}\ ReferenceCount: {}{d}\ PreferredInteropUserSync: {}{d}\ PrintfBufferSize: {}{d}\ ImagePitchAlignment: {}{d}\ ImageBaseAddressAlignment: {}{e}\ ", device_idx, to_string!(core::get_device_info(&device, DeviceInfo::Type)), to_string!(core::get_device_info(&device, DeviceInfo::VendorId)), to_string!(core::get_device_info(&device, DeviceInfo::MaxComputeUnits)), to_string!(core::get_device_info(&device, DeviceInfo::MaxWorkItemDimensions)), to_string!(core::get_device_info(&device, DeviceInfo::MaxWorkGroupSize)), to_string!(core::get_device_info(&device, DeviceInfo::MaxWorkItemSizes)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthChar)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthShort)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthInt)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthLong)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthFloat)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthDouble)), to_string!(core::get_device_info(&device, DeviceInfo::MaxClockFrequency)), to_string!(core::get_device_info(&device, DeviceInfo::AddressBits)), to_string!(core::get_device_info(&device, DeviceInfo::MaxReadImageArgs)), to_string!(core::get_device_info(&device, DeviceInfo::MaxWriteImageArgs)), to_string!(core::get_device_info(&device, DeviceInfo::MaxMemAllocSize)), to_string!(core::get_device_info(&device, DeviceInfo::Image2dMaxWidth)), to_string!(core::get_device_info(&device, DeviceInfo::Image2dMaxHeight)), to_string!(core::get_device_info(&device, DeviceInfo::Image3dMaxWidth)), to_string!(core::get_device_info(&device, DeviceInfo::Image3dMaxHeight)), to_string!(core::get_device_info(&device, DeviceInfo::Image3dMaxDepth)), to_string!(core::get_device_info(&device, DeviceInfo::ImageSupport)), to_string!(core::get_device_info(&device, DeviceInfo::MaxParameterSize)), to_string!(core::get_device_info(&device, DeviceInfo::MaxSamplers)), to_string!(core::get_device_info(&device, DeviceInfo::MemBaseAddrAlign)), to_string!(core::get_device_info(&device, DeviceInfo::MinDataTypeAlignSize)), to_string!(core::get_device_info(&device, DeviceInfo::SingleFpConfig)), to_string!(core::get_device_info(&device, DeviceInfo::GlobalMemCacheType)), to_string!(core::get_device_info(&device, DeviceInfo::GlobalMemCachelineSize)), to_string!(core::get_device_info(&device, DeviceInfo::GlobalMemCacheSize)), to_string!(core::get_device_info(&device, DeviceInfo::GlobalMemSize)), to_string!(core::get_device_info(&device, DeviceInfo::MaxConstantBufferSize)), to_string!(core::get_device_info(&device, DeviceInfo::MaxConstantArgs)), to_string!(core::get_device_info(&device, DeviceInfo::LocalMemType)), to_string!(core::get_device_info(&device, DeviceInfo::LocalMemSize)), to_string!(core::get_device_info(&device, DeviceInfo::ErrorCorrectionSupport)), to_string!(core::get_device_info(&device, DeviceInfo::ProfilingTimerResolution)), to_string!(core::get_device_info(&device, DeviceInfo::EndianLittle)), to_string!(core::get_device_info(&device, DeviceInfo::Available)), to_string!(core::get_device_info(&device, DeviceInfo::CompilerAvailable)), to_string!(core::get_device_info(&device, DeviceInfo::ExecutionCapabilities)), to_string!(core::get_device_info(&device, DeviceInfo::QueueProperties)), to_string!(core::get_device_info(&device, DeviceInfo::Name)), to_string!(core::get_device_info(&device, DeviceInfo::Vendor)), to_string!(core::get_device_info(&device, DeviceInfo::DriverVersion)), to_string!(core::get_device_info(&device, DeviceInfo::Profile)), to_string!(core::get_device_info(&device, DeviceInfo::Version)), to_string!(core::get_device_info(&device, DeviceInfo::Extensions)), to_string!(core::get_device_info(&device, DeviceInfo::Platform)), to_string!(core::get_device_info(&device, DeviceInfo::DoubleFpConfig)), to_string!(core::get_device_info(&device, DeviceInfo::HalfFpConfig)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredVectorWidthHalf)), to_string!(core::get_device_info(&device, DeviceInfo::HostUnifiedMemory)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthChar)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthShort)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthInt)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthLong)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthFloat)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthDouble)), to_string!(core::get_device_info(&device, DeviceInfo::NativeVectorWidthHalf)), to_string!(core::get_device_info(&device, DeviceInfo::OpenclCVersion)), to_string!(core::get_device_info(&device, DeviceInfo::LinkerAvailable)), to_string!(core::get_device_info(&device, DeviceInfo::BuiltInKernels)), to_string!(core::get_device_info(&device, DeviceInfo::ImageMaxBufferSize)), to_string!(core::get_device_info(&device, DeviceInfo::ImageMaxArraySize)), to_string!(core::get_device_info(&device, DeviceInfo::ParentDevice)), to_string!(core::get_device_info(&device, DeviceInfo::PartitionMaxSubDevices)), to_string!(core::get_device_info(&device, DeviceInfo::PartitionProperties)), to_string!(core::get_device_info(&device, DeviceInfo::PartitionAffinityDomain)), to_string!(core::get_device_info(&device, DeviceInfo::PartitionType)), to_string!(core::get_device_info(&device, DeviceInfo::ReferenceCount)), to_string!(core::get_device_info(&device, DeviceInfo::PreferredInteropUserSync)), to_string!(core::get_device_info(&device, DeviceInfo::PrintfBufferSize)), to_string!(core::get_device_info(&device, DeviceInfo::ImagePitchAlignment)), to_string!(core::get_device_info(&device, DeviceInfo::ImageBaseAddressAlignment)), b = begin, d = delim, e = end, ); // ################################################## // #################### CONTEXT ##################### // ################################################## println!("Context:{b}\ Reference Count: {}{d}\ Devices: {}{d}\ Properties: {}{d}\ Device Count: {}{e}\ ", to_string!(core::get_context_info(&context, ContextInfo::ReferenceCount)), to_string!(core::get_context_info(&context, ContextInfo::Devices)), to_string!(core::get_context_info(&context, ContextInfo::Properties)), to_string!(core::get_context_info(&context, ContextInfo::NumDevices)), b = begin, d = delim, e = end, ); // ################################################## // ##################### QUEUE ###################### // ################################################## println!("Command Queue:{b}\ Context: {}{d}\ Device: {}{d}\ ReferenceCount: {}{d}\ Properties: {}{e}\ ", to_string!(core::get_command_queue_info(&queue, CommandQueueInfo::Context)), to_string!(core::get_command_queue_info(&queue, CommandQueueInfo::Device)), to_string!(core::get_command_queue_info(&queue, CommandQueueInfo::ReferenceCount)), to_string!(core::get_command_queue_info(&queue, CommandQueueInfo::Properties)), b = begin, d = delim, e = end, ); // ################################################## // ################### MEM OBJECT ################### // ################################################## println!("Buffer Memory:{b}\ Type: {}{d}\ Flags: {}{d}\ Size: {}{d}\ HostPtr: {}{d}\ MapCount: {}{d}\ ReferenceCount: {}{d}\ Context: {}{d}\ AssociatedMemobject: {}{d}\ Offset: {}{e}\ ", to_string!(core::get_mem_object_info(&buffer, MemInfo::Type)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Flags)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Size)), to_string!(core::get_mem_object_info(&buffer, MemInfo::HostPtr)), to_string!(core::get_mem_object_info(&buffer, MemInfo::MapCount)), to_string!(core::get_mem_object_info(&buffer, MemInfo::ReferenceCount)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Context)), to_string!(core::get_mem_object_info(&buffer, MemInfo::AssociatedMemobject)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Offset)), b = begin, d = delim, e = end, ); // ################################################## // ##################### IMAGE ###################### // ################################################## println!("Image: {b}\ ElementSize: {}{d}\ RowPitch: {}{d}\ SlicePitch: {}{d}\ Width: {}{d}\ Height: {}{d}\ Depth: {}{d}\ ArraySize: {}{d}\ Buffer: {}{d}\ NumMipLevels: {}{d}\ NumSamples: {}{e}\ ", to_string!(core::get_image_info(&image, ImageInfo::ElementSize)), to_string!(core::get_image_info(&image, ImageInfo::RowPitch)), to_string!(core::get_image_info(&image, ImageInfo::SlicePitch)), to_string!(core::get_image_info(&image, ImageInfo::Width)), to_string!(core::get_image_info(&image, ImageInfo::Height)), to_string!(core::get_image_info(&image, ImageInfo::Depth)), to_string!(core::get_image_info(&image, ImageInfo::ArraySize)), to_string!(core::get_image_info(&image, ImageInfo::Buffer)), to_string!(core::get_image_info(&image, ImageInfo::NumMipLevels)), to_string!(core::get_image_info(&image, ImageInfo::NumSamples)), b = begin, d = delim, e = end, ); println!("Image Memory:{b}\ Type: {}{d}\ Flags: {}{d}\ Size: {}{d}\ HostPtr: {}{d}\ MapCount: {}{d}\ ReferenceCount: {}{d}\ Context: {}{d}\ AssociatedMemobject: {}{d}\ Offset: {}{e}\ ", to_string!(core::get_mem_object_info(&buffer, MemInfo::Type)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Flags)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Size)), to_string!(core::get_mem_object_info(&buffer, MemInfo::HostPtr)), to_string!(core::get_mem_object_info(&buffer, MemInfo::MapCount)), to_string!(core::get_mem_object_info(&buffer, MemInfo::ReferenceCount)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Context)), to_string!(core::get_mem_object_info(&buffer, MemInfo::AssociatedMemobject)), to_string!(core::get_mem_object_info(&buffer, MemInfo::Offset)), b = begin, d = delim, e = end, ); // ################################################## // #################### SAMPLER ##################### // ################################################## println!("Sampler:{b}\ ReferenceCount: {}{d}\ Context: {}{d}\ NormalizedCoords: {}{d}\ AddressingMode: {}{d}\ FilterMode: {}{e}\ ", to_string!(core::get_sampler_info(&sampler, SamplerInfo::ReferenceCount)), to_string!(core::get_sampler_info(&sampler, SamplerInfo::Context)), to_string!(core::get_sampler_info(&sampler, SamplerInfo::NormalizedCoords)), to_string!(core::get_sampler_info(&sampler, SamplerInfo::AddressingMode)), to_string!(core::get_sampler_info(&sampler, SamplerInfo::FilterMode)), b = begin, d = delim, e = end, ); // ################################################## // #################### PROGRAM ##################### // ################################################## println!("Program:{b}\ ReferenceCount: {}{d}\ Context: {}{d}\ NumDevices: {}{d}\ Devices: {}{d}\ Source: {}{d}\ BinarySizes: {}{d}\ Binaries: {}{d}\ NumKernels: {}{d}\ KernelNames: {}{e}\ ", to_string!(core::get_program_info(&program, ProgramInfo::ReferenceCount)), to_string!(core::get_program_info(&program, ProgramInfo::Context)), to_string!(core::get_program_info(&program, ProgramInfo::NumDevices)), to_string!(core::get_program_info(&program, ProgramInfo::Devices)), to_string!(core::get_program_info(&program, ProgramInfo::Source)), to_string!(core::get_program_info(&program, ProgramInfo::BinarySizes) .map(|_| "{Omitted}")), to_string!(core::get_program_info(&program, ProgramInfo::NumKernels)), to_string!(core::get_program_info(&program, ProgramInfo::KernelNames)), b = begin, d = delim, e = end, ); // ################################################## // ################# PROGRAM BUILD ################## // ################################################## println!("Program Build:{b}\ BuildStatus: {}{d}\ BuildOptions: {}{d}\ BuildLog: \n\n{}{d}\n\ BinaryType: {}{e}\ ", to_string!(core::get_program_build_info(&program, &device, ProgramBuildInfo::BuildStatus)), to_string!(core::get_program_build_info(&program, &device, ProgramBuildInfo::BuildOptions)), to_string!(core::get_program_build_info(&program, &device, ProgramBuildInfo::BuildLog)), to_string!(core::get_program_build_info(&program, &device, ProgramBuildInfo::BinaryType)), b = begin, d = delim, e = end, ); // ################################################## // ##################### KERNEL ##################### // ################################################## println!("Kernel Info:{b}\ FunctionName: {}{d}\ NumArgs: {}{d}\ ReferenceCount: {}{d}\ Context: {}{d}\ Program: {}{d}\ Attributes: {}{e}\ ", to_string!(core::get_kernel_info(&kernel, KernelInfo::FunctionName)), to_string!(core::get_kernel_info(&kernel, KernelInfo::NumArgs)), to_string!(core::get_kernel_info(&kernel, KernelInfo::ReferenceCount)), to_string!(core::get_kernel_info(&kernel, KernelInfo::Context)), to_string!(core::get_kernel_info(&kernel, KernelInfo::Program)), to_string!(core::get_kernel_info(&kernel, KernelInfo::Attributes)), b = begin, d = delim, e = end, ); // ################################################## // ################# KERNEL ARGUMENT ################ // ################################################## println!("Kernel Argument [0]:{b}\ AddressQualifier: {}{d}\ AccessQualifier: {}{d}\ TypeName: {}{d}\ TypeQualifier: {}{d}\ Name: {}{e}\ ", to_string!(core::get_kernel_arg_info(&kernel, 0, KernelArgInfo::AddressQualifier, Some(&[device_version]))), to_string!(core::get_kernel_arg_info(&kernel, 0, KernelArgInfo::AccessQualifier, Some(&[device_version]))), to_string!(core::get_kernel_arg_info(&kernel, 0, KernelArgInfo::TypeName, Some(&[device_version]))), to_string!(core::get_kernel_arg_info(&kernel, 0, KernelArgInfo::TypeQualifier, Some(&[device_version]))), to_string!(core::get_kernel_arg_info(&kernel, 0, KernelArgInfo::Name, Some(&[device_version]))), b = begin, d = delim, e = end, ); // ################################################## // ################ KERNEL WORK GROUP ############### // ################################################## println!("Kernel Work Group:{b}\ WorkGroupSize: {}{d}\ CompileWorkGroupSize: {}{d}\ LocalMemSize: {}{d}\ PreferredWorkGroupSizeMultiple: {}{d}\ PrivateMemSize: {}{d}\ GlobalWorkSize: {}{e}\ ", to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::WorkGroupSize)), to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::CompileWorkGroupSize)), to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::LocalMemSize)), to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::PreferredWorkGroupSizeMultiple)), to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::PrivateMemSize)), to_string!(core::get_kernel_work_group_info(&kernel, &device, KernelWorkGroupInfo::GlobalWorkSize)), b = begin, d = delim, e = end, ); // ################################################## // ##################### EVENT ###################### // ################################################## println!("Event:{b}\ CommandQueue: {}{d}\ CommandType: {}{d}\ ReferenceCount: {}{d}\ CommandExecutionStatus: {}{d}\ Context: {}{e}\ ", to_string!(core::get_event_info(&event, EventInfo::CommandQueue)), to_string!(core::get_event_info(&event, EventInfo::CommandType)), to_string!(core::get_event_info(&event, EventInfo::ReferenceCount)), to_string!(core::get_event_info(&event, EventInfo::CommandExecutionStatus)), to_string!(core::get_event_info(&event, EventInfo::Context)), b = begin, d = delim, e = end, ); // ################################################## // ################ EVENT PROFILING ################# // ################################################## println!("Event Profiling:{b}\ Queued: {}{d}\ Submit: {}{d}\ Start: {}{d}\ End: {}{e}\ ", to_string!(core::get_event_profiling_info(&event, ProfilingInfo::Queued)), to_string!(core::get_event_profiling_info(&event, ProfilingInfo::Submit)), to_string!(core::get_event_profiling_info(&event, ProfilingInfo::Start)), to_string!(core::get_event_profiling_info(&event, ProfilingInfo::End)), b = begin, d = delim, e = end, ); // ################################################## // ###################### END ####################### // ################################################## print!("\n"); Ok(()) } fn print_platform(plat_idx: usize, platform: Platform) -> ocl::Result<()> { for (device_idx, &device) in Device::list_all(&platform)?.iter().enumerate() { print_platform_device(plat_idx, platform, device_idx, device)?; } Ok(()) } fn info_core() -> ocl::Result<()> { let platforms = Platform::list(); for (plat_idx, &platform) in platforms.iter().enumerate() { print_platform(plat_idx, platform)?; } Ok(()) } pub fn main() { match info_core() { Ok(_) => (), Err(err) => println!("{}", err), } }