1 /* { dg-require-effective-target vect_int } */
2 /* { dg-require-effective-target vect_shift } */
3
4 #include <stdarg.h>
5 #include "tree-vect.h"
6
7 #define N 512
8
9 /* Modified rgb to rgb conversion from FFmpeg. */
10 __attribute__ ((noinline)) void
foo(unsigned char * src,unsigned char * dst)11 foo (unsigned char *src, unsigned char *dst)
12 {
13 unsigned char *s = src;
14 int *d = (int *)dst;
15 int i;
16
17 for (i = 0; i < N/4; i++)
18 {
19 const int b = *s++;
20 const int g = *s++;
21 const int r = *s++;
22 const int a = *s++;
23 *d = ((b>>3) | ((g&0xFC)<<3) | ((r&0xF8)<<8) | (a>>5));
24 d++;
25 }
26
27 s = src;
28 d = (int *)dst;
29 for (i = 0; i < N/4; i++)
30 {
31 const int b = *s++;
32 const int g = *s++;
33 const int r = *s++;
34 const int a = *s++;
35 if (*d != ((b>>3) | ((g&0xFC)<<3) | ((r&0xF8)<<8) | (a>>5)))
36 abort ();
37 d++;
38 }
39 }
40
main(void)41 int main (void)
42 {
43 int i;
44 unsigned char in[N], out[N];
45
46 check_vect ();
47
48 for (i = 0; i < N; i++)
49 {
50 in[i] = i;
51 out[i] = 255;
52 __asm__ volatile ("");
53 }
54
55 foo (in, out);
56
57 return 0;
58 }
59
60 /* This is an over-widening even though the final result is still an int.
61 It's better to do one vector of ops on chars and then widen than to
62 widen and then do 4 vectors of ops on ints. */
63 /* { dg-final { scan-tree-dump {vect_recog_over_widening_pattern: detected:[^\n]* << 3} "vect" } } */
64 /* { dg-final { scan-tree-dump {vect_recog_over_widening_pattern: detected:[^\n]* >> 3} "vect" } } */
65 /* { dg-final { scan-tree-dump {vect_recog_over_widening_pattern: detected:[^\n]* << 8} "vect" } } */
66 /* { dg-final { scan-tree-dump {vect_recog_over_widening_pattern: detected:[^\n]* >> 5} "vect" } } */
67 /* { dg-final { scan-tree-dump-times "vectorized 1 loops" 1 "vect" } } */
68
69