backup
[lcr.git] / crypt.cpp
1 /*****************************************************************************\
2 **                                                                           **
3 ** PBX4Linux                                                                 **
4 **                                                                           **
5 **---------------------------------------------------------------------------**
6 ** Copyright: Andreas Eversberg                                              **
7 **                                                                           **
8 ** cryption stuff                                                            **
9 **                                                                           **
10 \*****************************************************************************/ 
11
12 /* how authentication is performed:
13
14 Alice                                                         Bob
15 -----------------------------------------------------------------
16                          unencrypted call
17 start        *
18              | -----> sending random number -----> (gets lost)
19              |
20              |                                     *        start
21 comparing    | <----- sending random number <----- |
22 master state |                                     |
23              | -----> sending "slave" code  -----> |  slave state
24 calculating  |                                     |
25 rsa key pair |                                     |
26              |                                     |
27 done         | -----> sending public key    -----> |
28              |                                     |     crpyting
29              |                                     |  session key
30              |                                     |
31              | <----- sending session key   <----- |         done
32 decrypting   |                                     | enable crypt
33 dession key  |                                     *         stop
34              |
35 done         |
36 enable crypt |
37 stop         *
38                          encrypted call
39
40 When Bob and Alice activate their authentication process, they will make
41 up a random number.
42
43 Lets assume Alice starts encryption first. She activates the authentication
44 process. Bob hat not activates the process yet. Alice sends a random number
45 to Bob, but he will ignore it, because he is not listening.
46
47 Bob also activates the authentication process, and sends his random number.
48 Now Alice will receive that number and compares the values. If the values
49 are equal, the process will fail and Alice will send the message "LOOPED".
50 If Alice's random number is greater, she will identify herself as "master".
51 Bob will get a "SLAVE" message. Bob might also send a "MASTER" message,
52 if he got Alice's random number, due to parallel activation of the
53 authentication.
54
55 After transmission or reception of a master message, more messages are
56 ignored. After reception of a "RANDOM" message, more messages are
57 ignored. A reception of a "RANDOM" message always causes to identify who
58 is slave.
59
60 Now Alice starts calculating his public/private key pair, because she is
61 "master". When Bob receives the "SLAVE" message, he will change the timeout
62 value. If no random number or "SLAVE", "MASTER" or "LOOPED" is received within
63 a timeout value, the "ABORT" message is sent. If the "ABORT" message is
64 received at any state of the process, the process is aborted.
65
66 After the key of Alices is calculated, she will send it to Bob. Bob will use
67 the key to start encryption of a random session key. Both will change their
68 timeout values.
69
70 After Bob has finished is crypted session key, he will send it to Alice and
71 enable encryption. Bob has finished his process now.
72
73 As soon as Alice received the encrypted key, she will encrypt it and also
74 enable encryption with the same key as Bob. Alis has finished her process now.
75
76 Both will get displayed some of the first digits of the public key. Both can
77 talk about the digits now. A man in the middle cannot change the keys without
78 changing the public key. The voice of Alice and/or Bob is used to "sign" and
79 "check" that the public key is not modified.
80
81 If Alice or Bob wants to stop encryption, one will send the "ABORT" message.
82 After transmission or reception.
83
84
85 The states of the process:
86
87 CM_ST_NULL
88 ----------
89 no encryption
90
91 CM_ST_IDENT
92 -----------
93 Waiting for the remote random number or "MASTER", "SLAVE", "LOOPED" message.
94
95 CM_ST_KEYGEN
96 ------------
97 The master generates the key and waits for the key engine to finish.
98
99 CM_ST_KEYWAIT
100 -------------
101 The slave waits for the master to send the key.
102
103 CM_ST_CSKEY
104 -----------
105 The slave generates the session key and waits for the encryption engine to
106 finish.
107
108 CM_ST_CSWAIT
109 ------------
110 The master waits for the slave to send the crypted session key.
111
112 CM_ST_DSKEY
113 -----------
114 The master waits for the decryption engine to finish decryption of the session
115 key.
116
117 CM_ST_ACTIVE
118 ------------
119 The encryption is established.
120
121
122 Timouts
123 -------
124 CM_TO_IDENT     = waiting for the remote party to enable encryption
125 CM_TO_KEY       = waiting for key generation
126 CM_TO_CSKEY     = waiting for session key encryption
127 CM_TO_DSKEY     = waiting for session key decryption
128
129
130 Structure of message:
131 ---------------------
132
133 one octet message element
134 two octets element length (first octet = high-byte)
135 data as given in length
136
137 last element is 0
138 the message type is encoded as element
139
140
141 */
142
143 #include <stdio.h>
144 #include <string.h>
145 #include <stdlib.h>
146 #include <sys/types.h>
147 #ifdef CRYPTO
148 #include <openssl/rsa.h>
149 #endif
150 #include "main.h"
151
152
153 /* convert key string to binary key vector
154  * returns 0 if an error ocurred
155  */
156 unsigned char *crypt_key(unsigned char *key, int *binary_len)
157 {
158         static unsigned char binary_key[2048];
159         int i = 0;
160
161         binary_key[0] = '\0';
162
163         if (!key[0])
164                 return(NULL);
165
166         /* check for 0xXXXX... type of key */
167         if (!strncmp((char *)key, "0x", 2))
168         {
169                 key+=2;
170                 while(*key)
171                 {
172                         if (i == (int)sizeof(binary_key))
173                                 return(NULL);
174
175                         if (*key>='0' && *key<='9')
176                                 binary_key[i] = (*key-'0') << 8;
177                         else if (*key>='a' && *key<='f')
178                                 binary_key[i] = (*key-'a'+10) << 8;
179                         else if (*key>='A' && *key<='F')
180                                 binary_key[i] = (*key-'A'+10) << 8;
181                         else
182                                 return(NULL);
183                         key++;
184
185                         if (*key>='0' && *key<='9')
186                                 binary_key[i] += (*key - '0');
187                         else if (*key>='a' && *key<='f')
188                                 binary_key[i] += (*key - 'a' + 10);
189                         else if (*key>='A' && *key<='F')
190                                 binary_key[i] += (*key - 'A' + 10);
191                         else
192                                 return(NULL);
193                         key++;
194
195                         i++;
196                 }
197                 *binary_len = i;
198                 return(binary_key);
199         }
200
201         /* ascii key too long */
202         if (strlen((char *)key) >= sizeof((char *)binary_key))
203                 return(NULL);
204
205         memcpy(binary_key, key, strlen((char *)key));
206         *binary_len = strlen((char *)key);
207         return(binary_key);
208 }
209
210 /*
211  * support routine to get cpu speed
212  */
213 static unsigned long get_bogomips(void)
214 {
215         FILE *fp;
216         char buffer[64], *p;
217
218         fp = fopen("/proc/cpuinfo", "r");
219         if (!fp)
220         {
221                 PERROR("Cannot access /proc/cpuinfo. Will not use cpuinfo for identification of pear\n");
222                 return(0);
223         }
224         fduse++;
225         buffer[sizeof(buffer-1)] = '\0';
226         while(fgets(buffer, sizeof(buffer)-1, fp))
227         {
228                 if (!!strncmp(buffer, "bogomips", 8))
229                         continue;
230                 if (!strchr(buffer, ':'))
231                         continue;
232                 p = strchr(buffer, ':')+1;
233                 while(*p == ' ')
234                         p++;
235                 if (strchr(p, '.'))
236                         *strchr(p, '.') = '\0';
237                 fclose(fp);
238                 fduse--;
239                 return(atoi(p));
240         }
241         fclose(fp);
242         fduse--;
243         PERROR("Cannot find 'bogomips' in /proc/cpuinfo. Will not use cpuinfo for identification of pear\n");
244         return(0);
245 }
246
247
248 /*
249  * crc 32 stuff
250  */
251 static unsigned long crc_reflect(unsigned long ref, char ch)
252 {
253         unsigned long value = 0;
254         int i;
255
256         i = 1;
257         while(i < ch+1)
258         {
259                 if(ref & 1)
260                         value |= 1 << (ch - i);
261                 ref >>= 1;
262                 i++;
263         }
264         return(value);
265 }
266
267 static unsigned long crc32_table[256];
268 static int crc_initialized = 0;
269
270 void crc_init(void)
271 {
272         unsigned long ulPolynomial = 0x04c11db7;
273         int i, j;
274
275         i = 0;
276         while(i < 256)
277         {
278                 crc32_table[i] = crc_reflect(i, 8) << 24;
279                 j = 0;
280                 while(j < 8)
281                 {
282                         crc32_table[i] = (crc32_table[i] << 1) ^ (crc32_table[i] & (1 << 31) ? ulPolynomial : 0);
283                         j++;
284                 }
285                 crc32_table[i] = crc_reflect(crc32_table[i], 32);
286                 i++;
287         }
288         crc_initialized = 1;
289 }
290
291 unsigned long crc32(unsigned char *data, int len)
292 {
293         unsigned long crc = 0xffffffff;
294
295         if (!crc_initialized)
296                 FATAL("crc not initialized, exitting...");
297
298         while (len--)
299                 crc = (crc >> 8) ^ crc32_table[(crc & 0xFF) ^ *data++];
300         return(crc^0xffffffff);
301 }
302
303
304 CM_ST_NAMES
305
306 /* give name of state */
307 static char *statename(int state)
308 {
309         if (state>=0 && state<cm_st_num)
310                 return(cm_st_name[state]);
311         return("<<STATE UNKNOWN>>");
312 }
313
314 /*
315  * authentication key generation, encryption, decryption
316  */
317 struct auth_args {
318         class EndpointAppPBX *apppbx;
319         int     job;
320 };
321
322 static void *keyengine_child(void *arg)
323 {
324         struct auth_args *args = (struct auth_args *)arg;
325         class EndpointAppPBX *apppbx = args->apppbx;
326         int job = args->job;
327 #ifdef CRYPTO
328         RSA *rsa;
329         int exponent;
330         int i;
331 #endif
332
333         struct sched_param schedp;
334         int ret;
335
336         PDEBUG((DEBUG_EPOINT | DEBUG_CRYPT), "EPOINT(%d) child process started for using libcrypto\n", apppbx->ea_endpoint->ep_serial);
337
338         /* lower priority to keep pbx running fluently */
339         if (options.schedule > 0)
340         {
341                 memset(&schedp, 0, sizeof(schedp));
342                 schedp.sched_priority = 0;
343                 ret = sched_setscheduler(0, SCHED_OTHER, &schedp);
344                 if (ret < 0)
345                 {
346                         PERROR("Scheduling to normal priority failed (errno = %d).\nExitting child process...\n", errno);
347                         goto done;
348                 }
349         }
350
351         switch(job)
352         {
353                 /* generate rsa key pair */
354                 case CK_GENRSA_REQ:
355 #ifndef CRYPTO
356                 PERROR("Not compliled wiht crypto.\n");
357                 apppbx->e_crypt_keyengine_return = -1;
358 #else
359                 srandom(*((unsigned int *)mISDN_rand) ^ random());
360 //              exponent = (((random()<<1)|1) & 0x7f) + 0x80; /* odd */
361                 exponent = 65537;
362 //              if (exponent < 3) exponent = 3; /* >= 3 */
363                 rsa = RSA_generate_key(RSA_BITS, exponent, NULL, NULL);
364                 if (!rsa)
365                 {
366                         PERROR("Failed to generate rsa key pair.\n");
367                         apppbx->e_crypt_keyengine_return = -1;
368                         break;
369                 }
370                 ememuse++;
371                 apppbx->e_crypt_rsa_n_len = BN_num_bytes(rsa->n);
372                 if (apppbx->e_crypt_rsa_n_len > (int)sizeof(apppbx->e_crypt_rsa_n))
373                 {
374                         kerror_buffer:
375                         PERROR("e_crypt_rsa_* too small for bignum.\n");
376                         apppbx->e_crypt_keyengine_return = -1;
377                         RSA_free(rsa);
378                         ememuse--;
379                         break;
380                 }
381                 BN_bn2bin(rsa->n, apppbx->e_crypt_rsa_n);
382                 apppbx->e_crypt_rsa_n_len = BN_num_bytes(rsa->n);
383                 if (apppbx->e_crypt_rsa_e_len > (int)sizeof(apppbx->e_crypt_rsa_e))
384                         goto kerror_buffer;
385                 BN_bn2bin(rsa->e, apppbx->e_crypt_rsa_e);
386                 apppbx->e_crypt_rsa_e_len = BN_num_bytes(rsa->e);
387                 if (apppbx->e_crypt_rsa_d_len > (int)sizeof(apppbx->e_crypt_rsa_d))
388                         goto kerror_buffer;
389                 BN_bn2bin(rsa->d, apppbx->e_crypt_rsa_d);
390                 apppbx->e_crypt_rsa_p_len = BN_num_bytes(rsa->p);
391                 if (apppbx->e_crypt_rsa_p_len > (int)sizeof(apppbx->e_crypt_rsa_p))
392                         goto kerror_buffer;
393                 BN_bn2bin(rsa->p, apppbx->e_crypt_rsa_p);
394                 apppbx->e_crypt_rsa_q_len = BN_num_bytes(rsa->q);
395                 if (apppbx->e_crypt_rsa_q_len > (int)sizeof(apppbx->e_crypt_rsa_q))
396                         goto kerror_buffer;
397                 BN_bn2bin(rsa->q, apppbx->e_crypt_rsa_q);
398                 apppbx->e_crypt_rsa_dmp1_len = BN_num_bytes(rsa->dmp1);
399                 if (apppbx->e_crypt_rsa_dmp1_len > (int)sizeof(apppbx->e_crypt_rsa_dmp1))
400                         goto kerror_buffer;
401                 BN_bn2bin(rsa->dmp1, apppbx->e_crypt_rsa_dmp1);
402                 apppbx->e_crypt_rsa_dmq1_len = BN_num_bytes(rsa->dmq1);
403                 if (apppbx->e_crypt_rsa_dmq1_len > (int)sizeof(apppbx->e_crypt_rsa_dmq1))
404                         goto kerror_buffer;
405                 BN_bn2bin(rsa->dmq1, apppbx->e_crypt_rsa_dmq1);
406                 apppbx->e_crypt_rsa_iqmp_len = BN_num_bytes(rsa->iqmp);
407                 if (apppbx->e_crypt_rsa_iqmp_len > (int)sizeof(apppbx->e_crypt_rsa_iqmp))
408                         goto kerror_buffer;
409                 BN_bn2bin(rsa->iqmp, apppbx->e_crypt_rsa_iqmp);
410                 PDEBUG(DEBUG_CRYPT, "gen: rsa n=%02x...\n", *apppbx->e_crypt_rsa_n);
411                 PDEBUG(DEBUG_CRYPT, "gen: rsa e=%02x...\n", *apppbx->e_crypt_rsa_e);
412                 PDEBUG(DEBUG_CRYPT, "gen: rsa d=%02x...\n", *apppbx->e_crypt_rsa_d);
413                 PDEBUG(DEBUG_CRYPT, "gen: rsa p=%02x...\n", *apppbx->e_crypt_rsa_p);
414                 PDEBUG(DEBUG_CRYPT, "gen: rsa q=%02x...\n", *apppbx->e_crypt_rsa_q);
415                 PDEBUG(DEBUG_CRYPT, "gen: rsa dmp1=%02x...\n", *apppbx->e_crypt_rsa_dmp1);
416                 PDEBUG(DEBUG_CRYPT, "gen: rsa dmq1=%02x...\n", *apppbx->e_crypt_rsa_dmq1);
417                 PDEBUG(DEBUG_CRYPT, "gen: rsa iqmp=%02x...\n", *apppbx->e_crypt_rsa_iqmp);
418                 apppbx->e_crypt_keyengine_return = 1;
419                 RSA_free(rsa);
420                 ememuse--;
421 #endif
422                 break;
423
424                 /* encrypt session key */
425                 case CK_CPTRSA_REQ:
426 #ifndef CRYPTO
427                 PERROR("No crypto lib.\n");
428                 apppbx->e_crypt_keyengine_return = -1;
429 #else
430                 /* generating session key */
431                 srandom(*((unsigned int *)mISDN_rand) ^ random());
432                 i = 0;
433                 while(i < 56)
434                 {
435                         apppbx->e_crypt_key[i] = random();
436                         apppbx->e_crypt_key[i] ^= mISDN_rand[random() & 0xff];
437                         i++;
438                 }
439                 apppbx->e_crypt_key_len = i;
440                 /* encrypt via rsa */
441                 rsa = RSA_new();
442                 if (!rsa)
443                 {
444                         PERROR("Failed to allocate rsa structure.\n");
445                         apppbx->e_crypt_keyengine_return = 1;
446                         break;
447                 }
448                 ememuse++;
449                 rsa->n = BN_new();
450                 rsa->e = BN_new();
451                 if (!rsa->n || !rsa->e)
452                 {
453                         PERROR("Failed to generate rsa structure.\n");
454                         apppbx->e_crypt_keyengine_return = -1;
455                         RSA_free(rsa);
456                         ememuse--;
457                         break;
458                 }
459                 if (!BN_bin2bn(apppbx->e_crypt_rsa_n, apppbx->e_crypt_rsa_n_len, rsa->n))
460                 {
461                         eerror_bin2bn:
462                         PERROR("Failed to convert binary to bignum.\n");
463                         apppbx->e_crypt_keyengine_return = -1;
464                         RSA_free(rsa);
465                         ememuse--;
466                         break;
467                 }
468                 if ((apppbx->e_crypt_rsa_n_len*8) != BN_num_bits(rsa->n))
469                 {
470                         PERROR("SOFTWARE API ERROR: length not equal stored data. (%d != %d)\n", apppbx->e_crypt_rsa_n_len*8, BN_num_bits(rsa->n));
471                         apppbx->e_crypt_keyengine_return = -1;
472                         RSA_free(rsa);
473                         ememuse--;
474                         break;
475                 }
476                 if (!BN_bin2bn(apppbx->e_crypt_rsa_e, apppbx->e_crypt_rsa_e_len, rsa->e))
477                         goto eerror_bin2bn;
478                 PDEBUG(DEBUG_CRYPT, "crypt: rsa n=%02x...\n", *apppbx->e_crypt_rsa_n);
479                 PDEBUG(DEBUG_CRYPT, "crypt: rsa e=%02x...\n", *apppbx->e_crypt_rsa_e);
480                 PDEBUG(DEBUG_CRYPT, "crypt: key =%02x%02x%02x%02x... (len=%d)\n", apppbx->e_crypt_key[0], apppbx->e_crypt_key[1], apppbx->e_crypt_key[2], apppbx->e_crypt_key[3], apppbx->e_crypt_key_len);
481                 apppbx->e_crypt_ckey_len = RSA_public_encrypt(
482                         apppbx->e_crypt_key_len,
483                         apppbx->e_crypt_key,
484                         apppbx->e_crypt_ckey,
485                         rsa,
486                         RSA_PKCS1_PADDING);
487                 PDEBUG(DEBUG_CRYPT, "crypt: ckey =%02x%02x%02x%02x... (len=%d)\n", apppbx->e_crypt_ckey[0], apppbx->e_crypt_ckey[1], apppbx->e_crypt_ckey[2], apppbx->e_crypt_ckey[3], apppbx->e_crypt_ckey_len);
488                 RSA_free(rsa);
489                 ememuse--;
490                 if (apppbx->e_crypt_ckey_len > 0)
491                         apppbx->e_crypt_keyengine_return = 1;
492                 else
493                         apppbx->e_crypt_keyengine_return = -1;
494 #endif
495                 break;
496
497                 /* decrypt session key */
498                 case CK_DECRSA_REQ:
499 #ifndef CRYPTO
500                 PERROR("No crypto lib.\n");
501                 apppbx->e_crypt_keyengine_return = -1;
502 #else
503                 rsa = RSA_new();
504                 if (!rsa)
505                 {
506                         PERROR("Failed to allocate rsa structure.\n");
507                         apppbx->e_crypt_keyengine_return = 1;
508                         break;
509                 }
510                 ememuse++;
511                 rsa->n = BN_new();
512                 rsa->e = BN_new();
513                 rsa->d = BN_new();
514                 rsa->p = BN_new();
515                 rsa->q = BN_new();
516                 rsa->dmp1 = BN_new();
517                 rsa->dmq1 = BN_new();
518                 rsa->iqmp = BN_new();
519                 if (!rsa->n || !rsa->e
520                  || !rsa->d || !rsa->p
521                  || !rsa->q || !rsa->dmp1
522                  || !rsa->dmq1 || !rsa->iqmp)
523                 {
524                         PERROR("Failed to generate rsa structure.\n");
525                         apppbx->e_crypt_keyengine_return = 1;
526                         RSA_free(rsa);
527                         ememuse--;
528                         break;
529                 }
530                 if (!BN_bin2bn(apppbx->e_crypt_rsa_n, apppbx->e_crypt_rsa_n_len, rsa->n))
531                 {
532                         derror_bin2bn:
533                         PERROR("Failed to convert binary to bignum.\n");
534                         apppbx->e_crypt_keyengine_return = -1;
535                         RSA_free(rsa);
536                         ememuse--;
537                         break;
538                 }
539                 if (!BN_bin2bn(apppbx->e_crypt_rsa_e, apppbx->e_crypt_rsa_e_len, rsa->e))
540                         goto derror_bin2bn;
541                 if (!BN_bin2bn(apppbx->e_crypt_rsa_d, apppbx->e_crypt_rsa_d_len, rsa->d))
542                         goto derror_bin2bn;
543                 if (!BN_bin2bn(apppbx->e_crypt_rsa_p, apppbx->e_crypt_rsa_p_len, rsa->p))
544                         goto derror_bin2bn;
545                 if (!BN_bin2bn(apppbx->e_crypt_rsa_q, apppbx->e_crypt_rsa_q_len, rsa->q))
546                         goto derror_bin2bn;
547                 if (!BN_bin2bn(apppbx->e_crypt_rsa_dmp1, apppbx->e_crypt_rsa_dmp1_len, rsa->dmp1))
548                         goto derror_bin2bn;
549                 if (!BN_bin2bn(apppbx->e_crypt_rsa_dmq1, apppbx->e_crypt_rsa_dmq1_len, rsa->dmq1))
550                         goto derror_bin2bn;
551                 if (!BN_bin2bn(apppbx->e_crypt_rsa_iqmp, apppbx->e_crypt_rsa_iqmp_len, rsa->iqmp))
552                         goto derror_bin2bn;
553                 PDEBUG(DEBUG_CRYPT, "decrypt: ckey =%02x%02x%02x%02x... (len=%d)\n", apppbx->e_crypt_ckey[0], apppbx->e_crypt_ckey[1], apppbx->e_crypt_ckey[2], apppbx->e_crypt_ckey[3], apppbx->e_crypt_ckey_len);
554                 apppbx->e_crypt_key_len = RSA_private_decrypt(
555                         apppbx->e_crypt_ckey_len,
556                         apppbx->e_crypt_ckey,
557                         apppbx->e_crypt_key,
558                         rsa,
559                         RSA_PKCS1_PADDING);
560                 PDEBUG(DEBUG_CRYPT, "decrypt: key =%02x%02x%02x%02x... (len=%d)\n", apppbx->e_crypt_key[0], apppbx->e_crypt_key[1], apppbx->e_crypt_key[2], apppbx->e_crypt_key[3], apppbx->e_crypt_key_len);
561                 RSA_free(rsa);
562                 ememuse--;
563                 apppbx->e_crypt_keyengine_return = 1;
564 #endif
565                 break;
566
567                 default:
568                 PERROR("Unknown job %d\n", job);
569                 apppbx->e_crypt_keyengine_return = -1;
570         }
571
572         done:
573         PDEBUG((DEBUG_EPOINT | DEBUG_CRYPT), "child process done after using libcrypto with return value %d\n", apppbx->e_crypt_keyengine_return);
574
575         /* exit process */
576         apppbx->ea_endpoint->ep_use--;
577         FREE(args, sizeof(struct auth_args));
578         amemuse--;
579         return(NULL);
580 }
581
582 void EndpointAppPBX::cryptman_keyengine(int job)
583 {
584         struct auth_args *arg;
585         pthread_t tid;
586
587         if (e_crypt_keyengine_busy)
588         {
589                 e_crypt_keyengine_return = -1;
590                 PERROR("engine currently busy.\n");
591                 return;
592         }
593
594         arg = (struct auth_args *)MALLOC(sizeof(struct auth_args));
595         arg->apppbx = this;
596         arg->job = job;
597         e_crypt_keyengine_return = 0;
598         e_crypt_keyengine_busy = job;
599
600         ea_endpoint->ep_use++;
601         if ((pthread_create(&tid, NULL, keyengine_child, arg)<0))
602         {
603                 ea_endpoint->ep_use--;
604                 PERROR("failed to create keyengine-thread.\n");
605                 e_crypt_keyengine_return = -1;
606                 return;
607         }
608         amemuse++;
609
610         PDEBUG((DEBUG_EPOINT | DEBUG_CRYPT), "send_mail(%d): child process created for doing crypto stuff\n", ea_endpoint->ep_serial);
611
612 }
613
614
615 /* handler for authentication (called by apppbx's handler)
616  */
617 void EndpointAppPBX::cryptman_handler(void)
618 {
619         if (e_crypt_keyengine_busy)
620         {
621                 if (e_crypt_keyengine_return < 0)
622                 {
623                         e_crypt_keyengine_busy = 0;
624                         cryptman_message(CK_ERROR_IND, NULL, 0);
625                 } else
626                 if (e_crypt_keyengine_return > 0)
627                 {
628                         switch(e_crypt_keyengine_busy)
629                         {
630                                 case CK_GENRSA_REQ:
631                                 e_crypt_keyengine_busy = 0;
632                                 cryptman_message(CK_GENRSA_CONF, NULL, 0);
633                                 break;
634                                 case CK_CPTRSA_REQ:
635                                 e_crypt_keyengine_busy = 0;
636                                 cryptman_message(CK_CPTRSA_CONF, NULL, 0);
637                                 break;
638                                 case CK_DECRSA_REQ:
639                                 e_crypt_keyengine_busy = 0;
640                                 cryptman_message(CK_DECRSA_CONF, NULL, 0);
641                                 break;
642                         }
643                 }
644         }
645
646         /* check for event, make next event */
647         if (e_crypt_timeout_sec) if (e_crypt_timeout_sec<now_tv.tv_sec || (e_crypt_timeout_sec==now_tv.tv_sec && e_crypt_timeout_usec<now_tv.tv_usec))
648         {
649                 e_crypt_timeout_sec = 0;
650                 e_crypt_timeout_usec = 0;
651                 cryptman_message(CT_TIMEOUT, NULL, 0);
652         }
653 }
654
655
656 /*
657  * process message to the crypt manager
658  */
659 /* remote peer sends ident request */
660 void EndpointAppPBX::cr_ident(int message, unsigned char *param, int len)
661 {
662         unsigned char buf[4], *p;
663         unsigned long bogomips = 0, ran;
664         int l;
665
666         l = CM_SIZEOFINF(CM_INFO_RANDOM);
667         if (l != 4)
668         {
669                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) missing (or corrupt) random number, ignoring (len = %d)\n", ea_endpoint->ep_serial, l);
670                 return;
671         }
672         p = CM_GETINF(CM_INFO_RANDOM, buf);
673         ran = (p[0]<<24) + (p[1]<<16) + (p[2]<<8) + p[3];
674         l = CM_SIZEOFINF(CM_INFO_BOGOMIPS);
675         if (l != 4)
676         {
677                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) missing (or corrupt) random bogomips, just comparing random (len = %d)\n", ea_endpoint->ep_serial, l);
678                 goto compare_random;
679         }
680         p = CM_GETINF(CM_INFO_BOGOMIPS, buf);
681         bogomips = (p[0]<<24) + (p[1]<<16) + (p[2]<<8) + p[3];
682         if (e_crypt_bogomips > bogomips)
683         {
684                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) our cpu is faster, so we are master (%d > %d)\n", ea_endpoint->ep_serial, e_crypt_bogomips, bogomips);
685                 cr_master(message, NULL, 0);
686                 return;
687         }
688         if (e_crypt_bogomips < bogomips)
689         {
690                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) our cpu is slower, so we are slave (%d < %d)\n", ea_endpoint->ep_serial, e_crypt_bogomips, bogomips);
691                 cr_slave(message, NULL, 0);
692                 return;
693         }
694         PDEBUG(DEBUG_CRYPT, "EPOINT(%d) our cpu is equal speed, so we check for random value (%d == %d)\n", ea_endpoint->ep_serial, e_crypt_bogomips, bogomips);
695         compare_random:
696         /* bogomips are equal, so we compare */
697         if (e_crypt_random > ran)
698         {
699                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) our random value is greater, so we are master (%d > %d)\n", ea_endpoint->ep_serial, e_crypt_random, ran);
700                 cr_master(message, NULL, 0);
701                 return;
702         }
703         if (e_crypt_random < ran)
704         {
705                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) our random value is smaller, so we are slave (%d < %d)\n", ea_endpoint->ep_serial, e_crypt_random, ran);
706                 cr_slave(message, NULL, 0);
707                 return;
708         }
709         PDEBUG(DEBUG_CRYPT, "EPOINT(%d) random values are equal, so we are looped (%d == %d)\n", ea_endpoint->ep_serial, e_crypt_random, ran);
710         cr_looped(message, NULL, 0);
711 }
712
713 /* key-exchange activation by the user */
714 void EndpointAppPBX::cr_activate(int message, unsigned char *param, int len)
715 {
716         unsigned char buf[128] = "";
717         unsigned char msg;
718         unsigned char bogomips[4], ran[4];
719
720         /* activate listener */
721         cryptman_msg2crengine(CR_LISTEN_REQ, NULL, 0);
722         /* send ident message */
723         msg = CMSG_IDENT;
724         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
725         /* random number element */
726         srandom(now_tv.tv_sec ^ now_tv.tv_usec ^ random());
727         e_crypt_random = random();
728         ran[0] = e_crypt_random >> 24;
729         ran[1] = e_crypt_random >> 16;
730         ran[2] = e_crypt_random >> 8;
731         ran[3] = e_crypt_random;
732         CM_ADDINF(CM_INFO_RANDOM, 4, ran);
733         /* cpu speed element */
734         e_crypt_bogomips = get_bogomips();
735         if (e_crypt_bogomips > 0)
736         {
737                 bogomips[0] = e_crypt_bogomips >> 24;
738                 bogomips[1] = e_crypt_bogomips >> 16;
739                 bogomips[2] = e_crypt_bogomips >> 8;
740                 bogomips[3] = e_crypt_bogomips;
741                 CM_ADDINF(CM_INFO_BOGOMIPS, 4, bogomips);
742         }
743         /* send ident message */
744         cryptman_msg2peer(buf);
745         /* change state */
746         cryptman_state(CM_ST_IDENT);
747         /* set timeout */
748         cryptman_timeout(CM_TO_IDENT);
749 }
750
751 /* deactivation by the user */
752 void EndpointAppPBX::cr_deactivate(int message, unsigned char *param, int len)
753 {
754         unsigned char buf[128] = "";
755         unsigned char msg;
756
757         /* deactivate listener (if not already) */
758         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
759         /* message */
760         msg = CMSG_ABORT;
761         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
762         cryptman_msg2peer(buf);
763         /* deactivate encryption */
764         cryptman_msg2crengine(CC_DACT_REQ, NULL, 0);
765         /* change state */
766         cryptman_state(CM_ST_NULL);
767         /* send message to user */
768         cryptman_msg2user(CU_DACT_CONF, "Deactivated");
769 }
770
771 /* remote peer tells us to be master */
772 void EndpointAppPBX::cr_master(int message, unsigned char *param, int len)
773 {
774         unsigned char buf[128] = "";
775         unsigned char msg;
776
777         /* change to master state */
778         cryptman_state(CM_ST_KEYGEN);
779         if (message == CP_IDENT)
780         {
781                 /* send you-are-slave-message */
782                 msg = CMSG_SLAVE;
783                 CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
784                 cryptman_msg2peer(buf);
785         }
786         /* start generation of key */
787         cryptman_keyengine(CK_GENRSA_REQ);
788         /* disable timeout */
789         cryptman_timeout(0);
790         /* send message to user */
791         cryptman_msg2user(CU_INFO_IND, "Master");
792 }
793
794 /* remote peer tells us to be slave */
795 void EndpointAppPBX::cr_slave(int message, unsigned char *param, int len)
796 {
797         unsigned char buf[128] = "";
798         unsigned char msg;
799
800         /* change to slave state */
801         cryptman_state(CM_ST_KEYWAIT);
802         if (message == CP_IDENT)
803         {
804                 /* send you-are-slave-message */
805                 msg = CMSG_MASTER;
806                 /* message */
807                 CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
808                 cryptman_msg2peer(buf);
809         }
810         /* set timeout */
811         cryptman_timeout(CM_TO_PUBKEY);
812         /* send message to user */
813         cryptman_msg2user(CU_INFO_IND, "Slave");
814 }
815
816 /* remote peer tells us about loop */
817 void EndpointAppPBX::cr_looped(int message, unsigned char *param, int len)
818 {
819         unsigned char buf[128] = "";
820         unsigned char msg;
821
822         /* change to idle state */
823         cryptman_state(CM_ST_NULL);
824         /* deactivate listener */
825         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
826         if (message == CP_IDENT)
827         {
828                 /* send looped */
829                 msg = CMSG_LOOPED;
830                 /* message */
831                 CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
832                 cryptman_msg2peer(buf);
833         }
834         /* disable timeout */
835         cryptman_timeout(0);
836         /* send message to user */
837         cryptman_msg2user(CU_ERROR_IND, "Loop Detected");
838 }
839
840 /* abort */
841 void EndpointAppPBX::cr_abort(int message, unsigned char *param, int len)
842 {
843         /* if already encrypting */
844         if (e_crypt_state==CM_ST_WAIT_CRYPT
845          || e_crypt_state==CM_ST_SWAIT
846          || e_crypt_state==CM_ST_ACTIVE)
847         {
848                 /* deactivate blowfish */
849                 cryptman_msg2crengine(CC_DACT_REQ, NULL, 0);
850         }
851         /* change to idle state */
852         cryptman_state(CM_ST_NULL);
853         /* deactivate listener */
854         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
855         /* disable timeout */
856         cryptman_timeout(0);
857         /* send message to user */
858         if (message == CT_TIMEOUT)
859                 cryptman_msg2user(CU_ERROR_IND, "Timeout");
860         else if (message == CP_ABORT)
861                 cryptman_msg2user(CU_ERROR_IND, "Remote Abort");
862         else
863                 cryptman_msg2user(CU_DACT_IND, NULL);
864 }
865
866 /* abort but wait for engine to release*/
867 void EndpointAppPBX::cr_abort_engine(int message, unsigned char *param, int len)
868 {
869         /* change to release state */
870         cryptman_state(CM_ST_RELEASE);
871         /* deactivate listener */
872         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
873         /* disable timeout */
874         cryptman_timeout(0);
875         /* send message to user */
876         if (message == CT_TIMEOUT)
877                 cryptman_msg2user(CU_ERROR_IND, "Timeout");
878         else if (message == CP_ABORT)
879                 cryptman_msg2user(CU_ERROR_IND, "Remote Abort");
880         else
881                 cryptman_msg2user(CU_DACT_IND, NULL);
882 }
883
884 /* abort and disable crypt engine */
885 void EndpointAppPBX::cr_abort_wait(int message, unsigned char *param, int len)
886 {
887         /* change to idle state */
888         cryptman_state(CM_ST_NULL);
889         /* deactivate listener (if not already) */
890         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
891         /* deactivate blowfish */
892         cryptman_msg2crengine(CC_DACT_REQ, NULL, 0);
893         /* disable timeout */
894         cryptman_timeout(0);
895         /* send message to user */
896         if (message == CT_TIMEOUT)
897                 cryptman_msg2user(CU_ERROR_IND, "Timeout");
898         else if (message == CP_ABORT)
899                 cryptman_msg2user(CU_ERROR_IND, "Remote Abort");
900         else
901                 cryptman_msg2user(CU_DACT_IND, NULL);
902 }
903
904 /* key engine tells us that the rsa is ready */
905 void EndpointAppPBX::cr_genrsa(int message, unsigned char *param, int len)
906 {
907         unsigned char buf[1024] = "";
908         unsigned char msg;
909
910         /* change to wait for crypted session key state */
911         cryptman_state(CM_ST_CSWAIT);
912         /* message */
913         msg = CMSG_PUBKEY;
914         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
915         CM_ADDINF(CM_INFO_PUBKEY, e_crypt_rsa_n_len, &e_crypt_rsa_n);
916         CM_ADDINF(CM_INFO_PUBEXPONENT, e_crypt_rsa_e_len, &e_crypt_rsa_e);
917         cryptman_msg2peer(buf);
918         /* set timeout */
919         cryptman_timeout(CM_TO_CSKEY);
920 }
921
922 /* our engine has a key error */
923 void EndpointAppPBX::cr_keyerror(int message, unsigned char *param, int len)
924 {
925         unsigned char buf[128] = "";
926         unsigned char msg;
927
928         /* change to idle state */
929         cryptman_state(CM_ST_NULL);
930         /* deactivate listener */
931         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
932         /* message */
933         msg = CMSG_ABORT;
934         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
935         cryptman_msg2peer(buf);
936         /* send message to user */
937         cryptman_msg2user(CU_ERROR_IND, "Local Key Error");
938 }
939
940 /* remote sends us the rsa public key */
941 void EndpointAppPBX::cr_pubkey(int message, unsigned char *param, int len)
942 {
943         unsigned char buf[128] = "";
944         unsigned char msg = CMSG_ABORT;
945         int l;
946
947         l = CM_SIZEOFINF(CM_INFO_PUBKEY);
948         if (l<1 || l>(int)sizeof(e_crypt_rsa_n))
949         {
950                 size_error:
951                 /* change to idle state */
952                 cryptman_state(CM_ST_NULL);
953                 /* deactivate listener */
954                 cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
955                 /* message */
956                 CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
957                 cryptman_msg2peer(buf);
958                 /* send message to user */
959                 cryptman_msg2user(CU_ERROR_IND, "Remote Key Error");
960                 return;
961         }
962         CM_GETINF(CM_INFO_PUBKEY, e_crypt_rsa_n);
963         e_crypt_rsa_n_len = l;
964         l = CM_SIZEOFINF(CM_INFO_PUBEXPONENT);
965         if (l<1 || l>(int)sizeof(e_crypt_rsa_e))
966                 goto size_error;
967         CM_GETINF(CM_INFO_PUBEXPONENT, e_crypt_rsa_e);
968         e_crypt_rsa_e_len = l;
969         /* change to generating encrypted sessnion key state */
970         cryptman_state(CM_ST_CSKEY);
971         /* start generation of crypted session key */
972         cryptman_keyengine(CK_CPTRSA_REQ);
973         /* disable timeout */
974         cryptman_timeout(0);
975 }
976
977 /* key engine tells us that the crypted session key is ready */
978 void EndpointAppPBX::cr_cptrsa(int message, unsigned char *param, int len)
979 {
980         unsigned char buf[1024] = "";
981         unsigned char msg = CMSG_CSKEY;
982
983         /* change to wait for crypt engine state */
984         cryptman_state(CM_ST_WAIT_DELAY);
985         /* message */
986         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
987         CM_ADDINF(CM_INFO_CSKEY, e_crypt_ckey_len, &e_crypt_ckey);
988         cryptman_msg2peer(buf);
989         /* deactivate listener */
990         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
991         /* timeout 1 sec */
992         cryptman_timeout(1);
993 }
994
995 /* now we waited for the remote to receive and decrypt the session key */
996 void EndpointAppPBX::cr_waitdelay(int message, unsigned char *param, int len)
997 {
998         /* change to wait for crypt engine state */
999         cryptman_state(CM_ST_WAIT_CRYPT);
1000         /* disable timeout */
1001         cryptman_timeout(0);
1002         /* send message to crypt engine */
1003         cryptman_msg2crengine(CC_ACTBF_REQ, e_crypt_key, e_crypt_key_len);
1004 }
1005
1006 /* remote sends us the crypted session key */
1007 void EndpointAppPBX::cr_cskey(int message, unsigned char *param, int len)
1008 {
1009         unsigned char buf[128] = "";
1010         unsigned char msg = CMSG_ABORT;
1011         int l;
1012
1013         /* disable timeout */
1014         cryptman_timeout(0);
1015         l = CM_SIZEOFINF(CM_INFO_CSKEY);
1016         if (l<1 || l>(int)sizeof(e_crypt_ckey))
1017         {
1018                 /* change to idle state */
1019                 cryptman_state(CM_ST_NULL);
1020                 /* deactivate listener */
1021                 cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
1022                 /* message */
1023                 CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
1024                 cryptman_msg2peer(buf);
1025                 /* send message to user */
1026                 cryptman_msg2user(CU_ERROR_IND, "Remote Key Error");
1027                 return;
1028         }
1029         CM_GETINF(CM_INFO_CSKEY, e_crypt_ckey);
1030         e_crypt_ckey_len = l;
1031         /* change to generating decrypted session key state */
1032         cryptman_state(CM_ST_SESSION);
1033         /* start generation of decrypted session key */
1034         cryptman_keyengine(CK_DECRSA_REQ);
1035 }
1036
1037 /* key engine tells us that the decrypted session key is ready */
1038 void EndpointAppPBX::cr_decrsa(int message, unsigned char *param, int len)
1039 {
1040         /* change to wait for crypt engine state */
1041         cryptman_state(CM_ST_WAIT_CRYPT);
1042         /* deactivate listener */
1043         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
1044         /* send message to crypt engine */
1045         cryptman_msg2crengine(CC_ACTBF_REQ, e_crypt_key, e_crypt_key_len);
1046 }
1047
1048 /* blowfish now active */
1049 void EndpointAppPBX::cr_bfactive(int message, unsigned char *param, int len)
1050 {
1051         char text[64];
1052
1053         /* change to active state */
1054         cryptman_state(CM_ST_ACTIVE);
1055         /* send message to user */
1056         SPRINT(text, "PUB %02x%02x %02x%02x %02x%02x %02x%02x", e_crypt_key[0], e_crypt_key[1], e_crypt_key[2], e_crypt_key[3], e_crypt_key[4], e_crypt_key[5], e_crypt_key[6], e_crypt_key[7]);
1057         cryptman_msg2user(CU_ACTK_CONF, text);
1058 }
1059
1060 /* our crypt engine sends an error */
1061 void EndpointAppPBX::cr_crypterror(int message, unsigned char *param, int len)
1062 {
1063         unsigned char buf[128] = "";
1064         unsigned char msg = CMSG_ABORT;
1065
1066         /* change to idle state */
1067         cryptman_state(CM_ST_NULL);
1068         /* deactivate listener */
1069         cryptman_msg2crengine(CR_UNLISTEN_REQ, NULL, 0);
1070         /* message */
1071         CM_ADDINF(CM_INFO_MESSAGE, 1, &msg);
1072         cryptman_msg2peer(buf);
1073         /* send message to user */
1074         cryptman_msg2user(CU_ERROR_IND, "Blowfish Error");
1075 }
1076
1077 /* engine is done, now we are done with release */
1078 void EndpointAppPBX::cr_release(int message, unsigned char *param, int len)
1079 {
1080         /* change to idle state */
1081         cryptman_state(CM_ST_NULL);
1082 }
1083
1084 /* activate using shared key */
1085 void EndpointAppPBX::cr_sactivate(int message, unsigned char *param, int len)
1086 {
1087         /* change to 'wait for crypt engine' state */
1088         cryptman_state(CM_ST_SWAIT);
1089         /* disable timeout */
1090         cryptman_timeout(0);
1091         /* send key to crypt engine */
1092         cryptman_msg2crengine(CC_ACTBF_REQ, param, len);
1093 }
1094
1095 /* share key deactivation by the user */
1096 void EndpointAppPBX::cr_sdeactivate(int message, unsigned char *param, int len)
1097 {
1098         /* deactivate encryption */
1099         cryptman_msg2crengine(CC_DACT_REQ, NULL, 0);
1100         /* change state */
1101         cryptman_state(CM_ST_NULL);
1102         /* send message to user */
1103         cryptman_msg2user(CU_DACT_CONF, NULL);
1104 }
1105
1106 /* shared key abort */
1107 void EndpointAppPBX::cr_sabort(int message, unsigned char *param, int len)
1108 {
1109         /* change to idle state */
1110         cryptman_state(CM_ST_NULL);
1111         /* send message to user */
1112         cryptman_msg2user(CU_DACT_IND, "Deactivated");
1113 }
1114
1115 /* shared key: our crypt engine sends an error */
1116 void EndpointAppPBX::cr_scrypterror(int message, unsigned char *param, int len)
1117 {
1118         /* change to idle state */
1119         cryptman_state(CM_ST_NULL);
1120         /* send message to user */
1121         cryptman_msg2user(CU_ERROR_IND, "Blowfish Error");
1122 }
1123
1124 /* blowfish now active */
1125 void EndpointAppPBX::cr_sbfactive(int message, unsigned char *param, int len)
1126 {
1127         char text[64];
1128
1129         /* change to active state */
1130         cryptman_state(CM_ST_SACTIVE);
1131         /* send message to user */
1132         SPRINT(text, "Call Secure");
1133         cryptman_msg2user(CU_ACTS_CONF, text);
1134 }
1135
1136 /* user requests info */
1137 void EndpointAppPBX::cr_info(int message, unsigned char *param, int len)
1138 {
1139         /* send message to user */
1140         cryptman_msg2user(CU_INFO_CONF, e_crypt_info);
1141 }
1142
1143
1144 CM_MSG_NAMES
1145
1146 void EndpointAppPBX::cryptman_message(int message, unsigned char *param, int len)
1147 {
1148         char *msgtext = "<<UNKNOWN MESSAGE>>";
1149
1150         if (message>=0 && message<cm_msg_num)
1151                 msgtext = cm_msg_name[message];
1152
1153         PDEBUG(DEBUG_CRYPT, "EPOINT(%d) CRYPT MANAGER in state '%s' received message: %s len: %d\n", ea_endpoint->ep_serial, statename(e_crypt_state), msgtext, len);
1154
1155         /* all states */
1156         if (message == CU_INFO_REQ)
1157                 { cr_info(message, param, len); return; }
1158
1159         switch(e_crypt_state)
1160         {
1161                 /* in idle state */
1162                 case CM_ST_NULL:
1163                 if (message == CU_ACTK_REQ) /* request key-exchange encryption */
1164                         { cr_activate(message, param, len); return; }
1165                 if (message == CU_ACTS_REQ) /* request shared encryption */
1166                         { cr_sactivate(message, param, len); return; }
1167                 break;
1168
1169                 /* identifying state */
1170                 case CM_ST_IDENT:
1171                 if (message == CP_IDENT) /* request encryption */
1172                         { cr_ident(message, param, len); return; }
1173                 if (message == CP_SLAVE) /* we are slave */
1174                         { cr_slave(message, param, len); return; }
1175                 if (message == CP_MASTER) /* we are master */
1176                         { cr_master(message, param, len); return; }
1177                 if (message == CP_LOOPED) /* we are looped */
1178                         { cr_looped(message, param, len); return; }
1179                 if (message == CI_DISCONNECT_IND /* request aborting */
1180                  || message == CT_TIMEOUT /* timeout */
1181                  || message == CP_ABORT) /* request aborting */
1182                         { cr_abort(message, param, len); return; }
1183                 break;
1184
1185                 /* generating public key state */
1186                 case CM_ST_KEYGEN:
1187                 if (message == CK_GENRSA_CONF) /* public key is done */
1188                         { cr_genrsa(message, param, len); return; }
1189                 if (message == CK_ERROR_IND) /* key failed */
1190                         { cr_keyerror(message, param, len); return; }
1191                 if (message == CI_DISCONNECT_IND /* request aborting */
1192                  || message == CP_ABORT) /* request aborting */
1193                         { cr_abort_engine(message, param, len); return; }
1194                 break;
1195
1196                 /* waiting for public key state */
1197                 case CM_ST_KEYWAIT:
1198                 if (message == CP_PUBKEY) /* getting public key from remote */
1199                         { cr_pubkey(message, param, len); return; }
1200                 if (message == CI_DISCONNECT_IND /* request aborting */
1201                  || message == CT_TIMEOUT /* timeout */
1202                  || message == CP_ABORT) /* request aborting */
1203                         { cr_abort(message, param, len); return; }
1204                 break;
1205
1206                 /* generating crypted session key state */
1207                 case CM_ST_CSKEY:
1208                 if (message == CK_CPTRSA_CONF) /* crypted session key is done */
1209                         { cr_cptrsa(message, param, len); return; }
1210                 if (message == CK_ERROR_IND) /* key failed */
1211                         { cr_keyerror(message, param, len); return; }
1212                 if (message == CI_DISCONNECT_IND /* request aborting */
1213                  || message == CP_ABORT) /* request aborting */
1214                         { cr_abort_engine(message, param, len); return; }
1215                 break;
1216
1217                 /* waiting for crypted session key state */
1218                 case CM_ST_CSWAIT:
1219                 if (message == CP_CSKEY) /* getting crypted session key from remote */
1220                         { cr_cskey(message, param, len); return; }
1221                 if (message == CI_DISCONNECT_IND /* request aborting */
1222                  || message == CT_TIMEOUT /* timeout */
1223                  || message == CP_ABORT) /* request aborting */
1224                         { cr_abort(message, param, len); return; }
1225                 break;
1226
1227                 /* generating decrypted session key state */
1228                 case CM_ST_SESSION:
1229                 if (message == CK_DECRSA_CONF) /* decrypted is done */
1230                         { cr_decrsa(message, param, len); return; }
1231                 if (message == CK_ERROR_IND) /* key failed */
1232                         { cr_keyerror(message, param, len); return; }
1233                 if (message == CI_DISCONNECT_IND /* request aborting */
1234                  || message == CP_ABORT) /* request aborting */
1235                         { cr_abort_engine(message, param, len); return; }
1236                 break;
1237
1238                 /* wait encryption on state */
1239                 case CM_ST_WAIT_DELAY:
1240                 if (message == CT_TIMEOUT) /* timeout of delay */
1241                         { cr_waitdelay(message, param, len); return; }
1242                 if (message == CC_ERROR_IND) /* encrpytion error */
1243                         { cr_crypterror(message, param, len); return; }
1244                 if (message == CI_DISCONNECT_IND /* request aborting */
1245                  || message == CP_ABORT) /* request aborting */
1246                         { cr_abort_wait(message, param, len); return; }
1247                 break;
1248
1249                 /* wait encryption on state */
1250                 case CM_ST_WAIT_CRYPT:
1251                 if (message == CC_ACTBF_CONF) /* encrpytion active */
1252                         { cr_bfactive(message, param, len); return; }
1253                 if (message == CC_ERROR_IND) /* encrpytion error */
1254                         { cr_crypterror(message, param, len); return; }
1255                 if (message == CI_DISCONNECT_IND /* request aborting */
1256                  || message == CP_ABORT) /* request aborting */
1257                         { cr_abort_wait(message, param, len); return; }
1258                 break;
1259
1260                 /* active state */
1261                 case CM_ST_ACTIVE:
1262                 if (message == CU_DACT_REQ) /* deactivating encryption */
1263                         { cr_deactivate(message, param, len); return; }
1264                 if (message == CI_DISCONNECT_IND /* request aborting */
1265                  || message == CP_ABORT) /* request aborting */
1266                         { cr_abort(message, param, len); return; }
1267                 break;
1268
1269
1270                 /* engine done after abort state */
1271                 case CM_ST_RELEASE:
1272                 if (message == CK_GENRSA_CONF /* engine done */
1273                  || message == CK_CPTRSA_CONF /* engine done */
1274                  || message == CK_DECRSA_CONF /* engine done */
1275                  || message == CK_ERROR_IND) /* engine error */
1276                         { cr_release(message, param, len); return; }
1277                 break;
1278
1279                 /* shared active state */
1280                 case CM_ST_SACTIVE:
1281                 if (message == CU_DACT_REQ) /* deactivating encryption */
1282                         { cr_sdeactivate(message, param, len); return; }
1283                 if (message == CI_DISCONNECT_IND) /* request aborting */
1284                         { cr_sabort(message, param, len); return; }
1285                 break;
1286
1287                 /* wait shared encryption on state */
1288                 case CM_ST_SWAIT:
1289                 if (message == CC_ACTBF_CONF) /* encrpytion active */
1290                         { cr_sbfactive(message, param, len); return; }
1291                 if (message == CC_ERROR_IND) /* encrpytion error */
1292                         { cr_scrypterror(message, param, len); return; }
1293                 if (message == CI_DISCONNECT_IND) /* request aborting */
1294                         { cr_sabort(message, param, len); return; }
1295                 break;
1296
1297         }
1298
1299         PDEBUG(DEBUG_CRYPT, "message not handled in state %d\n", e_crypt_state);
1300 }
1301
1302
1303 /*
1304  * analyze the message element within the received message from peer and call 'cryptman_message'
1305  */
1306 void EndpointAppPBX::cryptman_msg2man(unsigned char *param, int len)
1307 {
1308         unsigned char *p;
1309         unsigned char msg;
1310         int i, l;
1311
1312         /* check if frame is correct */
1313         PDEBUG(DEBUG_CRYPT, "EPOINT(%d) message from peer to crypt_manager.\n", ea_endpoint->ep_serial);
1314         if (len == 0)
1315         {
1316                 PDEBUG(DEBUG_CRYPT, "ignoring message with 0-length.\n");
1317                 return;
1318         }
1319         i = 0;
1320         p = param;
1321         while(*p)
1322         {
1323                 if (i == len)
1324                 {
1325                         PDEBUG(DEBUG_CRYPT, "end of message without 0-termination.\n");
1326                         return;
1327                 }
1328                 if (i+3 > len)
1329                 {
1330                         PDEBUG(DEBUG_CRYPT, "message with element size, outside the frame length.\n");
1331                         return;
1332                 }
1333                 l = (p[1]<<8) + p[2];
1334 //              PDEBUG(DEBUG_CRYPT, "   inf %d (len = %d)\n", *p, l);
1335                 if (i+3+l > len)
1336                 {
1337                         PDEBUG(DEBUG_CRYPT, "message with element data, outside the frame length.\n");
1338                         return;
1339                 }
1340                 i += l + 3;
1341                 p += l + 3;
1342         }
1343         if (i+1 != len)
1344         {
1345                 PDEBUG(DEBUG_CRYPT, "warning: received null-element before end of frame.\n");
1346         }
1347
1348         l = CM_SIZEOFINF(CM_INFO_MESSAGE);
1349         if (l != 1)
1350         {
1351                 PDEBUG(DEBUG_CRYPT, "received message without (valid) message element (len = %d)\n", len);
1352                 return;
1353         }
1354         CM_GETINF(CM_INFO_MESSAGE, &msg);
1355         switch (msg)
1356         {
1357                 case CMSG_IDENT:
1358                 cryptman_message(CP_IDENT, param, len);
1359                 break;
1360                 case CMSG_SLAVE:
1361                 cryptman_message(CP_SLAVE, param, len);
1362                 break;
1363                 case CMSG_MASTER:
1364                 cryptman_message(CP_MASTER, param, len);
1365                 break;
1366                 case CMSG_PUBKEY:
1367                 cryptman_message(CP_PUBKEY, param, len);
1368                 break;
1369                 case CMSG_CSKEY:
1370                 cryptman_message(CP_CSKEY, param, len);
1371                 break;
1372                 case CMSG_ABORT:
1373                 cryptman_message(CP_ABORT, param, len);
1374                 break;
1375                 default:
1376                 PDEBUG(DEBUG_CRYPT, "received unknown message element %d\n", msg);
1377         }
1378 }
1379
1380 /* add information element to buffer
1381  */
1382 void EndpointAppPBX::cryptman_addinf(unsigned char *buf, int buf_size, int element, int len, void *data)
1383 {
1384         int l;
1385
1386         /* skip what we already have in the buffer */
1387         while (buf[0])
1388         {
1389                 l = (buf[1]<<8) + buf[2];
1390                 if (l >= buf_size-3)
1391                 {
1392                         PERROR("EPOINT(%d) buffer overflow while adding information to peer message.\n", ea_endpoint->ep_serial);
1393                         return;
1394                 }
1395                 buf_size -= l + 3;
1396                 buf += l + 3;
1397         }
1398         /* check if we have not enough space to add element including id, len, data, and the null-termination */
1399         if (len+4 > buf_size)
1400         {
1401                 PERROR("EPOINT(%d) cannot add element to message, because buffer would overflow.\n", ea_endpoint->ep_serial);
1402                 return;
1403         }
1404         buf[0] = element;
1405         buf[1] = len >> 8;
1406         buf[2] = len;
1407         memcpy(buf+3, data, len);
1408 }
1409
1410
1411 /* get size of element in buffer
1412  */
1413 int EndpointAppPBX::cryptman_sizeofinf(unsigned char *buf, int element)
1414 {
1415         int l;
1416
1417         /* skip what we already have in the buffer */
1418         while (buf[0])
1419         {
1420                 l = (buf[1]<<8) + buf[2];
1421                 if (buf[0] == element)
1422                         return(l);
1423                 buf += l + 3;
1424         }
1425         return(-1);
1426 }
1427
1428
1429 /* get information element from buffer
1430  */
1431 unsigned char *EndpointAppPBX::cryptman_getinf(unsigned char *buf, int element, unsigned char *to)
1432 {
1433         int l;
1434
1435         /* skip what we already have in the buffer */
1436         while (buf[0])
1437         {
1438                 l = (buf[1]<<8) + buf[2];
1439                 if (buf[0] == element)
1440                 {
1441                         memcpy(to, buf+3, l);
1442                         return(to);
1443                 }
1444                 buf += l + 3;
1445         }
1446         return(NULL);
1447 }
1448
1449
1450 /* send message to peer
1451  */
1452 void EndpointAppPBX::cryptman_msg2peer(unsigned char *buf)
1453 {
1454         struct message *message;
1455         unsigned char *p = buf;
1456         int len = 0;
1457         int l;
1458
1459         /* get len */
1460         while(p[0])
1461         {
1462                 l = (p[1]<<8) + p[2];
1463                 len += l + 3;
1464                 p += l + 3;
1465         }
1466         if (len+1 > (int)sizeof(message->param.crypt.data))
1467         {
1468                 PERROR("EPOINT(%d) message larger than allowed in param->crypt.data.\n", ea_endpoint->ep_serial);
1469                 return;
1470         }
1471         /* send message */
1472         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_CRYPT);
1473         message->param.crypt.type = CR_MESSAGE_REQ;
1474         message->param.crypt.len = len+1;
1475         memcpy(message->param.crypt.data, buf, len+1);
1476         message_put(message);
1477
1478         if (options.deb & DEBUG_CRYPT)
1479         {
1480                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) sending message\n", ea_endpoint->ep_serial);
1481                 p = buf;
1482                 while(p[0])
1483                 {
1484                         l = (p[1]<<8) + p[2];
1485                         PDEBUG(DEBUG_CRYPT, "   inf %d (len = %d)\n", p[0], l);
1486                         len += l + 3;
1487                         p += l + 3;
1488                 }
1489         }
1490 }
1491
1492 /* send message to crypt engine
1493  */
1494 void EndpointAppPBX::cryptman_msg2crengine(int msg, unsigned char *buf, int len)
1495 {
1496         struct message *message;
1497
1498         if (len > (int)sizeof(message->param.crypt.data))
1499         {
1500                 PERROR("EPOINT(%d) message larger than allowed in param->crypt.data.\n", ea_endpoint->ep_serial);
1501                 return;
1502         }
1503         /* send message */
1504         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_CRYPT);
1505         message->param.crypt.type = msg;
1506         message->param.crypt.len = len;
1507         if (len)
1508                 memcpy(message->param.crypt.data, buf, len);
1509         message_put(message);
1510
1511         if (options.deb & DEBUG_CRYPT)
1512         {
1513                 char *msgtext = "<<UNKNOWN MESSAGE>>";
1514
1515                 if (msg>=0 && msg<cm_msg_num)
1516                         msgtext = cm_msg_name[msg];
1517                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) sending message '%s' (len = %d)\n", ea_endpoint->ep_serial, msgtext, len);
1518         }
1519 }
1520
1521 /* send message to user
1522  */
1523 void EndpointAppPBX::cryptman_msg2user(int msg, char *text)
1524 {
1525         struct message *message;
1526         /* send message */
1527         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1528         message->param.crypt.type = msg;
1529         if (!text)
1530                 text = "";
1531         SCPY(e_crypt_info, text);
1532         if (text[0])
1533         {
1534                 UNCPY((char *)message->param.crypt.data, e_crypt_info, sizeof(message->param.crypt.data)-1);
1535                 message->param.crypt.len = strlen((char *)message->param.crypt.data)+1;
1536         }
1537         message_put(message);
1538
1539         if (options.deb & DEBUG_CRYPT)
1540         {
1541                 char *msgtext = "<<UNKNOWN MESSAGE>>";
1542
1543                 if (msg>=0 && msg<cm_msg_num)
1544                         msgtext = cm_msg_name[msg];
1545                 PDEBUG(DEBUG_CRYPT, "EPOINT(%d) sending message '%s' (text = %s)\n", ea_endpoint->ep_serial, msgtext, text?text:"");
1546         }
1547 }
1548
1549 /* change state
1550  */
1551 void EndpointAppPBX::cryptman_state(int state)
1552 {
1553         PDEBUG(DEBUG_CRYPT, "Changing state from %s to %s\n", statename(e_crypt_state), statename(state));
1554         e_crypt_state = state;
1555 }
1556
1557
1558 /* set timeout
1559  */
1560 void EndpointAppPBX::cryptman_timeout(int secs)
1561 {
1562         if (secs)
1563         {
1564                 e_crypt_timeout_sec = now_tv.tv_sec+secs;
1565                 e_crypt_timeout_usec = now_tv.tv_usec;
1566                 PDEBUG(DEBUG_CRYPT, "Changing timeout to %d seconds\n", secs);
1567         } else
1568         {
1569                 e_crypt_timeout_sec = 0;
1570                 e_crypt_timeout_usec = 0;
1571                 PDEBUG(DEBUG_CRYPT, "turning timeout off\n", secs);
1572         }
1573 }
1574
1575 /* encode a message to be sent via b-channel
1576  */
1577 int cryptman_encode_bch(unsigned char *data, int len, unsigned char *buf, int buf_len)
1578 {
1579         unsigned long crc;
1580         int overhead = 18;
1581
1582         len--; /* without null-termination */
1583         if (buf_len < len+overhead)
1584         {
1585                 PERROR("frame too long for buffer");
1586                 return(0);
1587         }
1588         PDEBUG(DEBUG_CRYPT, "encoding a block of %d bytes.\n", len);
1589
1590         /* write identification sequence to the header */
1591         UNCPY((char *)buf, "CRYPTMAN" ,8);
1592         buf += 8;
1593         /* length + checksumme */
1594         buf[0] = len >> 8;
1595         buf[1] = len & 0xff;
1596         crc = crc32(buf, 2);
1597         buf += 2;
1598         buf[0] = crc >> 24;
1599         buf[1] = crc >> 16;
1600         buf[2] = crc >> 8;
1601         buf[3] = crc;
1602         buf += 4;
1603         /* data + checksumme */
1604         memcpy(buf, data, len);
1605         crc = crc32(buf, len);
1606         buf += len;
1607         buf[0] = crc >> 24;
1608         buf[1] = crc >> 16;
1609         buf[2] = crc >> 8;
1610         buf[3] = crc;
1611         buf += 4;
1612         return(len + overhead);
1613 }
1614         
1615 /* decode a message from b-channel
1616  */
1617 void PmISDN::cryptman_listen_bch(unsigned char *p, int l)
1618 {
1619         int i;
1620         struct message *message;
1621
1622         retry:
1623         if (!l)
1624                 return;
1625
1626         /* check for the keyword */
1627         if (p_m_crypt_listen_state == 0)
1628         {
1629                 while((*p++)!='C' && l)
1630                         l--;
1631                 if (!l)
1632                         return;
1633                 l--;
1634                 p_m_crypt_listen_state++;
1635                 if (!l)
1636                         return;
1637         }
1638         if (p_m_crypt_listen_state < 8)
1639         {
1640                 i = p_m_crypt_listen_state;
1641                 while(i < 8)
1642                 {
1643                         l--;
1644                         if (*p++ != "CRYPTMAN"[i])
1645                         {
1646                                 p_m_crypt_listen_state = 0;
1647                                 goto retry;
1648                         }
1649                         p_m_crypt_listen_state++;
1650                         if (!l)
1651                                 break;
1652                         i++;
1653                 }
1654                 if (!l)
1655                         return;
1656         }
1657         /* high byte of length */
1658         if (p_m_crypt_listen_state == 8)
1659         {
1660                 p_m_crypt_listen_len = (*p++) << 8;
1661                 p_m_crypt_listen_state++;
1662                 if (!(--l))
1663                         return;
1664         }
1665         /* low byte of length */
1666         if (p_m_crypt_listen_state == 9)
1667         {
1668                 p_m_crypt_listen_len += *p++;
1669                 p_m_crypt_listen_state++;
1670                 if (!(--l))
1671                         return;
1672         }
1673         /* crc */
1674         if (p_m_crypt_listen_state == 10)
1675         {
1676                 p_m_crypt_listen_crc = (*p++) << 24;
1677                 p_m_crypt_listen_state++;
1678                 if (!(--l))
1679                         return;
1680         }
1681         if (p_m_crypt_listen_state == 11)
1682         {
1683                 p_m_crypt_listen_crc += (*p++) << 16;
1684                 p_m_crypt_listen_state++;
1685                 if (!(--l))
1686                         return;
1687         }
1688         if (p_m_crypt_listen_state == 12)
1689         {
1690                 p_m_crypt_listen_crc += (*p++) << 8;
1691                 p_m_crypt_listen_state++;
1692                 if (!(--l))
1693                         return;
1694         }
1695         if (p_m_crypt_listen_state == 13)
1696         {
1697                 unsigned char lencheck[2];
1698                 p_m_crypt_listen_crc += *p++;
1699                 /* check for CRC */
1700                 lencheck[0] = p_m_crypt_listen_len >> 8;
1701                 lencheck[1] = p_m_crypt_listen_len & 0xff;
1702                 if (crc32(lencheck, 2) != p_m_crypt_listen_crc)
1703                 {
1704                         PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of %d bytes, but checksumme of length is incorrect (must %08x is %08x\n", p_name, p_m_crypt_listen_len, crc32(lencheck, 2), p_m_crypt_listen_crc);
1705                         p_m_crypt_listen_state = 0;
1706                         goto retry;
1707                 }
1708                 if (p_m_crypt_listen_len > (int)sizeof(p_m_crypt_listen_msg))
1709                 {
1710                         PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of %d bytes, but too big for buffer (%d bytes)\n", p_name, p_m_crypt_listen_len, sizeof(p_m_crypt_listen_msg));
1711                         p_m_crypt_listen_state = 0;
1712                         goto retry;
1713                 }
1714                 if (!p_m_crypt_listen_len)
1715                 {
1716                         PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of 0 bytes\n", p_name);
1717                         p_m_crypt_listen_state = 0;
1718                         goto retry;
1719                 }
1720                 p_m_crypt_listen_state++;
1721                 if (!(--l))
1722                         return;
1723         }
1724         /* read message */
1725         while (p_m_crypt_listen_state>=14 && p_m_crypt_listen_state<(p_m_crypt_listen_len+14))
1726         {
1727                 p_m_crypt_listen_msg[p_m_crypt_listen_state-14] = *p++;
1728                 p_m_crypt_listen_state++;
1729                 if (!(--l))
1730                         return;
1731         }
1732         /* crc */
1733         if (p_m_crypt_listen_state == 14+p_m_crypt_listen_len)
1734         {
1735                 p_m_crypt_listen_crc = (*p++) << 24;
1736                 p_m_crypt_listen_state++;
1737                 if (!(--l))
1738                         return;
1739         }
1740         if (p_m_crypt_listen_state == 15+p_m_crypt_listen_len)
1741         {
1742                 p_m_crypt_listen_crc += (*p++) << 16;
1743                 p_m_crypt_listen_state++;
1744                 if (!(--l))
1745                         return;
1746         }
1747         if (p_m_crypt_listen_state == 16+p_m_crypt_listen_len)
1748         {
1749                 p_m_crypt_listen_crc += (*p++) << 8;
1750                 p_m_crypt_listen_state++;
1751                 if (!(--l))
1752                         return;
1753         }
1754         if (p_m_crypt_listen_state == 17+p_m_crypt_listen_len)
1755         {
1756                 l--;
1757                 p_m_crypt_listen_crc += *p++;
1758                 /* check for CRC */
1759                 if (crc32(p_m_crypt_listen_msg, p_m_crypt_listen_len) != p_m_crypt_listen_crc)
1760                 {
1761                         PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of %d bytes, but checksumme of data block is incorrect\n", p_name, p_m_crypt_listen_len);
1762                         p_m_crypt_listen_state = 0;
1763                         if (!l)
1764                                 return;
1765                         goto retry;
1766                 }
1767                 /* now send message */
1768                 p_m_crypt_listen_state = 0;
1769                 PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of %d bytes sending to crypt manager\n", p_name, p_m_crypt_listen_len);
1770                 if ((int)sizeof(message->param.crypt.data) < p_m_crypt_listen_len+1) /* null-terminated */
1771                 {
1772                         PDEBUG(DEBUG_CRYPT, "PmISDN(%s) received a block of %d bytes that is too large for message buffer\n", p_name, p_m_crypt_listen_len);
1773                         if (!l)
1774                                 return;
1775                         goto retry;
1776                 }
1777                 message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_CRYPT);
1778                 message->param.crypt.type = CR_MESSAGE_IND;
1779                 message->param.crypt.len = p_m_crypt_listen_len+1; /* null termination */
1780                 memcpy(message->param.crypt.data, p_m_crypt_listen_msg, p_m_crypt_listen_len);
1781                 message_put(message);
1782                 p_m_crypt_listen_state = 0;
1783                 if (!l)
1784                         return;
1785                 goto retry;
1786         }
1787 }
1788
1789
1790 /* encrypt call using share secret (keypad function)
1791  */
1792 void EndpointAppPBX::encrypt_shared(void)
1793 {
1794         struct message *message;
1795         char *errstr = "";
1796         class Port *port;
1797         int type, key_len;
1798         unsigned char *key;
1799         char *auth_pointer, *crypt_pointer, *key_pointer;
1800         int ret;
1801
1802         /* redisplay current crypt display */
1803         if (e_crypt != CRYPT_OFF)
1804         {
1805                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) encryption in progress, so we request the current message.\n", ea_endpoint->ep_serial);
1806                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1807                 message->param.crypt.type = CU_INFO_REQ;
1808                 message_put(message);
1809                 return;
1810         }
1811
1812         if (check_external(&errstr, &port))
1813         {
1814                 reject:
1815                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1816                 SCPY(message->param.notifyinfo.display, errstr);
1817                 message_put(message);
1818                 set_tone(ea_endpoint->ep_portlist, "crypt_off");
1819                 e_tone[0] = '\0';
1820                 return;
1821         }
1822
1823         /* check the key for the call */
1824         if (port->p_type==PORT_TYPE_DSS1_TE_OUT || port->p_type==PORT_TYPE_DSS1_NT_OUT)
1825                 ret = parse_secrets((char *)e_ext.number, (char *)port->p_dialinginfo.id, &auth_pointer, &crypt_pointer, &key_pointer);
1826         else
1827         {
1828                 if (!port->p_callerinfo.id[0])
1829                 {
1830                         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) incoming remote call has no caller ID.\n", ea_endpoint->ep_serial);
1831                         errstr = "No Remote ID";
1832                         goto reject;
1833                 }
1834                 ret = parse_secrets((char *)e_ext.number, (char *)numberrize_callerinfo(port->p_callerinfo.id, port->p_callerinfo.ntype), &auth_pointer, &crypt_pointer, &key_pointer);
1835         }
1836         if (!ret)
1837         {
1838                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key was not found.\n", ea_endpoint->ep_serial);
1839                 errstr = "No Key";
1840                 goto reject;
1841         }
1842         key = crypt_key((unsigned char *)key_pointer, &key_len);
1843         if (!key)
1844         {
1845                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key invalid.\n", ea_endpoint->ep_serial);
1846                 errstr = "Invalid Key";
1847                 goto reject;
1848         }
1849         if (key_len > 128)
1850         {
1851                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key too long.\n", ea_endpoint->ep_serial);
1852                 errstr = "Key Too Long";
1853                 goto reject;
1854         }
1855         if (!!strcasecmp(auth_pointer, "manual"))
1856         {
1857                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Wrong authentication method.\n", ea_endpoint->ep_serial);
1858                 errstr = "Wrong Auth Type";
1859                 goto reject;
1860         }
1861         if (!strcasecmp(crypt_pointer, "blowfish"))
1862         {
1863                 type = CC_ACTBF_REQ;
1864                 if (key_len < 4)
1865                 {
1866                         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key too short.\n", ea_endpoint->ep_serial);
1867                         errstr = "Key Too Short";
1868                         goto reject;
1869                 }
1870                 if (key_len > 56)
1871                 {
1872                         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key too long.\n", ea_endpoint->ep_serial);
1873                         errstr = "Key Too Long";
1874                         goto reject;
1875                 }
1876         } else
1877         {
1878                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Wrong crypt method.\n", ea_endpoint->ep_serial);
1879                 errstr = "Wrong Crypt Type";
1880                 goto reject;
1881         }
1882
1883         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Key is ok, sending activation+key to cryptman.\n", ea_endpoint->ep_serial);
1884         /* setting display message and state */
1885 //      SPRINT(e_crypt_display, "Shared Key");
1886         e_crypt = CRYPT_SWAIT;
1887         /* sending activation */
1888         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1889         message->param.crypt.type = CU_ACTS_REQ;
1890         message->param.crypt.len = key_len;
1891         memcpy(message->param.crypt.data, key, key_len);
1892         message_put(message);
1893 }
1894
1895
1896 /* encrypt call using rsa authentication (keypad function)
1897  */
1898 void EndpointAppPBX::encrypt_keyex(void)
1899 {
1900         struct message *message;
1901         char *errstr = "";
1902         class Port *port;
1903
1904         /* redisplay current crypt display */
1905         if (e_crypt != CRYPT_OFF)
1906         {
1907                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) encryption in progress, so we request the current message.\n", ea_endpoint->ep_serial);
1908                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1909                 message->param.crypt.type = CU_INFO_REQ;
1910                 message_put(message);
1911                 return;
1912         }
1913
1914
1915         if (check_external(&errstr, &port))
1916         {
1917                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1918                 SCPY(message->param.notifyinfo.display, errstr);
1919                 message_put(message);
1920                 set_tone(ea_endpoint->ep_portlist, "crypt_off");
1921                 e_tone[0] = '\0';
1922                 return;
1923         }
1924
1925 #ifndef CRYPTO
1926         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1927         SCPY(message->param.notifyinfo.display, "Not Compiled");
1928         message_put(message);
1929         set_tone(ea_endpoint->ep_portlist, "crypt_off");
1930         e_tone[0] = '\0';
1931 #else
1932         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Sending key-exchange activation to cryptman.\n", ea_endpoint->ep_serial);
1933         /* setting display message and state */
1934 //      SPRINT(e_crypt_display, "Key-Exchange");
1935         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1936         SCPY(message->param.notifyinfo.display, "Key-Exchange");
1937         message_put(message);
1938         e_crypt = CRYPT_KWAIT;
1939         /* sending activation */
1940         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1941         message->param.crypt.type = CU_ACTK_REQ;
1942         message_put(message);
1943 #endif /* CRYPTO */
1944 }
1945
1946
1947 /* turn encryption off (keypad function)
1948  */
1949 void EndpointAppPBX::encrypt_off(void)
1950 {
1951         struct message *message;
1952
1953         if (e_crypt!=CRYPT_ON && e_crypt!=CRYPT_OFF)
1954         {
1955                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1956                 SCPY(message->param.notifyinfo.display, "Please Wait");
1957                 message_put(message);
1958                 return;
1959         }
1960         if (e_crypt == CRYPT_OFF)
1961         {
1962                 message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1963                 SCPY(message->param.notifyinfo.display, "No Encryption");
1964                 message_put(message);
1965                 set_tone(ea_endpoint->ep_portlist, "crypt_off");
1966                 e_tone[0] = '\0';
1967                 return;
1968         }
1969
1970         PDEBUG(DEBUG_EPOINT, "EPOINT(%d) Sending deactivation to cryptman.\n", ea_endpoint->ep_serial);
1971         /* setting display message and state */
1972 //      SPRINT(e_crypt_display, "Deactivating");
1973         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
1974         SCPY(message->param.notifyinfo.display, "Deactivating");
1975         message_put(message);
1976         e_crypt = CRYPT_RELEASE;
1977         /* sending activation */
1978         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_call_id, EPOINT_TO_CALL, MESSAGE_CRYPT);
1979         message->param.crypt.type = CU_DACT_REQ;
1980         message_put(message);
1981 }
1982
1983
1984 /* messages from manager to endpoint
1985  */
1986 void EndpointAppPBX::encrypt_result(int msg, char *text)
1987 {
1988         struct message *message;
1989
1990         switch(msg)
1991         {
1992                 case CU_ACTK_CONF:
1993                 case CU_ACTS_CONF:
1994                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) encryption now active.\n", ea_endpoint->ep_serial);
1995                 set_tone(ea_endpoint->ep_portlist, "crypt_on");
1996                 e_tone[0] = '\0';
1997                 e_crypt = CRYPT_ON;
1998                 display:
1999                 if (text) if (text[0])
2000                 {
2001                         SCPY(e_crypt_info, text);
2002                         message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY);
2003                         SCPY(message->param.notifyinfo.display, e_crypt_info);
2004                         message_put(message);
2005                 }
2006                 break;
2007
2008                 case CU_ERROR_IND:
2009                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) encryption error. (%s)\n", ea_endpoint->ep_serial, text);
2010                 set_tone(ea_endpoint->ep_portlist, "crypt_off");
2011                 e_tone[0] = '\0';
2012                 e_crypt = CRYPT_OFF;
2013                 goto display;
2014                 break;
2015
2016                 case CU_DACT_CONF:
2017                 case CU_DACT_IND:
2018                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) encryption now off. (%s)\n", ea_endpoint->ep_serial, text);
2019                 set_tone(ea_endpoint->ep_portlist, "crypt_off");
2020                 e_tone[0] = '\0';
2021                 e_crypt = CRYPT_OFF;
2022                 goto display;
2023                 break;
2024
2025                 case CU_INFO_CONF:
2026                 case CU_INFO_IND:
2027                 PDEBUG(DEBUG_EPOINT, "EPOINT(%d) information. (%s)\n", ea_endpoint->ep_serial, text);
2028                 goto display;
2029                 break;
2030
2031                 default:
2032                 PERROR("EPOINT(%d) crypt manager sends us an invalid message. (type = %d)\n", ea_endpoint->ep_serial, msg);
2033         }
2034 }
2035
2036