5776625 [rkeene@sledge /home/rkeene/archive/floydssh/ssh]$ cat -n MPN.java
  1 /* gnu.java.math.MPN
  2    Copyright (C) 1999, 2000, 2001 Free Software Foundation, Inc.
  3    The file was changed by Radek Polak to work as midlet in MIDP 1.0
  4 
  5 This file is part of GNU Classpath.
  6 
  7 GNU Classpath is free software; you can redistribute it and/or modify
  8 it under the terms of the GNU General Public License as published by
  9 the Free Software Foundation; either version 2, or (at your option)
 10 any later version.
 11 
 12 GNU Classpath is distributed in the hope that it will be useful, but
 13 WITHOUT ANY WARRANTY; without even the implied warranty of
 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 15 General Public License for more details.
 16 
 17 You should have received a copy of the GNU General Public License
 18 along with GNU Classpath; see the file COPYING.  If not, write to the
 19 Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
 20 02111-1307 USA.
 21 
 22 Linking this library statically or dynamically with other modules is
 23 making a combined work based on this library.  Thus, the terms and
 24 conditions of the GNU General Public License cover the whole
 25 combination.
 26 
 27 As a special exception, the copyright holders of this library give you
 28 permission to link this library with independent modules to produce an
 29 executable, regardless of the license terms of these independent
 30 modules, and to copy and distribute the resulting executable under
 31 terms of your choice, provided that you also meet, for each linked
 32 independent module, the terms and conditions of the license of that
 33 module.  An independent module is a module which is not derived from
 34 or based on this library.  If you modify this library, you may extend
 35 this exception to your version of the library, but you are not
 36 obligated to do so.  If you do not wish to do so, delete this
 37 exception statement from your version. */
 38 
 39 // Included from Kawa 1.6.62 with permission of the author,
 40 // Per Bothner <per@bothner.com>.
 41 
 42 package ssh;
 43 
 44 /** This contains various low-level routines for unsigned bigints.
 45  * The interfaces match the mpn interfaces in gmp,
 46  * so it should be easy to replace them with fast native functions
 47  * that are trivial wrappers around the mpn_ functions in gmp
 48  * (at least on platforms that use 32-bit "limbs").
 49  */
 50 
 51 public class MPN
 52 {
 53   /** Add x[0:size-1] and y, and write the size least
 54    * significant words of the result to dest.
 55    * Return carry, either 0 or 1.
 56    * All values are unsigned.
 57    * This is basically the same as gmp's mpn_add_1. */
 58   public static int add_1 (int[] dest, int[] x, int size, int y)
 59   {
 60     long carry = (long) y & 0xffffffffL;
 61     for (int i = 0;  i < size;  i++)
 62       {
 63     carry += ((long) x[i] & 0xffffffffL);
 64     dest[i] = (int) carry;
 65     carry >>= 32;
 66       }
 67     return (int) carry;
 68   }
 69 
 70   /** Add x[0:len-1] and y[0:len-1] and write the len least
 71    * significant words of the result to dest[0:len-1].
 72    * All words are treated as unsigned.
 73    * @return the carry, either 0 or 1
 74    * This function is basically the same as gmp's mpn_add_n.
 75    */
 76   public static int add_n (int dest[], int[] x, int[] y, int len)
 77   {
 78     long carry = 0;
 79     for (int i = 0; i < len;  i++)
 80       {
 81     carry += ((long) x[i] & 0xffffffffL)
 82       + ((long) y[i] & 0xffffffffL);
 83     dest[i] = (int) carry;
 84     carry >>>= 32;
 85       }
 86     return (int) carry;
 87   }
 88 
 89   /** Subtract Y[0:size-1] from X[0:size-1], and write
 90    * the size least significant words of the result to dest[0:size-1].
 91    * Return borrow, either 0 or 1.
 92    * This is basically the same as gmp's mpn_sub_n function.
 93    */
 94 
 95   public static int sub_n (int[] dest, int[] X, int[] Y, int size)
 96   {
 97     int cy = 0;
 98     for (int i = 0;  i < size;  i++)
 99       {
100     int y = Y[i];
101     int x = X[i];
102     y += cy;    /* add previous carry to subtrahend */
103     // Invert the high-order bit, because: (unsigned) X > (unsigned) Y
104     // iff: (int) (X^0x80000000) > (int) (Y^0x80000000).
105     cy = (y^0x80000000) < (cy^0x80000000) ? 1 : 0;
106     y = x - y;
107     cy += (y^0x80000000) > (x ^ 0x80000000) ? 1 : 0;
108     dest[i] = y;
109       }
110     return cy;
111   }
112 
113   /** Multiply x[0:len-1] by y, and write the len least
114    * significant words of the product to dest[0:len-1].
115    * Return the most significant word of the product.
116    * All values are treated as if they were unsigned
117    * (i.e. masked with 0xffffffffL).
118    * OK if dest==x (not sure if this is guaranteed for mpn_mul_1).
119    * This function is basically the same as gmp's mpn_mul_1.
120    */
121 
122   public static int mul_1 (int[] dest, int[] x, int len, int y)
123   {
124     long yword = (long) y & 0xffffffffL;
125     long carry = 0;
126     for (int j = 0;  j < len; j++)
127       {
128         carry += ((long) x[j] & 0xffffffffL) * yword;
129         dest[j] = (int) carry;
130         carry >>>= 32;
131       }
132     return (int) carry;
133   }
134 
135   /**
136    * Multiply x[0:xlen-1] and y[0:ylen-1], and
137    * write the result to dest[0:xlen+ylen-1].
138    * The destination has to have space for xlen+ylen words,
139    * even if the result might be one limb smaller.
140    * This function requires that xlen >= ylen.
141    * The destination must be distinct from either input operands.
142    * All operands are unsigned.
143    * This function is basically the same gmp's mpn_mul. */
144 
145   public static void mul (int[] dest,
146               int[] x, int xlen,
147               int[] y, int ylen)
148   {
149     dest[xlen] = MPN.mul_1 (dest, x, xlen, y[0]);
150 
151     for (int i = 1;  i < ylen; i++)
152       {
153     long yword = (long) y[i] & 0xffffffffL;
154     long carry = 0;
155     for (int j = 0;  j < xlen; j++)
156       {
157         carry += ((long) x[j] & 0xffffffffL) * yword
158           + ((long) dest[i+j] & 0xffffffffL);
159         dest[i+j] = (int) carry;
160         carry >>>= 32;
161       }
162     dest[i+xlen] = (int) carry;
163       }
164   }
165 
166   /* Divide (unsigned long) N by (unsigned int) D.
167    * Returns (remainder << 32)+(unsigned int)(quotient).
168    * Assumes (unsigned int)(N>>32) < (unsigned int)D.
169    * Code transcribed from gmp-2.0's mpn_udiv_w_sdiv function.
170    */
171   public static long udiv_qrnnd (long N, int D)
172   {
173     long q, r;
174     long a1 = N >>> 32;
175     long a0 = N & 0xffffffffL;
176     if (D >= 0)
177       {
178     if (a1 < ((D - a1 - (a0 >>> 31)) & 0xffffffffL))
179       {
180         /* dividend, divisor, and quotient are nonnegative */
181         q = N / D;
182         r = N % D;
183       }
184     else
185       {
186         /* Compute c1*2^32 + c0 = a1*2^32 + a0 - 2^31*d */
187         long c = N - ((long) D << 31);
188         /* Divide (c1*2^32 + c0) by d */
189         q = c / D;
190         r = c % D;
191         /* Add 2^31 to quotient */
192         q += 1 << 31;
193       }
194       }
195     else
196       {
197     long b1 = D >>> 1;  /* d/2, between 2^30 and 2^31 - 1 */
198     //long c1 = (a1 >> 1); /* A/2 */
199     //int c0 = (a1 << 31) + (a0 >> 1);
200     long c = N >>> 1;
201     if (a1 < b1 || (a1 >> 1) < b1)
202       {
203         if (a1 < b1)
204           {
205         q = c / b1;
206         r = c % b1;
207           }
208         else /* c1 < b1, so 2^31 <= (A/2)/b1 < 2^32 */
209           {
210         c = ~(c - (b1 << 32));
211         q = c / b1;  /* (A/2) / (d/2) */
212         r = c % b1;
213         q = (~q) & 0xffffffffL;    /* (A/2)/b1 */
214         r = (b1 - 1) - r; /* r < b1 => new r >= 0 */
215           }
216         r = 2 * r + (a0 & 1);
217         if ((D & 1) != 0)
218           {
219         if (r >= q) {
220                 r = r - q;
221         } else if (q - r <= ((long) D & 0xffffffffL)) {
222                        r = r - q + D;
223                 q -= 1;
224         } else {
225                        r = r - q + D + D;
226                 q -= 2;
227         }
228           }
229       }
230     else                /* Implies c1 = b1 */
231       {             /* Hence a1 = d - 1 = 2*b1 - 1 */
232         if (a0 >= ((long)(-D) & 0xffffffffL))
233           {
234         q = -1;
235             r = a0 + D;
236           }
237         else
238           {
239         q = -2;
240             r = a0 + D + D;
241           }
242       }
243       }
244 
245     return (r << 32) | (q & 0xFFFFFFFFl);
246   }
247 
248     /** Divide divident[0:len-1] by (unsigned int)divisor.
249      * Write result into quotient[0:len-1.
250      * Return the one-word (unsigned) remainder.
251      * OK for quotient==dividend.
252      */
253 
254   public static int divmod_1 (int[] quotient, int[] dividend,
255                   int len, int divisor)
256   {
257     int i = len - 1;
258     long r = dividend[i];
259     if ((r & 0xffffffffL) >= ((long)divisor & 0xffffffffL))
260       r = 0;
261     else
262       {
263     quotient[i--] = 0;
264     r <<= 32;
265       }
266 
267     for (;  i >= 0;  i--)
268       {
269     int n0 = dividend[i];
270     r = (r & ~0xffffffffL) | (n0 & 0xffffffffL);
271     r = udiv_qrnnd (r, divisor);
272     quotient[i] = (int) r;
273       }
274     return (int)(r >> 32);
275   }
276 
277   /* Subtract x[0:len-1]*y from dest[offset:offset+len-1].
278    * All values are treated as if unsigned.
279    * @return the most significant word of
280    * the product, minus borrow-out from the subtraction.
281    */
282   public static int submul_1 (int[] dest, int offset, int[] x, int len, int y)
283   {
284     long yl = (long) y & 0xffffffffL;
285     int carry = 0;
286     int j = 0;
287     do
288       {
289     long prod = ((long) x[j] & 0xffffffffL) * yl;
290     int prod_low = (int) prod;
291     int prod_high = (int) (prod >> 32);
292     prod_low += carry;
293     // Invert the high-order bit, because: (unsigned) X > (unsigned) Y
294     // iff: (int) (X^0x80000000) > (int) (Y^0x80000000).
295     carry = ((prod_low ^ 0x80000000) < (carry ^ 0x80000000) ? 1 : 0)
296       + prod_high;
297     int x_j = dest[offset+j];
298     prod_low = x_j - prod_low;
299     if ((prod_low ^ 0x80000000) > (x_j ^ 0x80000000))
300       carry++;
301     dest[offset+j] = prod_low;
302       }
303     while (++j < len);
304     return carry;
305   }
306 
307   /** Divide zds[0:nx] by y[0:ny-1].
308    * The remainder ends up in zds[0:ny-1].
309    * The quotient ends up in zds[ny:nx].
310    * Assumes:  nx>ny.
311    * (int)y[ny-1] < 0  (i.e. most significant bit set)
312    */
313 
314   public static void divide (int[] zds, int nx, int[] y, int ny)
315   {
316     // This is basically Knuth's formulation of the classical algorithm,
317     // but translated from in scm_divbigbig in Jaffar's SCM implementation.
318 
319     // Correspondance with Knuth's notation:
320     // Knuth's u[0:m+n] == zds[nx:0].
321     // Knuth's v[1:n] == y[ny-1:0]
322     // Knuth's n == ny.
323     // Knuth's m == nx-ny.
324     // Our nx == Knuth's m+n.
325 
326     // Could be re-implemented using gmp's mpn_divrem:
327     // zds[nx] = mpn_divrem (&zds[ny], 0, zds, nx, y, ny).
328 
329     int j = nx;
330     do
331       {                          // loop over digits of quotient
332     // Knuth's j == our nx-j.
333     // Knuth's u[j:j+n] == our zds[j:j-ny].
334     int qhat;  // treated as unsigned
335     if (zds[j]==y[ny-1])
336       qhat = -1;  // 0xffffffff
337     else
338       {
339         long w = (((long)(zds[j])) << 32) + ((long)zds[j-1] & 0xffffffffL);
340         qhat = (int) udiv_qrnnd (w, y[ny-1]);
341       }
342     if (qhat != 0)
343       {
344         int borrow = submul_1 (zds, j - ny, y, ny, qhat);
345         int save = zds[j];
346         long num = ((long)save&0xffffffffL) - ((long)borrow&0xffffffffL);
347             while (num != 0)
348           {
349         qhat--;
350         long carry = 0;
351         for (int i = 0;  i < ny; i++)
352           {
353             carry += ((long) zds[j-ny+i] & 0xffffffffL)
354               + ((long) y[i] & 0xffffffffL);
355             zds[j-ny+i] = (int) carry;
356             carry >>>= 32;
357           }
358         zds[j] += carry;
359         num = carry - 1;
360           }
361       }
362     zds[j] = qhat;
363       } while (--j >= ny);
364   }
365 
366   /** Number of digits in the conversion base that always fits in a word.
367    * For example, for base 10 this is 9, since 10**9 is the
368    * largest number that fits into a words (assuming 32-bit words).
369    * This is the same as gmp's __mp_bases[radix].chars_per_limb.
370    * @param radix the base
371    * @return number of digits */
372   public static int chars_per_word (int radix)
373   {
374     if (radix < 10)
375       {
376     if (radix < 8)
377       {
378         if (radix <= 2)
379           return 32;
380         else if (radix == 3)
381           return 20;
382         else if (radix == 4)
383           return 16;
384         else
385           return 18 - radix;
386       }
387     else
388       return 10;
389       }
390     else if (radix < 12)
391       return 9;
392     else if (radix <= 16)
393       return 8;
394     else if (radix <= 23)
395       return 7;
396     else if (radix <= 40)
397       return 6;
398     // The following are conservative, but we don't care.
399     else if (radix <= 256)
400       return 4;
401     else
402       return 1;
403   }
404 
405   /** Count the number of leading zero bits in an int. */
406   public static int count_leading_zeros (int i)
407   {
408     if (i == 0)
409       return 32;
410     int count = 0;
411     for (int k = 16;  k > 0;  k = k >> 1) {
412       int j = i >>> k;
413       if (j == 0)
414     count += k;
415       else
416     i = j;
417     }
418     return count;
419   }
420 
421   public static int set_str (int dest[], byte[] str, int str_len, int base)
422   {
423     int size = 0;
424     if ((base & (base - 1)) == 0)
425       {
426     // The base is a power of 2.  Read the input string from
427     // least to most significant character/digit.  */
428 
429     int next_bitpos = 0;
430     int bits_per_indigit = 0;
431     for (int i = base; (i >>= 1) != 0; ) bits_per_indigit++;
432     int res_digit = 0;
433 
434     for (int i = str_len;  --i >= 0; )
435       {
436         int inp_digit = str[i];
437         res_digit |= inp_digit << next_bitpos;
438         next_bitpos += bits_per_indigit;
439         if (next_bitpos >= 32)
440           {
441         dest[size++] = res_digit;
442         next_bitpos -= 32;
443         res_digit = inp_digit >> (bits_per_indigit - next_bitpos);
444           }
445       }
446 
447     if (res_digit != 0)
448       dest[size++] = res_digit;
449       }
450     else
451       {
452     // General case.  The base is not a power of 2.
453     int indigits_per_limb = MPN.chars_per_word (base);
454     int str_pos = 0;
455 
456     while (str_pos < str_len)
457       {
458         int chunk = str_len - str_pos;
459         if (chunk > indigits_per_limb)
460           chunk = indigits_per_limb;
461         int res_digit = str[str_pos++];
462         int big_base = base;
463 
464         while (--chunk > 0)
465           {
466         res_digit = res_digit * base + str[str_pos++];
467         big_base *= base;
468           }
469 
470         int cy_limb;
471         if (size == 0)
472           cy_limb = res_digit;
473         else
474           {
475         cy_limb = MPN.mul_1 (dest, dest, size, big_base);
476         cy_limb += MPN.add_1 (dest, dest, size, res_digit);
477           }
478         if (cy_limb != 0)
479           dest[size++] = cy_limb;
480       }
481        }
482     return size;
483   }
484 
485   /** Compare x[0:size-1] with y[0:size-1], treating them as unsigned integers.
486    * @result -1, 0, or 1 depending on if x<y, x==y, or x>y.
487    * This is basically the same as gmp's mpn_cmp function.
488    */
489   public static int cmp (int[] x, int[] y, int size)
490   {
491     while (--size >= 0)
492       {
493     int x_word = x[size];
494     int y_word = y[size];
495     if (x_word != y_word)
496       {
497         // Invert the high-order bit, because:
498         // (unsigned) X > (unsigned) Y iff
499         // (int) (X^0x80000000) > (int) (Y^0x80000000).
500         return (x_word ^ 0x80000000) > (y_word ^0x80000000) ? 1 : -1;
501       }
502       }
503     return 0;
504   }
505 
506   /** Compare x[0:xlen-1] with y[0:ylen-1], treating them as unsigned integers.
507    * @result -1, 0, or 1 depending on if x<y, x==y, or x>y.
508    */
509   public static int cmp (int[] x, int xlen, int[] y, int ylen)
510   {
511     return xlen > ylen ? 1 : xlen < ylen ? -1 : cmp (x, y, xlen);
512   }
513 
514   /* Shift x[x_start:x_start+len-1] count bits to the "right"
515    * (i.e. divide by 2**count).
516    * Store the len least significant words of the result at dest.
517    * The bits shifted out to the right are returned.
518    * OK if dest==x.
519    * Assumes: 0 < count < 32
520    */
521 
522   public static int rshift (int[] dest, int[] x, int x_start,
523                 int len, int count)
524   {
525     int count_2 = 32 - count;
526     int low_word = x[x_start];
527     int retval = low_word << count_2;
528     int i = 1;
529     for (; i < len;  i++)
530       {
531     int high_word = x[x_start+i];
532     dest[i-1] = (low_word >>> count) | (high_word << count_2);
533     low_word = high_word;
534       }
535     dest[i-1] = low_word >>> count;
536     return retval;
537   }
538 
539   /* Shift x[x_start:x_start+len-1] count bits to the "right"
540    * (i.e. divide by 2**count).
541    * Store the len least significant words of the result at dest.
542    * OK if dest==x.
543    * Assumes: 0 <= count < 32
544    * Same as rshift, but handles count==0 (and has no return value).
545    */
546   public static void rshift0 (int[] dest, int[] x, int x_start,
547                   int len, int count)
548   {
549     if (count > 0)
550       rshift(dest, x, x_start, len, count);
551     else
552       for (int i = 0;  i < len;  i++)
553     dest[i] = x[i + x_start];
554   }
555 
556   /** Return the long-truncated value of right shifting.
557   * @param x a two's-complement "bignum"
558   * @param len the number of significant words in x
559   * @param count the shift count
560   * @return (long)(x[0..len-1] >> count).
561   */
562   public static long rshift_long (int[] x, int len, int count)
563   {
564     int wordno = count >> 5;
565     count &= 31;
566     int sign = x[len-1] < 0 ? -1 : 0;
567     int w0 = wordno >= len ? sign : x[wordno];
568     wordno++;
569     int w1 = wordno >= len ? sign : x[wordno];
570     if (count != 0)
571       {
572     wordno++;
573     int w2 = wordno >= len ? sign : x[wordno];
574     w0 = (w0 >>> count) | (w1 << (32-count));
575     w1 = (w1 >>> count) | (w2 << (32-count));
576       }
577     return ((long)w1 << 32) | ((long)w0 & 0xffffffffL);
578   }
579 
580   /* Shift x[0:len-1] left by count bits, and store the len least
581    * significant words of the result in dest[d_offset:d_offset+len-1].
582    * Return the bits shifted out from the most significant digit.
583    * Assumes 0 < count < 32.
584    * OK if dest==x.
585    */
586 
587   public static int lshift (int[] dest, int d_offset,
588                 int[] x, int len, int count)
589   {
590     int count_2 = 32 - count;
591     int i = len - 1;
592     int high_word = x[i];
593     int retval = high_word >>> count_2;
594     d_offset++;
595     while (--i >= 0)
596       {
597     int low_word = x[i];
598     dest[d_offset+i] = (high_word << count) | (low_word >>> count_2);
599     high_word = low_word;
600       }
601     dest[d_offset+i] = high_word << count;
602     return retval;
603   }
604 
605   /** Return least i such that word&(1<<i). Assumes word!=0. */
606 
607   public static int findLowestBit (int word)
608   {
609     int i = 0;
610     while ((word & 0xF) == 0)
611       {
612     word >>= 4;
613     i += 4;
614       }
615     if ((word & 3) == 0)
616       {
617     word >>= 2;
618     i += 2;
619       }
620     if ((word & 1) == 0)
621       i += 1;
622     return i;
623   }
624 
625   /** Calculate Greatest Common Divisior of x[0:len-1] and y[0:len-1].
626     * Assumes both arguments are non-zero.
627     * Leaves result in x, and returns len of result.
628     * Also destroys y (actually sets it to a copy of the result). */
629 
630   public static int gcd (int[] x, int[] y, int len)
631   {
632     int i, word;
633     // Find sh such that both x and y are divisible by 2**sh.
634     for (i = 0; ; i++)
635       {
636     word = x[i] | y[i];
637     if (word != 0)
638       {
639         // Must terminate, since x and y are non-zero.
640         break;
641       }
642       }
643     int initShiftWords = i;
644     int initShiftBits = findLowestBit (word);
645     // Logically: sh = initShiftWords * 32 + initShiftBits
646 
647     // Temporarily devide both x and y by 2**sh.
648     len -= initShiftWords;
649     MPN.rshift0 (x, x, initShiftWords, len, initShiftBits);
650     MPN.rshift0 (y, y, initShiftWords, len, initShiftBits);
651 
652     int[] odd_arg; /* One of x or y which is odd. */
653     int[] other_arg; /* The other one can be even or odd. */
654     if ((x[0] & 1) != 0)
655       {
656     odd_arg = x;
657     other_arg = y;
658       }
659     else
660       {
661     odd_arg = y;
662     other_arg = x;
663       }
664 
665     for (;;)
666       {
667     // Shift other_arg until it is odd; this doesn't
668     // affect the gcd, since we divide by 2**k, which does not
669     // divide odd_arg.
670     for (i = 0; other_arg[i] == 0; ) i++;
671     if (i > 0)
672       {
673         int j;
674         for (j = 0; j < len-i; j++)
675         other_arg[j] = other_arg[j+i];
676         for ( ; j < len; j++)
677           other_arg[j] = 0;
678       }
679     i = findLowestBit(other_arg[0]);
680     if (i > 0)
681       MPN.rshift (other_arg, other_arg, 0, len, i);
682 
683     // Now both odd_arg and other_arg are odd.
684 
685     // Subtract the smaller from the larger.
686     // This does not change the result, since gcd(a-b,b)==gcd(a,b).
687     i = MPN.cmp(odd_arg, other_arg, len);
688     if (i == 0)
689         break;
690     if (i > 0)
691       { // odd_arg > other_arg
692         MPN.sub_n (odd_arg, odd_arg, other_arg, len);
693         // Now odd_arg is even, so swap with other_arg;
694         int[] tmp = odd_arg; odd_arg = other_arg; other_arg = tmp;
695       }
696     else
697       { // other_arg > odd_arg
698         MPN.sub_n (other_arg, other_arg, odd_arg, len);
699     }
700     while (odd_arg[len-1] == 0 && other_arg[len-1] == 0)
701       len--;
702     }
703     if (initShiftWords + initShiftBits > 0)
704       {
705     if (initShiftBits > 0)
706       {
707         int sh_out = MPN.lshift (x, initShiftWords, x, len, initShiftBits);
708         if (sh_out != 0)
709           x[(len++)+initShiftWords] = sh_out;
710       }
711     else
712       {
713         for (i = len; --i >= 0;)
714           x[i+initShiftWords] = x[i];
715       }
716     for (i = initShiftWords;  --i >= 0; )
717       x[i] = 0;
718     len += initShiftWords;
719       }
720     return len;
721   }
722 
723   public static int intLength (int i)
724   {
725     return 32 - count_leading_zeros (i < 0 ? ~i : i);
726   }
727 
728   /** Calcaulte the Common Lisp "integer-length" function.
729    * Assumes input is canonicalized:  len==BigInteger.wordsNeeded(words,len) */
730   public static int intLength (int[] words, int len)
731   {
732     len--;
733     return intLength (words[len]) + 32 * len;
734   }
735 
736   /* DEBUGGING:
737   public static void dprint (BigInteger x)
738   {
739     if (x.words == null)
740       System.err.print(Long.toString((long) x.ival & 0xffffffffL, 16));
741     else
742       dprint (System.err, x.words, x.ival);
743   }
744   public static void dprint (int[] x) { dprint (System.err, x, x.length); }
745   public static void dprint (int[] x, int len) { dprint (System.err, x, len); }
746   public static void dprint (java.io.PrintStream ps, int[] x, int len)
747   {
748     ps.print('(');
749     for (int i = 0;  i < len; i++)
750       {
751     if (i > 0)
752       ps.print (' ');
753     ps.print ("#x" + Long.toString ((long) x[i] & 0xffffffffL, 16));
754       }
755     ps.print(')');
756   }
757   */
758 }
5776626 [rkeene@sledge /home/rkeene/archive/floydssh/ssh]$

Click here to go back to the directory listing.
Click here to download this file.
last modified: 2004-03-06 22:44:06