Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-19 Thread Matthias Kaehlcke
On Mon, Mar 18, 2019 at 04:55:38PM -0700, h...@zytor.com wrote:
> On March 18, 2019 4:52:19 PM PDT, Matthias Kaehlcke  wrote:
> >On Mon, Mar 18, 2019 at 04:44:03PM -0700, h...@zytor.com wrote:
> >> On March 18, 2019 3:16:39 PM PDT, Matthias Kaehlcke
> > wrote:
> >> >On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
> >> >> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke
> >> > wrote:
> >> >> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke
> >wrote:
> >> >> >> The compiler may emit calls to __lshrti3 from the compiler
> >runtime
> >> >> >> library, which results in undefined references:
> >> >> >> 
> >> >> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >> >> >>   include/linux/math64.h:186: undefined reference to
> >`__lshrti3'
> >> >> >> 
> >> >> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >> >> >> 
> >> >> >> Include the function for x86 builds with clang, which is the
> >> >> >> environment where the above error was observed.
> >> >> >> 
> >> >> >> Signed-off-by: Matthias Kaehlcke 
> >> >> >
> >> >> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
> >> >> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
> >> >> >error is fixed, a few comments inline for if the patch is
> >> >> >resurrected in the future because __lshrti3 is emitted in a
> >> >> >different context.
> >> >> >
> >> >> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> >> >> index 32e1e0f4b2d0..a71036471838 100644
> >> >> >> --- a/include/linux/libgcc.h
> >> >> >> +++ b/include/linux/libgcc.h
> >> >> >> @@ -22,15 +22,26 @@
> >> >> >>  #include 
> >> >> >> 
> >> >> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> >> >> +typedef int TItype __attribute__ ((mode (TI)));
> >> >> >
> >> >> >Consider using __int128 instead. Definition and use need a
> >> >> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)),
> >since
> >> >> >these 128 bit types aren't supported on all platforms.
> >> >> >
> >> >> >>  #ifdef __BIG_ENDIAN
> >> >> >>  struct DWstruct {
> >> >> >>  int high, low;
> >> >> >>  };
> >> >> >> +
> >> >> >> +struct DWstruct128 {
> >> >> >> +long long high, low;
> >> >> >> +};
> >> >> >
> >> >> >This struct isn't needed, struct DWstruct can be used.
> >> >> >
> >> >> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> >> >> new file mode 100644
> >> >> >> index ..2d2123bb3030
> >> >> >> --- /dev/null
> >> >> >> +++ b/lib/lshrti3.c
> >> >> >> @@ -0,0 +1,31 @@
> >> >> >> +// SPDX-License-Identifier: GPL-2.0
> >> >> >> +
> >> >> >> +#include 
> >> >> >> +#include 
> >> >> >> +
> >> >> >> +long long __lshrti3(long long u, word_type b)
> >> >> >
> >> >> >use TItype for input/output, which is what gcc does, though the
> >> >above
> >> >> >matches the interface in the documentation.
> >> >> >
> >> >> >> +{
> >> >> >> +DWunion128 uu, w;
> >> >> >> +word_type bm;
> >> >> >> +
> >> >> >> +if (b == 0)
> >> >> >> +return u;
> >> >> >> +
> >> >> >> +uu.ll = u;
> >> >> >> +bm = 64 - b;
> >> >> >> +
> >> >> >> +if (bm <= 0) {
> >> >> >> +w.s.high = 0;
> >> >> >> +w.s.low = (unsigned long long) uu.s.high >> -bm;
> >> >> >
> >> >> >include  and use u64 instead of unsigned long
> >long.
> >> >> 
> >> >> Ok, now I'm really puzzled.
> >> >> 
> >> >> How could we need a 128-bit shift when the prototype only has 64
> >bits
> >> >of input?!
> >> >
> >> >Good question, this is the code from libgcc:
> >> >
> >> >TItype
> >> >__lshrti3 (TItype u, shift_count_type b)
> >> >{
> >> >  if (b == 0)
> >> >return u;
> >> >
> >> >  const DWunion uu = {.ll = u};
> >> >  const shift_count_type bm = (8 * (8)) - b;
> >> >  DWunion w;
> >> >
> >> >  if (bm <= 0)
> >> >{
> >> >  w.s.high = 0;
> >> >  w.s.low = (UDItype) uu.s.high >> -bm;
> >> >}
> >> >  else
> >> >{
> >> >  const UDItype carries = (UDItype) uu.s.high << bm;
> >> >
> >> >  w.s.high = (UDItype) uu.s.high >> b;
> >> >  w.s.low = ((UDItype) uu.s.low >> b) | carries;
> >> >}
> >> >
> >> >  return w.ll;
> >> >}
> >> >
> >> >
> >> >My compiler knowledge is limited, my guess is that the function is a
> >> >generic implementation, and while a long long is 64-bit wide under
> >> >Linux it could be 128-bit on other platforms.
> >> 
> >> Yes, long long is just plain wrong.
> >> 
> >> How could we end up calling this function on 32 bits?!
> >
> >We didn't, in this case the function is called in 64-bit code
> >(arch/x86/kvm/x86.o: In function `mul_u64_u64_shr'), for the 32-bit
> >vDSO it was __lshrdi3.
> 
> Again, for 64 bits we can include libgcc in the link (with 
> --no-whole-archive).

I gave this a quick try but ended up with:

VDSOarch/x86/entry/vdso/vdso64.so.dbg
/usr/x86_64-pc-linux-gnu/x86_64-cros-linux-gnu/binutils-bin/2.27.0/ld.bfd.real:
cannot find -lgcc

I guess the solution is to specify the correct directory in LDPATH,
but not sure where that would be coming 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread hpa
On March 18, 2019 4:52:19 PM PDT, Matthias Kaehlcke  wrote:
>On Mon, Mar 18, 2019 at 04:44:03PM -0700, h...@zytor.com wrote:
>> On March 18, 2019 3:16:39 PM PDT, Matthias Kaehlcke
> wrote:
>> >On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
>> >> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke
>> > wrote:
>> >> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke
>wrote:
>> >> >> The compiler may emit calls to __lshrti3 from the compiler
>runtime
>> >> >> library, which results in undefined references:
>> >> >> 
>> >> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>> >> >>   include/linux/math64.h:186: undefined reference to
>`__lshrti3'
>> >> >> 
>> >> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> >> >> 
>> >> >> Include the function for x86 builds with clang, which is the
>> >> >> environment where the above error was observed.
>> >> >> 
>> >> >> Signed-off-by: Matthias Kaehlcke 
>> >> >
>> >> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
>> >> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
>> >> >error is fixed, a few comments inline for if the patch is
>> >> >resurrected in the future because __lshrti3 is emitted in a
>> >> >different context.
>> >> >
>> >> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> >> >> index 32e1e0f4b2d0..a71036471838 100644
>> >> >> --- a/include/linux/libgcc.h
>> >> >> +++ b/include/linux/libgcc.h
>> >> >> @@ -22,15 +22,26 @@
>> >> >>  #include 
>> >> >> 
>> >> >>  typedef int word_type __attribute__ ((mode (__word__)));
>> >> >> +typedef int TItype __attribute__ ((mode (TI)));
>> >> >
>> >> >Consider using __int128 instead. Definition and use need a
>> >> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)),
>since
>> >> >these 128 bit types aren't supported on all platforms.
>> >> >
>> >> >>  #ifdef __BIG_ENDIAN
>> >> >>  struct DWstruct {
>> >> >>int high, low;
>> >> >>  };
>> >> >> +
>> >> >> +struct DWstruct128 {
>> >> >> +  long long high, low;
>> >> >> +};
>> >> >
>> >> >This struct isn't needed, struct DWstruct can be used.
>> >> >
>> >> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> >> >> new file mode 100644
>> >> >> index ..2d2123bb3030
>> >> >> --- /dev/null
>> >> >> +++ b/lib/lshrti3.c
>> >> >> @@ -0,0 +1,31 @@
>> >> >> +// SPDX-License-Identifier: GPL-2.0
>> >> >> +
>> >> >> +#include 
>> >> >> +#include 
>> >> >> +
>> >> >> +long long __lshrti3(long long u, word_type b)
>> >> >
>> >> >use TItype for input/output, which is what gcc does, though the
>> >above
>> >> >matches the interface in the documentation.
>> >> >
>> >> >> +{
>> >> >> +  DWunion128 uu, w;
>> >> >> +  word_type bm;
>> >> >> +
>> >> >> +  if (b == 0)
>> >> >> +  return u;
>> >> >> +
>> >> >> +  uu.ll = u;
>> >> >> +  bm = 64 - b;
>> >> >> +
>> >> >> +  if (bm <= 0) {
>> >> >> +  w.s.high = 0;
>> >> >> +  w.s.low = (unsigned long long) uu.s.high >> -bm;
>> >> >
>> >> >include  and use u64 instead of unsigned long
>long.
>> >> 
>> >> Ok, now I'm really puzzled.
>> >> 
>> >> How could we need a 128-bit shift when the prototype only has 64
>bits
>> >of input?!
>> >
>> >Good question, this is the code from libgcc:
>> >
>> >TItype
>> >__lshrti3 (TItype u, shift_count_type b)
>> >{
>> >  if (b == 0)
>> >return u;
>> >
>> >  const DWunion uu = {.ll = u};
>> >  const shift_count_type bm = (8 * (8)) - b;
>> >  DWunion w;
>> >
>> >  if (bm <= 0)
>> >{
>> >  w.s.high = 0;
>> >  w.s.low = (UDItype) uu.s.high >> -bm;
>> >}
>> >  else
>> >{
>> >  const UDItype carries = (UDItype) uu.s.high << bm;
>> >
>> >  w.s.high = (UDItype) uu.s.high >> b;
>> >  w.s.low = ((UDItype) uu.s.low >> b) | carries;
>> >}
>> >
>> >  return w.ll;
>> >}
>> >
>> >
>> >My compiler knowledge is limited, my guess is that the function is a
>> >generic implementation, and while a long long is 64-bit wide under
>> >Linux it could be 128-bit on other platforms.
>> 
>> Yes, long long is just plain wrong.
>> 
>> How could we end up calling this function on 32 bits?!
>
>We didn't, in this case the function is called in 64-bit code
>(arch/x86/kvm/x86.o: In function `mul_u64_u64_shr'), for the 32-bit
>vDSO it was __lshrdi3.

Again, for 64 bits we can include libgcc in the link (with --no-whole-archive).
-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread hpa
On March 18, 2019 4:52:19 PM PDT, Matthias Kaehlcke  wrote:
>On Mon, Mar 18, 2019 at 04:44:03PM -0700, h...@zytor.com wrote:
>> On March 18, 2019 3:16:39 PM PDT, Matthias Kaehlcke
> wrote:
>> >On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
>> >> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke
>> > wrote:
>> >> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke
>wrote:
>> >> >> The compiler may emit calls to __lshrti3 from the compiler
>runtime
>> >> >> library, which results in undefined references:
>> >> >> 
>> >> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>> >> >>   include/linux/math64.h:186: undefined reference to
>`__lshrti3'
>> >> >> 
>> >> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> >> >> 
>> >> >> Include the function for x86 builds with clang, which is the
>> >> >> environment where the above error was observed.
>> >> >> 
>> >> >> Signed-off-by: Matthias Kaehlcke 
>> >> >
>> >> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
>> >> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
>> >> >error is fixed, a few comments inline for if the patch is
>> >> >resurrected in the future because __lshrti3 is emitted in a
>> >> >different context.
>> >> >
>> >> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> >> >> index 32e1e0f4b2d0..a71036471838 100644
>> >> >> --- a/include/linux/libgcc.h
>> >> >> +++ b/include/linux/libgcc.h
>> >> >> @@ -22,15 +22,26 @@
>> >> >>  #include 
>> >> >> 
>> >> >>  typedef int word_type __attribute__ ((mode (__word__)));
>> >> >> +typedef int TItype __attribute__ ((mode (TI)));
>> >> >
>> >> >Consider using __int128 instead. Definition and use need a
>> >> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)),
>since
>> >> >these 128 bit types aren't supported on all platforms.
>> >> >
>> >> >>  #ifdef __BIG_ENDIAN
>> >> >>  struct DWstruct {
>> >> >>int high, low;
>> >> >>  };
>> >> >> +
>> >> >> +struct DWstruct128 {
>> >> >> +  long long high, low;
>> >> >> +};
>> >> >
>> >> >This struct isn't needed, struct DWstruct can be used.
>> >> >
>> >> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> >> >> new file mode 100644
>> >> >> index ..2d2123bb3030
>> >> >> --- /dev/null
>> >> >> +++ b/lib/lshrti3.c
>> >> >> @@ -0,0 +1,31 @@
>> >> >> +// SPDX-License-Identifier: GPL-2.0
>> >> >> +
>> >> >> +#include 
>> >> >> +#include 
>> >> >> +
>> >> >> +long long __lshrti3(long long u, word_type b)
>> >> >
>> >> >use TItype for input/output, which is what gcc does, though the
>> >above
>> >> >matches the interface in the documentation.
>> >> >
>> >> >> +{
>> >> >> +  DWunion128 uu, w;
>> >> >> +  word_type bm;
>> >> >> +
>> >> >> +  if (b == 0)
>> >> >> +  return u;
>> >> >> +
>> >> >> +  uu.ll = u;
>> >> >> +  bm = 64 - b;
>> >> >> +
>> >> >> +  if (bm <= 0) {
>> >> >> +  w.s.high = 0;
>> >> >> +  w.s.low = (unsigned long long) uu.s.high >> -bm;
>> >> >
>> >> >include  and use u64 instead of unsigned long
>long.
>> >> 
>> >> Ok, now I'm really puzzled.
>> >> 
>> >> How could we need a 128-bit shift when the prototype only has 64
>bits
>> >of input?!
>> >
>> >Good question, this is the code from libgcc:
>> >
>> >TItype
>> >__lshrti3 (TItype u, shift_count_type b)
>> >{
>> >  if (b == 0)
>> >return u;
>> >
>> >  const DWunion uu = {.ll = u};
>> >  const shift_count_type bm = (8 * (8)) - b;
>> >  DWunion w;
>> >
>> >  if (bm <= 0)
>> >{
>> >  w.s.high = 0;
>> >  w.s.low = (UDItype) uu.s.high >> -bm;
>> >}
>> >  else
>> >{
>> >  const UDItype carries = (UDItype) uu.s.high << bm;
>> >
>> >  w.s.high = (UDItype) uu.s.high >> b;
>> >  w.s.low = ((UDItype) uu.s.low >> b) | carries;
>> >}
>> >
>> >  return w.ll;
>> >}
>> >
>> >
>> >My compiler knowledge is limited, my guess is that the function is a
>> >generic implementation, and while a long long is 64-bit wide under
>> >Linux it could be 128-bit on other platforms.
>> 
>> Yes, long long is just plain wrong.
>> 
>> How could we end up calling this function on 32 bits?!
>
>We didn't, in this case the function is called in 64-bit code
>(arch/x86/kvm/x86.o: In function `mul_u64_u64_shr'), for the 32-bit
>vDSO it was __lshrdi3.

That makes more sense.
-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Matthias Kaehlcke
On Mon, Mar 18, 2019 at 04:44:03PM -0700, h...@zytor.com wrote:
> On March 18, 2019 3:16:39 PM PDT, Matthias Kaehlcke  wrote:
> >On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
> >> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke
> > wrote:
> >> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke wrote:
> >> >> The compiler may emit calls to __lshrti3 from the compiler runtime
> >> >> library, which results in undefined references:
> >> >> 
> >> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >> >> 
> >> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >> >> 
> >> >> Include the function for x86 builds with clang, which is the
> >> >> environment where the above error was observed.
> >> >> 
> >> >> Signed-off-by: Matthias Kaehlcke 
> >> >
> >> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
> >> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
> >> >error is fixed, a few comments inline for if the patch is
> >> >resurrected in the future because __lshrti3 is emitted in a
> >> >different context.
> >> >
> >> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> >> index 32e1e0f4b2d0..a71036471838 100644
> >> >> --- a/include/linux/libgcc.h
> >> >> +++ b/include/linux/libgcc.h
> >> >> @@ -22,15 +22,26 @@
> >> >>  #include 
> >> >> 
> >> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> >> +typedef int TItype __attribute__ ((mode (TI)));
> >> >
> >> >Consider using __int128 instead. Definition and use need a
> >> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)), since
> >> >these 128 bit types aren't supported on all platforms.
> >> >
> >> >>  #ifdef __BIG_ENDIAN
> >> >>  struct DWstruct {
> >> >> int high, low;
> >> >>  };
> >> >> +
> >> >> +struct DWstruct128 {
> >> >> +   long long high, low;
> >> >> +};
> >> >
> >> >This struct isn't needed, struct DWstruct can be used.
> >> >
> >> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> >> new file mode 100644
> >> >> index ..2d2123bb3030
> >> >> --- /dev/null
> >> >> +++ b/lib/lshrti3.c
> >> >> @@ -0,0 +1,31 @@
> >> >> +// SPDX-License-Identifier: GPL-2.0
> >> >> +
> >> >> +#include 
> >> >> +#include 
> >> >> +
> >> >> +long long __lshrti3(long long u, word_type b)
> >> >
> >> >use TItype for input/output, which is what gcc does, though the
> >above
> >> >matches the interface in the documentation.
> >> >
> >> >> +{
> >> >> +   DWunion128 uu, w;
> >> >> +   word_type bm;
> >> >> +
> >> >> +   if (b == 0)
> >> >> +   return u;
> >> >> +
> >> >> +   uu.ll = u;
> >> >> +   bm = 64 - b;
> >> >> +
> >> >> +   if (bm <= 0) {
> >> >> +   w.s.high = 0;
> >> >> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
> >> >
> >> >include  and use u64 instead of unsigned long long.
> >> 
> >> Ok, now I'm really puzzled.
> >> 
> >> How could we need a 128-bit shift when the prototype only has 64 bits
> >of input?!
> >
> >Good question, this is the code from libgcc:
> >
> >TItype
> >__lshrti3 (TItype u, shift_count_type b)
> >{
> >  if (b == 0)
> >return u;
> >
> >  const DWunion uu = {.ll = u};
> >  const shift_count_type bm = (8 * (8)) - b;
> >  DWunion w;
> >
> >  if (bm <= 0)
> >{
> >  w.s.high = 0;
> >  w.s.low = (UDItype) uu.s.high >> -bm;
> >}
> >  else
> >{
> >  const UDItype carries = (UDItype) uu.s.high << bm;
> >
> >  w.s.high = (UDItype) uu.s.high >> b;
> >  w.s.low = ((UDItype) uu.s.low >> b) | carries;
> >}
> >
> >  return w.ll;
> >}
> >
> >
> >My compiler knowledge is limited, my guess is that the function is a
> >generic implementation, and while a long long is 64-bit wide under
> >Linux it could be 128-bit on other platforms.
> 
> Yes, long long is just plain wrong.
> 
> How could we end up calling this function on 32 bits?!

We didn't, in this case the function is called in 64-bit code
(arch/x86/kvm/x86.o: In function `mul_u64_u64_shr'), for the 32-bit
vDSO it was __lshrdi3.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread hpa
On March 18, 2019 3:16:39 PM PDT, Matthias Kaehlcke  wrote:
>On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
>> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke
> wrote:
>> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke wrote:
>> >> The compiler may emit calls to __lshrti3 from the compiler runtime
>> >> library, which results in undefined references:
>> >> 
>> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>> >> 
>> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> >> 
>> >> Include the function for x86 builds with clang, which is the
>> >> environment where the above error was observed.
>> >> 
>> >> Signed-off-by: Matthias Kaehlcke 
>> >
>> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
>> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
>> >error is fixed, a few comments inline for if the patch is
>> >resurrected in the future because __lshrti3 is emitted in a
>> >different context.
>> >
>> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> >> index 32e1e0f4b2d0..a71036471838 100644
>> >> --- a/include/linux/libgcc.h
>> >> +++ b/include/linux/libgcc.h
>> >> @@ -22,15 +22,26 @@
>> >>  #include 
>> >> 
>> >>  typedef int word_type __attribute__ ((mode (__word__)));
>> >> +typedef int TItype __attribute__ ((mode (TI)));
>> >
>> >Consider using __int128 instead. Definition and use need a
>> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)), since
>> >these 128 bit types aren't supported on all platforms.
>> >
>> >>  #ifdef __BIG_ENDIAN
>> >>  struct DWstruct {
>> >>   int high, low;
>> >>  };
>> >> +
>> >> +struct DWstruct128 {
>> >> + long long high, low;
>> >> +};
>> >
>> >This struct isn't needed, struct DWstruct can be used.
>> >
>> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> >> new file mode 100644
>> >> index ..2d2123bb3030
>> >> --- /dev/null
>> >> +++ b/lib/lshrti3.c
>> >> @@ -0,0 +1,31 @@
>> >> +// SPDX-License-Identifier: GPL-2.0
>> >> +
>> >> +#include 
>> >> +#include 
>> >> +
>> >> +long long __lshrti3(long long u, word_type b)
>> >
>> >use TItype for input/output, which is what gcc does, though the
>above
>> >matches the interface in the documentation.
>> >
>> >> +{
>> >> + DWunion128 uu, w;
>> >> + word_type bm;
>> >> +
>> >> + if (b == 0)
>> >> + return u;
>> >> +
>> >> + uu.ll = u;
>> >> + bm = 64 - b;
>> >> +
>> >> + if (bm <= 0) {
>> >> + w.s.high = 0;
>> >> + w.s.low = (unsigned long long) uu.s.high >> -bm;
>> >
>> >include  and use u64 instead of unsigned long long.
>> 
>> Ok, now I'm really puzzled.
>> 
>> How could we need a 128-bit shift when the prototype only has 64 bits
>of input?!
>
>Good question, this is the code from libgcc:
>
>TItype
>__lshrti3 (TItype u, shift_count_type b)
>{
>  if (b == 0)
>return u;
>
>  const DWunion uu = {.ll = u};
>  const shift_count_type bm = (8 * (8)) - b;
>  DWunion w;
>
>  if (bm <= 0)
>{
>  w.s.high = 0;
>  w.s.low = (UDItype) uu.s.high >> -bm;
>}
>  else
>{
>  const UDItype carries = (UDItype) uu.s.high << bm;
>
>  w.s.high = (UDItype) uu.s.high >> b;
>  w.s.low = ((UDItype) uu.s.low >> b) | carries;
>}
>
>  return w.ll;
>}
>
>
>My compiler knowledge is limited, my guess is that the function is a
>generic implementation, and while a long long is 64-bit wide under
>Linux it could be 128-bit on other platforms.

Yes, long long is just plain wrong.

How could we end up calling this function on 32 bits?!
-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Matthias Kaehlcke
On Mon, Mar 18, 2019 at 02:50:44PM -0700, h...@zytor.com wrote:
> On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke  wrote:
> >On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke wrote:
> >> The compiler may emit calls to __lshrti3 from the compiler runtime
> >> library, which results in undefined references:
> >> 
> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >> 
> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >> 
> >> Include the function for x86 builds with clang, which is the
> >> environment where the above error was observed.
> >> 
> >> Signed-off-by: Matthias Kaehlcke 
> >
> >With "Revert "kbuild: use -Oz instead of -Os when using clang"
> >(https://lore.kernel.org/patchwork/patch/1051932/) the above
> >error is fixed, a few comments inline for if the patch is
> >resurrected in the future because __lshrti3 is emitted in a
> >different context.
> >
> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> index 32e1e0f4b2d0..a71036471838 100644
> >> --- a/include/linux/libgcc.h
> >> +++ b/include/linux/libgcc.h
> >> @@ -22,15 +22,26 @@
> >>  #include 
> >> 
> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> +typedef int TItype __attribute__ ((mode (TI)));
> >
> >Consider using __int128 instead. Definition and use need a
> >'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)), since
> >these 128 bit types aren't supported on all platforms.
> >
> >>  #ifdef __BIG_ENDIAN
> >>  struct DWstruct {
> >>int high, low;
> >>  };
> >> +
> >> +struct DWstruct128 {
> >> +  long long high, low;
> >> +};
> >
> >This struct isn't needed, struct DWstruct can be used.
> >
> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> new file mode 100644
> >> index ..2d2123bb3030
> >> --- /dev/null
> >> +++ b/lib/lshrti3.c
> >> @@ -0,0 +1,31 @@
> >> +// SPDX-License-Identifier: GPL-2.0
> >> +
> >> +#include 
> >> +#include 
> >> +
> >> +long long __lshrti3(long long u, word_type b)
> >
> >use TItype for input/output, which is what gcc does, though the above
> >matches the interface in the documentation.
> >
> >> +{
> >> +  DWunion128 uu, w;
> >> +  word_type bm;
> >> +
> >> +  if (b == 0)
> >> +  return u;
> >> +
> >> +  uu.ll = u;
> >> +  bm = 64 - b;
> >> +
> >> +  if (bm <= 0) {
> >> +  w.s.high = 0;
> >> +  w.s.low = (unsigned long long) uu.s.high >> -bm;
> >
> >include  and use u64 instead of unsigned long long.
> 
> Ok, now I'm really puzzled.
> 
> How could we need a 128-bit shift when the prototype only has 64 bits of 
> input?!

Good question, this is the code from libgcc:

TItype
__lshrti3 (TItype u, shift_count_type b)
{
  if (b == 0)
return u;

  const DWunion uu = {.ll = u};
  const shift_count_type bm = (8 * (8)) - b;
  DWunion w;

  if (bm <= 0)
{
  w.s.high = 0;
  w.s.low = (UDItype) uu.s.high >> -bm;
}
  else
{
  const UDItype carries = (UDItype) uu.s.high << bm;

  w.s.high = (UDItype) uu.s.high >> b;
  w.s.low = ((UDItype) uu.s.low >> b) | carries;
}

  return w.ll;
}


My compiler knowledge is limited, my guess is that the function is a
generic implementation, and while a long long is 64-bit wide under
Linux it could be 128-bit on other platforms.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread hpa
On March 18, 2019 2:31:13 PM PDT, Matthias Kaehlcke  wrote:
>On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke wrote:
>> The compiler may emit calls to __lshrti3 from the compiler runtime
>> library, which results in undefined references:
>> 
>> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>> 
>> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> 
>> Include the function for x86 builds with clang, which is the
>> environment where the above error was observed.
>> 
>> Signed-off-by: Matthias Kaehlcke 
>
>With "Revert "kbuild: use -Oz instead of -Os when using clang"
>(https://lore.kernel.org/patchwork/patch/1051932/) the above
>error is fixed, a few comments inline for if the patch is
>resurrected in the future because __lshrti3 is emitted in a
>different context.
>
>> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> index 32e1e0f4b2d0..a71036471838 100644
>> --- a/include/linux/libgcc.h
>> +++ b/include/linux/libgcc.h
>> @@ -22,15 +22,26 @@
>>  #include 
>> 
>>  typedef int word_type __attribute__ ((mode (__word__)));
>> +typedef int TItype __attribute__ ((mode (TI)));
>
>Consider using __int128 instead. Definition and use need a
>'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)), since
>these 128 bit types aren't supported on all platforms.
>
>>  #ifdef __BIG_ENDIAN
>>  struct DWstruct {
>>  int high, low;
>>  };
>> +
>> +struct DWstruct128 {
>> +long long high, low;
>> +};
>
>This struct isn't needed, struct DWstruct can be used.
>
>> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> new file mode 100644
>> index ..2d2123bb3030
>> --- /dev/null
>> +++ b/lib/lshrti3.c
>> @@ -0,0 +1,31 @@
>> +// SPDX-License-Identifier: GPL-2.0
>> +
>> +#include 
>> +#include 
>> +
>> +long long __lshrti3(long long u, word_type b)
>
>use TItype for input/output, which is what gcc does, though the above
>matches the interface in the documentation.
>
>> +{
>> +DWunion128 uu, w;
>> +word_type bm;
>> +
>> +if (b == 0)
>> +return u;
>> +
>> +uu.ll = u;
>> +bm = 64 - b;
>> +
>> +if (bm <= 0) {
>> +w.s.high = 0;
>> +w.s.low = (unsigned long long) uu.s.high >> -bm;
>
>include  and use u64 instead of unsigned long long.

Ok, now I'm really puzzled.

How could we need a 128-bit shift when the prototype only has 64 bits of input?!

-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Matthias Kaehlcke
On Fri, Mar 15, 2019 at 01:54:50PM -0700, Matthias Kaehlcke wrote:
> The compiler may emit calls to __lshrti3 from the compiler runtime
> library, which results in undefined references:
> 
> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> 
> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> 
> Include the function for x86 builds with clang, which is the
> environment where the above error was observed.
> 
> Signed-off-by: Matthias Kaehlcke 

With "Revert "kbuild: use -Oz instead of -Os when using clang"
(https://lore.kernel.org/patchwork/patch/1051932/) the above
error is fixed, a few comments inline for if the patch is
resurrected in the future because __lshrti3 is emitted in a
different context.

> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> index 32e1e0f4b2d0..a71036471838 100644
> --- a/include/linux/libgcc.h
> +++ b/include/linux/libgcc.h
> @@ -22,15 +22,26 @@
>  #include 
> 
>  typedef int word_type __attribute__ ((mode (__word__)));
> +typedef int TItype __attribute__ ((mode (TI)));

Consider using __int128 instead. Definition and use need a
'defined(__SIZEOF_INT128__)' guard  (similar for mode (TI)), since
these 128 bit types aren't supported on all platforms.

>  #ifdef __BIG_ENDIAN
>  struct DWstruct {
>   int high, low;
>  };
> +
> +struct DWstruct128 {
> + long long high, low;
> +};

This struct isn't needed, struct DWstruct can be used.

> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> new file mode 100644
> index ..2d2123bb3030
> --- /dev/null
> +++ b/lib/lshrti3.c
> @@ -0,0 +1,31 @@
> +// SPDX-License-Identifier: GPL-2.0
> +
> +#include 
> +#include 
> +
> +long long __lshrti3(long long u, word_type b)

use TItype for input/output, which is what gcc does, though the above
matches the interface in the documentation.

> +{
> + DWunion128 uu, w;
> + word_type bm;
> +
> + if (b == 0)
> + return u;
> +
> + uu.ll = u;
> + bm = 64 - b;
> +
> + if (bm <= 0) {
> + w.s.high = 0;
> + w.s.low = (unsigned long long) uu.s.high >> -bm;

include  and use u64 instead of unsigned long long.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Matthias Kaehlcke
On Fri, Mar 15, 2019 at 04:53:40PM -0700, h...@zytor.com wrote:
> On March 15, 2019 4:47:01 PM PDT, Matthias Kaehlcke  wrote:
> >On Fri, Mar 15, 2019 at 03:12:08PM -0700, h...@zytor.com wrote:
> >> On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers
> > wrote:
> >> >On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
> >> >wrote:
> >> >>
> >> >> The compiler may emit calls to __lshrti3 from the compiler runtime
> >> >> library, which results in undefined references:
> >> >>
> >> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >> >
> >> >Looks like Clang will emit this at -Oz (but not -O2):
> >> >https://godbolt.org/z/w1_2YC
> >> >
> >> >>
> >> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >> >
> >> >Has it changed since? If so why not a newer version of libgcc_s?
> >> >
> >> >>
> >> >> Include the function for x86 builds with clang, which is the
> >> >> environment where the above error was observed.
> >> >>
> >> >> Signed-off-by: Matthias Kaehlcke 
> >> >> ---
> >> >>  arch/x86/Kconfig   |  1 +
> >> >>  include/linux/libgcc.h | 16 
> >> >>  lib/Kconfig|  3 +++
> >> >>  lib/Makefile   |  1 +
> >> >>  lib/lshrti3.c  | 31 +++
> >> >>  5 files changed, 52 insertions(+)
> >> >>  create mode 100644 lib/lshrti3.c
> >> >>
> >> >> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
> >> >> index c1f9b3cf437c..a5e0d923845d 100644
> >> >> --- a/arch/x86/Kconfig
> >> >> +++ b/arch/x86/Kconfig
> >> >> @@ -105,6 +105,7 @@ config X86
> >> >> select GENERIC_IRQ_PROBE
> >> >> select GENERIC_IRQ_RESERVATION_MODE
> >> >> select GENERIC_IRQ_SHOW
> >> >> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
> >> >> select GENERIC_PENDING_IRQ  if SMP
> >> >> select GENERIC_SMP_IDLE_THREAD
> >> >> select GENERIC_STRNCPY_FROM_USER
> >> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> >> index 32e1e0f4b2d0..a71036471838 100644
> >> >> --- a/include/linux/libgcc.h
> >> >> +++ b/include/linux/libgcc.h
> >> >> @@ -22,15 +22,26 @@
> >> >>  #include 
> >> >>
> >> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> >> +typedef int TItype __attribute__ ((mode (TI)));
> >> >
> >> >Well that's an interesting new compiler attribute.
> >>
> >>https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
> >> >Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
> >> >typedef int TItype __mode(TI);
> >> >
> >> >>
> >> >>  #ifdef __BIG_ENDIAN
> >> >>  struct DWstruct {
> >> >> int high, low;
> >> >>  };
> >> >> +
> >> >> +struct DWstruct128 {
> >> >> +   long long high, low;
> >> >> +};
> >> >> +
> >> >>  #elif defined(__LITTLE_ENDIAN)
> >> >>  struct DWstruct {
> >> >> int low, high;
> >> >>  };
> >> >> +
> >> >> +struct DWstruct128 {
> >> >> +   long long low, high;
> >> >> +};
> >> >> +
> >> >>  #else
> >> >>  #error I feel sick.
> >> >>  #endif
> >> >> @@ -40,4 +51,9 @@ typedef union {
> >> >> long long ll;
> >> >>  } DWunion;
> >> >>
> >> >> +typedef union {
> >> >> +   struct DWstruct128 s;
> >> >> +   TItype ll;
> >> >> +} DWunion128;
> >> >> +
> >> >>  #endif /* __ASM_LIBGCC_H */
> >> >> diff --git a/lib/Kconfig b/lib/Kconfig
> >> >> index a9e56539bd11..369e10259ea6 100644
> >> >> --- a/lib/Kconfig
> >> >> +++ b/lib/Kconfig
> >> >> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
> >> >>  config GENERIC_LIB_LSHRDI3
> >> >> bool
> >> >>
> >> >> +config GENERIC_LIB_LSHRTI3
> >> >> +   bool
> >> >> +
> >> >>  config GENERIC_LIB_MULDI3
> >> >> bool
> >> >>
> >> >> diff --git a/lib/Makefile b/lib/Makefile
> >> >> index 4e066120a0d6..42648411f451 100644
> >> >> --- a/lib/Makefile
> >> >> +++ b/lib/Makefile
> >> >> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
> >> >> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
> >> >>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
> >> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> >> new file mode 100644
> >> >> index ..2d2123bb3030
> >> >> --- /dev/null
> >> >> +++ b/lib/lshrti3.c
> >> >> @@ -0,0 +1,31 @@
> >> >> +// SPDX-License-Identifier: GPL-2.0
> >> >> +
> >> >> +#include 
> >> >> +#include 
> >> >> +
> >> >> +long long __lshrti3(long long u, word_type b)
> >> >> +{
> >> >> +   DWunion128 uu, w;
> >> >> +   word_type bm;
> >> >> +
> >> >> +   if (b == 0)
> >> >> +   return u;
> >> >> +
> >> >> +   uu.ll = u;
> >> >> +   bm = 64 - b;
> >> >> +
> >> >> +   if (bm <= 0) {
> >> >> +   

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Peter Zijlstra
On Mon, Mar 18, 2019 at 02:43:41PM +, David Laight wrote:
> From: Peter Zijlstra
> > Sent: 18 March 2019 09:14
> > On Fri, Mar 15, 2019 at 03:06:37PM -0700, Nick Desaulniers wrote:
> > > On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke  
> > > wrote:
> > > >
> > > > The compiler may emit calls to __lshrti3 from the compiler runtime
> > > > library, which results in undefined references:
> > > >
> > > > arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> > > >   include/linux/math64.h:186: undefined reference to `__lshrti3'
> > >
> > > Looks like Clang will emit this at -Oz (but not -O2):
> > > https://godbolt.org/z/w1_2YC
> > 
> > *OMG*, what is that compiler smoking and why do we want that?
> > 
> > It doesn't even do that for "-Os".
> 
> I like the way it moves %edx to %ecx, then %cl to %ecx and finally %ecx back 
> to %edx.
> I'm guessing this is all made worse by the prototype containing 'char' not 
> 'int'.
> 
> I'm sure the register tracking gets worse in every version of gcc.

This is clang, no GCC on that list comes even close to generating
anything as 'brilliant' as that.


RE: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread David Laight
From: Peter Zijlstra
> Sent: 18 March 2019 09:14
> On Fri, Mar 15, 2019 at 03:06:37PM -0700, Nick Desaulniers wrote:
> > On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke  wrote:
> > >
> > > The compiler may emit calls to __lshrti3 from the compiler runtime
> > > library, which results in undefined references:
> > >
> > > arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> > >   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >
> > Looks like Clang will emit this at -Oz (but not -O2):
> > https://godbolt.org/z/w1_2YC
> 
> *OMG*, what is that compiler smoking and why do we want that?
> 
> It doesn't even do that for "-Os".

I like the way it moves %edx to %ecx, then %cl to %ecx and finally %ecx back to 
%edx.
I'm guessing this is all made worse by the prototype containing 'char' not 
'int'.

I'm sure the register tracking gets worse in every version of gcc.

David

-
Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, 
UK
Registration No: 1397386 (Wales)



Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-18 Thread Peter Zijlstra
On Fri, Mar 15, 2019 at 03:06:37PM -0700, Nick Desaulniers wrote:
> On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke  wrote:
> >
> > The compiler may emit calls to __lshrti3 from the compiler runtime
> > library, which results in undefined references:
> >
> > arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >   include/linux/math64.h:186: undefined reference to `__lshrti3'
> 
> Looks like Clang will emit this at -Oz (but not -O2):
> https://godbolt.org/z/w1_2YC

*OMG*, what is that compiler smoking and why do we want that?

It doesn't even do that for "-Os".

So where "-Os" is "Optimize for Sadness" this "-Oz" thing is like a
downright depression. Please just take it out back. Don't enable crap
like this.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread hpa
On March 15, 2019 4:47:01 PM PDT, Matthias Kaehlcke  wrote:
>On Fri, Mar 15, 2019 at 03:12:08PM -0700, h...@zytor.com wrote:
>> On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers
> wrote:
>> >On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
>> >wrote:
>> >>
>> >> The compiler may emit calls to __lshrti3 from the compiler runtime
>> >> library, which results in undefined references:
>> >>
>> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>> >
>> >Looks like Clang will emit this at -Oz (but not -O2):
>> >https://godbolt.org/z/w1_2YC
>> >
>> >>
>> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> >
>> >Has it changed since? If so why not a newer version of libgcc_s?
>> >
>> >>
>> >> Include the function for x86 builds with clang, which is the
>> >> environment where the above error was observed.
>> >>
>> >> Signed-off-by: Matthias Kaehlcke 
>> >> ---
>> >>  arch/x86/Kconfig   |  1 +
>> >>  include/linux/libgcc.h | 16 
>> >>  lib/Kconfig|  3 +++
>> >>  lib/Makefile   |  1 +
>> >>  lib/lshrti3.c  | 31 +++
>> >>  5 files changed, 52 insertions(+)
>> >>  create mode 100644 lib/lshrti3.c
>> >>
>> >> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
>> >> index c1f9b3cf437c..a5e0d923845d 100644
>> >> --- a/arch/x86/Kconfig
>> >> +++ b/arch/x86/Kconfig
>> >> @@ -105,6 +105,7 @@ config X86
>> >> select GENERIC_IRQ_PROBE
>> >> select GENERIC_IRQ_RESERVATION_MODE
>> >> select GENERIC_IRQ_SHOW
>> >> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
>> >> select GENERIC_PENDING_IRQ  if SMP
>> >> select GENERIC_SMP_IDLE_THREAD
>> >> select GENERIC_STRNCPY_FROM_USER
>> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> >> index 32e1e0f4b2d0..a71036471838 100644
>> >> --- a/include/linux/libgcc.h
>> >> +++ b/include/linux/libgcc.h
>> >> @@ -22,15 +22,26 @@
>> >>  #include 
>> >>
>> >>  typedef int word_type __attribute__ ((mode (__word__)));
>> >> +typedef int TItype __attribute__ ((mode (TI)));
>> >
>> >Well that's an interesting new compiler attribute.
>>
>>https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
>> >Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
>> >typedef int TItype __mode(TI);
>> >
>> >>
>> >>  #ifdef __BIG_ENDIAN
>> >>  struct DWstruct {
>> >> int high, low;
>> >>  };
>> >> +
>> >> +struct DWstruct128 {
>> >> +   long long high, low;
>> >> +};
>> >> +
>> >>  #elif defined(__LITTLE_ENDIAN)
>> >>  struct DWstruct {
>> >> int low, high;
>> >>  };
>> >> +
>> >> +struct DWstruct128 {
>> >> +   long long low, high;
>> >> +};
>> >> +
>> >>  #else
>> >>  #error I feel sick.
>> >>  #endif
>> >> @@ -40,4 +51,9 @@ typedef union {
>> >> long long ll;
>> >>  } DWunion;
>> >>
>> >> +typedef union {
>> >> +   struct DWstruct128 s;
>> >> +   TItype ll;
>> >> +} DWunion128;
>> >> +
>> >>  #endif /* __ASM_LIBGCC_H */
>> >> diff --git a/lib/Kconfig b/lib/Kconfig
>> >> index a9e56539bd11..369e10259ea6 100644
>> >> --- a/lib/Kconfig
>> >> +++ b/lib/Kconfig
>> >> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
>> >>  config GENERIC_LIB_LSHRDI3
>> >> bool
>> >>
>> >> +config GENERIC_LIB_LSHRTI3
>> >> +   bool
>> >> +
>> >>  config GENERIC_LIB_MULDI3
>> >> bool
>> >>
>> >> diff --git a/lib/Makefile b/lib/Makefile
>> >> index 4e066120a0d6..42648411f451 100644
>> >> --- a/lib/Makefile
>> >> +++ b/lib/Makefile
>> >> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
>> >>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
>> >> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
>> >>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
>> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> >> new file mode 100644
>> >> index ..2d2123bb3030
>> >> --- /dev/null
>> >> +++ b/lib/lshrti3.c
>> >> @@ -0,0 +1,31 @@
>> >> +// SPDX-License-Identifier: GPL-2.0
>> >> +
>> >> +#include 
>> >> +#include 
>> >> +
>> >> +long long __lshrti3(long long u, word_type b)
>> >> +{
>> >> +   DWunion128 uu, w;
>> >> +   word_type bm;
>> >> +
>> >> +   if (b == 0)
>> >> +   return u;
>> >> +
>> >> +   uu.ll = u;
>> >> +   bm = 64 - b;
>> >> +
>> >> +   if (bm <= 0) {
>> >> +   w.s.high = 0;
>> >> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
>> >> +   } else {
>> >> +   const unsigned long long carries =
>> >> +   (unsigned long long) uu.s.high << bm;
>> >> +   w.s.high = (unsigned long long) uu.s.high >> b;
>> >> +   w.s.low = ((unsigned long long) 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread hpa
On March 15, 2019 4:34:10 PM PDT, Matthias Kaehlcke  wrote:
>Hi Peter,
>
>On Fri, Mar 15, 2019 at 03:08:57PM -0700, h...@zytor.com wrote:
>> On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers
> wrote:
>> >On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
>> >wrote:
>> >>
>> >> The compiler may emit calls to __lshrti3 from the compiler runtime
>> >> library, which results in undefined references:
>> >>
>> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>> >
>> >Looks like Clang will emit this at -Oz (but not -O2):
>> >https://godbolt.org/z/w1_2YC
>> >
>> >>
>> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>> >
>> >Has it changed since? If so why not a newer version of libgcc_s?
>> >
>> >>
>> >> Include the function for x86 builds with clang, which is the
>> >> environment where the above error was observed.
>> >>
>> >> Signed-off-by: Matthias Kaehlcke 
>> >> ---
>> >>  arch/x86/Kconfig   |  1 +
>> >>  include/linux/libgcc.h | 16 
>> >>  lib/Kconfig|  3 +++
>> >>  lib/Makefile   |  1 +
>> >>  lib/lshrti3.c  | 31 +++
>> >>  5 files changed, 52 insertions(+)
>> >>  create mode 100644 lib/lshrti3.c
>> >>
>> >> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
>> >> index c1f9b3cf437c..a5e0d923845d 100644
>> >> --- a/arch/x86/Kconfig
>> >> +++ b/arch/x86/Kconfig
>> >> @@ -105,6 +105,7 @@ config X86
>> >> select GENERIC_IRQ_PROBE
>> >> select GENERIC_IRQ_RESERVATION_MODE
>> >> select GENERIC_IRQ_SHOW
>> >> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
>> >> select GENERIC_PENDING_IRQ  if SMP
>> >> select GENERIC_SMP_IDLE_THREAD
>> >> select GENERIC_STRNCPY_FROM_USER
>> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> >> index 32e1e0f4b2d0..a71036471838 100644
>> >> --- a/include/linux/libgcc.h
>> >> +++ b/include/linux/libgcc.h
>> >> @@ -22,15 +22,26 @@
>> >>  #include 
>> >>
>> >>  typedef int word_type __attribute__ ((mode (__word__)));
>> >> +typedef int TItype __attribute__ ((mode (TI)));
>> >
>> >Well that's an interesting new compiler attribute.
>>
>>https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
>> >Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
>> >typedef int TItype __mode(TI);
>> >
>> >>
>> >>  #ifdef __BIG_ENDIAN
>> >>  struct DWstruct {
>> >> int high, low;
>> >>  };
>> >> +
>> >> +struct DWstruct128 {
>> >> +   long long high, low;
>> >> +};
>> >> +
>> >>  #elif defined(__LITTLE_ENDIAN)
>> >>  struct DWstruct {
>> >> int low, high;
>> >>  };
>> >> +
>> >> +struct DWstruct128 {
>> >> +   long long low, high;
>> >> +};
>> >> +
>> >>  #else
>> >>  #error I feel sick.
>> >>  #endif
>> >> @@ -40,4 +51,9 @@ typedef union {
>> >> long long ll;
>> >>  } DWunion;
>> >>
>> >> +typedef union {
>> >> +   struct DWstruct128 s;
>> >> +   TItype ll;
>> >> +} DWunion128;
>> >> +
>> >>  #endif /* __ASM_LIBGCC_H */
>> >> diff --git a/lib/Kconfig b/lib/Kconfig
>> >> index a9e56539bd11..369e10259ea6 100644
>> >> --- a/lib/Kconfig
>> >> +++ b/lib/Kconfig
>> >> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
>> >>  config GENERIC_LIB_LSHRDI3
>> >> bool
>> >>
>> >> +config GENERIC_LIB_LSHRTI3
>> >> +   bool
>> >> +
>> >>  config GENERIC_LIB_MULDI3
>> >> bool
>> >>
>> >> diff --git a/lib/Makefile b/lib/Makefile
>> >> index 4e066120a0d6..42648411f451 100644
>> >> --- a/lib/Makefile
>> >> +++ b/lib/Makefile
>> >> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
>> >>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
>> >> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
>> >>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
>> >>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
>> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> >> new file mode 100644
>> >> index ..2d2123bb3030
>> >> --- /dev/null
>> >> +++ b/lib/lshrti3.c
>> >> @@ -0,0 +1,31 @@
>> >> +// SPDX-License-Identifier: GPL-2.0
>> >> +
>> >> +#include 
>> >> +#include 
>> >> +
>> >> +long long __lshrti3(long long u, word_type b)
>> >> +{
>> >> +   DWunion128 uu, w;
>> >> +   word_type bm;
>> >> +
>> >> +   if (b == 0)
>> >> +   return u;
>> >> +
>> >> +   uu.ll = u;
>> >> +   bm = 64 - b;
>> >> +
>> >> +   if (bm <= 0) {
>> >> +   w.s.high = 0;
>> >> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
>> >> +   } else {
>> >> +   const unsigned long long carries =
>> >> +   (unsigned long long) uu.s.high << bm;
>> >> +   w.s.high = (unsigned long long) uu.s.high >> b;
>> >> +   w.s.low = ((unsigned 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread Matthias Kaehlcke
On Fri, Mar 15, 2019 at 03:12:08PM -0700, h...@zytor.com wrote:
> On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers  
> wrote:
> >On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
> >wrote:
> >>
> >> The compiler may emit calls to __lshrti3 from the compiler runtime
> >> library, which results in undefined references:
> >>
> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >
> >Looks like Clang will emit this at -Oz (but not -O2):
> >https://godbolt.org/z/w1_2YC
> >
> >>
> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >
> >Has it changed since? If so why not a newer version of libgcc_s?
> >
> >>
> >> Include the function for x86 builds with clang, which is the
> >> environment where the above error was observed.
> >>
> >> Signed-off-by: Matthias Kaehlcke 
> >> ---
> >>  arch/x86/Kconfig   |  1 +
> >>  include/linux/libgcc.h | 16 
> >>  lib/Kconfig|  3 +++
> >>  lib/Makefile   |  1 +
> >>  lib/lshrti3.c  | 31 +++
> >>  5 files changed, 52 insertions(+)
> >>  create mode 100644 lib/lshrti3.c
> >>
> >> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
> >> index c1f9b3cf437c..a5e0d923845d 100644
> >> --- a/arch/x86/Kconfig
> >> +++ b/arch/x86/Kconfig
> >> @@ -105,6 +105,7 @@ config X86
> >> select GENERIC_IRQ_PROBE
> >> select GENERIC_IRQ_RESERVATION_MODE
> >> select GENERIC_IRQ_SHOW
> >> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
> >> select GENERIC_PENDING_IRQ  if SMP
> >> select GENERIC_SMP_IDLE_THREAD
> >> select GENERIC_STRNCPY_FROM_USER
> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> index 32e1e0f4b2d0..a71036471838 100644
> >> --- a/include/linux/libgcc.h
> >> +++ b/include/linux/libgcc.h
> >> @@ -22,15 +22,26 @@
> >>  #include 
> >>
> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> +typedef int TItype __attribute__ ((mode (TI)));
> >
> >Well that's an interesting new compiler attribute.
> >https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
> >Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
> >typedef int TItype __mode(TI);
> >
> >>
> >>  #ifdef __BIG_ENDIAN
> >>  struct DWstruct {
> >> int high, low;
> >>  };
> >> +
> >> +struct DWstruct128 {
> >> +   long long high, low;
> >> +};
> >> +
> >>  #elif defined(__LITTLE_ENDIAN)
> >>  struct DWstruct {
> >> int low, high;
> >>  };
> >> +
> >> +struct DWstruct128 {
> >> +   long long low, high;
> >> +};
> >> +
> >>  #else
> >>  #error I feel sick.
> >>  #endif
> >> @@ -40,4 +51,9 @@ typedef union {
> >> long long ll;
> >>  } DWunion;
> >>
> >> +typedef union {
> >> +   struct DWstruct128 s;
> >> +   TItype ll;
> >> +} DWunion128;
> >> +
> >>  #endif /* __ASM_LIBGCC_H */
> >> diff --git a/lib/Kconfig b/lib/Kconfig
> >> index a9e56539bd11..369e10259ea6 100644
> >> --- a/lib/Kconfig
> >> +++ b/lib/Kconfig
> >> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
> >>  config GENERIC_LIB_LSHRDI3
> >> bool
> >>
> >> +config GENERIC_LIB_LSHRTI3
> >> +   bool
> >> +
> >>  config GENERIC_LIB_MULDI3
> >> bool
> >>
> >> diff --git a/lib/Makefile b/lib/Makefile
> >> index 4e066120a0d6..42648411f451 100644
> >> --- a/lib/Makefile
> >> +++ b/lib/Makefile
> >> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
> >>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
> >> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
> >>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
> >>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> new file mode 100644
> >> index ..2d2123bb3030
> >> --- /dev/null
> >> +++ b/lib/lshrti3.c
> >> @@ -0,0 +1,31 @@
> >> +// SPDX-License-Identifier: GPL-2.0
> >> +
> >> +#include 
> >> +#include 
> >> +
> >> +long long __lshrti3(long long u, word_type b)
> >> +{
> >> +   DWunion128 uu, w;
> >> +   word_type bm;
> >> +
> >> +   if (b == 0)
> >> +   return u;
> >> +
> >> +   uu.ll = u;
> >> +   bm = 64 - b;
> >> +
> >> +   if (bm <= 0) {
> >> +   w.s.high = 0;
> >> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
> >> +   } else {
> >> +   const unsigned long long carries =
> >> +   (unsigned long long) uu.s.high << bm;
> >> +   w.s.high = (unsigned long long) uu.s.high >> b;
> >> +   w.s.low = ((unsigned long long) uu.s.low >> b) |
> >carries;
> >> +   }
> >> +
> >> +   return w.ll;
> >> +}
> >> +#ifndef BUILD_VDSO
> >> +EXPORT_SYMBOL(__lshrti3);
> >> +#endif
> >
> >I don't think you want this.  Maybe that was 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread Matthias Kaehlcke
Hi Peter,

On Fri, Mar 15, 2019 at 03:08:57PM -0700, h...@zytor.com wrote:
> On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers  
> wrote:
> >On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
> >wrote:
> >>
> >> The compiler may emit calls to __lshrti3 from the compiler runtime
> >> library, which results in undefined references:
> >>
> >> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >>   include/linux/math64.h:186: undefined reference to `__lshrti3'
> >
> >Looks like Clang will emit this at -Oz (but not -O2):
> >https://godbolt.org/z/w1_2YC
> >
> >>
> >> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> >
> >Has it changed since? If so why not a newer version of libgcc_s?
> >
> >>
> >> Include the function for x86 builds with clang, which is the
> >> environment where the above error was observed.
> >>
> >> Signed-off-by: Matthias Kaehlcke 
> >> ---
> >>  arch/x86/Kconfig   |  1 +
> >>  include/linux/libgcc.h | 16 
> >>  lib/Kconfig|  3 +++
> >>  lib/Makefile   |  1 +
> >>  lib/lshrti3.c  | 31 +++
> >>  5 files changed, 52 insertions(+)
> >>  create mode 100644 lib/lshrti3.c
> >>
> >> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
> >> index c1f9b3cf437c..a5e0d923845d 100644
> >> --- a/arch/x86/Kconfig
> >> +++ b/arch/x86/Kconfig
> >> @@ -105,6 +105,7 @@ config X86
> >> select GENERIC_IRQ_PROBE
> >> select GENERIC_IRQ_RESERVATION_MODE
> >> select GENERIC_IRQ_SHOW
> >> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
> >> select GENERIC_PENDING_IRQ  if SMP
> >> select GENERIC_SMP_IDLE_THREAD
> >> select GENERIC_STRNCPY_FROM_USER
> >> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> >> index 32e1e0f4b2d0..a71036471838 100644
> >> --- a/include/linux/libgcc.h
> >> +++ b/include/linux/libgcc.h
> >> @@ -22,15 +22,26 @@
> >>  #include 
> >>
> >>  typedef int word_type __attribute__ ((mode (__word__)));
> >> +typedef int TItype __attribute__ ((mode (TI)));
> >
> >Well that's an interesting new compiler attribute.
> >https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
> >Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
> >typedef int TItype __mode(TI);
> >
> >>
> >>  #ifdef __BIG_ENDIAN
> >>  struct DWstruct {
> >> int high, low;
> >>  };
> >> +
> >> +struct DWstruct128 {
> >> +   long long high, low;
> >> +};
> >> +
> >>  #elif defined(__LITTLE_ENDIAN)
> >>  struct DWstruct {
> >> int low, high;
> >>  };
> >> +
> >> +struct DWstruct128 {
> >> +   long long low, high;
> >> +};
> >> +
> >>  #else
> >>  #error I feel sick.
> >>  #endif
> >> @@ -40,4 +51,9 @@ typedef union {
> >> long long ll;
> >>  } DWunion;
> >>
> >> +typedef union {
> >> +   struct DWstruct128 s;
> >> +   TItype ll;
> >> +} DWunion128;
> >> +
> >>  #endif /* __ASM_LIBGCC_H */
> >> diff --git a/lib/Kconfig b/lib/Kconfig
> >> index a9e56539bd11..369e10259ea6 100644
> >> --- a/lib/Kconfig
> >> +++ b/lib/Kconfig
> >> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
> >>  config GENERIC_LIB_LSHRDI3
> >> bool
> >>
> >> +config GENERIC_LIB_LSHRTI3
> >> +   bool
> >> +
> >>  config GENERIC_LIB_MULDI3
> >> bool
> >>
> >> diff --git a/lib/Makefile b/lib/Makefile
> >> index 4e066120a0d6..42648411f451 100644
> >> --- a/lib/Makefile
> >> +++ b/lib/Makefile
> >> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
> >>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
> >> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
> >>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
> >>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
> >>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
> >> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> >> new file mode 100644
> >> index ..2d2123bb3030
> >> --- /dev/null
> >> +++ b/lib/lshrti3.c
> >> @@ -0,0 +1,31 @@
> >> +// SPDX-License-Identifier: GPL-2.0
> >> +
> >> +#include 
> >> +#include 
> >> +
> >> +long long __lshrti3(long long u, word_type b)
> >> +{
> >> +   DWunion128 uu, w;
> >> +   word_type bm;
> >> +
> >> +   if (b == 0)
> >> +   return u;
> >> +
> >> +   uu.ll = u;
> >> +   bm = 64 - b;
> >> +
> >> +   if (bm <= 0) {
> >> +   w.s.high = 0;
> >> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
> >> +   } else {
> >> +   const unsigned long long carries =
> >> +   (unsigned long long) uu.s.high << bm;
> >> +   w.s.high = (unsigned long long) uu.s.high >> b;
> >> +   w.s.low = ((unsigned long long) uu.s.low >> b) |
> >carries;
> >> +   }
> >> +
> >> +   return w.ll;
> >> +}
> >> +#ifndef BUILD_VDSO
> >> +EXPORT_SYMBOL(__lshrti3);
> >> +#endif
> >
> >I don't think you want this.  Maybe 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread Matthias Kaehlcke
On Fri, Mar 15, 2019 at 03:06:37PM -0700, 'Nick Desaulniers' via Clang Built 
Linux wrote:
> On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke  wrote:
> >
> > The compiler may emit calls to __lshrti3 from the compiler runtime
> > library, which results in undefined references:
> >
> > arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
> >   include/linux/math64.h:186: undefined reference to `__lshrti3'
> 
> Looks like Clang will emit this at -Oz (but not -O2):
> https://godbolt.org/z/w1_2YC
> 
> >
> > Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
> 
> Has it changed since? If so why not a newer version of libgcc_s?

Our compiler folks who maintain this gcc version dug this up for
me. In the gcc sources there is no direct implementation of __lshrti3,
I was told it is somehow derived from __lshrdi3.

> > Include the function for x86 builds with clang, which is the
> > environment where the above error was observed.
> >
> > Signed-off-by: Matthias Kaehlcke 
> > ---
> >  arch/x86/Kconfig   |  1 +
> >  include/linux/libgcc.h | 16 
> >  lib/Kconfig|  3 +++
> >  lib/Makefile   |  1 +
> >  lib/lshrti3.c  | 31 +++
> >  5 files changed, 52 insertions(+)
> >  create mode 100644 lib/lshrti3.c
> >
> > diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
> > index c1f9b3cf437c..a5e0d923845d 100644
> > --- a/arch/x86/Kconfig
> > +++ b/arch/x86/Kconfig
> > @@ -105,6 +105,7 @@ config X86
> > select GENERIC_IRQ_PROBE
> > select GENERIC_IRQ_RESERVATION_MODE
> > select GENERIC_IRQ_SHOW
> > +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
> > select GENERIC_PENDING_IRQ  if SMP
> > select GENERIC_SMP_IDLE_THREAD
> > select GENERIC_STRNCPY_FROM_USER
> > diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> > index 32e1e0f4b2d0..a71036471838 100644
> > --- a/include/linux/libgcc.h
> > +++ b/include/linux/libgcc.h
> > @@ -22,15 +22,26 @@
> >  #include 
> >
> >  typedef int word_type __attribute__ ((mode (__word__)));
> > +typedef int TItype __attribute__ ((mode (TI)));
> 
> Well that's an interesting new compiler attribute.
> https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
> Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
> typedef int TItype __mode(TI);

ok

> >  #ifdef __BIG_ENDIAN
> >  struct DWstruct {
> > int high, low;
> >  };
> > +
> > +struct DWstruct128 {
> > +   long long high, low;
> > +};
> > +
> >  #elif defined(__LITTLE_ENDIAN)
> >  struct DWstruct {
> > int low, high;
> >  };
> > +
> > +struct DWstruct128 {
> > +   long long low, high;
> > +};
> > +
> >  #else
> >  #error I feel sick.
> >  #endif
> > @@ -40,4 +51,9 @@ typedef union {
> > long long ll;
> >  } DWunion;
> >
> > +typedef union {
> > +   struct DWstruct128 s;
> > +   TItype ll;
> > +} DWunion128;
> > +
> >  #endif /* __ASM_LIBGCC_H */
> > diff --git a/lib/Kconfig b/lib/Kconfig
> > index a9e56539bd11..369e10259ea6 100644
> > --- a/lib/Kconfig
> > +++ b/lib/Kconfig
> > @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
> >  config GENERIC_LIB_LSHRDI3
> > bool
> >
> > +config GENERIC_LIB_LSHRTI3
> > +   bool
> > +
> >  config GENERIC_LIB_MULDI3
> > bool
> >
> > diff --git a/lib/Makefile b/lib/Makefile
> > index 4e066120a0d6..42648411f451 100644
> > --- a/lib/Makefile
> > +++ b/lib/Makefile
> > @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
> >  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
> >  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
> >  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
> > +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
> >  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
> >  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
> >  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
> > diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> > new file mode 100644
> > index ..2d2123bb3030
> > --- /dev/null
> > +++ b/lib/lshrti3.c
> > @@ -0,0 +1,31 @@
> > +// SPDX-License-Identifier: GPL-2.0
> > +
> > +#include 
> > +#include 
> > +
> > +long long __lshrti3(long long u, word_type b)

This signature matches with the gcc documentation
(https://gcc.gnu.org/onlinedocs/gccint/Integer-library-routines.html),
however the gcc implementation of the function has 128-bit values as
input/output, so I guess to meet gcc's expectations the 'long long's
need to be changed to TItype.

> > +{
> > +   DWunion128 uu, w;
> > +   word_type bm;
> > +
> > +   if (b == 0)
> > +   return u;
> > +
> > +   uu.ll = u;
> > +   bm = 64 - b;
> > +
> > +   if (bm <= 0) {
> > +   w.s.high = 0;
> > +   w.s.low = (unsigned long long) uu.s.high >> -bm;
> > +   } else {
> > +   const unsigned long long carries =
> > +   (unsigned long long) uu.s.high << bm;
> > +   w.s.high = (unsigned long 

Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread hpa
On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers  
wrote:
>On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
>wrote:
>>
>> The compiler may emit calls to __lshrti3 from the compiler runtime
>> library, which results in undefined references:
>>
>> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>
>Looks like Clang will emit this at -Oz (but not -O2):
>https://godbolt.org/z/w1_2YC
>
>>
>> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>
>Has it changed since? If so why not a newer version of libgcc_s?
>
>>
>> Include the function for x86 builds with clang, which is the
>> environment where the above error was observed.
>>
>> Signed-off-by: Matthias Kaehlcke 
>> ---
>>  arch/x86/Kconfig   |  1 +
>>  include/linux/libgcc.h | 16 
>>  lib/Kconfig|  3 +++
>>  lib/Makefile   |  1 +
>>  lib/lshrti3.c  | 31 +++
>>  5 files changed, 52 insertions(+)
>>  create mode 100644 lib/lshrti3.c
>>
>> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
>> index c1f9b3cf437c..a5e0d923845d 100644
>> --- a/arch/x86/Kconfig
>> +++ b/arch/x86/Kconfig
>> @@ -105,6 +105,7 @@ config X86
>> select GENERIC_IRQ_PROBE
>> select GENERIC_IRQ_RESERVATION_MODE
>> select GENERIC_IRQ_SHOW
>> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
>> select GENERIC_PENDING_IRQ  if SMP
>> select GENERIC_SMP_IDLE_THREAD
>> select GENERIC_STRNCPY_FROM_USER
>> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> index 32e1e0f4b2d0..a71036471838 100644
>> --- a/include/linux/libgcc.h
>> +++ b/include/linux/libgcc.h
>> @@ -22,15 +22,26 @@
>>  #include 
>>
>>  typedef int word_type __attribute__ ((mode (__word__)));
>> +typedef int TItype __attribute__ ((mode (TI)));
>
>Well that's an interesting new compiler attribute.
>https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
>Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
>typedef int TItype __mode(TI);
>
>>
>>  #ifdef __BIG_ENDIAN
>>  struct DWstruct {
>> int high, low;
>>  };
>> +
>> +struct DWstruct128 {
>> +   long long high, low;
>> +};
>> +
>>  #elif defined(__LITTLE_ENDIAN)
>>  struct DWstruct {
>> int low, high;
>>  };
>> +
>> +struct DWstruct128 {
>> +   long long low, high;
>> +};
>> +
>>  #else
>>  #error I feel sick.
>>  #endif
>> @@ -40,4 +51,9 @@ typedef union {
>> long long ll;
>>  } DWunion;
>>
>> +typedef union {
>> +   struct DWstruct128 s;
>> +   TItype ll;
>> +} DWunion128;
>> +
>>  #endif /* __ASM_LIBGCC_H */
>> diff --git a/lib/Kconfig b/lib/Kconfig
>> index a9e56539bd11..369e10259ea6 100644
>> --- a/lib/Kconfig
>> +++ b/lib/Kconfig
>> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
>>  config GENERIC_LIB_LSHRDI3
>> bool
>>
>> +config GENERIC_LIB_LSHRTI3
>> +   bool
>> +
>>  config GENERIC_LIB_MULDI3
>> bool
>>
>> diff --git a/lib/Makefile b/lib/Makefile
>> index 4e066120a0d6..42648411f451 100644
>> --- a/lib/Makefile
>> +++ b/lib/Makefile
>> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
>>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
>>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
>>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
>> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
>>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
>>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
>>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
>> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> new file mode 100644
>> index ..2d2123bb3030
>> --- /dev/null
>> +++ b/lib/lshrti3.c
>> @@ -0,0 +1,31 @@
>> +// SPDX-License-Identifier: GPL-2.0
>> +
>> +#include 
>> +#include 
>> +
>> +long long __lshrti3(long long u, word_type b)
>> +{
>> +   DWunion128 uu, w;
>> +   word_type bm;
>> +
>> +   if (b == 0)
>> +   return u;
>> +
>> +   uu.ll = u;
>> +   bm = 64 - b;
>> +
>> +   if (bm <= 0) {
>> +   w.s.high = 0;
>> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
>> +   } else {
>> +   const unsigned long long carries =
>> +   (unsigned long long) uu.s.high << bm;
>> +   w.s.high = (unsigned long long) uu.s.high >> b;
>> +   w.s.low = ((unsigned long long) uu.s.low >> b) |
>carries;
>> +   }
>> +
>> +   return w.ll;
>> +}
>> +#ifndef BUILD_VDSO
>> +EXPORT_SYMBOL(__lshrti3);
>> +#endif
>
>I don't think you want this.  Maybe that was carried over from
>https://lkml.org/lkml/2019/3/15/669
>by accident?  The above linkage error mentions arch/x86/kvm/x86.o
>which I wouldn't expect to be linked into the VDSO image?

Or just "u64"...
-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread hpa
On March 15, 2019 3:06:37 PM PDT, Nick Desaulniers  
wrote:
>On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke 
>wrote:
>>
>> The compiler may emit calls to __lshrti3 from the compiler runtime
>> library, which results in undefined references:
>>
>> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>>   include/linux/math64.h:186: undefined reference to `__lshrti3'
>
>Looks like Clang will emit this at -Oz (but not -O2):
>https://godbolt.org/z/w1_2YC
>
>>
>> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).
>
>Has it changed since? If so why not a newer version of libgcc_s?
>
>>
>> Include the function for x86 builds with clang, which is the
>> environment where the above error was observed.
>>
>> Signed-off-by: Matthias Kaehlcke 
>> ---
>>  arch/x86/Kconfig   |  1 +
>>  include/linux/libgcc.h | 16 
>>  lib/Kconfig|  3 +++
>>  lib/Makefile   |  1 +
>>  lib/lshrti3.c  | 31 +++
>>  5 files changed, 52 insertions(+)
>>  create mode 100644 lib/lshrti3.c
>>
>> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
>> index c1f9b3cf437c..a5e0d923845d 100644
>> --- a/arch/x86/Kconfig
>> +++ b/arch/x86/Kconfig
>> @@ -105,6 +105,7 @@ config X86
>> select GENERIC_IRQ_PROBE
>> select GENERIC_IRQ_RESERVATION_MODE
>> select GENERIC_IRQ_SHOW
>> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
>> select GENERIC_PENDING_IRQ  if SMP
>> select GENERIC_SMP_IDLE_THREAD
>> select GENERIC_STRNCPY_FROM_USER
>> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
>> index 32e1e0f4b2d0..a71036471838 100644
>> --- a/include/linux/libgcc.h
>> +++ b/include/linux/libgcc.h
>> @@ -22,15 +22,26 @@
>>  #include 
>>
>>  typedef int word_type __attribute__ ((mode (__word__)));
>> +typedef int TItype __attribute__ ((mode (TI)));
>
>Well that's an interesting new compiler attribute.
>https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
>Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
>typedef int TItype __mode(TI);
>
>>
>>  #ifdef __BIG_ENDIAN
>>  struct DWstruct {
>> int high, low;
>>  };
>> +
>> +struct DWstruct128 {
>> +   long long high, low;
>> +};
>> +
>>  #elif defined(__LITTLE_ENDIAN)
>>  struct DWstruct {
>> int low, high;
>>  };
>> +
>> +struct DWstruct128 {
>> +   long long low, high;
>> +};
>> +
>>  #else
>>  #error I feel sick.
>>  #endif
>> @@ -40,4 +51,9 @@ typedef union {
>> long long ll;
>>  } DWunion;
>>
>> +typedef union {
>> +   struct DWstruct128 s;
>> +   TItype ll;
>> +} DWunion128;
>> +
>>  #endif /* __ASM_LIBGCC_H */
>> diff --git a/lib/Kconfig b/lib/Kconfig
>> index a9e56539bd11..369e10259ea6 100644
>> --- a/lib/Kconfig
>> +++ b/lib/Kconfig
>> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
>>  config GENERIC_LIB_LSHRDI3
>> bool
>>
>> +config GENERIC_LIB_LSHRTI3
>> +   bool
>> +
>>  config GENERIC_LIB_MULDI3
>> bool
>>
>> diff --git a/lib/Makefile b/lib/Makefile
>> index 4e066120a0d6..42648411f451 100644
>> --- a/lib/Makefile
>> +++ b/lib/Makefile
>> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
>>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
>>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
>>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
>> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
>>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
>>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
>>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
>> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
>> new file mode 100644
>> index ..2d2123bb3030
>> --- /dev/null
>> +++ b/lib/lshrti3.c
>> @@ -0,0 +1,31 @@
>> +// SPDX-License-Identifier: GPL-2.0
>> +
>> +#include 
>> +#include 
>> +
>> +long long __lshrti3(long long u, word_type b)
>> +{
>> +   DWunion128 uu, w;
>> +   word_type bm;
>> +
>> +   if (b == 0)
>> +   return u;
>> +
>> +   uu.ll = u;
>> +   bm = 64 - b;
>> +
>> +   if (bm <= 0) {
>> +   w.s.high = 0;
>> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
>> +   } else {
>> +   const unsigned long long carries =
>> +   (unsigned long long) uu.s.high << bm;
>> +   w.s.high = (unsigned long long) uu.s.high >> b;
>> +   w.s.low = ((unsigned long long) uu.s.low >> b) |
>carries;
>> +   }
>> +
>> +   return w.ll;
>> +}
>> +#ifndef BUILD_VDSO
>> +EXPORT_SYMBOL(__lshrti3);
>> +#endif
>
>I don't think you want this.  Maybe that was carried over from
>https://lkml.org/lkml/2019/3/15/669
>by accident?  The above linkage error mentions arch/x86/kvm/x86.o
>which I wouldn't expect to be linked into the VDSO image?

If we compile with the default ABI we can simply link with libgcc; with 
-mregparm=3 all versions of gcc are broken.
-- 
Sent from my Android device with K-9 Mail. Please excuse my brevity.


Re: [PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread Nick Desaulniers
On Fri, Mar 15, 2019 at 1:54 PM Matthias Kaehlcke  wrote:
>
> The compiler may emit calls to __lshrti3 from the compiler runtime
> library, which results in undefined references:
>
> arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
>   include/linux/math64.h:186: undefined reference to `__lshrti3'

Looks like Clang will emit this at -Oz (but not -O2):
https://godbolt.org/z/w1_2YC

>
> Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).

Has it changed since? If so why not a newer version of libgcc_s?

>
> Include the function for x86 builds with clang, which is the
> environment where the above error was observed.
>
> Signed-off-by: Matthias Kaehlcke 
> ---
>  arch/x86/Kconfig   |  1 +
>  include/linux/libgcc.h | 16 
>  lib/Kconfig|  3 +++
>  lib/Makefile   |  1 +
>  lib/lshrti3.c  | 31 +++
>  5 files changed, 52 insertions(+)
>  create mode 100644 lib/lshrti3.c
>
> diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
> index c1f9b3cf437c..a5e0d923845d 100644
> --- a/arch/x86/Kconfig
> +++ b/arch/x86/Kconfig
> @@ -105,6 +105,7 @@ config X86
> select GENERIC_IRQ_PROBE
> select GENERIC_IRQ_RESERVATION_MODE
> select GENERIC_IRQ_SHOW
> +   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
> select GENERIC_PENDING_IRQ  if SMP
> select GENERIC_SMP_IDLE_THREAD
> select GENERIC_STRNCPY_FROM_USER
> diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
> index 32e1e0f4b2d0..a71036471838 100644
> --- a/include/linux/libgcc.h
> +++ b/include/linux/libgcc.h
> @@ -22,15 +22,26 @@
>  #include 
>
>  typedef int word_type __attribute__ ((mode (__word__)));
> +typedef int TItype __attribute__ ((mode (TI)));

Well that's an interesting new compiler attribute.
https://stackoverflow.com/questions/4559025/what-does-gcc-attribute-modexx-actually-do
Please use `__mode(TI)` from include/linux/compiler_attributes.h ex.
typedef int TItype __mode(TI);

>
>  #ifdef __BIG_ENDIAN
>  struct DWstruct {
> int high, low;
>  };
> +
> +struct DWstruct128 {
> +   long long high, low;
> +};
> +
>  #elif defined(__LITTLE_ENDIAN)
>  struct DWstruct {
> int low, high;
>  };
> +
> +struct DWstruct128 {
> +   long long low, high;
> +};
> +
>  #else
>  #error I feel sick.
>  #endif
> @@ -40,4 +51,9 @@ typedef union {
> long long ll;
>  } DWunion;
>
> +typedef union {
> +   struct DWstruct128 s;
> +   TItype ll;
> +} DWunion128;
> +
>  #endif /* __ASM_LIBGCC_H */
> diff --git a/lib/Kconfig b/lib/Kconfig
> index a9e56539bd11..369e10259ea6 100644
> --- a/lib/Kconfig
> +++ b/lib/Kconfig
> @@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
>  config GENERIC_LIB_LSHRDI3
> bool
>
> +config GENERIC_LIB_LSHRTI3
> +   bool
> +
>  config GENERIC_LIB_MULDI3
> bool
>
> diff --git a/lib/Makefile b/lib/Makefile
> index 4e066120a0d6..42648411f451 100644
> --- a/lib/Makefile
> +++ b/lib/Makefile
> @@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
>  obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
>  obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
>  obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
> +obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
>  obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
>  obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
>  obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
> diff --git a/lib/lshrti3.c b/lib/lshrti3.c
> new file mode 100644
> index ..2d2123bb3030
> --- /dev/null
> +++ b/lib/lshrti3.c
> @@ -0,0 +1,31 @@
> +// SPDX-License-Identifier: GPL-2.0
> +
> +#include 
> +#include 
> +
> +long long __lshrti3(long long u, word_type b)
> +{
> +   DWunion128 uu, w;
> +   word_type bm;
> +
> +   if (b == 0)
> +   return u;
> +
> +   uu.ll = u;
> +   bm = 64 - b;
> +
> +   if (bm <= 0) {
> +   w.s.high = 0;
> +   w.s.low = (unsigned long long) uu.s.high >> -bm;
> +   } else {
> +   const unsigned long long carries =
> +   (unsigned long long) uu.s.high << bm;
> +   w.s.high = (unsigned long long) uu.s.high >> b;
> +   w.s.low = ((unsigned long long) uu.s.low >> b) | carries;
> +   }
> +
> +   return w.ll;
> +}
> +#ifndef BUILD_VDSO
> +EXPORT_SYMBOL(__lshrti3);
> +#endif

I don't think you want this.  Maybe that was carried over from
https://lkml.org/lkml/2019/3/15/669
by accident?  The above linkage error mentions arch/x86/kvm/x86.o
which I wouldn't expect to be linked into the VDSO image?
-- 
Thanks,
~Nick Desaulniers


[PATCH] lib: Add shared copy of __lshrti3 from libgcc

2019-03-15 Thread Matthias Kaehlcke
The compiler may emit calls to __lshrti3 from the compiler runtime
library, which results in undefined references:

arch/x86/kvm/x86.o: In function `mul_u64_u64_shr':
  include/linux/math64.h:186: undefined reference to `__lshrti3'

Add a copy of the __lshrti3 libgcc routine (from gcc v4.9.2).

Include the function for x86 builds with clang, which is the
environment where the above error was observed.

Signed-off-by: Matthias Kaehlcke 
---
 arch/x86/Kconfig   |  1 +
 include/linux/libgcc.h | 16 
 lib/Kconfig|  3 +++
 lib/Makefile   |  1 +
 lib/lshrti3.c  | 31 +++
 5 files changed, 52 insertions(+)
 create mode 100644 lib/lshrti3.c

diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
index c1f9b3cf437c..a5e0d923845d 100644
--- a/arch/x86/Kconfig
+++ b/arch/x86/Kconfig
@@ -105,6 +105,7 @@ config X86
select GENERIC_IRQ_PROBE
select GENERIC_IRQ_RESERVATION_MODE
select GENERIC_IRQ_SHOW
+   select GENERIC_LIB_LSHRTI3  if CC_IS_CLANG
select GENERIC_PENDING_IRQ  if SMP
select GENERIC_SMP_IDLE_THREAD
select GENERIC_STRNCPY_FROM_USER
diff --git a/include/linux/libgcc.h b/include/linux/libgcc.h
index 32e1e0f4b2d0..a71036471838 100644
--- a/include/linux/libgcc.h
+++ b/include/linux/libgcc.h
@@ -22,15 +22,26 @@
 #include 

 typedef int word_type __attribute__ ((mode (__word__)));
+typedef int TItype __attribute__ ((mode (TI)));

 #ifdef __BIG_ENDIAN
 struct DWstruct {
int high, low;
 };
+
+struct DWstruct128 {
+   long long high, low;
+};
+
 #elif defined(__LITTLE_ENDIAN)
 struct DWstruct {
int low, high;
 };
+
+struct DWstruct128 {
+   long long low, high;
+};
+
 #else
 #error I feel sick.
 #endif
@@ -40,4 +51,9 @@ typedef union {
long long ll;
 } DWunion;

+typedef union {
+   struct DWstruct128 s;
+   TItype ll;
+} DWunion128;
+
 #endif /* __ASM_LIBGCC_H */
diff --git a/lib/Kconfig b/lib/Kconfig
index a9e56539bd11..369e10259ea6 100644
--- a/lib/Kconfig
+++ b/lib/Kconfig
@@ -624,6 +624,9 @@ config GENERIC_LIB_ASHRDI3
 config GENERIC_LIB_LSHRDI3
bool

+config GENERIC_LIB_LSHRTI3
+   bool
+
 config GENERIC_LIB_MULDI3
bool

diff --git a/lib/Makefile b/lib/Makefile
index 4e066120a0d6..42648411f451 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -277,6 +277,7 @@ obj-$(CONFIG_PARMAN) += parman.o
 obj-$(CONFIG_GENERIC_LIB_ASHLDI3) += ashldi3.o
 obj-$(CONFIG_GENERIC_LIB_ASHRDI3) += ashrdi3.o
 obj-$(CONFIG_GENERIC_LIB_LSHRDI3) += lshrdi3.o
+obj-$(CONFIG_GENERIC_LIB_LSHRTI3) += lshrti3.o
 obj-$(CONFIG_GENERIC_LIB_MULDI3) += muldi3.o
 obj-$(CONFIG_GENERIC_LIB_CMPDI2) += cmpdi2.o
 obj-$(CONFIG_GENERIC_LIB_UCMPDI2) += ucmpdi2.o
diff --git a/lib/lshrti3.c b/lib/lshrti3.c
new file mode 100644
index ..2d2123bb3030
--- /dev/null
+++ b/lib/lshrti3.c
@@ -0,0 +1,31 @@
+// SPDX-License-Identifier: GPL-2.0
+
+#include 
+#include 
+
+long long __lshrti3(long long u, word_type b)
+{
+   DWunion128 uu, w;
+   word_type bm;
+
+   if (b == 0)
+   return u;
+
+   uu.ll = u;
+   bm = 64 - b;
+
+   if (bm <= 0) {
+   w.s.high = 0;
+   w.s.low = (unsigned long long) uu.s.high >> -bm;
+   } else {
+   const unsigned long long carries =
+   (unsigned long long) uu.s.high << bm;
+   w.s.high = (unsigned long long) uu.s.high >> b;
+   w.s.low = ((unsigned long long) uu.s.low >> b) | carries;
+   }
+
+   return w.ll;
+}
+#ifndef BUILD_VDSO
+EXPORT_SYMBOL(__lshrti3);
+#endif
-- 
2.21.0.360.g471c308f928-goog