kryptools 1.9.4__tar.gz → 1.9.5__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {kryptools-1.9.4 → kryptools-1.9.5}/PKG-INFO +1 -1
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/Zmod.py +16 -2
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/__init__.py +1 -1
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/dlp_rho.py +5 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_rho.py +1 -1
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/poly.py +6 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools.egg-info/PKG-INFO +1 -1
- {kryptools-1.9.4 → kryptools-1.9.5}/pyproject.toml +1 -1
- {kryptools-1.9.4 → kryptools-1.9.5}/LICENSE +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/README.md +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/GF2.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/aes.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/blockcipher.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/code.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/conway_polynomials.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/des.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/dlp.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/dlp_bsgs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/dlp_ic.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/dlp_qs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/ec.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_dix.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_ecm.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_fmt.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_pm1.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/factor_qs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/intfuncs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/keccak.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/la.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/lat.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/lat2.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/nt.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/primes.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools/sha1.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools.egg-info/SOURCES.txt +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools.egg-info/dependency_links.txt +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/kryptools.egg-info/top_level.txt +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/setup.cfg +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_GF2.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_Zmod.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_aes.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_code.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_des.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_dlog.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_ec.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_factor.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_factor_fmt.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_factor_pm1.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_factor_qs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_intfuncs.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_keccak.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_la.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_lat.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_nt.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_poly.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_primes.py +0 -0
- {kryptools-1.9.4 → kryptools-1.9.5}/tests/test_sha1.py +0 -0
|
@@ -2,8 +2,9 @@
|
|
|
2
2
|
Ring of intergers modulo `n`.
|
|
3
3
|
"""
|
|
4
4
|
|
|
5
|
-
from math import gcd
|
|
5
|
+
from math import gcd, floor
|
|
6
6
|
from random import randint
|
|
7
|
+
from fractions import Fraction
|
|
7
8
|
from .factor import factorint
|
|
8
9
|
from .primes import is_prime
|
|
9
10
|
from .nt import sqrt_mod, crt
|
|
@@ -60,6 +61,13 @@ class Zmod:
|
|
|
60
61
|
def __contains__(self, other: "ZmodPoint") -> bool:
|
|
61
62
|
return isinstance(other, ZmodPoint) and self.n == other.ring.n
|
|
62
63
|
|
|
64
|
+
def decompress(self, x: int, d: int) -> "ZmodPoint":
|
|
65
|
+
"Decompress an integer `x` with at most `d` bits to Z_n."
|
|
66
|
+
if not isinstance(d, int) or d <= 0 or d >= self.n.bit_length():
|
|
67
|
+
raise ValueError("The number of bits must be between 1 and the bit length of the modulus.")
|
|
68
|
+
x %= 2**d
|
|
69
|
+
return ZmodPoint( floor(Fraction(x * self.n, 2**d) + Fraction(1, 2) ), self)
|
|
70
|
+
|
|
63
71
|
def random(self, num: int = 0) -> "ZmodPoint":
|
|
64
72
|
"Return a single random point or a list of random points."
|
|
65
73
|
if num:
|
|
@@ -255,8 +263,14 @@ class ZmodPoint:
|
|
|
255
263
|
return self.x
|
|
256
264
|
return self.ring.n - self.x
|
|
257
265
|
|
|
266
|
+
def compress(self, d: int) -> list:
|
|
267
|
+
"Returns the value compressed to `d` bits."
|
|
268
|
+
if not isinstance(d, int) or d <= 0 or d > self.ring.n.bit_length():
|
|
269
|
+
raise ValueError("The number of bits must be between 1 and the bit length of the modulus.")
|
|
270
|
+
return floor(Fraction(self.x * 2**d, self.ring.n) + Fraction(1, 2) ) % 2**d
|
|
271
|
+
|
|
258
272
|
def bits(self) -> list:
|
|
259
|
-
"
|
|
273
|
+
"Returns a list of bits."
|
|
260
274
|
return [int(d) for d in str(format(self.x, "0" + str(int.bit_length(self.ring.n - 1)) + "b"))]
|
|
261
275
|
|
|
262
276
|
def sharp(self):
|
|
@@ -5,7 +5,7 @@ Implemenation of same basic algorithms used in cryptography.
|
|
|
5
5
|
__author__ = "Gerald Teschl"
|
|
6
6
|
__copyright__ = "Copyright 2024-2026, Gerald Teschl"
|
|
7
7
|
__license__ = "MIT License"
|
|
8
|
-
__version__ = "1.9.
|
|
8
|
+
__version__ = "1.9.5"
|
|
9
9
|
__email__ = "Gerald.Teschl@univie.ac.at"
|
|
10
10
|
|
|
11
11
|
from .nt import egcd, cf, convergents, legendre_symbol, jacobi_symbol, sqrt_mod, euler_phi, carmichael_lambda, moebius_mu, is_carmichael_number, order, crt
|
|
@@ -12,6 +12,11 @@ def dlog_rho(a: int, b: int, n: int, m: int = None, brent=0) -> int:
|
|
|
12
12
|
b %= n
|
|
13
13
|
if not m:
|
|
14
14
|
m = n - 1
|
|
15
|
+
else:
|
|
16
|
+
if pow(a, m, n) != 1:
|
|
17
|
+
raise ValueError("Incorrect order.")
|
|
18
|
+
if pow(b, m, n) != 1:
|
|
19
|
+
raise ValueError("DLP not solvable.")
|
|
15
20
|
trys = 10
|
|
16
21
|
max_iter = 10 * isqrt(m) # stop iterating and try a different start value
|
|
17
22
|
|
|
@@ -9,7 +9,7 @@ from random import randint
|
|
|
9
9
|
def factor_rho(n: int, x: int = 2, maxinit: int = 10, maxiter: int = 1000, brent: bool = True, verbose: int = 0) -> int | None:
|
|
10
10
|
"""Factor `n` using the Pollard's rho method with start value `x`."""
|
|
11
11
|
if not maxiter:
|
|
12
|
-
maxiter =
|
|
12
|
+
maxiter = 3 * isqrt(isqrt(n)) # stop iterating and try a different start value
|
|
13
13
|
|
|
14
14
|
def f(x: int) -> int:
|
|
15
15
|
return (pow(x, 2, n) + 2) % n
|
|
@@ -220,6 +220,12 @@ class Poly:
|
|
|
220
220
|
return self.__class__(list(map(func, self.coeff)), modulus = list(map(func, self.modulus)))
|
|
221
221
|
return self.__class__(list(map(func, self.coeff)), modulus = self.modulus, cyclic = self.cyclic)
|
|
222
222
|
|
|
223
|
+
def compress(self, d: int) -> list:
|
|
224
|
+
"Retun a list of compressed coefficients."
|
|
225
|
+
if not hasattr(self.coeff[0], "compress"):
|
|
226
|
+
raise ValueError("The unerlying ring does not seem to support compression.")
|
|
227
|
+
return [ c.compress(d) for c in self.coeff ]
|
|
228
|
+
|
|
223
229
|
def _check_type(self, other):
|
|
224
230
|
"Check if self and other can be added/multiplied."
|
|
225
231
|
return isinstance(other, int) or (isinstance(other, Number) and isinstance(self.coeff[0], Number)) or type(other) == type(self.coeff[0]) # pylint: disable=C0123
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|