diff options
author | Ralf S. Engelschall <rse@openssl.org> | 1998-12-21 10:56:39 +0000 |
---|---|---|
committer | Ralf S. Engelschall <rse@openssl.org> | 1998-12-21 10:56:39 +0000 |
commit | 58964a492275ca9a59a0cd9c8155cb2491b4b909 (patch) | |
tree | c7b16876a5789463bbbb468ef4829c8129b3d718 /ssl/ssl_ciph.c | |
parent | d02b48c63a58ea4367a0e905979f140b7d090f86 (diff) |
Import of old SSLeay release: SSLeay 0.9.0b
Diffstat (limited to 'ssl/ssl_ciph.c')
-rw-r--r-- | ssl/ssl_ciph.c | 223 |
1 files changed, 130 insertions, 93 deletions
diff --git a/ssl/ssl_ciph.c b/ssl/ssl_ciph.c index 9fed3ad59a..820994408b 100644 --- a/ssl/ssl_ciph.c +++ b/ssl/ssl_ciph.c @@ -1,5 +1,5 @@ /* ssl/ssl_ciph.c */ -/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * * This package is an SSL implementation written @@ -74,11 +74,10 @@ static EVP_CIPHER *ssl_cipher_methods[SSL_ENC_NUM_IDX]={ }; #define SSL_MD_MD5_IDX 0 -#define SSL_MD_SHA0_IDX 1 -#define SSL_MD_SHA1_IDX 2 -#define SSL_MD_NUM_IDX 3 +#define SSL_MD_SHA1_IDX 1 +#define SSL_MD_NUM_IDX 2 static EVP_MD *ssl_digest_methods[SSL_MD_NUM_IDX]={ - NULL,NULL,NULL, + NULL,NULL, }; typedef struct cipher_sort_st @@ -90,16 +89,24 @@ typedef struct cipher_sort_st #define CIPHER_ADD 1 #define CIPHER_KILL 2 #define CIPHER_DEL 3 -#define CIPHER_ORDER 4 +#define CIPHER_ORD 4 typedef struct cipher_choice_st { int type; unsigned long algorithms; unsigned long mask; - STACK *order; + long top; } CIPHER_CHOICE; +typedef struct cipher_order_st + { + SSL_CIPHER *cipher; + int active; + int dead; + struct cipher_order_st *next,*prev; + } CIPHER_ORDER; + static SSL_CIPHER cipher_aliases[]={ {0,SSL_TXT_ALL, 0,SSL_ALL, 0,SSL_ALL}, /* must be first */ {0,SSL_TXT_kRSA,0,SSL_kRSA, 0,SSL_MKEY_MASK}, @@ -126,7 +133,6 @@ static SSL_CIPHER cipher_aliases[]={ {0,SSL_TXT_eFZA,0,SSL_eFZA, 0,SSL_ENC_MASK}, {0,SSL_TXT_MD5, 0,SSL_MD5, 0,SSL_MAC_MASK}, - {0,SSL_TXT_SHA0,0,SSL_SHA0, 0,SSL_MAC_MASK}, {0,SSL_TXT_SHA1,0,SSL_SHA1, 0,SSL_MAC_MASK}, {0,SSL_TXT_SHA, 0,SSL_SHA, 0,SSL_MAC_MASK}, @@ -169,8 +175,6 @@ static void load_ciphers() ssl_digest_methods[SSL_MD_MD5_IDX]= EVP_get_digestbyname(SN_md5); - ssl_digest_methods[SSL_MD_SHA0_IDX]= - EVP_get_digestbyname(SN_sha); ssl_digest_methods[SSL_MD_SHA1_IDX]= EVP_get_digestbyname(SN_sha1); } @@ -225,9 +229,6 @@ EVP_MD **md; case SSL_MD5: i=SSL_MD_MD5_IDX; break; - case SSL_SHA0: - i=SSL_MD_SHA0_IDX; - break; case SSL_SHA1: i=SSL_MD_SHA1_IDX; break; @@ -246,6 +247,25 @@ EVP_MD **md; return(0); } +#define ITEM_SEP(a) \ + (((a) == ':') || ((a) == ' ') || ((a) == ';') || ((a) == ',')) + +static void ll_append_tail(head,curr,tail) +CIPHER_ORDER **head,*curr,**tail; + { + if (curr == *tail) return; + if (curr == *head) + *head=curr->next; + if (curr->prev != NULL) + curr->prev->next=curr->next; + if (curr->next != NULL) /* should always be true */ + curr->next->prev=curr->prev; + (*tail)->next=curr; + curr->prev= *tail; + curr->next=NULL; + *tail=curr; + } + STACK *ssl_create_cipher_list(ssl_method,cipher_list,cipher_list_by_id,str) SSL_METHOD *ssl_method; STACK **cipher_list,**cipher_list_by_id; @@ -262,9 +282,11 @@ char *str; int i,j,k,num=0,ch,multi; unsigned long al; STACK *ca_list=NULL; - STACK *c_list=NULL; - int old_x,old_y,current_x,num_x; + int current_x,num_x; CIPHER_CHOICE *ops=NULL; + CIPHER_ORDER *list=NULL,*head=NULL,*tail=NULL,*curr,*tail2,*curr2; + int list_num; + int type; SSL_CIPHER c_tmp,*cp; if (str == NULL) return(NULL); @@ -278,6 +300,7 @@ char *str; goto err; } strcpy(tmp_str,SSL_DEFAULT_CIPHER_LIST); + strcat(tmp_str,":"); strcat(tmp_str,&(str[7])); str=tmp_str; } @@ -286,7 +309,6 @@ char *str; num=ssl_method->num_ciphers(); if ((ret=(STACK *)sk_new(NULL)) == NULL) goto err; - if ((c_list=(STACK *)sk_new(NULL)) == NULL) goto err; if ((ca_list=(STACK *)sk_new(cmp_by_name)) == NULL) goto err; mask =SSL_kFZA; @@ -312,20 +334,42 @@ char *str; mask|=(ssl_cipher_methods[SSL_ENC_eFZA_IDX] == NULL)?SSL_eFZA:0; mask|=(ssl_digest_methods[SSL_MD_MD5_IDX ] == NULL)?SSL_MD5 :0; - mask|=(ssl_digest_methods[SSL_MD_SHA0_IDX] == NULL)?SSL_SHA0:0; mask|=(ssl_digest_methods[SSL_MD_SHA1_IDX] == NULL)?SSL_SHA1:0; + if ((list=(CIPHER_ORDER *)Malloc(sizeof(CIPHER_ORDER)*num)) == NULL) + goto err; + /* Get the initial list of ciphers */ + list_num=0; for (i=0; i<num; i++) { c=ssl_method->get_cipher((unsigned int)i); /* drop those that use any of that is not available */ if ((c != NULL) && c->valid && !(c->algorithms & mask)) { - if (!sk_push(c_list,(char *)c)) goto err; + list[list_num].cipher=c; + list[list_num].next=NULL; + list[list_num].prev=NULL; + list[list_num].active=0; + list_num++; if (!sk_push(ca_list,(char *)c)) goto err; } } + + for (i=1; i<list_num-1; i++) + { + list[i].prev= &(list[i-1]); + list[i].next= &(list[i+1]); + } + if (list_num > 0) + { + head= &(list[0]); + head->prev=NULL; + head->next= &(list[1]); + tail= &(list[list_num-1]); + tail->prev= &(list[list_num-2]); + tail->next=NULL; + } /* special case */ cipher_aliases[0].algorithms= ~mask; @@ -346,12 +390,11 @@ char *str; /* how many parameters are there? */ num=1; for (l=str; *l; l++) - if (*l == ':') num++; + if (ITEM_SEP(*l)) + num++; ops=(CIPHER_CHOICE *)Malloc(sizeof(CIPHER_CHOICE)*num); if (ops == NULL) goto err; memset(ops,0,sizeof(CIPHER_CHOICE)*num); - for (i=0; i<num; i++) - if ((ops[i].order=sk_new_null()) == NULL) goto err; /* we now parse the input string and create our operations */ l=str; @@ -361,16 +404,19 @@ char *str; for (;;) { ch= *l; + + if (ch == '\0') break; + if (ch == '-') { j=CIPHER_DEL; l++; } else if (ch == '+') - { j=CIPHER_ORDER; l++; } + { j=CIPHER_ORD; l++; } else if (ch == '!') { j=CIPHER_KILL; l++; } else { j=CIPHER_ADD; } - if (*l == ':') + if (ITEM_SEP(ch)) { l++; continue; @@ -395,20 +441,20 @@ char *str; if (i >= (CL_BUF-2)) break; } buf[i]='\0'; - if (ch != '\0') l++; /* check for multi-part specification */ - multi=(ch == '+')?1:0; + if (ch == '+') + { + multi=1; + l++; + } + else + multi=0; c_tmp.name=buf; j=sk_find(ca_list,(char *)&c_tmp); if (j < 0) - { - if (ch == '\0') - break; - else - continue; - } + goto end_loop; cp=(SSL_CIPHER *)sk_value(ca_list,j); ops[current_x].algorithms|=cp->algorithms; @@ -419,87 +465,86 @@ char *str; } current_x++; if (ch == '\0') break; +end_loop: + /* Make sure we scan until the next valid start point */ + while ((*l != '\0') && ITEM_SEP(*l)) + l++; } num_x=current_x; current_x=0; -#ifdef CIPHER_DEBUG - printf("<--->\n"); -#endif - - for (i=0; i<sk_num(c_list); i++) + /* We will now process the list of ciphers, once for each category, to + * decide what we should do with it. */ + for (j=0; j<num_x; j++) { - old_x= -1; - old_y= -1; - cp=(SSL_CIPHER *)sk_value(c_list,i); -#ifdef CIPHER_DEBUG - printf("[%s]\n",cp->name); -#endif - for (j=0; j<num_x; j++) + algorithms=ops[j].algorithms; + type=ops[j].type; + mask=ops[j].mask; + + curr=head; + curr2=head; + tail2=tail; + for (;;) { - algorithms=ops[j].algorithms; - ma=ops[j].mask & cp->algorithms; -#ifdef CIPHER_DEBUG - printf(" %s %08lX&%08lX==0 || %08lX != %08lX \n", - cp->name,ops[j].mask,cp->algorithms,ma,algorithms); -#endif + if ((curr == NULL) || (curr == tail2)) break; + curr=curr2; + curr2=curr->next; + + cp=curr->cipher; + ma=mask & cp->algorithms; if ((ma == 0) || ((ma & algorithms) != ma)) { + /* does not apply */ continue; } - k=ops[j].type; -#ifdef CIPHER_DEBUG - printf(">>%s\n",cp->name); -#endif /* add the cipher if it has not been added yet. */ - if (k == CIPHER_ADD) + if (type == CIPHER_ADD) { - if (old_x < 0) + if (!curr->active) { - old_x=j; - old_y=sk_num(ops[j].order); - sk_push(ops[j].order,(char *)cp); + ll_append_tail(&head,curr,&tail); + curr->active=1; } } /* Move the added cipher to this location */ - else if (k == CIPHER_ORDER) + else if (type == CIPHER_ORD) { - if (old_x >= 0) + if (curr->active) { - sk_value(ops[old_x].order,old_y)=NULL; - old_y=sk_num(ops[j].order); - sk_push(ops[j].order,(char *)cp); - old_x=j; + ll_append_tail(&head,curr,&tail); } } - /* Remove added cipher */ - else if ((k == CIPHER_DEL) || (k == CIPHER_KILL)) + else if (type == CIPHER_DEL) + curr->active=0; + if (type == CIPHER_KILL) { - if (old_x >= 0) - { - sk_value(ops[old_x].order,old_y)=NULL; - old_x= -1; - } - if (k == CIPHER_KILL) - break; + if (head == curr) + head=curr->next; + else + curr->prev->next=curr->next; + if (tail == curr) + tail=curr->prev; + curr->active=0; + if (curr->next != NULL) + curr->next->prev=curr->prev; + if (curr->prev != NULL) + curr->prev->next=curr->next; + curr->next=NULL; + curr->prev=NULL; } } } - for (i=0; i<num_x; i++) + for (curr=head; curr != NULL; curr=curr->next) { - for (j=0; j<sk_num(ops[i].order); j++) + if (curr->active) { - cp=(SSL_CIPHER *)sk_value(ops[i].order,j); - if (cp != NULL) - { - sk_push(ret,(char *)cp); + sk_push(ret,(char *)curr->cipher); #ifdef CIPHER_DEBUG - printf("<%s>\n",cp->name); + printf("<%s>\n",curr->cipher->name); #endif - } } } @@ -528,16 +573,10 @@ char *str; ret=NULL; err: if (tmp_str) Free(tmp_str); - if (ops != NULL) - { - for (i=0; i<num; i++) - if (ops[i].order != NULL) - sk_free(ops[i].order); - Free(ops); - } + if (ops != NULL) Free(ops); if (ret != NULL) sk_free(ret); - if (c_list != NULL) sk_free(c_list); if (ca_list != NULL) sk_free(ca_list); + if (list != NULL) Free(list); return(ok); } @@ -639,9 +678,6 @@ int len; case SSL_MD5: mac="MD5"; break; - case SSL_SHA0: - mac="SHA0"; - break; case SSL_SHA1: mac="SHA1"; break; @@ -667,9 +703,10 @@ SSL_CIPHER *c; { int i; + if (c == NULL) return("(NONE)"); i=(int)(c->id>>24L); if (i == 3) - return("SSLv3"); + return("TLSv1/SSLv3"); else if (i == 2) return("SSLv2"); else |