-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathdriver.py
executable file
·146 lines (141 loc) · 6.35 KB
/
driver.py
1
2
3
4
5
6
7
8
9
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
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
#! /usr/bin/python3
"""
Justin Baum
21 October 2020
driver.py
Driver code for using the Elliptic Curve
"""
import argparse
from sys import exit
from curve import Curve
from point import Point
from utils import factors
def main():
"""
Driver code
"""
# Parser Routine
parser = argparse.ArgumentParser(description=
"""
Elliptic Curves in Jacobian Coordinates
"""
)
# pylint: disable=line-too-long,invalid-name
parser.add_argument("-a", action="store", type=int, help="This is the value a in y^2 = x^3 + ax + b mod m", required=False)
parser.add_argument("-b", action="store", type=int, help="This is the value b in y^2 = x^3 + ax + b mod m", required=False)
parser.add_argument("-m", action="store", type=int, help="This is the value m in y^2 = x^3 + ax + b mod m", required=False)
parser.add_argument("-i", action="store", type=str, help="Input curve, space delimitted a,b,m in a file. File name", required=False)
parser.add_argument("-px", action="store", type=int, help="This is the point value x for the generator", required=False)
parser.add_argument("-py", action="store", type=int, help="This is the point value y for the generator", required=False)
parser.add_argument("-pz", action="store", type=int, help="This is the point value z for the generator", required=False)
parser.add_argument("-o", action="store", type=str, help="This is the path of the output file; stdout is default", required=False)
parser.add_argument("--bv", action="store_true", help="This is verbose brute force", required=False)
parser.add_argument("--brute", action="store_true", help="If the curve does not have order p where p is prime, the shortcut\
is rendered useless, and exhaustive search can be done", required=False)
parser.add_argument("--affine", action="store_true", help="For point generation, this converts all the points to affine(very slow)")
args = parser.parse_args()
x = args.px
y = args.py
z = args.pz
bv = args.bv
brute = args.brute or bv
affine = args.affine
inputfile = args.i
o = args.o if args.o else "/dev/tty"
with open(o, "w") as f:
a = None
b = None
m = None
# Parse Arguments
if inputfile:
try:
with open(inputfile, "r") as inputty:
try:
(a,b,m) = [int(i) for i in inputty.readline().split()]
except _:
f.write("Curve was unparseable\n")
exit(1)
except _:
f.write("File {} is unreadable\n".format(inputfile))
exit(1)
else:
a = args.a
b = args.b
m = args.m
if not(a and b and m):
f.write("No curve selected\n")
exit(1)
curve = Curve(a,b,m)
# Point Routine
# Go through order of point
if x is not None:
# we have a point
z = z if z else 1
point = Point(x,y,z,curve) if y else curve.point_from_x(x)
if isinstance(point, list):
if len(point) == 0:
f.write("This curve {} does not have a point at x = {}\n".format(curve, x))
exit(1)
else:
point = point[0]
if point not in curve:
f.write("This point {} is not on the curve {}\n".format(point, curve))
exit(1)
for (i, kpoint) in enumerate(point.order_multiplication_generator()):
if affine:
kpoint.convert_to_affine()
s = "{}p = {}\n".format(i, kpoint)
f.write(s)
# Curve Routine
else:
count_of_max_points = 0
for (i, point) in enumerate(curve.all_points()):
f.write("{}\n".format(point))
count_of_points = len(curve.points)
f.write("{}\nThe curve\n{}\nhas {} affine points:\n".format("-"*80, curve, count_of_points))
if not brute:
f.write("The points with order {}(assuming {} is prime, this is the maximum order of the group) are: \n{}\n".format(count_of_points, count_of_points, "-"*80))
# Lots of redundancy here
for point in curve.all_points():
if not point.infinity:
opposite_point = point * (count_of_points - 1)
if not opposite_point.infinity:
opposite_point.convert_to_affine()
if opposite_point.x == point.x:
if (opposite_point + point).infinity:
count_of_max_points += 1
f.write("{}\n".format(point, count_of_points))
f.write("{}\nThere are {} points with order {}\n".format("-"*80, count_of_max_points, count_of_points))
else:
# Brute force
max_order = 0
max_points = []
for point in curve.all_points():
if point.infinity:
continue
if bv:
f.write("The order for the point {} on curve {}\n{}\n".format(point, curve, "-"*80))
exponentiation = point.copy()
i = 0
if bv:
f.write("{}p = {}\n".format(i, Point.infinity()))
while not exponentiation.infinity:
i += 1
if bv:
f.write("{}p = {}\n".format(i, exponentiation))
exponentiation += point
if bv:
f.write("{}p = {}\n".format(i+1, exponentiation))
if i > max_order:
max_points = [point]
max_order = i
elif i == max_order:
max_points.append(point)
f.write("The points with max order {} are\n{}\n".format(max_order, "-"*80))
total_count = 0
for point in max_points:
f.write("{}\n".format(point))
total_count += 1
f.write("In total there are {} points with max order {}\n".format(total_count, count_of_points))
if __name__ == "__main__":
main()