Пример #1
0
int KSI_DataHash_createZero(KSI_CTX *ctx, KSI_HashAlgorithm algo_id, KSI_DataHash **hsh) {
	int res = KSI_UNKNOWN_ERROR;
	KSI_DataHash *tmp = NULL;
	unsigned char buf[KSI_MAX_IMPRINT_LEN];

	if (ctx == NULL || hsh == NULL) {
		res = KSI_INVALID_ARGUMENT;
		goto cleanup;
	}

	memset(buf, 0, sizeof(buf));
	buf[0] = algo_id;

	if (!KSI_isHashAlgorithmSupported(algo_id)) {
		KSI_pushError(ctx, res = KSI_UNAVAILABLE_HASH_ALGORITHM, "Hash algorithm not supported.");
		goto cleanup;
	}

	res = KSI_DataHash_fromImprint(ctx, buf, (KSI_hashAlgorithmInfo[algo_id].outputBitCount >> 3) + 1, &tmp);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	*hsh = tmp;
	tmp = NULL;

	res = KSI_OK;

cleanup:

	KSI_DataHash_free(tmp);

	return res;
}
Пример #2
0
int KSI_DataHash_fromDigest(KSI_CTX *ctx, KSI_HashAlgorithm algo_id, const unsigned char *digest, size_t digest_length, KSI_DataHash **hash) {
	int res = KSI_UNKNOWN_ERROR;
	KSI_DataHash *tmp_hash = NULL;

	KSI_ERR_clearErrors(ctx);
	if (ctx == NULL || digest == NULL || digest_length == 0 || hash == NULL) {
		KSI_pushError(ctx, res = KSI_INVALID_ARGUMENT, NULL);
		goto cleanup;
	}

	/* Make sure the algorithm is supported. */
	if (!KSI_isHashAlgorithmSupported(algo_id)) {
		KSI_pushError(ctx, res = KSI_UNAVAILABLE_HASH_ALGORITHM, "Hash algorithm not supported.");
		goto cleanup;
	}

	/* Verify the length of the digest with the algorithm. */
	if (KSI_getHashLength(algo_id) != digest_length) {
		KSI_pushError(ctx, res = KSI_INVALID_FORMAT, "Digest length does not match with algorithm.");
		goto cleanup;
	}

	/* Make sure it fits. */
	if (digest_length > KSI_MAX_IMPRINT_LEN) {
		KSI_pushError(ctx, res = KSI_CRYPTO_FAILURE, "Internal buffer too short to hold imprint");
		goto cleanup;
	}

	tmp_hash = KSI_new(KSI_DataHash);
	if (tmp_hash == NULL) {
		KSI_pushError(ctx, res = KSI_OUT_OF_MEMORY, NULL);
		goto cleanup;
	}

	tmp_hash->ref = 1;
	tmp_hash->ctx = ctx;

	tmp_hash->imprint[0] = (unsigned char)algo_id;
	memcpy(tmp_hash->imprint + 1, digest, digest_length);
	tmp_hash->imprint_length = digest_length + 1;

	*hash = tmp_hash;
	tmp_hash = NULL;

	res = KSI_OK;

cleanup:

	KSI_DataHash_free(tmp_hash);

	return res;
}
Пример #3
0
int KSI_PublicationData_fromBase32(KSI_CTX *ctx, const char *publication, KSI_PublicationData **published_data) {
	int res = KSI_UNKNOWN_ERROR;
	unsigned char *binary_publication = NULL;
	size_t binary_publication_length;
	KSI_PublicationData *tmp_published_data = NULL;
	unsigned i;
	unsigned long tmp_ulong;
	KSI_uint64_t tmp_uint64;
	KSI_HashAlgorithm algo_id;
	size_t hash_size;
	KSI_DataHash *pubHash = NULL;
	KSI_Integer *pubTime = NULL;

	KSI_ERR_clearErrors(ctx);

	if (ctx == NULL || publication == NULL || published_data == NULL) {
		KSI_pushError(ctx, res = KSI_INVALID_ARGUMENT, NULL);
		goto cleanup;
	}


	res = KSI_base32Decode(publication, &binary_publication, &binary_publication_length);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	if (binary_publication_length < 13) {
		res = KSI_INVALID_FORMAT;
		goto cleanup;
	}

	tmp_ulong = 0;
	for (i = 0; i < 4; ++i) {
		tmp_ulong <<= 8;
		tmp_ulong |= binary_publication[binary_publication_length - 4 + i];
	}

	if (KSI_crc32(binary_publication, binary_publication_length - 4, 0) !=
			tmp_ulong) {
		KSI_pushError(ctx, res = KSI_INVALID_FORMAT, "CRC mismatch.");
		goto cleanup;
	}

	res = KSI_PublicationData_new(ctx, &tmp_published_data);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	tmp_uint64 = 0;
	for (i = 0; i < 8; ++i) {
		tmp_uint64 <<= 8;
		tmp_uint64 |= binary_publication[i];
	}

	res = KSI_Integer_new(ctx, tmp_uint64, &pubTime);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	res = KSI_PublicationData_setTime(tmp_published_data, pubTime);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	pubTime = NULL;


	algo_id = binary_publication[8];
	if (!KSI_isHashAlgorithmSupported(algo_id)) {
		KSI_pushError(ctx, res = KSI_UNAVAILABLE_HASH_ALGORITHM, NULL);
		goto cleanup;
	}

	hash_size = KSI_getHashLength(algo_id);
	if (binary_publication_length != 8 + 1 + hash_size + 4) {
		KSI_pushError(ctx, res = KSI_INVALID_FORMAT, "Hash algorithm length mismatch.");
		goto cleanup;
	}

	res = KSI_DataHash_fromImprint(ctx, binary_publication + 8, hash_size + 1, &pubHash);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	res = KSI_PublicationData_setImprint(tmp_published_data, pubHash);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	pubHash = NULL;

	*published_data = tmp_published_data;
	tmp_published_data = NULL;

	res = KSI_OK;

cleanup:
	KSI_Integer_free(pubTime);
	KSI_DataHash_free(pubHash);
	KSI_free(binary_publication);
	KSI_PublicationData_free(tmp_published_data);

	return res;
}
Пример #4
0
int KSI_DataHasher_open(KSI_CTX *ctx, KSI_HashAlgorithm algo_id, KSI_DataHasher **hasher) {
	int res = KSI_UNKNOWN_ERROR;
	KSI_DataHasher *tmp_hasher = NULL;
	CRYPTO_HASH_CTX *tmp_cryptoCTX = NULL;
	HCRYPTPROV tmp_CSP = 0;

	KSI_ERR_clearErrors(ctx);
	if (ctx == NULL || hasher == NULL){
		res = KSI_INVALID_ARGUMENT;
		goto cleanup;
	}

	/*Test if hash algorithm is valid*/
	if (!KSI_isHashAlgorithmSupported(algo_id)) {
		KSI_pushError(ctx, res = KSI_UNAVAILABLE_HASH_ALGORITHM, NULL);
		goto cleanup;
	}

	/*Create new abstract data hasher object*/
	tmp_hasher = KSI_new(KSI_DataHasher);
	if (tmp_hasher == NULL) {
		KSI_pushError(ctx, res = KSI_OUT_OF_MEMORY, NULL);
		goto cleanup;
	}

	tmp_hasher->hashContext = NULL;
	tmp_hasher->ctx = ctx;
	tmp_hasher->algorithm = algo_id;
	tmp_hasher->closeExisting = closeExisting;

	/*Create new helper context for crypto api*/
	res = CRYPTO_HASH_CTX_new(&tmp_cryptoCTX);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	/*Create new crypto service provider (CSP)*/
	if (!CryptAcquireContext(&tmp_CSP, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)){
		char errm[1024];
		KSI_snprintf(errm, sizeof(errm), "Wincrypt Error (%d)", GetLastError());
		KSI_pushError(ctx, res = KSI_CRYPTO_FAILURE, errm);
		goto cleanup;
		}

	/*Set CSP in helper struct*/
	tmp_cryptoCTX->pt_CSP = tmp_CSP;
	/*Set helper struct in abstract struct*/
	tmp_hasher->hashContext = tmp_cryptoCTX;

	res = KSI_DataHasher_reset(tmp_hasher);
	if (res != KSI_OK) {
		KSI_pushError(ctx, res, NULL);
		goto cleanup;
	}

	*hasher = tmp_hasher;
	tmp_hasher = NULL;
	tmp_cryptoCTX = NULL;
	tmp_CSP = 0;

	res = KSI_OK;

cleanup:

	KSI_DataHasher_free(tmp_hasher);
	if (tmp_CSP) CryptReleaseContext(tmp_CSP, 0);
	CRYPTO_HASH_CTX_free(tmp_cryptoCTX);

	return res;
}