diff --git a/hmac-md5.h b/hmac-md5.h
new file mode 100644
index 0000000000000000000000000000000000000000..014e51b98a1c7547bdc105fb81dae42572721f9a
--- /dev/null
+++ b/hmac-md5.h
@@ -0,0 +1,46 @@
+/* hmac-md5.h
+ *
+ * HMAC message authentication code.
+ */
+
+/* nettle, low-level cryptographics library
+ *
+ * Copyright (C) 2001 Niels M�ller
+ *  
+ * The nettle library is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation; either version 2.1 of the License, or (at your
+ * option) any later version.
+ * 
+ * The nettle library is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
+ * License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with the nettle library; see the file COPYING.LIB.  If not, write to
+ * the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
+ * MA 02111-1307, USA.
+ */
+
+#ifndef NETTLE_HMAC_MD5_H_INCLUDED
+#define NETTLE_HMAC_MD5_H_INCLUDED
+
+#include "hmac.h"
+#include "md5.h"
+
+struct hmac_md5_ctx HMAC_CTX(struct md5_ctx);
+
+void
+hmac_md5_set_key(struct hmac_md5_ctx *ctx,
+		 unsigned key_length, const uint8_t *key);
+
+void
+hmac_md5_update(struct hmac_md5_ctx *ctx,
+		unsigned length, const uint8_t *data);
+
+void
+hmac_md5_digest(struct hmac_md5_ctx *ctx,
+		unsigned length, uint8_t *digest);
+
+#endif /* NETTLE_HMAC_MD5_H_INCLUDED */
diff --git a/rsa.h b/rsa.h
index 08df531dba5c9e67de6bed6935819e87261d1726..295abc31b8b58c92c2f66474191717d16cce73bd 100644
--- a/rsa.h
+++ b/rsa.h
@@ -137,5 +137,14 @@ rsa_sha1_verify(struct rsa_public_key *key,
 void
 rsa_compute_root(struct rsa_private_key *key, mpz_t x, const mpz_t m);
 
+#define RSA_SIGN(key, algorithm, ctx, length, data, signature) ( \
+  algorithm##_update(ctx, length, data), \
+  rsa_##algorithm##_sign(key, ctx, signature) \
+)
+
+#define RSA_VERIFY(key, algorithm, ctx, length, data, signature) ( \
+  algorithm##_update(ctx, length, data), \
+  rsa_##algorithm##_verify(key, ctx, signature) \
+)
 
 #endif /* NETTLE_RSA_H_INCLUDED */
diff --git a/rsa_md5.c b/rsa_md5.c
index a0a0109cfb2c47b47e0a80d5daf885c39f5f8714..a8cf622c7aa54311f5c6a6f5a4464145086cda77 100644
--- a/rsa_md5.c
+++ b/rsa_md5.c
@@ -90,7 +90,8 @@ rsa_md5_verify(struct rsa_public_key *key,
  *   md5Identifier ::= AlgorithmIdentifier {md5, NULL}
  */
 
-static const uint8_t md5_prefix[] =
+static const uint8_t
+md5_prefix[] =
 {
   /* 18 octets prefix, 16 octets hash, 34 total. */
   0x30,       32, /* SEQUENCE */
diff --git a/rsa_sha1.c b/rsa_sha1.c
index 21c70f29152a8c2fe47ecdd92e18498df00dba60..864e44a0c246b2bd5c626c2a6f9e05827e9570c4 100644
--- a/rsa_sha1.c
+++ b/rsa_sha1.c
@@ -90,7 +90,8 @@ rsa_sha1_verify(struct rsa_public_key *key,
  *   sha1Identifier ::= AlgorithmIdentifier {id-sha1, NULL}
  */
 
-static const uint8_t sha1_prefix[] =
+static const uint8_t
+sha1_prefix[] =
 {
   /* 15 octets prefix, 20 octets hash, total 35 */
   0x30,       33, /* SEQUENCE */
@@ -102,8 +103,6 @@ static const uint8_t sha1_prefix[] =
       /* Here comes the raw hash value */
 };
     
-
-
 static void
 pkcs1_encode_sha1(mpz_t m, unsigned length, struct sha1_ctx *hash)
 {
diff --git a/testsuite/Makefile.am b/testsuite/Makefile.am
index 3229f03c9c851a4af5c03b95c3ec12439d5e1200..b9eb25c3b1b556d27accdce27c7ca40bcc933771 100644
--- a/testsuite/Makefile.am
+++ b/testsuite/Makefile.am
@@ -5,7 +5,7 @@ TS_PROGS = aes-test arcfour-test blowfish-test cast128-test \
 	   des-test des3-test des-compat-test \
 	   md5-test md5-compat-test sha1-test sha256-test \
 	   serpent-test twofish-test \
-	   cbc-test bignum-test yarrow-test
+	   cbc-test rsa-test bignum-test yarrow-test
 
 # M4_FILES = aes-test.m4 arcfour-test.m4 blowfish-test.m4 cast128-test.m4 \
 # 	   des-test.m4 des3-test.m4 \
diff --git a/testsuite/aes-test.c b/testsuite/aes-test.c
index 42b3cda171d94d45f5505b5af28e4aae51d6ee33..1da4d5188d8c5cad6d7aa2feff38a26a40389fe2 100644
--- a/testsuite/aes-test.c
+++ b/testsuite/aes-test.c
@@ -2,7 +2,7 @@
 #include "aes.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* 128 bit keys */
   test_cipher(&nettle_aes128, 
diff --git a/testsuite/arcfour-test.c b/testsuite/arcfour-test.c
index 47886dfb870d5bd534bd522d94511f53a9f91cbf..5b1021a813e59c993c6fdf119975b8aa2a6a54ec 100644
--- a/testsuite/arcfour-test.c
+++ b/testsuite/arcfour-test.c
@@ -2,7 +2,7 @@
 #include "arcfour.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   test_cipher(&nettle_arcfour128,
 	      HL("01234567 89ABCDEF 00000000 00000000"),
diff --git a/testsuite/bignum-test.c b/testsuite/bignum-test.c
index 905eef0e4c5bfe865dd06dce7e9e4e8787b81e18..bfdcddb0c338f8ddd52ea59b3fe7c9784b8b8631 100644
--- a/testsuite/bignum-test.c
+++ b/testsuite/bignum-test.c
@@ -4,12 +4,12 @@
 #include "config.h"
 #endif
 
-#if HAVE_LIBGMP
-#include "bignum.h"
-
 #include <stdlib.h>
 #include <string.h>
 
+#if HAVE_LIBGMP
+#include "bignum.h"
+
 static void
 test_bignum(const char *hex, unsigned length, const uint8_t *base256)
 {
@@ -38,7 +38,7 @@ test_bignum(const char *hex, unsigned length, const uint8_t *base256)
 #endif /* HAVE_LIBGMP */
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
 #if HAVE_LIBGMP
   test_bignum("0", 0, "");
diff --git a/testsuite/blowfish-test.c b/testsuite/blowfish-test.c
index 9d160bd61edcbcf4f7eac7fc6dea82b79dd65e99..c4311bb7f960af524784a8a410ccbb6f336aaa1d 100644
--- a/testsuite/blowfish-test.c
+++ b/testsuite/blowfish-test.c
@@ -3,7 +3,7 @@
 #include "blowfish.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* 208 bit key. Test from GNUPG. */
   test_cipher(&nettle_blowfish128,
diff --git a/testsuite/cast128-test.c b/testsuite/cast128-test.c
index 611733ecc8043d7d75fc3695139691ca881fde3c..e4b7830e23a67c1dca6a12a1e9221f4822452368 100644
--- a/testsuite/cast128-test.c
+++ b/testsuite/cast128-test.c
@@ -2,7 +2,7 @@
 #include "cast128.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* Test vectors from B.1. Single Plaintext-Key-Ciphertext Sets, RFC
    * 2144 */
diff --git a/testsuite/cbc-test.c b/testsuite/cbc-test.c
index 6e1a9463358fa0604279d841d22324b85af60e78..4645ee8301c61e77516aa43932949ab4edefa047 100644
--- a/testsuite/cbc-test.c
+++ b/testsuite/cbc-test.c
@@ -3,7 +3,7 @@
 #include "cbc.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   uint8_t msg[2 * AES_BLOCK_SIZE] = "Listen, I'll say this only once!";
 
diff --git a/testsuite/des-compat-test.c b/testsuite/des-compat-test.c
index 9a950e0f6d7d846c3160834c9199e96ada081f31..b77a3e3a07d3fe2da633c05985b22652e07886c6 100644
--- a/testsuite/des-compat-test.c
+++ b/testsuite/des-compat-test.c
@@ -62,6 +62,7 @@
 #include <string.h>
 
 #include "des-compat.h"
+#include "testutils.h"
 
 #define C_Block des_cblock
 #define Key_schedule des_key_schedule
@@ -300,7 +301,8 @@ static int cfb64_test();
 static int ede_cfb64_test();
 #endif
 
-int main(int argc, char **argv)
+int
+test_main(void)
 	{
 	int i,j,err=0;
 	des_cblock in,out,outin,iv3;
diff --git a/testsuite/des-test.c b/testsuite/des-test.c
index 1ca8dd9ed99b50e6f5b7d618f3dbc43fb20c8144..fd47fbac15c27e61a5ebae21ac7a760b52b849e6 100644
--- a/testsuite/des-test.c
+++ b/testsuite/des-test.c
@@ -3,7 +3,7 @@
 #include "des.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   struct des_ctx ctx;
   
diff --git a/testsuite/des3-test.c b/testsuite/des3-test.c
index b3a4429199961a698783ade2aa645b7dc612b06f..678a235e4d28a2511493a08a145ec7c966f9a6da 100644
--- a/testsuite/des3-test.c
+++ b/testsuite/des3-test.c
@@ -3,7 +3,7 @@
 #include "des.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* Intermediate values:
    *   After first DES encryption:  "cd ea 2a 20 c2 e0 9e 48"
diff --git a/testsuite/md5-compat-test.c b/testsuite/md5-compat-test.c
index 4304ea853e5b62b4eb562fbf5ed7ed42b42edb31..bffb6232e56d2730a0a77edf09668b16920072f9 100644
--- a/testsuite/md5-compat-test.c
+++ b/testsuite/md5-compat-test.c
@@ -2,7 +2,7 @@
 #include "md5-compat.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   MD5_CTX ctx;
   unsigned char digest[MD5_DIGEST_SIZE];
diff --git a/testsuite/md5-test.c b/testsuite/md5-test.c
index a65958ab5dfd29b9e6bccd0fa0f287a1652fd5a9..fece067fb08f724c4fc25fbb2db2d08d9f4b3412 100644
--- a/testsuite/md5-test.c
+++ b/testsuite/md5-test.c
@@ -2,7 +2,7 @@
 #include "md5.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   test_hash(&nettle_md5, 0, "",
 	    H("D41D8CD98F00B204 E9800998ECF8427E"));
diff --git a/testsuite/serpent-test.c b/testsuite/serpent-test.c
index 345417e4fa29e9f71551c4ba43dd5d39a15c5bd7..b1101ea3edd26f6802f0c0733cf412a58dbfe3f6 100644
--- a/testsuite/serpent-test.c
+++ b/testsuite/serpent-test.c
@@ -2,7 +2,7 @@
 #include "serpent.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* The first test for each key size from the ecb_vk.txt and ecb_vt.txt
    * files in the serpent package. */
diff --git a/testsuite/sha1-test.c b/testsuite/sha1-test.c
index 5f602c97f491091eb0b762a113403935008e3a24..cd65ecab0765918df088f86a4b8d1fbca7409309 100644
--- a/testsuite/sha1-test.c
+++ b/testsuite/sha1-test.c
@@ -2,7 +2,7 @@
 #include "sha.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   test_hash(&nettle_sha1, 0, "",
 	    H("DA39A3EE5E6B4B0D 3255BFEF95601890 AFD80709")); 
diff --git a/testsuite/sha256-test.c b/testsuite/sha256-test.c
index 89a0a23497ea423156c2a5a4e0e67cb0ca8592f2..7799535130579f7347884070b7c97120cba8fe28 100644
--- a/testsuite/sha256-test.c
+++ b/testsuite/sha256-test.c
@@ -2,7 +2,7 @@
 #include "sha.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   test_hash(&nettle_sha256, 3, "abc",
 	    H("ba7816bf8f01cfea 414140de5dae2223"
diff --git a/testsuite/testutils.c b/testsuite/testutils.c
index 152b4f35cdaf4b1775b6d43c6a72f5dac034cec1..41ae577137242f14e64520b5b41ccdc5f199b9c6 100644
--- a/testsuite/testutils.c
+++ b/testsuite/testutils.c
@@ -5,9 +5,13 @@
 #include "cbc.h"
 
 #include <ctype.h>
+#include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 
+/* For getopt() */
+#include <unistd.h>
+
 /* -1 means invalid */
 const signed char hex_digits[0x100] =
   {
@@ -103,6 +107,33 @@ decode_hex_dup(const char *hex)
     }
 }
 
+int verbose = 0;
+
+int
+main(int argc, char **argv)
+{
+  int c;
+
+  while ((c = getopt (argc, argv, "v")) != -1)
+    switch (c)
+      {
+      case 'v':
+	verbose = 1;
+	break;
+      case '?':
+	if (isprint (optopt))
+	  fprintf (stderr, "Unknown option `-%c'.\n", optopt);
+	else
+	  fprintf (stderr,
+		   "Unknown option character `\\x%x'.\n",
+		   optopt);
+      default:
+	abort();
+      }
+
+  return test_main();
+}
+
 void
 test_cipher(const struct nettle_cipher *cipher,
 	    unsigned key_length,
diff --git a/testsuite/testutils.h b/testsuite/testutils.h
index efdb6d66de8a989dc9e14cefcd9b4a62611b6057..ff51d21531db19cf6cc3e08c687ad33d0b36c7dd 100644
--- a/testsuite/testutils.h
+++ b/testsuite/testutils.h
@@ -20,6 +20,12 @@ decode_hex(uint8_t *dst, const char *hex);
 const uint8_t *
 decode_hex_dup(const char *hex);
 
+/* The main program */
+int
+test_main(void);
+
+extern int verbose;
+
 void
 test_cipher(const struct nettle_cipher *cipher,
 	    unsigned key_length,
@@ -42,7 +48,7 @@ test_hash(const struct nettle_hash *hash,
 	  unsigned length,
 	  const uint8_t *data,
 	  const uint8_t *digest);
-	  
+
 #define H2(d, s) decode_hex((d), (s))
 #define H(x) decode_hex_dup(x)
 #define HL(x) decode_hex_length(x), decode_hex_dup(x)
diff --git a/testsuite/twofish-test.c b/testsuite/twofish-test.c
index 935c05230b6599ad40f7f98ad34e0c3ab286d931..65558d37abc0f1e961936df9399c48db89832ae7 100644
--- a/testsuite/twofish-test.c
+++ b/testsuite/twofish-test.c
@@ -2,7 +2,7 @@
 #include "twofish.h"
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   /* 128 bit key */
   test_cipher(&nettle_twofish128,
diff --git a/testsuite/yarrow-test.c b/testsuite/yarrow-test.c
index 938e51c40df2249bf0b21050e8156c7f6c6d1fde..955fe2ef2169c522382466dae4d9d90c709d2399 100644
--- a/testsuite/yarrow-test.c
+++ b/testsuite/yarrow-test.c
@@ -9,8 +9,6 @@
 #include <stdlib.h>
 #include <string.h>
 
-static int verbose = 0;
-
 /* Lagged fibonacci sequence as described in Knuth 3.6 */
 
 #define KK 100
@@ -166,7 +164,7 @@ open_file(const char *name)
 }
 
 int
-main(int argc, char **argv)
+test_main(void)
 {
   FILE *input;
   
@@ -200,11 +198,6 @@ main(int argc, char **argv)
   
   static const char zeroes[100];
 
-  if ((argc == 2)
-      && (argv[1][0] == '-')
-      && (argv[1][1] == 'v'))
-    verbose = 1;
-  
   yarrow256_init(&yarrow, 2, sources);
   memset(&yarrow.seed_file, 0, sizeof(yarrow.seed_file));