openssl-1.0.0 upgrade

external/openssl

    Updated version to 1.0.0
	openssl.version

    Updated small records patch for 1.0.0. This is probably the most significant change.
	patches/small_records.patch

    Removed bad_version.patch since fix is included in 0.9.8n and beyond
	patches/README
	patches/bad_version.patch
	openssl.config

    Changed import_openssl.sh to generate armv4 asm with the 1.0.0
    scripts, not our backported 0.9.9-dev backported version in
    patches/arm-asm.patch.
	import_openssl.sh
	openssl.config
	patches/README
	patches/arm-asm.patch

    Added -DOPENSSL_NO_STORE to match ./Configure output
    Added -DOPENSSL_NO_WHIRLPOOL (no-whrlpool) to skip new optional cipher
	android-config.mk
	openssl.config

    Fixed import to remove include directory during import like other
    imported directories (apps, ssl, crypto)
	import_openssl.sh

    Updated UNNEEDED_SOURCES. Pruned Makefiles which we don't use.
	openssl.config

    Updated to build newly required files
	patches/apps_Android.mk
	patches/crypto_Android.mk

    Disable some new openssl tools
	patches/progs.patch

    Updated upgrade testing notes to include running BigInteger tests
	README.android

    Automatically imported
	android.testssl/
	apps/
	crypto/
	e_os.h
	e_os2.h
	include/
	ssl/

dalvik

   Change makeCipherList to skip SSLv2 ciphers that 1.0.0 now returns
   so there are not duplicate ciphersuite names in getEnabledCipherSuites.
	libcore/x-net/src/main/native/org_apache_harmony_xnet_provider_jsse_NativeCrypto.cpp

   Updated OpenSSLSocketImpl_cipherauthenticationmethod for new
   SSL_CIPHER algorithms -> algorithm_auth (and const-ness)
	libcore/x-net/src/main/native/org_apache_harmony_xnet_provider_jsse_NativeCrypto.cpp

   Update to const SSL_CIPHER in OpenSSLSessionImpl_getCipherSuite (and cipherauthenticationmethod)
	libcore/x-net/src/main/native/org_apache_harmony_xnet_provider_jsse_NativeCrypto.cpp

   test_EnabledCipherSuites on both SSLSocketTest and
   SSLServerSocketTest caught the makeCipherList problem. However the
   asserts where a bit out of sync and didn't give good messages
   because they didn't actually show what was going on. As part of
   debugging the issue they found, I tried to make align the asserts
   and improve their output for the future.

	libcore/x-net/src/test/java/tests/api/javax/net/ssl/SSLServerSocketTest.java
	libcore/x-net/src/test/java/tests/api/javax/net/ssl/SSLSocketTest.java

vendor/google

    Add const to X509V3_EXT_METHOD* for 1.0.0 compatibility
	libraries/libjingle/talk/base/openssladapter.cc

Change-Id: I90fb1566dede6034eebc96d2b0dcf4533d9643bf
diff --git a/crypto/dsa/Makefile b/crypto/dsa/Makefile
deleted file mode 100644
index 6c9578c..0000000
--- a/crypto/dsa/Makefile
+++ /dev/null
@@ -1,188 +0,0 @@
-#
-# OpenSSL/crypto/dsa/Makefile
-#
-
-DIR=	dsa
-TOP=	../..
-CC=	cc
-INCLUDES= -I.. -I$(TOP) -I../../include
-CFLAG=-g
-MAKEFILE=	Makefile
-AR=		ar r
-
-CFLAGS= $(INCLUDES) $(CFLAG)
-
-GENERAL=Makefile
-TEST=dsatest.c
-APPS=
-
-LIB=$(TOP)/libcrypto.a
-LIBSRC= dsa_gen.c dsa_key.c dsa_lib.c dsa_asn1.c dsa_vrf.c dsa_sign.c \
-	dsa_err.c dsa_ossl.c dsa_depr.c dsa_utl.c
-LIBOBJ= dsa_gen.o dsa_key.o dsa_lib.o dsa_asn1.o dsa_vrf.o dsa_sign.o \
-	dsa_err.o dsa_ossl.o dsa_depr.o dsa_utl.o
-
-SRC= $(LIBSRC)
-
-EXHEADER= dsa.h
-HEADER=	$(EXHEADER)
-
-ALL=    $(GENERAL) $(SRC) $(HEADER)
-
-top:
-	(cd ../..; $(MAKE) DIRS=crypto SDIRS=$(DIR) sub_all)
-
-all:	lib
-
-lib:	$(LIBOBJ)
-	$(ARX) $(LIB) $(LIBOBJ)
-	$(RANLIB) $(LIB) || echo Never mind.
-	@touch lib
-
-files:
-	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO
-
-links:
-	@$(PERL) $(TOP)/util/mklink.pl ../../include/openssl $(EXHEADER)
-	@$(PERL) $(TOP)/util/mklink.pl ../../test $(TEST)
-	@$(PERL) $(TOP)/util/mklink.pl ../../apps $(APPS)
-
-install:
-	@[ -n "$(INSTALLTOP)" ] # should be set by top Makefile...
-	@headerlist="$(EXHEADER)"; for i in $$headerlist ; \
-	do  \
-	(cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
-	chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
-	done;
-
-tags:
-	ctags $(SRC)
-
-tests:
-
-lint:
-	lint -DLINT $(INCLUDES) $(SRC)>fluff
-
-depend:
-	@[ -n "$(MAKEDEPEND)" ] # should be set by upper Makefile...
-	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(PROGS) $(LIBSRC)
-
-dclean:
-	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new
-	mv -f Makefile.new $(MAKEFILE)
-
-clean:
-	rm -f *.o */*.o *.obj lib tags core .pure .nfs* *.old *.bak fluff
-
-# DO NOT DELETE THIS LINE -- make depend depends on it.
-
-dsa_asn1.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_asn1.o: ../../include/openssl/asn1t.h ../../include/openssl/bio.h
-dsa_asn1.o: ../../include/openssl/bn.h ../../include/openssl/buffer.h
-dsa_asn1.o: ../../include/openssl/crypto.h ../../include/openssl/dsa.h
-dsa_asn1.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h
-dsa_asn1.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h
-dsa_asn1.o: ../../include/openssl/opensslconf.h
-dsa_asn1.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_asn1.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h
-dsa_asn1.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h
-dsa_asn1.o: ../cryptlib.h dsa_asn1.c
-dsa_depr.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_depr.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_depr.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_depr.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_depr.o: ../../include/openssl/err.h ../../include/openssl/evp.h
-dsa_depr.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h
-dsa_depr.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h
-dsa_depr.o: ../../include/openssl/opensslconf.h
-dsa_depr.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_depr.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h
-dsa_depr.o: ../../include/openssl/sha.h ../../include/openssl/stack.h
-dsa_depr.o: ../../include/openssl/symhacks.h ../cryptlib.h dsa_depr.c
-dsa_err.o: ../../include/openssl/bio.h ../../include/openssl/crypto.h
-dsa_err.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_err.o: ../../include/openssl/err.h ../../include/openssl/lhash.h
-dsa_err.o: ../../include/openssl/opensslconf.h ../../include/openssl/opensslv.h
-dsa_err.o: ../../include/openssl/ossl_typ.h ../../include/openssl/safestack.h
-dsa_err.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h
-dsa_err.o: dsa_err.c
-dsa_gen.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_gen.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_gen.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_gen.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_gen.o: ../../include/openssl/err.h ../../include/openssl/evp.h
-dsa_gen.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h
-dsa_gen.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h
-dsa_gen.o: ../../include/openssl/opensslconf.h ../../include/openssl/opensslv.h
-dsa_gen.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h
-dsa_gen.o: ../../include/openssl/safestack.h ../../include/openssl/sha.h
-dsa_gen.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h
-dsa_gen.o: ../cryptlib.h dsa_gen.c
-dsa_key.o: ../../e_os.h ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_key.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_key.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_key.o: ../../include/openssl/err.h ../../include/openssl/lhash.h
-dsa_key.o: ../../include/openssl/opensslconf.h ../../include/openssl/opensslv.h
-dsa_key.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h
-dsa_key.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h
-dsa_key.o: ../../include/openssl/symhacks.h ../cryptlib.h dsa_key.c
-dsa_lib.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_lib.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_lib.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_lib.o: ../../include/openssl/dh.h ../../include/openssl/dsa.h
-dsa_lib.o: ../../include/openssl/e_os2.h ../../include/openssl/ec.h
-dsa_lib.o: ../../include/openssl/ecdh.h ../../include/openssl/ecdsa.h
-dsa_lib.o: ../../include/openssl/engine.h ../../include/openssl/err.h
-dsa_lib.o: ../../include/openssl/evp.h ../../include/openssl/fips.h
-dsa_lib.o: ../../include/openssl/lhash.h ../../include/openssl/obj_mac.h
-dsa_lib.o: ../../include/openssl/objects.h ../../include/openssl/opensslconf.h
-dsa_lib.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_lib.o: ../../include/openssl/pkcs7.h ../../include/openssl/safestack.h
-dsa_lib.o: ../../include/openssl/sha.h ../../include/openssl/stack.h
-dsa_lib.o: ../../include/openssl/symhacks.h ../../include/openssl/x509.h
-dsa_lib.o: ../../include/openssl/x509_vfy.h ../cryptlib.h dsa_lib.c
-dsa_ossl.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_ossl.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_ossl.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_ossl.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_ossl.o: ../../include/openssl/err.h ../../include/openssl/lhash.h
-dsa_ossl.o: ../../include/openssl/opensslconf.h
-dsa_ossl.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_ossl.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h
-dsa_ossl.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h
-dsa_ossl.o: ../cryptlib.h dsa_ossl.c
-dsa_sign.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_sign.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_sign.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_sign.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h
-dsa_sign.o: ../../include/openssl/err.h ../../include/openssl/fips.h
-dsa_sign.o: ../../include/openssl/lhash.h ../../include/openssl/opensslconf.h
-dsa_sign.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_sign.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h
-dsa_sign.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h
-dsa_sign.o: ../cryptlib.h dsa_sign.c
-dsa_utl.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_utl.o: ../../include/openssl/bio.h ../../include/openssl/bn.h
-dsa_utl.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h
-dsa_utl.o: ../../include/openssl/dh.h ../../include/openssl/dsa.h
-dsa_utl.o: ../../include/openssl/e_os2.h ../../include/openssl/ec.h
-dsa_utl.o: ../../include/openssl/ecdh.h ../../include/openssl/ecdsa.h
-dsa_utl.o: ../../include/openssl/engine.h ../../include/openssl/err.h
-dsa_utl.o: ../../include/openssl/evp.h ../../include/openssl/fips.h
-dsa_utl.o: ../../include/openssl/lhash.h ../../include/openssl/obj_mac.h
-dsa_utl.o: ../../include/openssl/objects.h ../../include/openssl/opensslconf.h
-dsa_utl.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h
-dsa_utl.o: ../../include/openssl/pkcs7.h ../../include/openssl/safestack.h
-dsa_utl.o: ../../include/openssl/sha.h ../../include/openssl/stack.h
-dsa_utl.o: ../../include/openssl/symhacks.h ../../include/openssl/x509.h
-dsa_utl.o: ../../include/openssl/x509_vfy.h ../cryptlib.h dsa_utl.c
-dsa_vrf.o: ../../e_os.h ../../include/openssl/asn1.h
-dsa_vrf.o: ../../include/openssl/asn1_mac.h ../../include/openssl/bio.h
-dsa_vrf.o: ../../include/openssl/bn.h ../../include/openssl/buffer.h
-dsa_vrf.o: ../../include/openssl/crypto.h ../../include/openssl/dsa.h
-dsa_vrf.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h
-dsa_vrf.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h
-dsa_vrf.o: ../../include/openssl/opensslconf.h ../../include/openssl/opensslv.h
-dsa_vrf.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h
-dsa_vrf.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h
-dsa_vrf.o: ../../include/openssl/symhacks.h ../cryptlib.h dsa_vrf.c
diff --git a/crypto/dsa/dsa.h b/crypto/dsa/dsa.h
index 702c50d..ac50a5c 100644
--- a/crypto/dsa/dsa.h
+++ b/crypto/dsa/dsa.h
@@ -88,8 +88,6 @@
 # define OPENSSL_DSA_MAX_MODULUS_BITS	10000
 #endif
 
-#define OPENSSL_DSA_FIPS_MIN_MODULUS_BITS 1024
-
 #define DSA_FLAG_CACHE_MONT_P	0x01
 #define DSA_FLAG_NO_EXP_CONSTTIME       0x02 /* new with 0.9.7h; the built-in DSA
                                               * implementation now uses constant time
@@ -99,25 +97,6 @@
                                               * be used for all exponents.
                                               */
 
-/* If this flag is set the DSA method is FIPS compliant and can be used
- * in FIPS mode. This is set in the validated module method. If an
- * application sets this flag in its own methods it is its reposibility
- * to ensure the result is compliant.
- */
-
-#define DSA_FLAG_FIPS_METHOD			0x0400
-
-/* If this flag is set the operations normally disabled in FIPS mode are
- * permitted it is then the applications responsibility to ensure that the
- * usage is compliant.
- */
-
-#define DSA_FLAG_NON_FIPS_ALLOW			0x0400
-
-#ifdef OPENSSL_FIPS
-#define FIPS_DSA_SIZE_T	int
-#endif
-
 #ifdef  __cplusplus
 extern "C" {
 #endif
@@ -139,7 +118,7 @@
 	int (*dsa_sign_setup)(DSA *dsa, BN_CTX *ctx_in, BIGNUM **kinvp,
 								BIGNUM **rp);
 	int (*dsa_do_verify)(const unsigned char *dgst, int dgst_len,
-							DSA_SIG *sig, DSA *dsa);
+			     DSA_SIG *sig, DSA *dsa);
 	int (*dsa_mod_exp)(DSA *dsa, BIGNUM *rr, BIGNUM *a1, BIGNUM *p1,
 			BIGNUM *a2, BIGNUM *p2, BIGNUM *m, BN_CTX *ctx,
 			BN_MONT_CTX *in_mont);
@@ -152,7 +131,7 @@
 	char *app_data;
 	/* If this is non-NULL, it is used to generate DSA parameters */
 	int (*dsa_paramgen)(DSA *dsa, int bits,
-			unsigned char *seed, int seed_len,
+			const unsigned char *seed, int seed_len,
 			int *counter_ret, unsigned long *h_ret,
 			BN_GENCB *cb);
 	/* If this is non-NULL, it is used to generate DSA keys */
@@ -186,7 +165,6 @@
 	ENGINE *engine;
 	};
 
-#define DSAparams_dup(x) ASN1_dup_of_const(DSA,i2d_DSAparams,d2i_DSAparams,x)
 #define d2i_DSAparams_fp(fp,x) (DSA *)ASN1_d2i_fp((char *(*)())DSA_new, \
 		(char *(*)())d2i_DSAparams,(fp),(unsigned char **)(x))
 #define i2d_DSAparams_fp(fp,x) ASN1_i2d_fp(i2d_DSAparams,(fp), \
@@ -195,6 +173,7 @@
 #define i2d_DSAparams_bio(bp,x) ASN1_i2d_bio_of_const(DSA,i2d_DSAparams,bp,x)
 
 
+DSA *DSAparams_dup(DSA *x);
 DSA_SIG * DSA_SIG_new(void);
 void	DSA_SIG_free(DSA_SIG *a);
 int	i2d_DSA_SIG(const DSA_SIG *a, unsigned char **pp);
@@ -210,11 +189,6 @@
 const DSA_METHOD *DSA_get_default_method(void);
 int	DSA_set_method(DSA *dsa, const DSA_METHOD *);
 
-#ifdef OPENSSL_FIPS
-DSA *	FIPS_dsa_new(void);
-void	FIPS_dsa_free (DSA *r);
-#endif
-
 DSA *	DSA_new(void);
 DSA *	DSA_new_method(ENGINE *engine);
 void	DSA_free (DSA *r);
@@ -246,7 +220,7 @@
 
 /* New version */
 int	DSA_generate_parameters_ex(DSA *dsa, int bits,
-		unsigned char *seed,int seed_len,
+		const unsigned char *seed,int seed_len,
 		int *counter_ret, unsigned long *h_ret, BN_GENCB *cb);
 
 int	DSA_generate_key(DSA *a);
@@ -275,10 +249,13 @@
 DH *DSA_dup_DH(const DSA *r);
 #endif
 
-#ifdef OPENSSL_FIPS
-int FIPS_dsa_sig_encode(unsigned char *out, DSA_SIG *sig);
-int FIPS_dsa_sig_decode(DSA_SIG *sig, const unsigned char *in, int inlen);
-#endif
+#define EVP_PKEY_CTX_set_dsa_paramgen_bits(ctx, nbits) \
+	EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_DSA, EVP_PKEY_OP_PARAMGEN, \
+				EVP_PKEY_CTRL_DSA_PARAMGEN_BITS, nbits, NULL)
+
+#define	EVP_PKEY_CTRL_DSA_PARAMGEN_BITS		(EVP_PKEY_ALG_CTRL + 1)
+#define	EVP_PKEY_CTRL_DSA_PARAMGEN_Q_BITS	(EVP_PKEY_ALG_CTRL + 2)
+#define	EVP_PKEY_CTRL_DSA_PARAMGEN_MD		(EVP_PKEY_ALG_CTRL + 3)
 
 /* BEGIN ERROR CODES */
 /* The following lines are auto generated by the script mkerr.pl. Any changes
@@ -290,33 +267,39 @@
 
 /* Function codes. */
 #define DSA_F_D2I_DSA_SIG				 110
+#define DSA_F_DO_DSA_PRINT				 104
 #define DSA_F_DSAPARAMS_PRINT				 100
 #define DSA_F_DSAPARAMS_PRINT_FP			 101
-#define DSA_F_DSA_BUILTIN_KEYGEN			 119
-#define DSA_F_DSA_BUILTIN_PARAMGEN			 118
 #define DSA_F_DSA_DO_SIGN				 112
 #define DSA_F_DSA_DO_VERIFY				 113
-#define DSA_F_DSA_GENERATE_PARAMETERS			 117
 #define DSA_F_DSA_NEW_METHOD				 103
-#define DSA_F_DSA_PRINT					 104
+#define DSA_F_DSA_PARAM_DECODE				 119
 #define DSA_F_DSA_PRINT_FP				 105
-#define DSA_F_DSA_SET_DEFAULT_METHOD			 115
-#define DSA_F_DSA_SET_METHOD				 116
+#define DSA_F_DSA_PRIV_DECODE				 115
+#define DSA_F_DSA_PRIV_ENCODE				 116
+#define DSA_F_DSA_PUB_DECODE				 117
+#define DSA_F_DSA_PUB_ENCODE				 118
 #define DSA_F_DSA_SIGN					 106
 #define DSA_F_DSA_SIGN_SETUP				 107
 #define DSA_F_DSA_SIG_NEW				 109
 #define DSA_F_DSA_VERIFY				 108
 #define DSA_F_I2D_DSA_SIG				 111
+#define DSA_F_OLD_DSA_PRIV_DECODE			 122
+#define DSA_F_PKEY_DSA_CTRL				 120
+#define DSA_F_PKEY_DSA_KEYGEN				 121
 #define DSA_F_SIG_CB					 114
 
 /* Reason codes. */
 #define DSA_R_BAD_Q_VALUE				 102
+#define DSA_R_BN_DECODE_ERROR				 108
+#define DSA_R_BN_ERROR					 109
 #define DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE		 100
-#define DSA_R_KEY_SIZE_TOO_SMALL			 106
+#define DSA_R_DECODE_ERROR				 104
+#define DSA_R_INVALID_DIGEST_TYPE			 106
 #define DSA_R_MISSING_PARAMETERS			 101
 #define DSA_R_MODULUS_TOO_LARGE				 103
-#define DSA_R_NON_FIPS_METHOD				 104
-#define DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE	 105
+#define DSA_R_NO_PARAMETERS_SET				 107
+#define DSA_R_PARAMETER_ENCODING_ERROR			 105
 
 #ifdef  __cplusplus
 }
diff --git a/crypto/dsa/dsa_ameth.c b/crypto/dsa/dsa_ameth.c
new file mode 100644
index 0000000..5482330
--- /dev/null
+++ b/crypto/dsa/dsa_ameth.c
@@ -0,0 +1,657 @@
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
+ * project 2006.
+ */
+/* ====================================================================
+ * Copyright (c) 2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+
+#include <stdio.h>
+#include "cryptlib.h"
+#include <openssl/x509.h>
+#include <openssl/asn1.h>
+#include <openssl/dsa.h>
+#include <openssl/bn.h>
+#ifndef OPENSSL_NO_CMS
+#include <openssl/cms.h>
+#endif
+#include "asn1_locl.h"
+
+static int dsa_pub_decode(EVP_PKEY *pkey, X509_PUBKEY *pubkey)
+	{
+	const unsigned char *p, *pm;
+	int pklen, pmlen;
+	int ptype;
+	void *pval;
+	ASN1_STRING *pstr;
+	X509_ALGOR *palg;
+	ASN1_INTEGER *public_key = NULL;
+
+	DSA *dsa = NULL;
+
+	if (!X509_PUBKEY_get0_param(NULL, &p, &pklen, &palg, pubkey))
+		return 0;
+	X509_ALGOR_get0(NULL, &ptype, &pval, palg);
+
+
+	if (ptype == V_ASN1_SEQUENCE)
+		{
+		pstr = pval;	
+		pm = pstr->data;
+		pmlen = pstr->length;
+
+		if (!(dsa = d2i_DSAparams(NULL, &pm, pmlen)))
+			{
+			DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_DECODE_ERROR);
+			goto err;
+			}
+
+		}
+	else if ((ptype == V_ASN1_NULL) || (ptype == V_ASN1_UNDEF))
+		{
+		if (!(dsa = DSA_new()))
+			{
+			DSAerr(DSA_F_DSA_PUB_DECODE, ERR_R_MALLOC_FAILURE);
+			goto err;
+			}
+		}
+	else
+		{
+		DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_PARAMETER_ENCODING_ERROR);
+		goto err;
+		}
+
+	if (!(public_key=d2i_ASN1_INTEGER(NULL, &p, pklen)))
+		{
+		DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_DECODE_ERROR);
+		goto err;
+		}
+
+	if (!(dsa->pub_key = ASN1_INTEGER_to_BN(public_key, NULL)))
+		{
+		DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_BN_DECODE_ERROR);
+		goto err;
+		}
+
+	ASN1_INTEGER_free(public_key);
+	EVP_PKEY_assign_DSA(pkey, dsa);
+	return 1;
+
+	err:
+	if (public_key)
+		ASN1_INTEGER_free(public_key);
+	if (dsa)
+		DSA_free(dsa);
+	return 0;
+
+	}
+
+static int dsa_pub_encode(X509_PUBKEY *pk, const EVP_PKEY *pkey)
+	{
+	DSA *dsa;
+	void *pval = NULL;
+	int ptype;
+	unsigned char *penc = NULL;
+	int penclen;
+
+	dsa=pkey->pkey.dsa;
+	if (pkey->save_parameters && dsa->p && dsa->q && dsa->g)
+		{
+		ASN1_STRING *str;
+		str = ASN1_STRING_new();
+		str->length = i2d_DSAparams(dsa, &str->data);
+		if (str->length <= 0)
+			{
+			DSAerr(DSA_F_DSA_PUB_ENCODE, ERR_R_MALLOC_FAILURE);
+			goto err;
+			}
+		pval = str;
+		ptype = V_ASN1_SEQUENCE;
+		}
+	else
+		ptype = V_ASN1_UNDEF;
+
+	dsa->write_params=0;
+
+	penclen = i2d_DSAPublicKey(dsa, &penc);
+
+	if (penclen <= 0)
+		{
+		DSAerr(DSA_F_DSA_PUB_ENCODE, ERR_R_MALLOC_FAILURE);
+		goto err;
+		}
+
+	if (X509_PUBKEY_set0_param(pk, OBJ_nid2obj(EVP_PKEY_DSA),
+				ptype, pval, penc, penclen))
+		return 1;
+
+	err:
+	if (penc)
+		OPENSSL_free(penc);
+	if (pval)
+		ASN1_STRING_free(pval);
+
+	return 0;
+	}
+
+/* In PKCS#8 DSA: you just get a private key integer and parameters in the
+ * AlgorithmIdentifier the pubkey must be recalculated.
+ */
+	
+static int dsa_priv_decode(EVP_PKEY *pkey, PKCS8_PRIV_KEY_INFO *p8)
+	{
+	const unsigned char *p, *pm;
+	int pklen, pmlen;
+	int ptype;
+	void *pval;
+	ASN1_STRING *pstr;
+	X509_ALGOR *palg;
+	ASN1_INTEGER *privkey = NULL;
+	BN_CTX *ctx = NULL;
+
+	STACK_OF(ASN1_TYPE) *ndsa = NULL;
+	DSA *dsa = NULL;
+
+	if (!PKCS8_pkey_get0(NULL, &p, &pklen, &palg, p8))
+		return 0;
+	X509_ALGOR_get0(NULL, &ptype, &pval, palg);
+
+	/* Check for broken DSA PKCS#8, UGH! */
+	if (*p == (V_ASN1_SEQUENCE|V_ASN1_CONSTRUCTED))
+		{
+		ASN1_TYPE *t1, *t2;
+	    	if(!(ndsa = d2i_ASN1_SEQUENCE_ANY(NULL, &p, pklen)));
+			goto decerr;
+		if (sk_ASN1_TYPE_num(ndsa) != 2)
+			goto decerr;
+		/* 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;
+			pval = t1->value.ptr;
+			}
+		else if (ptype == V_ASN1_SEQUENCE)
+			p8->broken = PKCS8_NS_DB;
+		else
+			goto decerr;
+
+		if (t2->type != V_ASN1_INTEGER)
+			goto decerr;
+
+		privkey = t2->value.integer;
+		}
+	else
+		{
+		const unsigned char *q = p;
+		if (!(privkey=d2i_ASN1_INTEGER(NULL, &p, pklen)))
+			goto decerr;
+		if (privkey->type == V_ASN1_NEG_INTEGER)
+			{
+			p8->broken = PKCS8_NEG_PRIVKEY;
+			ASN1_INTEGER_free(privkey);
+			if (!(privkey=d2i_ASN1_UINTEGER(NULL, &q, pklen)))
+				goto decerr;
+			}
+		if (ptype != V_ASN1_SEQUENCE)
+			goto decerr;
+		}
+
+	pstr = pval;	
+	pm = pstr->data;
+	pmlen = pstr->length;
+	if (!(dsa = d2i_DSAparams(NULL, &pm, pmlen)))
+		goto decerr;
+	/* We have parameters now set private key */
+	if (!(dsa->priv_key = ASN1_INTEGER_to_BN(privkey, NULL)))
+		{
+		DSAerr(DSA_F_DSA_PRIV_DECODE,DSA_R_BN_ERROR);
+		goto dsaerr;
+		}
+	/* Calculate public key */
+	if (!(dsa->pub_key = BN_new()))
+		{
+		DSAerr(DSA_F_DSA_PRIV_DECODE, ERR_R_MALLOC_FAILURE);
+		goto dsaerr;
+		}
+	if (!(ctx = BN_CTX_new()))
+		{
+		DSAerr(DSA_F_DSA_PRIV_DECODE, ERR_R_MALLOC_FAILURE);
+		goto dsaerr;
+		}
+			
+	if (!BN_mod_exp(dsa->pub_key, dsa->g, dsa->priv_key, dsa->p, ctx))
+		{
+		DSAerr(DSA_F_DSA_PRIV_DECODE,DSA_R_BN_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);
+
+	return 1;
+
+	decerr:
+	DSAerr(DSA_F_DSA_PRIV_DECODE, EVP_R_DECODE_ERROR);
+	dsaerr:
+	BN_CTX_free (ctx);
+	if (privkey)
+		ASN1_INTEGER_free(privkey);
+	sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
+	DSA_free(dsa);
+	return 0;
+	}
+
+static int dsa_priv_encode(PKCS8_PRIV_KEY_INFO *p8, const EVP_PKEY *pkey)
+{
+	ASN1_STRING *params = NULL;
+	ASN1_INTEGER *prkey = NULL;
+	unsigned char *dp = NULL;
+	int dplen;
+
+	params = ASN1_STRING_new();
+
+	if (!params)
+		{
+		DSAerr(DSA_F_DSA_PRIV_ENCODE,ERR_R_MALLOC_FAILURE);
+		goto err;
+		}
+
+	params->length = i2d_DSAparams(pkey->pkey.dsa, &params->data);
+	if (params->length <= 0)
+		{
+		DSAerr(DSA_F_DSA_PRIV_ENCODE,ERR_R_MALLOC_FAILURE);
+		goto err;
+		}
+	params->type = V_ASN1_SEQUENCE;
+
+	/* Get private key into integer */
+	prkey = BN_to_ASN1_INTEGER(pkey->pkey.dsa->priv_key, NULL);
+
+	if (!prkey)
+		{
+		DSAerr(DSA_F_DSA_PRIV_ENCODE,DSA_R_BN_ERROR);
+		goto err;
+		}
+
+	dplen = i2d_ASN1_INTEGER(prkey, &dp);
+
+	ASN1_INTEGER_free(prkey);
+
+	if (!PKCS8_pkey_set0(p8, OBJ_nid2obj(NID_dsa), 0,
+				V_ASN1_SEQUENCE, params, dp, dplen))
+		goto err;
+
+	return 1;
+
+err:
+	if (dp != NULL)
+		OPENSSL_free(dp);
+	if (params != NULL)
+		ASN1_STRING_free(params);
+	if (prkey != NULL)
+		ASN1_INTEGER_free(prkey);
+	return 0;
+}
+
+static int int_dsa_size(const EVP_PKEY *pkey)
+	{
+	return(DSA_size(pkey->pkey.dsa));
+	}
+
+static int dsa_bits(const EVP_PKEY *pkey)
+	{
+	return BN_num_bits(pkey->pkey.dsa->p);
+	}
+
+static int dsa_missing_parameters(const EVP_PKEY *pkey)
+	{
+	DSA *dsa;
+	dsa=pkey->pkey.dsa;
+	if ((dsa->p == NULL) || (dsa->q == NULL) || (dsa->g == NULL))
+			return 1;
+	return 0;
+	}
+
+static int dsa_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from)
+	{
+	BIGNUM *a;
+
+	if ((a=BN_dup(from->pkey.dsa->p)) == NULL)
+		return 0;
+	if (to->pkey.dsa->p != NULL)
+		BN_free(to->pkey.dsa->p);
+	to->pkey.dsa->p=a;
+
+	if ((a=BN_dup(from->pkey.dsa->q)) == NULL)
+		return 0;
+	if (to->pkey.dsa->q != NULL)
+		BN_free(to->pkey.dsa->q);
+	to->pkey.dsa->q=a;
+
+	if ((a=BN_dup(from->pkey.dsa->g)) == NULL)
+		return 0;
+	if (to->pkey.dsa->g != NULL)
+		BN_free(to->pkey.dsa->g);
+	to->pkey.dsa->g=a;
+	return 1;
+	}
+
+static int dsa_cmp_parameters(const EVP_PKEY *a, const EVP_PKEY *b)
+	{
+	if (	BN_cmp(a->pkey.dsa->p,b->pkey.dsa->p) ||
+		BN_cmp(a->pkey.dsa->q,b->pkey.dsa->q) ||
+		BN_cmp(a->pkey.dsa->g,b->pkey.dsa->g))
+		return 0;
+	else
+		return 1;
+	}
+
+static int dsa_pub_cmp(const EVP_PKEY *a, const EVP_PKEY *b)
+	{
+	if (BN_cmp(b->pkey.dsa->pub_key,a->pkey.dsa->pub_key) != 0)
+		return 0;
+	else
+		return 1;
+	}
+
+static void int_dsa_free(EVP_PKEY *pkey)
+	{
+	DSA_free(pkey->pkey.dsa);
+	}
+
+static void update_buflen(const BIGNUM *b, size_t *pbuflen)
+	{
+	size_t i;
+	if (!b)
+		return;
+	if (*pbuflen < (i = (size_t)BN_num_bytes(b)))
+			*pbuflen = i;
+	}
+
+static int do_dsa_print(BIO *bp, const DSA *x, int off, int ptype)
+	{
+	unsigned char *m=NULL;
+	int ret=0;
+	size_t buf_len=0;
+	const char *ktype = NULL;
+
+	const BIGNUM *priv_key, *pub_key;
+
+	if (ptype == 2)
+		priv_key = x->priv_key;
+	else
+		priv_key = NULL;
+
+	if (ptype > 0)
+		pub_key = x->pub_key;
+	else
+		pub_key = NULL;
+
+	if (ptype == 2)
+		ktype = "Private-Key";
+	else if (ptype == 1)
+		ktype = "Public-Key";
+	else
+		ktype = "DSA-Parameters";
+
+	update_buflen(x->p, &buf_len);
+	update_buflen(x->q, &buf_len);
+	update_buflen(x->g, &buf_len);
+	update_buflen(priv_key, &buf_len);
+	update_buflen(pub_key, &buf_len);
+
+	m=(unsigned char *)OPENSSL_malloc(buf_len+10);
+	if (m == NULL)
+		{
+		DSAerr(DSA_F_DO_DSA_PRINT,ERR_R_MALLOC_FAILURE);
+		goto err;
+		}
+
+	if (priv_key)
+		{
+		if(!BIO_indent(bp,off,128))
+		   goto err;
+		if (BIO_printf(bp,"%s: (%d bit)\n",ktype, BN_num_bits(x->p))
+			<= 0) goto err;
+		}
+
+	if (!ASN1_bn_print(bp,"priv:",priv_key,m,off))
+		goto err;
+	if (!ASN1_bn_print(bp,"pub: ",pub_key,m,off))
+		goto err;
+	if (!ASN1_bn_print(bp,"P:   ",x->p,m,off)) goto err;
+	if (!ASN1_bn_print(bp,"Q:   ",x->q,m,off)) goto err;
+	if (!ASN1_bn_print(bp,"G:   ",x->g,m,off)) goto err;
+	ret=1;
+err:
+	if (m != NULL) OPENSSL_free(m);
+	return(ret);
+	}
+
+static int dsa_param_decode(EVP_PKEY *pkey,
+					const unsigned char **pder, int derlen)
+	{
+	DSA *dsa;
+	if (!(dsa = d2i_DSAparams(NULL, pder, derlen)))
+		{
+		DSAerr(DSA_F_DSA_PARAM_DECODE, ERR_R_DSA_LIB);
+		return 0;
+		}
+	EVP_PKEY_assign_DSA(pkey, dsa);
+	return 1;
+	}
+
+static int dsa_param_encode(const EVP_PKEY *pkey, unsigned char **pder)
+	{
+	return i2d_DSAparams(pkey->pkey.dsa, pder);
+	}
+
+static int dsa_param_print(BIO *bp, const EVP_PKEY *pkey, int indent,
+							ASN1_PCTX *ctx)
+	{
+	return do_dsa_print(bp, pkey->pkey.dsa, indent, 0);
+	}
+
+static int dsa_pub_print(BIO *bp, const EVP_PKEY *pkey, int indent,
+							ASN1_PCTX *ctx)
+	{
+	return do_dsa_print(bp, pkey->pkey.dsa, indent, 1);
+	}
+
+
+static int dsa_priv_print(BIO *bp, const EVP_PKEY *pkey, int indent,
+							ASN1_PCTX *ctx)
+	{
+	return do_dsa_print(bp, pkey->pkey.dsa, indent, 2);
+	}
+
+static int old_dsa_priv_decode(EVP_PKEY *pkey,
+					const unsigned char **pder, int derlen)
+	{
+	DSA *dsa;
+	if (!(dsa = d2i_DSAPrivateKey (NULL, pder, derlen)))
+		{
+		DSAerr(DSA_F_OLD_DSA_PRIV_DECODE, ERR_R_DSA_LIB);
+		return 0;
+		}
+	EVP_PKEY_assign_DSA(pkey, dsa);
+	return 1;
+	}
+
+static int old_dsa_priv_encode(const EVP_PKEY *pkey, unsigned char **pder)
+	{
+	return i2d_DSAPrivateKey(pkey->pkey.dsa, pder);
+	}
+
+static int dsa_pkey_ctrl(EVP_PKEY *pkey, int op, long arg1, void *arg2)
+	{
+	switch (op)
+		{
+		case ASN1_PKEY_CTRL_PKCS7_SIGN:
+		if (arg1 == 0)
+			{
+			int snid, hnid;
+			X509_ALGOR *alg1, *alg2;
+			PKCS7_SIGNER_INFO_get0_algs(arg2, NULL, &alg1, &alg2);
+			if (alg1 == NULL || alg1->algorithm == NULL)
+				return -1;
+			hnid = OBJ_obj2nid(alg1->algorithm);
+			if (hnid == NID_undef)
+				return -1;
+			if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey)))
+				return -1; 
+			X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0);
+			}
+		return 1;
+#ifndef OPENSSL_NO_CMS
+		case ASN1_PKEY_CTRL_CMS_SIGN:
+		if (arg1 == 0)
+			{
+			int snid, hnid;
+			X509_ALGOR *alg1, *alg2;
+			CMS_SignerInfo_get0_algs(arg2, NULL, NULL, &alg1, &alg2);
+			if (alg1 == NULL || alg1->algorithm == NULL)
+				return -1;
+			hnid = OBJ_obj2nid(alg1->algorithm);
+			if (hnid == NID_undef)
+				return -1;
+			if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey)))
+				return -1; 
+			X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0);
+			}
+		return 1;
+#endif
+
+		case ASN1_PKEY_CTRL_DEFAULT_MD_NID:
+		*(int *)arg2 = NID_sha1;
+		return 2;
+
+		default:
+		return -2;
+
+		}
+
+	}
+
+/* NB these are sorted in pkey_id order, lowest first */
+
+const EVP_PKEY_ASN1_METHOD dsa_asn1_meths[] = 
+	{
+
+		{
+		EVP_PKEY_DSA2,
+		EVP_PKEY_DSA,
+		ASN1_PKEY_ALIAS
+		},
+
+		{
+		EVP_PKEY_DSA1,
+		EVP_PKEY_DSA,
+		ASN1_PKEY_ALIAS
+		},
+
+		{
+		EVP_PKEY_DSA4,
+		EVP_PKEY_DSA,
+		ASN1_PKEY_ALIAS
+		},
+
+		{
+		EVP_PKEY_DSA3,
+		EVP_PKEY_DSA,
+		ASN1_PKEY_ALIAS
+		},
+
+		{
+		EVP_PKEY_DSA,
+		EVP_PKEY_DSA,
+		0,
+
+		"DSA",
+		"OpenSSL DSA method",
+
+		dsa_pub_decode,
+		dsa_pub_encode,
+		dsa_pub_cmp,
+		dsa_pub_print,
+
+		dsa_priv_decode,
+		dsa_priv_encode,
+		dsa_priv_print,
+
+		int_dsa_size,
+		dsa_bits,
+
+		dsa_param_decode,
+		dsa_param_encode,
+		dsa_missing_parameters,
+		dsa_copy_parameters,
+		dsa_cmp_parameters,
+		dsa_param_print,
+
+		int_dsa_free,
+		dsa_pkey_ctrl,
+		old_dsa_priv_decode,
+		old_dsa_priv_encode
+		}
+	};
+
diff --git a/crypto/dsa/dsa_asn1.c b/crypto/dsa/dsa_asn1.c
index bc7d7a0..c37460b 100644
--- a/crypto/dsa/dsa_asn1.c
+++ b/crypto/dsa/dsa_asn1.c
@@ -3,7 +3,7 @@
  * project 2000.
  */
 /* ====================================================================
- * Copyright (c) 2000 The OpenSSL Project.  All rights reserved.
+ * Copyright (c) 2000-2005 The OpenSSL Project.  All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -61,25 +61,23 @@
 #include <openssl/dsa.h>
 #include <openssl/asn1.h>
 #include <openssl/asn1t.h>
-#include <openssl/bn.h>
-#include <openssl/rand.h>
-#ifdef OPENSSL_FIPS
-#include <openssl/fips.h>
-#endif
-
 
 /* Override the default new methods */
-static int sig_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it)
+static int sig_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
+								void *exarg)
 {
 	if(operation == ASN1_OP_NEW_PRE) {
 		DSA_SIG *sig;
 		sig = OPENSSL_malloc(sizeof(DSA_SIG));
+		if (!sig)
+			{
+			DSAerr(DSA_F_SIG_CB, ERR_R_MALLOC_FAILURE);
+			return 0;
+			}
 		sig->r = NULL;
 		sig->s = NULL;
 		*pval = (ASN1_VALUE *)sig;
-		if(sig) return 2;
-		DSAerr(DSA_F_SIG_CB, ERR_R_MALLOC_FAILURE);
-		return 0;
+		return 2;
 	}
 	return 1;
 }
@@ -89,10 +87,11 @@
 	ASN1_SIMPLE(DSA_SIG, s, CBIGNUM)
 } ASN1_SEQUENCE_END_cb(DSA_SIG, DSA_SIG)
 
-IMPLEMENT_ASN1_ENCODE_FUNCTIONS_const_fname(DSA_SIG,DSA_SIG,DSA_SIG)
+IMPLEMENT_ASN1_FUNCTIONS_const(DSA_SIG)
 
 /* Override the default free and new methods */
-static int dsa_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it)
+static int dsa_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
+							void *exarg)
 {
 	if(operation == ASN1_OP_NEW_PRE) {
 		*pval = (ASN1_VALUE *)DSA_new();
@@ -145,76 +144,7 @@
 
 IMPLEMENT_ASN1_ENCODE_FUNCTIONS_const_fname(DSA, DSAPublicKey, DSAPublicKey)
 
-int DSA_sign(int type, const unsigned char *dgst, int dlen, unsigned char *sig,
-	     unsigned int *siglen, DSA *dsa)
+DSA *DSAparams_dup(DSA *dsa)
 	{
-	DSA_SIG *s;
-#ifdef OPENSSL_FIPS
-	if(FIPS_mode() && !(dsa->flags & DSA_FLAG_NON_FIPS_ALLOW))
-		{
-		DSAerr(DSA_F_DSA_SIGN, DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE);
-		return 0;
-		}
-#endif
-	RAND_seed(dgst, dlen);
-	s=DSA_do_sign(dgst,dlen,dsa);
-	if (s == NULL)
-		{
-		*siglen=0;
-		return(0);
-		}
-	*siglen=i2d_DSA_SIG(s,&sig);
-	DSA_SIG_free(s);
-	return(1);
+	return ASN1_item_dup(ASN1_ITEM_rptr(DSAparams), dsa);
 	}
-
-int DSA_size(const DSA *r)
-	{
-	int ret,i;
-	ASN1_INTEGER bs;
-	unsigned char buf[4];	/* 4 bytes looks really small.
-				   However, i2d_ASN1_INTEGER() will not look
-				   beyond the first byte, as long as the second
-				   parameter is NULL. */
-
-	i=BN_num_bits(r->q);
-	bs.length=(i+7)/8;
-	bs.data=buf;
-	bs.type=V_ASN1_INTEGER;
-	/* If the top bit is set the asn1 encoding is 1 larger. */
-	buf[0]=0xff;	
-
-	i=i2d_ASN1_INTEGER(&bs,NULL);
-	i+=i; /* r and s */
-	ret=ASN1_object_size(1,i,V_ASN1_SEQUENCE);
-	return(ret);
-	}
-
-/* data has already been hashed (probably with SHA or SHA-1). */
-/* returns
- *      1: correct signature
- *      0: incorrect signature
- *     -1: error
- */
-int DSA_verify(int type, const unsigned char *dgst, int dgst_len,
-	     const unsigned char *sigbuf, int siglen, DSA *dsa)
-	{
-	DSA_SIG *s;
-	int ret=-1;
-#ifdef OPENSSL_FIPS
-	if(FIPS_mode() && !(dsa->flags & DSA_FLAG_NON_FIPS_ALLOW))
-		{
-		DSAerr(DSA_F_DSA_VERIFY, DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE);
-		return 0;
-		}
-#endif
-
-	s = DSA_SIG_new();
-	if (s == NULL) return(ret);
-	if (d2i_DSA_SIG(&s,&sigbuf,siglen) == NULL) goto err;
-	ret=DSA_do_verify(dgst,dgst_len,s,dsa);
-err:
-	DSA_SIG_free(s);
-	return(ret);
-	}
-
diff --git a/crypto/dsa/dsa_err.c b/crypto/dsa/dsa_err.c
index 872839a..bba984e 100644
--- a/crypto/dsa/dsa_err.c
+++ b/crypto/dsa/dsa_err.c
@@ -1,6 +1,6 @@
 /* crypto/dsa/dsa_err.c */
 /* ====================================================================
- * Copyright (c) 1999-2007 The OpenSSL Project.  All rights reserved.
+ * Copyright (c) 1999-2006 The OpenSSL Project.  All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -71,23 +71,26 @@
 static ERR_STRING_DATA DSA_str_functs[]=
 	{
 {ERR_FUNC(DSA_F_D2I_DSA_SIG),	"d2i_DSA_SIG"},
+{ERR_FUNC(DSA_F_DO_DSA_PRINT),	"DO_DSA_PRINT"},
 {ERR_FUNC(DSA_F_DSAPARAMS_PRINT),	"DSAparams_print"},
 {ERR_FUNC(DSA_F_DSAPARAMS_PRINT_FP),	"DSAparams_print_fp"},
-{ERR_FUNC(DSA_F_DSA_BUILTIN_KEYGEN),	"DSA_BUILTIN_KEYGEN"},
-{ERR_FUNC(DSA_F_DSA_BUILTIN_PARAMGEN),	"DSA_BUILTIN_PARAMGEN"},
 {ERR_FUNC(DSA_F_DSA_DO_SIGN),	"DSA_do_sign"},
 {ERR_FUNC(DSA_F_DSA_DO_VERIFY),	"DSA_do_verify"},
-{ERR_FUNC(DSA_F_DSA_GENERATE_PARAMETERS),	"DSA_generate_parameters"},
 {ERR_FUNC(DSA_F_DSA_NEW_METHOD),	"DSA_new_method"},
-{ERR_FUNC(DSA_F_DSA_PRINT),	"DSA_print"},
+{ERR_FUNC(DSA_F_DSA_PARAM_DECODE),	"DSA_PARAM_DECODE"},
 {ERR_FUNC(DSA_F_DSA_PRINT_FP),	"DSA_print_fp"},
-{ERR_FUNC(DSA_F_DSA_SET_DEFAULT_METHOD),	"DSA_set_default_method"},
-{ERR_FUNC(DSA_F_DSA_SET_METHOD),	"DSA_set_method"},
+{ERR_FUNC(DSA_F_DSA_PRIV_DECODE),	"DSA_PRIV_DECODE"},
+{ERR_FUNC(DSA_F_DSA_PRIV_ENCODE),	"DSA_PRIV_ENCODE"},
+{ERR_FUNC(DSA_F_DSA_PUB_DECODE),	"DSA_PUB_DECODE"},
+{ERR_FUNC(DSA_F_DSA_PUB_ENCODE),	"DSA_PUB_ENCODE"},
 {ERR_FUNC(DSA_F_DSA_SIGN),	"DSA_sign"},
 {ERR_FUNC(DSA_F_DSA_SIGN_SETUP),	"DSA_sign_setup"},
 {ERR_FUNC(DSA_F_DSA_SIG_NEW),	"DSA_SIG_new"},
 {ERR_FUNC(DSA_F_DSA_VERIFY),	"DSA_verify"},
 {ERR_FUNC(DSA_F_I2D_DSA_SIG),	"i2d_DSA_SIG"},
+{ERR_FUNC(DSA_F_OLD_DSA_PRIV_DECODE),	"OLD_DSA_PRIV_DECODE"},
+{ERR_FUNC(DSA_F_PKEY_DSA_CTRL),	"PKEY_DSA_CTRL"},
+{ERR_FUNC(DSA_F_PKEY_DSA_KEYGEN),	"PKEY_DSA_KEYGEN"},
 {ERR_FUNC(DSA_F_SIG_CB),	"SIG_CB"},
 {0,NULL}
 	};
@@ -95,12 +98,15 @@
 static ERR_STRING_DATA DSA_str_reasons[]=
 	{
 {ERR_REASON(DSA_R_BAD_Q_VALUE)           ,"bad q value"},
+{ERR_REASON(DSA_R_BN_DECODE_ERROR)       ,"bn decode error"},
+{ERR_REASON(DSA_R_BN_ERROR)              ,"bn error"},
 {ERR_REASON(DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE),"data too large for key size"},
-{ERR_REASON(DSA_R_KEY_SIZE_TOO_SMALL)    ,"key size too small"},
+{ERR_REASON(DSA_R_DECODE_ERROR)          ,"decode error"},
+{ERR_REASON(DSA_R_INVALID_DIGEST_TYPE)   ,"invalid digest type"},
 {ERR_REASON(DSA_R_MISSING_PARAMETERS)    ,"missing parameters"},
 {ERR_REASON(DSA_R_MODULUS_TOO_LARGE)     ,"modulus too large"},
-{ERR_REASON(DSA_R_NON_FIPS_METHOD)       ,"non fips method"},
-{ERR_REASON(DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE),"operation not allowed in fips mode"},
+{ERR_REASON(DSA_R_NO_PARAMETERS_SET)     ,"no parameters set"},
+{ERR_REASON(DSA_R_PARAMETER_ENCODING_ERROR),"parameter encoding error"},
 {0,NULL}
 	};
 
diff --git a/crypto/dsa/dsa_gen.c b/crypto/dsa/dsa_gen.c
index 6f1728e..0fcd25f 100644
--- a/crypto/dsa/dsa_gen.c
+++ b/crypto/dsa/dsa_gen.c
@@ -74,69 +74,88 @@
 #ifndef OPENSSL_NO_SHA
 
 #include <stdio.h>
-#include <time.h>
 #include "cryptlib.h"
 #include <openssl/evp.h>
 #include <openssl/bn.h>
-#include <openssl/dsa.h>
 #include <openssl/rand.h>
 #include <openssl/sha.h>
-
-#ifndef OPENSSL_FIPS
-
-static int dsa_builtin_paramgen(DSA *ret, int bits,
-		unsigned char *seed_in, int seed_len,
-		int *counter_ret, unsigned long *h_ret, BN_GENCB *cb);
+#include "dsa_locl.h"
 
 int DSA_generate_parameters_ex(DSA *ret, int bits,
-		unsigned char *seed_in, int seed_len,
+		const unsigned char *seed_in, int seed_len,
 		int *counter_ret, unsigned long *h_ret, BN_GENCB *cb)
 	{
 	if(ret->meth->dsa_paramgen)
 		return ret->meth->dsa_paramgen(ret, bits, seed_in, seed_len,
 				counter_ret, h_ret, cb);
-	return dsa_builtin_paramgen(ret, bits, seed_in, seed_len,
-			counter_ret, h_ret, cb);
+	else
+		{
+		const EVP_MD *evpmd;
+		size_t qbits = bits >= 2048 ? 256 : 160;
+
+		if (bits >= 2048)
+			{
+			qbits = 256;
+			evpmd = EVP_sha256();
+			}
+		else
+			{
+			qbits = 160;
+			evpmd = EVP_sha1();
+			}
+
+		return dsa_builtin_paramgen(ret, bits, qbits, evpmd,
+				seed_in, seed_len, counter_ret, h_ret, cb);
+		}
 	}
 
-static int dsa_builtin_paramgen(DSA *ret, int bits,
-		unsigned char *seed_in, int seed_len,
-		int *counter_ret, unsigned long *h_ret, BN_GENCB *cb)
+int dsa_builtin_paramgen(DSA *ret, size_t bits, size_t qbits,
+	const EVP_MD *evpmd, const unsigned char *seed_in, size_t seed_len,
+	int *counter_ret, unsigned long *h_ret, BN_GENCB *cb)
 	{
 	int ok=0;
-	unsigned char seed[SHA_DIGEST_LENGTH];
-	unsigned char md[SHA_DIGEST_LENGTH];
-	unsigned char buf[SHA_DIGEST_LENGTH],buf2[SHA_DIGEST_LENGTH];
+	unsigned char seed[SHA256_DIGEST_LENGTH];
+	unsigned char md[SHA256_DIGEST_LENGTH];
+	unsigned char buf[SHA256_DIGEST_LENGTH],buf2[SHA256_DIGEST_LENGTH];
 	BIGNUM *r0,*W,*X,*c,*test;
 	BIGNUM *g=NULL,*q=NULL,*p=NULL;
 	BN_MONT_CTX *mont=NULL;
-	int k,n=0,i,b,m=0;
+	int i, k,n=0,b,m=0, qsize = qbits >> 3;
 	int counter=0;
 	int r=0;
 	BN_CTX *ctx=NULL;
 	unsigned int h=2;
 
-	if (bits < 512) bits=512;
-	bits=(bits+63)/64*64;
+	if (qsize != SHA_DIGEST_LENGTH && qsize != SHA224_DIGEST_LENGTH &&
+	    qsize != SHA256_DIGEST_LENGTH)
+		/* invalid q size */
+		return 0;
+
+	if (evpmd == NULL)
+		/* use SHA1 as default */
+		evpmd = EVP_sha1();
+
+	if (bits < 512)
+		bits = 512;
+
+	bits = (bits+63)/64*64;
 
 	/* NB: seed_len == 0 is special case: copy generated seed to
  	 * seed_in if it is not NULL.
  	 */
-	if (seed_len && (seed_len < 20))
-		seed_in = NULL; /* seed buffer too small -- ignore */
-	if (seed_len > 20) 
-		seed_len = 20; /* App. 2.2 of FIPS PUB 186 allows larger SEED,
-		                * but our internal buffers are restricted to 160 bits*/
-	if ((seed_in != NULL) && (seed_len == 20))
-		{
-		memcpy(seed,seed_in,seed_len);
-		/* set seed_in to NULL to avoid it being copied back */
-		seed_in = NULL;
-		}
+	if (seed_len && (seed_len < (size_t)qsize))
+		seed_in = NULL;		/* seed buffer too small -- ignore */
+	if (seed_len > (size_t)qsize) 
+		seed_len = qsize;	/* App. 2.2 of FIPS PUB 186 allows larger SEED,
+					 * but our internal buffers are restricted to 160 bits*/
+	if (seed_in != NULL)
+		memcpy(seed, seed_in, seed_len);
 
-	if ((ctx=BN_CTX_new()) == NULL) goto err;
+	if ((ctx=BN_CTX_new()) == NULL)
+		goto err;
 
-	if ((mont=BN_MONT_CTX_new()) == NULL) goto err;
+	if ((mont=BN_MONT_CTX_new()) == NULL)
+		goto err;
 
 	BN_CTX_start(ctx);
 	r0 = BN_CTX_get(ctx);
@@ -163,7 +182,7 @@
 
 			if (!seed_len)
 				{
-				RAND_pseudo_bytes(seed,SHA_DIGEST_LENGTH);
+				RAND_pseudo_bytes(seed, qsize);
 				seed_is_random = 1;
 				}
 			else
@@ -171,25 +190,27 @@
 				seed_is_random = 0;
 				seed_len=0; /* use random seed if 'seed_in' turns out to be bad*/
 				}
-			memcpy(buf,seed,SHA_DIGEST_LENGTH);
-			memcpy(buf2,seed,SHA_DIGEST_LENGTH);
+			memcpy(buf , seed, qsize);
+			memcpy(buf2, seed, qsize);
 			/* precompute "SEED + 1" for step 7: */
-			for (i=SHA_DIGEST_LENGTH-1; i >= 0; i--)
+			for (i = qsize-1; i >= 0; i--)
 				{
 				buf[i]++;
-				if (buf[i] != 0) break;
+				if (buf[i] != 0)
+					break;
 				}
 
 			/* step 2 */
-			EVP_Digest(seed,SHA_DIGEST_LENGTH,md,NULL,HASH, NULL);
-			EVP_Digest(buf,SHA_DIGEST_LENGTH,buf2,NULL,HASH, NULL);
-			for (i=0; i<SHA_DIGEST_LENGTH; i++)
+			EVP_Digest(seed, qsize, md,   NULL, evpmd, NULL);
+			EVP_Digest(buf,  qsize, buf2, NULL, evpmd, NULL);
+			for (i = 0; i < qsize; i++)
 				md[i]^=buf2[i];
 
 			/* step 3 */
-			md[0]|=0x80;
-			md[SHA_DIGEST_LENGTH-1]|=0x01;
-			if (!BN_bin2bn(md,SHA_DIGEST_LENGTH,q)) goto err;
+			md[0] |= 0x80;
+			md[qsize-1] |= 0x01;
+			if (!BN_bin2bn(md, qsize, q))
+				goto err;
 
 			/* step 4 */
 			r = BN_is_prime_fasttest_ex(q, DSS_prime_checks, ctx,
@@ -224,18 +245,19 @@
 			for (k=0; k<=n; k++)
 				{
 				/* obtain "SEED + offset + k" by incrementing: */
-				for (i=SHA_DIGEST_LENGTH-1; i >= 0; i--)
+				for (i = qsize-1; i >= 0; i--)
 					{
 					buf[i]++;
-					if (buf[i] != 0) break;
+					if (buf[i] != 0)
+						break;
 					}
 
-				EVP_Digest(buf,SHA_DIGEST_LENGTH,md,NULL,HASH, NULL);
+				EVP_Digest(buf, qsize, md ,NULL, evpmd, NULL);
 
 				/* step 8 */
-				if (!BN_bin2bn(md,SHA_DIGEST_LENGTH,r0))
+				if (!BN_bin2bn(md, qsize, r0))
 					goto err;
-				if (!BN_lshift(r0,r0,160*k)) goto err;
+				if (!BN_lshift(r0,r0,(qsize << 3)*k)) goto err;
 				if (!BN_add(W,W,r0)) goto err;
 				}
 
@@ -309,7 +331,6 @@
 			ok=0;
 			goto err;
 			}
-		if (seed_in != NULL) memcpy(seed_in,seed,20);
 		if (counter_ret != NULL) *counter_ret=counter;
 		if (h_ret != NULL) *h_ret=h;
 		}
@@ -322,4 +343,3 @@
 	return ok;
 	}
 #endif
-#endif
diff --git a/crypto/dsa/dsa_key.c b/crypto/dsa/dsa_key.c
index 5e39124..c4aa86b 100644
--- a/crypto/dsa/dsa_key.c
+++ b/crypto/dsa/dsa_key.c
@@ -64,8 +64,6 @@
 #include <openssl/dsa.h>
 #include <openssl/rand.h>
 
-#ifndef OPENSSL_FIPS
-
 static int dsa_builtin_keygen(DSA *dsa);
 
 int DSA_generate_key(DSA *dsa)
@@ -128,5 +126,3 @@
 	return(ok);
 	}
 #endif
-
-#endif
diff --git a/crypto/dsa/dsa_lib.c b/crypto/dsa/dsa_lib.c
index 85556d1..e9b7590 100644
--- a/crypto/dsa/dsa_lib.c
+++ b/crypto/dsa/dsa_lib.c
@@ -76,14 +76,6 @@
 
 void DSA_set_default_method(const DSA_METHOD *meth)
 	{
-#ifdef OPENSSL_FIPS
-	if (FIPS_mode() && !(meth->flags & DSA_FLAG_FIPS_METHOD))
-		{
-		DSAerr(DSA_F_DSA_SET_DEFAULT_METHOD, DSA_R_NON_FIPS_METHOD);
-		return;
-		}
-#endif
-		
 	default_DSA_method = meth;
 	}
 
@@ -104,13 +96,6 @@
 	/* NB: The caller is specifically setting a method, so it's not up to us
 	 * to deal with which ENGINE it comes from. */
         const DSA_METHOD *mtmp;
-#ifdef OPENSSL_FIPS
-	if (FIPS_mode() && !(meth->flags & DSA_FLAG_FIPS_METHOD))
-		{
-		DSAerr(DSA_F_DSA_SET_METHOD, DSA_R_NON_FIPS_METHOD);
-		return 0;
-		}
-#endif
         mtmp = dsa->meth;
         if (mtmp->finish) mtmp->finish(dsa);
 #ifndef OPENSSL_NO_ENGINE
@@ -162,18 +147,6 @@
 			}
 		}
 #endif
-#ifdef OPENSSL_FIPS
-	if (FIPS_mode() && !(ret->meth->flags & DSA_FLAG_FIPS_METHOD))
-		{
-		DSAerr(DSA_F_DSA_NEW_METHOD, DSA_R_NON_FIPS_METHOD);
-#ifndef OPENSSL_NO_ENGINE
-		if (ret->engine)
-			ENGINE_finish(ret->engine);
-#endif
-		OPENSSL_free(ret);
-		return NULL;
-		}
-#endif
 
 	ret->pad=0;
 	ret->version=0;
@@ -190,7 +163,7 @@
 	ret->method_mont_p=NULL;
 
 	ret->references=1;
-	ret->flags=ret->meth->flags & ~DSA_FLAG_NON_FIPS_ALLOW;
+	ret->flags=ret->meth->flags;
 	CRYPTO_new_ex_data(CRYPTO_EX_INDEX_DSA, ret, &ret->ex_data);
 	if ((ret->meth->init != NULL) && !ret->meth->init(ret))
 		{
@@ -260,6 +233,28 @@
 	return ((i > 1) ? 1 : 0);
 	}
 
+int DSA_size(const DSA *r)
+	{
+	int ret,i;
+	ASN1_INTEGER bs;
+	unsigned char buf[4];	/* 4 bytes looks really small.
+				   However, i2d_ASN1_INTEGER() will not look
+				   beyond the first byte, as long as the second
+				   parameter is NULL. */
+
+	i=BN_num_bits(r->q);
+	bs.length=(i+7)/8;
+	bs.data=buf;
+	bs.type=V_ASN1_INTEGER;
+	/* If the top bit is set the asn1 encoding is 1 larger. */
+	buf[0]=0xff;	
+
+	i=i2d_ASN1_INTEGER(&bs,NULL);
+	i+=i; /* r and s */
+	ret=ASN1_object_size(1,i,V_ASN1_SEQUENCE);
+	return(ret);
+	}
+
 int DSA_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func,
 	     CRYPTO_EX_dup *dup_func, CRYPTO_EX_free *free_func)
         {
diff --git a/crypto/dsa/dsa_locl.h b/crypto/dsa/dsa_locl.h
new file mode 100644
index 0000000..2b8cfee
--- /dev/null
+++ b/crypto/dsa/dsa_locl.h
@@ -0,0 +1,59 @@
+/* ====================================================================
+ * Copyright (c) 2007 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+
+#include <openssl/dsa.h>
+
+int dsa_builtin_paramgen(DSA *ret, size_t bits, size_t qbits,
+	const EVP_MD *evpmd, const unsigned char *seed_in, size_t seed_len,
+	int *counter_ret, unsigned long *h_ret, BN_GENCB *cb);
diff --git a/crypto/dsa/dsa_ossl.c b/crypto/dsa/dsa_ossl.c
index 412cf1d..4fead07 100644
--- a/crypto/dsa/dsa_ossl.c
+++ b/crypto/dsa/dsa_ossl.c
@@ -61,16 +61,15 @@
 #include <stdio.h>
 #include "cryptlib.h"
 #include <openssl/bn.h>
+#include <openssl/sha.h>
 #include <openssl/dsa.h>
 #include <openssl/rand.h>
 #include <openssl/asn1.h>
 
-#ifndef OPENSSL_FIPS
-
 static DSA_SIG *dsa_do_sign(const unsigned char *dgst, int dlen, DSA *dsa);
 static int dsa_sign_setup(DSA *dsa, BN_CTX *ctx_in, BIGNUM **kinvp, BIGNUM **rp);
 static int dsa_do_verify(const unsigned char *dgst, int dgst_len, DSA_SIG *sig,
-		  DSA *dsa);
+			 DSA *dsa);
 static int dsa_init(DSA *dsa);
 static int dsa_finish(DSA *dsa);
 
@@ -135,7 +134,7 @@
 	BIGNUM m;
 	BIGNUM xr;
 	BN_CTX *ctx=NULL;
-	int i,reason=ERR_R_BN_LIB;
+	int reason=ERR_R_BN_LIB;
 	DSA_SIG *ret=NULL;
 
 	BN_init(&m);
@@ -150,8 +149,9 @@
 	s=BN_new();
 	if (s == NULL) goto err;
 
-	i=BN_num_bytes(dsa->q); /* should be 20 */
-	if ((dlen > i) || (dlen > 50))
+	/* reject a excessive digest length (currently at most
+	 * dsa-with-SHA256 is supported) */
+	if (dlen > SHA256_DIGEST_LENGTH)
 		{
 		reason=DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE;
 		goto err;
@@ -172,7 +172,14 @@
 		dsa->r=NULL;
 		}
 
-	if (BN_bin2bn(dgst,dlen,&m) == NULL) goto err;
+	
+	if (dlen > BN_num_bytes(dsa->q))
+		/* if the digest length is greater than the size of q use the
+		 * BN_num_bits(dsa->q) leftmost bits of the digest, see
+		 * fips 186-3, 4.2 */
+		dlen = BN_num_bytes(dsa->q);
+	if (BN_bin2bn(dgst,dlen,&m) == NULL)
+		goto err;
 
 	/* Compute  s = inv(k) (m + xr) mod q */
 	if (!BN_mod_mul(&xr,dsa->priv_key,r,dsa->q,ctx)) goto err;/* s = xr */
@@ -283,30 +290,31 @@
 	if (!ret)
 		{
 		DSAerr(DSA_F_DSA_SIGN_SETUP,ERR_R_BN_LIB);
-		if (kinv != NULL) BN_clear_free(kinv);
-		if (r != NULL) BN_clear_free(r);
+		if (r != NULL)
+			BN_clear_free(r);
 		}
 	if (ctx_in == NULL) BN_CTX_free(ctx);
-	if (kinv != NULL) BN_clear_free(kinv);
 	BN_clear_free(&k);
 	BN_clear_free(&kq);
 	return(ret);
 	}
 
 static int dsa_do_verify(const unsigned char *dgst, int dgst_len, DSA_SIG *sig,
-		  DSA *dsa)
+			 DSA *dsa)
 	{
 	BN_CTX *ctx;
 	BIGNUM u1,u2,t1;
 	BN_MONT_CTX *mont=NULL;
-	int ret = -1;
+	int ret = -1, i;
 	if (!dsa->p || !dsa->q || !dsa->g)
 		{
 		DSAerr(DSA_F_DSA_DO_VERIFY,DSA_R_MISSING_PARAMETERS);
 		return -1;
 		}
 
-	if (BN_num_bits(dsa->q) != 160)
+	i = BN_num_bits(dsa->q);
+	/* fips 186-3 allows only different sizes for q */
+	if (i != 160 && i != 224 && i != 256)
 		{
 		DSAerr(DSA_F_DSA_DO_VERIFY,DSA_R_BAD_Q_VALUE);
 		return -1;
@@ -318,6 +326,14 @@
 		return -1;
 		}
 
+	/* reject a excessive digest length (currently at most
+	 * dsa-with-SHA256 is supported) */
+	if (dgst_len > SHA256_DIGEST_LENGTH)
+		{
+		DSAerr(DSA_F_DSA_DO_VERIFY,DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE);
+		return -1;
+		}
+
 	BN_init(&u1);
 	BN_init(&u2);
 	BN_init(&t1);
@@ -342,6 +358,11 @@
 	if ((BN_mod_inverse(&u2,sig->s,dsa->q,ctx)) == NULL) goto err;
 
 	/* save M in u1 */
+	if (dgst_len > (i >> 3))
+		/* if the digest length is greater than the size of q use the
+		 * BN_num_bits(dsa->q) leftmost bits of the digest, see
+		 * fips 186-3, 4.2 */
+		dgst_len = (i >> 3);
 	if (BN_bin2bn(dgst,dgst_len,&u1) == NULL) goto err;
 
 	/* u1 = M * w mod q */
@@ -393,4 +414,3 @@
 	return(1);
 }
 
-#endif
diff --git a/crypto/dsa/dsa_pmeth.c b/crypto/dsa/dsa_pmeth.c
new file mode 100644
index 0000000..4ce91e2
--- /dev/null
+++ b/crypto/dsa/dsa_pmeth.c
@@ -0,0 +1,315 @@
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
+ * project 2006.
+ */
+/* ====================================================================
+ * Copyright (c) 2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+
+#include <stdio.h>
+#include "cryptlib.h"
+#include <openssl/asn1t.h>
+#include <openssl/x509.h>
+#include <openssl/evp.h>
+#include <openssl/bn.h>
+#include "evp_locl.h"
+#include "dsa_locl.h"
+
+/* DSA pkey context structure */
+
+typedef struct
+	{
+	/* Parameter gen parameters */
+	int nbits;		/* size of p in bits (default: 1024) */
+	int qbits;		/* size of q in bits (default: 160)  */
+	const EVP_MD *pmd;	/* MD for parameter generation */
+	/* Keygen callback info */
+	int gentmp[2];
+	/* message digest */
+	const EVP_MD *md;	/* MD for the signature */
+	} DSA_PKEY_CTX;
+
+static int pkey_dsa_init(EVP_PKEY_CTX *ctx)
+	{
+	DSA_PKEY_CTX *dctx;
+	dctx = OPENSSL_malloc(sizeof(DSA_PKEY_CTX));
+	if (!dctx)
+		return 0;
+	dctx->nbits = 1024;
+	dctx->qbits = 160;
+	dctx->pmd = NULL;
+	dctx->md = NULL;
+
+	ctx->data = dctx;
+	ctx->keygen_info = dctx->gentmp;
+	ctx->keygen_info_count = 2;
+	
+	return 1;
+	}
+
+static int pkey_dsa_copy(EVP_PKEY_CTX *dst, EVP_PKEY_CTX *src)
+	{
+	DSA_PKEY_CTX *dctx, *sctx;
+	if (!pkey_dsa_init(dst))
+		return 0;
+       	sctx = src->data;
+	dctx = dst->data;
+	dctx->nbits = sctx->nbits;
+	dctx->qbits = sctx->qbits;
+	dctx->pmd = sctx->pmd;
+	dctx->md  = sctx->md;
+	return 1;
+	}
+
+static void pkey_dsa_cleanup(EVP_PKEY_CTX *ctx)
+	{
+	DSA_PKEY_CTX *dctx = ctx->data;
+	if (dctx)
+		OPENSSL_free(dctx);
+	}
+
+static int pkey_dsa_sign(EVP_PKEY_CTX *ctx, unsigned char *sig, size_t *siglen,
+					const unsigned char *tbs, size_t tbslen)
+	{
+	int ret, type;
+	unsigned int sltmp;
+	DSA_PKEY_CTX *dctx = ctx->data;
+	DSA *dsa = ctx->pkey->pkey.dsa;
+
+	if (dctx->md)
+		type = EVP_MD_type(dctx->md);
+	else
+		type = NID_sha1;
+
+	ret = DSA_sign(type, tbs, tbslen, sig, &sltmp, dsa);
+
+	if (ret <= 0)
+		return ret;
+	*siglen = sltmp;
+	return 1;
+	}
+
+static int pkey_dsa_verify(EVP_PKEY_CTX *ctx,
+					const unsigned char *sig, size_t siglen,
+					const unsigned char *tbs, size_t tbslen)
+	{
+	int ret, type;
+	DSA_PKEY_CTX *dctx = ctx->data;
+	DSA *dsa = ctx->pkey->pkey.dsa;
+
+	if (dctx->md)
+		type = EVP_MD_type(dctx->md);
+	else
+		type = NID_sha1;
+
+	ret = DSA_verify(type, tbs, tbslen, sig, siglen, dsa);
+
+	return ret;
+	}
+
+static int pkey_dsa_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2)
+	{
+	DSA_PKEY_CTX *dctx = ctx->data;
+	switch (type)
+		{
+		case EVP_PKEY_CTRL_DSA_PARAMGEN_BITS:
+		if (p1 < 256)
+			return -2;
+		dctx->nbits = p1;
+		return 1;
+
+		case EVP_PKEY_CTRL_DSA_PARAMGEN_Q_BITS:
+		if (p1 != 160 && p1 != 224 && p1 && p1 != 256)
+			return -2;
+		dctx->qbits = p1;
+		return 1;
+
+		case EVP_PKEY_CTRL_DSA_PARAMGEN_MD:
+		if (EVP_MD_type((const EVP_MD *)p2) != NID_sha1   &&
+		    EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
+		    EVP_MD_type((const EVP_MD *)p2) != NID_sha256)
+			{
+			DSAerr(DSA_F_PKEY_DSA_CTRL, DSA_R_INVALID_DIGEST_TYPE);
+			return 0;
+			}
+		dctx->md = p2;
+		return 1;
+
+		case EVP_PKEY_CTRL_MD:
+		if (EVP_MD_type((const EVP_MD *)p2) != NID_sha1   &&
+		    EVP_MD_type((const EVP_MD *)p2) != NID_dsa    &&
+		    EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
+		    EVP_MD_type((const EVP_MD *)p2) != NID_sha256)
+			{
+			DSAerr(DSA_F_PKEY_DSA_CTRL, DSA_R_INVALID_DIGEST_TYPE);
+			return 0;
+			}
+		dctx->md = p2;
+		return 1;
+
+		case EVP_PKEY_CTRL_DIGESTINIT:
+		case EVP_PKEY_CTRL_PKCS7_SIGN:
+		case EVP_PKEY_CTRL_CMS_SIGN:
+		return 1;
+		
+		case EVP_PKEY_CTRL_PEER_KEY:
+			DSAerr(DSA_F_PKEY_DSA_CTRL,
+			EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
+			return -2;	
+		default:
+		return -2;
+
+		}
+	}
+			
+static int pkey_dsa_ctrl_str(EVP_PKEY_CTX *ctx,
+			const char *type, const char *value)
+	{
+	if (!strcmp(type, "dsa_paramgen_bits"))
+		{
+		int nbits;
+		nbits = atoi(value);
+		return EVP_PKEY_CTX_set_dsa_paramgen_bits(ctx, nbits);
+		}
+	if (!strcmp(type, "dsa_paramgen_q_bits"))
+		{
+		int qbits = atoi(value);
+		return EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_DSA, EVP_PKEY_OP_PARAMGEN,
+		                         EVP_PKEY_CTRL_DSA_PARAMGEN_Q_BITS, qbits, NULL);
+		}
+	if (!strcmp(type, "dsa_paramgen_md"))
+		{
+		return EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_DSA, EVP_PKEY_OP_PARAMGEN,
+		                         EVP_PKEY_CTRL_DSA_PARAMGEN_MD, 0, 
+		                         (void *)EVP_get_digestbyname(value));
+		}
+	return -2;
+	}
+
+static int pkey_dsa_paramgen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
+	{
+	DSA *dsa = NULL;
+	DSA_PKEY_CTX *dctx = ctx->data;
+	BN_GENCB *pcb, cb;
+	int ret;
+	if (ctx->pkey_gencb)
+		{
+		pcb = &cb;
+		evp_pkey_set_cb_translate(pcb, ctx);
+		}
+	else
+		pcb = NULL;
+	dsa = DSA_new();
+	if (!dsa)
+		return 0;
+	ret = dsa_builtin_paramgen(dsa, dctx->nbits, dctx->qbits, dctx->pmd,
+	                           NULL, 0, NULL, NULL, pcb);
+	if (ret)
+		EVP_PKEY_assign_DSA(pkey, dsa);
+	else
+		DSA_free(dsa);
+	return ret;
+	}
+
+static int pkey_dsa_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
+	{
+	DSA *dsa = NULL;
+	if (ctx->pkey == NULL)
+		{
+		DSAerr(DSA_F_PKEY_DSA_KEYGEN, DSA_R_NO_PARAMETERS_SET);
+		return 0;
+		}
+	dsa = DSA_new();
+	if (!dsa)
+		return 0;
+	EVP_PKEY_assign_DSA(pkey, dsa);
+	/* Note: if error return, pkey is freed by parent routine */
+	if (!EVP_PKEY_copy_parameters(pkey, ctx->pkey))
+		return 0;
+	return DSA_generate_key(pkey->pkey.dsa);
+	}
+
+const EVP_PKEY_METHOD dsa_pkey_meth = 
+	{
+	EVP_PKEY_DSA,
+	EVP_PKEY_FLAG_AUTOARGLEN,
+	pkey_dsa_init,
+	pkey_dsa_copy,
+	pkey_dsa_cleanup,
+
+	0,
+	pkey_dsa_paramgen,
+
+	0,
+	pkey_dsa_keygen,
+
+	0,
+	pkey_dsa_sign,
+
+	0,
+	pkey_dsa_verify,
+
+	0,0,
+
+	0,0,0,0,
+
+	0,0,
+
+	0,0,
+
+	0,0,
+
+	pkey_dsa_ctrl,
+	pkey_dsa_ctrl_str
+
+
+	};
diff --git a/crypto/dsa/dsa_prn.c b/crypto/dsa/dsa_prn.c
new file mode 100644
index 0000000..6f29f5e
--- /dev/null
+++ b/crypto/dsa/dsa_prn.c
@@ -0,0 +1,121 @@
+/* crypto/dsa/dsa_prn.c */
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
+ * project 2006.
+ */
+/* ====================================================================
+ * Copyright (c) 2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+
+#include <stdio.h>
+#include "cryptlib.h"
+#include <openssl/evp.h>
+#include <openssl/dsa.h>
+
+#ifndef OPENSSL_NO_FP_API
+int DSA_print_fp(FILE *fp, const DSA *x, int off)
+	{
+	BIO *b;
+	int ret;
+
+	if ((b=BIO_new(BIO_s_file())) == NULL)
+		{
+		DSAerr(DSA_F_DSA_PRINT_FP,ERR_R_BUF_LIB);
+		return(0);
+		}
+	BIO_set_fp(b,fp,BIO_NOCLOSE);
+	ret=DSA_print(b,x,off);
+	BIO_free(b);
+	return(ret);
+	}
+
+int DSAparams_print_fp(FILE *fp, const DSA *x)
+	{
+	BIO *b;
+	int ret;
+
+	if ((b=BIO_new(BIO_s_file())) == NULL)
+		{
+		DSAerr(DSA_F_DSAPARAMS_PRINT_FP,ERR_R_BUF_LIB);
+		return(0);
+		}
+	BIO_set_fp(b,fp,BIO_NOCLOSE);
+	ret=DSAparams_print(b, x);
+	BIO_free(b);
+	return(ret);
+	}
+#endif
+
+int DSA_print(BIO *bp, const DSA *x, int off)
+	{
+	EVP_PKEY *pk;
+	int ret;
+	pk = EVP_PKEY_new();
+	if (!pk || !EVP_PKEY_set1_DSA(pk, (DSA *)x))
+		return 0;
+	ret = EVP_PKEY_print_private(bp, pk, off, NULL);
+	EVP_PKEY_free(pk);
+	return ret;
+	}
+
+int DSAparams_print(BIO *bp, const DSA *x)
+	{
+	EVP_PKEY *pk;
+	int ret;
+	pk = EVP_PKEY_new();
+	if (!pk || !EVP_PKEY_set1_DSA(pk, (DSA *)x))
+		return 0;
+	ret = EVP_PKEY_print_params(bp, pk, 4, NULL);
+	EVP_PKEY_free(pk);
+	return ret;
+	}
+
diff --git a/crypto/dsa/dsa_sign.c b/crypto/dsa/dsa_sign.c
index 4cfbbe5..17555e5 100644
--- a/crypto/dsa/dsa_sign.c
+++ b/crypto/dsa/dsa_sign.c
@@ -58,38 +58,33 @@
 
 /* Original version from Steven Schoch <schoch@sheba.arc.nasa.gov> */
 
-#include <stdio.h>
 #include "cryptlib.h"
-#include <openssl/bn.h>
 #include <openssl/dsa.h>
 #include <openssl/rand.h>
-#include <openssl/asn1.h>
-#ifdef OPENSSL_FIPS
-#include <openssl/fips.h>
-#endif
-
 
 DSA_SIG * DSA_do_sign(const unsigned char *dgst, int dlen, DSA *dsa)
 	{
-#ifdef OPENSSL_FIPS
-	if(FIPS_mode() && !(dsa->flags & DSA_FLAG_NON_FIPS_ALLOW))
-		{
-		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE);
-		return NULL;
-		}
-#endif
 	return dsa->meth->dsa_do_sign(dgst, dlen, dsa);
 	}
 
+int DSA_sign(int type, const unsigned char *dgst, int dlen, unsigned char *sig,
+	     unsigned int *siglen, DSA *dsa)
+	{
+	DSA_SIG *s;
+	RAND_seed(dgst, dlen);
+	s=DSA_do_sign(dgst,dlen,dsa);
+	if (s == NULL)
+		{
+		*siglen=0;
+		return(0);
+		}
+	*siglen=i2d_DSA_SIG(s,&sig);
+	DSA_SIG_free(s);
+	return(1);
+	}
+
 int DSA_sign_setup(DSA *dsa, BN_CTX *ctx_in, BIGNUM **kinvp, BIGNUM **rp)
 	{
-#ifdef OPENSSL_FIPS
-	if(FIPS_mode() && !(dsa->flags & DSA_FLAG_NON_FIPS_ALLOW))
-		{
-		DSAerr(DSA_F_DSA_SIGN_SETUP, DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE);
-		return 0;
-		}
-#endif
 	return dsa->meth->dsa_sign_setup(dsa, ctx_in, kinvp, rp);
 	}
 
diff --git a/crypto/dsa/dsa_utl.c b/crypto/dsa/dsa_utl.c
deleted file mode 100644
index 24c021d..0000000
--- a/crypto/dsa/dsa_utl.c
+++ /dev/null
@@ -1,95 +0,0 @@
-/* crypto/dsa/dsa_lib.c */
-/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
- * All rights reserved.
- *
- * This package is an SSL implementation written
- * by Eric Young (eay@cryptsoft.com).
- * The implementation was written so as to conform with Netscapes SSL.
- * 
- * This library is free for commercial and non-commercial use as long as
- * the following conditions are aheared to.  The following conditions
- * apply to all code found in this distribution, be it the RC4, RSA,
- * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
- * included with this distribution is covered by the same copyright terms
- * except that the holder is Tim Hudson (tjh@cryptsoft.com).
- * 
- * Copyright remains Eric Young's, and as such any Copyright notices in
- * the code are not to be removed.
- * If this package is used in a product, Eric Young should be given attribution
- * as the author of the parts of the library used.
- * This can be in the form of a textual message at program startup or
- * in documentation (online or textual) provided with the package.
- * 
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the copyright
- *    notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *    notice, this list of conditions and the following disclaimer in the
- *    documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- *    must display the following acknowledgement:
- *    "This product includes cryptographic software written by
- *     Eric Young (eay@cryptsoft.com)"
- *    The word 'cryptographic' can be left out if the rouines from the library
- *    being used are not cryptographic related :-).
- * 4. If you include any Windows specific code (or a derivative thereof) from 
- *    the apps directory (application code) you must include an acknowledgement:
- *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
- * 
- * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- * 
- * The licence and distribution terms for any publically available version or
- * derivative of this code cannot be changed.  i.e. this code cannot simply be
- * copied and put under another distribution licence
- * [including the GNU Public Licence.]
- */
-
-/* Original version from Steven Schoch <schoch@sheba.arc.nasa.gov> */
-
-#include <stdio.h>
-#include "cryptlib.h"
-#include <openssl/bn.h>
-#include <openssl/dsa.h>
-#include <openssl/asn1.h>
-#ifndef OPENSSL_NO_ENGINE
-#include <openssl/engine.h>
-#endif
-#ifndef OPENSSL_NO_DH
-#include <openssl/dh.h>
-#endif
-
-DSA_SIG *DSA_SIG_new(void)
-	{
-	DSA_SIG *sig;
-	sig = OPENSSL_malloc(sizeof(DSA_SIG));
-	if (!sig)
-		return NULL;
-	sig->r = NULL;
-	sig->s = NULL;
-	return sig;
-	}
-
-void DSA_SIG_free(DSA_SIG *sig)
-	{
-	if (sig)
-		{
-		if (sig->r)
-			BN_free(sig->r);
-		if (sig->s)
-			BN_free(sig->s);
-		OPENSSL_free(sig);
-		}
-	}
-
diff --git a/crypto/dsa/dsa_vrf.c b/crypto/dsa/dsa_vrf.c
index c75e423..226a75f 100644
--- a/crypto/dsa/dsa_vrf.c
+++ b/crypto/dsa/dsa_vrf.c
@@ -58,27 +58,32 @@
 
 /* Original version from Steven Schoch <schoch@sheba.arc.nasa.gov> */
 
-#include <stdio.h>
 #include "cryptlib.h"
-#include <openssl/bn.h>
 #include <openssl/dsa.h>
-#include <openssl/rand.h>
-#include <openssl/asn1.h>
-#ifdef OPENSSL_FIPS
-#include <openssl/fips.h>
-#endif
-
-#include <openssl/asn1_mac.h>
 
 int DSA_do_verify(const unsigned char *dgst, int dgst_len, DSA_SIG *sig,
 		  DSA *dsa)
 	{
-#ifdef OPENSSL_FIPS
-	if(FIPS_mode() && !(dsa->flags & DSA_FLAG_NON_FIPS_ALLOW))
-		{
-		DSAerr(DSA_F_DSA_DO_VERIFY, DSA_R_OPERATION_NOT_ALLOWED_IN_FIPS_MODE);
-		return 0;
-		}
-#endif
 	return dsa->meth->dsa_do_verify(dgst, dgst_len, sig, dsa);
 	}
+
+/* data has already been hashed (probably with SHA or SHA-1). */
+/* returns
+ *      1: correct signature
+ *      0: incorrect signature
+ *     -1: error
+ */
+int DSA_verify(int type, const unsigned char *dgst, int dgst_len,
+	     const unsigned char *sigbuf, int siglen, DSA *dsa)
+	{
+	DSA_SIG *s;
+	int ret=-1;
+
+	s = DSA_SIG_new();
+	if (s == NULL) return(ret);
+	if (d2i_DSA_SIG(&s,&sigbuf,siglen) == NULL) goto err;
+	ret=DSA_do_verify(dgst,dgst_len,s,dsa);
+err:
+	DSA_SIG_free(s);
+	return(ret);
+	}
diff --git a/crypto/dsa/dsatest.c b/crypto/dsa/dsatest.c
index 912317b..edffd24 100644
--- a/crypto/dsa/dsatest.c
+++ b/crypto/dsa/dsatest.c
@@ -169,7 +169,6 @@
 		}
 	BIO_printf(bio_err,"\ncounter=%d h=%ld\n",counter,h);
 		
-	if (dsa == NULL) goto end;
 	DSA_print(bio_err,dsa,0);
 	if (counter != 105) 
 		{
@@ -223,7 +222,7 @@
 		ERR_print_errors(bio_err);
 	if (dsa != NULL) DSA_free(dsa);
 	CRYPTO_cleanup_all_ex_data();
-	ERR_remove_state(0);
+	ERR_remove_thread_state(NULL);
 	ERR_free_strings();
 	CRYPTO_mem_leaks(bio_err);
 	if (bio_err != NULL)