1 /*  libGringotts - generic data encoding (crypto+compression) library
2  *  (c) 2002, Germano Rizzo <mano@pluto.linux.it>
3  *
4  *  libgrg_structs.c - functions to manage the various libgrg structs
5  *  Author: Germano Rizzo
6  *
7  *  This program is free software; you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License as published by
9  *  the Free Software Foundation; either version 2 of the License, or
10  *  (at your option) any later version.
11  *
12  *  This program is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *  GNU Library General Public License for more details.
16  *
17  *  You should have received a copy of the GNU General Public License
18  *  along with this program; if not, write to the Free Software
19  *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20  */
21 
22 #include <unistd.h>
23 #include <fcntl.h>
24 #include <stdlib.h>
25 #include <time.h>
26 #include <string.h>
27 
28 #include <mhash.h>
29 
30 #include "config.h"
31 #include "libgrg_structs.h"
32 #include "libgrg_utils.h"
33 #include "libgringotts.h"
34 
35 static int
reinit_random(GRG_CTX gctx)36 reinit_random (GRG_CTX gctx)
37 {
38 #ifdef HAVE__DEV_RANDOM
39 	if (!gctx)
40 		return 0;
41 
42 	close (gctx->rnd);
43 
44 	if (gctx->sec_lvl == GRG_SEC_PARANOIA)
45 		gctx->rnd = open ("/dev/random", O_RDONLY);
46 	else
47 		gctx->rnd = open ("/dev/urandom", O_RDONLY);
48 
49 	if (gctx->rnd < 3)
50 	{
51 		close (gctx->rnd);
52 		return 0;
53 	}
54 #else
55 #warning compiling without /dev/random
56 	srandom ((unsigned int) time (NULL));
57 #endif
58 
59 	return 1;
60 }
61 
62 GRG_CTX
grg_context_initialize(const unsigned char * header,const grg_crypt_algo crypt_algo,const grg_hash_algo hash_algo,const grg_comp_algo comp_algo,const grg_comp_ratio comp_lvl,const grg_security_lvl sec_lvl)63 grg_context_initialize (const unsigned char *header,
64 			const grg_crypt_algo crypt_algo,
65 			const grg_hash_algo hash_algo,
66 			const grg_comp_algo comp_algo,
67 			const grg_comp_ratio comp_lvl,
68 			const grg_security_lvl sec_lvl)
69 {
70 	GRG_CTX ret = (GRG_CTX) malloc (sizeof (struct _grg_context));
71 
72 	if (!ret)
73 		return NULL;
74 
75 	ret->rnd = -1;		//dummy
76 #ifdef HAVE__DEV_RANDOM
77 	if (!reinit_random (ret))
78 	{
79 		free (ret);
80 		return NULL;
81 	}
82 #endif
83 
84 	if (!header || (strlen (header) != HEADER_LEN))
85 	{
86 #ifdef HAVE__DEV_RANDOM
87 		close (ret->rnd);
88 #endif
89 		free (ret);
90 		return NULL;
91 	}
92 
93 	memcpy (ret->header, header, HEADER_LEN);
94 	ret->crypt_algo = crypt_algo;
95 	ret->hash_algo = hash_algo;
96 	ret->comp_algo = comp_algo;
97 	ret->comp_lvl = comp_lvl;
98 	ret->sec_lvl = sec_lvl;
99 
100 	return ret;
101 }
102 
103 GRG_CTX
grg_context_initialize_defaults(const unsigned char * header)104 grg_context_initialize_defaults (const unsigned char *header)
105 {
106 	return grg_context_initialize (header, GRG_SERPENT, GRG_RIPEMD_160,
107 				       GRG_ZLIB, GRG_LVL_BEST,
108 				       GRG_SEC_NORMAL);
109 }
110 
111 void
grg_context_free(GRG_CTX gctx)112 grg_context_free (GRG_CTX gctx)
113 {
114 #ifdef HAVE__DEV_RANDOM
115 	close (gctx->rnd);
116 #endif
117 
118 	free (gctx);
119 }
120 
121 grg_crypt_algo
grg_ctx_get_crypt_algo(const GRG_CTX gctx)122 grg_ctx_get_crypt_algo (const GRG_CTX gctx)
123 {
124 	return gctx->crypt_algo;
125 }
126 
127 grg_hash_algo
grg_ctx_get_hash_algo(const GRG_CTX gctx)128 grg_ctx_get_hash_algo (const GRG_CTX gctx)
129 {
130 	return gctx->hash_algo;
131 }
132 
133 grg_comp_algo
grg_ctx_get_comp_algo(const GRG_CTX gctx)134 grg_ctx_get_comp_algo (const GRG_CTX gctx)
135 {
136 	return gctx->comp_algo;
137 }
138 
139 grg_comp_ratio
grg_ctx_get_comp_ratio(const GRG_CTX gctx)140 grg_ctx_get_comp_ratio (const GRG_CTX gctx)
141 {
142 	return gctx->comp_lvl;
143 }
144 
145 grg_security_lvl
grg_ctx_get_security_lvl(const GRG_CTX gctx)146 grg_ctx_get_security_lvl (const GRG_CTX gctx)
147 {
148 	return gctx->sec_lvl;
149 }
150 
151 void
grg_ctx_set_crypt_algo(GRG_CTX gctx,const grg_crypt_algo crypt_algo)152 grg_ctx_set_crypt_algo (GRG_CTX gctx, const grg_crypt_algo crypt_algo)
153 {
154 	if (!gctx)
155 		return;
156 
157 	gctx->crypt_algo = crypt_algo;
158 }
159 
160 void
grg_ctx_set_hash_algo(GRG_CTX gctx,const grg_hash_algo hash_algo)161 grg_ctx_set_hash_algo (GRG_CTX gctx, const grg_hash_algo hash_algo)
162 {
163 	if (!gctx)
164 		return;
165 
166 	gctx->hash_algo = hash_algo;
167 }
168 
169 void
grg_ctx_set_comp_algo(GRG_CTX gctx,const grg_comp_algo comp_algo)170 grg_ctx_set_comp_algo (GRG_CTX gctx, const grg_comp_algo comp_algo)
171 {
172 	if (!gctx)
173 		return;
174 
175 	gctx->comp_algo = comp_algo;
176 }
177 
178 void
grg_ctx_set_comp_ratio(GRG_CTX gctx,const grg_comp_ratio comp_ratio)179 grg_ctx_set_comp_ratio (GRG_CTX gctx, const grg_comp_ratio comp_ratio)
180 {
181 	if (!gctx)
182 		return;
183 
184 	gctx->comp_lvl = comp_ratio;
185 }
186 
187 void
grg_ctx_set_security_lvl(GRG_CTX gctx,const grg_security_lvl sec_level)188 grg_ctx_set_security_lvl (GRG_CTX gctx, const grg_security_lvl sec_level)
189 {
190 	if (!gctx)
191 		return;
192 
193 	gctx->sec_lvl = sec_level;
194 	reinit_random (gctx);
195 }
196 
197 GRG_KEY
grg_key_gen(const unsigned char * pwd,const int pwd_len)198 grg_key_gen (const unsigned char *pwd, const int pwd_len)
199 {
200 	GRG_KEY key;
201 	int real_pwd_len;
202 
203 	if (!pwd)
204 		return NULL;
205 
206 	if (pwd_len < 0)
207 		real_pwd_len = strlen (pwd);
208 	else
209 		real_pwd_len = pwd_len;
210 
211 	key = (GRG_KEY) malloc (sizeof (struct _grg_key));
212 
213 	if (!key)
214 		return NULL;
215 
216 	mhash_keygen (KEYGEN_S2K_SIMPLE, MHASH_RIPEMD160, 0,
217 		      key->key_192_ripe, 24, NULL, 0, (unsigned char *) pwd,
218 		      real_pwd_len);
219 	mhash_keygen (KEYGEN_S2K_SIMPLE, MHASH_RIPEMD160, 0,
220 		      key->key_256_ripe, 32, NULL, 0, (unsigned char *) pwd,
221 		      real_pwd_len);
222 	mhash_keygen (KEYGEN_S2K_SIMPLE, MHASH_SHA1, 0, key->key_192_sha, 24,
223 		      NULL, 0, (unsigned char *) pwd, real_pwd_len);
224 	mhash_keygen (KEYGEN_S2K_SIMPLE, MHASH_SHA1, 0, key->key_256_sha, 32,
225 		      NULL, 0, (unsigned char *) pwd, real_pwd_len);
226 
227 	return key;
228 }
229 
230 GRG_KEY
grg_key_clone(const GRG_KEY src)231 grg_key_clone (const GRG_KEY src)
232 {
233 	GRG_KEY clone = (GRG_KEY) malloc (sizeof (struct _grg_key));
234 
235 	if (clone)
236 		memcpy (clone, src, sizeof (struct _grg_key));
237 
238 	return clone;
239 }
240 
241 int
grg_key_compare(const GRG_KEY k1,const GRG_KEY k2)242 grg_key_compare (const GRG_KEY k1, const GRG_KEY k2)
243 {
244 	if (!k1 || !k2)
245 		return 0;
246 
247 	if (memcmp (k1->key_256_ripe, k2->key_256_ripe, 32))
248 		return 0;
249 
250 	return 1;
251 }
252 
253 void
grg_key_free(const GRG_CTX gctx,GRG_KEY key)254 grg_key_free (const GRG_CTX gctx, GRG_KEY key)
255 {
256 	grg_free (gctx, key, sizeof (struct _grg_key));
257 }
258