1
2 /*
3 * Licensed Materials - Property of IBM
4 *
5 * trousers - An open source TCG Software Stack
6 *
7 * (C) Copyright International Business Machines Corp. 2005, 2007
8 *
9 */
10
11
12 #include <stdlib.h>
13 #include <stdio.h>
14 #include <errno.h>
15 #include <string.h>
16
17 #include "trousers/tss.h"
18 #include "trousers/trousers.h"
19 #include "trousers_types.h"
20 #include "spi_utils.h"
21 #include "capabilities.h"
22 #include "tsplog.h"
23 #include "obj.h"
24
25 TSS_RESULT
obj_hash_add(TSS_HCONTEXT tspContext,UINT32 type,TSS_HOBJECT * phObject)26 obj_hash_add(TSS_HCONTEXT tspContext, UINT32 type, TSS_HOBJECT *phObject)
27 {
28 TSS_RESULT result;
29 struct tr_hash_obj *hash = calloc(1, sizeof(struct tr_hash_obj));
30
31 if (hash == NULL) {
32 LogError("malloc of %zd bytes failed.",
33 sizeof(struct tr_hash_obj));
34 return TSPERR(TSS_E_OUTOFMEMORY);
35 }
36
37 if ((type == TSS_HASH_SHA1) ||
38 (type == TSS_HASH_DEFAULT)) {
39 hash->type = TSS_HASH_SHA1;
40 hash->hashSize = 20;
41 } else if (type == TSS_HASH_OTHER) {
42 hash->type = TSS_HASH_OTHER;
43 hash->hashSize = 0;
44 }
45
46 if ((result = obj_list_add(&hash_list, tspContext, 0, hash, phObject))) {
47 free(hash);
48 return result;
49 }
50
51 return TSS_SUCCESS;
52 }
53
54 TSS_BOOL
obj_is_hash(TSS_HOBJECT hObject)55 obj_is_hash(TSS_HOBJECT hObject)
56 {
57 TSS_BOOL answer = FALSE;
58
59 if ((obj_list_get_obj(&hash_list, hObject))) {
60 answer = TRUE;
61 obj_list_put(&hash_list);
62 }
63
64 return answer;
65 }
66
67 TSS_RESULT
obj_hash_get_tsp_context(TSS_HHASH hHash,TSS_HCONTEXT * tspContext)68 obj_hash_get_tsp_context(TSS_HHASH hHash, TSS_HCONTEXT *tspContext)
69 {
70 struct tsp_object *obj;
71
72 if ((obj = obj_list_get_obj(&hash_list, hHash)) == NULL)
73 return TSPERR(TSS_E_INVALID_HANDLE);
74
75 *tspContext = obj->tspContext;
76
77 obj_list_put(&hash_list);
78
79 return TSS_SUCCESS;
80 }
81
82 TSS_RESULT
obj_hash_set_value(TSS_HHASH hHash,UINT32 size,BYTE * value)83 obj_hash_set_value(TSS_HHASH hHash, UINT32 size, BYTE *value)
84 {
85 struct tsp_object *obj;
86 struct tr_hash_obj *hash;
87 TSS_RESULT result = TSS_SUCCESS;
88
89 if ((obj = obj_list_get_obj(&hash_list, hHash)) == NULL)
90 return TSPERR(TSS_E_INVALID_HANDLE);
91
92 hash = (struct tr_hash_obj *)obj->data;
93
94 if (hash->type != TSS_HASH_OTHER &&
95 size != TCPA_SHA1_160_HASH_LEN) {
96 result = TSPERR(TSS_E_HASH_INVALID_LENGTH);
97 goto done;
98 }
99
100 free(hash->hashData);
101
102 if ((hash->hashData = calloc(1, size)) == NULL) {
103 LogError("malloc of %d bytes failed.", size);
104 result = TSPERR(TSS_E_OUTOFMEMORY);
105 goto done;
106 }
107 hash->hashSize = size;
108 memcpy(hash->hashData, value, size);
109
110 done:
111 obj_list_put(&hash_list);
112
113 return result;
114 }
115
116 TSS_RESULT
obj_hash_get_value(TSS_HHASH hHash,UINT32 * size,BYTE ** value)117 obj_hash_get_value(TSS_HHASH hHash, UINT32 *size, BYTE **value)
118 {
119 struct tsp_object *obj;
120 struct tr_hash_obj *hash;
121 TSS_RESULT result = TSS_SUCCESS;
122
123 if ((obj = obj_list_get_obj(&hash_list, hHash)) == NULL)
124 return TSPERR(TSS_E_INVALID_HANDLE);
125
126 hash = (struct tr_hash_obj *)obj->data;
127
128 if (hash->hashData == NULL) {
129 result = TSPERR(TSS_E_HASH_NO_DATA);
130 goto done;
131 }
132
133 if ((*value = calloc_tspi(obj->tspContext, hash->hashSize)) == NULL) {
134 LogError("malloc of %d bytes failed.", hash->hashSize);
135 result = TSPERR(TSS_E_OUTOFMEMORY);
136 goto done;
137 }
138 *size = hash->hashSize;
139 memcpy(*value, hash->hashData, *size);
140
141 done:
142 obj_list_put(&hash_list);
143
144 return result;
145 }
146
147 TSS_RESULT
obj_hash_update_value(TSS_HHASH hHash,UINT32 size,BYTE * data)148 obj_hash_update_value(TSS_HHASH hHash, UINT32 size, BYTE *data)
149 {
150 struct tsp_object *obj;
151 struct tr_hash_obj *hash;
152 TSS_RESULT result = TSS_SUCCESS;
153
154 if ((obj = obj_list_get_obj(&hash_list, hHash)) == NULL)
155 return TSPERR(TSS_E_INVALID_HANDLE);
156
157 hash = (struct tr_hash_obj *)obj->data;
158
159 if (hash->type != TSS_HASH_SHA1 &&
160 hash->type != TSS_HASH_DEFAULT) {
161 result = TSPERR(TSS_E_FAIL);
162 goto done;
163 }
164
165 if (hash->hashUpdateBuffer == NULL) {
166 hash->hashUpdateBuffer = calloc(1, size);
167 if (hash->hashUpdateBuffer == NULL) {
168 LogError("malloc of %u bytes failed.", size);
169 result = TSPERR(TSS_E_OUTOFMEMORY);
170 goto done;
171 }
172 } else {
173 hash->hashUpdateBuffer = realloc(hash->hashUpdateBuffer,
174 size + hash->hashUpdateSize);
175
176 if (hash->hashUpdateBuffer == NULL) {
177 LogError("malloc of %u bytes failed.", size + hash->hashUpdateSize);
178 result = TSPERR(TSS_E_OUTOFMEMORY);
179 goto done;
180 }
181 }
182
183 memcpy(&hash->hashUpdateBuffer[hash->hashUpdateSize], data, size);
184 hash->hashUpdateSize += size;
185
186 if (hash->hashData == NULL) {
187 hash->hashData = calloc(1, TCPA_SHA1_160_HASH_LEN);
188 if (hash->hashData == NULL) {
189 LogError("malloc of %d bytes failed.", TCPA_SHA1_160_HASH_LEN);
190 result = TSPERR(TSS_E_OUTOFMEMORY);
191 goto done;
192 }
193 }
194
195 result = Trspi_Hash(TSS_HASH_SHA1, hash->hashUpdateSize, hash->hashUpdateBuffer,
196 hash->hashData);
197
198 done:
199 obj_list_put(&hash_list);
200
201 return result;
202 }
203
204 void
__tspi_hash_free(void * data)205 __tspi_hash_free(void *data)
206 {
207 struct tr_hash_obj *hash = (struct tr_hash_obj *)data;
208
209 free(hash->hashData);
210 free(hash->hashUpdateBuffer);
211 free(hash);
212 }
213
214 /*
215 * remove hash object hObject from the list
216 */
217 TSS_RESULT
obj_hash_remove(TSS_HOBJECT hObject,TSS_HCONTEXT tspContext)218 obj_hash_remove(TSS_HOBJECT hObject, TSS_HCONTEXT tspContext)
219 {
220 TSS_RESULT result;
221
222 if ((result = obj_list_remove(&hash_list, &__tspi_hash_free, hObject, tspContext)))
223 return result;
224
225 return TSS_SUCCESS;
226 }
227
228