Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(125)

Side by Side Diff: runtime/lib/bigint.dart

Issue 1038253002: Various cleanup in bigint implementation: (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 5 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 // Copyright 2009 The Go Authors. All rights reserved. 5 // Copyright 2009 The Go Authors. All rights reserved.
6 // Use of this source code is governed by a BSD-style 6 // Use of this source code is governed by a BSD-style
7 // license that can be found in the LICENSE file. 7 // license that can be found in the LICENSE file.
8 8
9 /* 9 /*
10 * Copyright (c) 2003-2005 Tom Wu 10 * Copyright (c) 2003-2005 Tom Wu
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after
264 return _dlShift(ds); 264 return _dlShift(ds);
265 } 265 }
266 var cbs = _DIGIT_BITS - bs; 266 var cbs = _DIGIT_BITS - bs;
267 var bm = (1 << cbs) - 1; 267 var bm = (1 << cbs) - 1;
268 var r_used = _used + ds + 1; 268 var r_used = _used + ds + 1;
269 var digits = _digits; 269 var digits = _digits;
270 var r_digits = new Uint32List(r_used + (r_used & 1)); 270 var r_digits = new Uint32List(r_used + (r_used & 1));
271 var c = 0; 271 var c = 0;
272 var i = _used; 272 var i = _used;
273 while (--i >= 0) { 273 while (--i >= 0) {
274 r_digits[i + ds + 1] = (digits[i] >> cbs) | c; 274 final d = digits[i];
275 c = (digits[i] & bm) << bs; 275 r_digits[i + ds + 1] = (d >> cbs) | c;
276 c = (d & bm) << bs;
276 } 277 }
277 r_digits[ds] = c; 278 r_digits[ds] = c;
278 return new _Bigint(_neg, r_used, r_digits); 279 return new _Bigint(_neg, r_used, r_digits);
279 } 280 }
280 281
281 // r_digits[0..r_used-1] = x_digits[0..x_used-1] << n. 282 // r_digits[0..r_used-1] = x_digits[0..x_used-1] << n.
282 // Return r_used. 283 // Return r_used.
283 static int _lShiftDigits(Uint32List x_digits, int x_used, int n, 284 static int _lShiftDigits(Uint32List x_digits, int x_used, int n,
284 Uint32List r_digits) { 285 Uint32List r_digits) {
285 var ds = n ~/ _DIGIT_BITS; 286 var ds = n ~/ _DIGIT_BITS;
286 var bs = n % _DIGIT_BITS; 287 var bs = n % _DIGIT_BITS;
287 if (bs == 0) { 288 if (bs == 0) {
288 return _dlShiftDigits(x_digits, x_used, ds, r_digits); 289 return _dlShiftDigits(x_digits, x_used, ds, r_digits);
289 } 290 }
290 var cbs = _DIGIT_BITS - bs; 291 var cbs = _DIGIT_BITS - bs;
291 var bm = (1 << cbs) - 1; 292 var bm = (1 << cbs) - 1;
292 var r_used = x_used + ds + 1; 293 var r_used = x_used + ds + 1;
293 assert(r_digits.length >= r_used + (r_used & 1)); 294 assert(r_digits.length >= r_used + (r_used & 1));
294 var c = 0; 295 var c = 0;
295 var i = x_used; 296 var i = x_used;
296 while (--i >= 0) { 297 while (--i >= 0) {
297 r_digits[i + ds + 1] = (x_digits[i] >> cbs) | c; 298 final d = x_digits[i];
298 c = (x_digits[i] & bm) << bs; 299 r_digits[i + ds + 1] = (d >> cbs) | c;
300 c = (d & bm) << bs;
299 } 301 }
300 r_digits[ds] = c; 302 r_digits[ds] = c;
301 i = ds; 303 i = ds;
302 while (--i >= 0) { 304 while (--i >= 0) {
303 r_digits[i] = 0; 305 r_digits[i] = 0;
304 } 306 }
305 if (r_used.isOdd) { 307 if (r_digits[r_used - 1] == 0) {
308 r_used--; // Clamp result.
309 } else if (r_used.isOdd) {
306 r_digits[r_used] = 0; 310 r_digits[r_used] = 0;
307 } 311 }
308 return r_used; 312 return r_used;
309 } 313 }
310 314
311 // Return this >> n. 315 // Return this >> n.
312 _Bigint _rShift(int n) { 316 _Bigint _rShift(int n) {
313 var ds = n ~/ _DIGIT_BITS; 317 var ds = n ~/ _DIGIT_BITS;
314 var bs = n % _DIGIT_BITS; 318 var bs = n % _DIGIT_BITS;
315 if (bs == 0) { 319 if (bs == 0) {
316 return _drShift(ds); 320 return _drShift(ds);
317 } 321 }
318 var r_used = _used - ds; 322 var r_used = _used - ds;
319 if (r_used <= 0) { 323 if (r_used <= 0) {
320 return _neg ? _MINUS_ONE : _ZERO; 324 return _neg ? _MINUS_ONE : _ZERO;
321 } 325 }
322 var cbs = _DIGIT_BITS - bs; 326 var cbs = _DIGIT_BITS - bs;
323 var bm = (1 << bs) - 1; 327 var bm = (1 << bs) - 1;
324 var digits = _digits; 328 var digits = _digits;
325 var r_digits = new Uint32List(r_used + (r_used & 1)); 329 var r_digits = new Uint32List(r_used + (r_used & 1));
326 r_digits[0] = digits[ds] >> bs; 330 r_digits[0] = digits[ds] >> bs;
327 var used = _used; 331 var used = _used;
328 for (var i = ds + 1; i < used; i++) { 332 for (var i = ds + 1; i < used; i++) {
329 r_digits[i - ds - 1] |= (digits[i] & bm) << cbs; 333 final d = digits[i];
330 r_digits[i - ds] = digits[i] >> bs; 334 r_digits[i - ds - 1] |= (d & bm) << cbs;
335 r_digits[i - ds] = d >> bs;
331 } 336 }
332 var r = new _Bigint(_neg, r_used, r_digits); 337 var r = new _Bigint(_neg, r_used, r_digits);
333 if (_neg) { 338 if (_neg) {
334 // Round down if any bit was shifted out. 339 // Round down if any bit was shifted out.
335 if ((digits[ds] & bm) != 0) { 340 if ((digits[ds] & bm) != 0) {
336 return r._sub(_ONE); 341 return r._sub(_ONE);
337 } 342 }
338 for (var i = 0; i < ds; i++) { 343 for (var i = 0; i < ds; i++) {
339 if (digits[i] != 0) { 344 if (digits[i] != 0) {
340 return r._sub(_ONE); 345 return r._sub(_ONE);
(...skipping 14 matching lines...) Expand all
355 } 360 }
356 var r_used = x_used - ds; 361 var r_used = x_used - ds;
357 if (r_used <= 0) { 362 if (r_used <= 0) {
358 return 0; 363 return 0;
359 } 364 }
360 var cbs = _DIGIT_BITS - bs; 365 var cbs = _DIGIT_BITS - bs;
361 var bm = (1 << bs) - 1; 366 var bm = (1 << bs) - 1;
362 assert(r_digits.length >= r_used + (r_used & 1)); 367 assert(r_digits.length >= r_used + (r_used & 1));
363 r_digits[0] = x_digits[ds] >> bs; 368 r_digits[0] = x_digits[ds] >> bs;
364 for (var i = ds + 1; i < x_used; i++) { 369 for (var i = ds + 1; i < x_used; i++) {
365 r_digits[i - ds - 1] |= (x_digits[i] & bm) << cbs; 370 final d = x_digits[i];
366 r_digits[i - ds] = x_digits[i] >> bs; 371 r_digits[i - ds - 1] |= (d & bm) << cbs;
372 r_digits[i - ds] = d >> bs;
367 } 373 }
368 if (r_used.isOdd) { 374 if (r_digits[r_used - 1] == 0) {
375 r_used--; // Clamp result.
376 } else if (r_used.isOdd) {
369 r_digits[r_used] = 0; 377 r_digits[r_used] = 0;
370 } 378 }
371 return r_used; 379 return r_used;
372 } 380 }
373 381
374 // Return 0 if abs(this) == abs(a). 382 // Return 0 if abs(this) == abs(a).
375 // Return a positive number if abs(this) > abs(a). 383 // Return a positive number if abs(this) > abs(a).
376 // Return a negative number if abs(this) < abs(a). 384 // Return a negative number if abs(this) < abs(a).
377 int _absCompare(_Bigint a) { 385 int _absCompare(_Bigint a) {
378 var r = _used - a._used; 386 var r = _used - a._used;
(...skipping 569 matching lines...) Expand 10 before | Expand all | Expand 10 after
948 _Bigint _divRem(_Bigint a, bool div) { 956 _Bigint _divRem(_Bigint a, bool div) {
949 assert(a._used > 0); 957 assert(a._used > 0);
950 if (_used < a._used) { 958 if (_used < a._used) {
951 return div ? _ZERO : this; 959 return div ? _ZERO : this;
952 } 960 }
953 var nsh = _DIGIT_BITS - _nbits(a._digits[a._used - 1]); 961 var nsh = _DIGIT_BITS - _nbits(a._digits[a._used - 1]);
954 // For 64-bit processing, make sure y has an even number of digits. 962 // For 64-bit processing, make sure y has an even number of digits.
955 if (a._used.isOdd) { 963 if (a._used.isOdd) {
956 nsh += _DIGIT_BITS; 964 nsh += _DIGIT_BITS;
957 } 965 }
958 var y; // Normalized positive divisor. 966 // Concatenated positive quotient and normalized positive remainder.
959 var r; // Concatenated positive quotient and normalized positive remainder. 967 var r_digits;
968 var r_used;
969 // Normalized positive divisor.
970 var y_digits;
971 var y_used;
960 if (nsh > 0) { 972 if (nsh > 0) {
961 y = a._lShift(nsh)._abs(); 973 y_digits = new Uint32List(a._used + 3); // +3 for normalization.
962 r = _lShift(nsh)._abs(); 974 y_used = _lShiftDigits(a._digits, a._used, nsh, y_digits);
975 r_digits = new Uint32List(_used + 3); // +3 for normalization.
976 r_used = _lShiftDigits(_digits, _used, nsh, r_digits);
977 } else {
978 y_digits = a._digits;
979 y_used = a._used;
980 r_digits = _cloneDigits(_digits, 0, _used, _used + 2);
981 r_used = _used;
963 } 982 }
964 else { 983 Uint32List yt_qd = new Uint32List(4);
965 y = a._abs(); 984 yt_qd[_YT_LO] = y_digits[y_used - 2];
966 r = _abs(); 985 yt_qd[_YT] = y_digits[y_used - 1];
967 }
968 var y_used = y._used;
969 var y_digits = y._digits;
970 Uint32List args = new Uint32List(4);
971 args[_YT_LO] = y_digits[y_used - 2];
972 args[_YT] = y_digits[y_used - 1];
973 var r_used = r._used;
974 // For 64-bit processing, make sure y_used, i, and j are even. 986 // For 64-bit processing, make sure y_used, i, and j are even.
975 assert(y_used.isEven); 987 assert(y_used.isEven);
976 var i = r_used + (r_used & 1); 988 var i = r_used + (r_used & 1);
977 var j = i - y_used; 989 var j = i - y_used;
978 var t = y._dlShift(j); 990 // t_digits is a temporary array of i digits.
979 if (r._compare(t) >= 0) { 991 var t_digits = new Uint32List(i);
992 var t_used = _dlShiftDigits(y_digits, y_used, j, t_digits);
993 // Explicit first division step in case normalized dividend is larger or
994 // equal to shifted normalized divisor.
995 if (_compareDigits(r_digits, r_used, t_digits, t_used) >= 0) {
980 assert(i == r_used); 996 assert(i == r_used);
981 r = r._or(_ONE._dlShift(r_used++))._sub(t); 997 r_digits[r_used++] = 1; // Quotient = 1.
982 assert(r._used == r_used && (i + 1) == r_used); 998 r_digits[r_used] = 0; // Leading zero.
999 // Subtract divisor from remainder.
1000 _absSub(r_digits, r_used, t_digits, t_used, r_digits);
983 } 1001 }
984 // Negate y so we can later use _mulAdd instead of non-existent _mulSub. 1002 // Negate y so we can later use _mulAdd instead of non-existent _mulSub.
985 y = _ONE._dlShift(y_used)._sub(y); 1003 var ny_digits = new Uint32List(y_used + 2);
986 if (y._used < y_used) { 1004 ny_digits[y_used] = 1;
987 y_digits = _cloneDigits(y._digits, 0, y._used, y_used); 1005 _absSub(ny_digits, y_used + 1, y_digits, y_used, ny_digits);
988 } else { 1006 // ny_digits is read-only and has y_used digits (possibly including several
989 y_digits = y._digits;
990 }
991 // y_digits is read-only and has y_used digits (possibly including several
992 // leading zeros) plus a leading zero for 64-bit processing. 1007 // leading zeros) plus a leading zero for 64-bit processing.
993 var r_digits = _cloneDigits(r._digits, 0, r._used, i + 1);
994 // r_digits is modified during iteration. 1008 // r_digits is modified during iteration.
995 // r_digits[0..y_used-1] is the current remainder. 1009 // r_digits[0..y_used-1] is the current remainder.
996 // r_digits[y_used..r_used-1] is the current quotient. 1010 // r_digits[y_used..r_used-1] is the current quotient.
997 --i; 1011 --i;
998 while (j > 0) { 1012 while (j > 0) {
999 var d0 = _estQuotientDigit(args, r_digits, i); 1013 var d0 = _estQuotientDigit(yt_qd, r_digits, i);
1000 j -= d0; 1014 j -= d0;
1001 var d1 = _mulAdd(args, _QD, y_digits, 0, r_digits, j, y_used); 1015 var d1 = _mulAdd(yt_qd, _QD, ny_digits, 0, r_digits, j, y_used);
1002 // _estQuotientDigit and _mulAdd must agree on the number of digits to 1016 // _estQuotientDigit and _mulAdd must agree on the number of digits to
1003 // process. 1017 // process.
1004 assert(d0 == d1); 1018 assert(d0 == d1);
1005 if (d0 == 1) { 1019 if (d0 == 1) {
1006 if (r_digits[i] < args[_QD]) { 1020 if (r_digits[i] < yt_qd[_QD]) {
1007 var t = y._dlShift(j); 1021 var t_used = _dlShiftDigits(ny_digits, y_used, j, t_digits);
1008 var t_digits = t._digits;
1009 var t_used = t._used;
1010 _absSub(r_digits, r_used, t_digits, t_used, r_digits); 1022 _absSub(r_digits, r_used, t_digits, t_used, r_digits);
1011 while (r_digits[i] < --args[_QD]) { 1023 while (r_digits[i] < --yt_qd[_QD]) {
1012 _absSub(r_digits, r_used, t_digits, t_used, r_digits); 1024 _absSub(r_digits, r_used, t_digits, t_used, r_digits);
1013 } 1025 }
1014 } 1026 }
1015 } else { 1027 } else {
1016 assert(d0 == 2); 1028 assert(d0 == 2);
1017 assert(r_digits[i] <= args[_QD_HI]); 1029 assert(r_digits[i] <= yt_qd[_QD_HI]);
1018 if ((r_digits[i] < args[_QD_HI]) || (r_digits[i-1] < args[_QD])) { 1030 if ((r_digits[i] < yt_qd[_QD_HI]) || (r_digits[i-1] < yt_qd[_QD])) {
1019 var t = y._dlShift(j); 1031 var t_used = _dlShiftDigits(ny_digits, y_used, j, t_digits);
1020 var t_digits = t._digits;
1021 var t_used = t._used;
1022 _absSub(r_digits, r_used, t_digits, t_used, r_digits); 1032 _absSub(r_digits, r_used, t_digits, t_used, r_digits);
1023 if (args[_QD] == 0) { 1033 if (yt_qd[_QD] == 0) {
1024 --args[_QD_HI]; 1034 --yt_qd[_QD_HI];
1025 } 1035 }
1026 --args[_QD]; 1036 --yt_qd[_QD];
1027 assert(r_digits[i] <= args[_QD_HI]); 1037 assert(r_digits[i] <= yt_qd[_QD_HI]);
1028 while ((r_digits[i] < args[_QD_HI]) || (r_digits[i-1] < args[_QD])) { 1038 while ((r_digits[i] < yt_qd[_QD_HI]) ||
1039 (r_digits[i-1] < yt_qd[_QD])) {
1029 _absSub(r_digits, r_used, t_digits, t_used, r_digits); 1040 _absSub(r_digits, r_used, t_digits, t_used, r_digits);
1030 if (args[_QD] == 0) { 1041 if (yt_qd[_QD] == 0) {
1031 --args[_QD_HI]; 1042 --yt_qd[_QD_HI];
1032 } 1043 }
1033 --args[_QD]; 1044 --yt_qd[_QD];
1034 assert(r_digits[i] <= args[_QD_HI]); 1045 assert(r_digits[i] <= yt_qd[_QD_HI]);
1035 } 1046 }
1036 } 1047 }
1037 } 1048 }
1038 i -= d0; 1049 i -= d0;
1039 } 1050 }
1040 if (div) { 1051 if (div) {
1041 // Return quotient, i.e. r_digits[y_used..r_used-1] with proper sign. 1052 // Return quotient, i.e. r_digits[y_used..r_used-1] with proper sign.
1042 r_digits = _cloneDigits(r_digits, y_used, r_used, r_used - y_used); 1053 r_digits = _cloneDigits(r_digits, y_used, r_used, r_used - y_used);
1043 r = new _Bigint(false, r_used - y_used, r_digits); 1054 var r = new _Bigint(false, r_used - y_used, r_digits);
1044 if (_neg != a._neg && r._used > 0) { 1055 if (_neg != a._neg && r._used > 0) {
1045 r = r._negate(); 1056 r = r._negate();
1046 } 1057 }
1047 return r; 1058 return r;
1048 } 1059 }
1049 // Return remainder, i.e. denormalized r_digits[0..y_used-1] with 1060 // Return remainder, i.e. denormalized r_digits[0..y_used-1] with
1050 // proper sign. 1061 // proper sign.
1051 r_digits = _cloneDigits(r_digits, 0, y_used, y_used); 1062 r_digits = _cloneDigits(r_digits, 0, y_used, y_used);
1052 r = new _Bigint(false, y_used, r_digits); 1063 var r = new _Bigint(false, y_used, r_digits);
1053 if (nsh > 0) { 1064 if (nsh > 0) {
1054 r = r._rShift(nsh); // Denormalize remainder. 1065 r = r._rShift(nsh); // Denormalize remainder.
1055 } 1066 }
1056 if (_neg && r._used > 0) { 1067 if (_neg && r._used > 0) {
1057 r = r._negate(); 1068 r = r._negate();
1058 } 1069 }
1059 return r; 1070 return r;
1060 } 1071 }
1061 1072
1062 // Customized version of _rem() minimizing allocations for use in reduction. 1073 // Customized version of _rem() minimizing allocations for use in reduction.
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
1182 } 1193 }
1183 1194
1184 // This method must support smi._toBigint()._shlFromInt(int). 1195 // This method must support smi._toBigint()._shlFromInt(int).
1185 // An out of memory exception is thrown if the result cannot be allocated. 1196 // An out of memory exception is thrown if the result cannot be allocated.
1186 int _shlFromInt(int other) { 1197 int _shlFromInt(int other) {
1187 if (_used == 0) return other; // Shift amount is zero. 1198 if (_used == 0) return other; // Shift amount is zero.
1188 if (_neg) throw new RangeError(this); 1199 if (_neg) throw new RangeError(this);
1189 assert(_DIGIT_BITS == 32); // Otherwise this code needs to be revised. 1200 assert(_DIGIT_BITS == 32); // Otherwise this code needs to be revised.
1190 var shift; 1201 var shift;
1191 if (_used > 2 || (_used == 2 && _digits[1] > 0x10000000)) { 1202 if (_used > 2 || (_used == 2 && _digits[1] > 0x10000000)) {
1203 if (other == 0) return 0; // Shifted value is zero.
1192 throw new OutOfMemoryError(); 1204 throw new OutOfMemoryError();
1193 } else { 1205 } else {
1194 shift = ((_used == 2) ? (_digits[1] << _DIGIT_BITS) : 0) + _digits[0]; 1206 shift = ((_used == 2) ? (_digits[1] << _DIGIT_BITS) : 0) + _digits[0];
1195 } 1207 }
1196 return other._toBigint()._lShift(shift)._toValidInt(); 1208 return other._toBigint()._lShift(shift)._toValidInt();
1197 } 1209 }
1198 1210
1199 // Overriden operators and methods. 1211 // Overriden operators and methods.
1200 1212
1201 // The following operators override operators of _IntegerImplementation for 1213 // The following operators override operators of _IntegerImplementation for
(...skipping 489 matching lines...) Expand 10 before | Expand all | Expand 10 after
1691 var neg_norm_m = _Bigint._ONE._dlShift(nm_used)._sub(_norm_m); 1703 var neg_norm_m = _Bigint._ONE._dlShift(nm_used)._sub(_norm_m);
1692 if (neg_norm_m._used < nm_used) { 1704 if (neg_norm_m._used < nm_used) {
1693 _neg_norm_m_digits = 1705 _neg_norm_m_digits =
1694 _Bigint._cloneDigits(neg_norm_m._digits, 0, nm_used, nm_used); 1706 _Bigint._cloneDigits(neg_norm_m._digits, 0, nm_used, nm_used);
1695 } else { 1707 } else {
1696 _neg_norm_m_digits = neg_norm_m._digits; 1708 _neg_norm_m_digits = neg_norm_m._digits;
1697 } 1709 }
1698 // _neg_norm_m_digits is read-only and has nm_used digits (possibly 1710 // _neg_norm_m_digits is read-only and has nm_used digits (possibly
1699 // including several leading zeros) plus a leading zero for 64-bit 1711 // including several leading zeros) plus a leading zero for 64-bit
1700 // processing. 1712 // processing.
1701 _t_digits = new Uint32List(2*nm_used + 2); 1713 _t_digits = new Uint32List(2*nm_used);
1702 } 1714 }
1703 1715
1704 int _convert(_Bigint x, Uint32List r_digits) { 1716 int _convert(_Bigint x, Uint32List r_digits) {
1705 var digits; 1717 var digits;
1706 var used; 1718 var used;
1707 if (x._neg || x._compare(_m) >= 0) { 1719 if (x._neg || x._compare(_m) >= 0) {
1708 var r = x._rem(_m); 1720 var r = x._rem(_m);
1709 if (x._neg && !r._neg && r._used > 0) { 1721 if (x._neg && !r._neg && r._used > 0) {
1710 r = _m._sub(r); 1722 r = _m._sub(r);
1711 } 1723 }
1712 assert(!r._neg); 1724 assert(!r._neg);
1713 used = r._used; 1725 used = r._used;
1714 digits = r._digits; 1726 digits = r._digits;
1715 } else { 1727 } else {
1716 used = x._used; 1728 used = x._used;
1717 digits = x._digits; 1729 digits = x._digits;
1718 } 1730 }
1719 var i = used + (used & 1); // Copy leading zero if any. 1731 var i = used + (used & 1); // Copy leading zero if any.
1720 while (--i >= 0) { 1732 while (--i >= 0) {
1721 r_digits[i] = digits[i]; 1733 r_digits[i] = digits[i];
1722 } 1734 }
1723 return used; 1735 return used;
1724 } 1736 }
1725 1737
1726 _Bigint _revert(Uint32List x_digits, int x_used) { 1738 _Bigint _revert(Uint32List x_digits, int x_used) {
1727 return new _Bigint(false, x_used, x_digits); 1739 return new _Bigint(false, x_used, x_digits);
1728 } 1740 }
1729 1741
1730 int _reduce(Uint32List x_digits, int x_used) { 1742 int _reduce(Uint32List x_digits, int x_used) {
1743 if (x_used < _m._used) {
1744 return x_used;
1745 }
1731 // The function _remDigits(...) is optimized for reduction and equivalent to 1746 // The function _remDigits(...) is optimized for reduction and equivalent to
1732 // calling _convert(_revert(x_digits, x_used)._rem(_m), x_digits); 1747 // calling _convert(_revert(x_digits, x_used)._rem(_m), x_digits);
1733 return _Bigint._remDigits(x_digits, x_used, 1748 return _Bigint._remDigits(x_digits, x_used,
1734 _norm_m._digits, _norm_m._used, 1749 _norm_m._digits, _norm_m._used,
1735 _neg_norm_m_digits, 1750 _neg_norm_m_digits,
1736 _m_nsh, 1751 _m_nsh,
1737 _mt_qd, 1752 _mt_qd,
1738 _t_digits, 1753 _t_digits,
1739 x_digits); 1754 x_digits);
1740 } 1755 }
1741 1756
1742 int _sqr(Uint32List x_digits, int x_used, Uint32List r_digits) { 1757 int _sqr(Uint32List x_digits, int x_used, Uint32List r_digits) {
1743 var r_used = _Bigint._sqrDigits(x_digits, x_used, r_digits); 1758 var r_used = _Bigint._sqrDigits(x_digits, x_used, r_digits);
1744 return _reduce(r_digits, r_used); 1759 return _reduce(r_digits, r_used);
1745 } 1760 }
1746 1761
1747 int _mul(Uint32List x_digits, int x_used, 1762 int _mul(Uint32List x_digits, int x_used,
1748 Uint32List y_digits, int y_used, 1763 Uint32List y_digits, int y_used,
1749 Uint32List r_digits) { 1764 Uint32List r_digits) {
1750 var r_used = _Bigint._mulDigits(x_digits, x_used, 1765 var r_used = _Bigint._mulDigits(x_digits, x_used,
1751 y_digits, y_used, 1766 y_digits, y_used,
1752 r_digits); 1767 r_digits);
1753 return _reduce(r_digits, r_used); 1768 return _reduce(r_digits, r_used);
1754 } 1769 }
1755 } 1770 }
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698