Re: What is the type of vector signed + vector unsigned?
On Tue, Dec 29, 2020 at 8:19 PM Alexander Monakov wrote: > > On Tue, 29 Dec 2020, Richard Biener via Gcc wrote: > > > >I think clang follows gcc and uses the type of the first operand. > > > > The desired behavior is the one that OpenCL specifies. If it is > > implementation > > defined we should document behavior. I agree symmetry is nice but eventually > > the current C behavior is what OpenCL specifies. > > Where does OpenCL specify that? Checking the 1.2 OpenCL standard I see the > opposite (the code would fail to compile): > > 6.2.1 > Implicit Conversions > > [...] > > Implicit conversions between built-in vector data types are disallowed. But then in 6.4 it says operations operate component-wise not saying anything about type requirements ... which suggests that int4 i; uint4 u; i = i + u; is valid and is implemented as in C i.x = i.x + u.x; i.y = i.y + u.y; ... and C then doing the appropriate implicit conversions. So yes, OpenCL doesn't specify implicit conversions and 6.4 suggests that components are promoted as to C rules which means the current C implementation matches neither. Note changing the C frontend can change operation outcome. IIRC we at some point decided to allow implicit sign conversions (we don't implement convert_VECTOR_TYPE nor clangs convert_vector). Richard. > Alexander
Re: What is the type of vector signed + vector unsigned?
On Tue, 29 Dec 2020, Richard Biener via Gcc wrote: > >I think clang follows gcc and uses the type of the first operand. > > The desired behavior is the one that OpenCL specifies. If it is implementation > defined we should document behavior. I agree symmetry is nice but eventually > the current C behavior is what OpenCL specifies. Where does OpenCL specify that? Checking the 1.2 OpenCL standard I see the opposite (the code would fail to compile): 6.2.1 Implicit Conversions [...] Implicit conversions between built-in vector data types are disallowed. Alexander
Re: What is the type of vector signed + vector unsigned?
On December 29, 2020 6:42:30 PM GMT+01:00, Marc Glisse wrote: >On Tue, 29 Dec 2020, Richard Sandiford via Gcc wrote: > >> Any thoughts on what f should return in the following testcase, given >the >> usual GNU behaviour of treating signed >> as arithmetic shift right? >> >>typedef int vs4 __attribute__((vector_size(16))); >>typedef unsigned int vu4 __attribute__((vector_size(16))); >>int >>f (void) >>{ >> vs4 x = { -1, -1, -1, -1 }; >> vu4 y = { 0, 0, 0, 0 }; >> return ((x + y) >> 1)[0]; >>} >> >> The C frontend takes the type of x+y from the first operand, so x+y >> is signed and f returns -1. > >Symmetry is an important property of addition in C/C++. > >> The C++ frontend applies similar rules to x+y as it would to scalars, >> with unsigned T having a higher rank than signed T, so x+y is >unsigned >> and f returns 0x7fff. > >That looks like the most natural choice. > >> FWIW, Clang treats x+y as signed, so f returns -1 for both C and C++. > >I think clang follows gcc and uses the type of the first operand. The desired behavior is the one that OpenCL specifies. If it is implementation defined we should document behavior. I agree symmetry is nice but eventually the current C behavior is what OpenCL specifies. Richard.
Re: What is the type of vector signed + vector unsigned?
On Tue, 29 Dec 2020, Richard Sandiford via Gcc wrote: Any thoughts on what f should return in the following testcase, given the usual GNU behaviour of treating signed >> as arithmetic shift right? typedef int vs4 __attribute__((vector_size(16))); typedef unsigned int vu4 __attribute__((vector_size(16))); int f (void) { vs4 x = { -1, -1, -1, -1 }; vu4 y = { 0, 0, 0, 0 }; return ((x + y) >> 1)[0]; } The C frontend takes the type of x+y from the first operand, so x+y is signed and f returns -1. Symmetry is an important property of addition in C/C++. The C++ frontend applies similar rules to x+y as it would to scalars, with unsigned T having a higher rank than signed T, so x+y is unsigned and f returns 0x7fff. That looks like the most natural choice. FWIW, Clang treats x+y as signed, so f returns -1 for both C and C++. I think clang follows gcc and uses the type of the first operand. -- Marc Glisse
What is the type of vector signed + vector unsigned?
Any thoughts on what f should return in the following testcase, given the usual GNU behaviour of treating signed >> as arithmetic shift right? typedef int vs4 __attribute__((vector_size(16))); typedef unsigned int vu4 __attribute__((vector_size(16))); int f (void) { vs4 x = { -1, -1, -1, -1 }; vu4 y = { 0, 0, 0, 0 }; return ((x + y) >> 1)[0]; } The C frontend takes the type of x+y from the first operand, so x+y is signed and f returns -1. The C++ frontend applies similar rules to x+y as it would to scalars, with unsigned T having a higher rank than signed T, so x+y is unsigned and f returns 0x7fff. FWIW, Clang treats x+y as signed, so f returns -1 for both C and C++. [Was looking at this in the context of PR96377.] Thanks, Richard