Deleted Added
full compact
pk.c (102250) pk.c (189092)
1/*-
2 * Copyright (c) 1991, 1993
3 * Dave Safford. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. Neither the name of the University nor the names of its contributors
14 * may be used to endorse or promote products derived from this software
15 * without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
28 *
29 */
30
31#include <sys/cdefs.h>
32
1/*-
2 * Copyright (c) 1991, 1993
3 * Dave Safford. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. Neither the name of the University nor the names of its contributors
14 * may be used to endorse or promote products derived from this software
15 * without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
28 *
29 */
30
31#include <sys/cdefs.h>
32
33__FBSDID("$FreeBSD: head/contrib/telnet/libtelnet/pk.c 102250 2002-08-22 06:19:07Z nsayer $");
33__FBSDID("$FreeBSD: head/contrib/telnet/libtelnet/pk.c 189092 2009-02-26 21:43:15Z ed $");
34
35/* public key routines */
36/* functions:
37 genkeys(char *public, char *secret)
38 common_key(char *secret, char *public, desData *deskey)
39 pk_encode(char *in, *out, DesData *deskey);
40 pk_decode(char *in, *out, DesData *deskey);
41 where
42 char public[HEXKEYBYTES + 1];
43 char secret[HEXKEYBYTES + 1];
44 */
45
46#include <sys/time.h>
47#include <openssl/des.h>
48#include <fcntl.h>
49#include <stdio.h>
50#include <stdlib.h>
51#include <string.h>
52
53#include "mp.h"
54#include "pk.h"
55
56static void adjust(char keyout[HEXKEYBYTES+1], char *keyin);
57
58/*
59 * Choose top 128 bits of the common key to use as our idea key.
60 */
61static void
62extractideakey(MINT *ck, IdeaData *ideakey)
63{
64 MINT *a;
65 MINT *z;
66 short r;
67 int i;
68 short base = (1 << 8);
69 char *k;
70
34
35/* public key routines */
36/* functions:
37 genkeys(char *public, char *secret)
38 common_key(char *secret, char *public, desData *deskey)
39 pk_encode(char *in, *out, DesData *deskey);
40 pk_decode(char *in, *out, DesData *deskey);
41 where
42 char public[HEXKEYBYTES + 1];
43 char secret[HEXKEYBYTES + 1];
44 */
45
46#include <sys/time.h>
47#include <openssl/des.h>
48#include <fcntl.h>
49#include <stdio.h>
50#include <stdlib.h>
51#include <string.h>
52
53#include "mp.h"
54#include "pk.h"
55
56static void adjust(char keyout[HEXKEYBYTES+1], char *keyin);
57
58/*
59 * Choose top 128 bits of the common key to use as our idea key.
60 */
61static void
62extractideakey(MINT *ck, IdeaData *ideakey)
63{
64 MINT *a;
65 MINT *z;
66 short r;
67 int i;
68 short base = (1 << 8);
69 char *k;
70
71 z = itom(0);
72 a = itom(0);
73 madd(ck, z, a);
71 z = mp_itom(0);
72 a = mp_itom(0);
73 mp_madd(ck, z, a);
74 for (i = 0; i < ((KEYSIZE - 128) / 8); i++) {
74 for (i = 0; i < ((KEYSIZE - 128) / 8); i++) {
75 sdiv(a, base, a, &r);
75 mp_sdiv(a, base, a, &r);
76 }
77 k = (char *)ideakey;
78 for (i = 0; i < 16; i++) {
76 }
77 k = (char *)ideakey;
78 for (i = 0; i < 16; i++) {
79 sdiv(a, base, a, &r);
79 mp_sdiv(a, base, a, &r);
80 *k++ = r;
81 }
80 *k++ = r;
81 }
82 mfree(z);
83 mfree(a);
82 mp_mfree(z);
83 mp_mfree(a);
84}
85
86/*
87 * Choose middle 64 bits of the common key to use as our des key, possibly
88 * overwriting the lower order bits by setting parity.
89 */
90static void
91extractdeskey(MINT *ck, DesData *deskey)
92{
93 MINT *a;
94 MINT *z;
95 short r;
96 int i;
97 short base = (1 << 8);
98 char *k;
99
84}
85
86/*
87 * Choose middle 64 bits of the common key to use as our des key, possibly
88 * overwriting the lower order bits by setting parity.
89 */
90static void
91extractdeskey(MINT *ck, DesData *deskey)
92{
93 MINT *a;
94 MINT *z;
95 short r;
96 int i;
97 short base = (1 << 8);
98 char *k;
99
100 z = itom(0);
101 a = itom(0);
102 madd(ck, z, a);
100 z = mp_itom(0);
101 a = mp_itom(0);
102 mp_madd(ck, z, a);
103 for (i = 0; i < ((KEYSIZE - 64) / 2) / 8; i++) {
103 for (i = 0; i < ((KEYSIZE - 64) / 2) / 8; i++) {
104 sdiv(a, base, a, &r);
104 mp_sdiv(a, base, a, &r);
105 }
106 k = (char *)deskey;
107 for (i = 0; i < 8; i++) {
105 }
106 k = (char *)deskey;
107 for (i = 0; i < 8; i++) {
108 sdiv(a, base, a, &r);
108 mp_sdiv(a, base, a, &r);
109 *k++ = r;
110 }
109 *k++ = r;
110 }
111 mfree(z);
112 mfree(a);
111 mp_mfree(z);
112 mp_mfree(a);
113}
114
115/*
116 * get common key from my secret key and his public key
117 */
118void
119common_key(char *xsecret, char *xpublic, IdeaData *ideakey, DesData *deskey)
120{
121 MINT *public;
122 MINT *secret;
123 MINT *common;
113}
114
115/*
116 * get common key from my secret key and his public key
117 */
118void
119common_key(char *xsecret, char *xpublic, IdeaData *ideakey, DesData *deskey)
120{
121 MINT *public;
122 MINT *secret;
123 MINT *common;
124 MINT *modulus = xtom(HEXMODULUS);
124 MINT *modulus = mp_xtom(HEXMODULUS);
125
125
126 public = xtom(xpublic);
127 secret = xtom(xsecret);
128 common = itom(0);
129 pow(public, secret, modulus, common);
126 public = mp_xtom(xpublic);
127 secret = mp_xtom(xsecret);
128 common = mp_itom(0);
129 mp_pow(public, secret, modulus, common);
130 extractdeskey(common, deskey);
131 extractideakey(common, ideakey);
132 des_set_odd_parity(deskey);
130 extractdeskey(common, deskey);
131 extractideakey(common, ideakey);
132 des_set_odd_parity(deskey);
133 mfree(common);
134 mfree(secret);
135 mfree(public);
136 mfree(modulus);
133 mp_mfree(common);
134 mp_mfree(secret);
135 mp_mfree(public);
136 mp_mfree(modulus);
137}
138
139/*
140 * Generate a seed
141 */
142static void
143getseed(char *seed, int seedsize)
144{
145 int i;
146
147 srandomdev();
148 for (i = 0; i < seedsize; i++) {
149 seed[i] = random() & 0xff;
150 }
151}
152
153/*
154 * Generate a random public/secret key pair
155 */
156void
157genkeys(char *public, char *secret)
158{
159 size_t i;
160
161# define BASEBITS (8*sizeof(short) - 1)
162# define BASE (1 << BASEBITS)
163
137}
138
139/*
140 * Generate a seed
141 */
142static void
143getseed(char *seed, int seedsize)
144{
145 int i;
146
147 srandomdev();
148 for (i = 0; i < seedsize; i++) {
149 seed[i] = random() & 0xff;
150 }
151}
152
153/*
154 * Generate a random public/secret key pair
155 */
156void
157genkeys(char *public, char *secret)
158{
159 size_t i;
160
161# define BASEBITS (8*sizeof(short) - 1)
162# define BASE (1 << BASEBITS)
163
164 MINT *pk = itom(0);
165 MINT *sk = itom(0);
164 MINT *pk = mp_itom(0);
165 MINT *sk = mp_itom(0);
166 MINT *tmp;
166 MINT *tmp;
167 MINT *base = itom(BASE);
168 MINT *root = itom(PROOT);
169 MINT *modulus = xtom(HEXMODULUS);
167 MINT *base = mp_itom(BASE);
168 MINT *root = mp_itom(PROOT);
169 MINT *modulus = mp_xtom(HEXMODULUS);
170 short r;
171 unsigned short seed[KEYSIZE/BASEBITS + 1];
172 char *xkey;
173
174 getseed((char *)seed, sizeof(seed));
175 for (i = 0; i < KEYSIZE/BASEBITS + 1; i++) {
176 r = seed[i] % BASE;
170 short r;
171 unsigned short seed[KEYSIZE/BASEBITS + 1];
172 char *xkey;
173
174 getseed((char *)seed, sizeof(seed));
175 for (i = 0; i < KEYSIZE/BASEBITS + 1; i++) {
176 r = seed[i] % BASE;
177 tmp = itom(r);
178 mult(sk, base, sk);
179 madd(sk, tmp, sk);
180 mfree(tmp);
177 tmp = mp_itom(r);
178 mp_mult(sk, base, sk);
179 mp_madd(sk, tmp, sk);
180 mp_mfree(tmp);
181 }
181 }
182 tmp = itom(0);
183 mdiv(sk, modulus, tmp, sk);
184 mfree(tmp);
185 pow(root, sk, modulus, pk);
186 xkey = mtox(sk);
182 tmp = mp_itom(0);
183 mp_mdiv(sk, modulus, tmp, sk);
184 mp_mfree(tmp);
185 mp_pow(root, sk, modulus, pk);
186 xkey = mp_mtox(sk);
187 adjust(secret, xkey);
187 adjust(secret, xkey);
188 xkey = mtox(pk);
188 xkey = mp_mtox(pk);
189 adjust(public, xkey);
189 adjust(public, xkey);
190 mfree(sk);
191 mfree(base);
192 mfree(pk);
193 mfree(root);
194 mfree(modulus);
190 mp_mfree(sk);
191 mp_mfree(base);
192 mp_mfree(pk);
193 mp_mfree(root);
194 mp_mfree(modulus);
195}
196
197/*
198 * Adjust the input key so that it is 0-filled on the left
199 */
200static void
201adjust(char keyout[HEXKEYBYTES+1], char *keyin)
202{
203 char *p;
204 char *s;
205
206 for (p = keyin; *p; p++)
207 ;
208 for (s = keyout + HEXKEYBYTES; p >= keyin; p--, s--) {
209 *s = *p;
210 }
211 while (s >= keyout) {
212 *s-- = '0';
213 }
214}
215
216static char hextab[17] = "0123456789ABCDEF";
217
218/* given a DES key, cbc encrypt and translate input to terminated hex */
219void
220pk_encode(char *in, char *out, DesData *key)
221{
222 char buf[256];
223 DesData i;
224 des_key_schedule k;
225 int l,op,deslen;
226
227 memset(&i,0,sizeof(i));
228 memset(buf,0,sizeof(buf));
229 deslen = ((strlen(in) + 7)/8)*8;
230 des_key_sched(key, k);
231 des_cbc_encrypt(in,buf,deslen, k,&i,DES_ENCRYPT);
232 for (l=0,op=0;l<deslen;l++) {
233 out[op++] = hextab[(buf[l] & 0xf0) >> 4];
234 out[op++] = hextab[(buf[l] & 0x0f)];
235 }
236 out[op] = '\0';
237}
238
239/* given a DES key, translate input from hex and decrypt */
240void
241pk_decode(char *in, char *out, DesData *key)
242{
243 char buf[256];
244 DesData i;
245 des_key_schedule k;
246 int n1,n2,op;
247 size_t l;
248
249 memset(&i,0,sizeof(i));
250 memset(buf,0,sizeof(buf));
251 for (l=0,op=0;l<strlen(in)/2;l++,op+=2) {
252 if (in[op] > '9')
253 n1 = in[op] - 'A' + 10;
254 else
255 n1 = in[op] - '0';
256 if (in[op+1] > '9')
257 n2 = in[op+1] - 'A' + 10;
258 else
259 n2 = in[op+1] - '0';
260 buf[l] = n1*16 +n2;
261 }
262 des_key_sched(key, k);
263 des_cbc_encrypt(buf,out,strlen(in)/2, k,&i,DES_DECRYPT);
264 out[strlen(in)/2] = '\0';
265}
195}
196
197/*
198 * Adjust the input key so that it is 0-filled on the left
199 */
200static void
201adjust(char keyout[HEXKEYBYTES+1], char *keyin)
202{
203 char *p;
204 char *s;
205
206 for (p = keyin; *p; p++)
207 ;
208 for (s = keyout + HEXKEYBYTES; p >= keyin; p--, s--) {
209 *s = *p;
210 }
211 while (s >= keyout) {
212 *s-- = '0';
213 }
214}
215
216static char hextab[17] = "0123456789ABCDEF";
217
218/* given a DES key, cbc encrypt and translate input to terminated hex */
219void
220pk_encode(char *in, char *out, DesData *key)
221{
222 char buf[256];
223 DesData i;
224 des_key_schedule k;
225 int l,op,deslen;
226
227 memset(&i,0,sizeof(i));
228 memset(buf,0,sizeof(buf));
229 deslen = ((strlen(in) + 7)/8)*8;
230 des_key_sched(key, k);
231 des_cbc_encrypt(in,buf,deslen, k,&i,DES_ENCRYPT);
232 for (l=0,op=0;l<deslen;l++) {
233 out[op++] = hextab[(buf[l] & 0xf0) >> 4];
234 out[op++] = hextab[(buf[l] & 0x0f)];
235 }
236 out[op] = '\0';
237}
238
239/* given a DES key, translate input from hex and decrypt */
240void
241pk_decode(char *in, char *out, DesData *key)
242{
243 char buf[256];
244 DesData i;
245 des_key_schedule k;
246 int n1,n2,op;
247 size_t l;
248
249 memset(&i,0,sizeof(i));
250 memset(buf,0,sizeof(buf));
251 for (l=0,op=0;l<strlen(in)/2;l++,op+=2) {
252 if (in[op] > '9')
253 n1 = in[op] - 'A' + 10;
254 else
255 n1 = in[op] - '0';
256 if (in[op+1] > '9')
257 n2 = in[op+1] - 'A' + 10;
258 else
259 n2 = in[op+1] - '0';
260 buf[l] = n1*16 +n2;
261 }
262 des_key_sched(key, k);
263 des_cbc_encrypt(buf,out,strlen(in)/2, k,&i,DES_DECRYPT);
264 out[strlen(in)/2] = '\0';
265}