/** Verify a signature 
   @param hashname	[in] String naming the hash
   @param keydatalen	[in] The length of the public key
   @param keydata	[in] The public key of the signer
   @param sigdatalen	[in] The length of the signature data
   @param sigdata	[in] The signature data
   @param filedatalen	[in] The length of the file in octets
   @param filedata	[in] The contents of the file being verified
   @param ...           [in] Additional len,data pairs until len is 0
   @return nonzero on error [or invalid], 0 on success
   If 
*/
int verify_data(
   char  *hashname,
         unsigned long  keydatalen,
         unsigned char *keydata,
         unsigned long  sigdatalen,
         unsigned char *sigdata,
         unsigned long  filedatalen,
   const unsigned char *filedata, ...)
{
   rsa_key rsakey;
   unsigned char rsabuf[2048], md[MAXBLOCKSIZE];
   unsigned long rsalen, mdlen;
   int           stat;
   int           res;
   va_list args;
   const unsigned char *dataptr;
   unsigned long datalen;
   hash_state hs;
   struct ltc_hash_descriptor *hd;
   int hashid;

   heap_start(heap_mem, HEAP_SIZE);

   if (strcmp(hashname,"des") == 0) {
       symmetric_key skey;
       DO(des_setup(keydata, keydatalen, 0, &skey),0x400000);
       DO(des_ecb_encrypt(filedata, sigdata, &skey),0x500000);
       return res;
   }

   register_hash(&sha256_desc);
//   register_hash(&sha512_desc);
//   register_hash(&whirlpool_desc);
   register_hash(&rmd160_desc);
   register_hash(&md4_desc);
   register_hash(&ltc_md5_desc);
   register_hash(&sha1_desc);
   ltc_mp = tfm_desc;

   hashid = find_hash(hashname);
   if ((res = hash_is_valid(hashid)) != CRYPT_OK)
      return res;

   hd = &hash_descriptor[hashid];
   if ((res = hd->init(&hs)) != CRYPT_OK)
      return res;

   va_start(args, filedata);
   dataptr = filedata;
   datalen = filedatalen;

   for(;;) {
      if((res = hd->process(&hs, dataptr, datalen)) != 0)
         return res;
      if((datalen = va_arg(args, unsigned long)) == 0)
         break;
      if((dataptr = va_arg(args, unsigned char *)) == NULL)
         break;
   }
   va_end(args);

   if (keydatalen == 0) {
       res = hd->done(&hs, sigdata);
       *keydata = hd->hashsize;
       return res+0x100000;
   }

   if((res = hd->done(&hs, md)) != 0)
      return res+0x200000;

   mdlen = hd->hashsize;

   DO(rsa_import(keydata, keydatalen, &rsakey),0x300000);
   DO(rsa_verify_hash(sigdata, sigdatalen, md, mdlen, find_hash(hashname), 8, &stat, &rsakey),0x400000);
   rsa_free(&rsakey);
   return (stat == 0) ? -1 : 0;
}
示例#2
0
static void sign_file(const char *fname, rsa_key *key, prng_state *prng, const int prng_index, const int hash_index)
{
    const size_t sigfnamelen = strlen(fname) + 5;
    char *sigfname = (char *) malloc(sigfnamelen);
    unsigned char hash[256];
    unsigned long hashlen = sizeof (hash);
    unsigned char sig[1024];
    unsigned long siglen = sizeof (sig);
    int rc = 0;
    int status = 0;

    if (!sigfname) {
        fail("out of memory");
    }

    if ((rc = hash_file(hash_index, fname, hash, &hashlen)) != CRYPT_OK) {
        fail("hash_file for '%s' failed: %s", fname, error_to_string(rc));
    }

    if ((rc = rsa_sign_hash(hash, hashlen, sig, &siglen, prng, prng_index, hash_index, SALT_LEN, key)) != CRYPT_OK) {
        fail("rsa_sign_hash for '%s' failed: %s", fname, error_to_string(rc));
    }

    if ((rc = rsa_verify_hash(sig, siglen, hash, hashlen, hash_index, SALT_LEN, &status, key)) != CRYPT_OK) {
        fail("rsa_verify_hash for '%s' failed: %s", fname, error_to_string(rc));
    }

    if (!status) {
        fail("Generated signature isn't valid! Bug in the program!");
    }

    snprintf(sigfname, sigfnamelen, "%s.sig", fname);
    write_file(sigfname, sig, siglen);
    free(sigfname);
}
示例#3
0
int pkcs_1_pss_test(void)
{
  struct ltc_prng_descriptor* no_prng_desc = no_prng_desc_get();
  int prng_idx = register_prng(no_prng_desc);
  int hash_idx = find_hash("sha1");
  unsigned int i;
  unsigned int j;

  DO(prng_is_valid(prng_idx));
  DO(hash_is_valid(hash_idx));

  for (i = 0; i < sizeof(testcases_pss)/sizeof(testcases_pss[0]); ++i) {
    testcase_t* t = &testcases_pss[i];
    rsa_key k, *key = &k;
    DOX(mp_init_multi(&key->e, &key->d, &key->N, &key->dQ,
                       &key->dP, &key->qP, &key->p, &key->q, NULL), t->name);

    DOX(mp_read_unsigned_bin(key->e, t->rsa.e, t->rsa.e_l), t->name);
    DOX(mp_read_unsigned_bin(key->d, t->rsa.d, t->rsa.d_l), t->name);
    DOX(mp_read_unsigned_bin(key->N, t->rsa.n, t->rsa.n_l), t->name);
    DOX(mp_read_unsigned_bin(key->dQ, t->rsa.dQ, t->rsa.dQ_l), t->name);
    DOX(mp_read_unsigned_bin(key->dP, t->rsa.dP, t->rsa.dP_l), t->name);
    DOX(mp_read_unsigned_bin(key->qP, t->rsa.qInv, t->rsa.qInv_l), t->name);
    DOX(mp_read_unsigned_bin(key->q, t->rsa.q, t->rsa.q_l), t->name);
    DOX(mp_read_unsigned_bin(key->p, t->rsa.p, t->rsa.p_l), t->name);
    key->type = PK_PRIVATE;

    for (j = 0; j < sizeof(t->data)/sizeof(t->data[0]); ++j) {
        rsaData_t* s = &t->data[j];
        unsigned char buf[20], obuf[256];
        unsigned long buflen = sizeof(buf), obuflen = sizeof(obuf);
        int stat;
        prng_descriptor[prng_idx].add_entropy(s->o2, s->o2_l, (prng_state*)no_prng_desc);
        DOX(hash_memory(hash_idx, s->o1, s->o1_l, buf, &buflen), s->name);
        DOX(rsa_sign_hash(buf, buflen, obuf, &obuflen, (prng_state*)no_prng_desc, prng_idx, hash_idx, s->o2_l, key), s->name);
        DOX(obuflen == (unsigned long)s->o3_l?CRYPT_OK:CRYPT_FAIL_TESTVECTOR, s->name);
        DOX(memcmp(s->o3, obuf, s->o3_l)==0?CRYPT_OK:CRYPT_FAIL_TESTVECTOR, s->name);
        DOX(rsa_verify_hash(obuf, obuflen, buf, buflen, hash_idx, s->o2_l, &stat, key), s->name);
        DOX(stat == 1?CRYPT_OK:CRYPT_FAIL_TESTVECTOR, s->name);
    } /* for */

    mp_clear_multi(key->d,  key->e, key->N, key->dQ, key->dP, key->qP, key->p, key->q, NULL);
  } /* for */

  unregister_prng(no_prng_desc);
  no_prng_desc_free(no_prng_desc);

  return 0;
}
示例#4
0
int main() {
	ltc_mp = ltm_desc;
	rsa_key priv_key, pub_key;
	int hash_idx, prng_idx;
	int ret = rsa_import(openssl_private_rsa, sizeof(openssl_private_rsa), &priv_key);
	ret = rsa_import(openssl_public_rsa, sizeof(openssl_public_rsa), &pub_key);

	if (register_hash(&sha1_desc) == -1) {
		printf("Error registering SHA1\n");
		return -1;
	}

	hash_idx = find_hash("sha1");
	register_prng(&sprng_desc);
	prng_idx = find_prng("sprng");
	prng_state prng;
	int err;
	if ((err = yarrow_start(&prng)) != CRYPT_OK) {
		printf("Start error: %s\n", error_to_string(err));
	}
	/* add entropy */
	if ((err = yarrow_add_entropy("hello world", 11, &prng))
	!= CRYPT_OK) {
		printf("Add_entropy error: %s\n", error_to_string(err));
	}
	int stat;
	unsigned char buf[1024];
	long size = 1024;
	//ret =  rsa_decrypt_key(sig, strlen(sig), buf, &size, 0, 0, hash_idx, &stat, &key);

	ret =  rsa_sign_hash(hash, strlen(hash), buf, &size, &prng, prng_idx, hash_idx, 0, &priv_key);
	ret = rsa_verify_hash(sig, strlen(sig), hash, strlen(hash), hash_idx, 0, &stat, &pub_key);
	printf("status is : %d\n", ret);
	//load stuff!
	return 0;
}
示例#5
0
bool
xbps_verify_file_signature(struct xbps_repo *repo, const char *fname)
{
	xbps_dictionary_t repokeyd = NULL;
	xbps_data_t pubkey;
	char *hexfp = NULL;
	unsigned char *digest = NULL, *sig_buf = NULL;
	size_t sigbuflen, sigfilelen;
	char *rkeyfile = NULL, *sig = NULL;
	bool val = false;

	if (!xbps_dictionary_count(repo->idxmeta)) {
		xbps_dbg_printf(repo->xhp, "%s: unsigned repository\n", repo->uri);
		return false;
	}
	hexfp = xbps_pubkey2fp(repo->xhp,
	    xbps_dictionary_get(repo->idxmeta, "public-key"));
	if (hexfp == NULL) {
		xbps_dbg_printf(repo->xhp, "%s: incomplete signed repo, missing hexfp obj\n", repo->uri);
		return false;
	}
	/*
	 * Prepare repository RSA public key to verify fname signature.
	 */
	rkeyfile = xbps_xasprintf("%s/keys/%s.plist", repo->xhp->metadir, hexfp);
	repokeyd = xbps_plist_dictionary_from_file(repo->xhp, rkeyfile);
	if (xbps_object_type(repokeyd) != XBPS_TYPE_DICTIONARY) {
		xbps_dbg_printf(repo->xhp, "cannot read rkey data at %s: %s\n",
		    rkeyfile, strerror(errno));
		goto out;
	}

	pubkey = xbps_dictionary_get(repokeyd, "public-key");
	if (xbps_object_type(pubkey) != XBPS_TYPE_DATA)
		goto out;

	/*
	 * Prepare fname and signature data buffers.
	 */
	if (!(digest = xbps_file_hash_raw(fname))) {
		xbps_dbg_printf(repo->xhp, "can't open file %s: %s\n", fname, strerror(errno));
		goto out;
	}
	sig = xbps_xasprintf("%s.sig", fname);
	if (!xbps_mmap_file(sig, (void *)&sig_buf, &sigbuflen, &sigfilelen)) {
		xbps_dbg_printf(repo->xhp, "can't open signature file %s: %s\n", sig, strerror(errno));
		goto out;
	}
	/*
	 * Verify fname RSA signature.
	 */
	if (rsa_verify_hash(repo, pubkey, sig_buf, sigfilelen, digest))
		val = true;

out:
	if (hexfp)
		free(hexfp);
	if (rkeyfile)
		free(rkeyfile);
	if (digest)
		free(digest);
	if (sig_buf)
		(void)munmap(sig_buf, sigbuflen);
	if (sig)
		free(sig);
	if (repokeyd)
		xbps_object_release(repokeyd);

	return val;
}
示例#6
0
int rsa_test(void)
{
   unsigned char in[1024], out[1024], tmp[1024];
   rsa_key       key, privKey, pubKey;
   int           hash_idx, prng_idx, stat, stat2;
   unsigned long rsa_msgsize, len, len2, cnt;
   static unsigned char lparam[] = { 0x01, 0x02, 0x03, 0x04 };

   if (rsa_compat_test() != 0) {
      return 1;
   }
      
   hash_idx = find_hash("sha1");
   prng_idx = find_prng("yarrow");
   if (hash_idx == -1 || prng_idx == -1) {
      fprintf(stderr, "rsa_test requires LTC_SHA1 and yarrow");
      return 1;
   }
   
   /* make 10 random key */
   for (cnt = 0; cnt < 10; cnt++) {
      DO(rsa_make_key(&yarrow_prng, prng_idx, 1024/8, 65537, &key));
      if (mp_count_bits(key.N) != 1024) {
         fprintf(stderr, "rsa_1024 key modulus has %d bits\n", mp_count_bits(key.N));

len = mp_unsigned_bin_size(key.N);
mp_to_unsigned_bin(key.N, tmp);
 fprintf(stderr, "N == \n");
for (cnt = 0; cnt < len; ) {
   fprintf(stderr, "%02x ", tmp[cnt]);
   if (!(++cnt & 15)) fprintf(stderr, "\n");
}

len = mp_unsigned_bin_size(key.p);
mp_to_unsigned_bin(key.p, tmp);
 fprintf(stderr, "p == \n");
for (cnt = 0; cnt < len; ) {
   fprintf(stderr, "%02x ", tmp[cnt]);
   if (!(++cnt & 15)) fprintf(stderr, "\n");
}

len = mp_unsigned_bin_size(key.q);
mp_to_unsigned_bin(key.q, tmp);
 fprintf(stderr, "\nq == \n");
for (cnt = 0; cnt < len; ) {
   fprintf(stderr, "%02x ", tmp[cnt]);
   if (!(++cnt & 15)) fprintf(stderr, "\n");
}
 fprintf(stderr, "\n");


         return 1;
      }
      if (cnt != 9) {
         rsa_free(&key);
      }
   }
    
   /* encrypt the key (without lparam) */
   for (cnt = 0; cnt < 4; cnt++) {
   for (rsa_msgsize = 1; rsa_msgsize <= 86; rsa_msgsize++) {
      /* make a random key/msg */
      yarrow_read(in, rsa_msgsize, &yarrow_prng);

      len  = sizeof(out);
      len2 = rsa_msgsize;
   
      DO(rsa_encrypt_key(in, rsa_msgsize, out, &len, NULL, 0, &yarrow_prng, prng_idx, hash_idx, &key));
      /* change a byte */
      out[8] ^= 1;
      DO(rsa_decrypt_key(out, len, tmp, &len2, NULL, 0, hash_idx, &stat2, &key));
      /* change a byte back */
      out[8] ^= 1;
      if (len2 != rsa_msgsize) {
         fprintf(stderr, "\nrsa_decrypt_key mismatch len %lu (first decrypt)", len2);
         return 1;
      }

      len2 = rsa_msgsize;
      DO(rsa_decrypt_key(out, len, tmp, &len2, NULL, 0, hash_idx, &stat, &key));
      if (!(stat == 1 && stat2 == 0)) {
         fprintf(stderr, "rsa_decrypt_key failed");
         return 1;
      }
      if (len2 != rsa_msgsize || memcmp(tmp, in, rsa_msgsize)) {
         unsigned long x;
         fprintf(stderr, "\nrsa_decrypt_key mismatch, len %lu (second decrypt)\n", len2);
         fprintf(stderr, "Original contents: \n"); 
         for (x = 0; x < rsa_msgsize; ) {
             fprintf(stderr, "%02x ", in[x]);
             if (!(++x % 16)) {
                fprintf(stderr, "\n");
             }
         }
         fprintf(stderr, "\n");
         fprintf(stderr, "Output contents: \n"); 
         for (x = 0; x < rsa_msgsize; ) {
             fprintf(stderr, "%02x ", out[x]);
             if (!(++x % 16)) {
                fprintf(stderr, "\n");
             }
         }     
         fprintf(stderr, "\n");
         return 1;
      }
   }
   }

   /* encrypt the key (with lparam) */
   for (rsa_msgsize = 1; rsa_msgsize <= 86; rsa_msgsize++) {
      len  = sizeof(out);
      len2 = rsa_msgsize;
      DO(rsa_encrypt_key(in, rsa_msgsize, out, &len, lparam, sizeof(lparam), &yarrow_prng, prng_idx, hash_idx, &key));
      /* change a byte */
      out[8] ^= 1;
      DO(rsa_decrypt_key(out, len, tmp, &len2, lparam, sizeof(lparam), hash_idx, &stat2, &key));
      if (len2 != rsa_msgsize) {
         fprintf(stderr, "\nrsa_decrypt_key mismatch len %lu (first decrypt)", len2);
         return 1;
      }
      /* change a byte back */
      out[8] ^= 1;

      len2 = rsa_msgsize;
      DO(rsa_decrypt_key(out, len, tmp, &len2, lparam, sizeof(lparam), hash_idx, &stat, &key));
      if (!(stat == 1 && stat2 == 0)) {
         fprintf(stderr, "rsa_decrypt_key failed");
         return 1;
      }
      if (len2 != rsa_msgsize || memcmp(tmp, in, rsa_msgsize)) {
         fprintf(stderr, "rsa_decrypt_key mismatch len %lu", len2);
         return 1;
      }
   }

   /* encrypt the key LTC_PKCS #1 v1.5 (payload from 1 to 117 bytes) */
   for (rsa_msgsize = 1; rsa_msgsize <= 117; rsa_msgsize++) {
      len  = sizeof(out);
      len2 = rsa_msgsize;
      DO(rsa_encrypt_key_ex(in, rsa_msgsize, out, &len, NULL, 0, &yarrow_prng, prng_idx, 0, LTC_PKCS_1_V1_5, &key));

      len2 = rsa_msgsize;
      DO(rsa_decrypt_key_ex(out, len, tmp, &len2, NULL, 0, 0, LTC_PKCS_1_V1_5, &stat, &key));
      if (!(stat == 1 && stat2 == 0)) {
         fprintf(stderr, "rsa_decrypt_key_ex failed, %d, %d", stat, stat2);
         return 1;
      }
      if (len2 != rsa_msgsize || memcmp(tmp, in, rsa_msgsize)) {
         fprintf(stderr, "rsa_decrypt_key_ex mismatch len %lu", len2);
         return 1;
      }
   }

   /* sign a message (unsalted, lower cholestorol and Atkins approved) now */
   len = sizeof(out);
   DO(rsa_sign_hash(in, 20, out, &len, &yarrow_prng, prng_idx, hash_idx, 0, &key));

/* export key and import as both private and public */
   len2 = sizeof(tmp);
   DO(rsa_export(tmp, &len2, PK_PRIVATE, &key)); 
   DO(rsa_import(tmp, len2, &privKey)); 
   len2 = sizeof(tmp);
   DO(rsa_export(tmp, &len2, PK_PUBLIC, &key));
   DO(rsa_import(tmp, len2, &pubKey));

   /* verify with original */
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat, &key));
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat2, &key));
   
   if (!(stat == 1 && stat2 == 0)) {
      fprintf(stderr, "rsa_verify_hash (unsalted, origKey) failed, %d, %d", stat, stat2);
      rsa_free(&key);
      rsa_free(&pubKey);
      rsa_free(&privKey);
      return 1;
   }

   /* verify with privKey */
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat, &privKey));
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat2, &privKey));
   
   if (!(stat == 1 && stat2 == 0)) {
      fprintf(stderr, "rsa_verify_hash (unsalted, privKey) failed, %d, %d", stat, stat2);
      rsa_free(&key);
      rsa_free(&pubKey);
      rsa_free(&privKey);
      return 1;
   }

   /* verify with pubKey */
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat, &pubKey));
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 0, &stat2, &pubKey));
   
   if (!(stat == 1 && stat2 == 0)) {
      fprintf(stderr, "rsa_verify_hash (unsalted, pubkey) failed, %d, %d", stat, stat2);
      rsa_free(&key);
      rsa_free(&pubKey);
      rsa_free(&privKey);
      return 1;
   }

   /* sign a message (salted) now (use privKey to make, pubKey to verify) */
   len = sizeof(out);
   DO(rsa_sign_hash(in, 20, out, &len, &yarrow_prng, prng_idx, hash_idx, 8, &privKey));
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 8, &stat, &pubKey));
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash(out, len, in, 20, hash_idx, 8, &stat2, &pubKey));
   
   if (!(stat == 1 && stat2 == 0)) {
      fprintf(stderr, "rsa_verify_hash (salted) failed, %d, %d", stat, stat2);
      rsa_free(&key);
      rsa_free(&pubKey);
      rsa_free(&privKey);
      return 1;
   }
   
   /* sign a message with LTC_PKCS #1 v1.5 */
   len = sizeof(out);
   DO(rsa_sign_hash_ex(in, 20, out, &len, LTC_PKCS_1_V1_5, &yarrow_prng, prng_idx, hash_idx, 8, &privKey));
   DO(rsa_verify_hash_ex(out, len, in, 20, LTC_PKCS_1_V1_5, hash_idx, 8, &stat, &pubKey));
   /* change a byte */
   in[0] ^= 1;
   DO(rsa_verify_hash_ex(out, len, in, 20, LTC_PKCS_1_V1_5, hash_idx, 8, &stat2, &pubKey));
   
   if (!(stat == 1 && stat2 == 0)) {
      fprintf(stderr, "rsa_verify_hash_ex failed, %d, %d", stat, stat2);
      rsa_free(&key);
      rsa_free(&pubKey);
      rsa_free(&privKey);
      return 1;
   }

   /* free the key and return */
   rsa_free(&key);
   rsa_free(&pubKey);
   rsa_free(&privKey);
   return 0;
}