-
Notifications
You must be signed in to change notification settings - Fork 242
/
Copy pathecdhp.c
218 lines (172 loc) · 7.64 KB
/
ecdhp.c
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
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
/*
Example Elliptic Curve Diffie-Hellman program for 32-bit constrained environments. Uses point compression.
Stack-only memory allocation
Use with this mirdef.h header (for a PC using MS C)
#define MR_LITTLE_ENDIAN
#define MIRACL 32
#define mr_utype int
#define MR_IBITS 32
#define MR_LBITS 32
#define mr_unsign32 unsigned int
#define mr_dltype __int64
#define mr_unsign64 unsigned __int64
#define MR_STATIC 6
#define MR_ALWAYS_BINARY
#define MR_STRIPPED_DOWN
#define MR_GENERIC_MT
#define MAXBASE ((mr_small)1<<(MIRACL-1))
#define MR_BITSINCHAR 8
#define MR_COMBA 6
#define MR_GENERALIZED_MERSENNE
#define MR_SPECIAL
#define MR_SIMPLE_BASE
#define MR_SIMPLE_IO
In an embedded environment perhaps these should be defined as well..
#define MR_NO_STANDARD_IO
#define MR_NO_FILE_IO
Build the library from these modules (Example using MS C compiler)
mex 6 ms86 mrcomba
rem (mex 6 sse2 mrcomba) will be faster on most PCs that support SSE2
cl /c /O2 /W3 mrcore.c
cl /c /O2 /W3 mrarth0.c
cl /c /O2 /W3 mrarth1.c
cl /c /O2 /W3 mrio1.c
cl /c /O2 /W3 mrbits.c
cl /c /O2 /W3 mrcurve.c
cl /c /O2 /W3 mrsroot.c
cl /c /O2 /W3 mrjack.c
cl /c /O2 /W3 mrlucas.c
cl /c /O2 /W3 mrarth2.c
cl /c /O2 /W3 mrmonty.c
cl /c /O2 /W3 mrcomba.c
cl /c /O2 /W3 mrxgcd.c
cl /c /O2 /W3 mrmuldv.c
cl /c /O2 /W3 mrebrick.c
rem
rem Create library 'miracl.lib'
del miracl.lib
lib /OUT:miracl.lib mrio1.obj mrmonty.obj mrcomba.obj mrxgcd.obj mrmuldv.obj
lib /OUT:miracl.lib miracl.lib mrbits.obj mrarth2.obj mrlucas.obj mrjack.obj
lib /OUT:miracl.lib miracl.lib mrarth0.obj mrarth1.obj mrcore.obj mrebrick.obj
lib /OUT:miracl.lib miracl.lib mrcurve.obj mrsroot.obj
del mr*.obj
rem Create the program
cl /O2 ecdhp.c miracl.lib
*/
#include <stdio.h>
#include <string.h>
#include "miracl.h"
/* !!!!!! THIS CODE AND THESE ROMS ARE NOW CREATED AUTOMATICALLY USING THE ROMAKER.C APPLICATION !!!!!!!! */
/* !!!!!! READ COMMENTS IN ROMAKER.C !!!!!! */
#define HEXDIGS (MIRACL/4)
#define CURVE_BITS 192
/* NIST p192 bit elliptic curve Y^2=X^3-3X+B (from secp192.ecs).
Here is stored P, B, the group order q, and the generator G(x,y) */
static const mr_small rom[]=
{0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFE,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,
0xC146B9B1,0xFEB8DEEC,0x72243049,0x0FA7E9AB,0xE59C80E7,0x64210519,
0xB4D22831,0x146BC9B1,0x99DEF836,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,
0x82FF1012,0xF4FF0AFD,0x43A18800,0x7CBF20EB,0xB03090F6,0x188DA80E,
0x1E794811,0x73F977A1,0x6B24CDD5,0x631011ED,0xFFC8DA78,0x07192B95};
#define WINDOW 4
/* 32 precomputed points based on fixed generator G(x,y) */
/* (created using romaker.c program with window size of 4) */
/* These values are only correct if MR_SPECIAL is defined! */
static const mr_small prom[]=
{0x0,0x0,0x0,0x0,0x0,0x0,
0x0,0x0,0x0,0x0,0x0,0x0,
0x82ff1012,0xf4ff0afd,0x43a18800,0x7cbf20eb,0xb03090f6,0x188da80e,
0x1e794811,0x73f977a1,0x6b24cdd5,0x631011ed,0xffc8da78,0x7192b95,
0x5d7c48d8,0xc39649c5,0x5a927c35,0xeb2cdfae,0xcba671fb,0x67e30cbd,
0xecbfbe7d,0x7a83cee1,0x6301577,0xce32d03c,0x5810f5c3,0xa93549c4,
0x66e3ead3,0x6f5ef889,0xdfc9bf1a,0xf29e6fea,0x452006e0,0xce216bb8,
0x927b3779,0x46b9092d,0xb5b80a20,0x1d0aeb4b,0x5aaec958,0xd98a2ee2,
0xc0a1e340,0xb19963d8,0x80d1090b,0x4730d4f4,0x184ac737,0x51a581d9,
0xe69912a5,0xecc56731,0x2f683f16,0x7cdfcea0,0xe0bb9f6e,0x5bd81ee2,
0xd4f43374,0xe4b15a2d,0xf292c341,0x757eea7,0xd0f8dc24,0xc730691,
0xbbf45e00,0xdf797890,0xe9de8708,0x8a9e83,0x9354de3e,0x31b24c31,
0xddf63aba,0xcb5ec043,0xf84f41e1,0xc94c21d9,0x61d24416,0xf0f40883,
0x406495f7,0xf37585b0,0x16bcd0ca,0xe5de3b5b,0xe13ea488,0x27853c1a,
0x8e8ae68f,0xd074232a,0xee29f7a9,0x749e528e,0x9716469f,0x611dea3,
0xd8043cc,0x66b867dd,0x3a727de6,0x6a654654,0x8338bdc9,0xf9546052,
0xc5d8f50,0xb6eb7193,0xb904b596,0x1c245c02,0x951f7513,0x4bc1f71,
0xbe34803d,0xa4d0916e,0x8c21962a,0x8bec948a,0xfd69f8d0,0x150096e7,
0xe71aac0c,0xbd44ffe8,0x4322d065,0x7d69a0b0,0xeca3ba2a,0x9f56d96c,
0x25a59dce,0xee59f0d1,0xc3f4575a,0x837d62dd,0x35de73d9,0xa4e07fb3,
0x1cf46ae2,0xec76760c,0xa33d44b0,0xff549832,0xf3185c11,0xe95ad210,
0x38ed372e,0x273e5ec5,0xb0ab1169,0x51d39136,0x8f3a27c8,0xa5ea86f6,
0x74d2d7d5,0x291237ea,0x56338e9b,0x953636ee,0x285c120c,0xda65e86,
0xf13c3233,0x1302f04c,0x978391b2,0xfc898ab9,0x3aa06272,0x26d65c2e,
0x18c5efe6,0xd50947a8,0xfe113c6c,0x45db23ae,0xe5bbe86d,0x91f199f2,
0x60fec064,0x376881b6,0x475daea4,0x387343e9,0xac8d8a19,0xeccd57e8,
0x5b510228,0xc9fef5b9,0x192ebcd6,0x374c0a4c,0xce6a83f9,0x2298f204,
0xf4c574d0,0x46e4b820,0xefeb2cc0,0x6d58644,0x10c3c949,0xe713a400,
0x2d64eedf,0x6178cb0e,0xb85e1f99,0x27af7d5e,0x6cb7be1f,0xd873ced7,
0x52a67f9c,0xefc9129c,0x6004d9ad,0xa3d7b957,0xdc41f8e2,0xfc599808,
0x7fdf928a,0xbb6c6b59,0xd7f93bf4,0xad167ef0,0x154e061c,0xfaa9e432,
0xd52c8f3f,0xc3d0d63,0xd5f7e08f,0x6101b2be,0xd6ae3cf3,0xd877cddd};
#define WORDS 6 /* Number of words per big variable 6*32 = 192 */
/* Note that in a real application a source of real random numbers would be required, to
replace those generated by MIRACL's internal pseudo-random generator "bigbits"
Alternatively from a truly random and unguessable seed, use MIRACL's strong random
number generator */
/* Elliptic Curve Diffie-Hellman, using point compression to minimize bandwidth,
and precomputation to speed up off-line calculation */
int main()
{
int promptr;
epoint *PB;
big A,B,p,a,b,pa,pb,key;
ebrick binst;
miracl instance; /* create miracl workspace on the stack */
/* Specify base 16 here so that HEX can be read in directly without a base-change */
miracl *mip=mirsys(&instance,WORDS*HEXDIGS,16); /* size of bigs is fixed */
char mem_big[MR_BIG_RESERVE(8)]; /* we need 8 bigs... */
char mem_ecp[MR_ECP_RESERVE(1)]; /* ..and 1 elliptic curve points */
memset(mem_big, 0, MR_BIG_RESERVE(8)); /* clear the memory */
memset(mem_ecp, 0, MR_ECP_RESERVE(1));
A=mirvar_mem(mip, mem_big, 0); /* Initialise big numbers */
B=mirvar_mem(mip, mem_big, 1);
pa=mirvar_mem(mip, mem_big, 2);
pb=mirvar_mem(mip, mem_big, 3);
key=mirvar_mem(mip, mem_big, 4);
a=mirvar_mem(mip, mem_big, 5);
b=mirvar_mem(mip, mem_big, 6);
p=mirvar_mem(mip, mem_big, 7);
PB=epoint_init_mem(mip, mem_ecp, 0); /* initialise Elliptic Curve points */
irand(mip, 3L); /* change parameter for different random numbers */
promptr=0;
init_big_from_rom(p,WORDS,rom,WORDS*5,&promptr); /* Read in prime modulus p from ROM */
init_big_from_rom(B,WORDS,rom,WORDS*5,&promptr); /* Read in curve parameter B from ROM */
/* don't need q or G(x,y) (we have precomputed table from it) */
convert(mip,-3,A); /* set A=-3 */
/* Create precomputation instance from precomputed table in ROM */
ebrick_init(&binst,prom,A,B,p,WINDOW,CURVE_BITS);
/* offline calculations */
bigbits(mip,CURVE_BITS,a); /* A's random number */
mul_brick(mip,&binst,a,pa,pa); /* a*G =(pa,ya) */
bigbits(mip,CURVE_BITS,b); /* B's random number */
mul_brick(mip,&binst,b,pb,pb); /* b*G =(pb,yb) */
/* swap X values of point */
/* online calculations */
ecurve_init(mip,A,B,p,MR_PROJECTIVE);
epoint_set(mip,pb,pb,0,PB); /* decompress PB */
ecurve_mult(mip,a,PB,PB);
epoint_get(mip,PB,key,key);
/* since internal base is HEX, can use otnum instead of cotnum - avoiding a base change */
#ifndef MR_NO_STANDARD_IO
printf("Alice's Key= ");
otnum(mip,key,stdout);
#endif
epoint_set(mip,pa,pa,0,PB); /* decompress PA */
ecurve_mult(mip,b,PB,PB);
epoint_get(mip,PB,key,key);
#ifndef MR_NO_STANDARD_IO
printf("Bob's Key= ");
otnum(mip,key,stdout);
#endif
/* clear the memory */
memset(mem_big, 0, MR_BIG_RESERVE(8));
memset(mem_ecp, 0, MR_ECP_RESERVE(1));
return 0;
}