llvm / llvm/llvm-project

[AVX-512] Look for vmovdqa64/vblendm elimination / merge-mask folds made possible by inverting a conditional

Open
#190,080 1 comment 0 reactions 0 assignees View on GitHub
backend:X86 missed-optimization
Dominant language
LLVM
Stars
40.5k
Forks
18.7k
PR merge metrics
PR metrics pending

Description

In Zig: ([Godbolt](https://zig.godbo.lt/#g:!((g:!((g:!((h:codeEditor,i:(filename:'1',fontScale:16,fontUsePx:'0',j:1,lang:zig,selection:(endColumn:1,endLineNumber:12,positionColumn:1,positionLineNumber:12,selectionStartColumn:1,selectionStartLineNumber:12,startColumn:1,startLineNumber:12),source:'const+V+%3D+@Vector(8,+u64)%3B%0A%0Aexport+fn+foo(y:+u64,+z:+V)+V+%7B%0A++++return+@select(%0A++++++++u64,%0A++++++++z+%3D%3D+@as(V,+@splat(0)),%0A++++++++~@as(V,+@splat(0)),%0A++++++++@as(V,+@splat(y)),%0A++++)%3B%0A%7D%0A%0A'),l:'5',n:'0',o:'Zig+source+%231',t:'0')),k:49.404817415928996,l:'4',m:100,n:'0',o:'',s:0,t:'0'),(g:!((h:compiler,i:(compiler:ztrunk,filters:(b:'0',binary:'1',binaryObject:'1',commentOnly:'0',debugCalls:'1',demangle:'0',directives:'0',execute:'1',intel:'0',libraryCode:'0',trim:'1',verboseDemangling:'0'),flagsViewOpen:'1',fontScale:20,fontUsePx:'0',j:2,lang:zig,libs:!(),options:'-O+ReleaseFast+-target+x86_64-linux+-mcpu%3Dznver5+-fomit-frame-pointer',overrides:!(),selection:(endColumn:1,endLineNumber:1,positionColumn:1,positionLineNumber:1,selectionStartColumn:1,selectionStartLineNumber:1,startColumn:1,startLineNumber:1),source:1),l:'5',n:'0',o:'+zig+trunk+(Editor+%231)',t:'0')),header:(),k:50.59518258407102,l:'4',m:100,n:'0',o:'',s:0,t:'0')),l:'2',m:100,n:'0',o:'',t:'0')),version:4))

```zig
const V = @Vector(8, u64);

export fn foo(y: u64, z: V) V {
return @select(
u64,
z == @as(V, @splat(0)),
~@as(V, @splat(0)),
@as(V, @splat(y)),
);
}
```

LLVM: ([Godbolt](https://llvm.godbo.lt/#g:!((g:!((g:!((h:codeEditor,i:(filename:'1',fontScale:14,fontUsePx:'0',j:1,lang:llvm,selection:(endColumn:1,endLineNumber:1,positionColumn:1,positionLineNumber:1,selectionStartColumn:1,selectionStartLineNumber:1,startColumn:1,startLineNumber:1),source:'define+internal+%3C8+x+i64%3E+@foo(i64+%250,+%3C8+x+i64%3E+%251)+unnamed_addr+align+1+%7B%0AEntry:%0A++%252+%3D+icmp+eq+%3C8+x+i64%3E+%251,+zeroinitializer%0A++%253+%3D+insertelement+%3C1+x+i64%3E+poison,+i64+%250,+i64+0%0A++%254+%3D+shufflevector+%3C1+x+i64%3E+%253,+%3C1+x+i64%3E+poison,+%3C8+x+i32%3E+zeroinitializer%0A++%255+%3D+select+%3C8+x+i1%3E+%252,+%3C8+x+i64%3E+splat+(i64+-1),+%3C8+x+i64%3E+%254%0A++ret+%3C8+x+i64%3E+%255%0A%7D%0A'),l:'5',n:'0',o:'LLVM+IR+source+%231',t:'0')),k:50.56669572798606,l:'4',n:'0',o:'',s:0,t:'0'),(g:!((h:compiler,i:(compiler:llctrunk,filters:(b:'0',binary:'1',binaryObject:'1',commentOnly:'0',debugCalls:'1',demangle:'0',directives:'0',execute:'1',intel:'0',libraryCode:'0',trim:'1',verboseDemangling:'0'),flagsViewOpen:'1',fontScale:14,fontUsePx:'0',j:1,lang:llvm,libs:!(),options:'-O3+-mcpu%3Dznver5',overrides:!(),selection:(endColumn:1,endLineNumber:1,positionColumn:1,positionLineNumber:1,selectionStartColumn:1,selectionStartLineNumber:1,startColumn:1,startLineNumber:1),source:1),l:'5',n:'0',o:'+llc+(trunk)+(Editor+%231)',t:'0')),k:49.43330427201394,l:'4',m:100,n:'0',o:'',s:0,t:'0')),l:'2',n:'0',o:'',t:'0')),version:4))

```llvm
define internal <8 x i64> @foo(i64 %0, <8 x i64> %1) unnamed_addr align 1 {
Entry:
%2 = icmp eq <8 x i64> %1, zeroinitializer
%3 = insertelement <1 x i64> poison, i64 %0, i64 0
%4 = shufflevector <1 x i64> %3, <1 x i64> poison, <8 x i32> zeroinitializer
%5 = select <8 x i1> %2, <8 x i64> splat (i64 -1), <8 x i64> %4
ret <8 x i64> %5
}
```

Compiles to:

```asm
foo:
vptestnmq k1, zmm0, zmm0
vpbroadcastq zmm0, rdi
vpternlogd zmm1, zmm1, zmm1, 255
vmovdqa64 zmm0 {k1}, zmm1
ret
```

Should be:

```asm
foo:
vptestmq k1, zmm0, zmm0
vpternlogd zmm0, zmm0, zmm0, 255
vpbroadcastq zmm0 {k1}, rdi
ret
```

Contributor guide

Open the contributing guide

Research direction

Reproduce the Zig and LLVM IR examples with llc -O3 -mcpu=znver5 and compare the generated AVX-512 assembly with the desired sequence. Trace the x86 backend's handling of conditional vector moves and merge masks; done means the redundant vmovdqa64/vblendm pattern is eliminated and a regression test covers the improved code generation.

Written by the indexing model from the issue text.

Assessment

Tech stack
zig
Domain
compilers, performance
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
48/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.