From d02b48c63a58ea4367a0e905979f140b7d090f86 Mon Sep 17 00:00:00 2001 From: "Ralf S. Engelschall" Date: Mon, 21 Dec 1998 10:52:47 +0000 Subject: Import of old SSLeay release: SSLeay 0.8.1b --- crypto/x509/Makefile.ssl | 96 ++++ crypto/x509/attrib | 38 ++ crypto/x509/by_dir.c | 320 +++++++++++++ crypto/x509/by_file.c | 205 +++++++++ crypto/x509/f | 465 +++++++++++++++++++ crypto/x509/v3_net.c | 87 ++++ crypto/x509/v3_x509.c | 88 ++++ crypto/x509/x509.doc | 27 ++ crypto/x509/x509.err | 43 ++ crypto/x509/x509.h | 1113 ++++++++++++++++++++++++++++++++++++++++++++++ crypto/x509/x509_cmp.c | 247 ++++++++++ crypto/x509/x509_d2.c | 106 +++++ crypto/x509/x509_def.c | 83 ++++ crypto/x509/x509_err.c | 121 +++++ crypto/x509/x509_ext.c | 222 +++++++++ crypto/x509/x509_lu.c | 439 ++++++++++++++++++ crypto/x509/x509_obj.c | 180 ++++++++ crypto/x509/x509_r2x.c | 122 +++++ crypto/x509/x509_req.c | 111 +++++ crypto/x509/x509_set.c | 164 +++++++ crypto/x509/x509_txt.c | 130 ++++++ crypto/x509/x509_v3.c | 409 +++++++++++++++++ crypto/x509/x509_vfy.c | 585 ++++++++++++++++++++++++ crypto/x509/x509_vfy.h | 341 ++++++++++++++ crypto/x509/x509name.c | 357 +++++++++++++++ crypto/x509/x509pack.c | 157 +++++++ crypto/x509/x509rset.c | 89 ++++ crypto/x509/x509type.c | 115 +++++ crypto/x509/x_all.c | 465 +++++++++++++++++++ 29 files changed, 6925 insertions(+) create mode 100644 crypto/x509/Makefile.ssl create mode 100644 crypto/x509/attrib create mode 100644 crypto/x509/by_dir.c create mode 100644 crypto/x509/by_file.c create mode 100644 crypto/x509/f create mode 100644 crypto/x509/v3_net.c create mode 100644 crypto/x509/v3_x509.c create mode 100644 crypto/x509/x509.doc create mode 100644 crypto/x509/x509.err create mode 100644 crypto/x509/x509.h create mode 100644 crypto/x509/x509_cmp.c create mode 100644 crypto/x509/x509_d2.c create mode 100644 crypto/x509/x509_def.c create mode 100644 crypto/x509/x509_err.c create mode 100644 crypto/x509/x509_ext.c create mode 100644 crypto/x509/x509_lu.c create mode 100644 crypto/x509/x509_obj.c create mode 100644 crypto/x509/x509_r2x.c create mode 100644 crypto/x509/x509_req.c create mode 100644 crypto/x509/x509_set.c create mode 100644 crypto/x509/x509_txt.c create mode 100644 crypto/x509/x509_v3.c create mode 100644 crypto/x509/x509_vfy.c create mode 100644 crypto/x509/x509_vfy.h create mode 100644 crypto/x509/x509name.c create mode 100644 crypto/x509/x509pack.c create mode 100644 crypto/x509/x509rset.c create mode 100644 crypto/x509/x509type.c create mode 100644 crypto/x509/x_all.c (limited to 'crypto/x509') diff --git a/crypto/x509/Makefile.ssl b/crypto/x509/Makefile.ssl new file mode 100644 index 0000000000..e54a74d1e8 --- /dev/null +++ b/crypto/x509/Makefile.ssl @@ -0,0 +1,96 @@ +# +# SSLeay/crypto/x509/Makefile +# + +DIR= x509 +TOP= ../.. +CC= cc +INCLUDES= -I.. -I../../include +CFLAG=-g +INSTALLTOP=/usr/local/ssl +MAKE= make -f Makefile.ssl +MAKEDEPEND= makedepend -f Makefile.ssl +MAKEFILE= Makefile.ssl +AR= ar r + +CFLAGS= $(INCLUDES) $(CFLAG) + +ERR=x509 +ERRC=x509_err +GENERAL=Makefile README +TEST= +APPS= + +LIB=$(TOP)/libcrypto.a +LIBSRC= x509_def.c x509_d2.c x509_r2x.c x509_cmp.c \ + x509_obj.c x509_req.c x509_vfy.c \ + x509_set.c x509rset.c $(ERRC).c \ + x509name.c x509_v3.c x509_ext.c x509pack.c \ + x509type.c x509_lu.c x_all.c x509_txt.c \ + by_file.c by_dir.c \ + v3_net.c v3_x509.c +LIBOBJ= x509_def.o x509_d2.o x509_r2x.o x509_cmp.o \ + x509_obj.o x509_req.o x509_vfy.o \ + x509_set.o x509rset.o $(ERRC).o \ + x509name.o x509_v3.o x509_ext.o x509pack.o \ + x509type.o x509_lu.o x_all.o x509_txt.o \ + by_file.o by_dir.o \ + v3_net.o v3_x509.o + +SRC= $(LIBSRC) + +EXHEADER= x509.h x509_vfy.h +HEADER= $(EXHEADER) + +ALL= $(GENERAL) $(SRC) $(HEADER) + +top: + (cd ../..; $(MAKE) DIRS=crypto SDIRS=$(DIR) sub_all) + +all: lib + +lib: $(LIBOBJ) + $(AR) $(LIB) $(LIBOBJ) + sh $(TOP)/util/ranlib.sh $(LIB) + @touch lib + +files: + perl $(TOP)/util/files.pl Makefile.ssl >> $(TOP)/MINFO + +links: + /bin/rm -f Makefile + $(TOP)/util/point.sh Makefile.ssl Makefile ; + $(TOP)/util/mklink.sh ../../include $(EXHEADER) + $(TOP)/util/mklink.sh ../../test $(TEST) + $(TOP)/util/mklink.sh ../../apps $(APPS) + +install: + @for i in $(EXHEADER) ; \ + do \ + (cp $$i $(INSTALLTOP)/include/$$i; \ + chmod 644 $(INSTALLTOP)/include/$$i ); \ + done; + +tags: + ctags $(SRC) + +tests: + +lint: + lint -DLINT $(INCLUDES) $(SRC)>fluff + +depend: + $(MAKEDEPEND) $(INCLUDES) $(PROGS) $(LIBSRC) + +dclean: + perl -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new + mv -f Makefile.new $(MAKEFILE) + +clean: + /bin/rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff + +errors: + perl $(TOP)/util/err-ins.pl $(ERR).err $(ERR).h + perl ../err/err_genc.pl $(ERR).h $(ERRC).c + +# DO NOT DELETE THIS LINE -- make depend depends on it. diff --git a/crypto/x509/attrib b/crypto/x509/attrib new file mode 100644 index 0000000000..37f6cd755f --- /dev/null +++ b/crypto/x509/attrib @@ -0,0 +1,38 @@ + +PKCS7 + STACK of X509_ATTRIBUTES + ASN1_OBJECT + STACK of ASN1_TYPE + +So it is + +p7.xa[].obj +p7.xa[].data[] + +get_obj_by_nid(STACK , nid) +get_num_by_nid(STACK , nid) +get_data_by_nid(STACK , nid, index) + +X509_ATTRIBUTE *X509_ATTRIBUTE_new(void ); +void X509_ATTRIBUTE_free(X509_ATTRIBUTE *a); + +X509_ATTRIBUTE *X509_ATTRIBUTE_create_by_NID(X509_ATTRIBUTE **ex, + int nid, STACK *value); + +X509_ATTRIBUTE *X509_ATTRIBUTE_create_by_OBJ(X509_ATTRIBUTE **ex, + int nid, STACK *value); + +int X509_ATTRIBUTE_set_object(X509_ATTRIBUTE *ex,ASN1_OBJECT *obj); +int X509_ATTRIBUTE_add_data(X509_ATTRIBUTE *ex, int index, + ASN1_TYPE *value); + +ASN1_OBJECT * X509_ATTRIBUTE_get_object(X509_ATTRIBUTE *ex); +int X509_ATTRIBUTE_get_num(X509_ATTRIBUTE *ne); +ASN1_TYPE * X509_ATTRIBUTE_get_data(X509_ATTRIBUTE *ne,int index); + +ASN1_TYPE * X509_ATTRIBUTE_get_data_by_NID(X509_ATTRIBUTE *ne, + ASN1_OBJECT *obj); + +X509_ATTRUBUTE *PKCS7_get_s_att_by_NID(PKCS7 *p7,int nid); +X509_ATTRUBUTE *PKCS7_get_u_att_by_NID(PKCS7 *p7,int nid); + diff --git a/crypto/x509/by_dir.c b/crypto/x509/by_dir.c new file mode 100644 index 0000000000..6676a2e404 --- /dev/null +++ b/crypto/x509/by_dir.c @@ -0,0 +1,320 @@ +/* crypto/x509/by_dir.c */ +/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include +#include +#include +#include +#include + +#include "cryptlib.h" +#include "lhash.h" +#include "x509.h" +#include "pem.h" + +typedef struct lookup_dir_st + { + BUF_MEM *buffer; + int num_dirs; + char **dirs; + int *dirs_type; + int num_dirs_alloced; + } BY_DIR; + +#ifndef NOPROTO +static int dir_ctrl(X509_LOOKUP *ctx,int cmd,char *argp,long argl,char **ret); +static int new_dir(X509_LOOKUP *lu); +static void free_dir(X509_LOOKUP *lu); +static int add_cert_dir(BY_DIR *ctx,char *dir,int type); +static int get_cert_by_subject(X509_LOOKUP *xl,int type,X509_NAME *name, + X509_OBJECT *ret); +#else +static int dir_ctrl(); +static int new_dir(); +static void free_dir(); +static int add_cert_dir(); +static int get_cert_by_subject(); +#endif + +X509_LOOKUP_METHOD x509_dir_lookup= + { + "Load certs from files in a directory", + new_dir, /* new */ + free_dir, /* free */ + NULL, /* init */ + NULL, /* shutdown */ + dir_ctrl, /* ctrl */ + get_cert_by_subject, /* get_by_subject */ + NULL, /* get_by_issuer_serial */ + NULL, /* get_by_fingerprint */ + NULL, /* get_by_alias */ + }; + +X509_LOOKUP_METHOD *X509_LOOKUP_hash_dir() + { + return(&x509_dir_lookup); + } + +static int dir_ctrl(ctx,cmd,argp,argl,retp) +X509_LOOKUP *ctx; +int cmd; +long argl; +char *argp; +char **retp; + { + int ret=0; + BY_DIR *ld; + char *dir; + + ld=(BY_DIR *)ctx->method_data; + + switch (cmd) + { + case X509_L_ADD_DIR: + if (argl == X509_FILETYPE_DEFAULT) + { + ret=add_cert_dir(ld,X509_get_default_cert_dir(), + X509_FILETYPE_PEM); + if (!ret) + { + X509err(X509_F_DIR_CTRL,X509_R_LOADING_CERT_DIR); + } + else + { + dir=(char *)Getenv(X509_get_default_cert_dir_env()); + ret=add_cert_dir(ld,dir,X509_FILETYPE_PEM); + } + } + else + ret=add_cert_dir(ld,argp,(int)argl); + break; + } + return(ret); + } + +static int new_dir(lu) +X509_LOOKUP *lu; + { + BY_DIR *a; + + if ((a=(BY_DIR *)Malloc(sizeof(BY_DIR))) == NULL) + return(0); + if ((a->buffer=BUF_MEM_new()) == NULL) + { + Free(a); + return(0); + } + a->num_dirs=0; + a->dirs=NULL; + a->dirs_type=NULL; + a->num_dirs_alloced=0; + lu->method_data=(char *)a; + return(1); + } + +static void free_dir(lu) +X509_LOOKUP *lu; + { + BY_DIR *a; + int i; + + a=(BY_DIR *)lu->method_data; + for (i=0; inum_dirs; i++) + if (a->dirs[i] != NULL) Free(a->dirs[i]); + if (a->dirs != NULL) Free(a->dirs); + if (a->dirs_type != NULL) Free(a->dirs_type); + if (a->buffer != NULL) BUF_MEM_free(a->buffer); + Free(a); + } + +static int add_cert_dir(ctx,dir, type) +BY_DIR *ctx; +char *dir; +int type; + { + int j,len; + int *ip; + char *s,*ss,*p; + char **pp; + + if (dir == NULL) return(0); + + s=dir; + p=s; + for (;;) + { + if ((*p == LIST_SEPARATOR_CHAR) || (*p == '\0')) + { + ss=s; + s=p+1; + len=(int)(p-ss); + if (len == 0) continue; + for (j=0; jnum_dirs; j++) + if (strncmp(ctx->dirs[j],ss,(unsigned int)len) == 0) + continue; + if (ctx->num_dirs_alloced < (ctx->num_dirs+1)) + { + ctx->num_dirs_alloced+=10; + pp=(char **)Malloc(ctx->num_dirs_alloced* + sizeof(char *)); + ip=(int *)Malloc(ctx->num_dirs_alloced* + sizeof(int)); + if ((pp == NULL) || (ip == NULL)) + { + X509err(X509_F_ADD_CERT_DIR,ERR_R_MALLOC_FAILURE); + return(0); + } + memcpy(pp,ctx->dirs,(ctx->num_dirs_alloced-10)* + sizeof(char *)); + memcpy(ip,ctx->dirs_type,(ctx->num_dirs_alloced-10)* + sizeof(int)); + if (ctx->dirs != NULL) + Free((char *)ctx->dirs); + if (ctx->dirs_type != NULL) + Free((char *)ctx->dirs_type); + ctx->dirs=pp; + ctx->dirs_type=ip; + } + ctx->dirs_type[ctx->num_dirs]=type; + ctx->dirs[ctx->num_dirs]=(char *)Malloc((unsigned int)len+1); + if (ctx->dirs[ctx->num_dirs] == NULL) return(0); + strncpy(ctx->dirs[ctx->num_dirs],ss,(unsigned int)len); + ctx->dirs[ctx->num_dirs][len]='\0'; + ctx->num_dirs++; + } + if (*p == '\0') break; + p++; + } + return(1); + } + +static int get_cert_by_subject(xl,type,name,ret) +X509_LOOKUP *xl; +int type; +X509_NAME *name; +X509_OBJECT *ret; + { + BY_DIR *ctx; + X509 st_x509; + X509_CINF st_x509_cinf; + int ok=0; + int i,j,k; + unsigned long h; + BUF_MEM *b=NULL; + struct stat st; + X509_OBJECT stmp,*tmp; + + if (name == NULL) return(0); + + st_x509.cert_info= &st_x509_cinf; + st_x509_cinf.subject=name; + stmp.data.x509= &st_x509; + stmp.type=type; + + if ((b=BUF_MEM_new()) == NULL) + { + X509err(X509_F_GET_CERT_BY_SUBJECT,ERR_R_BUF_LIB); + goto finish; + } + + ctx=(BY_DIR *)xl->method_data; + + h=X509_NAME_hash(name); + for (i=0; inum_dirs; i++) + { + j=strlen(ctx->dirs[i])+1+8+6+1; + if (!BUF_MEM_grow(b,j)) + { + X509err(X509_F_GET_CERT_BY_SUBJECT,ERR_R_MALLOC_FAILURE); + goto finish; + } + k=0; + for (;;) + { + sprintf(b->data,"%s/%08lx.%d",ctx->dirs[i],h,k); + k++; + if (stat(b->data,&st) < 0) + break; + /* found one. */ + if ((X509_load_cert_file(xl,b->data, + ctx->dirs_type[i])) == 0) + break; + } + + /* we have added it to the cache so now pull + * it out again */ + CRYPTO_r_lock(CRYPTO_LOCK_X509_STORE); + tmp=(X509_OBJECT *)lh_retrieve(xl->store_ctx->certs, + (char *)&stmp); + CRYPTO_r_unlock(CRYPTO_LOCK_X509_STORE); + + if (tmp != NULL) + { + ok=1; + ret->type=tmp->type; + ret->data.x509=tmp->data.x509; + /* CRYPTO_add(&tmp->data.x509->references,1, + CRYPTO_LOCK_X509);*/ + goto finish; + } + } +finish: + if (b != NULL) BUF_MEM_free(b); + return(ok); + } + diff --git a/crypto/x509/by_file.c b/crypto/x509/by_file.c new file mode 100644 index 0000000000..2dac28f542 --- /dev/null +++ b/crypto/x509/by_file.c @@ -0,0 +1,205 @@ +/* crypto/x509/by_file.c */ +/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include +#include +#include +#include +#include + +#include "cryptlib.h" +#include "lhash.h" +#include "buffer.h" +#include "x509.h" +#include "pem.h" + +#ifndef NOPROTO +static int by_file_ctrl(X509_LOOKUP *ctx,int cmd,char *argc, + long argl,char **ret); +#else +static int by_file_ctrl(); +#endif + +X509_LOOKUP_METHOD x509_file_lookup= + { + "Load file into cache", + NULL, /* new */ + NULL, /* free */ + NULL, /* init */ + NULL, /* shutdown */ + by_file_ctrl, /* ctrl */ + NULL, /* get_by_subject */ + NULL, /* get_by_issuer_serial */ + NULL, /* get_by_fingerprint */ + NULL, /* get_by_alias */ + }; + +X509_LOOKUP_METHOD *X509_LOOKUP_file() + { + return(&x509_file_lookup); + } + +static int by_file_ctrl(ctx,cmd,argp,argl,ret) +X509_LOOKUP *ctx; +int cmd; +char *argp; +long argl; +char **ret; + { + int ok=0; + char *file; + + switch (cmd) + { + case X509_L_FILE_LOAD: + if (argl == X509_FILETYPE_DEFAULT) + { + ok=X509_load_cert_file(ctx,X509_get_default_cert_file(), + X509_FILETYPE_PEM); + if (!ok) + { + X509err(X509_F_BY_FILE_CTRL,X509_R_LOADING_DEFAULTS); + } + else + { + file=(char *)Getenv(X509_get_default_cert_file_env()); + ok=X509_load_cert_file(ctx,file, + X509_FILETYPE_PEM); + } + } + else + ok=X509_load_cert_file(ctx,argp,(int)argl); + break; + } + return(ok); + } + +int X509_load_cert_file(ctx,file,type) +X509_LOOKUP *ctx; +char *file; +int type; + { + int ret=0; + BIO *in=NULL; + int i,count=0; + X509 *x=NULL; + + if (file == NULL) return(1); +#ifndef WIN16 + in=BIO_new(BIO_s_file()); +#else + in=BIO_new(BIO_s_file_internal_w16()); +#endif + + if ((in == NULL) || (BIO_read_filename(in,file) <= 0)) + { + X509err(X509_F_X509_LOAD_CERT_FILE,ERR_R_SYS_LIB); + goto err; + } + + if (type == X509_FILETYPE_PEM) + { + for (;;) + { + x=PEM_read_bio_X509(in,NULL,NULL); + if (x == NULL) + { + if ((ERR_GET_REASON(ERR_peek_error()) == + PEM_R_NO_START_LINE) && (count > 0)) + { + ERR_clear_error(); + break; + } + else + { + X509err(X509_F_X509_LOAD_CERT_FILE, + ERR_R_PEM_LIB); + goto err; + } + } + i=X509_STORE_add_cert(ctx->store_ctx,x); + if (!i) goto err; + count++; + X509_free(x); + x=NULL; + } + ret=count; + } + else if (type == X509_FILETYPE_ASN1) + { + x=d2i_X509_bio(in,NULL); + if (x == NULL) + { + X509err(X509_F_X509_LOAD_CERT_FILE,ERR_R_ASN1_LIB); + goto err; + } + i=X509_STORE_add_cert(ctx->store_ctx,x); + if (!i) goto err; + ret=i; + } + else + { + X509err(X509_F_X509_LOAD_CERT_FILE,X509_R_BAD_X509_FILETYPE); + goto err; + } +err: + if (x != NULL) X509_free(x); + if (in != NULL) BIO_free(in); + return(ret); + } + diff --git a/crypto/x509/f b/crypto/x509/f new file mode 100644 index 0000000000..6ec986db87 --- /dev/null +++ b/crypto/x509/f @@ -0,0 +1,465 @@ +*** x509name.c Wed Jul 2 09:35:35 1997 +--- /home/eay/play/x Sat Jul 5 01:39:56 1997 +*************** +*** 1,202 **** +! /* crypto/x509/x509name.c */ +! /* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) +! * All rights reserved. +! * +! * This package is an SSL implementation written +! * by Eric Young (eay@cryptsoft.com). +! * The implementation was written so as to conform with Netscapes SSL. +! * +! * This library is free for commercial and non-commercial use as long as +! * the following conditions are aheared to. The following conditions +! * apply to all code found in this distribution, be it the RC4, RSA, +! * lhash, DES, etc., code; not just the SSL code. The SSL documentation +! * included with this distribution is covered by the same copyright terms +! * except that the holder is Tim Hudson (tjh@cryptsoft.com). +! * +! * Copyright remains Eric Young's, and as such any Copyright notices in +! * the code are not to be removed. +! * If this package is used in a product, Eric Young should be given attribution +! * as the author of the parts of the library used. +! * This can be in the form of a textual message at program startup or +! * in documentation (online or textual) provided with the package. +! * +! * Redistribution and use in source and binary forms, with or without +! * modification, are permitted provided that the following conditions +! * are met: +! * 1. Redistributions of source code must retain the copyright +! * notice, this list of conditions and the following disclaimer. +! * 2. Redistributions in binary form must reproduce the above copyright +! * notice, this list of conditions and the following disclaimer in the +! * documentation and/or other materials provided with the distribution. +! * 3. All advertising materials mentioning features or use of this software +! * must display the following acknowledgement: +! * "This product includes cryptographic software written by +! * Eric Young (eay@cryptsoft.com)" +! * The word 'cryptographic' can be left out if the rouines from the library +! * being used are not cryptographic related :-). +! * 4. If you include any Windows specific code (or a derivative thereof) from +! * the apps directory (application code) you must include an acknowledgement: +! * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" +! * +! * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND +! * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +! * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +! * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +! * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +! * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +! * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +! * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +! * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +! * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +! * SUCH DAMAGE. +! * +! * The licence and distribution terms for any publically available version or +! * derivative of this code cannot be changed. i.e. this code cannot simply be +! * copied and put under another distribution licence +! * [including the GNU Public Licence.] +! */ +! +! #include +! #include "stack.h" +! #include "cryptlib.h" +! #include "asn1.h" +! #include "objects.h" +! #include "evp.h" +! #include "x509.h" +! +! int X509_NAME_get_text_by_NID(name,nid,buf,len) +! X509_NAME *name; +! int nid; +! char *buf; +! int len; + { + ASN1_OBJECT *obj; + + obj=OBJ_nid2obj(nid); +! if (obj == NULL) return(-1); +! return(X509_NAME_get_text_by_OBJ(name,obj,buf,len)); + } + +- int X509_NAME_get_text_by_OBJ(name,obj,buf,len) +- X509_NAME *name; +- ASN1_OBJECT *obj; +- char *buf; +- int len; +- { +- int i; +- ASN1_STRING *data; + +! i=X509_NAME_get_index_by_OBJ(name,obj,0); +! if (i < 0) return(-1); +! data=X509_NAME_ENTRY_get_data(X509_NAME_get_entry(name,i)); +! i=(data->length > (len-1))?(len-1):data->length; +! if (buf == NULL) return(data->length); +! memcpy(buf,data->data,i); +! buf[i]='\0'; +! return(i); +! } + +! int X509_NAME_entry_count(name) +! X509_NAME *name; + { +! if (name == NULL) return(0); +! return(sk_num(name->entries)); + } + +! int X509_NAME_get_index_by_NID(name,nid,oldpos) +! X509_NAME *name; +! int nid; +! int oldpos; +! { +! ASN1_OBJECT *obj; + +! obj=OBJ_nid2obj(nid); +! if (obj == NULL) return(-2); +! return(X509_NAME_get_index_by_OBJ(name,obj,oldpos)); + } + +- int X509_NAME_get_index_by_OBJ(name,obj,oldpos) +- X509_NAME *name; +- ASN1_OBJECT *obj; +- int oldpos; +- { +- int n; +- X509_NAME_ENTRY *ne; +- STACK *sk; + +! if (name == NULL) return(-1); +! if (oldpos < 0) +! oldpos= -1; +! sk=name->entries; +! n=sk_num(sk); +! for (oldpos++; oldpos < n; oldpos++) + { +! ne=(X509_NAME_ENTRY *)sk_value(sk,oldpos); +! if (OBJ_cmp(ne->object,obj) == 0) +! return(oldpos); + } +! return(-1); + } + +- X509_NAME_ENTRY *X509_NAME_get_entry(name,loc) +- X509_NAME *name; +- int loc; +- { +- if ( (name == NULL) || (sk_num(name->entries) <= loc) || (loc < 0)) +- return(NULL); +- else +- return((X509_NAME_ENTRY *)sk_value(name->entries,loc)); +- } + +! X509_NAME_ENTRY *X509_NAME_delete_entry(name,loc) +! X509_NAME *name; +! int loc; + { +! X509_NAME_ENTRY *ret; +! int i,j,n,set_prev,set_next; +! STACK *sk; +! +! if ((name == NULL) || (sk_num(name->entries) <= loc) || (loc < 0)) +! return(NULL); +! sk=name->entries; +! ret=(X509_NAME_ENTRY *)sk_delete(sk,loc); +! n=sk_num(sk); +! name->modified=1; +! if (loc == n) return(ret); +! +! /* else we need to fixup the set field */ +! if (loc != 0) +! set_prev=((X509_NAME_ENTRY *)sk_value(sk,loc-1))->set; +! else +! set_prev=ret->set-1; +! set_next=((X509_NAME_ENTRY *)sk_value(sk,loc))->set; + +! /* set_prev is the previous set +! * set is the current set +! * set_next is the following +! * prev 1 1 1 1 1 1 1 1 +! * set 1 1 2 2 +! * next 1 1 2 2 2 2 3 2 +! * so basically only if prev and next differ by 2, then +! * re-number down by 1 */ +! if (set_prev+1 < set_next) +! { +! j=set_next-set_prev-1; +! for (i=loc; iset-=j; +! } +! return(ret); + } + + /* if set is -1, append to previous set, 0 'a new one', and 1, + * prepend to the guy we are about to stomp on. */ +! int X509_NAME_add_entry(name,ne,loc,set) +! X509_NAME *name; +! X509_NAME_ENTRY *ne; +! int loc; +! int set; + { +! X509_NAME_ENTRY *new_name=NULL; + int n,i,inc; + STACK *sk; + +--- 1,77 ---- +! X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(X509_NAME_ENTRY **ne, int nid, +! int type,unsigned char *bytes, int len) + { + ASN1_OBJECT *obj; + + obj=OBJ_nid2obj(nid); +! if (obj == NULL) +! { +! X509err(X509_F_X509_NAME_ENTRY_CREATE_BY_NID,X509_R_UNKNOWN_NID); +! return(NULL); +! } +! return(X509_NAME_ENTRY_create_by_OBJ(ne,obj,type,bytes,len)); + } + + +! X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne, +! ASN1_OBJECT *obj, int type,unsigned char *bytes, +! int len) +! { +! X509_NAME_ENTRY *ret; + +! if ((ne == NULL) || (*ne == NULL)) + { +! if ((ret=X509_NAME_ENTRY_new()) == NULL) +! return(NULL); + } ++ else ++ ret= *ne; + +! if (!X509_NAME_ENTRY_set_object(ret,obj)) +! goto err; +! if (!X509_NAME_ENTRY_set_data(ret,type,bytes,len)) +! goto err; + +! if ((ne != NULL) && (*ne == NULL)) *ne=ret; +! return(ret); +! err: +! if ((ne == NULL) || (ret != *ne)) +! X509_NAME_ENTRY_free(ret); +! return(NULL); + } + + +! int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne, ASN1_OBJECT *obj) +! { +! if ((ne == NULL) || (obj == NULL)) + { +! X509err(X509_F_X509_NAME_ENTRY_SET_OBJECT,ERR_R_PASSED_NULL_PARAMETER); +! return(0); + } +! ASN1_OBJECT_free(ne->object); +! ne->object=OBJ_dup(obj); +! return((ne->object == NULL)?0:1); + } + + +! int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne,int type,unsigned char *bytes,int len) + { +! int i; + +! if ((ne == NULL) || ((bytes == NULL) && (len != 0))) return(0); +! if (len < 0) len=strlen((char *)bytes); +! i=ASN1_STRING_set(ne->value,bytes,len); +! if (!i) return(0); +! ne->value->type=ASN1_PRINTABLE_type(bytes,len); +! return(1); + } + + /* if set is -1, append to previous set, 0 'a new one', and 1, + * prepend to the guy we are about to stomp on. */ +! int X509_NAME_add_entry(X509_NAME *name,X509_NAME_ENTRY *ne,int loc,int set) + { +! /* ERIC: renamed new to nenew for C++ users --tjh */ +! X509_NAME_ENTRY *nenew; + int n,i,inc; + STACK *sk; + +*************** +*** 206,213 **** + if (loc > n) loc=n; + else if (loc < 0) loc=n; + +- name->modified=1; +- + if (set == -1) + { + if (loc == 0) +--- 81,86 ---- +*************** +*** 223,245 **** + } + else /* if (set >= 0) */ + { +- inc=(set == 0)?1:0; + if (loc >= n) + { + if (loc != 0) + set=((X509_NAME_ENTRY *) +! sk_value(sk,n-1))->set+1; + else + set=0; + } + else + set=((X509_NAME_ENTRY *)sk_value(sk,loc))->set; + } + +! if ((new_name=X509_NAME_ENTRY_dup(ne)) == NULL) + goto err; +! new_name->set=set; +! if (!sk_insert(sk,(char *)new_name,loc)) + { + X509err(X509_F_X509_NAME_ADD_ENTRY,ERR_R_MALLOC_FAILURE); + goto err; +--- 96,122 ---- + } + else /* if (set >= 0) */ + { + if (loc >= n) + { + if (loc != 0) + set=((X509_NAME_ENTRY *) +! sk_value(sk,loc-1))->set+1; + else + set=0; + } + else + set=((X509_NAME_ENTRY *)sk_value(sk,loc))->set; ++ inc=(set == 0)?1:0; + } + +! if ((nenew=X509_NAME_ENTRY_dup(ne)) == NULL) + goto err; +! /* eric forgot to put this in when he cut the nice +! * interface so that I don't have to do the icky things +! * that req.c does --tjh :-) +! */ +! nenew->set=set; +! if (!sk_insert(sk,(char *)nenew,loc)) + { + X509err(X509_F_X509_NAME_ADD_ENTRY,ERR_R_MALLOC_FAILURE); + goto err; +*************** +*** 252,357 **** + } + return(1); + err: +! if (new_name != NULL) + X509_NAME_ENTRY_free(ne); + return(0); +- } +- +- X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(ne,nid,type,bytes,len) +- X509_NAME_ENTRY **ne; +- int nid; +- int type; +- unsigned char *bytes; +- int len; +- { +- ASN1_OBJECT *obj; +- +- obj=OBJ_nid2obj(nid); +- if (obj == NULL) +- { +- X509err(X509_F_X509_NAME_ENTRY_CREATE_BY_NID,X509_R_UNKNOWN_NID); +- return(NULL); +- } +- return(X509_NAME_ENTRY_create_by_OBJ(ne,obj,type,bytes,len)); +- } +- +- X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(ne,obj,type,bytes,len) +- X509_NAME_ENTRY **ne; +- ASN1_OBJECT *obj; +- int type; +- unsigned char *bytes; +- int len; +- { +- X509_NAME_ENTRY *ret; +- +- if ((ne == NULL) || (*ne == NULL)) +- { +- if ((ret=X509_NAME_ENTRY_new()) == NULL) +- return(NULL); +- } +- else +- ret= *ne; +- +- if (!X509_NAME_ENTRY_set_object(ret,obj)) +- goto err; +- if (!X509_NAME_ENTRY_set_data(ret,type,bytes,len)) +- goto err; +- +- if ((ne != NULL) && (*ne == NULL)) *ne=ret; +- return(ret); +- err: +- if ((ne == NULL) || (ret != *ne)) +- X509_NAME_ENTRY_free(ret); +- return(NULL); +- } +- +- int X509_NAME_ENTRY_set_object(ne,obj) +- X509_NAME_ENTRY *ne; +- ASN1_OBJECT *obj; +- { +- if ((ne == NULL) || (obj == NULL)) +- { +- X509err(X509_F_X509_NAME_ENTRY_SET_OBJECT,ERR_R_PASSED_NULL_PARAMETER); +- return(0); +- } +- ASN1_OBJECT_free(ne->object); +- ne->object=OBJ_dup(obj); +- return((ne->object == NULL)?0:1); +- } +- +- int X509_NAME_ENTRY_set_data(ne,type,bytes,len) +- X509_NAME_ENTRY *ne; +- int type; +- unsigned char *bytes; +- int len; +- { +- int i; +- +- if ((ne == NULL) || ((bytes == NULL) && (len != 0))) return(0); +- if (len < 0) len=strlen((char *)bytes); +- i=ASN1_STRING_set(ne->value,bytes,len); +- if (!i) return(0); +- if (type != V_ASN1_UNDEF) +- { +- if (type == V_ASN1_APP_CHOOSE) +- ne->value->type=ASN1_PRINTABLE_type(bytes,len); +- else +- ne->value->type=type; +- } +- return(1); +- } +- +- ASN1_OBJECT *X509_NAME_ENTRY_get_object(ne) +- X509_NAME_ENTRY *ne; +- { +- if (ne == NULL) return(NULL); +- return(ne->object); +- } +- +- ASN1_STRING *X509_NAME_ENTRY_get_data(ne) +- X509_NAME_ENTRY *ne; +- { +- if (ne == NULL) return(NULL); +- return(ne->value); + } + +--- 129,136 ---- + } + return(1); + err: +! if (nenew != NULL) + X509_NAME_ENTRY_free(ne); + return(0); + } + diff --git a/crypto/x509/v3_net.c b/crypto/x509/v3_net.c new file mode 100644 index 0000000000..5e79a57f03 --- /dev/null +++ b/crypto/x509/v3_net.c @@ -0,0 +1,87 @@ +/* crypto/x509/v3_net.c */ +/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include +#include "stack.h" +#include "cryptlib.h" +#include "asn1.h" +#include "objects.h" +#include "x509.h" + +#define NETSCAPE_X509_EXT_NUM 8 + +static X509_EXTENSION_METHOD netscape_x509_ext[NETSCAPE_X509_EXT_NUM]={ +{NID_netscape_ca_policy_url,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_ssl_server_name,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_revocation_url,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_base_url,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_cert_type,V_ASN1_BIT_STRING,X509_EXT_PACK_STRING}, +{NID_netscape_ca_revocation_url,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_renewal_url,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_netscape_comment,V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, + }; + +int X509v3_add_netscape_extensions() + { + int i; + + for (i=0; i +#include "stack.h" +#include "cryptlib.h" +#include "asn1.h" +#include "objects.h" +#include "x509.h" + +#define STD_X509_EXT_NUM 9 + +static X509_EXTENSION_METHOD std_x509_ext[STD_X509_EXT_NUM]={ +{NID_subject_key_identifier, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_key_usage, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_private_key_usage_period, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_subject_alt_name, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_issuer_alt_name, V_ASN1_BIT_STRING,X509_EXT_PACK_STRING}, +{NID_basic_constraints, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_crl_number, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_certificate_policies, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, +{NID_authority_key_identifier, V_ASN1_IA5STRING,X509_EXT_PACK_STRING}, + }; + +int X509v3_add_standard_extensions() + { + int i; + + for (i=0; i and are used to manipulate + * Netscapes spki strucutres - usefull if you are writing a CA web page + */ +typedef struct Netscape_spkac_st + { + X509_PUBKEY *pubkey; + ASN1_IA5STRING *challenge; /* challenge sent in atlas >= PR2 */ + } NETSCAPE_SPKAC; + +typedef struct Netscape_spki_st + { + NETSCAPE_SPKAC *spkac; /* signed public key and challenge */ + X509_ALGOR *sig_algor; + ASN1_BIT_STRING *signature; + } NETSCAPE_SPKI; + +#ifndef HEADER_BN_H +#define BIGNUM char +#endif + +typedef struct CBCParameter_st + { + unsigned char iv[8]; + } CBC_PARAM; + +#include "x509_vfy.h" +#include "pkcs7.h" + +#ifdef SSLEAY_MACROS +#define X509_verify(a,r) ASN1_verify((int (*)())i2d_X509_CINF,a->sig_alg,\ + a->signature,(char *)a->cert_info,r) +#define X509_REQ_verify(a,r) ASN1_verify((int (*)())i2d_X509_REQ_INFO, \ + a->sig_alg,a->signature,(char *)a->req_info,r) +#define X509_CRL_verify(a,r) ASN1_verify((int (*)())i2d_X509_CRL_INFO, \ + a->sig_alg, a->signature,(char *)a->crl,r) +#define NETSCAPE_SPKI_verify(a,r) ASN1_verify((int (*)())i2d_NETSCAPE_SPKAC, \ + a->sig_algor,a->signature, (char *)a->spkac,r) + +#define X509_sign(x,pkey,md) \ + ASN1_sign((int (*)())i2d_X509_CINF, x->cert_info->signature, \ + x->sig_alg, x->signature, (char *)x->cert_info,pkey,md) +#define X509_REQ_sign(x,pkey,md) \ + ASN1_sign((int (*)())i2d_X509_REQ_INFO,x->sig_alg, NULL, \ + x->signature, (char *)x->req_info,pkey,md) +#define X509_CRL_sign(x,pkey,md) \ + ASN1_sign((int (*)())i2d_X509_CRL_INFO,x->crl->sig_alg,x->sig_alg, \ + x->signature, (char *)x->crl,pkey,md) +#define NETSCAPE_SPKI_sign(x,pkey,md) \ + ASN1_sign((int (*)())i2d_NETSCAPE_SPKAC, x->sig_algor,NULL, \ + x->signature, (char *)x->spkac,pkey,md) + +#define X509_dup(x509) (X509 *)ASN1_dup((int (*)())i2d_X509, \ + (char *(*)())d2i_X509,(char *)x509) +#define X509_EXTENSION_dup(ex) (X509_EXTENSION *)ASN1_dup( \ + (int (*)())i2d_X509_EXTENSION, \ + (char *(*)())d2i_X509_EXTENSION,(char *)ex) +#define d2i_X509_fp(fp,x509) (X509 *)ASN1_d2i_fp((char *(*)())X509_new, \ + (char *(*)())d2i_X509, (fp),(unsigned char **)(x509)) +#define i2d_X509_fp(fp,x509) ASN1_i2d_fp(i2d_X509,fp,(unsigned char *)x509) +#define d2i_X509_bio(bp,x509) (X509 *)ASN1_d2i_bio((char *(*)())X509_new, \ + (char *(*)())d2i_X509, (bp),(unsigned char **)(x509)) +#define i2d_X509_bio(bp,x509) ASN1_i2d_bio(i2d_X509,bp,(unsigned char *)x509) + +#define X509_CRL_dup(crl) (X509_CRL *)ASN1_dup((int (*)())i2d_X509_CRL, \ + (char *(*)())d2i_X509_CRL,(char *)crl) +#define d2i_X509_CRL_fp(fp,crl) (X509_CRL *)ASN1_d2i_fp((char *(*)()) \ + X509_CRL_new,(char *(*)())d2i_X509_CRL, (fp),\ + (unsigned char **)(crl)) +#define i2d_X509_CRL_fp(fp,crl) ASN1_i2d_fp(i2d_X509_CRL,fp,\ + (unsigned char *)crl) +#define d2i_X509_CRL_bio(bp,crl) (X509_CRL *)ASN1_d2i_bio((char *(*)()) \ + X509_CRL_new,(char *(*)())d2i_X509_CRL, (bp),\ + (unsigned char **)(crl)) +#define i2d_X509_CRL_bio(bp,crl) ASN1_i2d_bio(i2d_X509_CRL,bp,\ + (unsigned char *)crl) + +#define PKCS7_dup(p7) (PKCS7 *)ASN1_dup((int (*)())i2d_PKCS7, \ + (char *(*)())d2i_PKCS7,(char *)p7) +#define d2i_PKCS7_fp(fp,p7) (PKCS7 *)ASN1_d2i_fp((char *(*)()) \ + PKCS7_new,(char *(*)())d2i_PKCS7, (fp),\ + (unsigned char **)(p7)) +#define i2d_PKCS7_fp(fp,p7) ASN1_i2d_fp(i2d_PKCS7,fp,\ + (unsigned char *)p7) +#define d2i_PKCS7_bio(bp,p7) (PKCS7 *)ASN1_d2i_bio((char *(*)()) \ + PKCS7_new,(char *(*)())d2i_PKCS7, (bp),\ + (unsigned char **)(p7)) +#define i2d_PKCS7_bio(bp,p7) ASN1_i2d_bio(i2d_PKCS7,bp,\ + (unsigned char *)p7) + +#define X509_REQ_dup(req) (X509_REQ *)ASN1_dup((int (*)())i2d_X509_REQ, \ + (char *(*)())d2i_X509_REQ,(char *)req) +#define d2i_X509_REQ_fp(fp,req) (X509_REQ *)ASN1_d2i_fp((char *(*)())\ + X509_REQ_new, (char *(*)())d2i_X509_REQ, (fp),\ + (unsigned char **)(req)) +#define i2d_X509_REQ_fp(fp,req) ASN1_i2d_fp(i2d_X509_REQ,fp,\ + (unsigned char *)req) +#define d2i_X509_REQ_bio(bp,req) (X509_REQ *)ASN1_d2i_bio((char *(*)())\ + X509_REQ_new, (char *(*)())d2i_X509_REQ, (bp),\ + (unsigned char **)(req)) +#define i2d_X509_REQ_bio(bp,req) ASN1_i2d_bio(i2d_X509_REQ,bp,\ + (unsigned char *)req) + +#define RSAPublicKey_dup(rsa) (RSA *)ASN1_dup((int (*)())i2d_RSAPublicKey, \ + (char *(*)())d2i_RSAPublicKey,(char *)rsa) +#define RSAPrivateKey_dup(rsa) (RSA *)ASN1_dup((int (*)())i2d_RSAPrivateKey, \ + (char *(*)())d2i_RSAPrivateKey,(char *)rsa) + +#define d2i_RSAPrivateKey_fp(fp,rsa) (RSA *)ASN1_d2i_fp((char *(*)())\ + RSA_new,(char *(*)())d2i_RSAPrivateKey, (fp), \ + (unsigned char **)(rsa)) +#define i2d_RSAPrivateKey_fp(fp,rsa) ASN1_i2d_fp(i2d_RSAPrivateKey,fp, \ + (unsigned char *)rsa) +#define d2i_RSAPrivateKey_bio(bp,rsa) (RSA *)ASN1_d2i_bio((char *(*)())\ + RSA_new,(char *(*)())d2i_RSAPrivateKey, (bp), \ + (unsigned char **)(rsa)) +#define i2d_RSAPrivateKey_bio(bp,rsa) ASN1_i2d_bio(i2d_RSAPrivateKey,bp, \ + (unsigned char *)rsa) + +#define d2i_RSAPublicKey_fp(fp,rsa) (RSA *)ASN1_d2i_fp((char *(*)())\ + RSA_new,(char *(*)())d2i_RSAPublicKey, (fp), \ + (unsigned char **)(rsa)) +#define i2d_RSAPublicKey_fp(fp,rsa) ASN1_i2d_fp(i2d_RSAPublicKey,fp, \ + (unsigned char *)rsa) +#define d2i_RSAPublicKey_bio(bp,rsa) (RSA *)ASN1_d2i_bio((char *(*)())\ + RSA_new,(char *(*)())d2i_RSAPublicKey, (bp), \ + (unsigned char **)(rsa)) +#define i2d_RSAPublicKey_bio(bp,rsa) ASN1_i2d_bio(i2d_RSAPublicKey,bp, \ + (unsigned char *)rsa) + +#define d2i_DSAPrivateKey_fp(fp,dsa) (DSA *)ASN1_d2i_fp((char *(*)())\ + DSA_new,(char *(*)())d2i_DSAPrivateKey, (fp), \ + (unsigned char **)(dsa)) +#define i2d_DSAPrivateKey_fp(fp,dsa) ASN1_i2d_fp(i2d_DSAPrivateKey,fp, \ + (unsigned char *)dsa) +#define d2i_DSAPrivateKey_bio(bp,dsa) (DSA *)ASN1_d2i_bio((char *(*)())\ + DSA_new,(char *(*)())d2i_DSAPrivateKey, (bp), \ + (unsigned char **)(dsa)) +#define i2d_DSAPrivateKey_bio(bp,dsa) ASN1_i2d_bio(i2d_DSAPrivateKey,bp, \ + (unsigned char *)dsa) + +#define X509_NAME_dup(xn) (X509_NAME *)ASN1_dup((int (*)())i2d_X509_NAME, \ + (char *(*)())d2i_X509_NAME,(char *)xn) +#define X509_NAME_ENTRY_dup(ne) (X509_NAME_ENTRY *)ASN1_dup( \ + (int (*)())i2d_X509_NAME_ENTRY, \ + (char *(*)())d2i_X509_NAME_ENTRY,\ + (char *)ne) + +#define X509_digest(data,type,md,len) \ + ASN1_digest((int (*)())i2d_X509,type,(char *)data,md,len) +#define X509_NAME_digest(data,type,md,len) \ + ASN1_digest((int (*)())i2d_X509_NAME,type,(char *)data,md,len) +#define PKCS7_ISSUER_AND_SERIAL_digest(data,type,md,len) \ + ASN1_digest((int (*)())i2d_PKCS7_ISSUER_AND_SERIAL,type,\ + (char *)data,md,len) +#endif + +#define X509_get_version(x) ASN1_INTEGER_get((x)->cert_info->version) +/* #define X509_get_serialNumber(x) ((x)->cert_info->serialNumber) */ +#define X509_get_notBefore(x) ((x)->cert_info->validity->notBefore) +#define X509_get_notAfter(x) ((x)->cert_info->validity->notAfter) +#define X509_extract_key(x) X509_get_pubkey(x) /*****/ +#define X509_REQ_get_version(x) ASN1_INTEGER_get((x)->req_info->version) +#define X509_REQ_get_subject_name(x) ((x)->req_info->subject) +#define X509_REQ_extract_key(a) X509_REQ_get_pubkey(a) +#define X509_name_cmp(a,b) X509_NAME_cmp((a),(b)) +#define X509_get_signature_type(x) EVP_PKEY_type(OBJ_obj2nid((x)->sig_alg->algorithm)) + +/* This one is only used so that a binary form can output, as in + * i2d_X509_NAME(X509_get_X509_PUBKEY(x),&buf) */ +#define X509_get_X509_PUBKEY(x) ((x)->cert_info->key) + +#ifndef NOPROTO + +#ifndef SSLEAY_MACROS +#ifdef HEADER_ENVELOPE_H +int X509_verify(X509 *a, EVP_PKEY *r); +char *X509_verify_cert_error_string(int n); + +int X509_REQ_verify(X509_REQ *a, EVP_PKEY *r); +int X509_CRL_verify(X509_CRL *a, EVP_PKEY *r); +int NETSCAPE_SPKI_verify(NETSCAPE_SPKI *a, EVP_PKEY *r); + +int X509_sign(X509 *x, EVP_PKEY *pkey, EVP_MD *md); +int X509_REQ_sign(X509_REQ *x, EVP_PKEY *pkey, EVP_MD *md); +int X509_CRL_sign(X509_CRL *x, EVP_PKEY *pkey, EVP_MD *md); +int NETSCAPE_SPKI_sign(NETSCAPE_SPKI *x, EVP_PKEY *pkey, EVP_MD *md); + +int X509_digest(X509 *data,EVP_MD *type,unsigned char *md,unsigned int *len); +int X509_NAME_digest(X509_NAME *data,EVP_MD *type, + unsigned char *md,unsigned int *len); +#endif + +#ifndef WIN16 +X509 *d2i_X509_fp(FILE *fp, X509 *x509); +int i2d_X509_fp(FILE *fp,X509 *x509); +X509_CRL *d2i_X509_CRL_fp(FILE *fp,X509_CRL *crl); +int i2d_X509_CRL_fp(FILE *fp,X509_CRL *crl); +X509_REQ *d2i_X509_REQ_fp(FILE *fp,X509_REQ *req); +int i2d_X509_REQ_fp(FILE *fp,X509_REQ *req); +RSA *d2i_RSAPrivateKey_fp(FILE *fp,RSA *rsa); +int i2d_RSAPrivateKey_fp(FILE *fp,RSA *rsa); +DSA *d2i_DSAPrivateKey_fp(FILE *fp, DSA *dsa); +int i2d_DSAPrivateKey_fp(FILE *fp, DSA *dsa); +RSA *d2i_RSAPublicKey_fp(FILE *fp,RSA *rsa); +int i2d_RSAPublicKey_fp(FILE *fp,RSA *rsa); +#endif + +#ifdef HEADER_BIO_H +X509 *d2i_X509_bio(BIO *bp,X509 *x509); +int i2d_X509_bio(BIO *bp,X509 *x509); +X509_CRL *d2i_X509_CRL_bio(BIO *bp,X509_CRL *crl); +int i2d_X509_CRL_bio(BIO *bp,X509_CRL *crl); +X509_REQ *d2i_X509_REQ_bio(BIO *bp,X509_REQ *req); +int i2d_X509_REQ_bio(BIO *bp,X509_REQ *req); +RSA *d2i_RSAPrivateKey_bio(BIO *bp,RSA *rsa); +int i2d_RSAPrivateKey_bio(BIO *bp,RSA *rsa); +DSA *d2i_DSAPrivateKey_bio(BIO *bp, DSA *dsa); +int i2d_DSAPrivateKey_bio(BIO *bp, DSA *dsa); +RSA *d2i_RSAPublicKey_bio(BIO *bp,RSA *rsa); +int i2d_RSAPublicKey_bio(BIO *bp,RSA *rsa); +#endif + +X509 *X509_dup(X509 *x509); +X509_EXTENSION *X509_EXTENSION_dup(X509_EXTENSION *ex); +X509_CRL *X509_CRL_dup(X509_CRL *crl); +X509_REQ *X509_REQ_dup(X509_REQ *req); +X509_NAME *X509_NAME_dup(X509_NAME *xn); +X509_NAME_ENTRY *X509_NAME_ENTRY_dup(X509_NAME_ENTRY *ne); +RSA *RSAPublicKey_dup(RSA *rsa); +RSA *RSAPrivateKey_dup(RSA *rsa); + +#endif /* !SSLEAY_MACROS */ + +int X509_cmp_current_time(ASN1_UTCTIME *s); +ASN1_UTCTIME * X509_gmtime_adj(ASN1_UTCTIME *s, long adj); + +char * X509_get_default_cert_area(void ); +char * X509_get_default_cert_dir(void ); +char * X509_get_default_cert_file(void ); +char * X509_get_default_cert_dir_env(void ); +char * X509_get_default_cert_file_env(void ); +char * X509_get_default_private_dir(void ); + +X509_REQ * X509_to_X509_REQ(X509 *x, EVP_PKEY *pkey); +X509 * X509_REQ_to_X509(X509_REQ *r, int days,EVP_PKEY *pkey); +void ERR_load_X509_strings(void ); + +X509_ALGOR * X509_ALGOR_new(void ); +void X509_ALGOR_free(X509_ALGOR *a); +int i2d_X509_ALGOR(X509_ALGOR *a,unsigned char **pp); +X509_ALGOR * d2i_X509_ALGOR(X509_ALGOR **a,unsigned char **pp, + long length); + +X509_VAL * X509_VAL_new(void ); +void X509_VAL_free(X509_VAL *a); +int i2d_X509_VAL(X509_VAL *a,unsigned char **pp); +X509_VAL * d2i_X509_VAL(X509_VAL **a,unsigned char **pp, + long length); + +X509_PUBKEY * X509_PUBKEY_new(void ); +void X509_PUBKEY_free(X509_PUBKEY *a); +int i2d_X509_PUBKEY(X509_PUBKEY *a,unsigned char **pp); +X509_PUBKEY * d2i_X509_PUBKEY(X509_PUBKEY **a,unsigned char **pp, + long length); +int X509_PUBKEY_set(X509_PUBKEY **x, EVP_PKEY *pkey); +EVP_PKEY * X509_PUBKEY_get(X509_PUBKEY *key); +int X509_get_pubkey_parameters(EVP_PKEY *pkey, STACK *chain); + + +X509_SIG * X509_SIG_new(void ); +void X509_SIG_free(X509_SIG *a); +int i2d_X509_SIG(X509_SIG *a,unsigned char **pp); +X509_SIG * d2i_X509_SIG(X509_SIG **a,unsigned char **pp,long length); + +X509_REQ_INFO *X509_REQ_INFO_new(void); +void X509_REQ_INFO_free(X509_REQ_INFO *a); +int i2d_X509_REQ_INFO(X509_REQ_INFO *a,unsigned char **pp); +X509_REQ_INFO *d2i_X509_REQ_INFO(X509_REQ_INFO **a,unsigned char **pp, + long length); + +X509_REQ * X509_REQ_new(void); +void X509_REQ_free(X509_REQ *a); +int i2d_X509_REQ(X509_REQ *a,unsigned char **pp); +X509_REQ * d2i_X509_REQ(X509_REQ **a,unsigned char **pp,lon