xref: /llvm-project/llvm/test/CodeGen/X86/memcmp-minsize-x32.ll (revision 95395ee51124792302390305b02cbeace5f07611)
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2; RUN: llc < %s -mtriple=i686-unknown-unknown -mattr=cmov | FileCheck %s --check-prefixes=X86,X86-NOSSE
3; RUN: llc < %s -mtriple=i686-unknown-unknown -mattr=+sse2 | FileCheck %s --check-prefixes=X86,X86-SSE2
4
5; This tests codegen time inlining/optimization of memcmp
6; rdar://6480398
7
8@.str = private constant [65 x i8] c"0123456789012345678901234567890123456789012345678901234567890123\00", align 1
9
10declare dso_local i32 @memcmp(ptr, ptr, i32)
11
12define i32 @length2(ptr %X, ptr %Y) nounwind minsize {
13; X86-LABEL: length2:
14; X86:       # %bb.0:
15; X86-NEXT:    pushl $2
16; X86-NEXT:    pushl {{[0-9]+}}(%esp)
17; X86-NEXT:    pushl {{[0-9]+}}(%esp)
18; X86-NEXT:    calll memcmp
19; X86-NEXT:    addl $12, %esp
20; X86-NEXT:    retl
21  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 2) nounwind
22  ret i32 %m
23}
24
25define i1 @length2_eq(ptr %X, ptr %Y) nounwind minsize {
26; X86-LABEL: length2_eq:
27; X86:       # %bb.0:
28; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
29; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
30; X86-NEXT:    movzwl (%ecx), %ecx
31; X86-NEXT:    cmpw (%eax), %cx
32; X86-NEXT:    sete %al
33; X86-NEXT:    retl
34  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 2) nounwind
35  %c = icmp eq i32 %m, 0
36  ret i1 %c
37}
38
39define i1 @length2_eq_const(ptr %X) nounwind minsize {
40; X86-LABEL: length2_eq_const:
41; X86:       # %bb.0:
42; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
43; X86-NEXT:    cmpw $12849, (%eax) # imm = 0x3231
44; X86-NEXT:    setne %al
45; X86-NEXT:    retl
46  %m = tail call i32 @memcmp(ptr %X, ptr getelementptr inbounds ([65 x i8], ptr @.str, i32 0, i32 1), i32 2) nounwind
47  %c = icmp ne i32 %m, 0
48  ret i1 %c
49}
50
51define i1 @length2_eq_nobuiltin_attr(ptr %X, ptr %Y) nounwind minsize {
52; X86-LABEL: length2_eq_nobuiltin_attr:
53; X86:       # %bb.0:
54; X86-NEXT:    pushl $2
55; X86-NEXT:    pushl {{[0-9]+}}(%esp)
56; X86-NEXT:    pushl {{[0-9]+}}(%esp)
57; X86-NEXT:    calll memcmp
58; X86-NEXT:    addl $12, %esp
59; X86-NEXT:    testl %eax, %eax
60; X86-NEXT:    sete %al
61; X86-NEXT:    retl
62  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 2) nounwind nobuiltin
63  %c = icmp eq i32 %m, 0
64  ret i1 %c
65}
66
67define i32 @length3(ptr %X, ptr %Y) nounwind minsize {
68; X86-LABEL: length3:
69; X86:       # %bb.0:
70; X86-NEXT:    pushl $3
71; X86-NEXT:    pushl {{[0-9]+}}(%esp)
72; X86-NEXT:    pushl {{[0-9]+}}(%esp)
73; X86-NEXT:    calll memcmp
74; X86-NEXT:    addl $12, %esp
75; X86-NEXT:    retl
76  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 3) nounwind
77  ret i32 %m
78}
79
80define i1 @length3_eq(ptr %X, ptr %Y) nounwind minsize {
81; X86-LABEL: length3_eq:
82; X86:       # %bb.0:
83; X86-NEXT:    pushl $3
84; X86-NEXT:    pushl {{[0-9]+}}(%esp)
85; X86-NEXT:    pushl {{[0-9]+}}(%esp)
86; X86-NEXT:    calll memcmp
87; X86-NEXT:    addl $12, %esp
88; X86-NEXT:    testl %eax, %eax
89; X86-NEXT:    setne %al
90; X86-NEXT:    retl
91  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 3) nounwind
92  %c = icmp ne i32 %m, 0
93  ret i1 %c
94}
95
96define i32 @length4(ptr %X, ptr %Y) nounwind minsize {
97; X86-LABEL: length4:
98; X86:       # %bb.0:
99; X86-NEXT:    pushl $4
100; X86-NEXT:    pushl {{[0-9]+}}(%esp)
101; X86-NEXT:    pushl {{[0-9]+}}(%esp)
102; X86-NEXT:    calll memcmp
103; X86-NEXT:    addl $12, %esp
104; X86-NEXT:    retl
105  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 4) nounwind
106  ret i32 %m
107}
108
109define i1 @length4_eq(ptr %X, ptr %Y) nounwind minsize {
110; X86-LABEL: length4_eq:
111; X86:       # %bb.0:
112; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
113; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
114; X86-NEXT:    movl (%ecx), %ecx
115; X86-NEXT:    cmpl (%eax), %ecx
116; X86-NEXT:    setne %al
117; X86-NEXT:    retl
118  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 4) nounwind
119  %c = icmp ne i32 %m, 0
120  ret i1 %c
121}
122
123define i1 @length4_eq_const(ptr %X) nounwind minsize {
124; X86-LABEL: length4_eq_const:
125; X86:       # %bb.0:
126; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
127; X86-NEXT:    cmpl $875770417, (%eax) # imm = 0x34333231
128; X86-NEXT:    sete %al
129; X86-NEXT:    retl
130  %m = tail call i32 @memcmp(ptr %X, ptr getelementptr inbounds ([65 x i8], ptr @.str, i32 0, i32 1), i32 4) nounwind
131  %c = icmp eq i32 %m, 0
132  ret i1 %c
133}
134
135define i32 @length5(ptr %X, ptr %Y) nounwind minsize {
136; X86-LABEL: length5:
137; X86:       # %bb.0:
138; X86-NEXT:    pushl $5
139; X86-NEXT:    pushl {{[0-9]+}}(%esp)
140; X86-NEXT:    pushl {{[0-9]+}}(%esp)
141; X86-NEXT:    calll memcmp
142; X86-NEXT:    addl $12, %esp
143; X86-NEXT:    retl
144  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 5) nounwind
145  ret i32 %m
146}
147
148define i1 @length5_eq(ptr %X, ptr %Y) nounwind minsize {
149; X86-LABEL: length5_eq:
150; X86:       # %bb.0:
151; X86-NEXT:    pushl $5
152; X86-NEXT:    pushl {{[0-9]+}}(%esp)
153; X86-NEXT:    pushl {{[0-9]+}}(%esp)
154; X86-NEXT:    calll memcmp
155; X86-NEXT:    addl $12, %esp
156; X86-NEXT:    testl %eax, %eax
157; X86-NEXT:    setne %al
158; X86-NEXT:    retl
159  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 5) nounwind
160  %c = icmp ne i32 %m, 0
161  ret i1 %c
162}
163
164define i32 @length8(ptr %X, ptr %Y) nounwind minsize {
165; X86-LABEL: length8:
166; X86:       # %bb.0:
167; X86-NEXT:    pushl $8
168; X86-NEXT:    pushl {{[0-9]+}}(%esp)
169; X86-NEXT:    pushl {{[0-9]+}}(%esp)
170; X86-NEXT:    calll memcmp
171; X86-NEXT:    addl $12, %esp
172; X86-NEXT:    retl
173  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 8) nounwind
174  ret i32 %m
175}
176
177define i1 @length8_eq(ptr %X, ptr %Y) nounwind minsize {
178; X86-LABEL: length8_eq:
179; X86:       # %bb.0:
180; X86-NEXT:    pushl $8
181; X86-NEXT:    pushl {{[0-9]+}}(%esp)
182; X86-NEXT:    pushl {{[0-9]+}}(%esp)
183; X86-NEXT:    calll memcmp
184; X86-NEXT:    addl $12, %esp
185; X86-NEXT:    testl %eax, %eax
186; X86-NEXT:    sete %al
187; X86-NEXT:    retl
188  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 8) nounwind
189  %c = icmp eq i32 %m, 0
190  ret i1 %c
191}
192
193define i1 @length8_eq_const(ptr %X) nounwind minsize {
194; X86-LABEL: length8_eq_const:
195; X86:       # %bb.0:
196; X86-NEXT:    pushl $8
197; X86-NEXT:    pushl $.L.str
198; X86-NEXT:    pushl {{[0-9]+}}(%esp)
199; X86-NEXT:    calll memcmp
200; X86-NEXT:    addl $12, %esp
201; X86-NEXT:    testl %eax, %eax
202; X86-NEXT:    setne %al
203; X86-NEXT:    retl
204  %m = tail call i32 @memcmp(ptr %X, ptr @.str, i32 8) nounwind
205  %c = icmp ne i32 %m, 0
206  ret i1 %c
207}
208
209define i1 @length12_eq(ptr %X, ptr %Y) nounwind minsize {
210; X86-LABEL: length12_eq:
211; X86:       # %bb.0:
212; X86-NEXT:    pushl $12
213; X86-NEXT:    pushl {{[0-9]+}}(%esp)
214; X86-NEXT:    pushl {{[0-9]+}}(%esp)
215; X86-NEXT:    calll memcmp
216; X86-NEXT:    addl $12, %esp
217; X86-NEXT:    testl %eax, %eax
218; X86-NEXT:    setne %al
219; X86-NEXT:    retl
220  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 12) nounwind
221  %c = icmp ne i32 %m, 0
222  ret i1 %c
223}
224
225define i32 @length12(ptr %X, ptr %Y) nounwind minsize {
226; X86-LABEL: length12:
227; X86:       # %bb.0:
228; X86-NEXT:    pushl $12
229; X86-NEXT:    pushl {{[0-9]+}}(%esp)
230; X86-NEXT:    pushl {{[0-9]+}}(%esp)
231; X86-NEXT:    calll memcmp
232; X86-NEXT:    addl $12, %esp
233; X86-NEXT:    retl
234  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 12) nounwind
235  ret i32 %m
236}
237
238; PR33329 - https://bugs.llvm.org/show_bug.cgi?id=33329
239
240define i32 @length16(ptr %X, ptr %Y) nounwind minsize {
241; X86-LABEL: length16:
242; X86:       # %bb.0:
243; X86-NEXT:    pushl $16
244; X86-NEXT:    pushl {{[0-9]+}}(%esp)
245; X86-NEXT:    pushl {{[0-9]+}}(%esp)
246; X86-NEXT:    calll memcmp
247; X86-NEXT:    addl $12, %esp
248; X86-NEXT:    retl
249  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 16) nounwind
250  ret i32 %m
251}
252
253define i1 @length16_eq(ptr %x, ptr %y) nounwind minsize {
254; X86-NOSSE-LABEL: length16_eq:
255; X86-NOSSE:       # %bb.0:
256; X86-NOSSE-NEXT:    pushl $16
257; X86-NOSSE-NEXT:    pushl {{[0-9]+}}(%esp)
258; X86-NOSSE-NEXT:    pushl {{[0-9]+}}(%esp)
259; X86-NOSSE-NEXT:    calll memcmp
260; X86-NOSSE-NEXT:    addl $12, %esp
261; X86-NOSSE-NEXT:    testl %eax, %eax
262; X86-NOSSE-NEXT:    setne %al
263; X86-NOSSE-NEXT:    retl
264;
265; X86-SSE2-LABEL: length16_eq:
266; X86-SSE2:       # %bb.0:
267; X86-SSE2-NEXT:    movl {{[0-9]+}}(%esp), %eax
268; X86-SSE2-NEXT:    movl {{[0-9]+}}(%esp), %ecx
269; X86-SSE2-NEXT:    movdqu (%ecx), %xmm0
270; X86-SSE2-NEXT:    movdqu (%eax), %xmm1
271; X86-SSE2-NEXT:    pcmpeqb %xmm0, %xmm1
272; X86-SSE2-NEXT:    pmovmskb %xmm1, %eax
273; X86-SSE2-NEXT:    cmpl $65535, %eax # imm = 0xFFFF
274; X86-SSE2-NEXT:    setne %al
275; X86-SSE2-NEXT:    retl
276  %call = tail call i32 @memcmp(ptr %x, ptr %y, i32 16) nounwind
277  %cmp = icmp ne i32 %call, 0
278  ret i1 %cmp
279}
280
281define i1 @length16_eq_const(ptr %X) nounwind minsize {
282; X86-NOSSE-LABEL: length16_eq_const:
283; X86-NOSSE:       # %bb.0:
284; X86-NOSSE-NEXT:    pushl $16
285; X86-NOSSE-NEXT:    pushl $.L.str
286; X86-NOSSE-NEXT:    pushl {{[0-9]+}}(%esp)
287; X86-NOSSE-NEXT:    calll memcmp
288; X86-NOSSE-NEXT:    addl $12, %esp
289; X86-NOSSE-NEXT:    testl %eax, %eax
290; X86-NOSSE-NEXT:    sete %al
291; X86-NOSSE-NEXT:    retl
292;
293; X86-SSE2-LABEL: length16_eq_const:
294; X86-SSE2:       # %bb.0:
295; X86-SSE2-NEXT:    movl {{[0-9]+}}(%esp), %eax
296; X86-SSE2-NEXT:    movdqu (%eax), %xmm0
297; X86-SSE2-NEXT:    pcmpeqb {{\.?LCPI[0-9]+_[0-9]+}}, %xmm0
298; X86-SSE2-NEXT:    pmovmskb %xmm0, %eax
299; X86-SSE2-NEXT:    cmpl $65535, %eax # imm = 0xFFFF
300; X86-SSE2-NEXT:    sete %al
301; X86-SSE2-NEXT:    retl
302  %m = tail call i32 @memcmp(ptr %X, ptr @.str, i32 16) nounwind
303  %c = icmp eq i32 %m, 0
304  ret i1 %c
305}
306
307; PR33914 - https://bugs.llvm.org/show_bug.cgi?id=33914
308
309define i32 @length24(ptr %X, ptr %Y) nounwind minsize {
310; X86-LABEL: length24:
311; X86:       # %bb.0:
312; X86-NEXT:    pushl $24
313; X86-NEXT:    pushl {{[0-9]+}}(%esp)
314; X86-NEXT:    pushl {{[0-9]+}}(%esp)
315; X86-NEXT:    calll memcmp
316; X86-NEXT:    addl $12, %esp
317; X86-NEXT:    retl
318  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 24) nounwind
319  ret i32 %m
320}
321
322define i1 @length24_eq(ptr %x, ptr %y) nounwind minsize {
323; X86-LABEL: length24_eq:
324; X86:       # %bb.0:
325; X86-NEXT:    pushl $24
326; X86-NEXT:    pushl {{[0-9]+}}(%esp)
327; X86-NEXT:    pushl {{[0-9]+}}(%esp)
328; X86-NEXT:    calll memcmp
329; X86-NEXT:    addl $12, %esp
330; X86-NEXT:    testl %eax, %eax
331; X86-NEXT:    sete %al
332; X86-NEXT:    retl
333  %call = tail call i32 @memcmp(ptr %x, ptr %y, i32 24) nounwind
334  %cmp = icmp eq i32 %call, 0
335  ret i1 %cmp
336}
337
338define i1 @length24_eq_const(ptr %X) nounwind minsize {
339; X86-LABEL: length24_eq_const:
340; X86:       # %bb.0:
341; X86-NEXT:    pushl $24
342; X86-NEXT:    pushl $.L.str
343; X86-NEXT:    pushl {{[0-9]+}}(%esp)
344; X86-NEXT:    calll memcmp
345; X86-NEXT:    addl $12, %esp
346; X86-NEXT:    testl %eax, %eax
347; X86-NEXT:    setne %al
348; X86-NEXT:    retl
349  %m = tail call i32 @memcmp(ptr %X, ptr @.str, i32 24) nounwind
350  %c = icmp ne i32 %m, 0
351  ret i1 %c
352}
353
354define i32 @length32(ptr %X, ptr %Y) nounwind minsize {
355; X86-LABEL: length32:
356; X86:       # %bb.0:
357; X86-NEXT:    pushl $32
358; X86-NEXT:    pushl {{[0-9]+}}(%esp)
359; X86-NEXT:    pushl {{[0-9]+}}(%esp)
360; X86-NEXT:    calll memcmp
361; X86-NEXT:    addl $12, %esp
362; X86-NEXT:    retl
363  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 32) nounwind
364  ret i32 %m
365}
366
367; PR33325 - https://bugs.llvm.org/show_bug.cgi?id=33325
368
369define i1 @length32_eq(ptr %x, ptr %y) nounwind minsize {
370; X86-LABEL: length32_eq:
371; X86:       # %bb.0:
372; X86-NEXT:    pushl $32
373; X86-NEXT:    pushl {{[0-9]+}}(%esp)
374; X86-NEXT:    pushl {{[0-9]+}}(%esp)
375; X86-NEXT:    calll memcmp
376; X86-NEXT:    addl $12, %esp
377; X86-NEXT:    testl %eax, %eax
378; X86-NEXT:    sete %al
379; X86-NEXT:    retl
380  %call = tail call i32 @memcmp(ptr %x, ptr %y, i32 32) nounwind
381  %cmp = icmp eq i32 %call, 0
382  ret i1 %cmp
383}
384
385define i1 @length32_eq_const(ptr %X) nounwind minsize {
386; X86-LABEL: length32_eq_const:
387; X86:       # %bb.0:
388; X86-NEXT:    pushl $32
389; X86-NEXT:    pushl $.L.str
390; X86-NEXT:    pushl {{[0-9]+}}(%esp)
391; X86-NEXT:    calll memcmp
392; X86-NEXT:    addl $12, %esp
393; X86-NEXT:    testl %eax, %eax
394; X86-NEXT:    setne %al
395; X86-NEXT:    retl
396  %m = tail call i32 @memcmp(ptr %X, ptr @.str, i32 32) nounwind
397  %c = icmp ne i32 %m, 0
398  ret i1 %c
399}
400
401define i32 @length64(ptr %X, ptr %Y) nounwind minsize {
402; X86-LABEL: length64:
403; X86:       # %bb.0:
404; X86-NEXT:    pushl $64
405; X86-NEXT:    pushl {{[0-9]+}}(%esp)
406; X86-NEXT:    pushl {{[0-9]+}}(%esp)
407; X86-NEXT:    calll memcmp
408; X86-NEXT:    addl $12, %esp
409; X86-NEXT:    retl
410  %m = tail call i32 @memcmp(ptr %X, ptr %Y, i32 64) nounwind
411  ret i32 %m
412}
413
414define i1 @length64_eq(ptr %x, ptr %y) nounwind minsize {
415; X86-LABEL: length64_eq:
416; X86:       # %bb.0:
417; X86-NEXT:    pushl $64
418; X86-NEXT:    pushl {{[0-9]+}}(%esp)
419; X86-NEXT:    pushl {{[0-9]+}}(%esp)
420; X86-NEXT:    calll memcmp
421; X86-NEXT:    addl $12, %esp
422; X86-NEXT:    testl %eax, %eax
423; X86-NEXT:    setne %al
424; X86-NEXT:    retl
425  %call = tail call i32 @memcmp(ptr %x, ptr %y, i32 64) nounwind
426  %cmp = icmp ne i32 %call, 0
427  ret i1 %cmp
428}
429
430define i1 @length64_eq_const(ptr %X) nounwind minsize {
431; X86-LABEL: length64_eq_const:
432; X86:       # %bb.0:
433; X86-NEXT:    pushl $64
434; X86-NEXT:    pushl $.L.str
435; X86-NEXT:    pushl {{[0-9]+}}(%esp)
436; X86-NEXT:    calll memcmp
437; X86-NEXT:    addl $12, %esp
438; X86-NEXT:    testl %eax, %eax
439; X86-NEXT:    sete %al
440; X86-NEXT:    retl
441  %m = tail call i32 @memcmp(ptr %X, ptr @.str, i32 64) nounwind
442  %c = icmp eq i32 %m, 0
443  ret i1 %c
444}
445
446