Add an utility to calculate hashes over a set of files
[libgcrypt.git] / tests / gchash.c
1 /* gchash.c - Calculate hash values
2  * Copyright (C) 2013 Dmitry Eremin-Solenikov
3  *
4  * This file is part of Libgcrypt.
5  *
6  * Libgcrypt is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU Lesser General Public License as
8  * published by the Free Software Foundation; either version 2.1 of
9  * the License, or (at your option) any later version.
10  *
11  * Libgcrypt is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this program; if not, see <http://www.gnu.org/licenses/>.
18  */
19
20 #ifdef HAVE_CONFIG_H
21 # include <config.h>
22 #endif
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <ctype.h>
26
27 #ifdef _GCRYPT_IN_LIBGCRYPT
28 # undef _GCRYPT_IN_LIBGCRYPT
29 # include "gcrypt.h"
30 #else
31 # include <gcrypt.h>
32 #endif
33
34
35 void
36 init_gcrypt (void)
37 {
38   if (!gcry_check_version (GCRYPT_VERSION)) {
39     fputs ("libgcrypt version mismatch\n", stderr);
40     exit (2);
41   }
42
43   gcry_control (GCRYCTL_SUSPEND_SECMEM_WARN);
44
45   /* Allocate a pool of 16k secure memory.  This make the secure memory
46    * available and also drops privileges where needed.  */
47   gcry_control (GCRYCTL_INIT_SECMEM, 16384, 0);
48
49   gcry_control (GCRYCTL_RESUME_SECMEM_WARN);
50
51   gcry_control (GCRYCTL_INITIALIZATION_FINISHED, 0);
52 }
53
54 int
55 main (int argc, char **argv)
56 {
57   gcry_md_hd_t hd;
58   gcry_error_t err;
59   int algo;
60
61   init_gcrypt();
62
63   if (argc < 2 || (argv[1] && !strcmp(argv[1], "--help")))
64     {
65       fprintf (stderr, "Usage: %s <digest> <file>...\n", argv[0]);
66       return 1;
67     }
68
69   algo = gcry_md_map_name (argv[1]);
70   if (algo == GCRY_MD_NONE)
71     {
72       fprintf (stderr, "Unknown algorithm '%s'\n", argv[1]);
73       return 1;
74     }
75
76   err = gcry_md_open(&hd, algo, 0);
77   if (err)
78     {
79       fprintf (stderr, "LibGCrypt error %s/%s\n",
80           gcry_strsource (err),
81           gcry_strerror (err));
82       exit (1);
83     }
84
85   for (argv += 2; *argv; argv++)
86     {
87       FILE *fp;
88       unsigned char buf[1024];
89       size_t size;
90       int i;
91       unsigned char *h;
92       if (!strcmp (*argv, "-"))
93         fp = stdin;
94       else
95         fp = fopen (*argv, "r");
96
97       if (fp == NULL)
98         {
99           perror ("fopen");
100           return 1;
101         }
102
103       while (!feof (fp))
104         {
105           size = fread (buf, 1, sizeof(buf), fp);
106           gcry_md_write (hd, buf, size);
107         }
108
109       h  = gcry_md_read(hd, 0);
110
111       for (i = 0; i < gcry_md_get_algo_dlen (algo); i++)
112         printf("%02hhx", h[i]);
113       printf("  %s\n", *argv);
114
115       gcry_md_reset(hd);
116     }
117
118   gcry_md_close(hd);
119   return 0;
120 }