| Bill Allombert on Thu, 21 Nov 2002 21:10:53 +0100 |
[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]
| Re: CVS branch gmp-kernel-2-2-5 |
Hello PARI/GP developers, Here a patch to apply to the gmp-kernel-2-2-5 branch. Please do chmod a+x config/kernel-name after applying. This patch allows to use the assemby level 0 kernel code when available. With this patch, pari and pari-gmp are comparable performance on the benchmark. Please test thoroughly so that I can commit it with confidence. This patch split cleanly the kernel Makefile.SH in level 0: (MakeLVL0.SH) and level 1: (MakeLVL1.SH). level 0 are currently : ix86 alpha sparcv7 sparcv8_micro sparcv8_super hppa m68k none level 1 are currently : m68k none gmp. The way to specify the kernel to use to the --kernel= switch or interactively is as follow: -- A fully qualified kernel name (fqkn) is of the form <level 0>-<level 1>. The special <level 0> value 'auto' is accepted and stand for the auto-detected value. A name without dash '-' is an alias. Alias stands for name-none, but gmp stand for auto-gmp. The default kernel is auto-none. This patch has been tested on x86, alpha, sparcv8_micro. It is supposed to run on hppa but it is not tested. It will *not* work on m68k. This is trivial to fix but pointless, since it cannot work with the gmp kernel. Cheers, Bill.
Index: Configure
===================================================================
RCS file: /home/megrez/cvsroot/pari/Configure,v
retrieving revision 1.95.2.1
diff -u -r1.95.2.1 Configure
--- Configure 2002/11/06 09:50:46 1.95.2.1
+++ Configure 2002/11/21 17:34:34
@@ -339,24 +339,38 @@
esac
if test -n "$kernel"; then
- asmarch="$kernel";
+ tmp_kern=`./kernel-name $kernel $asmarch`
+ kernlvl0=`echo "$tmp_kern" | sed -e 's/\(.*\)-.*/\1/'`
+ kernlvl1=`echo "$tmp_kern" | sed -e 's/.*-\(.*\)/\1/'`
else
if test "$fastread" != yes; then
cat << EOM
==========================================================================
An optimized Pari kernel is available for these architectures
("none" means that we will use the portable C version of GP/PARI)
+("-gmp" means we will use the GMP library (that need to be installed))
EOM
- rep='none sparcv7 sparcv8_super sparcv8_micro m68k ix86 alpha hppa gmp'
+ rep='none sparcv7 sparcv8_super sparcv8_micro m68k ix86 alpha hppa
+ none-gmp sparcv7-gmp sparcv8_super-gmp sparcv8_micro-gmp ix86-gmp alpha-gmp hppa-gmp'
. ./display
echo $n ..."Which of these apply, if any ? $c"
- dflt=$asmarch; . ./myread; asmarch=$ans
+ dflt=$asmarch; . ./myread;
+ tmp_kern=`./kernel-name $ans $asmarch`
+ kernlvl0=`echo "$tmp_kern" | sed -e 's/\(.*\)-.*/\1/'`
+ kernlvl1=`echo "$tmp_kern" | sed -e 's/.*-\(.*\)/\1/'`
+
cat << EOM
==========================================================================
EOM
+ else
+ tmp_kern=`./kernel-name auto $asmarch`
+ kernlvl0=`echo "$tmp_kern" | sed -e 's/\(.*\)-.*/\1/'`
+ kernlvl1=`echo "$tmp_kern" | sed -e 's/.*-\(.*\)/\1/'`
fi
fi
-case "$asmarch" in
+
+
+case "$kernlvl0" in
none) prettyk="C portable";;
sparcv7) prettyk=SparcV7;;
sparcv8_super) prettyk=SuperSparc;;
@@ -366,10 +380,17 @@
hppa) prettyk=HPPA;;
alpha) prettyk=Alpha;;
ppc) prettyk=PPC;;
- *) prettyk="$asmarch";;
+ *) prettyk="$kernlvl0";;
esac
+
+case "$kernlvl1" in
+ gmp) prettyk="$prettyk/GMP";;
+ none) ;;
+ *) prettyk="$prettyk/$kernlvl1";;
+esac
+
# 'i386 (running ix86 kernel)' looks ugly
-if test "$arch" != "$asmarch" -a \( "$arch" != "i386" -o "$asmarch" != "ix86" \)
+if test "$arch" != "$kernlvl0" -a \( "$arch" != "i386" -o "$prettyk" != "ix86" \)
then
pretty="$pretty ($prettyk kernel)"
fi
@@ -698,12 +719,12 @@
if test -n "$DLLD"; then
# Which Dynamic Lib Linker?
#
- if test $DLLD = ld -a -n "$ld"; then
+ if test "$DLLD" = ld -a -n "$ld"; then
DLLD=$ld;
fi
if test "$fastread" != yes; then
echo $n ..."Which linker for building dynamic libs? $c"
- dflt=$DLLD; rep=; . ./myread
+ dflt="$DLLD"; rep=; . ./myread
DLLD=$ans
fi
@@ -820,7 +841,7 @@
#
# GMP
#
-if test "$asmarch" = "gmp"; then
+if test "$kernlvl1" = "gmp"; then
LIBS="$LIBS -lgmp"
fi
#
@@ -1391,7 +1412,8 @@
libpari_base version TOP config_dir src_dir emacs_dir doc_dir\
bindir includedir mandir miscdir libdir datadir\
optimization objdir static suffix\
- ASMINLINE arch asmarch osname pretty prefix share_prefix\
+ ASMINLINE arch asmarch osname kernlvl0 kernlvl1\
+ pretty prefix share_prefix\
__gnuc__ gnuas CPP AS ASFLAGS CC cflags DBGFLAGS OPTFLAGS LD LDFLAGS\
DLLD DLSUFFIX soname sodest KERNELCPPFLAGS DLLDFLAGS EXTRADLLDFLAGS\
runpath runpathprefix LDDYN LIBS DYNLIBS DYNFLAGS DYNRELOC\
Index: config/Makefile.SH
===================================================================
RCS file: /home/megrez/cvsroot/pari/config/Makefile.SH,v
retrieving revision 1.50
diff -u -r1.50 Makefile.SH
--- config/Makefile.SH 2002/10/22 22:07:51 1.50
+++ config/Makefile.SH 2002/11/21 17:34:34
@@ -1,10 +1,5 @@
file=$objdir/Makefile
-case "$asmarch" in
- sparcv8*) ASMARCH=sparcv8;;
- *) ASMARCH=$asmarch;;
-esac
-
echo Extracting $file
rm -f $file
@@ -43,12 +38,20 @@
dlld_ignore=- ;;
*) systems=;;
esac
+#FIXME:
+#This is a kludge to work around the fact that there is two kernels
+#in the sparcv8 directory...
+
+case "$kernlvl0" in
+ sparcv8*) dirlvl0=sparcv8;;
+ *) dirlvl0="$kernlvl0";;
+esac
-if test -s $src_dir/kernel/$ASMARCH/MakeVar.SH; then
- . $src_dir/kernel/$ASMARCH/MakeVar.SH
+if test -s $src_dir/kernel/$dirlvl0/MakeVar.SH; then
+ . $src_dir/kernel/$dirlvl0/MakeVar.SH
fi
-case "$ASMARCH" in
+case "$kernlvl0" in
m68k) hlist=pari68k
kerntest=kernel.old;; # OLD_CODES should be defined
*) hlist=pariport
@@ -381,7 +384,7 @@
@$doexec -g
cleanobj: cleantest
- -\$(RM) *\$(_O) *.s pariinl.h libpari* tune* $exec
+ -\$(RM) *\$(_O) *.s pariinl.h parilvl0.h parilvl1.h libpari* tune* $exec
clean: cleanobj
@@ -588,12 +591,33 @@
\$(INSTALL_DATA) $emx/pariemacs.txt \$(EMACSDIR)
\$(INSTALL_DATA) $emx/with-syntax.el \$(EMACSDIR)
\$(INSTALL_DATA) $emx/pari-translator.el \$(EMACSDIR)
+
EOT
fi
+
+cat >> $file << EOT
+pariinl.h: parilvl0.h parilvl1.h
+ cat parilvl0.h parilvl1.h > pariinl.h
+
+EOT
-if test -s $src_dir/kernel/$ASMARCH/Makefile.SH; then
- . $src_dir/kernel/$ASMARCH/Makefile.SH
+#FIXME:
+#This is a kludge to work around the fact that there is two kernels
+#in the sparcv8 directory...
+
+case "$kernlvl0" in
+ sparcv8*) dirlvl0=sparcv8;;
+ *) dirlvl0=$kernlvl0;;
+esac
+
+if test -s $src_dir/kernel/$dirlvl0/MakeLVL0.SH; then
+ . $src_dir/kernel/$dirlvl0/MakeLVL0.SH
fi
+
+if test -s $src_dir/kernel/$kernlvl1/MakeLVL1.SH; then
+ . $src_dir/kernel/$kernlvl1/MakeLVL1.SH
+fi
+
HUGELINE=
for dir in basemath modules language gp graph gpdyn graphdyn systems; do
eval list='$'$dir
--- /dev/null Sat Feb 23 10:50:49 2002
+++ config/kernel-name Thu Nov 21 12:42:40 2002
@@ -0,0 +1,24 @@
+#! /bin/sh
+name=$1;
+arch=$2;
+
+case "$name" in
+ *-*)
+ kernlvl0=`echo "$name" | sed -e 's/\(.*\)-.*/\1/'`
+ kernlvl1=`echo "$name" | sed -e 's/.*-\(.*\)/\1/'`
+ ;;
+ gmp) #Alias for auto-gmp
+ kernlvl0="$arch"; kernlvl1="gmp";;
+ *)
+ kernlvl0="$name"; kernlvl1="none";;
+esac
+
+if [ "$kernlvl0" = "auto" ]; then
+ kernlvl0="$arch";
+fi
+
+case "$kernlvl0" in
+ m68k) kernlvl1="m68k";;
+esac
+
+echo "$kernlvl0-$kernlvl1"
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/alpha/MakeLVL0.SH Wed Nov 20 12:12:38 2002
@@ -0,0 +1,9 @@
+kern=$src/kernel/$kernlvl0
+
+cat >> $file << EOT
+parilvl0.h: $kern/asm0.h $kern/asm1.h
+ cat $kern/asm0.h $kern/asm1.h > parilvl0.h
+kernel\$(_O): $kern/level0.s
+ \$(AS) \$(ASFLAGS) -o kernel\$(_O) $kern/level0.s
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/hppa/MakeLVL0.SH Thu Nov 21 16:39:37 2002
@@ -0,0 +1,12 @@
+# Level 0 kernel is "asm extern"
+# Level 1 kernel is the C generic one
+
+$kern=$src/kernel/$asmarch
+
+cat >> $file << EOT
+parilvl0.h: $src/kernel/none/asm0.h
+ cat $src/kernel/none/asm0.h > parilvl0.h
+kernel\$(_O): $kern/level0.s
+ \$(AS) \$(ASFLAGS) -o kernel\$(_O) $kern/level0.s
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/ix86/MakeLVL0.SH Wed Nov 20 12:19:44 2002
@@ -0,0 +1,13 @@
+# Level 0 kernel is "asm inline" if gcc and "asm extern" if not
+
+level0=$src/kernel/$kernlvl0
+
+cat >> $file << EOT
+parilvl0.h: $level0/level0.h
+ cat $level0/level0.h > parilvl0.h
+level0.s: $level0/l0asm.c $level0/l0asm.h
+ \$(CPP) $level0/l0asm.c | sed -e '/^#/d' -e '/^ *#line/d' -e 's/% */%/g' > level0.s
+kernel\$(_O): level0.s
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o kernel\$(_O) level0.s
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/m68k/MakeLVL0.SH Thu Nov 21 18:11:06 2002
@@ -0,0 +1,21 @@
+# Level 0 kernel is the C generic one.
+
+# Level 1 kernel is in assembly (mp.s), except the new functions that
+# were only written in C (karatsuba and others).
+# The assembly file is compiled in mpasm.o
+
+kernel="$kernel mpasm"
+
+cat >> $file << EOT
+pariinl.h: $src/kernel/none/level0.h $src/kernel/none/level1.h
+ cat $src/kernel/none/level0.h $src/kernel/none/level1.h > \$@
+kernel.o: .headers $src/kernel/none/level0.h
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o kernel.o $src/kernel/none/level0.c
+mpasm.o: $src/kernel/m68k/mp.s
+ \$(AS) \$(ASFLAGS) -o mpasm.o $src/kernel/m68k/mp.s
+mp.o: .headers $src/kernel/none/mp.c
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mp.o $src/kernel/none/mp.c
+mpinl.o: .headers $src/kernel/none/level1.h
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mpinl.o $src/kernel/none/level1.c
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/none/MakeLVL1.SH Wed Nov 20 12:09:41 2002
@@ -0,0 +1,13 @@
+# Functions that can be inlined are externally defined too
+# This is done with level0.c and level1.c
+
+kern=$src/kernel/$kernlvl1
+
+cat >> $file << EOT
+parilvl1.h: $kern/level1.h
+ cat $kern/level1.h > parilvl1.h
+mp\$(_O): .headers $kern/mp.c
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mp\$(_O) $kern/mp.c
+mpinl\$(_O): .headers $kern/level1.h
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mpinl\$(_O) $kern/level1.c
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/none/MakeLVL0.SH Wed Nov 20 12:11:15 2002
@@ -0,0 +1,11 @@
+# Functions that can be inlined are externally defined too
+# This is done with level0.c and level1.c
+
+kern=$src/kernel/$kernlvl0
+
+cat >> $file << EOT
+parilvl0.h: $kern/level0.h
+ cat $kern/level0.h > parilvl0.h
+kernel\$(_O): .headers $kern/level0.h
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o kernel\$(_O) $kern/level0.c
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/sparcv7/MakeLVL0.SH Wed Nov 20 11:09:27 2002
@@ -0,0 +1,20 @@
+# Level 0 kernel is "asm extern"
+# Level 1 kernel is the C generic one
+level0=$src/kernel/none/asm0.h
+kernel1=$src/kernel/$asmarch/level0.S
+if test "$osname" = "nextstep" -o "$osname" = "linux" -o "$gnuas" = "yes";
+then
+cat >> $file << EOT
+kernel1.s: $kernel1
+ \$(CPP) $KERNELCPPFLAGS $kernel1 > \$@
+EOT
+kernel1=kernel1.s
+fi
+
+cat >> $file << EOT
+parilvl0.h: $level0
+ cat \$^ > \$@
+kernel.o: $kernel1
+ \$(AS) \$(ASFLAGS) -o \$@ $kernel1
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/sparcv8/MakeLVL0.SH Thu Nov 21 12:30:15 2002
@@ -0,0 +1,43 @@
+# For SunOS
+# If __GNUC__, most level0 functions are "asm inline"
+# If not, they are "asm extern"
+# The object kernel.o (resp. kernel2.o) contains entries for the functions
+# that can (resp. cannot) be inline.
+# Problem: "divll" uses "overflow", so kernel2.o is not the same when
+# compiled with gcc or with cc. We should try to find a workaround.
+# For NextStep or Linux
+# We don't accept "asm inline" since it does not work (Ptitboul)
+if test "$gnuas" = "yes"; then do_cpp=yes; fi
+
+ker=$src/kernel/sparcv8
+kernel1=$ker/level0_$asmarch.S
+kernel2=$ker/level0.S
+
+if test "$osname" = "nextstep" -o "$osname" = "linux"
+then
+ level0=$src/kernel/none/asm0.h
+else
+ level0=$ker/level0.h
+fi
+
+if test "$osname" = "nextstep" -o "$osname" = "linux" -o "$do_cpp" = "yes"
+then
+cat >> $file << EOT
+kernel1.s: $kernel1
+ \$(CPP) $KERNELCPPFLAGS $kernel1 > \$@
+kernel2.s: $kernel2
+ \$(CPP) $KERNELCPPFLAGS $kernel2 > \$@
+EOT
+kernel1=kernel1.s
+kernel2=kernel2.s
+fi
+
+cat >> $file << EOT
+parilvl0.h: $level0
+ cat $level0 > parilvl0.h
+kernel\$(_O): $kernel1
+ \$(AS) \$(ASFLAGS) -o \$@ $kernel1
+kernel2\$(_O): $kernel2
+ \$(AS) \$(ASFLAGS) -o \$@ $kernel2
+
+EOT
--- /dev/null Sat Feb 23 10:50:49 2002
+++ src/kernel/gmp/MakeLVL1.SH Wed Nov 20 12:09:27 2002
@@ -0,0 +1,13 @@
+# Functions that can be inlined are externally defined too
+# This is done with level0.c and level1.c
+
+kern=$src/kernel/$kernlvl1
+
+cat >> $file << EOT
+parilvl1.h: $kern/level1.h
+ cat $kern/level1.h > parilvl1.h
+mp\$(_O): .headers $kern/mp.c
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mp\$(_O) $kern/mp.c
+mpinl\$(_O): .headers $kern/level1.h
+ \$(CC) -c \$(CFLAGS) \$(CPPFLAGS) -o mpinl\$(_O) $kern/level1.c
+EOT