Пример #1
0
char *UI_construct_prompt(UI *ui, const char *object_desc,
                          const char *object_name)
{
    char *prompt = NULL;

    if (ui->meth->ui_construct_prompt)
        prompt = ui->meth->ui_construct_prompt(ui, object_desc, object_name);
    else {
        char prompt1[] = "Enter ";
        char prompt2[] = " for ";
        char prompt3[] = ":";
        int len = 0;

        if (object_desc == NULL)
            return NULL;
        len = sizeof(prompt1) - 1 + strlen(object_desc);
        if (object_name)
            len += sizeof(prompt2) - 1 + strlen(object_name);
        len += sizeof(prompt3) - 1;

        prompt = OPENSSL_malloc(len + 1);
        if (prompt == NULL)
            return NULL;
        BUF_strlcpy(prompt, prompt1, len + 1);
        BUF_strlcat(prompt, object_desc, len + 1);
        if (object_name) {
            BUF_strlcat(prompt, prompt2, len + 1);
            BUF_strlcat(prompt, object_name, len + 1);
        }
        BUF_strlcat(prompt, prompt3, len + 1);
    }
    return prompt;
}
Пример #2
0
int DSO_set_filename(DSO *dso, const char *filename)
	{
	char *copied;

	if((dso == NULL) || (filename == NULL))
		{
		DSOerr(DSO_F_DSO_SET_FILENAME,ERR_R_PASSED_NULL_PARAMETER);
		return(0);
		}
	if(dso->loaded_filename)
		{
		DSOerr(DSO_F_DSO_SET_FILENAME,DSO_R_DSO_ALREADY_LOADED);
		return(0);
		}
	/* We'll duplicate filename */
	copied = OPENSSL_malloc(strlen(filename) + 1);
	if(copied == NULL)
		{
		DSOerr(DSO_F_DSO_SET_FILENAME,ERR_R_MALLOC_FAILURE);
		return(0);
		}
	BUF_strlcpy(copied, filename, strlen(filename) + 1);
	if(dso->filename)
		OPENSSL_free(dso->filename);
	dso->filename = copied;
	return(1);
	}
Пример #3
0
int EVP_PBE_CipherInit(ASN1_OBJECT *pbe_obj, const char *pass, int passlen,
	     ASN1_TYPE *param, EVP_CIPHER_CTX *ctx, int en_de)
{

	EVP_PBE_CTL *pbetmp, pbelu;
	int i;
	pbelu.pbe_nid = OBJ_obj2nid(pbe_obj);
	if (pbelu.pbe_nid != NID_undef) i = sk_find(pbe_algs, (char *)&pbelu);
	else i = -1;

	if (i == -1) {
		char obj_tmp[80];
		EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_UNKNOWN_PBE_ALGORITHM);
		if (!pbe_obj) BUF_strlcpy (obj_tmp, "NULL", sizeof obj_tmp);
		else i2t_ASN1_OBJECT(obj_tmp, sizeof obj_tmp, pbe_obj);
		ERR_add_error_data(2, "TYPE=", obj_tmp);
		return 0;
	}
	if(!pass) passlen = 0;
	else if (passlen == -1) passlen = strlen(pass);
	pbetmp = (EVP_PBE_CTL *)sk_value (pbe_algs, i);
	i = (*pbetmp->keygen)(ctx, pass, passlen, param, pbetmp->cipher,
						 pbetmp->md, en_de);
	if (!i) {
		EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_KEYGEN_FAILURE);
		return 0;
	}
	return 1;	
}
Пример #4
0
char *DSO_convert_filename(DSO *dso, const char *filename)
{
    char *result = NULL;

    if (dso == NULL) {
        DSOerr(DSO_F_DSO_CONVERT_FILENAME, ERR_R_PASSED_NULL_PARAMETER);
        return (NULL);
    }
    if (filename == NULL)
        filename = dso->filename;
    if (filename == NULL) {
        DSOerr(DSO_F_DSO_CONVERT_FILENAME, DSO_R_NO_FILENAME);
        return (NULL);
    }
    if ((dso->flags & DSO_FLAG_NO_NAME_TRANSLATION) == 0) {
        if (dso->name_converter != NULL)
            result = dso->name_converter(dso, filename);
        else if (dso->meth->dso_name_converter != NULL)
            result = dso->meth->dso_name_converter(dso, filename);
    }
    if (result == NULL) {
        result = OPENSSL_malloc(strlen(filename) + 1);
        if (result == NULL) {
            DSOerr(DSO_F_DSO_CONVERT_FILENAME, ERR_R_MALLOC_FAILURE);
            return (NULL);
        }
        BUF_strlcpy(result, filename, strlen(filename) + 1);
    }
    return (result);
}
Пример #5
0
size_t BUF_strlcat(char *dst, const char *src, size_t dst_size) {
  size_t l = 0;
  for (; dst_size > 0 && *dst; dst_size--, dst++) {
    l++;
  }
  return l + BUF_strlcpy(dst, src, dst_size);
}
Пример #6
0
size_t BUF_strlcat(char *dst, const char *src, size_t size)
	{
	size_t l = 0;
	for(; size > 0 && *dst; size--, dst++)
		l++;
	return l + BUF_strlcpy(dst, src, size);
	}
Пример #7
0
int EVP_PBE_CipherInit(ASN1_OBJECT *pbe_obj, const char *pass, int passlen,
		       ASN1_TYPE *param, EVP_CIPHER_CTX *ctx, int en_de)
	{
	const EVP_CIPHER *cipher;
	const EVP_MD *md;
	int cipher_nid, md_nid;
	EVP_PBE_KEYGEN *keygen;

	if (!EVP_PBE_find(EVP_PBE_TYPE_OUTER, OBJ_obj2nid(pbe_obj),
					&cipher_nid, &md_nid, &keygen))
		{
		char obj_tmp[80];
		EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_UNKNOWN_PBE_ALGORITHM);
		if (!pbe_obj) BUF_strlcpy (obj_tmp, "NULL", sizeof obj_tmp);
		else i2t_ASN1_OBJECT(obj_tmp, sizeof obj_tmp, pbe_obj);
		ERR_add_error_data(2, "TYPE=", obj_tmp);
		return 0;
		}

	if(!pass)
		passlen = 0;
	else if (passlen == -1)
		passlen = strlen(pass);

	if (cipher_nid == -1)
		cipher = NULL;
	else
		{
		cipher = EVP_get_cipherbynid(cipher_nid);
		if (!cipher)
			{
			EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_UNKNOWN_CIPHER);
			return 0;
			}
		}

	if (md_nid == -1)
		md = NULL;
	else
		{
		md = EVP_get_digestbynid(md_nid);
		if (!md)
			{
			EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_UNKNOWN_DIGEST);
			return 0;
			}
		}

	if (!keygen(ctx, pass, passlen, param, cipher, md, en_de))
		{
		EVPerr(EVP_F_EVP_PBE_CIPHERINIT,EVP_R_KEYGEN_FAILURE);
		return 0;
		}
	return 1;	
}
Пример #8
0
/* Convert an ASN1_TIME structure to GeneralizedTime */
ASN1_GENERALIZEDTIME *ASN1_TIME_to_generalizedtime(ASN1_TIME *t,
                                                   ASN1_GENERALIZEDTIME **out)
{
    ASN1_GENERALIZEDTIME *ret;
    char *str;
    int newlen;

    if (!ASN1_TIME_check(t))
        return NULL;

    if (!out || !*out) {
        if (!(ret = ASN1_GENERALIZEDTIME_new()))
            return NULL;
        if (out)
            *out = ret;
    } else
        ret = *out;

    /* If already GeneralizedTime just copy across */
    if (t->type == V_ASN1_GENERALIZEDTIME) {
        if (!ASN1_STRING_set(ret, t->data, t->length))
            return NULL;
        return ret;
    }

    /* grow the string */
    if (!ASN1_STRING_set(ret, NULL, t->length + 2))
        return NULL;
    /* ASN1_STRING_set() allocated 'len + 1' bytes. */
    newlen = t->length + 2 + 1;
    str = (char *)ret->data;
    /* Work out the century and prepend */
    if (t->data[0] >= '5')
        BUF_strlcpy(str, "19", newlen);
    else
        BUF_strlcpy(str, "20", newlen);

    BUF_strlcat(str, (char *)t->data, newlen);

    return ret;
}
Пример #9
0
static ASN1_INTEGER *x509_load_serial(char *CAfile, char *serialfile,
                                      int create)
{
    char *buf = NULL, *p;
    ASN1_INTEGER *bs = NULL;
    BIGNUM *serial = NULL;
    size_t len;

    len = ((serialfile == NULL)
           ? (strlen(CAfile) + strlen(POSTFIX) + 1)
           : (strlen(serialfile))) + 1;
    buf = app_malloc(len, "serial# buffer");
    if (serialfile == NULL) {
        BUF_strlcpy(buf, CAfile, len);
        for (p = buf; *p; p++)
            if (*p == '.') {
                *p = '\0';
                break;
            }
        BUF_strlcat(buf, POSTFIX, len);
    } else
        BUF_strlcpy(buf, serialfile, len);

    serial = load_serial(buf, create, NULL);
    if (serial == NULL)
        goto end;

    if (!BN_add_word(serial, 1)) {
        BIO_printf(bio_err, "add_word failure\n");
        goto end;
    }

    if (!save_serial(buf, NULL, serial, &bs))
        goto end;

 end:
    OPENSSL_free(buf);
    BN_free(serial);
    return bs;
}
Пример #10
0
char *BUF_strndup(const char *str, size_t siz)
	{
	char *ret;

	if (str == NULL) return(NULL);

	ret=OPENSSL_malloc(siz+1);
	if (ret == NULL) 
		{
		BUFerr(BUF_F_BUF_STRNDUP,ERR_R_MALLOC_FAILURE);
		return(NULL);
		}
	BUF_strlcpy(ret,str,siz+1);
	return(ret);
	}
Пример #11
0
static void print_leak(const MEM *m, MEM_LEAK *l)
	{
	char buf[1024];
	char *bufp = buf;
	APP_INFO *amip;
	int ami_cnt;
	struct tm *lcl = NULL;
	unsigned long ti;

#define BUF_REMAIN (sizeof buf - (size_t)(bufp - buf))

	if(m->addr == (char *)l->bio)
	    return;

	if (options & V_CRYPTO_MDEBUG_TIME)
		{
		lcl = localtime(&m->time);
	
		BIO_snprintf(bufp, BUF_REMAIN, "[%02d:%02d:%02d] ",
			lcl->tm_hour,lcl->tm_min,lcl->tm_sec);
		bufp += strlen(bufp);
		}

	BIO_snprintf(bufp, BUF_REMAIN, "%5lu file=%s, line=%d, ",
		m->order,m->file,m->line);
	bufp += strlen(bufp);

	if (options & V_CRYPTO_MDEBUG_THREAD)
		{
		BIO_snprintf(bufp, BUF_REMAIN, "thread=%lu, ", m->thread);
		bufp += strlen(bufp);
		}

	BIO_snprintf(bufp, BUF_REMAIN, "number=%d, address=%08lX\n",
		m->num,(unsigned long)m->addr);
	bufp += strlen(bufp);

	BIO_puts(l->bio,buf);
	
	l->chunks++;
	l->bytes+=m->num;

	amip=m->app_info;
	ami_cnt=0;
	if (!amip)
		return;
	ti=amip->thread;
	
	do
		{
		int buf_len;
		int info_len;

		ami_cnt++;
		memset(buf,'>',ami_cnt);
		BIO_snprintf(buf + ami_cnt, sizeof buf - ami_cnt,
			" thread=%lu, file=%s, line=%d, info=\"",
			amip->thread, amip->file, amip->line);
		buf_len=strlen(buf);
		info_len=strlen(amip->info);
		if (128 - buf_len - 3 < info_len)
			{
			memcpy(buf + buf_len, amip->info, 128 - buf_len - 3);
			buf_len = 128 - 3;
			}
		else
			{
			BUF_strlcpy(buf + buf_len, amip->info,
				    sizeof buf - buf_len);
			buf_len = strlen(buf);
			}
		BIO_snprintf(buf + buf_len, sizeof buf - buf_len, "\"\n");
		
		BIO_puts(l->bio,buf);

		amip = amip->next;
		}
	while(amip && amip->thread == ti);
		
#ifdef LEVITTE_DEBUG_MEM
	if (amip)
		{
		fprintf(stderr, "Thread switch detected in backtrace!!!!\n");
		abort();
		}
#endif
	}
static int do_accept(int acc_sock, int *sock, char **host)
	{
	int ret;
	struct hostent *h1,*h2;
	static struct sockaddr_in from;
	int len;
/*	struct linger ling; */

	if (!ssl_sock_init()) return(0);

#ifndef OPENSSL_SYS_WINDOWS
redoit:
#endif

	memset((char *)&from,0,sizeof(from));
	len=sizeof(from);
	/* Note: under VMS with SOCKETSHR the fourth parameter is currently
	 * of type (int *) whereas under other systems it is (void *) if
	 * you don't have a cast it will choke the compiler: if you do
	 * have a cast then you can either go for (int *) or (void *).
	 */
	ret=accept(acc_sock,(struct sockaddr *)&from,(void *)&len);
	if (ret == INVALID_SOCKET)
		{
#if defined(OPENSSL_SYS_WINDOWS) || (defined(OPENSSL_SYS_NETWARE) && !defined(NETWARE_BSDSOCK))
		int i;
		i=WSAGetLastError();
		BIO_printf(bio_err,"accept error %d\n",i);
#else
		if (errno == EINTR)
			{
			/*check_timeout(); */
			goto redoit;
			}
		fprintf(stderr,"errno=%d ",errno);
		perror("accept");
#endif
		return(0);
		}

/*
	ling.l_onoff=1;
	ling.l_linger=0;
	i=setsockopt(ret,SOL_SOCKET,SO_LINGER,(char *)&ling,sizeof(ling));
	if (i < 0) { perror("linger"); return(0); }
	i=0;
	i=setsockopt(ret,SOL_SOCKET,SO_KEEPALIVE,(char *)&i,sizeof(i));
	if (i < 0) { perror("keepalive"); return(0); }
*/

	if (host == NULL) goto end;
#ifndef BIT_FIELD_LIMITS
	/* I should use WSAAsyncGetHostByName() under windows */
	h1=gethostbyaddr((char *)&from.sin_addr.s_addr,
		sizeof(from.sin_addr.s_addr),AF_INET);
#else
	h1=gethostbyaddr((char *)&from.sin_addr,
		sizeof(struct in_addr),AF_INET);
#endif
	if (h1 == NULL)
		{
		BIO_printf(bio_err,"bad gethostbyaddr\n");
		*host=NULL;
		/* return(0); */
		}
	else
		{
		if ((*host=(char *)OPENSSL_malloc(strlen(h1->h_name)+1)) == NULL)
			{
			perror("OPENSSL_malloc");
			closesocket(ret);
			return(0);
			}
		BUF_strlcpy(*host,h1->h_name,strlen(h1->h_name)+1);

		h2=GetHostByName(*host);
		if (h2 == NULL)
			{
			BIO_printf(bio_err,"gethostbyname failure\n");
			closesocket(ret);
			return(0);
			}
		if (h2->h_addrtype != AF_INET)
			{
			BIO_printf(bio_err,"gethostbyname addr is not AF_INET\n");
			closesocket(ret);
			return(0);
			}
		}
end:
	*sock=ret;
	return(1);
	}
Пример #13
0
int MAIN(int argc, char **argv)
{
    ENGINE *e = NULL;
    char *infile=NULL, *outfile=NULL, *keyname = NULL;	
    char *certfile=NULL;
    BIO *in=NULL, *out = NULL;
    char **args;
    char *name = NULL;
    char *csp_name = NULL;
    PKCS12 *p12 = NULL;
    char pass[50], macpass[50];
    int export_cert = 0;
    int options = 0;
    int chain = 0;
    int badarg = 0;
    int iter = PKCS12_DEFAULT_ITER;
    int maciter = PKCS12_DEFAULT_ITER;
    int twopass = 0;
    int keytype = 0;
    int cert_pbe;
    int key_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
    int ret = 1;
    int macver = 1;
    int noprompt = 0;
    STACK *canames = NULL;
    char *cpass = NULL, *mpass = NULL;
    char *passargin = NULL, *passargout = NULL, *passarg = NULL;
    char *passin = NULL, *passout = NULL;
    char *inrand = NULL;
    char *CApath = NULL, *CAfile = NULL;
#ifndef OPENSSL_NO_ENGINE
    char *engine=NULL;
#endif

    apps_startup();

#ifdef OPENSSL_FIPS
    if (FIPS_mode())
	cert_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
    else
#endif
    cert_pbe = NID_pbe_WithSHA1And40BitRC2_CBC;

    enc = EVP_des_ede3_cbc();
    if (bio_err == NULL ) bio_err = BIO_new_fp (stderr, BIO_NOCLOSE);

	if (!load_config(bio_err, NULL))
		goto end;

    args = argv + 1;


    while (*args) {
	if (*args[0] == '-') {
		if (!strcmp (*args, "-nokeys")) options |= NOKEYS;
		else if (!strcmp (*args, "-keyex")) keytype = KEY_EX;
		else if (!strcmp (*args, "-keysig")) keytype = KEY_SIG;
		else if (!strcmp (*args, "-nocerts")) options |= NOCERTS;
		else if (!strcmp (*args, "-clcerts")) options |= CLCERTS;
		else if (!strcmp (*args, "-cacerts")) options |= CACERTS;
		else if (!strcmp (*args, "-noout")) options |= (NOKEYS|NOCERTS);
		else if (!strcmp (*args, "-info")) options |= INFO;
		else if (!strcmp (*args, "-chain")) chain = 1;
		else if (!strcmp (*args, "-twopass")) twopass = 1;
		else if (!strcmp (*args, "-nomacver")) macver = 0;
		else if (!strcmp (*args, "-descert"))
    			cert_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
		else if (!strcmp (*args, "-export")) export_cert = 1;
		else if (!strcmp (*args, "-des")) enc=EVP_des_cbc();
#ifndef OPENSSL_NO_IDEA
		else if (!strcmp (*args, "-idea")) enc=EVP_idea_cbc();
#endif
		else if (!strcmp (*args, "-des3")) enc = EVP_des_ede3_cbc();
#ifndef OPENSSL_NO_AES
		else if (!strcmp(*args,"-aes128")) enc=EVP_aes_128_cbc();
		else if (!strcmp(*args,"-aes192")) enc=EVP_aes_192_cbc();
		else if (!strcmp(*args,"-aes256")) enc=EVP_aes_256_cbc();
#endif
		else if (!strcmp (*args, "-noiter")) iter = 1;
		else if (!strcmp (*args, "-maciter"))
					 maciter = PKCS12_DEFAULT_ITER;
		else if (!strcmp (*args, "-nomaciter"))
					 maciter = 1;
		else if (!strcmp (*args, "-nodes")) enc=NULL;
		else if (!strcmp (*args, "-certpbe")) {
			if (args[1]) {
				args++;
				cert_pbe=OBJ_txt2nid(*args);
				if(cert_pbe == NID_undef) {
					BIO_printf(bio_err,
						 "Unknown PBE algorithm %s\n", *args);
					badarg = 1;
				}
			} else badarg = 1;
		} else if (!strcmp (*args, "-keypbe")) {
			if (args[1]) {
				args++;
				key_pbe=OBJ_txt2nid(*args);
				if(key_pbe == NID_undef) {
					BIO_printf(bio_err,
						 "Unknown PBE algorithm %s\n", *args);
					badarg = 1;
				}
			} else badarg = 1;
		} else if (!strcmp (*args, "-rand")) {
		    if (args[1]) {
			args++;	
			inrand = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-inkey")) {
		    if (args[1]) {
			args++;	
			keyname = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-certfile")) {
		    if (args[1]) {
			args++;	
			certfile = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-name")) {
		    if (args[1]) {
			args++;	
			name = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-CSP")) {
		    if (args[1]) {
			args++;	
			csp_name = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-caname")) {
		    if (args[1]) {
			args++;	
			if (!canames) canames = sk_new_null();
			sk_push(canames, *args);
		    } else badarg = 1;
		} else if (!strcmp (*args, "-in")) {
		    if (args[1]) {
			args++;	
			infile = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-out")) {
		    if (args[1]) {
			args++;	
			outfile = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-passin")) {
		    if (args[1]) {
			args++;	
			passargin = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-passout")) {
		    if (args[1]) {
			args++;	
			passargout = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-password")) {
		    if (args[1]) {
			args++;	
			passarg = *args;
		    	noprompt = 1;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-CApath")) {
		    if (args[1]) {
			args++;	
			CApath = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-CAfile")) {
		    if (args[1]) {
			args++;	
			CAfile = *args;
		    } else badarg = 1;
#ifndef OPENSSL_NO_ENGINE
		} else if (!strcmp(*args,"-engine")) {
		    if (args[1]) {
			args++;	
			engine = *args;
		    } else badarg = 1;
#endif
		} else badarg = 1;

	} else badarg = 1;
	args++;
    }

    if (badarg) {
	BIO_printf (bio_err, "Usage: pkcs12 [options]\n");
	BIO_printf (bio_err, "where options are\n");
	BIO_printf (bio_err, "-export       output PKCS12 file\n");
	BIO_printf (bio_err, "-chain        add certificate chain\n");
	BIO_printf (bio_err, "-inkey file   private key if not infile\n");
	BIO_printf (bio_err, "-certfile f   add all certs in f\n");
	BIO_printf (bio_err, "-CApath arg   - PEM format directory of CA's\n");
	BIO_printf (bio_err, "-CAfile arg   - PEM format file of CA's\n");
	BIO_printf (bio_err, "-name \"name\"  use name as friendly name\n");
	BIO_printf (bio_err, "-caname \"nm\"  use nm as CA friendly name (can be used more than once).\n");
	BIO_printf (bio_err, "-in  infile   input filename\n");
	BIO_printf (bio_err, "-out outfile  output filename\n");
	BIO_printf (bio_err, "-noout        don't output anything, just verify.\n");
	BIO_printf (bio_err, "-nomacver     don't verify MAC.\n");
	BIO_printf (bio_err, "-nocerts      don't output certificates.\n");
	BIO_printf (bio_err, "-clcerts      only output client certificates.\n");
	BIO_printf (bio_err, "-cacerts      only output CA certificates.\n");
	BIO_printf (bio_err, "-nokeys       don't output private keys.\n");
	BIO_printf (bio_err, "-info         give info about PKCS#12 structure.\n");
	BIO_printf (bio_err, "-des          encrypt private keys with DES\n");
	BIO_printf (bio_err, "-des3         encrypt private keys with triple DES (default)\n");
#ifndef OPENSSL_NO_IDEA
	BIO_printf (bio_err, "-idea         encrypt private keys with idea\n");
#endif
#ifndef OPENSSL_NO_AES
	BIO_printf (bio_err, "-aes128, -aes192, -aes256\n");
	BIO_printf (bio_err, "              encrypt PEM output with cbc aes\n");
#endif
	BIO_printf (bio_err, "-nodes        don't encrypt private keys\n");
	BIO_printf (bio_err, "-noiter       don't use encryption iteration\n");
	BIO_printf (bio_err, "-maciter      use MAC iteration\n");
	BIO_printf (bio_err, "-twopass      separate MAC, encryption passwords\n");
	BIO_printf (bio_err, "-descert      encrypt PKCS#12 certificates with triple DES (default RC2-40)\n");
	BIO_printf (bio_err, "-certpbe alg  specify certificate PBE algorithm (default RC2-40)\n");
	BIO_printf (bio_err, "-keypbe alg   specify private key PBE algorithm (default 3DES)\n");
	BIO_printf (bio_err, "-keyex        set MS key exchange type\n");
	BIO_printf (bio_err, "-keysig       set MS key signature type\n");
	BIO_printf (bio_err, "-password p   set import/export password source\n");
	BIO_printf (bio_err, "-passin p     input file pass phrase source\n");
	BIO_printf (bio_err, "-passout p    output file pass phrase source\n");
#ifndef OPENSSL_NO_ENGINE
	BIO_printf (bio_err, "-engine e     use engine e, possibly a hardware device.\n");
#endif
	BIO_printf(bio_err,  "-rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
	BIO_printf(bio_err,  "              load the file (or the files in the directory) into\n");
	BIO_printf(bio_err,  "              the random number generator\n");
    	goto end;
    }

#ifndef OPENSSL_NO_ENGINE
    e = setup_engine(bio_err, engine, 0);
#endif

    if(passarg) {
	if(export_cert) passargout = passarg;
	else passargin = passarg;
    }

    if(!app_passwd(bio_err, passargin, passargout, &passin, &passout)) {
	BIO_printf(bio_err, "Error getting passwords\n");
	goto end;
    }

    if(!cpass) {
    	if(export_cert) cpass = passout;
    	else cpass = passin;
    }

    if(cpass) {
	mpass = cpass;
	noprompt = 1;
    } else {
	cpass = pass;
	mpass = macpass;
    }

    if(export_cert || inrand) {
    	app_RAND_load_file(NULL, bio_err, (inrand != NULL));
        if (inrand != NULL)
		BIO_printf(bio_err,"%ld semi-random bytes loaded\n",
			app_RAND_load_files(inrand));
    }
    ERR_load_crypto_strings();

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read files");
#endif

    if (!infile) in = BIO_new_fp(stdin, BIO_NOCLOSE);
    else in = BIO_new_file(infile, "rb");
    if (!in) {
	    BIO_printf(bio_err, "Error opening input file %s\n",
						infile ? infile : "<stdin>");
	    perror (infile);
	    goto end;
   }

#if 0
   if (certfile) {
    	if(!(certsin = BIO_new_file(certfile, "r"))) {
	    BIO_printf(bio_err, "Can't open certificate file %s\n", certfile);
	    perror (certfile);
	    goto end;
	}
    }

    if (keyname) {
    	if(!(inkey = BIO_new_file(keyname, "r"))) {
	    BIO_printf(bio_err, "Can't key certificate file %s\n", keyname);
	    perror (keyname);
	    goto end;
	}
     }
#endif

#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
    CRYPTO_push_info("write files");
#endif

    if (!outfile) {
	out = BIO_new_fp(stdout, BIO_NOCLOSE);
#ifdef OPENSSL_SYS_VMS
	{
	    BIO *tmpbio = BIO_new(BIO_f_linebuffer());
	    out = BIO_push(tmpbio, out);
	}
#endif
    } else out = BIO_new_file(outfile, "wb");
    if (!out) {
	BIO_printf(bio_err, "Error opening output file %s\n",
						outfile ? outfile : "<stdout>");
	perror (outfile);
	goto end;
    }
    if (twopass) {
#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read MAC password");
#endif
	if(EVP_read_pw_string (macpass, sizeof macpass, "Enter MAC Password:"******"Can't read Password\n");
    	    goto end;
       	}
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    }

    if (export_cert) {
	EVP_PKEY *key = NULL;
	STACK_OF(PKCS12_SAFEBAG) *bags = NULL;
	STACK_OF(PKCS7) *safes = NULL;
	PKCS12_SAFEBAG *bag = NULL;
	PKCS8_PRIV_KEY_INFO *p8 = NULL;
	PKCS7 *authsafe = NULL;
	X509 *ucert = NULL;
	STACK_OF(X509) *certs=NULL;
	char *catmp = NULL;
	int i;
	unsigned char keyid[EVP_MAX_MD_SIZE];
	unsigned int keyidlen = 0;

#ifdef CRYPTO_MDEBUG
	CRYPTO_push_info("process -export_cert");
	CRYPTO_push_info("reading private key");
#endif
	key = load_key(bio_err, keyname ? keyname : infile, FORMAT_PEM, 1,
		passin, e, "private key");
	if (!key) {
		goto export_end;
	}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from input");
#endif

	/* Load in all certs in input file */
	if(!(certs = load_certs(bio_err, infile, FORMAT_PEM, NULL, e,
		"certificates"))) {
		goto export_end;
	}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from input 2");
#endif

	for(i = 0; i < sk_X509_num(certs); i++) {
		ucert = sk_X509_value(certs, i);
		if(X509_check_private_key(ucert, key)) {
			X509_digest(ucert, EVP_sha1(), keyid, &keyidlen);
			break;
		}
	}
	if(!keyidlen) {
		ucert = NULL;
		BIO_printf(bio_err, "No certificate matches private key\n");
		goto export_end;
	}
	
#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from certfile");
#endif

	bags = sk_PKCS12_SAFEBAG_new_null ();

	/* Add any more certificates asked for */
	if (certfile) {
		STACK_OF(X509) *morecerts=NULL;
		if(!(morecerts = load_certs(bio_err, certfile, FORMAT_PEM,
					    NULL, e,
					    "certificates from certfile"))) {
			goto export_end;
		}
		while(sk_X509_num(morecerts) > 0) {
			sk_X509_push(certs, sk_X509_shift(morecerts));
		}
		sk_X509_free(morecerts);
 	}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("building chain");
#endif

	/* If chaining get chain from user cert */
	if (chain) {
        	int vret;
		STACK_OF(X509) *chain2;
		X509_STORE *store = X509_STORE_new();
		if (!store)
			{
			BIO_printf (bio_err, "Memory allocation error\n");
			goto export_end;
			}
		if (!X509_STORE_load_locations(store, CAfile, CApath))
			X509_STORE_set_default_paths (store);

		vret = get_cert_chain (ucert, store, &chain2);
		X509_STORE_free(store);

		if (!vret) {
		    /* Exclude verified certificate */
		    for (i = 1; i < sk_X509_num (chain2) ; i++) 
			sk_X509_push(certs, sk_X509_value (chain2, i));
		    /* Free first certificate */
		    X509_free(sk_X509_value(chain2, 0));
		    sk_X509_free(chain2);
		} else {
			BIO_printf (bio_err, "Error %s getting chain.\n",
					X509_verify_cert_error_string(vret));
			goto export_end;
		}			
    	}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("building bags");
#endif

	/* We now have loads of certificates: include them all */
	for(i = 0; i < sk_X509_num(certs); i++) {
		X509 *cert = NULL;
		cert = sk_X509_value(certs, i);
		bag = PKCS12_x5092certbag(cert);
		/* If it matches private key set id */
		if(cert == ucert) {
			if(name) PKCS12_add_friendlyname(bag, name, -1);
			PKCS12_add_localkeyid(bag, keyid, keyidlen);
		} else if((catmp = sk_shift(canames))) 
				PKCS12_add_friendlyname(bag, catmp, -1);
		sk_PKCS12_SAFEBAG_push(bags, bag);
	}
	sk_X509_pop_free(certs, X509_free);
	certs = NULL;

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("encrypting bags");
#endif

	if(!noprompt &&
		EVP_read_pw_string(pass, sizeof pass, "Enter Export Password:"******"Can't read Password\n");
	    goto export_end;
        }
	if (!twopass) BUF_strlcpy(macpass, pass, sizeof macpass);
	/* Turn certbags into encrypted authsafe */
	authsafe = PKCS12_pack_p7encdata(cert_pbe, cpass, -1, NULL, 0,
								 iter, bags);
	sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
	bags = NULL;

	if (!authsafe) {
		ERR_print_errors (bio_err);
		goto export_end;
	}

	safes = sk_PKCS7_new_null ();
	sk_PKCS7_push (safes, authsafe);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("building shrouded key bag");
#endif

	/* Make a shrouded key bag */
	p8 = EVP_PKEY2PKCS8 (key);
	if(keytype) PKCS8_add_keyusage(p8, keytype);
	bag = PKCS12_MAKE_SHKEYBAG(key_pbe, cpass, -1, NULL, 0, iter, p8);
	PKCS8_PRIV_KEY_INFO_free(p8);
	p8 = NULL;
        if (name) PKCS12_add_friendlyname (bag, name, -1);
	if(csp_name) PKCS12_add_CSPName_asc(bag, csp_name, -1);
	PKCS12_add_localkeyid (bag, keyid, keyidlen);
	bags = sk_PKCS12_SAFEBAG_new_null();
	sk_PKCS12_SAFEBAG_push (bags, bag);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("encrypting shrouded key bag");
#endif

	/* Turn it into unencrypted safe bag */
	authsafe = PKCS12_pack_p7data (bags);
	sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
	bags = NULL;
	sk_PKCS7_push (safes, authsafe);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("building pkcs12");
#endif

	p12 = PKCS12_init(NID_pkcs7_data);

	PKCS12_pack_authsafes(p12, safes);

	sk_PKCS7_pop_free(safes, PKCS7_free);
	safes = NULL;

	PKCS12_set_mac (p12, mpass, -1, NULL, 0, maciter, NULL);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("writing pkcs12");
#endif

	i2d_PKCS12_bio (out, p12);

	ret = 0;

    export_end:
#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_pop_info();
	CRYPTO_push_info("process -export_cert: freeing");
#endif

	if (key) EVP_PKEY_free(key);
	if (certs) sk_X509_pop_free(certs, X509_free);
	if (safes) sk_PKCS7_pop_free(safes, PKCS7_free);
	if (bags) sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
#endif
	goto end;
	
    }

    if (!(p12 = d2i_PKCS12_bio (in, NULL))) {
	ERR_print_errors(bio_err);
	goto end;
    }

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read import password");
#endif
    if(!noprompt && EVP_read_pw_string(pass, sizeof pass, "Enter Import Password:"******"Can't read Password\n");
	goto end;
    }
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif

    if (!twopass) BUF_strlcpy(macpass, pass, sizeof macpass);

    if (options & INFO) BIO_printf (bio_err, "MAC Iteration %ld\n", p12->mac->iter ? ASN1_INTEGER_get (p12->mac->iter) : 1);
    if(macver) {
#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("verify MAC");
#endif
	/* If we enter empty password try no password first */
	if(!mpass[0] && PKCS12_verify_mac(p12, NULL, 0)) {
		/* If mac and crypto pass the same set it to NULL too */
		if(!twopass) cpass = NULL;
	} else if (!PKCS12_verify_mac(p12, mpass, -1)) {
	    BIO_printf (bio_err, "Mac verify error: invalid password?\n");
	    ERR_print_errors (bio_err);
	    goto end;
	}
	BIO_printf (bio_err, "MAC verified OK\n");
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    }

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("output keys and certificates");
#endif
    if (!dump_certs_keys_p12 (out, p12, cpass, -1, options, passout)) {
	BIO_printf(bio_err, "Error outputting keys and certificates\n");
	ERR_print_errors (bio_err);
	goto end;
    }
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    ret = 0;
 end:
    if (p12) PKCS12_free(p12);
    if(export_cert || inrand) app_RAND_write_file(NULL, bio_err);
#ifdef CRYPTO_MDEBUG
    CRYPTO_remove_all_info();
#endif
    BIO_free(in);
    BIO_free_all(out);
    if (canames) sk_free(canames);
    if(passin) OPENSSL_free(passin);
    if(passout) OPENSSL_free(passout);
    apps_shutdown();
    OPENSSL_EXIT(ret);
}
Пример #14
0
int BIO_dump_indent_cb(int (*cb)(const void *data, size_t len, void *u),
	void *u, const char *s, int len, int indent)
	{
	int ret=0;
	char buf[288+1],tmp[20],str[128+1];
	int i,j,rows,trc;
	unsigned char ch;
	int dump_width;

	trc=0;

#ifdef TRUNCATE
	for(; (len > 0) && ((s[len-1] == ' ') || (s[len-1] == '\0')); len--)
		trc++;
#endif

	if (indent < 0)
		indent = 0;
	if (indent)
		{
		if (indent > 128) indent=128;
		memset(str,' ',indent);
		}
	str[indent]='\0';

	dump_width=DUMP_WIDTH_LESS_INDENT(indent);
	rows=(len/dump_width);
	if ((rows*dump_width)<len)
		rows++;
	for(i=0;i<rows;i++)
		{
		buf[0]='\0';	/* start with empty string */
		BUF_strlcpy(buf,str,sizeof buf);
		BIO_snprintf(tmp,sizeof tmp,"%04x - ",i*dump_width);
		BUF_strlcat(buf,tmp,sizeof buf);
		for(j=0;j<dump_width;j++)
			{
			if (((i*dump_width)+j)>=len)
				{
				BUF_strlcat(buf,"   ",sizeof buf);
				}
			else
				{
				ch=((unsigned char)*(s+i*dump_width+j)) & 0xff;
				BIO_snprintf(tmp,sizeof tmp,"%02x%c",ch,
					j==7?'-':' ');
				BUF_strlcat(buf,tmp,sizeof buf);
				}
			}
		BUF_strlcat(buf,"  ",sizeof buf);
		for(j=0;j<dump_width;j++)
			{
			if (((i*dump_width)+j)>=len)
				break;
			ch=((unsigned char)*(s+i*dump_width+j)) & 0xff;
#ifndef CHARSET_EBCDIC
			BIO_snprintf(tmp,sizeof tmp,"%c",
				((ch>=' ')&&(ch<='~'))?ch:'.');
#else
			BIO_snprintf(tmp,sizeof tmp,"%c",
				((ch>=os_toascii[' '])&&(ch<=os_toascii['~']))
				? os_toebcdic[ch]
				: '.');
#endif
			BUF_strlcat(buf,tmp,sizeof buf);
			}
		BUF_strlcat(buf,"\n",sizeof buf);
		/* if this is the last call then update the ddt_dump thing so
		 * that we will move the selection point in the debug window
		 */
		ret+=cb((void *)buf,strlen(buf),u);
		}
#ifdef TRUNCATE
	if (trc > 0)
		{
		BIO_snprintf(buf,sizeof buf,"%s%04x - <SPACES/NULS>\n",str,
			len+trc);
		ret+=cb((void *)buf,strlen(buf),u);
		}
#endif
	return(ret);
	}
Пример #15
0
int OBJ_obj2txt(char *buf, int buf_len, const ASN1_OBJECT *a, int no_name)
{
  int i,idx=0,n=0,len,nid;
  unsigned long l;
  unsigned char *p;
  const char *s;
  char tbuf[DECIMAL_SIZE(i)+DECIMAL_SIZE(l)+2];

  if (buf_len <= 0) return(0);

  if ((a == NULL) || (a->data == NULL)) {
    buf[0]='\0';
    return(0);
  }

  if (no_name || (nid=OBJ_obj2nid(a)) == NID_undef) {
    len=a->length;
    p=a->data;

    idx=0;
    l=0;
    while (idx < a->length) {
      l|=(p[idx]&0x7f);
      if (!(p[idx] & 0x80)) break;
      l<<=7L;
      idx++;
    }
    idx++;
    i=(int)(l/40);
    if (i > 2) i=2;
    l-=(long)(i*40);

    BIO_snprintf(tbuf,sizeof tbuf,"%d.%lu",i,l);
    i=strlen(tbuf);
    BUF_strlcpy(buf,tbuf,buf_len);
    buf_len-=i;
    buf+=i;
    n+=i;

    l=0;
    for (; idx<len; idx++) {
      l|=p[idx]&0x7f;
      if (!(p[idx] & 0x80)) {
        BIO_snprintf(tbuf,sizeof tbuf,".%lu",l);
        i=strlen(tbuf);
        if (buf_len > 0)
          BUF_strlcpy(buf,tbuf,buf_len);
        buf_len-=i;
        buf+=i;
        n+=i;
        l=0;
      }
      l<<=7L;
    }
  } else {
    s=OBJ_nid2ln(nid);
    if (s == NULL)
      s=OBJ_nid2sn(nid);
    BUF_strlcpy(buf,s,buf_len);
    n=strlen(s);
  }
  return(n);
}
Пример #16
0
static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
{
    long ret=1;
    FILE *fp=(FILE *)b->ptr;
    FILE **fpp;
    char p[4];

    switch (cmd)
    {
    case BIO_C_FILE_SEEK:
    case BIO_CTRL_RESET:
        ret=(long)fseek(fp,num,0);
        break;
    case BIO_CTRL_EOF:
        ret=(long)feof(fp);
        break;
    case BIO_C_FILE_TELL:
    case BIO_CTRL_INFO:
        ret=ftell(fp);
        break;
    case BIO_C_SET_FILE_PTR:
        file_free(b);
        b->shutdown=(int)num&BIO_CLOSE;
        b->ptr=(char *)ptr;
        b->init=1;
#if defined(OPENSSL_SYS_WINDOWS)
        if (num & BIO_FP_TEXT)
            _setmode(fileno((FILE *)ptr),_O_TEXT);
        else
            _setmode(fileno((FILE *)ptr),_O_BINARY);
#elif defined(OPENSSL_SYS_MSDOS)
        {
            int fd = fileno((FILE*)ptr);
            /* Set correct text/binary mode */
            if (num & BIO_FP_TEXT)
                _setmode(fd,_O_TEXT);
            /* Dangerous to set stdin/stdout to raw (unless redirected) */
            else
            {
                if (fd == STDIN_FILENO || fd == STDOUT_FILENO)
                {
                    if (isatty(fd) <= 0)
                        _setmode(fd,_O_BINARY);
                }
                else
                    _setmode(fd,_O_BINARY);
            }
        }
#elif defined(OPENSSL_SYS_OS2)
        if (num & BIO_FP_TEXT)
            setmode(fileno((FILE *)ptr), O_TEXT);
        else
            setmode(fileno((FILE *)ptr), O_BINARY);
#endif
        break;
    case BIO_C_SET_FILENAME:
        file_free(b);
        b->shutdown=(int)num&BIO_CLOSE;
        if (num & BIO_FP_APPEND)
        {
            if (num & BIO_FP_READ)
                BUF_strlcpy(p,"a+",sizeof p);
            else	BUF_strlcpy(p,"a",sizeof p);
        }
        else if ((num & BIO_FP_READ) && (num & BIO_FP_WRITE))
            BUF_strlcpy(p,"r+",sizeof p);
        else if (num & BIO_FP_WRITE)
            BUF_strlcpy(p,"w",sizeof p);
        else if (num & BIO_FP_READ)
            BUF_strlcpy(p,"r",sizeof p);
        else
        {
            BIOerr(BIO_F_FILE_CTRL,BIO_R_BAD_FOPEN_MODE);
            ret=0;
            break;
        }
#if defined(OPENSSL_SYS_MSDOS) || defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_OS2)
        if (!(num & BIO_FP_TEXT))
            strcat(p,"b");
        else
            strcat(p,"t");
#endif
        fp=fopen(ptr,p);
        if (fp == NULL)
        {
            SYSerr(SYS_F_FOPEN,get_last_sys_error());
            ERR_add_error_data(5,"fopen('",ptr,"','",p,"')");
            BIOerr(BIO_F_FILE_CTRL,ERR_R_SYS_LIB);
            ret=0;
            break;
        }
        b->ptr=(char *)fp;
        b->init=1;
        break;
    case BIO_C_GET_FILE_PTR:
        /* the ptr parameter is actually a FILE ** in this case. */
        if (ptr != NULL)
        {
            fpp=(FILE **)ptr;
            *fpp=(FILE *)b->ptr;
        }
        break;
    case BIO_CTRL_GET_CLOSE:
        ret=(long)b->shutdown;
        break;
    case BIO_CTRL_SET_CLOSE:
        b->shutdown=(int)num;
        break;
    case BIO_CTRL_FLUSH:
        fflush((FILE *)b->ptr);
        break;
    case BIO_CTRL_DUP:
        ret=1;
        break;

    case BIO_CTRL_WPENDING:
    case BIO_CTRL_PENDING:
    case BIO_CTRL_PUSH:
    case BIO_CTRL_POP:
    default:
        ret=0;
        break;
    }
    return(ret);
}
Пример #17
0
int UI_set_result(UI *ui, UI_STRING *uis, const char *result)
{
    int l = strlen(result);

    ui->flags &= ~UI_FLAG_REDOABLE;

    if (!uis)
        return -1;
    switch (uis->type) {
    case UIT_PROMPT:
    case UIT_VERIFY:
        {
            char number1[DECIMAL_SIZE(uis->_.string_data.result_minsize) + 1];
            char number2[DECIMAL_SIZE(uis->_.string_data.result_maxsize) + 1];

            BIO_snprintf(number1, sizeof(number1), "%d",
                         uis->_.string_data.result_minsize);
            BIO_snprintf(number2, sizeof(number2), "%d",
                         uis->_.string_data.result_maxsize);

            if (l < uis->_.string_data.result_minsize) {
                ui->flags |= UI_FLAG_REDOABLE;
                UIerr(UI_F_UI_SET_RESULT, UI_R_RESULT_TOO_SMALL);
                ERR_add_error_data(5, "You must type in ",
                                   number1, " to ", number2, " characters");
                return -1;
            }
            if (l > uis->_.string_data.result_maxsize) {
                ui->flags |= UI_FLAG_REDOABLE;
                UIerr(UI_F_UI_SET_RESULT, UI_R_RESULT_TOO_LARGE);
                ERR_add_error_data(5, "You must type in ",
                                   number1, " to ", number2, " characters");
                return -1;
            }
        }

        if (!uis->result_buf) {
            UIerr(UI_F_UI_SET_RESULT, UI_R_NO_RESULT_BUFFER);
            return -1;
        }

        BUF_strlcpy(uis->result_buf, result,
                    uis->_.string_data.result_maxsize + 1);
        break;
    case UIT_BOOLEAN:
        {
            const char *p;

            if (!uis->result_buf) {
                UIerr(UI_F_UI_SET_RESULT, UI_R_NO_RESULT_BUFFER);
                return -1;
            }

            uis->result_buf[0] = '\0';
            for (p = result; *p; p++) {
                if (strchr(uis->_.boolean_data.ok_chars, *p)) {
                    uis->result_buf[0] = uis->_.boolean_data.ok_chars[0];
                    break;
                }
                if (strchr(uis->_.boolean_data.cancel_chars, *p)) {
                    uis->result_buf[0] = uis->_.boolean_data.cancel_chars[0];
                    break;
                }
            }
        }
    default:
        break;
    }
    return 0;
}
Пример #18
0
int srp_main(int argc, char **argv)
{
    CA_DB *db = NULL;
    DB_ATTR db_attr;
    CONF *conf = NULL;
    int gNindex = -1, maxgN = -1, ret = 1, errors = 0, verbose =
        0, i, doupdatedb = 0;
    int mode = OPT_ERR;
    char *user = NULL, *passinarg = NULL, *passoutarg = NULL;
    char *passin = NULL, *passout = NULL, *gN = NULL, *userinfo = NULL;
    char *randfile = NULL, *tofree = NULL, *section = NULL;
    char **gNrow = NULL, *configfile = NULL, *dbfile = NULL, **pp, *prog;
    long errorline = -1;
    OPTION_CHOICE o;

    prog = opt_init(argc, argv, srp_options);
    while ((o = opt_next()) != OPT_EOF) {
        switch (o) {
        case OPT_EOF:
        case OPT_ERR:
 opthelp:
            BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
            goto end;
        case OPT_HELP:
            opt_help(srp_options);
            ret = 0;
            goto end;
        case OPT_VERBOSE:
            verbose++;
            break;
        case OPT_CONFIG:
            configfile = opt_arg();
            break;
        case OPT_NAME:
            section = opt_arg();
            break;
        case OPT_SRPVFILE:
            dbfile = opt_arg();
            break;
        case OPT_ADD:
        case OPT_DELETE:
        case OPT_MODIFY:
        case OPT_LIST:
            if (mode != OPT_ERR) {
                BIO_printf(bio_err,
                           "%s: Only one of -add/delete-modify/-list\n",
                           prog);
                goto opthelp;
            }
            mode = o;
            break;
        case OPT_GN:
            gN = opt_arg();
            break;
        case OPT_USERINFO:
            userinfo = opt_arg();
            break;
        case OPT_PASSIN:
            passinarg = opt_arg();
            break;
        case OPT_PASSOUT:
            passoutarg = opt_arg();
            break;
        case OPT_ENGINE:
            (void)setup_engine(opt_arg(), 0);
            break;
        }
    }
    argc = opt_num_rest();
    argv = opt_rest();

    if (dbfile && configfile) {
        BIO_printf(bio_err,
                   "-dbfile and -configfile cannot be specified together.\n");
        goto end;
    }
    if (mode == OPT_ERR) {
        BIO_printf(bio_err,
                   "Exactly one of the options -add, -delete, -modify -list must be specified.\n");
        goto opthelp;
    }
    if ((mode == OPT_DELETE || mode == OPT_MODIFY || mode == OPT_ADD)
        && argc < 1) {
        BIO_printf(bio_err,
                   "Need at least one user for options -add, -delete, -modify. \n");
        goto opthelp;
    }
    if ((passin || passout) && argc != 1) {
        BIO_printf(bio_err,
                   "-passin, -passout arguments only valid with one user.\n");
        goto opthelp;
    }

    if (!app_passwd(passinarg, passoutarg, &passin, &passout)) {
        BIO_printf(bio_err, "Error getting passwords\n");
        goto end;
    }

    if (!dbfile) {

        /*****************************************************************/
        tofree = NULL;
        if (configfile == NULL)
            configfile = getenv("OPENSSL_CONF");
        if (configfile == NULL)
            configfile = getenv("SSLEAY_CONF");
        if (configfile == NULL) {
            const char *s = X509_get_default_cert_area();
            size_t len = strlen(s) + 1 + sizeof(CONFIG_FILE);

            tofree = app_malloc(len, "config filename space");
# ifdef OPENSSL_SYS_VMS
            strcpy(tofree, s);
# else
            BUF_strlcpy(tofree, s, len);
            BUF_strlcat(tofree, "/", len);
# endif
            BUF_strlcat(tofree, CONFIG_FILE, len);
            configfile = tofree;
        }

        if (verbose)
            BIO_printf(bio_err, "Using configuration from %s\n", configfile);
        conf = NCONF_new(NULL);
        if (NCONF_load(conf, configfile, &errorline) <= 0) {
            if (errorline <= 0)
                BIO_printf(bio_err, "error loading the config file '%s'\n",
                           configfile);
            else
                BIO_printf(bio_err, "error on line %ld of config file '%s'\n",
                           errorline, configfile);
            goto end;
        }
        OPENSSL_free(tofree);
        tofree = NULL;

        /* Lets get the config section we are using */
        if (section == NULL) {
            if (verbose)
                BIO_printf(bio_err,
                           "trying to read " ENV_DEFAULT_SRP
                           " in \" BASE_SECTION \"\n");

            section = NCONF_get_string(conf, BASE_SECTION, ENV_DEFAULT_SRP);
            if (section == NULL) {
                lookup_fail(BASE_SECTION, ENV_DEFAULT_SRP);
                goto end;
            }
        }

        if (randfile == NULL && conf)
            randfile = NCONF_get_string(conf, BASE_SECTION, "RANDFILE");

        if (verbose)
            BIO_printf(bio_err,
                       "trying to read " ENV_DATABASE " in section \"%s\"\n",
                       section);

        if ((dbfile = NCONF_get_string(conf, section, ENV_DATABASE)) == NULL) {
            lookup_fail(section, ENV_DATABASE);
            goto end;
        }

    }
    if (randfile == NULL)
        ERR_clear_error();
    else
        app_RAND_load_file(randfile, 0);

    if (verbose)
        BIO_printf(bio_err, "Trying to read SRP verifier file \"%s\"\n",
                   dbfile);

    db = load_index(dbfile, &db_attr);
    if (db == NULL)
        goto end;

    /* Lets check some fields */
    for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++) {
        pp = sk_OPENSSL_PSTRING_value(db->db->data, i);

        if (pp[DB_srptype][0] == DB_SRP_INDEX) {
            maxgN = i;
            if ((gNindex < 0) && (gN != NULL) && strcmp(gN, pp[DB_srpid]) == 0)
                gNindex = i;

            print_index(db, i, verbose > 1);
        }
    }

    if (verbose)
        BIO_printf(bio_err, "Database initialised\n");

    if (gNindex >= 0) {
        gNrow = sk_OPENSSL_PSTRING_value(db->db->data, gNindex);
        print_entry(db, gNindex, verbose > 1, "Default g and N");
    } else if (maxgN > 0 && !SRP_get_default_gN(gN)) {
        BIO_printf(bio_err, "No g and N value for index \"%s\"\n", gN);
        goto end;
    } else {
        if (verbose)
            BIO_printf(bio_err, "Database has no g N information.\n");
        gNrow = NULL;
    }

    if (verbose > 1)
        BIO_printf(bio_err, "Starting user processing\n");

    if (argc > 0)
        user = *(argv++);

    while (mode == OPT_LIST || user) {
        int userindex = -1;
        if (user)
            if (verbose > 1)
                BIO_printf(bio_err, "Processing user \"%s\"\n", user);
        if ((userindex = get_index(db, user, 'U')) >= 0) {
            print_user(db, userindex, (verbose > 0)
                       || mode == OPT_LIST);
        }

        if (mode == OPT_LIST) {
            if (user == NULL) {
                BIO_printf(bio_err, "List all users\n");

                for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++) {
                    print_user(db, i, 1);
                }
            } else if (userindex < 0) {
                BIO_printf(bio_err,
                           "user \"%s\" does not exist, ignored. t\n", user);
                errors++;
            }
        } else if (mode == OPT_ADD) {
            if (userindex >= 0) {
                /* reactivation of a new user */
                char **row =
                    sk_OPENSSL_PSTRING_value(db->db->data, userindex);
                BIO_printf(bio_err, "user \"%s\" reactivated.\n", user);
                row[DB_srptype][0] = 'V';

                doupdatedb = 1;
            } else {
                char *row[DB_NUMBER];
                char *gNid;
                row[DB_srpverifier] = NULL;
                row[DB_srpsalt] = NULL;
                row[DB_srpinfo] = NULL;
                if (!
                    (gNid =
                     srp_create_user(user, &(row[DB_srpverifier]),
                                     &(row[DB_srpsalt]),
                                     gNrow ? gNrow[DB_srpsalt] : gN,
                                     gNrow ? gNrow[DB_srpverifier] : NULL,
                                     passout, verbose))) {
                    BIO_printf(bio_err,
                               "Cannot create srp verifier for user \"%s\", operation abandoned .\n",
                               user);
                    errors++;
                    goto end;
                }
                row[DB_srpid] = BUF_strdup(user);
                row[DB_srptype] = BUF_strdup("v");
                row[DB_srpgN] = BUF_strdup(gNid);

                if ((row[DB_srpid] == NULL)
                    || (row[DB_srpgN] == NULL)
                    || (row[DB_srptype] == NULL)
                    || (row[DB_srpverifier] == NULL)
                    || (row[DB_srpsalt] == NULL)
                    || (userinfo
                        && ((row[DB_srpinfo] = BUF_strdup(userinfo)) == NULL))
                    || !update_index(db, row)) {
                    OPENSSL_free(row[DB_srpid]);
                    OPENSSL_free(row[DB_srpgN]);
                    OPENSSL_free(row[DB_srpinfo]);
                    OPENSSL_free(row[DB_srptype]);
                    OPENSSL_free(row[DB_srpverifier]);
                    OPENSSL_free(row[DB_srpsalt]);
                    goto end;
                }
                doupdatedb = 1;
            }
        } else if (mode == OPT_MODIFY) {
            if (userindex < 0) {
                BIO_printf(bio_err,
                           "user \"%s\" does not exist, operation ignored.\n",
                           user);
                errors++;
            } else {

                char **row =
                    sk_OPENSSL_PSTRING_value(db->db->data, userindex);
                char type = row[DB_srptype][0];
                if (type == 'v') {
                    BIO_printf(bio_err,
                               "user \"%s\" already updated, operation ignored.\n",
                               user);
                    errors++;
                } else {
                    char *gNid;

                    if (row[DB_srptype][0] == 'V') {
                        int user_gN;
                        char **irow = NULL;
                        if (verbose)
                            BIO_printf(bio_err,
                                       "Verifying password for user \"%s\"\n",
                                       user);
                        if ((user_gN =
                             get_index(db, row[DB_srpgN], DB_SRP_INDEX)) >= 0)
                            irow =
                                sk_OPENSSL_PSTRING_value(db->db->data,
                                                         userindex);

                        if (!srp_verify_user
                            (user, row[DB_srpverifier], row[DB_srpsalt],
                             irow ? irow[DB_srpsalt] : row[DB_srpgN],
                             irow ? irow[DB_srpverifier] : NULL, passin,
                             verbose)) {
                            BIO_printf(bio_err,
                                       "Invalid password for user \"%s\", operation abandoned.\n",
                                       user);
                            errors++;
                            goto end;
                        }
                    }
                    if (verbose)
                        BIO_printf(bio_err, "Password for user \"%s\" ok.\n",
                                   user);

                    if (!
                        (gNid =
                         srp_create_user(user, &(row[DB_srpverifier]),
                                         &(row[DB_srpsalt]),
                                         gNrow ? gNrow[DB_srpsalt] : NULL,
                                         gNrow ? gNrow[DB_srpverifier] : NULL,
                                         passout, verbose))) {
                        BIO_printf(bio_err,
                                   "Cannot create srp verifier for user \"%s\", operation abandoned.\n",
                                   user);
                        errors++;
                        goto end;
                    }

                    row[DB_srptype][0] = 'v';
                    row[DB_srpgN] = BUF_strdup(gNid);

                    if (row[DB_srpid] == NULL
                        || row[DB_srpgN] == NULL
                        || row[DB_srptype] == NULL
                        || row[DB_srpverifier] == NULL
                        || row[DB_srpsalt] == NULL
                        || (userinfo
                            && ((row[DB_srpinfo] = BUF_strdup(userinfo))
                                == NULL)))
                        goto end;

                    doupdatedb = 1;
                }
            }
        } else if (mode == OPT_DELETE) {
            if (userindex < 0) {
                BIO_printf(bio_err,
                           "user \"%s\" does not exist, operation ignored. t\n",
                           user);
                errors++;
            } else {
                char **xpp = sk_OPENSSL_PSTRING_value(db->db->data, userindex);

                BIO_printf(bio_err, "user \"%s\" revoked. t\n", user);
                xpp[DB_srptype][0] = 'R';
                doupdatedb = 1;
            }
        }
        if (--argc > 0)
            user = *(argv++);
        else {
            user = NULL;
        }
    }

    if (verbose)
        BIO_printf(bio_err, "User procession done.\n");

    if (doupdatedb) {
        /* Lets check some fields */
        for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++) {
            pp = sk_OPENSSL_PSTRING_value(db->db->data, i);

            if (pp[DB_srptype][0] == 'v') {
                pp[DB_srptype][0] = 'V';
                print_user(db, i, verbose);
            }
        }

        if (verbose)
            BIO_printf(bio_err, "Trying to update srpvfile.\n");
        if (!save_index(dbfile, "new", db))
            goto end;

        if (verbose)
            BIO_printf(bio_err, "Temporary srpvfile created.\n");
        if (!rotate_index(dbfile, "new", "old"))
            goto end;

        if (verbose)
            BIO_printf(bio_err, "srpvfile updated.\n");
    }

    ret = (errors != 0);
 end:
    if (errors != 0)
        if (verbose)
            BIO_printf(bio_err, "User errors %d.\n", errors);

    if (verbose)
        BIO_printf(bio_err, "SRP terminating with code %d.\n", ret);
    OPENSSL_free(tofree);
    if (ret)
        ERR_print_errors(bio_err);
    if (randfile)
        app_RAND_write_file(randfile);
    NCONF_free(conf);
    free_index(db);
    OBJ_cleanup();
    return (ret);
}
Пример #19
0
int MAIN(int argc, char **argv)
{
    ENGINE *e = NULL;
    char *infile=NULL, *outfile=NULL, *keyname = NULL;	
    char *certfile=NULL;
    BIO *in=NULL, *out = NULL;
    char **args;
    char *name = NULL;
    char *csp_name = NULL;
    int add_lmk = 0;
    PKCS12 *p12 = NULL;
    char pass[50], macpass[50];
    int export_cert = 0;
    int options = 0;
    int chain = 0;
    int badarg = 0;
    int iter = PKCS12_DEFAULT_ITER;
    int maciter = PKCS12_DEFAULT_ITER;
    int twopass = 0;
    int keytype = 0;
    int cert_pbe = NID_pbe_WithSHA1And40BitRC2_CBC;
    int key_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
    int ret = 1;
    int macver = 1;
    int noprompt = 0;
    STACK_OF(OPENSSL_STRING) *canames = NULL;
    char *cpass = NULL, *mpass = NULL;
    char *passargin = NULL, *passargout = NULL, *passarg = NULL;
    char *passin = NULL, *passout = NULL;
    char *inrand = NULL;
    char *macalg = NULL;
    char *CApath = NULL, *CAfile = NULL;
#ifndef OPENSSL_NO_ENGINE
    char *engine=NULL;
#endif

    apps_startup();

    enc = EVP_des_ede3_cbc();
    if (bio_err == NULL ) bio_err = BIO_new_fp (stderr, BIO_NOCLOSE);

	if (!load_config(bio_err, NULL))
		goto end;

    args = argv + 1;


    while (*args) {
	if (*args[0] == '-') {
		if (!strcmp (*args, "-nokeys")) options |= NOKEYS;
		else if (!strcmp (*args, "-keyex")) keytype = KEY_EX;
		else if (!strcmp (*args, "-keysig")) keytype = KEY_SIG;
		else if (!strcmp (*args, "-nocerts")) options |= NOCERTS;
		else if (!strcmp (*args, "-clcerts")) options |= CLCERTS;
		else if (!strcmp (*args, "-cacerts")) options |= CACERTS;
		else if (!strcmp (*args, "-noout")) options |= (NOKEYS|NOCERTS);
		else if (!strcmp (*args, "-info")) options |= INFO;
		else if (!strcmp (*args, "-chain")) chain = 1;
		else if (!strcmp (*args, "-twopass")) twopass = 1;
		else if (!strcmp (*args, "-nomacver")) macver = 0;
		else if (!strcmp (*args, "-descert"))
    			cert_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
		else if (!strcmp (*args, "-export")) export_cert = 1;
		else if (!strcmp (*args, "-des")) enc=EVP_des_cbc();
		else if (!strcmp (*args, "-des3")) enc = EVP_des_ede3_cbc();
#ifndef OPENSSL_NO_IDEA
		else if (!strcmp (*args, "-idea")) enc=EVP_idea_cbc();
#endif
#ifndef OPENSSL_NO_SEED
		else if (!strcmp(*args, "-seed")) enc=EVP_seed_cbc();
#endif
#ifndef OPENSSL_NO_AES
		else if (!strcmp(*args,"-aes128")) enc=EVP_aes_128_cbc();
		else if (!strcmp(*args,"-aes192")) enc=EVP_aes_192_cbc();
		else if (!strcmp(*args,"-aes256")) enc=EVP_aes_256_cbc();
#endif
#ifndef OPENSSL_NO_CAMELLIA
		else if (!strcmp(*args,"-camellia128")) enc=EVP_camellia_128_cbc();
		else if (!strcmp(*args,"-camellia192")) enc=EVP_camellia_192_cbc();
		else if (!strcmp(*args,"-camellia256")) enc=EVP_camellia_256_cbc();
#endif
		else if (!strcmp (*args, "-noiter")) iter = 1;
		else if (!strcmp (*args, "-maciter"))
					 maciter = PKCS12_DEFAULT_ITER;
		else if (!strcmp (*args, "-nomaciter"))
					 maciter = 1;
		else if (!strcmp (*args, "-nomac"))
					 maciter = -1;
		else if (!strcmp (*args, "-macalg"))
		    if (args[1]) {
			args++;	
			macalg = *args;
		    } else badarg = 1;
		else if (!strcmp (*args, "-nodes")) enc=NULL;
		else if (!strcmp (*args, "-certpbe")) {
			if (!set_pbe(bio_err, &cert_pbe, *++args))
				badarg = 1;
		} else if (!strcmp (*args, "-keypbe")) {
			if (!set_pbe(bio_err, &key_pbe, *++args))
				badarg = 1;
		} else if (!strcmp (*args, "-rand")) {
		    if (args[1]) {
			args++;	
			inrand = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-inkey")) {
		    if (args[1]) {
			args++;	
			keyname = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-certfile")) {
		    if (args[1]) {
			args++;	
			certfile = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-name")) {
		    if (args[1]) {
			args++;	
			name = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-LMK"))
			add_lmk = 1;
		else if (!strcmp (*args, "-CSP")) {
		    if (args[1]) {
			args++;	
			csp_name = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-caname")) {
		    if (args[1]) {
			args++;	
			if (!canames) canames = sk_OPENSSL_STRING_new_null();
			sk_OPENSSL_STRING_push(canames, *args);
		    } else badarg = 1;
		} else if (!strcmp (*args, "-in")) {
		    if (args[1]) {
			args++;	
			infile = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-out")) {
		    if (args[1]) {
			args++;	
			outfile = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-passin")) {
		    if (args[1]) {
			args++;	
			passargin = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-passout")) {
		    if (args[1]) {
			args++;	
			passargout = *args;
		    } else badarg = 1;
		} else if (!strcmp (*args, "-password")) {
		    if (args[1]) {
			args++;	
			passarg = *args;
		    	noprompt = 1;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-CApath")) {
		    if (args[1]) {
			args++;	
			CApath = *args;
		    } else badarg = 1;
		} else if (!strcmp(*args,"-CAfile")) {
		    if (args[1]) {
			args++;	
			CAfile = *args;
		    } else badarg = 1;
#ifndef OPENSSL_NO_ENGINE
		} else if (!strcmp(*args,"-engine")) {
		    if (args[1]) {
			args++;	
			engine = *args;
		    } else badarg = 1;
#endif
		} else badarg = 1;

	} else badarg = 1;
	args++;
    }

    if (badarg) {
	BIO_printf (bio_err, "Usage: pkcs12 [options]\n");
	BIO_printf (bio_err, "where options are\n");
	BIO_printf (bio_err, "-export       output PKCS12 file\n");
	BIO_printf (bio_err, "-chain        add certificate chain\n");
	BIO_printf (bio_err, "-inkey file   private key if not infile\n");
	BIO_printf (bio_err, "-certfile f   add all certs in f\n");
	BIO_printf (bio_err, "-CApath arg   - PEM format directory of CA's\n");
	BIO_printf (bio_err, "-CAfile arg   - PEM format file of CA's\n");
	BIO_printf (bio_err, "-name \"name\"  use name as friendly name\n");
	BIO_printf (bio_err, "-caname \"nm\"  use nm as CA friendly name (can be used more than once).\n");
	BIO_printf (bio_err, "-in  infile   input filename\n");
	BIO_printf (bio_err, "-out outfile  output filename\n");
	BIO_printf (bio_err, "-noout        don't output anything, just verify.\n");
	BIO_printf (bio_err, "-nomacver     don't verify MAC.\n");
	BIO_printf (bio_err, "-nocerts      don't output certificates.\n");
	BIO_printf (bio_err, "-clcerts      only output client certificates.\n");
	BIO_printf (bio_err, "-cacerts      only output CA certificates.\n");
	BIO_printf (bio_err, "-nokeys       don't output private keys.\n");
	BIO_printf (bio_err, "-info         give info about PKCS#12 structure.\n");
	BIO_printf (bio_err, "-des          encrypt private keys with DES\n");
	BIO_printf (bio_err, "-des3         encrypt private keys with triple DES (default)\n");
#ifndef OPENSSL_NO_IDEA
	BIO_printf (bio_err, "-idea         encrypt private keys with idea\n");
#endif
#ifndef OPENSSL_NO_SEED
	BIO_printf (bio_err, "-seed         encrypt private keys with seed\n");
#endif
#ifndef OPENSSL_NO_AES
	BIO_printf (bio_err, "-aes128, -aes192, -aes256\n");
	BIO_printf (bio_err, "              encrypt PEM output with cbc aes\n");
#endif
#ifndef OPENSSL_NO_CAMELLIA
	BIO_printf (bio_err, "-camellia128, -camellia192, -camellia256\n");
	BIO_printf (bio_err, "              encrypt PEM output with cbc camellia\n");
#endif
	BIO_printf (bio_err, "-nodes        don't encrypt private keys\n");
	BIO_printf (bio_err, "-noiter       don't use encryption iteration\n");
	BIO_printf (bio_err, "-nomaciter    don't use MAC iteration\n");
	BIO_printf (bio_err, "-maciter      use MAC iteration\n");
	BIO_printf (bio_err, "-nomac        don't generate MAC\n");
	BIO_printf (bio_err, "-twopass      separate MAC, encryption passwords\n");
	BIO_printf (bio_err, "-descert      encrypt PKCS#12 certificates with triple DES (default RC2-40)\n");
	BIO_printf (bio_err, "-certpbe alg  specify certificate PBE algorithm (default RC2-40)\n");
	BIO_printf (bio_err, "-keypbe alg   specify private key PBE algorithm (default 3DES)\n");
	BIO_printf (bio_err, "-macalg alg   digest algorithm used in MAC (default SHA1)\n");
	BIO_printf (bio_err, "-keyex        set MS key exchange type\n");
	BIO_printf (bio_err, "-keysig       set MS key signature type\n");
	BIO_printf (bio_err, "-password p   set import/export password source\n");
	BIO_printf (bio_err, "-passin p     input file pass phrase source\n");
	BIO_printf (bio_err, "-passout p    output file pass phrase source\n");
#ifndef OPENSSL_NO_ENGINE
	BIO_printf (bio_err, "-engine e     use engine e, possibly a hardware device.\n");
#endif
	BIO_printf(bio_err,  "-rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
	BIO_printf(bio_err,  "              load the file (or the files in the directory) into\n");
	BIO_printf(bio_err,  "              the random number generator\n");
	BIO_printf(bio_err,  "-CSP name     Microsoft CSP name\n");
	BIO_printf(bio_err,  "-LMK          Add local machine keyset attribute to private key\n");
    	goto end;
    }

#ifndef OPENSSL_NO_ENGINE
    e = setup_engine(bio_err, engine, 0);
#endif

    if(passarg) {
	if(export_cert) passargout = passarg;
	else passargin = passarg;
    }

    if(!app_passwd(bio_err, passargin, passargout, &passin, &passout)) {
	BIO_printf(bio_err, "Error getting passwords\n");
	goto end;
    }

    if(!cpass) {
    	if(export_cert) cpass = passout;
    	else cpass = passin;
    }

    if(cpass) {
	mpass = cpass;
	noprompt = 1;
    } else {
	cpass = pass;
	mpass = macpass;
    }

    if(export_cert || inrand) {
    	app_RAND_load_file(NULL, bio_err, (inrand != NULL));
        if (inrand != NULL)
		BIO_printf(bio_err,"%ld semi-random bytes loaded\n",
			app_RAND_load_files(inrand));
    }
    ERR_load_crypto_strings();

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read files");
#endif

    if (!infile) in = BIO_new_fp(stdin, BIO_NOCLOSE);
    else in = BIO_new_file(infile, "rb");
    if (!in) {
	    BIO_printf(bio_err, "Error opening input file %s\n",
						infile ? infile : "<stdin>");
	    perror (infile);
	    goto end;
   }

#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
    CRYPTO_push_info("write files");
#endif

    if (!outfile) {
	out = BIO_new_fp(stdout, BIO_NOCLOSE);
#ifdef OPENSSL_SYS_VMS
	{
	    BIO *tmpbio = BIO_new(BIO_f_linebuffer());
	    out = BIO_push(tmpbio, out);
	}
#endif
    } else out = BIO_new_file(outfile, "wb");
    if (!out) {
	BIO_printf(bio_err, "Error opening output file %s\n",
						outfile ? outfile : "<stdout>");
	perror (outfile);
	goto end;
    }
    if (twopass) {
#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read MAC password");
#endif
	if(EVP_read_pw_string (macpass, sizeof macpass, "Enter MAC Password:"******"Can't read Password\n");
    	    goto end;
       	}
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    }

    if (export_cert) {
	EVP_PKEY *key = NULL;
	X509 *ucert = NULL, *x = NULL;
	STACK_OF(X509) *certs=NULL;
	const EVP_MD *macmd = NULL;
	unsigned char *catmp = NULL;
	int i;

	if ((options & (NOCERTS|NOKEYS)) == (NOCERTS|NOKEYS))
		{	
		BIO_printf(bio_err, "Nothing to do!\n");
		goto export_end;
		}

	if (options & NOCERTS)
		chain = 0;

#ifdef CRYPTO_MDEBUG
	CRYPTO_push_info("process -export_cert");
	CRYPTO_push_info("reading private key");
#endif
	if (!(options & NOKEYS))
		{
		key = load_key(bio_err, keyname ? keyname : infile,
				FORMAT_PEM, 1, passin, e, "private key");
		if (!key)
			goto export_end;
		}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from input");
#endif

	/* Load in all certs in input file */
	if(!(options & NOCERTS))
		{
		certs = load_certs(bio_err, infile, FORMAT_PEM, NULL, e,
							"certificates");
		if (!certs)
			goto export_end;

		if (key)
			{
			/* Look for matching private key */
			for(i = 0; i < sk_X509_num(certs); i++)
				{
				x = sk_X509_value(certs, i);
				if(X509_check_private_key(x, key))
					{
					ucert = x;
					/* Zero keyid and alias */
					X509_keyid_set1(ucert, NULL, 0);
					X509_alias_set1(ucert, NULL, 0);
					/* Remove from list */
					(void)sk_X509_delete(certs, i);
					break;
					}
				}
			if (!ucert)
				{
				BIO_printf(bio_err, "No certificate matches private key\n");
				goto export_end;
				}
			}

		}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from input 2");
#endif

	/* Add any more certificates asked for */
	if(certfile)
		{
		STACK_OF(X509) *morecerts=NULL;
		if(!(morecerts = load_certs(bio_err, certfile, FORMAT_PEM,
					    NULL, e,
					    "certificates from certfile")))
			goto export_end;
		while(sk_X509_num(morecerts) > 0)
			sk_X509_push(certs, sk_X509_shift(morecerts));
		sk_X509_free(morecerts);
 		}

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading certs from certfile");
#endif

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("building chain");
#endif

	/* If chaining get chain from user cert */
	if (chain) {
        	int vret;
		STACK_OF(X509) *chain2;
		X509_STORE *store = X509_STORE_new();
		if (!store)
			{
			BIO_printf (bio_err, "Memory allocation error\n");
			goto export_end;
			}
		if (!X509_STORE_load_locations(store, CAfile, CApath))
			X509_STORE_set_default_paths (store);

		vret = get_cert_chain (ucert, store, &chain2);
		X509_STORE_free(store);

		if (!vret) {
		    /* Exclude verified certificate */
		    for (i = 1; i < sk_X509_num (chain2) ; i++) 
			sk_X509_push(certs, sk_X509_value (chain2, i));
		    /* Free first certificate */
		    X509_free(sk_X509_value(chain2, 0));
		    sk_X509_free(chain2);
		} else {
			if (vret >= 0)
				BIO_printf (bio_err, "Error %s getting chain.\n",
					X509_verify_cert_error_string(vret));
			else
				ERR_print_errors(bio_err);
			goto export_end;
		}			
    	}

	/* Add any CA names */

	for (i = 0; i < sk_OPENSSL_STRING_num(canames); i++)
		{
		catmp = (unsigned char *)sk_OPENSSL_STRING_value(canames, i);
		X509_alias_set1(sk_X509_value(certs, i), catmp, -1);
		}

	if (csp_name && key)
		EVP_PKEY_add1_attr_by_NID(key, NID_ms_csp_name,
				MBSTRING_ASC, (unsigned char *)csp_name, -1);

	if (add_lmk && key)
		EVP_PKEY_add1_attr_by_NID(key, NID_LocalKeySet, 0, NULL, -1);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("reading password");
#endif

	if(!noprompt &&
		EVP_read_pw_string(pass, sizeof pass, "Enter Export Password:"******"Can't read Password\n");
	    	goto export_end;
        	}
	if (!twopass) BUF_strlcpy(macpass, pass, sizeof macpass);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("creating PKCS#12 structure");
#endif

	p12 = PKCS12_create(cpass, name, key, ucert, certs,
				key_pbe, cert_pbe, iter, -1, keytype);

	if (!p12)
		{
	    	ERR_print_errors (bio_err);
		goto export_end;
		}

	if (macalg)
		{
		macmd = EVP_get_digestbyname(macalg);
		if (!macmd)
			{
			BIO_printf(bio_err, "Unknown digest algorithm %s\n", 
						macalg);
			}
		}

	if (maciter != -1)
		PKCS12_set_mac(p12, mpass, -1, NULL, 0, maciter, macmd);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_push_info("writing pkcs12");
#endif

	i2d_PKCS12_bio(out, p12);

	ret = 0;

    export_end:
#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
	CRYPTO_pop_info();
	CRYPTO_push_info("process -export_cert: freeing");
#endif

	if (key) EVP_PKEY_free(key);
	if (certs) sk_X509_pop_free(certs, X509_free);
	if (ucert) X509_free(ucert);

#ifdef CRYPTO_MDEBUG
	CRYPTO_pop_info();
#endif
	goto end;
	
    }

    if (!(p12 = d2i_PKCS12_bio (in, NULL))) {
	ERR_print_errors(bio_err);
	goto end;
    }

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("read import password");
#endif
    if(!noprompt && EVP_read_pw_string(pass, sizeof pass, "Enter Import Password:"******"Can't read Password\n");
	goto end;
    }
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif

    if (!twopass) BUF_strlcpy(macpass, pass, sizeof macpass);

    if ((options & INFO) && p12->mac) BIO_printf (bio_err, "MAC Iteration %ld\n", p12->mac->iter ? ASN1_INTEGER_get (p12->mac->iter) : 1);
    if(macver) {
#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("verify MAC");
#endif
	/* If we enter empty password try no password first */
	if(!mpass[0] && PKCS12_verify_mac(p12, NULL, 0)) {
		/* If mac and crypto pass the same set it to NULL too */
		if(!twopass) cpass = NULL;
	} else if (!PKCS12_verify_mac(p12, mpass, -1)) {
	    BIO_printf (bio_err, "Mac verify error: invalid password?\n");
	    ERR_print_errors (bio_err);
	    goto end;
	}
	BIO_printf (bio_err, "MAC verified OK\n");
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    }

#ifdef CRYPTO_MDEBUG
    CRYPTO_push_info("output keys and certificates");
#endif
    if (!dump_certs_keys_p12 (out, p12, cpass, -1, options, passout)) {
	BIO_printf(bio_err, "Error outputting keys and certificates\n");
	ERR_print_errors (bio_err);
	goto end;
    }
#ifdef CRYPTO_MDEBUG
    CRYPTO_pop_info();
#endif
    ret = 0;
 end:
    if (p12) PKCS12_free(p12);
    if(export_cert || inrand) app_RAND_write_file(NULL, bio_err);
#ifdef CRYPTO_MDEBUG
    CRYPTO_remove_all_info();
#endif
    BIO_free(in);
    BIO_free_all(out);
    if (canames) sk_OPENSSL_STRING_free(canames);
    if(passin) OPENSSL_free(passin);
    if(passout) OPENSSL_free(passout);
    apps_shutdown();
    OPENSSL_EXIT(ret);
}
Пример #20
0
static int def_load_bio(CONF *conf, BIO *in, long *line)
	{
/* The macro BUFSIZE conflicts with a system macro in VxWorks */
#define CONFBUFSIZE	512
	int bufnum=0,i,ii;
	BUF_MEM *buff=NULL;
	char *s,*p,*end;
	int again;
	long eline=0;
	char btmp[DECIMAL_SIZE(eline)+1];
	CONF_VALUE *v=NULL,*tv;
	CONF_VALUE *sv=NULL;
	char *section=NULL,*buf;
	STACK_OF(CONF_VALUE) *section_sk=NULL,*ts __UNUSED;
	char *start,*psection,*pname;
	void *h = (void *)(conf->data);

	if ((buff=BUF_MEM_new()) == NULL)
		{
		CONFerr(CONF_F_DEF_LOAD_BIO,ERR_R_BUF_LIB);
		goto err;
		}

	section=(char *)OPENSSL_malloc(10);
	if (section == NULL)
		{
		CONFerr(CONF_F_DEF_LOAD_BIO,ERR_R_MALLOC_FAILURE);
		goto err;
		}
	BUF_strlcpy(section,"default",10);

	if (_CONF_new_data(conf) == 0)
		{
		CONFerr(CONF_F_DEF_LOAD_BIO,ERR_R_MALLOC_FAILURE);
		goto err;
		}

	sv=_CONF_new_section(conf,section);
	if (sv == NULL)
		{
		CONFerr(CONF_F_DEF_LOAD_BIO,
					CONF_R_UNABLE_TO_CREATE_NEW_SECTION);
		goto err;
		}
	section_sk=(STACK_OF(CONF_VALUE) *)sv->value;

	bufnum=0;
	again=0;
	for (;;)
		{
		if (!BUF_MEM_grow(buff,bufnum+CONFBUFSIZE))
			{
			CONFerr(CONF_F_DEF_LOAD_BIO,ERR_R_BUF_LIB);
			goto err;
			}
		p= &(buff->data[bufnum]);
		*p='\0';
		BIO_gets(in, p, CONFBUFSIZE-1);
		p[CONFBUFSIZE-1]='\0';
		ii=i=strlen(p);
		if (i == 0 && !again) break;
		again=0;
		while (i > 0)
			{
			if ((p[i-1] != '\r') && (p[i-1] != '\n'))
				break;
			else
				i--;
			}
		/* we removed some trailing stuff so there is a new
		 * line on the end. */
		if (ii && i == ii)
			again=1; /* long line */
		else
			{
			p[i]='\0';
			eline++; /* another input line */
			}

		/* we now have a line with trailing \r\n removed */

		/* i is the number of bytes */
		bufnum+=i;

		v=NULL;
		/* check for line continuation */
		if (bufnum >= 1)
			{
			/* If we have bytes and the last char '\\' and
			 * second last char is not '\\' */
			p= &(buff->data[bufnum-1]);
			if (IS_ESC(conf,p[0]) &&
				((bufnum <= 1) || !IS_ESC(conf,p[-1])))
				{
				bufnum--;
				again=1;
				}
			}
		if (again) continue;
		bufnum=0;
		buf=buff->data;

		clear_comments(conf, buf);
		s=eat_ws(conf, buf);
		if (IS_EOF(conf,*s)) continue; /* blank line */
		if (*s == '[')
			{
			char *ss;

			s++;
			start=eat_ws(conf, s);
			ss=start;
again:
			end=eat_alpha_numeric(conf, ss);
			p=eat_ws(conf, end);
			if (*p != ']')
				{
				if (*p != '\0')
					{
					ss=p;
					goto again;
					}
				CONFerr(CONF_F_DEF_LOAD_BIO,
					CONF_R_MISSING_CLOSE_SQUARE_BRACKET);
				goto err;
				}
			*end='\0';
			if (!str_copy(conf,NULL,&section,start)) goto err;
			if ((sv=_CONF_get_section(conf,section)) == NULL)
				sv=_CONF_new_section(conf,section);
			if (sv == NULL)
				{
				CONFerr(CONF_F_DEF_LOAD_BIO,
					CONF_R_UNABLE_TO_CREATE_NEW_SECTION);
				goto err;
				}
			section_sk=(STACK_OF(CONF_VALUE) *)sv->value;
			continue;
			}
		else
			{
Пример #21
0
static long file_ctrl(BIO *b, int cmd, long num, void *ptr) {
  long ret = 1;
  FILE *fp = (FILE *)b->ptr;
  FILE **fpp;
  char p[4];

  switch (cmd) {
    case BIO_CTRL_RESET:
      num = 0;
    case BIO_C_FILE_SEEK:
      ret = (long)fseek(fp, num, 0);
      break;
    case BIO_CTRL_EOF:
      ret = (long)feof(fp);
      break;
    case BIO_C_FILE_TELL:
    case BIO_CTRL_INFO:
      ret = ftell(fp);
      break;
    case BIO_C_SET_FILE_PTR:
      file_free(b);
      b->shutdown = (int)num & BIO_CLOSE;
      b->ptr = ptr;
      b->init = 1;
      break;
    case BIO_C_SET_FILENAME:
      file_free(b);
      b->shutdown = (int)num & BIO_CLOSE;
      if (num & BIO_FP_APPEND) {
        if (num & BIO_FP_READ) {
          BUF_strlcpy(p, "a+", sizeof(p));
        } else {
          BUF_strlcpy(p, "a", sizeof(p));
        }
      } else if ((num & BIO_FP_READ) && (num & BIO_FP_WRITE)) {
        BUF_strlcpy(p, "r+", sizeof(p));
      } else if (num & BIO_FP_WRITE) {
        BUF_strlcpy(p, "w", sizeof(p));
      } else if (num & BIO_FP_READ) {
        BUF_strlcpy(p, "r", sizeof(p));
      } else {
        OPENSSL_PUT_ERROR(BIO, BIO_R_BAD_FOPEN_MODE);
        ret = 0;
        break;
      }
      fp = fopen(ptr, p);
      if (fp == NULL) {
        OPENSSL_PUT_SYSTEM_ERROR();
        ERR_add_error_data(5, "fopen('", ptr, "','", p, "')");
        OPENSSL_PUT_ERROR(BIO, ERR_R_SYS_LIB);
        ret = 0;
        break;
      }
      b->ptr = fp;
      b->init = 1;
      break;
    case BIO_C_GET_FILE_PTR:
      /* the ptr parameter is actually a FILE ** in this case. */
      if (ptr != NULL) {
        fpp = (FILE **)ptr;
        *fpp = (FILE *)b->ptr;
      }
      break;
    case BIO_CTRL_GET_CLOSE:
      ret = (long)b->shutdown;
      break;
    case BIO_CTRL_SET_CLOSE:
      b->shutdown = (int)num;
      break;
    case BIO_CTRL_FLUSH:
      ret = 0 == fflush((FILE *)b->ptr);
      break;
    case BIO_CTRL_WPENDING:
    case BIO_CTRL_PENDING:
    default:
      ret = 0;
      break;
  }
  return ret;
}
Пример #22
0
int MAIN(int argc, char **argv)
	{
	int add_user = 0;
	int list_user= 0;
	int delete_user= 0;
	int modify_user= 0;
	char * user = NULL;

	char *passargin = NULL, *passargout = NULL;
	char *passin = NULL, *passout = NULL;
        char * gN = NULL;
	int gNindex = -1;
	char ** gNrow = NULL;
	int maxgN = -1;

	char * userinfo = NULL;

	int badops=0;
	int ret=1;
	int errors=0;
	int verbose=0;
	int doupdatedb=0;
	char *configfile=NULL;
	char *dbfile=NULL;
	CA_DB *db=NULL;
	char **pp ;
	int i;
	long errorline = -1;
	char *randfile=NULL;
#ifndef OPENSSL_NO_ENGINE
	char *engine = NULL;
#endif
	char *tofree=NULL;
	DB_ATTR db_attr;

#ifdef EFENCE
EF_PROTECT_FREE=1;
EF_PROTECT_BELOW=1;
EF_ALIGNMENT=0;
#endif

	apps_startup();

	conf = NULL;
	section = NULL;

	if (bio_err == NULL)
		if ((bio_err=BIO_new(BIO_s_file())) != NULL)
			BIO_set_fp(bio_err,stderr,BIO_NOCLOSE|BIO_FP_TEXT);

	argc--;
	argv++;
	while (argc >= 1 && badops == 0)
		{
		if	(strcmp(*argv,"-verbose") == 0)
			verbose++;
		else if	(strcmp(*argv,"-config") == 0)
			{
			if (--argc < 1) goto bad;
			configfile= *(++argv);
			}
		else if (strcmp(*argv,"-name") == 0)
			{
			if (--argc < 1) goto bad;
			section= *(++argv);
			}
		else if	(strcmp(*argv,"-srpvfile") == 0)
			{
			if (--argc < 1) goto bad;
			dbfile= *(++argv);
			}
		else if (strcmp(*argv,"-add") == 0)
			add_user=1;
		else if (strcmp(*argv,"-delete") == 0)
			delete_user=1;
		else if (strcmp(*argv,"-modify") == 0)
			modify_user=1;
		else if (strcmp(*argv,"-list") == 0)
			list_user=1;
		else if (strcmp(*argv,"-gn") == 0)
			{
			if (--argc < 1) goto bad;
			gN= *(++argv);
			}
		else if (strcmp(*argv,"-userinfo") == 0)
			{
			if (--argc < 1) goto bad;
			userinfo= *(++argv);
			}
		else if (strcmp(*argv,"-passin") == 0)
			{
			if (--argc < 1) goto bad;
			passargin= *(++argv);
			}
		else if (strcmp(*argv,"-passout") == 0)
			{
			if (--argc < 1) goto bad;
			passargout= *(++argv);
			}
#ifndef OPENSSL_NO_ENGINE
		else if (strcmp(*argv,"-engine") == 0)
			{
			if (--argc < 1) goto bad;
			engine= *(++argv);
			}
#endif

		else if (**argv == '-')
			{
bad:
			BIO_printf(bio_err,"unknown option %s\n",*argv);
			badops=1;
			break;
			}
		else 
			break;
	
		argc--;
		argv++;
		}

	if (dbfile && configfile)
		{
		BIO_printf(bio_err,"-dbfile and -configfile cannot be specified together.\n");
		badops = 1;
		}
	if (add_user+delete_user+modify_user+list_user != 1)
		{
		BIO_printf(bio_err,"Exactly one of the options -add, -delete, -modify -list must be specified.\n");
		badops = 1;
		}
	if (delete_user+modify_user+delete_user== 1 && argc <= 0)
		{
		BIO_printf(bio_err,"Need at least one user for options -add, -delete, -modify. \n");
		badops = 1;
		}
	if ((passin || passout) && argc != 1 )
		{
		BIO_printf(bio_err,"-passin, -passout arguments only valid with one user.\n");
		badops = 1;
		}

	if (badops)
		{
		for (pp=srp_usage; (*pp != NULL); pp++)
			BIO_printf(bio_err,"%s",*pp);

		BIO_printf(bio_err," -rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
		BIO_printf(bio_err,"                 load the file (or the files in the directory) into\n");
		BIO_printf(bio_err,"                 the random number generator\n");
		goto err;
		}

	ERR_load_crypto_strings();

#ifndef OPENSSL_NO_ENGINE
	setup_engine(bio_err, engine, 0);
#endif

	if(!app_passwd(bio_err, passargin, passargout, &passin, &passout))
		{
		BIO_printf(bio_err, "Error getting passwords\n");
		goto err;
		}

        if (!dbfile)
		{


	/*****************************************************************/
		tofree=NULL;
		if (configfile == NULL) configfile = getenv("OPENSSL_CONF");
		if (configfile == NULL) configfile = getenv("SSLEAY_CONF");
		if (configfile == NULL)
			{
			const char *s=X509_get_default_cert_area();
			size_t len;

#ifdef OPENSSL_SYS_VMS
			len = strlen(s)+sizeof(CONFIG_FILE);
			tofree=OPENSSL_malloc(len);
			strcpy(tofree,s);
#else
			len = strlen(s)+sizeof(CONFIG_FILE)+1;
			tofree=OPENSSL_malloc(len);
			BUF_strlcpy(tofree,s,len);
			BUF_strlcat(tofree,"/",len);
#endif
			BUF_strlcat(tofree,CONFIG_FILE,len);
			configfile=tofree;
			}

		VERBOSE BIO_printf(bio_err,"Using configuration from %s\n",configfile);
		conf = NCONF_new(NULL);
		if (NCONF_load(conf,configfile,&errorline) <= 0)
			{
			if (errorline <= 0)
				BIO_printf(bio_err,"error loading the config file '%s'\n",
					configfile);
			else
				BIO_printf(bio_err,"error on line %ld of config file '%s'\n"
					,errorline,configfile);
			goto err;
			}
		if(tofree)
			{
			OPENSSL_free(tofree);
			tofree = NULL;
			}

		if (!load_config(bio_err, conf))
			goto err;

	/* Lets get the config section we are using */
		if (section == NULL)
			{
			VERBOSE BIO_printf(bio_err,"trying to read " ENV_DEFAULT_SRP " in \" BASE_SECTION \"\n");

			section=NCONF_get_string(conf,BASE_SECTION,ENV_DEFAULT_SRP);
			if (section == NULL)
				{
				lookup_fail(BASE_SECTION,ENV_DEFAULT_SRP);
				goto err;
				}
			}
         
		if (randfile == NULL && conf)
	        	randfile = NCONF_get_string(conf, BASE_SECTION, "RANDFILE");

	
		VERBOSE BIO_printf(bio_err,"trying to read " ENV_DATABASE " in section \"%s\"\n",section);

		if ((dbfile=NCONF_get_string(conf,section,ENV_DATABASE)) == NULL)
			{
			lookup_fail(section,ENV_DATABASE);
			goto err;
			}

        	}
	if (randfile == NULL)
		ERR_clear_error();
       	else 
		app_RAND_load_file(randfile, bio_err, 0);

	VERBOSE BIO_printf(bio_err,"Trying to read SRP verifier file \"%s\"\n",dbfile);

	db = load_index(dbfile, &db_attr);
	if (db == NULL) goto err;

	/* Lets check some fields */
	for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++)
		{
		pp = sk_OPENSSL_PSTRING_value(db->db->data, i);
	
		if (pp[DB_srptype][0] == DB_SRP_INDEX)
			{
			maxgN = i;
			if (gNindex < 0 && gN != NULL && !strcmp(gN, pp[DB_srpid]))
				gNindex = i;

			print_index(db, bio_err, i, verbose > 1);
			}
		}
	
	VERBOSE BIO_printf(bio_err, "Database initialised\n");

	if (gNindex >= 0)
		{
		gNrow = sk_OPENSSL_PSTRING_value(db->db->data,gNindex);
		print_entry(db, bio_err, gNindex, verbose > 1, "Default g and N");
		}
	else if (maxgN > 0 && !SRP_get_default_gN(gN))
		{
		BIO_printf(bio_err, "No g and N value for index \"%s\"\n", gN);
		goto err;
		}
	else
		{
		VERBOSE BIO_printf(bio_err, "Database has no g N information.\n");
		gNrow = NULL;
		}
	

	VVERBOSE BIO_printf(bio_err,"Starting user processing\n");

	if (argc > 0)
		user = *(argv++) ;

	while (list_user || user)
		{
		int userindex = -1;
		if (user) 
			VVERBOSE BIO_printf(bio_err, "Processing user \"%s\"\n", user);
		if ((userindex = get_index(db, user, 'U')) >= 0)
			{
			print_user(db, bio_err, userindex, (verbose > 0) || list_user);
			}
		
		if (list_user)
			{
			if (user == NULL)
				{
				BIO_printf(bio_err,"List all users\n");

				for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++)
					{
					print_user(db,bio_err, i, 1);
					}
				list_user = 0;
				}
			else if (userindex < 0)
				{
				BIO_printf(bio_err, "user \"%s\" does not exist, ignored. t\n",
					   user);
				errors++;
				}
			}
		else if (add_user)
			{
			if (userindex >= 0)
				{
				/* reactivation of a new user */
				char **row = sk_OPENSSL_PSTRING_value(db->db->data, userindex);
				BIO_printf(bio_err, "user \"%s\" reactivated.\n", user);
				row[DB_srptype][0] = 'V';

				doupdatedb = 1;
				}
			else
				{
				char *row[DB_NUMBER] ; char *gNid;
				row[DB_srpverifier] = NULL;
				row[DB_srpsalt] = NULL;
				row[DB_srpinfo] = NULL;
				if (!(gNid = srp_create_user(user,&(row[DB_srpverifier]), &(row[DB_srpsalt]),gNrow?gNrow[DB_srpsalt]:gN,gNrow?gNrow[DB_srpverifier]:NULL, passout, bio_err,verbose)))
					{
						BIO_printf(bio_err, "Cannot create srp verifier for user \"%s\", operation abandoned .\n", user);
						errors++;
						goto err;
					}
				row[DB_srpid] = BUF_strdup(user);
				row[DB_srptype] = BUF_strdup("v");
				row[DB_srpgN] = BUF_strdup(gNid);

				if (!row[DB_srpid] || !row[DB_srpgN] || !row[DB_srptype] || !row[DB_srpverifier] || !row[DB_srpsalt] ||
					(userinfo && (!(row[DB_srpinfo] = BUF_strdup(userinfo)))) || 
					!update_index(db, bio_err, row))
					{
					if (row[DB_srpid]) OPENSSL_free(row[DB_srpid]);
					if (row[DB_srpgN]) OPENSSL_free(row[DB_srpgN]);
					if (row[DB_srpinfo]) OPENSSL_free(row[DB_srpinfo]);
					if (row[DB_srptype]) OPENSSL_free(row[DB_srptype]);
					if (row[DB_srpverifier]) OPENSSL_free(row[DB_srpverifier]);
					if (row[DB_srpsalt]) OPENSSL_free(row[DB_srpsalt]);
					goto err;
					}
				doupdatedb = 1;
				}
			}
		else if (modify_user)
			{
			if (userindex < 0)
				{
				BIO_printf(bio_err,"user \"%s\" does not exist, operation ignored.\n",user);
				errors++;
				}
			else
				{

				char **row = sk_OPENSSL_PSTRING_value(db->db->data, userindex);
				char type = row[DB_srptype][0];
				if (type == 'v')
					{
					BIO_printf(bio_err,"user \"%s\" already updated, operation ignored.\n",user);
					errors++;
					}
				else
					{
					char *gNid;

					if (row[DB_srptype][0] == 'V')
						{
						int user_gN;
						char **irow = NULL;
						VERBOSE BIO_printf(bio_err,"Verifying password for user \"%s\"\n",user);
						if ( (user_gN = get_index(db, row[DB_srpgN], DB_SRP_INDEX)) >= 0)
							irow = (char **)sk_OPENSSL_PSTRING_value(db->db->data, userindex);

 						if (!srp_verify_user(user, row[DB_srpverifier], row[DB_srpsalt], irow ? irow[DB_srpsalt] : row[DB_srpgN], irow ? irow[DB_srpverifier] : NULL, passin, bio_err, verbose))
							{
							BIO_printf(bio_err, "Invalid password for user \"%s\", operation abandoned.\n", user);
							errors++;
							goto err;
							}
						} 
					VERBOSE BIO_printf(bio_err,"Password for user \"%s\" ok.\n",user);

					if (!(gNid=srp_create_user(user,&(row[DB_srpverifier]), &(row[DB_srpsalt]),gNrow?gNrow[DB_srpsalt]:NULL, gNrow?gNrow[DB_srpverifier]:NULL, passout, bio_err,verbose)))
						{
						BIO_printf(bio_err, "Cannot create srp verifier for user \"%s\", operation abandoned.\n", user);
						errors++;
						goto err;
						}

					row[DB_srptype][0] = 'v';
					row[DB_srpgN] = BUF_strdup(gNid);
 
					if (!row[DB_srpid] || !row[DB_srpgN] || !row[DB_srptype] || !row[DB_srpverifier] || !row[DB_srpsalt] ||
						(userinfo && (!(row[DB_srpinfo] = BUF_strdup(userinfo)))))  
						goto err;

					doupdatedb = 1;
					}
				}
			}
		else if (delete_user)
			{
			if (userindex < 0)
				{
				BIO_printf(bio_err, "user \"%s\" does not exist, operation ignored. t\n", user);
				errors++;
				}
			else
				{
				char **xpp = sk_OPENSSL_PSTRING_value(db->db->data,userindex);
				BIO_printf(bio_err, "user \"%s\" revoked. t\n", user);

				xpp[DB_srptype][0] = 'R';
				
				doupdatedb = 1;
				}
			}
		if (--argc > 0)
			user = *(argv++) ;
		else
			{
			user = NULL;
			list_user = 0;
			}
		}

	VERBOSE BIO_printf(bio_err,"User procession done.\n");


	if (doupdatedb)
		{
		/* Lets check some fields */
		for (i = 0; i < sk_OPENSSL_PSTRING_num(db->db->data); i++)
			{
			pp = sk_OPENSSL_PSTRING_value(db->db->data,i);
	
			if (pp[DB_srptype][0] == 'v')
				{
				pp[DB_srptype][0] = 'V';
				print_user(db, bio_err, i, verbose);
				}
			}

		VERBOSE BIO_printf(bio_err, "Trying to update srpvfile.\n");
		if (!save_index(dbfile, "new", db)) goto err;
				
		VERBOSE BIO_printf(bio_err, "Temporary srpvfile created.\n");
		if (!rotate_index(dbfile, "new", "old")) goto err;

		VERBOSE BIO_printf(bio_err, "srpvfile updated.\n");
		}

	ret = (errors != 0);
err:
	if (errors != 0)
	VERBOSE BIO_printf(bio_err,"User errors %d.\n",errors);

	VERBOSE BIO_printf(bio_err,"SRP terminating with code %d.\n",ret);
	if(tofree)
		OPENSSL_free(tofree);
	if (ret) ERR_print_errors(bio_err);
	if (randfile) app_RAND_write_file(randfile, bio_err);
	if (conf) NCONF_free(conf);
	if (db) free_index(db);

	OBJ_cleanup();
	apps_shutdown();
	OPENSSL_EXIT(ret);
	}
Пример #23
0
char *X509_NAME_oneline(X509_NAME *a, char *buf, int len)
{
    X509_NAME_ENTRY *ne;
    size_t i;
    int n, lold, l, l1, l2, num, j, type;
    const char *s;
    char *p;
    unsigned char *q;
    BUF_MEM *b = NULL;
    static const char hex[17] = "0123456789ABCDEF";
    int gs_doit[4];
    char tmp_buf[80];

    if (buf == NULL) {
        if ((b = BUF_MEM_new()) == NULL)
            goto err;
        if (!BUF_MEM_grow(b, 200))
            goto err;
        b->data[0] = '\0';
        len = 200;
    } else if (len <= 0) {
        return NULL;
    }
    if (a == NULL) {
        if (b) {
            buf = b->data;
            OPENSSL_free(b);
        }
        BUF_strlcpy(buf, "NO X509_NAME", len);
        return buf;
    }

    len--;                      /* space for '\0' */
    l = 0;
    for (i = 0; i < sk_X509_NAME_ENTRY_num(a->entries); i++) {
        ne = sk_X509_NAME_ENTRY_value(a->entries, i);
        n = OBJ_obj2nid(ne->object);
        if ((n == NID_undef) || ((s = OBJ_nid2sn(n)) == NULL)) {
            i2t_ASN1_OBJECT(tmp_buf, sizeof(tmp_buf), ne->object);
            s = tmp_buf;
        }
        l1 = strlen(s);

        type = ne->value->type;
        num = ne->value->length;
        if (num > NAME_ONELINE_MAX) {
            OPENSSL_PUT_ERROR(X509, X509_R_NAME_TOO_LONG);
            goto end;
        }
        q = ne->value->data;

        if ((type == V_ASN1_GENERALSTRING) && ((num % 4) == 0)) {
            gs_doit[0] = gs_doit[1] = gs_doit[2] = gs_doit[3] = 0;
            for (j = 0; j < num; j++)
                if (q[j] != 0)
                    gs_doit[j & 3] = 1;

            if (gs_doit[0] | gs_doit[1] | gs_doit[2])
                gs_doit[0] = gs_doit[1] = gs_doit[2] = gs_doit[3] = 1;
            else {
                gs_doit[0] = gs_doit[1] = gs_doit[2] = 0;
                gs_doit[3] = 1;
            }
        } else
            gs_doit[0] = gs_doit[1] = gs_doit[2] = gs_doit[3] = 1;

        for (l2 = j = 0; j < num; j++) {
            if (!gs_doit[j & 3])
                continue;
            l2++;
            if ((q[j] < ' ') || (q[j] > '~'))
                l2 += 3;
        }

        lold = l;
        l += 1 + l1 + 1 + l2;
        if (l > NAME_ONELINE_MAX) {
            OPENSSL_PUT_ERROR(X509, X509_R_NAME_TOO_LONG);
            goto end;
        }
        if (b != NULL) {
            if (!BUF_MEM_grow(b, l + 1))
                goto err;
            p = &(b->data[lold]);
        } else if (l > len) {
            break;
        } else
            p = &(buf[lold]);
        *(p++) = '/';
        OPENSSL_memcpy(p, s, (unsigned int)l1);
        p += l1;
        *(p++) = '=';

        q = ne->value->data;

        for (j = 0; j < num; j++) {
            if (!gs_doit[j & 3])
                continue;
            n = q[j];
            if ((n < ' ') || (n > '~')) {
                *(p++) = '\\';
                *(p++) = 'x';
                *(p++) = hex[(n >> 4) & 0x0f];
                *(p++) = hex[n & 0x0f];
            } else
                *(p++) = n;
        }
Пример #24
0
int RSA_print(BIO *bp, const RSA *x, int off)
	{
	char str[128];
	const char *s;
	unsigned char *m=NULL;
	int ret=0;
	size_t buf_len=0, i;

	if (x->n)
		buf_len = (size_t)BN_num_bytes(x->n);
	if (x->e)
		if (buf_len < (i = (size_t)BN_num_bytes(x->e)))
			buf_len = i;
	if (x->d)
		if (buf_len < (i = (size_t)BN_num_bytes(x->d)))
			buf_len = i;
	if (x->p)
		if (buf_len < (i = (size_t)BN_num_bytes(x->p)))
			buf_len = i;
	if (x->q)
		if (buf_len < (i = (size_t)BN_num_bytes(x->q)))
			buf_len = i;
	if (x->dmp1)
		if (buf_len < (i = (size_t)BN_num_bytes(x->dmp1)))
			buf_len = i;
	if (x->dmq1)
		if (buf_len < (i = (size_t)BN_num_bytes(x->dmq1)))
			buf_len = i;
	if (x->iqmp)
		if (buf_len < (i = (size_t)BN_num_bytes(x->iqmp)))
			buf_len = i;

	m=(unsigned char *)OPENSSL_malloc(buf_len+10);
	if (m == NULL)
		{
		RSAerr(RSA_F_RSA_PRINT,ERR_R_MALLOC_FAILURE);
		goto err;
		}

	if (x->d != NULL)
		{
		if(!BIO_indent(bp,off,128))
		   goto err;
		if (BIO_printf(bp,"Private-Key: (%d bit)\n",BN_num_bits(x->n))
			<= 0) goto err;
		}

	if (x->d == NULL)
		BIO_snprintf(str,sizeof str,"Modulus (%d bit):",BN_num_bits(x->n));
	else
		BUF_strlcpy(str,"modulus:",sizeof str);
	if (!print(bp,str,x->n,m,off)) goto err;
	s=(x->d == NULL)?"Exponent:":"publicExponent:";
	if (!print(bp,s,x->e,m,off)) goto err;
	if (!print(bp,"privateExponent:",x->d,m,off)) goto err;
	if (!print(bp,"prime1:",x->p,m,off)) goto err;
	if (!print(bp,"prime2:",x->q,m,off)) goto err;
	if (!print(bp,"exponent1:",x->dmp1,m,off)) goto err;
	if (!print(bp,"exponent2:",x->dmq1,m,off)) goto err;
	if (!print(bp,"coefficient:",x->iqmp,m,off)) goto err;
	ret=1;
err:
	if (m != NULL) OPENSSL_free(m);
	return(ret);
	}
Пример #25
0
int pkcs12_main(int argc, char **argv)
{
    char *infile = NULL, *outfile = NULL, *keyname = NULL, *certfile = NULL;
    char *name = NULL, *csp_name = NULL;
    char pass[50], macpass[50];
    int export_cert = 0, options = 0, chain = 0, twopass = 0, keytype = 0;
    int iter = PKCS12_DEFAULT_ITER, maciter = PKCS12_DEFAULT_ITER;
# ifndef OPENSSL_NO_RC2
    int cert_pbe = NID_pbe_WithSHA1And40BitRC2_CBC;
# else
    int cert_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
# endif
    int key_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
    int ret = 1, macver = 1, noprompt = 0, add_lmk = 0;
    char *passinarg = NULL, *passoutarg = NULL, *passarg = NULL;
    char *passin = NULL, *passout = NULL, *inrand = NULL, *macalg = NULL;
    char *cpass = NULL, *mpass = NULL, *CApath = NULL, *CAfile = NULL;
    char *prog;
    ENGINE *e = NULL;
    BIO *in = NULL, *out = NULL;
    PKCS12 *p12 = NULL;
    STACK_OF(OPENSSL_STRING) *canames = NULL;
    const EVP_CIPHER *enc = EVP_des_ede3_cbc();
    OPTION_CHOICE o;

    prog = opt_init(argc, argv, pkcs12_options);
    while ((o = opt_next()) != OPT_EOF) {
        switch (o) {
        case OPT_EOF:
        case OPT_ERR:
 opthelp:
            BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
            goto end;
        case OPT_HELP:
            opt_help(pkcs12_options);
            ret = 0;
            goto end;
        case OPT_NOKEYS:
            options |= NOKEYS;
            break;
        case OPT_KEYEX:
            keytype = KEY_EX;
            break;
        case OPT_KEYSIG:
            keytype = KEY_SIG;
            break;
        case OPT_NOCERTS:
            options |= NOCERTS;
            break;
        case OPT_CLCERTS:
            options |= CLCERTS;
            break;
        case OPT_CACERTS:
            options |= CACERTS;
            break;
        case OPT_NOOUT:
            options |= (NOKEYS | NOCERTS);
            break;
        case OPT_INFO:
            options |= INFO;
            break;
        case OPT_CHAIN:
            chain = 1;
            break;
        case OPT_TWOPASS:
            twopass = 1;
            break;
        case OPT_NOMACVER:
            macver = 0;
            break;
        case OPT_DESCERT:
            cert_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
            break;
        case OPT_EXPORT:
            export_cert = 1;
            break;
        case OPT_CIPHER:
            if (!opt_cipher(opt_unknown(), &enc))
                goto opthelp;
            break;
        case OPT_NOITER:
            iter = 1;
            break;
        case OPT_MACITER:
            maciter = PKCS12_DEFAULT_ITER;
            break;
        case OPT_NOMACITER:
            maciter = 1;
            break;
        case OPT_NOMAC:
            maciter = -1;
            break;
        case OPT_MACALG:
            macalg = opt_arg();
            break;
        case OPT_NODES:
            enc = NULL;
            break;
        case OPT_CERTPBE:
            if (!set_pbe(&cert_pbe, opt_arg()))
                goto opthelp;
            break;
        case OPT_KEYPBE:
            if (!set_pbe(&key_pbe, opt_arg()))
                goto opthelp;
            break;
        case OPT_RAND:
            inrand = opt_arg();
            break;
        case OPT_INKEY:
            keyname = opt_arg();
            break;
        case OPT_CERTFILE:
            certfile = opt_arg();
            break;
        case OPT_NAME:
            name = opt_arg();
            break;
        case OPT_LMK:
            add_lmk = 1;
            break;
        case OPT_CSP:
            csp_name = opt_arg();
            break;
        case OPT_CANAME:
            if (canames == NULL
                && (canames = sk_OPENSSL_STRING_new_null()) == NULL)
                goto end;
            sk_OPENSSL_STRING_push(canames, opt_arg());
            break;
        case OPT_IN:
            infile = opt_arg();
            break;
        case OPT_OUT:
            outfile = opt_arg();
            break;
        case OPT_PASSIN:
            passinarg = opt_arg();
            break;
        case OPT_PASSOUT:
            passoutarg = opt_arg();
            break;
        case OPT_PASSWORD:
            passarg = opt_arg();
            break;
        case OPT_CAPATH:
            CApath = opt_arg();
            break;
        case OPT_CAFILE:
            CAfile = opt_arg();
            break;
        case OPT_ENGINE:
            e = setup_engine(opt_arg(), 0);
            break;
        }
    }
    argc = opt_num_rest();
    argv = opt_rest();

    if (passarg) {
        if (export_cert)
            passoutarg = passarg;
        else
            passinarg = passarg;
    }

    if (!app_passwd(passinarg, passoutarg, &passin, &passout)) {
        BIO_printf(bio_err, "Error getting passwords\n");
        goto end;
    }

    if (!cpass) {
        if (export_cert)
            cpass = passout;
        else
            cpass = passin;
    }

    if (cpass) {
        mpass = cpass;
        noprompt = 1;
    } else {
        cpass = pass;
        mpass = macpass;
    }

    if (export_cert || inrand) {
        app_RAND_load_file(NULL, (inrand != NULL));
        if (inrand != NULL)
            BIO_printf(bio_err, "%ld semi-random bytes loaded\n",
                       app_RAND_load_files(inrand));
    }

    in = bio_open_default(infile, "rb");
    if (in == NULL)
        goto end;

    out = bio_open_default(outfile, "wb");
    if (out == NULL)
        goto end;

    if (twopass) {
        if (EVP_read_pw_string
            (macpass, sizeof macpass, "Enter MAC Password:"******"Can't read Password\n");
            goto end;
        }
    }

    if (export_cert) {
        EVP_PKEY *key = NULL;
        X509 *ucert = NULL, *x = NULL;
        STACK_OF(X509) *certs = NULL;
        const EVP_MD *macmd = NULL;
        unsigned char *catmp = NULL;
        int i;

        if ((options & (NOCERTS | NOKEYS)) == (NOCERTS | NOKEYS)) {
            BIO_printf(bio_err, "Nothing to do!\n");
            goto export_end;
        }

        if (options & NOCERTS)
            chain = 0;

        if (!(options & NOKEYS)) {
            key = load_key(keyname ? keyname : infile,
                           FORMAT_PEM, 1, passin, e, "private key");
            if (!key)
                goto export_end;
        }

        /* Load in all certs in input file */
        if (!(options & NOCERTS)) {
            certs = load_certs(infile, FORMAT_PEM, NULL, e,
                               "certificates");
            if (!certs)
                goto export_end;

            if (key) {
                /* Look for matching private key */
                for (i = 0; i < sk_X509_num(certs); i++) {
                    x = sk_X509_value(certs, i);
                    if (X509_check_private_key(x, key)) {
                        ucert = x;
                        /* Zero keyid and alias */
                        X509_keyid_set1(ucert, NULL, 0);
                        X509_alias_set1(ucert, NULL, 0);
                        /* Remove from list */
                        (void)sk_X509_delete(certs, i);
                        break;
                    }
                }
                if (!ucert) {
                    BIO_printf(bio_err,
                               "No certificate matches private key\n");
                    goto export_end;
                }
            }

        }

        /* Add any more certificates asked for */
        if (certfile) {
            STACK_OF(X509) *morecerts = NULL;
            if (!(morecerts = load_certs(certfile, FORMAT_PEM, NULL, e,
                                         "certificates from certfile")))
                goto export_end;
            while (sk_X509_num(morecerts) > 0)
                sk_X509_push(certs, sk_X509_shift(morecerts));
            sk_X509_free(morecerts);
        }

        /* If chaining get chain from user cert */
        if (chain) {
            int vret;
            STACK_OF(X509) *chain2;
            X509_STORE *store;
            if (!(store = setup_verify(CAfile, CApath)))
                goto export_end;

            vret = get_cert_chain(ucert, store, &chain2);
            X509_STORE_free(store);

            if (!vret) {
                /* Exclude verified certificate */
                for (i = 1; i < sk_X509_num(chain2); i++)
                    sk_X509_push(certs, sk_X509_value(chain2, i));
                /* Free first certificate */
                X509_free(sk_X509_value(chain2, 0));
                sk_X509_free(chain2);
            } else {
                if (vret >= 0)
                    BIO_printf(bio_err, "Error %s getting chain.\n",
                               X509_verify_cert_error_string(vret));
                else
                    ERR_print_errors(bio_err);
                goto export_end;
            }
        }

        /* Add any CA names */

        for (i = 0; i < sk_OPENSSL_STRING_num(canames); i++) {
            catmp = (unsigned char *)sk_OPENSSL_STRING_value(canames, i);
            X509_alias_set1(sk_X509_value(certs, i), catmp, -1);
        }

        if (csp_name && key)
            EVP_PKEY_add1_attr_by_NID(key, NID_ms_csp_name,
                                      MBSTRING_ASC, (unsigned char *)csp_name,
                                      -1);

        if (add_lmk && key)
            EVP_PKEY_add1_attr_by_NID(key, NID_LocalKeySet, 0, NULL, -1);

        if (!noprompt &&
            EVP_read_pw_string(pass, sizeof pass, "Enter Export Password:"******"Can't read Password\n");
            goto export_end;
        }
        if (!twopass)
            BUF_strlcpy(macpass, pass, sizeof macpass);

        p12 = PKCS12_create(cpass, name, key, ucert, certs,
                            key_pbe, cert_pbe, iter, -1, keytype);

        if (!p12) {
            ERR_print_errors(bio_err);
            goto export_end;
        }

        if (macalg) {
            if (!opt_md(macalg, &macmd))
                goto opthelp;
        }

        if (maciter != -1)
            PKCS12_set_mac(p12, mpass, -1, NULL, 0, maciter, macmd);

        i2d_PKCS12_bio(out, p12);

        ret = 0;

 export_end:

        EVP_PKEY_free(key);
        if (certs)
            sk_X509_pop_free(certs, X509_free);
        if (ucert)
            X509_free(ucert);

        goto end;

    }

    if (!(p12 = d2i_PKCS12_bio(in, NULL))) {
        ERR_print_errors(bio_err);
        goto end;
    }

    if (!noprompt
        && EVP_read_pw_string(pass, sizeof pass, "Enter Import Password:"******"Can't read Password\n");
        goto end;
    }

    if (!twopass)
        BUF_strlcpy(macpass, pass, sizeof macpass);

    if ((options & INFO) && p12->mac)
        BIO_printf(bio_err, "MAC Iteration %ld\n",
                   p12->mac->iter ? ASN1_INTEGER_get(p12->mac->iter) : 1);
    if (macver) {
        /* If we enter empty password try no password first */
        if (!mpass[0] && PKCS12_verify_mac(p12, NULL, 0)) {
            /* If mac and crypto pass the same set it to NULL too */
            if (!twopass)
                cpass = NULL;
        } else if (!PKCS12_verify_mac(p12, mpass, -1)) {
            BIO_printf(bio_err, "Mac verify error: invalid password?\n");
            ERR_print_errors(bio_err);
            goto end;
        }
    }

    if (!dump_certs_keys_p12(out, p12, cpass, -1, options, passout, enc)) {
        BIO_printf(bio_err, "Error outputting keys and certificates\n");
        ERR_print_errors(bio_err);
        goto end;
    }
    ret = 0;
 end:
    PKCS12_free(p12);
    if (export_cert || inrand)
        app_RAND_write_file(NULL);
    BIO_free(in);
    BIO_free_all(out);
    if (canames)
        sk_OPENSSL_STRING_free(canames);
    if (passin)
        OPENSSL_free(passin);
    if (passout)
        OPENSSL_free(passout);
    return (ret);
}
Пример #26
0
EVP_PKEY *EVP_PKCS82PKEY(PKCS8_PRIV_KEY_INFO *p8)
{
  EVP_PKEY *pkey = NULL;
#ifndef OPENSSL_NO_RSA
  RSA *rsa = NULL;
#endif
#ifndef OPENSSL_NO_DSA
  DSA *dsa = NULL;
  ASN1_TYPE *t1, *t2;
  ASN1_INTEGER *privkey;
  STACK_OF(ASN1_TYPE) *ndsa = NULL;
#endif
#ifndef OPENSSL_NO_EC
  EC_KEY *eckey = NULL;
  const unsigned char *p_tmp;
#endif
#if !defined(OPENSSL_NO_DSA) || !defined(OPENSSL_NO_EC)
  ASN1_TYPE    *param = NULL;  
  BN_CTX *ctx = NULL;
  int plen;
#endif
  X509_ALGOR *a;
  const unsigned char *p;
  const unsigned char *cp;
  int pkeylen;
  int  nid;
  char obj_tmp[80];

  if(p8->pkey->type == V_ASN1_OCTET_STRING) {
    p8->broken = PKCS8_OK;
    p = p8->pkey->value.octet_string->data;
    pkeylen = p8->pkey->value.octet_string->length;
  } else {
    p8->broken = PKCS8_NO_OCTET;
    p = p8->pkey->value.sequence->data;
    pkeylen = p8->pkey->value.sequence->length;
  }
  if (!(pkey = EVP_PKEY_new())) {
    EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
    return NULL;
  }
  a = p8->pkeyalg;
  nid = OBJ_obj2nid(a->algorithm);
  switch(nid)
  {
#ifndef OPENSSL_NO_RSA
    case NID_rsaEncryption:
    cp = p;
    if (!(rsa = d2i_RSAPrivateKey (NULL,&cp, pkeylen))) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      return NULL;
    }
    EVP_PKEY_assign_RSA (pkey, rsa);
    break;
#endif
#ifndef OPENSSL_NO_DSA
    case NID_dsa:
    /* PKCS#8 DSA is weird: you just get a private key integer
           * and parameters in the AlgorithmIdentifier the pubkey must
     * be recalculated.
     */
  
    /* Check for broken DSA PKCS#8, UGH! */
    if(*p == (V_ASN1_SEQUENCE|V_ASN1_CONSTRUCTED)) {
        if(!(ndsa = ASN1_seq_unpack_ASN1_TYPE(p, pkeylen, 
                d2i_ASN1_TYPE,
                ASN1_TYPE_free))) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
        }
        if(sk_ASN1_TYPE_num(ndsa) != 2 ) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
        }
        /* Handle Two broken types:
         * SEQUENCE {parameters, priv_key}
         * SEQUENCE {pub_key, priv_key}
         */

        t1 = sk_ASN1_TYPE_value(ndsa, 0);
        t2 = sk_ASN1_TYPE_value(ndsa, 1);
        if(t1->type == V_ASN1_SEQUENCE) {
      p8->broken = PKCS8_EMBEDDED_PARAM;
      param = t1;
        } else if(a->parameter->type == V_ASN1_SEQUENCE) {
      p8->broken = PKCS8_NS_DB;
      param = a->parameter;
        } else {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
        }

        if(t2->type != V_ASN1_INTEGER) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
        }
        privkey = t2->value.integer;
    } else {
      if (!(privkey=d2i_ASN1_INTEGER (NULL, &p, pkeylen))) {
        EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
        goto dsaerr;
      }
      param = p8->pkeyalg->parameter;
    }
    if (!param || (param->type != V_ASN1_SEQUENCE)) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
    }
    cp = p = param->value.sequence->data;
    plen = param->value.sequence->length;
    if (!(dsa = d2i_DSAparams (NULL, &cp, plen))) {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto dsaerr;
    }
    /* We have parameters now set private key */
    if (!(dsa->priv_key = ASN1_INTEGER_to_BN(privkey, NULL))) {
      EVPerr(EVP_F_EVP_PKCS82PKEY,EVP_R_BN_DECODE_ERROR);
      goto dsaerr;
    }
    /* Calculate public key (ouch!) */
    if (!(dsa->pub_key = BN_new())) {
      EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
      goto dsaerr;
    }
    if (!(ctx = BN_CTX_new())) {
      EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
      goto dsaerr;
    }
      
    if (!BN_mod_exp(dsa->pub_key, dsa->g,
             dsa->priv_key, dsa->p, ctx)) {
      
      EVPerr(EVP_F_EVP_PKCS82PKEY,EVP_R_BN_PUBKEY_ERROR);
      goto dsaerr;
    }

    EVP_PKEY_assign_DSA(pkey, dsa);
    BN_CTX_free (ctx);
    if(ndsa) sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
    else ASN1_INTEGER_free(privkey);
    break;
    dsaerr:
    BN_CTX_free (ctx);
    sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
    DSA_free(dsa);
    EVP_PKEY_free(pkey);
    return NULL;
    break;
#endif
#ifndef OPENSSL_NO_EC
    case NID_X9_62_id_ecPublicKey:
    p_tmp = p;
    /* extract the ec parameters */
    param = p8->pkeyalg->parameter;

    if (!param || ((param->type != V_ASN1_SEQUENCE) &&
        (param->type != V_ASN1_OBJECT)))
    {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto ecerr;
    }

    if (param->type == V_ASN1_SEQUENCE)
    {
      cp = p = param->value.sequence->data;
      plen = param->value.sequence->length;

      if (!(eckey = d2i_ECParameters(NULL, &cp, plen)))
      {
        EVPerr(EVP_F_EVP_PKCS82PKEY,
          EVP_R_DECODE_ERROR);
        goto ecerr;
      }
    }
    else
    {
      EC_GROUP *group;
      cp = p = param->value.object->data;
      plen = param->value.object->length;

      /* type == V_ASN1_OBJECT => the parameters are given
       * by an asn1 OID
       */
      if ((eckey = EC_KEY_new()) == NULL)
      {
        EVPerr(EVP_F_EVP_PKCS82PKEY,
          ERR_R_MALLOC_FAILURE);
        goto ecerr;
      }
      group = EC_GROUP_new_by_curve_name(OBJ_obj2nid(a->parameter->value.object));
      if (group == NULL)
        goto ecerr;
      EC_GROUP_set_asn1_flag(group, OPENSSL_EC_NAMED_CURVE);
      if (EC_KEY_set_group(eckey, group) == 0)
        goto ecerr;
      EC_GROUP_free(group);
    }

    /* We have parameters now set private key */
    if (!d2i_ECPrivateKey(&eckey, &p_tmp, pkeylen))
    {
      EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
      goto ecerr;
    }

    /* calculate public key (if necessary) */
    if (EC_KEY_get0_public_key(eckey) == NULL)
    {
      const BIGNUM *priv_key;
      const EC_GROUP *group;
      EC_POINT *pub_key;
      /* the public key was not included in the SEC1 private
       * key => calculate the public key */
      group   = EC_KEY_get0_group(eckey);
      pub_key = EC_POINT_new(group);
      if (pub_key == NULL)
      {
        EVPerr(EVP_F_EVP_PKCS82PKEY, ERR_R_EC_LIB);
        goto ecerr;
      }
      if (!EC_POINT_copy(pub_key, EC_GROUP_get0_generator(group)))
      {
        EC_POINT_free(pub_key);
        EVPerr(EVP_F_EVP_PKCS82PKEY, ERR_R_EC_LIB);
        goto ecerr;
      }
      priv_key = EC_KEY_get0_private_key(eckey);
      if (!EC_POINT_mul(group, pub_key, priv_key, NULL, NULL, ctx))
      {
        EC_POINT_free(pub_key);
        EVPerr(EVP_F_EVP_PKCS82PKEY, ERR_R_EC_LIB);
        goto ecerr;
      }
      if (EC_KEY_set_public_key(eckey, pub_key) == 0)
      {
        EC_POINT_free(pub_key);
        EVPerr(EVP_F_EVP_PKCS82PKEY, ERR_R_EC_LIB);
        goto ecerr;
      }
      EC_POINT_free(pub_key);
    }

    EVP_PKEY_assign_EC_KEY(pkey, eckey);
    if (ctx)
      BN_CTX_free(ctx);
    break;
ecerr:
    if (ctx)
      BN_CTX_free(ctx);
    if (eckey)
      EC_KEY_free(eckey);
    if (pkey)
      EVP_PKEY_free(pkey);
    return NULL;
#endif
    default:
    EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_UNSUPPORTED_PRIVATE_KEY_ALGORITHM);
    if (!a->algorithm) BUF_strlcpy (obj_tmp, "NULL", sizeof obj_tmp);
    else i2t_ASN1_OBJECT(obj_tmp, 80, a->algorithm);
    ERR_add_error_data(2, "TYPE=", obj_tmp);
    EVP_PKEY_free (pkey);
    return NULL;
  }
  return pkey;
}
Пример #27
0
static int def_load_bio(CONF *conf, BIO *in, long *line)
{
/* The macro BUFSIZE conflicts with a system macro in VxWorks */
#define CONFBUFSIZE     512
    int bufnum = 0, i, ii;
    BUF_MEM *buff = NULL;
    char *s, *p, *end;
    int again;
    long eline = 0;
    char btmp[DECIMAL_SIZE(eline) + 1];
    CONF_VALUE *v = NULL, *tv;
    CONF_VALUE *sv = NULL;
    char *section = NULL, *buf;
    char *start, *psection, *pname;
    void *h = (void *)(conf->data);

    if ((buff = BUF_MEM_new()) == NULL) {
        CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_BUF_LIB);
        goto err;
    }

    section = (char *)OPENSSL_malloc(10);
    if (section == NULL) {
        CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
        goto err;
    }
    BUF_strlcpy(section, "default", 10);

    if (_CONF_new_data(conf) == 0) {
        CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
        goto err;
    }

    sv = _CONF_new_section(conf, section);
    if (sv == NULL) {
        CONFerr(CONF_F_DEF_LOAD_BIO, CONF_R_UNABLE_TO_CREATE_NEW_SECTION);
        goto err;
    }

    bufnum = 0;
    again = 0;
    for (;;) {
        if (!BUF_MEM_grow(buff, bufnum + CONFBUFSIZE)) {
            CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_BUF_LIB);
            goto err;
        }
        p = &(buff->data[bufnum]);
        *p = '\0';
        BIO_gets(in, p, CONFBUFSIZE - 1);
        p[CONFBUFSIZE - 1] = '\0';
        ii = i = sgx_strlen(p);
        if (i == 0 && !again)
            break;
        again = 0;
        while (i > 0) {
            if ((p[i - 1] != '\r') && (p[i - 1] != '\n'))
                break;
            else
                i--;
        }
        /*
         * we removed some trailing stuff so there is a new line on the end.
         */
        if (ii && i == ii)
            again = 1;          /* long line */
        else {
            p[i] = '\0';
            eline++;            /* another input line */
        }

        /* we now have a line with trailing \r\n removed */

        /* i is the number of bytes */
        bufnum += i;

        v = NULL;
        /* check for line continuation */
        if (bufnum >= 1) {
            /*
             * If we have bytes and the last char '\\' and second last char
             * is not '\\'
             */
            p = &(buff->data[bufnum - 1]);
            if (IS_ESC(conf, p[0]) && ((bufnum <= 1) || !IS_ESC(conf, p[-1]))) {
                bufnum--;
                again = 1;
            }
        }
        if (again)
            continue;
        bufnum = 0;
        buf = buff->data;

        clear_comments(conf, buf);
        s = eat_ws(conf, buf);
        if (IS_EOF(conf, *s))
            continue;           /* blank line */
        if (*s == '[') {
            char *ss;

            s++;
            start = eat_ws(conf, s);
            ss = start;
 again:
            end = eat_alpha_numeric(conf, ss);
            p = eat_ws(conf, end);
            if (*p != ']') {
                if (*p != '\0' && ss != p) {
                    ss = p;
                    goto again;
                }
                CONFerr(CONF_F_DEF_LOAD_BIO,
                        CONF_R_MISSING_CLOSE_SQUARE_BRACKET);
                goto err;
            }
            *end = '\0';
            if (!str_copy(conf, NULL, &section, start))
                goto err;
            if ((sv = _CONF_get_section(conf, section)) == NULL)
                sv = _CONF_new_section(conf, section);
            if (sv == NULL) {
                CONFerr(CONF_F_DEF_LOAD_BIO,
                        CONF_R_UNABLE_TO_CREATE_NEW_SECTION);
                goto err;
            }
            continue;
        } else {
            pname = s;
            psection = NULL;
            end = eat_alpha_numeric(conf, s);
            if ((end[0] == ':') && (end[1] == ':')) {
                *end = '\0';
                end += 2;
                psection = pname;
                pname = end;
                end = eat_alpha_numeric(conf, end);
            }
            p = eat_ws(conf, end);
            if (*p != '=') {
                CONFerr(CONF_F_DEF_LOAD_BIO, CONF_R_MISSING_EQUAL_SIGN);
                goto err;
            }
            *end = '\0';
            p++;
            start = eat_ws(conf, p);
            while (!IS_EOF(conf, *p))
                p++;
            p--;
            while ((p != start) && (IS_WS(conf, *p)))
                p--;
            p++;
            *p = '\0';

            if (!(v = (CONF_VALUE *)OPENSSL_malloc(sizeof(CONF_VALUE)))) {
                CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
                goto err;
            }
            if (psection == NULL)
                psection = section;
            v->name = (char *)OPENSSL_malloc(strlen(pname) + 1);
            v->value = NULL;
            if (v->name == NULL) {
                CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
                goto err;
            }
            BUF_strlcpy(v->name, pname, sgx_strlen(pname) + 1);
            if (!str_copy(conf, psection, &(v->value), start))
                goto err;

            if (sgx_strcmp(psection, section) != 0) {
                if ((tv = _CONF_get_section(conf, psection))
                    == NULL)
                    tv = _CONF_new_section(conf, psection);
                if (tv == NULL) {
                    CONFerr(CONF_F_DEF_LOAD_BIO,
                            CONF_R_UNABLE_TO_CREATE_NEW_SECTION);
                    goto err;
                }
            } else
                tv = sv;
#if 1
            if (_CONF_add_string(conf, tv, v) == 0) {
                CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
                goto err;
            }
#else
            v->section = tv->section;
            if (!sk_CONF_VALUE_push(ts, v)) {
                CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE);
                goto err;
            }
            vv = (CONF_VALUE *)lh_insert(conf->data, v);
            if (vv != NULL) {
                sk_CONF_VALUE_delete_ptr(ts, vv);
                OPENSSL_free(vv->name);
                OPENSSL_free(vv->value);
                OPENSSL_free(vv);
            }
#endif
            v = NULL;
        }
    }
    if (buff != NULL)
        BUF_MEM_free(buff);
    if (section != NULL)
        OPENSSL_free(section);
    return (1);
 err:
    if (buff != NULL)
        BUF_MEM_free(buff);
    if (section != NULL)
        OPENSSL_free(section);
    if (line != NULL)
        *line = eline;
    BIO_snprintf(btmp, sizeof btmp, "%ld", eline);
    ERR_add_error_data(2, "line ", btmp);
    if ((h != conf->data) && (conf->data != NULL)) {
        CONF_free(conf->data);
        conf->data = NULL;
    }
    if (v != NULL) {
        if (v->name != NULL)
            OPENSSL_free(v->name);
        if (v->value != NULL)
            OPENSSL_free(v->value);
        if (v != NULL)
            OPENSSL_free(v);
    }
    return (0);
}
Пример #28
0
static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
{
    long ret = 1;
    FILE *fp = (FILE *)b->ptr;
    FILE **fpp;
    char p[4];

    switch (cmd) {
    case BIO_C_FILE_SEEK:
    case BIO_CTRL_RESET:
        if (b->flags & BIO_FLAGS_UPLINK)
            ret = (long)UP_fseek(b->ptr, num, 0);
        else
            ret = (long)fseek(fp, num, 0);
        break;
    case BIO_CTRL_EOF:
        if (b->flags & BIO_FLAGS_UPLINK)
            ret = (long)UP_feof(fp);
        else
            ret = (long)feof(fp);
        break;
    case BIO_C_FILE_TELL:
    case BIO_CTRL_INFO:
        if (b->flags & BIO_FLAGS_UPLINK)
            ret = UP_ftell(b->ptr);
        else
            ret = ftell(fp);
        break;
    case BIO_C_SET_FILE_PTR:
        file_free(b);
        b->shutdown = (int)num & BIO_CLOSE;
        b->ptr = ptr;
        b->init = 1;
#  if BIO_FLAGS_UPLINK!=0
#   if defined(__MINGW32__) && defined(__MSVCRT__) && !defined(_IOB_ENTRIES)
#    define _IOB_ENTRIES 20
#   endif
#   if defined(_IOB_ENTRIES)
        /* Safety net to catch purely internal BIO_set_fp calls */
        if ((size_t)ptr >= (size_t)stdin &&
            (size_t)ptr < (size_t)(stdin + _IOB_ENTRIES))
            BIO_clear_flags(b, BIO_FLAGS_UPLINK);
#   endif
#  endif
#  ifdef UP_fsetmod
        if (b->flags & BIO_FLAGS_UPLINK)
            UP_fsetmod(b->ptr, (char)((num & BIO_FP_TEXT) ? 't' : 'b'));
        else
#  endif
        {
#  if defined(OPENSSL_SYS_WINDOWS)
            int fd = _fileno((FILE *)ptr);
            if (num & BIO_FP_TEXT)
                _setmode(fd, _O_TEXT);
            else
                _setmode(fd, _O_BINARY);
#  elif defined(OPENSSL_SYS_NETWARE) && defined(NETWARE_CLIB)
            int fd = fileno((FILE *)ptr);
            /* Under CLib there are differences in file modes */
            if (num & BIO_FP_TEXT)
                setmode(fd, O_TEXT);
            else
                setmode(fd, O_BINARY);
#  elif defined(OPENSSL_SYS_MSDOS)
            int fd = fileno((FILE *)ptr);
            /* Set correct text/binary mode */
            if (num & BIO_FP_TEXT)
                _setmode(fd, _O_TEXT);
            /* Dangerous to set stdin/stdout to raw (unless redirected) */
            else {
                if (fd == STDIN_FILENO || fd == STDOUT_FILENO) {
                    if (isatty(fd) <= 0)
                        _setmode(fd, _O_BINARY);
                } else
                    _setmode(fd, _O_BINARY);
            }
#  elif defined(OPENSSL_SYS_OS2) || defined(OPENSSL_SYS_WIN32_CYGWIN)
            int fd = fileno((FILE *)ptr);
            if (num & BIO_FP_TEXT)
                setmode(fd, O_TEXT);
            else
                setmode(fd, O_BINARY);
#  endif
        }
        break;
    case BIO_C_SET_FILENAME:
        file_free(b);
        b->shutdown = (int)num & BIO_CLOSE;
        if (num & BIO_FP_APPEND) {
            if (num & BIO_FP_READ)
                BUF_strlcpy(p, "a+", sizeof p);
            else
                BUF_strlcpy(p, "a", sizeof p);
        } else if ((num & BIO_FP_READ) && (num & BIO_FP_WRITE))
            BUF_strlcpy(p, "r+", sizeof p);
        else if (num & BIO_FP_WRITE)
            BUF_strlcpy(p, "w", sizeof p);
        else if (num & BIO_FP_READ)
            BUF_strlcpy(p, "r", sizeof p);
        else {
            BIOerr(BIO_F_FILE_CTRL, BIO_R_BAD_FOPEN_MODE);
            ret = 0;
            break;
        }
#  if defined(OPENSSL_SYS_MSDOS) || defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_OS2) || defined(OPENSSL_SYS_WIN32_CYGWIN)
        if (!(num & BIO_FP_TEXT))
            strcat(p, "b");
        else
            strcat(p, "t");
#  endif
#  if defined(OPENSSL_SYS_NETWARE)
        if (!(num & BIO_FP_TEXT))
            strcat(p, "b");
        else
            strcat(p, "t");
#  endif
        fp = fopen(ptr, p);
        if (fp == NULL) {
            SYSerr(SYS_F_FOPEN, get_last_sys_error());
            ERR_add_error_data(5, "fopen('", ptr, "','", p, "')");
            BIOerr(BIO_F_FILE_CTRL, ERR_R_SYS_LIB);
            ret = 0;
            break;
        }
        b->ptr = fp;
        b->init = 1;
        BIO_clear_flags(b, BIO_FLAGS_UPLINK); /* we did fopen -> we disengage
                                               * UPLINK */
        break;
    case BIO_C_GET_FILE_PTR:
        /* the ptr parameter is actually a FILE ** in this case. */
        if (ptr != NULL) {
            fpp = (FILE **)ptr;
            *fpp = (FILE *)b->ptr;
        }
        break;
    case BIO_CTRL_GET_CLOSE:
        ret = (long)b->shutdown;
        break;
    case BIO_CTRL_SET_CLOSE:
        b->shutdown = (int)num;
        break;
    case BIO_CTRL_FLUSH:
        if (b->flags & BIO_FLAGS_UPLINK)
            UP_fflush(b->ptr);
        else
            fflush((FILE *)b->ptr);
        break;
    case BIO_CTRL_DUP:
        ret = 1;
        break;

    case BIO_CTRL_WPENDING:
    case BIO_CTRL_PENDING:
    case BIO_CTRL_PUSH:
    case BIO_CTRL_POP:
    default:
        ret = 0;
        break;
    }
    return (ret);
}
Пример #29
0
EVP_PKEY *EVP_PKCS82PKEY (PKCS8_PRIV_KEY_INFO *p8)
{
    EVP_PKEY *pkey = NULL;
#ifndef OPENSSL_NO_RSA
    RSA *rsa = NULL;
#endif
#ifndef OPENSSL_NO_DSA
    DSA *dsa = NULL;
    ASN1_INTEGER *privkey;
    ASN1_TYPE *t1, *t2, *param = NULL;
    STACK_OF(ASN1_TYPE) *ndsa = NULL;
    BN_CTX *ctx = NULL;
    int plen;
#endif
    X509_ALGOR *a;
    unsigned char *p;
    const unsigned char *cp;
    int pkeylen;
    char obj_tmp[80];

    if(p8->pkey->type == V_ASN1_OCTET_STRING) {
        p8->broken = PKCS8_OK;
        p = p8->pkey->value.octet_string->data;
        pkeylen = p8->pkey->value.octet_string->length;
    } else {
        p8->broken = PKCS8_NO_OCTET;
        p = p8->pkey->value.sequence->data;
        pkeylen = p8->pkey->value.sequence->length;
    }
    if (!(pkey = EVP_PKEY_new())) {
        EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
        return NULL;
    }
    a = p8->pkeyalg;
    switch (OBJ_obj2nid(a->algorithm))
    {
#ifndef OPENSSL_NO_RSA
    case NID_rsaEncryption:
        cp = p;
        if (!(rsa = d2i_RSAPrivateKey (NULL,&cp, pkeylen))) {
            EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
            return NULL;
        }
        EVP_PKEY_assign_RSA (pkey, rsa);
        break;
#endif
#ifndef OPENSSL_NO_DSA
    case NID_dsa:
        /* PKCS#8 DSA is weird: you just get a private key integer
             * and parameters in the AlgorithmIdentifier the pubkey must
         * be recalculated.
         */

        /* Check for broken DSA PKCS#8, UGH! */
        if(*p == (V_ASN1_SEQUENCE|V_ASN1_CONSTRUCTED)) {
            if(!(ndsa = ASN1_seq_unpack_ASN1_TYPE(p, pkeylen,
                                                  d2i_ASN1_TYPE,
                                                  ASN1_TYPE_free))) {
                EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
                goto dsaerr;
            }
            if(sk_ASN1_TYPE_num(ndsa) != 2 ) {
                EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
                goto dsaerr;
            }
            /* Handle Two broken types:
             * SEQUENCE {parameters, priv_key}
             * SEQUENCE {pub_key, priv_key}
             */

            t1 = sk_ASN1_TYPE_value(ndsa, 0);
            t2 = sk_ASN1_TYPE_value(ndsa, 1);
            if(t1->type == V_ASN1_SEQUENCE) {
                p8->broken = PKCS8_EMBEDDED_PARAM;
                param = t1;
            } else if(a->parameter->type == V_ASN1_SEQUENCE) {
                p8->broken = PKCS8_NS_DB;
                param = a->parameter;
            } else {
                EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
                goto dsaerr;
            }

            if(t2->type != V_ASN1_INTEGER) {
                EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
                goto dsaerr;
            }
            privkey = t2->value.integer;
        } else {
            if (!(privkey=d2i_ASN1_INTEGER (NULL, &p, pkeylen))) {
                EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
                goto dsaerr;
            }
            param = p8->pkeyalg->parameter;
        }
        if (!param || (param->type != V_ASN1_SEQUENCE)) {
            EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
            goto dsaerr;
        }
        cp = p = param->value.sequence->data;
        plen = param->value.sequence->length;
        if (!(dsa = d2i_DSAparams (NULL, &cp, plen))) {
            EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_DECODE_ERROR);
            goto dsaerr;
        }
        /* We have parameters now set private key */
        if (!(dsa->priv_key = ASN1_INTEGER_to_BN(privkey, NULL))) {
            EVPerr(EVP_F_EVP_PKCS82PKEY,EVP_R_BN_DECODE_ERROR);
            goto dsaerr;
        }
        /* Calculate public key (ouch!) */
        if (!(dsa->pub_key = BN_new())) {
            EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
            goto dsaerr;
        }
        if (!(ctx = BN_CTX_new())) {
            EVPerr(EVP_F_EVP_PKCS82PKEY,ERR_R_MALLOC_FAILURE);
            goto dsaerr;
        }

        if (!BN_mod_exp(dsa->pub_key, dsa->g,
                        dsa->priv_key, dsa->p, ctx)) {

            EVPerr(EVP_F_EVP_PKCS82PKEY,EVP_R_BN_PUBKEY_ERROR);
            goto dsaerr;
        }

        EVP_PKEY_assign_DSA(pkey, dsa);
        BN_CTX_free (ctx);
        if(ndsa) sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
        else ASN1_INTEGER_free(privkey);
        break;
dsaerr:
        BN_CTX_free (ctx);
        sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
        DSA_free(dsa);
        EVP_PKEY_free(pkey);
        return NULL;
        break;
#endif
    default:
        EVPerr(EVP_F_EVP_PKCS82PKEY, EVP_R_UNSUPPORTED_PRIVATE_KEY_ALGORITHM);
        if (!a->algorithm) BUF_strlcpy (obj_tmp, "NULL", sizeof obj_tmp);
        else i2t_ASN1_OBJECT(obj_tmp, 80, a->algorithm);
        ERR_add_error_data(2, "TYPE=", obj_tmp);
        EVP_PKEY_free (pkey);
        return NULL;
    }
    return pkey;
}