Re: Adding support for R6 of MIPS architecture
> I think mpn/alpha/addmul_1.asm might serve as a better starting point > than the mips64 lo/hi code. That code is simple enough, yet OK for > pipelined in-order and out-of-order cores. I will take a look at that. On second thought, the top-level alpha code is overscheduled, at least for the devices it would be used for. The instructions should be directly 1:1 translatable to MIPS code, though. The best loop strategy is usually to put the the multiplier operand load at the top of the loop, and then schedule the low multiply at a distance which corresponds to L1d latency. The high multiply can then be scheduled for multiplier hardware throughput. Then do accumulation scheduled after multiplier latency. For implementations with pipelined multiply, performance might become limited by the recurrent carry latency. To handle that problem, add incoming carry as late as possible, and then compute outgoing carry with as few instructions as possible, I just use user-level QEMU. I see. By default I would assume it to reject r6 instruction execution. -- Torbjörn Please encrypt, key id 0xC8601622 ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
On Wed, 2015-02-11 at 13:51 +0100, Torbjörn Granlund wrote: > I think mpn/alpha/addmul_1.asm might serve as a better starting point > than the mips64 lo/hi code. That code is simple enough, yet OK for > pipelined in-order and out-of-order cores. I will take a look at that. > The top-of-tree Qemu is pretty good these days, I use it for GCC > testing, including R6 testing. > > Have you been able to boot some kernel under QEMU in r6 mode? Or are > you using user-level QEMU, passing options to QEMU with some trickery? I just use user-level QEMU. Steve Ellcey sell...@imgtec.com ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
Steve Ellcey writes: > I think the old assembly code should be tweaked for r6 in a slightly > deeper way. Two extra move instructions in a critical loop isn't OK. > The mips code you started with is seriously out-of-date, with > over-scheduling of load; this ought to be fixed too. My thought was to get a working version checked in and then make improvements after that. While paperwork is handled, one may as well write a good version. (And if assign-future is not chosen, you need to finish the code before signing.) I think mpn/alpha/addmul_1.asm might serve as a better starting point than the mips64 lo/hi code. That code is simple enough, yet OK for pipelined in-order and out-of-order cores. The top-of-tree Qemu is pretty good these days, I use it for GCC testing, including R6 testing. Have you been able to boot some kernel under QEMU in r6 mode? Or are you using user-level QEMU, passing options to QEMU with some trickery? Torbjörn Please encrypt, key id 0xC8601622 ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
On Fri, 2015-02-06 at 09:13 +0100, Torbjörn Granlund wrote: > I think the old assembly code should be tweaked for r6 in a slightly > deeper way. Two extra move instructions in a critical loop isn't OK. > The mips code you started with is seriously out-of-date, with > over-scheduling of load; this ought to be fixed too. My thought was to get a working version checked in and then make improvements after that. > In the r6 parts which exists and are planned, are mulu and muhu > pipelined? If they are pipelined, how close can a 2nd multiply be > scheduled without issue stalling? What are their latency? mulu and muhu will be pipelined (at least for high and medium end cores), I am not entirely sure about low end cores. > Is there a way to do 'make check' with a simulator or a remote system? > > If you are patient enough, perhaps you could find a QEMU release which > works well enough for testing this? I recall having seen some mention > of mipsr6 around QEMU, so presumably the QEMU folks made some attempt at > supporting this. The top-of-tree Qemu is pretty good these days, I use it for GCC testing, including R6 testing. > Finding a linux config which works with a QEMU version and config can be > quite irksome. Often, you will need to patch QEMU's handling of one or > two instructions. > > QEMU's mips64 emulator have been particularly buggy in the past years, > with perhaps a dozen releases which were useless. > > I usually build MIPS code using a cross compiler on an x86 Linux box and > that is what I did to build GMP (using --build=x86_64-unknown-linux-gnu > --host=mips-img-linux-gnu or some other host depending on what flavor of > MIPS I wanted to build). I was hoping I could run 'make check' on the > x86 box and have it run tests via a simulator. That makes it easier to > build and test multiple MIPS architectures. > > GMP provides a TEST_ENVIRONMENT environment variable which could be used > for remote executiion. OK, I will look into TEST_ENVIRONMENT. > > I tweaked the GMP configure script to recognize mips*-mti-* and > mips*-img-* targets, these hosts/targets exist in GCC and binutils as > names to use for cross compilers targeting MIPS (mti for pre-r6, img for > r6). > > Then GCC apparently abuses the GNU configure system. GMP follows the > GNU convention cpu-system[-kernel]-os. For r6 CPUs, use either > cpu=mips64r6 or [when pipeline-specific optimised assembly is provided] > cpu=mipsfoo where foo describes the specific CPU. > > We need FSF paperwork to handle your patch. Are you willing to sign > your work to the FSF? If you are employed to do programming, we need > assignment or disclaimer from your employer too. I'll have to work on this. The company I work for (Imagination Technologies, which purchased MIPS) has an FSF copyright assignment on file but it does not include GMP in the list of projects. Steve Ellcey sell...@imgtec.com ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
Steve Ellcey writes: OK, so what I did was to create a mips32r6 directory under mips32 and a mips64r6 directory under mips64 and put copies of the routines that had to be changed for r6 in those directories. I have done test builds for various MIPS targets and verified that the non-r6 code has not changed. For the new r6 stuff I have verified that it all builds but I haven't tested the changes with 'make check'. Nice contribution! I think the old assembly code should be tweaked for r6 in a slightly deeper way. Two extra move instructions in a critical loop isn't OK. The mips code you started with is seriously out-of-date, with over-scheduling of load; this ought to be fixed too. In the r6 parts which exists and are planned, are mulu and muhu pipelined? If they are pipelined, how close can a 2nd multiply be scheduled without issue stalling? What are their latency? Is there a way to do 'make check' with a simulator or a remote system? If you are patient enough, perhaps you could find a QEMU release which works well enough for testing this? I recall having seen some mention of mipsr6 around QEMU, so presumably the QEMU folks made some attempt at supporting this. Finding a linux config which works with a QEMU version and config can be quite irksome. Often, you will need to patch QEMU's handling of one or two instructions. QEMU's mips64 emulator have been particularly buggy in the past years, with perhaps a dozen releases which were useless. I usually build MIPS code using a cross compiler on an x86 Linux box and that is what I did to build GMP (using --build=x86_64-unknown-linux-gnu --host=mips-img-linux-gnu or some other host depending on what flavor of MIPS I wanted to build). I was hoping I could run 'make check' on the x86 box and have it run tests via a simulator. That makes it easier to build and test multiple MIPS architectures. GMP provides a TEST_ENVIRONMENT environment variable which could be used for remote executiion. I tweaked the GMP configure script to recognize mips*-mti-* and mips*-img-* targets, these hosts/targets exist in GCC and binutils as names to use for cross compilers targeting MIPS (mti for pre-r6, img for r6). Then GCC apparently abuses the GNU configure system. GMP follows the GNU convention cpu-system[-kernel]-os. For r6 CPUs, use either cpu=mips64r6 or [when pipeline-specific optimised assembly is provided] cpu=mipsfoo where foo describes the specific CPU. We need FSF paperwork to handle your patch. Are you willing to sign your work to the FSF? If you are employed to do programming, we need assignment or disclaimer from your employer too. Torbjörn Please encrypt, key id 0xC8601622 ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
On Tue, 2015-02-03 at 10:57 +0100, Torbjörn Granlund wrote: > Marc Glisse writes: > > Apparently not, the motivation for the patch is that multu has > disappeared... > > Then I see no other robust approach than making mpn/mipsnomultu_64 (or > somesuch). > > Well, an analogous robust approach would be moving the dmultu code into > mpn/mips64/dmultu and put the r6 code into mpn/mips64/nodmultu. > > (As a side note, I have been planning to move things around a bit, > creating mpn/x86/32 and mpn/x86/64 with the contents of mpn/x86 and > mpn/x86_64, respectively. SImilarly for powerpc32 and powerpc64, > sparc32 and sparc64, etc. Common code between 32-bit and 64-bit limbs > will live in the shared directory (mpn/x86, mpn/powerpc, mpn/sparc, > etc). There is a good amount of such common code already, which is > shared in an ugly manner.) OK, so what I did was to create a mips32r6 directory under mips32 and a mips64r6 directory under mips64 and put copies of the routines that had to be changed for r6 in those directories. I have done test builds for various MIPS targets and verified that the non-r6 code has not changed. For the new r6 stuff I have verified that it all builds but I haven't tested the changes with 'make check'. Is there a way to do 'make check' with a simulator or a remote system? I usually build MIPS code using a cross compiler on an x86 Linux box and that is what I did to build GMP (using --build=x86_64-unknown-linux-gnu --host=mips-img-linux-gnu or some other host depending on what flavor of MIPS I wanted to build). I was hoping I could run 'make check' on the x86 box and have it run tests via a simulator. That makes it easier to build and test multiple MIPS architectures. I tweaked the GMP configure script to recognize mips*-mti-* and mips*-img-* targets, these hosts/targets exist in GCC and binutils as names to use for cross compilers targeting MIPS (mti for pre-r6, img for r6). I have attached the patch as it currently exists to this email so people could look it over. Steve Ellcey sell...@imgtec.com diff -r 2ff56d3c5dfe configure.ac --- a/configure.ac Wed Aug 27 11:24:26 2014 +0200 +++ b/configure.ac Thu Feb 05 14:27:13 2015 -0800 @@ -907,27 +907,41 @@ gcc_cflags_optlist="abi" gcc_cflags_abi="-mabi=32" gcc_testlist="gcc-mips-o32" -path="mips32" +case $host in + mips32r6 | mips*-img-*) + path="mips32/mips32r6 mips32" ;; + *) + path="mips32" ;; +esac cc_cflags="-O2 -o32" # no -g, it disables all optimizations # this suits both mips32 and mips64 GMP_INCLUDE_MPN(mips32/mips-defs.m4) case $host in - [mips64*-*-* | mips*-*-irix[6789]*]) + [mips64*-*-* | mips*-mti-* | mips*-img-* | mips*-*-irix[6789]*]) abilist="n32 64 o32" cclist_n32="gcc cc" gcc_n32_cflags="$gcc_cflags -mabi=n32" cc_n32_cflags="-O2 -n32" # no -g, it disables all optimizations limb_n32=longlong -path_n32="mips64" cclist_64="gcc cc" gcc_64_cflags="$gcc_cflags -mabi=64" gcc_64_ldflags="-Wc,-mabi=64" cc_64_cflags="-O2 -64" # no -g, it disables all optimizations cc_64_ldflags="-Wc,-64" -path_64="mips64" + + case $host in + mips64r6 | mips*-img-*) + path_n32="mips64/mips64r6 mips64" + path_64="mips64/mips64r6 mips64" + ;; + *) + path_n32="mips64" + path_64="mips64" + ;; + esac ;; esac ;; diff -r 2ff56d3c5dfe mpn/mips32/mips32r6/addmul_1.asm --- /dev/null Thu Jan 01 00:00:00 1970 + +++ b/mpn/mips32/mips32r6/addmul_1.asm Thu Feb 05 14:27:13 2015 -0800 @@ -0,0 +1,104 @@ +dnl MIPS32 mpn_addmul_1 -- Multiply a limb vector with a single limb and add +dnl the product to a second limb vector. + +dnl Copyright 1992, 1994, 1996, 2000, 2002 Free Software Foundation, Inc. + +dnl This file is part of the GNU MP Library. +dnl +dnl The GNU MP Library is free software; you can redistribute it and/or modify +dnl it under the terms of either: +dnl +dnl* the GNU Lesser General Public License as published by the Free +dnl Software Foundation; either version 3 of the License, or (at your +dnl option) any later version. +dnl +dnl or +dnl +dnl* the GNU General Public License as published by the Free Software +dnl Foundation; either version 2 of the License, or (at your option) any +dnl later version. +dnl +dnl or both in parallel, as here. +dnl +dnl The GNU MP Library is distributed in the hope that it will be useful, but +dnl WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY +dnl or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +dnl for more details. +dnl +dnl You should have received copies of the GNU General Public License and the +dnl GNU Lesser General Public License along with the GNU MP Library. If not, +dnl see https://www.gnu.org/licenses/. + +include(`../config.m4') + +C INPUT PARAMETERS +C res_ptr $4 +C s1
Re: Adding support for R6 of MIPS architecture
Marc Glisse writes: Apparently not, the motivation for the patch is that multu has disappeared... Then I see no other robust approach than making mpn/mipsnomultu_64 (or somesuch). Well, an analogous robust approach would be moving the dmultu code into mpn/mips64/dmultu and put the r6 code into mpn/mips64/nodmultu. (As a side note, I have been planning to move things around a bit, creating mpn/x86/32 and mpn/x86/64 with the contents of mpn/x86 and mpn/x86_64, respectively. SImilarly for powerpc32 and powerpc64, sparc32 and sparc64, etc. Common code between 32-bit and 64-bit limbs will live in the shared directory (mpn/x86, mpn/powerpc, mpn/sparc, etc). There is a good amount of such common code already, which is shared in an ugly manner.) -- Torbjörn Please encrypt, key id 0xC8601622 ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
On Mon, 2 Feb 2015, Torbjörn Granlund wrote: Does MIPS64r6 contain all older architecture revisions as a subset, Apparently not, the motivation for the patch is that multu has disappeared... -- Marc Glisse ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Re: Adding support for R6 of MIPS architecture
"Steve Ellcey " writes: #if __mips_isa_rev < 6 multu $8,$7 #else mulu$11,$8,$7 muhu$12,$8,$7 #endif are not working. I guess I things more like: ifdef(`ISA_REV6',` mulu$11,$8,$7 muhu$12,$8,$7 ',` multu $8,$7 ') But I am not sure how or where I would set ISA_REV6. Should this be handled in the configure script or in a *.m4 file under mpn/mips32 or mpn/mips64? Is there an example of a compiler macro being checked and used to set a asm ifdef somewhere that I could copy from? Usually, we provide specific asm files for each cpu (e.g., R1) or at least every sub-architecture (e.g., MIPS64r3 vs MIPS64r6). Since none of the GMP developers stumbled over a MIPS system in the last 15 years, the MIPS situation is a bit different; here we have just 32-bit and 64-bit code. I believe these new multiply instructions are different enough to make them hard to stick into existing code, using just a simple conditional. Surely, they don't write anything to the HI and LO registers? Does MIPS64r6 contain all older architecture revisions as a subset, i.e., are they 100% backwards compatible (for user level code0? In that case, the right approach would be to create a subdirectory mpn/mips64/r6 and put any r6 specific code there. Thenn make config.guess recognise mipsr6 CPUs and add the proper paths to configure.ac. You are welcome to work on that. Presumably none of the GMP team members have any system on which to test R6 code, we will not be able to assist much with such a project. We'll cheer you on, though. :-) Assuming 1005 backwards compatibility, it is important that any new code improves performance for new devices; else the old code wil be preferable. -- Torbjörn Please encrypt, key id 0xC8601622 ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel
Adding support for R6 of MIPS architecture
I am new to the gmp-devel list but have been downloading GMP and using it as part of my GCC toolchain builds that also include GLIBC. Recently I updated some of the GMP files that glibc uses in order to support new revisions of the MIPS architecture (mips32r6 and mips64r6) and I would like to get those changes into the official GMP as well. I went ahead and downloaded the GMP 6.0.0 sources from hg (I tried the unstable branch but it had no configure file and running autoconf on configure.ac gave me a bunch of errors) and made the same changes there as I had done in glibc. Then I tried building GMP and it failed because the assembly language files are preproccessed by m4 and not by GCC and so my code with things like: #if __mips_isa_rev < 6 multu $8,$7 #else mulu$11,$8,$7 muhu$12,$8,$7 #endif are not working. I guess I things more like: ifdef(`ISA_REV6',` mulu$11,$8,$7 muhu$12,$8,$7 ',` multu $8,$7 ') But I am not sure how or where I would set ISA_REV6. Should this be handled in the configure script or in a *.m4 file under mpn/mips32 or mpn/mips64? Is there an example of a compiler macro being checked and used to set a asm ifdef somewhere that I could copy from? The files that I need to change for MIPS R6 are addmul_1.asm, mul_1.asm, and submul_1.asm in both the mpn/mips32 and mpn/mips64 directories. There is also a file mpn/mips64/sqr_diagonal.asm that needs changes but it doesn't look like this file is currently compiled as part of GMP. Steve Ellcey sell...@imgtec.com ___ gmp-devel mailing list gmp-devel@gmplib.org https://gmplib.org/mailman/listinfo/gmp-devel