This is an automated email from the git hooks/post-receive script.

ppm-guest pushed a commit to annotated tag v0.06
in repository libmath-prime-util-perl.

commit eafd373d048098ca699a07972d99414d09611566
Author: Dana Jacobsen <d...@acm.org>
Date:   Fri Jun 8 16:13:44 2012 -0600

    Make asm x64 only
---
 MANIFEST |   1 +
 TODO     |   2 ++
 factor.c | 102 +++++++++++++++++++++++++++++++++------------------------------
 3 files changed, 56 insertions(+), 49 deletions(-)

diff --git a/MANIFEST b/MANIFEST
index 80c5c05..40dfd94 100644
--- a/MANIFEST
+++ b/MANIFEST
@@ -32,6 +32,7 @@ t/13-primecount.t
 t/14-nthprime.t
 t/15-probprime.t
 t/16-randomprime.t
+t/17-pseudoprime.t
 t/30-relations.t
 t/50-factoring.t
 t/90-release-perlcritic.t
diff --git a/TODO b/TODO
index a559ec0..8644218 100644
--- a/TODO
+++ b/TODO
@@ -22,3 +22,5 @@
 - speed up random_prime for large numbers
 
 - Add other bases to pseudoprime test
+
+- test x64 asm if Perl is built for 32-bit
diff --git a/factor.c b/factor.c
index 1b06519..d5be28a 100644
--- a/factor.c
+++ b/factor.c
@@ -85,66 +85,71 @@ int trial_factor(UV n, UV *factors, UV maxtrial)
   #define mulmod(a,b,m)  (UV)(((uint64_t)(a)*(uint64_t)(b)) % ((uint64_t)(m)))
   #define sqrmod(n,m)    (UV)(((uint64_t)(n)*(uint64_t)(n)) % ((uint64_t)(m)))
 
-  static UV powmod(UV n, UV power, UV m) {
-    UV t = 1;
-    while (power) {
-      if (power & 1)
-        t = mulmod(t, n, m);
-      n = sqrmod(n, m);
-      power >>= 1;
-    }
-    return t;
+#elif defined(__GNUC__) && defined(__x86_64__)
+
+  /* GCC on a 64-bit Intel x86 */
+  static UV _mulmod(UV a, UV b, UV c) {
+    UV d; /* to hold the result of a*b mod c */
+    /* calculates a*b mod c, stores result in d */
+    asm ("mov %1, %%rax;"        /* put a into rax */
+         "mul %2;"               /* mul a*b -> rdx:rax */
+         "div %3;"               /* (a*b)/c -> quot in rax remainder in rdx */
+         "mov %%rdx, %0;"        /* store result in d */
+         :"=r"(d)                /* output */
+         :"r"(a), "r"(b), "r"(c) /* input */
+         :"%rax", "%rdx"         /* clobbered registers */
+        );
+    return d;
   }
+  #define mulmod(a,b,m) _mulmod(a,b,m)
+  #define sqrmod(n,m)   _mulmod(n,n,m)
 
 #else
 
   /* UV is the largest integral type available (that we know of). */
 
-  /* if n is smaller than this, you can multiply without overflow */
-  #define HALF_WORD (UVCONST(1) << (BITS_PER_WORD/2))
-
-  #if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
-    /* Inline assembly -- basically as fast as a regular (a*b)%m */
-    static UV _mulmod(UV a, UV b, UV c) {
-      UV d; /* to hold the result of a*b mod c */
-      /* calculates a*b mod c, stores result in d */
-      asm ("mov %1, %%rax;"        /* put a into rax */
-           "mul %2;"               /* mul a*b -> rdx:rax */
-           "div %3;"               /* (a*b)/c -> quot in rax remainder in rdx 
*/
-           "mov %%rdx, %0;"        /* store result in d */
-           :"=r"(d)                /* output */
-           :"r"(a), "r"(b), "r"(c) /* input */
-           :"%rax", "%rdx"         /* clobbered registers */
-          );
-      return d;
-    }
-    #define mulmod(a,b,m) _mulmod(a,b,m)
-    #define sqrmod(n,m)   _mulmod(n,n,m)
-  #else
-    /* Do it by hand */
-    static UV _mulmod(UV a, UV b, UV m) {
-      UV r = 0;
-      while (b > 0) {
-        if (b & 1) {
-          if (r == 0) {
-            r = a;
-          } else {
-            r = m - r;
-            r = (a >= r)  ?  a-r  :  m-r+a;
-          }
+  /* Do it by hand */
+  static UV _mulmod(UV a, UV b, UV m) {
+    UV r = 0;
+    while (b > 0) {
+      if (b & 1) {
+        if (r == 0) {
+          r = a;
+        } else {
+          r = m - r;
+          r = (a >= r)  ?  a-r  :  m-r+a;
         }
-        a = (a > (m-a))  ?  (a-m)+a  :  a+a;
-        b >>= 1;
       }
-      return r;
+      a = (a > (m-a))  ?  (a-m)+a  :  a+a;
+      b >>= 1;
     }
-    #define mulmod(a,b,m) (((a)|(b)) < HALF_WORD) ? 
((a)*(b))%(m):_mulmod(a,b,m)
-    #define sqrmod(n,m)   ((n) < HALF_WORD)       ? 
((n)*(n))%(m):_mulmod(n,n,m)
-  #endif
+    return r;
+  }
+
+  /* if n is smaller than this, you can multiply without overflow */
+  #define HALF_WORD (UVCONST(1) << (BITS_PER_WORD/2))
+  #define mulmod(a,b,m) (((a)|(b)) < HALF_WORD) ? ((a)*(b))%(m):_mulmod(a,b,m)
+  #define sqrmod(n,m)   ((n) < HALF_WORD)       ? ((n)*(n))%(m):_mulmod(n,n,m)
+
+#endif
 
+#ifndef addmod
   #define addmod(n,a,m) ((((m)-(n)) > (a))  ?  ((n)+(a))  :  ((n)+(a)-(m)))
+#endif
 
-  /* n^power mod m */
+/* n^power mod m */
+#ifndef HALF_WORD
+  static UV powmod(UV n, UV power, UV m) {
+    UV t = 1;
+    while (power) {
+      if (power & 1)
+        t = mulmod(t, n, m);
+      n = sqrmod(n, m);
+      power >>= 1;
+    }
+    return t;
+  }
+#else
   static UV powmod(UV n, UV power, UV m) {
     UV t = 1;
     if (m < HALF_WORD) {
@@ -165,7 +170,6 @@ int trial_factor(UV n, UV *factors, UV maxtrial)
     }
     return t;
   }
-
 #endif
 
 /* n^power + a mod m */

-- 
Alioth's /usr/local/bin/git-commit-notice on 
/srv/git.debian.org/git/pkg-perl/packages/libmath-prime-util-perl.git

_______________________________________________
Pkg-perl-cvs-commits mailing list
Pkg-perl-cvs-commits@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/pkg-perl-cvs-commits

Reply via email to