summaryrefslogtreecommitdiff
path: root/hash.h
blob: 585ef4e318c6963c2d071602636c272bad9e02d7 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
/*
 * Copyright (C) 2007-2009 Andre Noll <maan@tuebingen.mpg.de>
 *
 * Licensed under the GPL v2. For licencing details see COPYING.
 */

/** \file hash.h Inline functions for hash values. */

#include "portable_io.h"

/** hash arrays are always unsigned char. */
#define HASH_TYPE unsigned char

/** Size of the hash value in bytes. */
#define HASH_SIZE 20

void sha1_hash(const char *data, unsigned long len, unsigned char *result);
void sha3_hash(const char *data, unsigned long len, unsigned char *result);
void sha256_hash(const char *data, unsigned long len, unsigned char *result);

static inline void hash_function(uint8_t table_version, const char *data,
		unsigned long len, unsigned char *result)
{
	switch (table_version) {
	case 1: return sha1_hash(data, len, result);
	case 2: return sha3_hash(data, len, result);
	case 3: return sha256_hash(data, len, result);
	}
	assert(0);
}

/**
 * Compare two hashes.
 *
 * \param h1 Pointer to the first hash value.
 * \param h2 Pointer to the second hash value.
 *
 * \return 1, -1, or zero, depending on whether \a h1 is greater than,
 * less than or equal to h2, respectively.
 */
_static_inline_ int hash_compare(HASH_TYPE *h1, HASH_TYPE *h2)
{
	int i;

	for (i = 0; i < HASH_SIZE; i++) {
		if (h1[i] < h2[i])
			return -1;
		if (h1[i] > h2[i])
			return 1;
	}
	return 0;
}

/**
 * Convert a hash value to ascii format.
 *
 * \param hash the hash value.
 * \param asc Result pointer.
 *
 * \a asc must point to an area of at least 2 * \p HASH_SIZE + 1 bytes which
 * will be filled by the function with the ascii representation of the hash
 * value given by \a hash, and a terminating \p NULL byte.
 */
_static_inline_ void hash_to_asc(HASH_TYPE *hash, char *asc)
{
	int i;
	const char hexchar[] = "0123456789abcdef";

	for (i = 0; i < HASH_SIZE; i++) {
		asc[2 * i] = hexchar[hash[i] >> 4];
		asc[2 * i + 1] = hexchar[hash[i] & 0xf];
	}
	asc[2 * HASH_SIZE] = '\0';
}