[libclc] [libclc] Move sign to the CLC builtins library (PR #115699)

Fraser Cormack via cfe-commits cfe-commits at lists.llvm.org
Mon Nov 11 08:07:07 PST 2024


frasercrmck wrote:

> > So is the sign function currently implemented in the OpenCL headers?
> 
> The sign function for SPIR-V/Mesa is currently implemented by libclc [here](https://github.com/llvm/llvm-project/blob/main/libclc/generic/lib/common/sign.cl). With this change, `sign` now calls `__clc_sign` which has the same implementation. We just need to do a bit of extra inlining of CLC functions into OpenCL functions to maintain more or less the same SPIR-V.

There are differences in the SPIR-V and I was wondering if you could tell me whether or not it's okay.

Before:

```
   %_Z4signf = OpFunction %float DontInline %13378
       %x_52 = OpFunctionParameter %float
  %entry_170 = OpLabel
     %retval = OpVariable %_ptr_Function_float Function
  %x_addr_52 = OpVariable %_ptr_Function_float Function
               OpStore %x_addr_52 %x_52 Aligned 4
      %14371 = OpLoad %float %x_addr_52 Aligned 4
      %14372 = OpIsNan %bool %14371
   %call_162 = OpSelect %uint %14372 %uint_1 %uint_0
     %tobool = OpINotEqual %bool %call_162 %uint_0
               OpBranchConditional %tobool %if_then %if_end
    %if_then = OpLabel
               OpStore %retval %float_0 Aligned 4
               OpBranch %return
     %if_end = OpLabel
      %14376 = OpLoad %float %x_addr_52 Aligned 4
    %cmp_109 = OpFOrdGreaterThan %bool %14376 %float_0
               OpBranchConditional %cmp_109 %if_then1 %if_end2
   %if_then1 = OpLabel
               OpStore %retval %float_1 Aligned 4
               OpBranch %return
    %if_end2 = OpLabel
      %14378 = OpLoad %float %x_addr_52 Aligned 4
       %cmp3 = OpFOrdLessThan %bool %14378 %float_0
               OpBranchConditional %cmp3 %if_then4 %if_end5
   %if_then4 = OpLabel
               OpStore %retval %float_n1 Aligned 4
               OpBranch %return
    %if_end5 = OpLabel
      %14381 = OpLoad %float %x_addr_52 Aligned 4
               OpStore %retval %14381 Aligned 4
               OpBranch %return
     %return = OpLabel
      %14382 = OpLoad %float %retval Aligned 4
               OpReturnValue %14382
               OpFunctionEnd
```

```
   %_Z4signf = OpFunction %float DontInline %13378
       %a_32 = OpFunctionParameter %float
  %entry_170 = OpLabel
   %retval_i = OpVariable %_ptr_Function_float Function
   %x_addr_i = OpVariable %_ptr_Function_float Function
  %a_addr_32 = OpVariable %_ptr_Function_float Function
               OpStore %a_addr_32 %a_32 Aligned 4
      %14372 = OpLoad %float %a_addr_32 Aligned 4
      %14373 = OpBitcast %_ptr_Function_uchar %retval_i
               OpLifetimeStart %14373 4
      %14374 = OpBitcast %_ptr_Function_uchar %x_addr_i
               OpLifetimeStart %14374 4
               OpStore %x_addr_i %14372 Aligned 4
      %14375 = OpLoad %float %x_addr_i Aligned 4
      %14376 = OpIsNan %bool %14375
     %call_i = OpSelect %uint %14376 %uint_1 %uint_0
   %tobool_i = OpINotEqual %bool %call_i %uint_0
               OpBranchConditional %tobool_i %if_then_i %if_end_i
  %if_then_i = OpLabel
               OpStore %retval_i %float_0 Aligned 4
               OpBranch %_Z10__clc_signf_exit
   %if_end_i = OpLabel
      %14380 = OpLoad %float %x_addr_i Aligned 4
      %cmp_i = OpFOrdGreaterThan %bool %14380 %float_0
               OpBranchConditional %cmp_i %if_then1_i %if_end2_i
 %if_then1_i = OpLabel
               OpStore %retval_i %float_1 Aligned 4
               OpBranch %_Z10__clc_signf_exit
  %if_end2_i = OpLabel
      %14382 = OpLoad %float %x_addr_i Aligned 4
     %cmp3_i = OpFOrdLessThan %bool %14382 %float_0
               OpBranchConditional %cmp3_i %if_then4_i %if_end5_i
 %if_then4_i = OpLabel
               OpStore %retval_i %float_n1 Aligned 4
               OpBranch %_Z10__clc_signf_exit
  %if_end5_i = OpLabel
      %14385 = OpLoad %float %x_addr_i Aligned 4
               OpStore %retval_i %14385 Aligned 4
               OpBranch %_Z10__clc_signf_exit
%_Z10__clc_signf_exit = OpLabel
      %14386 = OpLoad %float %retval_i Aligned 4
      %14387 = OpBitcast %_ptr_Function_uchar %retval_i
               OpLifetimeStop %14387 4
      %14388 = OpBitcast %_ptr_Function_uchar %x_addr_i
               OpLifetimeStop %14388 4
               OpReturnValue %14386
               OpFunctionEnd
```

So it's an extra `alloca` and some lifetime instructions - a result of inlining unoptimized code. Do you think these will be sufficiently eliminated by the SPIR-V producer, or should libclc be eliminating these before they reach SPIR-V?

https://github.com/llvm/llvm-project/pull/115699


More information about the cfe-commits mailing list