Comparing version 0.2.20 to 0.2.21
@@ -141,4 +141,12 @@ import { u128Safe as u128 } from '..'; | ||
}); | ||
}) | ||
it("Should power number 11", () => { | ||
expect(new u128(10) ** 38).toStrictEqual(new u128(0x98A224000000000, 0x4B3B4CA85A86C47A)); | ||
}); | ||
it("Should power number 12", () => { | ||
expect(new u128(9) ** 40).toStrictEqual(new u128(0x3CEA59789C79D441, 0x6F32F1EF8B18A2BC)); | ||
}); | ||
}); | ||
describe("Overflow Underflow Throwable", () => { | ||
@@ -262,3 +270,3 @@ it("Should throw when add two numbers 1", () => { | ||
!(new u128(2) ** 128); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -269,3 +277,3 @@ | ||
!(new u128(3) ** 81); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -276,3 +284,3 @@ | ||
!(new u128(3) ** 120); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -283,3 +291,3 @@ | ||
!(new u128(4) ** 64); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -290,3 +298,3 @@ | ||
!(new u128(4) ** 120); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -297,3 +305,3 @@ | ||
!(new u128(5) ** 56); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -304,3 +312,3 @@ | ||
!(new u128(5) ** 60); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -311,3 +319,3 @@ | ||
!(new u128(6) ** 50); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -318,3 +326,3 @@ | ||
!(new u128(7) ** 49); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -325,3 +333,3 @@ | ||
!(new u128(8) ** 43); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -332,3 +340,3 @@ | ||
!(new u128(9) ** 41); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -339,3 +347,3 @@ | ||
!(new u128(10) ** 39); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -346,3 +354,3 @@ | ||
!(new u128(11) ** 38); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -353,3 +361,3 @@ | ||
!(new u128(12) ** 36); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -360,3 +368,3 @@ | ||
!(new u128(0, 1) ** 2); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
@@ -367,4 +375,22 @@ | ||
!(new u128(u64.MAX_VALUE) ** 3); | ||
}).toThrow(); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
it("Should throw power with overflow 17", () => { | ||
expect(() => { | ||
!(new u128(11) ** 38); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
it("Should throw power with overflow 18", () => { | ||
expect(() => { | ||
!(new u128(11) ** 40); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
it("Should throw power with overflow 19", () => { | ||
expect(() => { | ||
!(new u128(9) ** 41); | ||
}).toThrow("Overflow during exponentiation"); | ||
}); | ||
}); | ||
@@ -371,0 +397,0 @@ |
@@ -69,2 +69,10 @@ import { u128 } from '../../assembly/integer/u128'; | ||
it("Should convert from decimal string with leading zeros", () => { | ||
expect(u128.from('01')).toStrictEqual(u128.One); | ||
}); | ||
it("Should convert from decimal string with leading zeros and plus", () => { | ||
expect(u128.from('+0001')).toStrictEqual(u128.One); | ||
}); | ||
it("Should convert from decimal with invalid chars string 1", () => { | ||
@@ -71,0 +79,0 @@ expect(u128.from('00000123abc')).toStrictEqual(new u128(123)); |
@@ -6,3 +6,3 @@ import { CharCode } from "util/string"; | ||
// @ts-ignore: decorator | ||
@lazy const MaxBaseForExponent128: u64[] = [ | ||
@lazy const MaxBaseForExponent128 = memory.data<u64>([ | ||
u64.MAX_VALUE, // 0 | ||
@@ -47,7 +47,7 @@ u64.MAX_VALUE, // 1 | ||
0x000000000000000A, // 38 | ||
]; | ||
]); | ||
// Use LUT wrapped by function for lazy compilation | ||
// @ts-ignore: decorator | ||
@lazy const RadixCharsTable: u8[] = [ | ||
@lazy const RadixCharsTable = memory.data<u8>([ | ||
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 36, 36, 36, 36, 36, 36, | ||
@@ -58,23 +58,30 @@ 36, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, | ||
25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35 | ||
]; | ||
]); | ||
@inline | ||
export function isPowerOverflow128(base: u128, exponent: i32): bool { | ||
if (!(exponent > 1 && base > u128.One)) return false; | ||
if (base.hi != 0 || exponent >= 128) return true; | ||
// @ts-ignore: decorator | ||
@inline export function isPowerOverflow128(base: u128, exponent: i32): bool { | ||
// never overflow | ||
if (exponent <= 1 || base <= u128.One) { | ||
return false; | ||
} | ||
// always overflow | ||
if (base.hi != 0 || exponent >= 128) { | ||
return true; | ||
} | ||
var low = base.lo; | ||
if (low <= 9) { | ||
if (low <= 10) { | ||
switch (<i32>low) { | ||
case 2: return exponent > 127; | ||
case 3: return exponent > 80; | ||
case 4: return exponent > 63; | ||
case 5: return exponent > 55; | ||
case 6: return exponent > 49; | ||
case 7: return exponent > 45; | ||
case 8: return exponent > 42; | ||
case 9: return exponent > 40; | ||
case 2: return exponent > 127; | ||
case 3: return exponent > 80; | ||
case 4: return exponent > 63; | ||
case 5: return exponent > 55; | ||
case 6: return exponent > 49; | ||
case 7: return exponent > 45; | ||
case 8: return exponent > 42; | ||
case 9: return exponent > 40; | ||
case 10: return exponent > 38; | ||
} | ||
} | ||
return low > MaxBaseForExponent128[exponent]; | ||
if (exponent >= 38) return true; | ||
return low > load<u64>(MaxBaseForExponent128 + (exponent << 3)); | ||
} | ||
@@ -151,12 +158,15 @@ | ||
// @ts-ignore | ||
var index = <i32>(isNeg | (first == CharCode.PLUS)); | ||
var index = i32(isNeg | (first == CharCode.PLUS)); | ||
if (str.charCodeAt(index) == CharCode._0) { | ||
let second = str.charCodeAt(++index); | ||
if (second == CharCode.x || second == CharCode.X) { | ||
if ((second | 32) == CharCode.x) { | ||
radix = 16; ++index; | ||
} else if (second == CharCode.o || second == CharCode.O) { | ||
} else if ((second | 32) == CharCode.o) { | ||
radix = 8; ++index; | ||
} else if (second == CharCode.b || second == CharCode.B) { | ||
} else if ((second | 32) == CharCode.b) { | ||
radix = 2; ++index; | ||
} else if (second == CharCode._0) { | ||
// skip leading zeros | ||
while (index < len && str.charCodeAt(index) == CharCode._0) ++index; | ||
} | ||
@@ -167,2 +177,4 @@ } | ||
if (index >= len) return result; | ||
if (ASC_SHRINK_LEVEL >= 1) { | ||
@@ -174,3 +186,3 @@ let radix128 = u128.fromU64(radix); | ||
let num = unchecked(table[n]); | ||
let num = load<u8>(table + n); | ||
if (num >= <u8>radix) break; | ||
@@ -212,3 +224,3 @@ | ||
let num = unchecked(table[n]); | ||
let num = load<u8>(table + n); | ||
if (num >= 16) break; | ||
@@ -229,3 +241,3 @@ | ||
let num = unchecked(table[n]); | ||
let num = load<u8>(table + n); | ||
if (num >= <u8>radix) break; | ||
@@ -232,0 +244,0 @@ |
{ | ||
"name": "as-bignum", | ||
"version": "0.2.20", | ||
"version": "0.2.21", | ||
"description": "128 and 256 bits integer and fixed point arithmetics for AssemblyScript. Also support checking overflow/underflow", | ||
@@ -5,0 +5,0 @@ "main": "js/index.js", |
951520
4557