aboutsummaryrefslogtreecommitdiff
path: root/fontconfig/src/fchash.c
diff options
context:
space:
mode:
Diffstat (limited to 'fontconfig/src/fchash.c')
-rw-r--r--fontconfig/src/fchash.c234
1 files changed, 53 insertions, 181 deletions
diff --git a/fontconfig/src/fchash.c b/fontconfig/src/fchash.c
index 38300028c..1526cfd2b 100644
--- a/fontconfig/src/fchash.c
+++ b/fontconfig/src/fchash.c
@@ -3,7 +3,9 @@
*
* Copyright © 2003 Keith Packard
* Copyright © 2013 Red Hat, Inc.
+ * Copyright © 2014 Google, Inc.
* Red Hat Author(s): Akira TAGOH
+ * Google Author(s): Behdad Esfahbod
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
@@ -27,6 +29,9 @@
#include <stdio.h>
#include <string.h>
+/* SHA256 */
+
+
#define ROTRN(w, v, n) ((((FcChar32)v) >> n) | (((FcChar32)v) << (w - n)))
#define ROTR32(v, n) ROTRN(32, v, n)
#define SHR(v, n) (v >> n)
@@ -38,28 +43,21 @@
#define ss1(x) (ROTR32(x, 17) ^ ROTR32(x, 19) ^ SHR(x, 10))
-static FcChar32 *
-FcHashInitSHA256Digest (void)
+
+void
+FcHashInitDigest (FcHashDigest digest)
{
- int i;
- static const FcChar32 h[] = {
+ static const FcHashDigest init = {
0x6a09e667UL, 0xbb67ae85UL, 0x3c6ef372UL, 0xa54ff53aUL,
0x510e527fUL, 0x9b05688cUL, 0x1f83d9abUL, 0x5be0cd19UL
};
- FcChar32 *ret = malloc (sizeof (FcChar32) * 8);
- if (!ret)
- return NULL;
-
- for (i = 0; i < 8; i++)
- ret[i] = h[i];
-
- return ret;
+ memcpy (digest, init, sizeof (FcHashDigest));
}
-static void
-FcHashComputeSHA256Digest (FcChar32 *hash,
- const char *block)
+void
+FcHashDigestAddBlock (FcHashDigest digest,
+ const char block[64])
{
static const FcChar32 k[] = {
0x428a2f98UL, 0x71374491UL, 0xb5c0fbcfUL, 0xe9b5dba5UL,
@@ -82,7 +80,7 @@ FcHashComputeSHA256Digest (FcChar32 *hash,
FcChar32 w[64], i, j, t1, t2;
FcChar32 a, b, c, d, e, f, g, h;
-#define H(n) (hash[n])
+#define H(n) (digest[n])
a = H(0);
b = H(1);
@@ -130,188 +128,62 @@ FcHashComputeSHA256Digest (FcChar32 *hash,
#undef H
}
-static FcChar8 *
-FcHashSHA256ToString (FcChar32 *hash)
-{
- FcChar8 *ret = NULL;
- static const char hex[] = "0123456789abcdef";
- int i, j;
-
- if (hash)
- {
- ret = malloc (sizeof (FcChar8) * (8 * 8 + 7 + 1));
- if (!ret)
- return NULL;
- memcpy (ret, "sha256:", 7);
-#define H(n) hash[n]
- for (i = 0; i < 8; i++)
- {
- FcChar32 v = H(i);
-
- for (j = 0; j < 8; j++)
- ret[7 + (i * 8) + j] = hex[(v >> (28 - j * 4)) & 0xf];
- }
- ret[7 + i * 8] = 0;
-#undef H
- free (hash);
- }
-
- return ret;
-}
-
-FcChar8 *
-FcHashGetSHA256Digest (const FcChar8 *input_strings,
- size_t len)
-{
- size_t i, round_len = len / 64;
- char block[64];
- FcChar32 *ret = FcHashInitSHA256Digest ();
-
- if (!ret)
- return NULL;
-
- for (i = 0; i < round_len; i++)
- {
- FcHashComputeSHA256Digest (ret, (const char *)&input_strings[i * 64]);
- }
- /* padding */
- if ((len % 64) != 0)
- memcpy (block, &input_strings[len / 64], len % 64);
- memset (&block[len % 64], 0, 64 - (len % 64));
- block[len % 64] = 0x80;
- if ((64 - (len % 64)) < 9)
- {
- /* process a block once */
- FcHashComputeSHA256Digest (ret, block);
- memset (block, 0, 64);
- }
- /* set input size at the end */
- len *= 8;
- block[63 - 0] = (uint64_t)len & 0xff;
- block[63 - 1] = ((uint64_t)len >> 8) & 0xff;
- block[63 - 2] = ((uint64_t)len >> 16) & 0xff;
- block[63 - 3] = ((uint64_t)len >> 24) & 0xff;
- block[63 - 4] = ((uint64_t)len >> 32) & 0xff;
- block[63 - 5] = ((uint64_t)len >> 40) & 0xff;
- block[63 - 6] = ((uint64_t)len >> 48) & 0xff;
- block[63 - 7] = ((uint64_t)len >> 56) & 0xff;
- FcHashComputeSHA256Digest (ret, block);
-
- return FcHashSHA256ToString (ret);
-}
-
-FcChar8 *
-FcHashGetSHA256DigestFromFile (const FcChar8 *filename)
+void
+FcHashDigestFinish (FcHashDigest digest,
+ const char *residual, /* < 64 bytes */
+ size_t total_len)
{
- FILE *fp = fopen ((const char *)filename, "rb");
char ibuf[64];
- FcChar32 *ret;
- size_t len;
- struct stat st;
-
- if (!fp)
- return NULL;
+ unsigned int len = total_len % 64;
+ uint64_t v;
- if (FcStat (filename, &st))
- goto bail0;
+ if (!len)
+ return;
- ret = FcHashInitSHA256Digest ();
- if (!ret)
- goto bail0;
+ memcpy (ibuf, residual, len);
+ memset (ibuf + len, 0, 64 - len);
+ ibuf[len] = 0x80;
- while (!feof (fp))
+ if ((64 - len) < 9)
{
- if ((len = fread (ibuf, sizeof (char), 64, fp)) < 64)
- {
- uint64_t v;
-
- /* add a padding */
- memset (&ibuf[len], 0, 64 - len);
- ibuf[len] = 0x80;
- if ((64 - len) < 9)
- {
- /* process a block once */
- FcHashComputeSHA256Digest (ret, ibuf);
- memset (ibuf, 0, 64);
- }
- /* set input size at the end */
- v = (long)st.st_size * 8;
- ibuf[63 - 0] = v & 0xff;
- ibuf[63 - 1] = (v >> 8) & 0xff;
- ibuf[63 - 2] = (v >> 16) & 0xff;
- ibuf[63 - 3] = (v >> 24) & 0xff;
- ibuf[63 - 4] = (v >> 32) & 0xff;
- ibuf[63 - 5] = (v >> 40) & 0xff;
- ibuf[63 - 6] = (v >> 48) & 0xff;
- ibuf[63 - 7] = (v >> 56) & 0xff;
- FcHashComputeSHA256Digest (ret, ibuf);
- break;
- }
- else
- {
- FcHashComputeSHA256Digest (ret, ibuf);
- }
+ FcHashDigestAddBlock (digest, ibuf);
+ memset (ibuf, 0, 64);
}
- fclose (fp);
-
- return FcHashSHA256ToString (ret);
-
-bail0:
- fclose (fp);
- return NULL;
+ /* set input size at the end */
+ v = (uint64_t) total_len * 8;
+ ibuf[63 - 0] = v & 0xff;
+ ibuf[63 - 1] = (v >> 8) & 0xff;
+ ibuf[63 - 2] = (v >> 16) & 0xff;
+ ibuf[63 - 3] = (v >> 24) & 0xff;
+ ibuf[63 - 4] = (v >> 32) & 0xff;
+ ibuf[63 - 5] = (v >> 40) & 0xff;
+ ibuf[63 - 6] = (v >> 48) & 0xff;
+ ibuf[63 - 7] = (v >> 56) & 0xff;
+ FcHashDigestAddBlock (digest, ibuf);
}
FcChar8 *
-FcHashGetSHA256DigestFromMemory (const char *fontdata,
- size_t length)
+FcHashToString (const FcHashDigest digest)
{
- char ibuf[64];
- FcChar32 *ret;
- size_t i = 0;
+ FcChar8 *ret = NULL;
+ static const char hex[] = "0123456789abcdef";
+ int i, j;
- ret = FcHashInitSHA256Digest ();
+ ret = malloc (sizeof (FcChar8) * (8 * 8 + 7 + 1));
if (!ret)
return NULL;
-
- while (i <= length)
+ memcpy (ret, "sha256:", 7);
+#define H(n) digest[n]
+ for (i = 0; i < 8; i++)
{
- if ((length - i) < 64)
- {
- uint64_t v;
- size_t n;
+ FcChar32 v = H(i);
- /* add a padding */
- n = length - i;
- if (n > 0)
- memcpy (ibuf, &fontdata[i], n);
- memset (&ibuf[n], 0, 64 - n);
- ibuf[n] = 0x80;
- if ((64 - n) < 9)
- {
- /* process a block once */
- FcHashComputeSHA256Digest (ret, ibuf);
- memset (ibuf, 0, 64);
- }
- /* set input size at the end */
- v = length * 8;
- ibuf[63 - 0] = v & 0xff;
- ibuf[63 - 1] = (v >> 8) & 0xff;
- ibuf[63 - 2] = (v >> 16) & 0xff;
- ibuf[63 - 3] = (v >> 24) & 0xff;
- ibuf[63 - 4] = (v >> 32) & 0xff;
- ibuf[63 - 5] = (v >> 40) & 0xff;
- ibuf[63 - 6] = (v >> 48) & 0xff;
- ibuf[63 - 7] = (v >> 56) & 0xff;
- FcHashComputeSHA256Digest (ret, ibuf);
- break;
- }
- else
- {
- FcHashComputeSHA256Digest (ret, &fontdata[i]);
- }
- i += 64;
+ for (j = 0; j < 8; j++)
+ ret[7 + (i * 8) + j] = hex[(v >> (28 - j * 4)) & 0xf];
}
+ ret[7 + i * 8] = 0;
+#undef H
- return FcHashSHA256ToString (ret);
+ return ret;
}