1 /*
2  * XML Security Library (http://www.aleksey.com/xmlsec).
3  *
4  *
5  * This is free software; see Copyright file in the source
6  * distribution for preciese wording.
7  *
8  * Copyright (C) 2002-2016 Aleksey Sanin <aleksey@aleksey.com>. All Rights Reserved.
9  */
10 /**
11  * SECTION:keysdata
12  * @Short_description: Crypto key data object functions.
13  * @Stability: Stable
14  *
15  */
16 
17 #include "globals.h"
18 
19 #include <stdlib.h>
20 #include <string.h>
21 
22 #include <libxml/tree.h>
23 
24 #include <xmlsec/xmlsec.h>
25 #include <xmlsec/xmltree.h>
26 #include <xmlsec/keys.h>
27 #include <xmlsec/keyinfo.h>
28 #include <xmlsec/transforms.h>
29 #include <xmlsec/base64.h>
30 #include <xmlsec/keyinfo.h>
31 #include <xmlsec/errors.h>
32 
33 /**************************************************************************
34  *
35  * Global xmlSecKeyDataIds list functions
36  *
37  *************************************************************************/
38 static xmlSecPtrList xmlSecAllKeyDataIds;
39 static int xmlSecImportPersistKey = 0;
40 
41 /**
42  * xmlSecKeyDataIdsGet:
43  *
44  * Gets global registered key data klasses list.
45  *
46  * Returns: the pointer to list of all registered key data klasses.
47  */
48 xmlSecPtrListPtr
xmlSecKeyDataIdsGet(void)49 xmlSecKeyDataIdsGet(void) {
50     return(&xmlSecAllKeyDataIds);
51 }
52 
53 /**
54  * xmlSecKeyDataIdsInit:
55  *
56  * Initializes the key data klasses. This function is called from the
57  * #xmlSecInit function and the application should not call it directly.
58  *
59  * Returns: 0 on success or a negative value if an error occurs.
60  */
61 int
xmlSecKeyDataIdsInit(void)62 xmlSecKeyDataIdsInit(void) {
63     int ret;
64 
65     ret = xmlSecPtrListInitialize(xmlSecKeyDataIdsGet(), xmlSecKeyDataIdListId);
66     if(ret < 0) {
67         xmlSecInternalError("xmlSecPtrListInitialize(xmlSecKeyDataIdListId)", NULL);
68         return(-1);
69     }
70 
71     ret = xmlSecKeyDataIdsRegisterDefault();
72     if(ret < 0) {
73         xmlSecInternalError("xmlSecKeyDataIdsRegisterDefault", NULL);
74         return(-1);
75     }
76 
77     return(0);
78 }
79 
80 /**
81  * xmlSecKeyDataIdsShutdown:
82  *
83  * Shuts down the keys data klasses. This function is called from the
84  * #xmlSecShutdown function and the application should not call it directly.
85  */
86 void
xmlSecKeyDataIdsShutdown(void)87 xmlSecKeyDataIdsShutdown(void) {
88     xmlSecPtrListFinalize(xmlSecKeyDataIdsGet());
89 }
90 
91 /**
92  * xmlSecKeyDataIdsRegister:
93  * @id:                 the key data klass.
94  *
95  * Registers @id in the global list of key data klasses.
96  *
97  * Returns: 0 on success or a negative value if an error occurs.
98  */
99 int
xmlSecKeyDataIdsRegister(xmlSecKeyDataId id)100 xmlSecKeyDataIdsRegister(xmlSecKeyDataId id) {
101     int ret;
102 
103     xmlSecAssert2(id != xmlSecKeyDataIdUnknown, -1);
104 
105     ret = xmlSecPtrListAdd(xmlSecKeyDataIdsGet(), (xmlSecPtr)id);
106     if(ret < 0) {
107         xmlSecInternalError("xmlSecPtrListAdd",
108                             xmlSecKeyDataKlassGetName(id));
109         return(-1);
110     }
111 
112     return(0);
113 }
114 
115 /**
116  * xmlSecKeyDataIdsRegisterDefault:
117  *
118  * Registers default (implemented by XML Security Library)
119  * key data klasses: <dsig:KeyName/> element processing klass,
120  * <dsig:KeyValue/> element processing klass, ...
121  *
122  * Returns: 0 on success or a negative value if an error occurs.
123  */
124 int
xmlSecKeyDataIdsRegisterDefault(void)125 xmlSecKeyDataIdsRegisterDefault(void) {
126     if(xmlSecKeyDataIdsRegister(xmlSecKeyDataNameId) < 0) {
127         xmlSecInternalError("xmlSecKeyDataIdsRegister(xmlSecKeyDataNameId)", NULL);
128         return(-1);
129     }
130 
131     if(xmlSecKeyDataIdsRegister(xmlSecKeyDataValueId) < 0) {
132         xmlSecInternalError("xmlSecKeyDataIdsRegister(xmlSecKeyDataValueId)", NULL);
133         return(-1);
134     }
135 
136     if(xmlSecKeyDataIdsRegister(xmlSecKeyDataRetrievalMethodId) < 0) {
137         xmlSecInternalError("xmlSecKeyDataIdsRegister(xmlSecKeyDataRetrievalMethodId", NULL);
138         return(-1);
139     }
140 
141 #ifndef XMLSEC_NO_XMLENC
142     if(xmlSecKeyDataIdsRegister(xmlSecKeyDataEncryptedKeyId) < 0) {
143         xmlSecInternalError("xmlSecKeyDataIdsRegister(xmlSecKeyDataEncryptedKeyId)", NULL);
144         return(-1);
145     }
146 #endif /* XMLSEC_NO_XMLENC */
147 
148     return(0);
149 }
150 
151 /**************************************************************************
152  *
153  * xmlSecKeyData functions
154  *
155  *************************************************************************/
156 /**
157  * xmlSecKeyDataCreate:
158  * @id:                 the data id.
159  *
160  * Allocates and initializes new key data of the specified type @id.
161  * Caller is responsible for destroying returned object with
162  * #xmlSecKeyDataDestroy function.
163  *
164  * Returns: the pointer to newly allocated key data structure
165  * or NULL if an error occurs.
166  */
167 xmlSecKeyDataPtr
xmlSecKeyDataCreate(xmlSecKeyDataId id)168 xmlSecKeyDataCreate(xmlSecKeyDataId id)  {
169     xmlSecKeyDataPtr data;
170     int ret;
171 
172     xmlSecAssert2(id != NULL, NULL);
173     xmlSecAssert2(id->klassSize >= sizeof(xmlSecKeyDataKlass), NULL);
174     xmlSecAssert2(id->objSize >= sizeof(xmlSecKeyData), NULL);
175     xmlSecAssert2(id->name != NULL, NULL);
176 
177     /* Allocate a new xmlSecKeyData and fill the fields. */
178     data = (xmlSecKeyDataPtr)xmlMalloc(id->objSize);
179     if(data == NULL) {
180         xmlSecMallocError(id->objSize,
181                           xmlSecKeyDataKlassGetName(id));
182         return(NULL);
183     }
184     memset(data, 0, id->objSize);
185     data->id = id;
186 
187     if(id->initialize != NULL) {
188         ret = (id->initialize)(data);
189         if(ret < 0) {
190             xmlSecInternalError("id->initialize",
191                                 xmlSecKeyDataKlassGetName(id));
192             xmlSecKeyDataDestroy(data);
193             return(NULL);
194         }
195     }
196 
197     return(data);
198 }
199 
200 /**
201  * xmlSecKeyDataDuplicate:
202  * @data:               the pointer to the key data.
203  *
204  * Creates a duplicate of the given @data. Caller is responsible for
205  * destroying returned object with #xmlSecKeyDataDestroy function.
206  *
207  * Returns: the pointer to newly allocated key data structure
208  * or NULL if an error occurs.
209  */
210 xmlSecKeyDataPtr
xmlSecKeyDataDuplicate(xmlSecKeyDataPtr data)211 xmlSecKeyDataDuplicate(xmlSecKeyDataPtr data) {
212     xmlSecKeyDataPtr newData;
213     int ret;
214 
215     xmlSecAssert2(xmlSecKeyDataIsValid(data), NULL);
216     xmlSecAssert2(data->id->duplicate != NULL, NULL);
217 
218     newData = xmlSecKeyDataCreate(data->id);
219     if(newData == NULL) {
220         xmlSecInternalError("xmlSecKeyDataCreate",
221                             xmlSecKeyDataGetName(data));
222         return(NULL);
223     }
224 
225     ret = (data->id->duplicate)(newData, data);
226     if(ret < 0) {
227         xmlSecInternalError("id->duplicate",
228                             xmlSecKeyDataGetName(data));
229         xmlSecKeyDataDestroy(newData);
230         return(NULL);
231     }
232 
233     return(newData);
234 }
235 
236 /**
237  * xmlSecKeyDataDestroy:
238  * @data:               the pointer to the key data.
239  *
240  * Destroys the data and frees all allocated memory.
241  */
242 void
xmlSecKeyDataDestroy(xmlSecKeyDataPtr data)243 xmlSecKeyDataDestroy(xmlSecKeyDataPtr data) {
244     xmlSecAssert(xmlSecKeyDataIsValid(data));
245     xmlSecAssert(data->id->objSize > 0);
246 
247     if(data->id->finalize != NULL) {
248         (data->id->finalize)(data);
249     }
250     memset(data, 0, data->id->objSize);
251     xmlFree(data);
252 }
253 
254 
255 /**
256  * xmlSecKeyDataXmlRead:
257  * @id:                 the data klass.
258  * @key:                the destination key.
259  * @node:               the pointer to an XML node.
260  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
261  *
262  * Reads the key data of klass @id from XML @node and adds them to @key.
263  *
264  * Returns: 0 on success or a negative value otherwise.
265  */
266 int
xmlSecKeyDataXmlRead(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlNodePtr node,xmlSecKeyInfoCtxPtr keyInfoCtx)267 xmlSecKeyDataXmlRead(xmlSecKeyDataId id, xmlSecKeyPtr key, xmlNodePtr node, xmlSecKeyInfoCtxPtr keyInfoCtx) {
268     xmlSecAssert2(id != NULL, -1);
269     xmlSecAssert2(id->xmlRead != NULL, -1);
270     xmlSecAssert2(key != NULL, -1);
271     xmlSecAssert2(node != NULL, -1);
272 
273     return((id->xmlRead)(id, key, node, keyInfoCtx));
274 }
275 
276 /**
277  * xmlSecKeyDataXmlWrite:
278  * @id:                 the data klass.
279  * @key:                the source key.
280  * @node:               the pointer to an XML node.
281  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
282  *
283  * Writes the key data of klass @id from @key to an XML @node.
284  *
285  * Returns: 0 on success or a negative value otherwise.
286  */
287 int
xmlSecKeyDataXmlWrite(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlNodePtr node,xmlSecKeyInfoCtxPtr keyInfoCtx)288 xmlSecKeyDataXmlWrite(xmlSecKeyDataId id, xmlSecKeyPtr key, xmlNodePtr node, xmlSecKeyInfoCtxPtr keyInfoCtx) {
289     xmlSecAssert2(id != NULL, -1);
290     xmlSecAssert2(id->xmlWrite != NULL, -1);
291     xmlSecAssert2(key != NULL, -1);
292     xmlSecAssert2(node != NULL, -1);
293 
294     return((id->xmlWrite)(id, key, node, keyInfoCtx));
295 }
296 
297 /**
298  * xmlSecKeyDataBinRead:
299  * @id:                 the data klass.
300  * @key:                the destination key.
301  * @buf:                the input binary buffer.
302  * @bufSize:            the input buffer size.
303  * @keyInfoCtx:         the <dsig:KeyInfo/> node processing context.
304  *
305  * Reads the key data of klass @id from binary buffer @buf to @key.
306  *
307  * Returns: 0 on success or a negative value if an error occurs.
308  */
309 int
xmlSecKeyDataBinRead(xmlSecKeyDataId id,xmlSecKeyPtr key,const xmlSecByte * buf,xmlSecSize bufSize,xmlSecKeyInfoCtxPtr keyInfoCtx)310 xmlSecKeyDataBinRead(xmlSecKeyDataId id, xmlSecKeyPtr key,
311                     const xmlSecByte* buf, xmlSecSize bufSize,
312                     xmlSecKeyInfoCtxPtr keyInfoCtx) {
313     xmlSecAssert2(id != NULL, -1);
314     xmlSecAssert2(id->binRead != NULL, -1);
315     xmlSecAssert2(key != NULL, -1);
316     xmlSecAssert2(buf != NULL, -1);
317 
318     return((id->binRead)(id, key, buf, bufSize, keyInfoCtx));
319 }
320 
321 /**
322  * xmlSecKeyDataBinWrite:
323  * @id:                 the data klass.
324  * @key:                the source key.
325  * @buf:                the output binary buffer.
326  * @bufSize:            the output buffer size.
327  * @keyInfoCtx:         the <dsig:KeyInfo/> node processing context.
328  *
329  * Writes the key data of klass @id from the @key to a binary buffer @buf.
330  *
331  * Returns: 0 on success or a negative value if an error occurs.
332  */
333 int
xmlSecKeyDataBinWrite(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlSecByte ** buf,xmlSecSize * bufSize,xmlSecKeyInfoCtxPtr keyInfoCtx)334 xmlSecKeyDataBinWrite(xmlSecKeyDataId id, xmlSecKeyPtr key,
335                     xmlSecByte** buf, xmlSecSize* bufSize,
336                     xmlSecKeyInfoCtxPtr keyInfoCtx) {
337     xmlSecAssert2(id != NULL, -1);
338     xmlSecAssert2(id->binWrite != NULL, -1);
339     xmlSecAssert2(key != NULL, -1);
340     xmlSecAssert2(buf != NULL, -1);
341 
342     return((id->binWrite)(id, key, buf, bufSize, keyInfoCtx));
343 }
344 
345 /**
346  * xmlSecKeyDataGenerate:
347  * @data:               the pointer to key data.
348  * @sizeBits:           the desired key data size (in bits).
349  * @type:               the desired key data type.
350  *
351  * Generates new key data of given size and type.
352  *
353  * Returns: 0 on success or a negative value otherwise.
354  */
355 int
xmlSecKeyDataGenerate(xmlSecKeyDataPtr data,xmlSecSize sizeBits,xmlSecKeyDataType type)356 xmlSecKeyDataGenerate(xmlSecKeyDataPtr data, xmlSecSize sizeBits,
357                       xmlSecKeyDataType type) {
358     int ret;
359 
360     xmlSecAssert2(xmlSecKeyDataIsValid(data), -1);
361     xmlSecAssert2(data->id->generate != NULL, -1);
362 
363     /* write data */
364     ret = data->id->generate(data, sizeBits, type);
365     if(ret < 0) {
366         xmlSecInternalError2("id->generate",
367                              xmlSecKeyDataGetName(data),
368                              "size=%d", sizeBits);
369         return(-1);
370     }
371     return(0);
372 }
373 
374 /**
375  * xmlSecKeyDataGetType:
376  * @data:               the pointer to key data.
377  *
378  * Gets key data type.
379  *
380  * Returns: key data type.
381  */
382 xmlSecKeyDataType
xmlSecKeyDataGetType(xmlSecKeyDataPtr data)383 xmlSecKeyDataGetType(xmlSecKeyDataPtr data) {
384     xmlSecAssert2(xmlSecKeyDataIsValid(data), xmlSecKeyDataTypeUnknown);
385     xmlSecAssert2(data->id->getType != NULL, xmlSecKeyDataTypeUnknown);
386 
387     return(data->id->getType(data));
388 }
389 
390 /**
391  * xmlSecKeyDataGetSize:
392  * @data:               the pointer to key data.
393  *
394  * Gets key data size.
395  *
396  * Returns: key data size (in bits).
397  */
398 xmlSecSize
xmlSecKeyDataGetSize(xmlSecKeyDataPtr data)399 xmlSecKeyDataGetSize(xmlSecKeyDataPtr data) {
400     xmlSecAssert2(xmlSecKeyDataIsValid(data), 0);
401     xmlSecAssert2(data->id->getSize != NULL, 0);
402 
403     return(data->id->getSize(data));
404 }
405 
406 /**
407  * xmlSecKeyDataGetIdentifier:
408  * @data:               the pointer to key data.
409  *
410  * Gets key data identifier string.
411  *
412  * Returns: key data id string.
413  */
414 const xmlChar*
xmlSecKeyDataGetIdentifier(xmlSecKeyDataPtr data)415 xmlSecKeyDataGetIdentifier(xmlSecKeyDataPtr data) {
416     xmlSecAssert2(xmlSecKeyDataIsValid(data), NULL);
417     xmlSecAssert2(data->id->getIdentifier != NULL, NULL);
418 
419     return(data->id->getIdentifier(data));
420 }
421 
422 /**
423  * xmlSecKeyDataDebugDump:
424  * @data:               the pointer to key data.
425  * @output:             the pointer to output FILE.
426  *
427  * Prints key data debug info.
428  */
429 void
xmlSecKeyDataDebugDump(xmlSecKeyDataPtr data,FILE * output)430 xmlSecKeyDataDebugDump(xmlSecKeyDataPtr data, FILE *output) {
431     xmlSecAssert(xmlSecKeyDataIsValid(data));
432     xmlSecAssert(data->id->debugDump != NULL);
433     xmlSecAssert(output != NULL);
434 
435     data->id->debugDump(data, output);
436 }
437 
438 /**
439  * xmlSecKeyDataDebugXmlDump:
440  * @data:               the pointer to key data.
441  * @output:             the pointer to output FILE.
442  *
443  * Prints key data debug info in XML format.
444  */
445 void
xmlSecKeyDataDebugXmlDump(xmlSecKeyDataPtr data,FILE * output)446 xmlSecKeyDataDebugXmlDump(xmlSecKeyDataPtr data, FILE *output) {
447     xmlSecAssert(xmlSecKeyDataIsValid(data));
448     xmlSecAssert(data->id->debugXmlDump != NULL);
449     xmlSecAssert(output != NULL);
450 
451     data->id->debugXmlDump(data, output);
452 }
453 
454 /**************************************************************************
455  *
456  * xmlSecKeyDataBinary methods
457  *
458  * key (xmlSecBuffer) is located after xmlSecKeyData structure
459  *
460  *************************************************************************/
461 /**
462  * xmlSecKeyDataBinaryValueInitialize:
463  * @data:               the pointer to binary key data.
464  *
465  * Initializes key data.
466  *
467  * Returns: 0 on success or a negative value otherwise.
468  */
469 int
xmlSecKeyDataBinaryValueInitialize(xmlSecKeyDataPtr data)470 xmlSecKeyDataBinaryValueInitialize(xmlSecKeyDataPtr data) {
471     xmlSecBufferPtr buffer;
472     int ret;
473 
474     xmlSecAssert2(xmlSecKeyDataIsValid(data), -1);
475     xmlSecAssert2(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize), -1);
476 
477     /* initialize buffer */
478     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
479     xmlSecAssert2(buffer != NULL, -1);
480 
481     ret = xmlSecBufferInitialize(buffer, 0);
482     if(ret < 0) {
483         xmlSecInternalError("xmlSecBufferInitialize",
484                             xmlSecKeyDataGetName(data));
485         return(-1);
486     }
487 
488     return(0);
489 }
490 
491 /**
492  * xmlSecKeyDataBinaryValueDuplicate:
493  * @dst:                the pointer to destination binary key data.
494  * @src:                the pointer to source binary key data.
495  *
496  * Copies binary key data from @src to @dst.
497  *
498  * Returns: 0 on success or a negative value otherwise.
499  */
500 int
xmlSecKeyDataBinaryValueDuplicate(xmlSecKeyDataPtr dst,xmlSecKeyDataPtr src)501 xmlSecKeyDataBinaryValueDuplicate(xmlSecKeyDataPtr dst, xmlSecKeyDataPtr src) {
502     xmlSecBufferPtr buffer;
503     int ret;
504 
505     xmlSecAssert2(xmlSecKeyDataIsValid(dst), -1);
506     xmlSecAssert2(xmlSecKeyDataCheckSize(dst, xmlSecKeyDataBinarySize), -1);
507     xmlSecAssert2(xmlSecKeyDataIsValid(src), -1);
508     xmlSecAssert2(xmlSecKeyDataCheckSize(src, xmlSecKeyDataBinarySize), -1);
509 
510     buffer = xmlSecKeyDataBinaryValueGetBuffer(src);
511     xmlSecAssert2(buffer != NULL, -1);
512 
513     /* copy data */
514     ret = xmlSecKeyDataBinaryValueSetBuffer(dst,
515                     xmlSecBufferGetData(buffer),
516                     xmlSecBufferGetSize(buffer));
517     if(ret < 0) {
518         xmlSecInternalError("xmlSecKeyDataBinaryValueSetBuffer",
519                             xmlSecKeyDataGetName(dst));
520         return(-1);
521     }
522 
523     return(0);
524 }
525 
526 /**
527  * xmlSecKeyDataBinaryValueFinalize:
528  * @data:               the pointer to binary key data.
529  *
530  * Cleans up binary key data.
531  */
532 void
xmlSecKeyDataBinaryValueFinalize(xmlSecKeyDataPtr data)533 xmlSecKeyDataBinaryValueFinalize(xmlSecKeyDataPtr data) {
534     xmlSecBufferPtr buffer;
535 
536     xmlSecAssert(xmlSecKeyDataIsValid(data));
537     xmlSecAssert(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize));
538 
539     /* initialize buffer */
540     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
541     xmlSecAssert(buffer != NULL);
542 
543     xmlSecBufferFinalize(buffer);
544 }
545 
546 /**
547  * xmlSecKeyDataBinaryValueXmlRead:
548  * @id:                 the data klass.
549  * @key:                the pointer to destination key.
550  * @node:               the pointer to an XML node.
551  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
552  *
553  * Reads binary key data from @node to the key by base64 decoding the @node content.
554  *
555  * Returns: 0 on success or a negative value otherwise.
556  */
557 int
xmlSecKeyDataBinaryValueXmlRead(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlNodePtr node,xmlSecKeyInfoCtxPtr keyInfoCtx)558 xmlSecKeyDataBinaryValueXmlRead(xmlSecKeyDataId id, xmlSecKeyPtr key,
559                                 xmlNodePtr node, xmlSecKeyInfoCtxPtr keyInfoCtx) {
560     xmlChar* str;
561     xmlSecSize len;
562     xmlSecKeyDataPtr data;
563     int ret;
564 
565     xmlSecAssert2(id != xmlSecKeyDataIdUnknown, -1);
566     xmlSecAssert2(key != NULL, -1);
567     xmlSecAssert2(node != NULL, -1);
568     xmlSecAssert2(keyInfoCtx != NULL, -1);
569 
570     str = xmlNodeGetContent(node);
571     if(str == NULL) {
572         xmlSecInvalidNodeContentError(node, xmlSecKeyDataKlassGetName(id), "empty");
573         return(-1);
574     }
575 
576     /* usual trick: decode into the same buffer */
577     ret = xmlSecBase64Decode(str, (xmlSecByte*)str, xmlStrlen(str));
578     if(ret < 0) {
579         xmlSecInternalError("xmlSecBase64Decode",
580                             xmlSecKeyDataKlassGetName(id));
581         xmlFree(str);
582         return(-1);
583     }
584     len = ret;
585 
586     /* check do we have a key already */
587     data = xmlSecKeyGetValue(key);
588     if(data != NULL) {
589         xmlSecBufferPtr buffer;
590 
591         if(!xmlSecKeyDataCheckId(data, id)) {
592             xmlSecOtherError2(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
593                               xmlSecKeyDataGetName(data),
594                               "id=%s",
595                               xmlSecErrorsSafeString(xmlSecKeyDataKlassGetName(id)));
596             xmlFree(str);
597             return(-1);
598         }
599 
600         buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
601         if((buffer != NULL) && (xmlSecBufferGetSize(buffer) != len)) {
602             xmlSecOtherError3(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
603                               xmlSecKeyDataGetName(data),
604                               "cur-data-size=%lu;new-data-size=%lu",
605                               (unsigned long)xmlSecBufferGetSize(buffer),
606                               (unsigned long)len);
607             xmlFree(str);
608             return(-1);
609         }
610         if((buffer != NULL) && (len > 0) && (memcmp(xmlSecBufferGetData(buffer), str, len) != 0)) {
611             xmlSecOtherError(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
612                              xmlSecKeyDataGetName(data),
613                              "key already has a different value");
614             xmlFree(str);
615             return(-1);
616         }
617         if(buffer != NULL) {
618             /* we already have exactly the same key */
619             xmlFree(str);
620             return(0);
621         }
622 
623         /* we have binary key value with empty buffer */
624     }
625 
626 
627     data = xmlSecKeyDataCreate(id);
628     if(data == NULL ) {
629         xmlSecInternalError("xmlSecKeyDataCreate",
630                             xmlSecKeyDataKlassGetName(id));
631         xmlFree(str);
632         return(-1);
633     }
634 
635     ret = xmlSecKeyDataBinaryValueSetBuffer(data, (xmlSecByte*)str, len);
636     if(ret < 0) {
637         xmlSecInternalError2("xmlSecKeyDataBinaryValueSetBuffer",
638                              xmlSecKeyDataKlassGetName(id),
639                              "size=%d", len);
640         xmlSecKeyDataDestroy(data);
641         xmlFree(str);
642         return(-1);
643     }
644     xmlFree(str);
645 
646     if(xmlSecKeyReqMatchKeyValue(&(keyInfoCtx->keyReq), data) != 1) {
647         xmlSecInternalError("xmlSecKeyReqMatchKeyValue",
648                             xmlSecKeyDataKlassGetName(id));
649         xmlSecKeyDataDestroy(data);
650         return(0);
651     }
652 
653     ret = xmlSecKeySetValue(key, data);
654     if(ret < 0) {
655         xmlSecInternalError("xmlSecKeySetValue",
656                             xmlSecKeyDataKlassGetName(id));
657         xmlSecKeyDataDestroy(data);
658         return(-1);
659     }
660 
661     return(0);
662 }
663 
664 /**
665  * xmlSecKeyDataBinaryValueXmlWrite:
666  * @id:                 the data klass.
667  * @key:                the pointer to source key.
668  * @node:               the pointer to an XML node.
669  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
670  *
671  * Base64 encodes binary key data of klass @id from the @key and
672  * sets to the @node content.
673  *
674  * Returns: 0 on success or a negative value otherwise.
675  */
676 int
xmlSecKeyDataBinaryValueXmlWrite(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlNodePtr node,xmlSecKeyInfoCtxPtr keyInfoCtx)677 xmlSecKeyDataBinaryValueXmlWrite(xmlSecKeyDataId id, xmlSecKeyPtr key,
678                             xmlNodePtr node, xmlSecKeyInfoCtxPtr keyInfoCtx) {
679     xmlSecBufferPtr buffer;
680     xmlSecKeyDataPtr value;
681     xmlChar* str;
682 
683     xmlSecAssert2(id != xmlSecKeyDataIdUnknown, -1);
684     xmlSecAssert2(key != NULL, -1);
685     xmlSecAssert2(node != NULL, -1);
686     xmlSecAssert2(keyInfoCtx != NULL, -1);
687 
688     if((xmlSecKeyDataTypeSymmetric & keyInfoCtx->keyReq.keyType) == 0) {
689         /* we can have only symmetric key */
690         return(0);
691     }
692 
693     value = xmlSecKeyGetValue(key);
694     xmlSecAssert2(xmlSecKeyDataIsValid(value), -1);
695 
696     buffer = xmlSecKeyDataBinaryValueGetBuffer(value);
697     xmlSecAssert2(buffer != NULL, -1);
698 
699     str = xmlSecBase64Encode(xmlSecBufferGetData(buffer),
700                              xmlSecBufferGetSize(buffer),
701                              keyInfoCtx->base64LineSize);
702     if(str == NULL) {
703         xmlSecInternalError("xmlSecBase64Encode",
704                             xmlSecKeyDataKlassGetName(id));
705         return(-1);
706     }
707     xmlNodeSetContent(node, str);
708     xmlFree(str);
709     return(0);
710 }
711 
712 /**
713  * xmlSecKeyDataBinaryValueBinRead:
714  * @id:                 the data klass.
715  * @key:                the pointer to destination key.
716  * @buf:                the source binary buffer.
717  * @bufSize:            the source binary buffer size.
718  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
719  *
720  * Reads binary key data of the klass @id from @buf to the @key.
721  *
722  * Returns: 0 on success or a negative value otherwise.
723  */
724 int
xmlSecKeyDataBinaryValueBinRead(xmlSecKeyDataId id,xmlSecKeyPtr key,const xmlSecByte * buf,xmlSecSize bufSize,xmlSecKeyInfoCtxPtr keyInfoCtx)725 xmlSecKeyDataBinaryValueBinRead(xmlSecKeyDataId id, xmlSecKeyPtr key,
726                                 const xmlSecByte* buf, xmlSecSize bufSize,
727                                 xmlSecKeyInfoCtxPtr keyInfoCtx) {
728     xmlSecKeyDataPtr data;
729     int ret;
730 
731     xmlSecAssert2(id != xmlSecKeyDataIdUnknown, -1);
732     xmlSecAssert2(key != NULL, -1);
733     xmlSecAssert2(buf != NULL, -1);
734     xmlSecAssert2(bufSize > 0, -1);
735     xmlSecAssert2(keyInfoCtx != NULL, -1);
736 
737     /* check do we have a key already */
738     data = xmlSecKeyGetValue(key);
739     if(data != NULL) {
740         xmlSecBufferPtr buffer;
741 
742         if(!xmlSecKeyDataCheckId(data, id)) {
743             xmlSecOtherError2(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
744                               xmlSecKeyDataGetName(data),
745                               "id=%s",
746                               xmlSecErrorsSafeString(xmlSecKeyDataKlassGetName(id)));
747             return(-1);
748         }
749 
750         buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
751         if((buffer != NULL) && (xmlSecBufferGetSize(buffer) != bufSize)) {
752             xmlSecOtherError3(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
753                               xmlSecKeyDataGetName(data),
754                               "cur-data-size=%lu;new-data-size=%lu",
755                               (unsigned long)xmlSecBufferGetSize(buffer),
756                               (unsigned long)bufSize);
757             return(-1);
758         }
759         if((buffer != NULL) && (bufSize > 0) && (memcmp(xmlSecBufferGetData(buffer), buf, bufSize) != 0)) {
760             xmlSecOtherError(XMLSEC_ERRORS_R_KEY_DATA_ALREADY_EXIST,
761                              xmlSecKeyDataGetName(data),
762                              "key already has a different value");
763             return(-1);
764         }
765         if(buffer != NULL) {
766             /* we already have exactly the same key */
767             return(0);
768         }
769 
770         /* we have binary key value with empty buffer */
771     }
772 
773     data = xmlSecKeyDataCreate(id);
774     if(data == NULL ) {
775         xmlSecInternalError("xmlSecKeyDataCreate",
776                             xmlSecKeyDataKlassGetName(id));
777         return(-1);
778     }
779 
780     ret = xmlSecKeyDataBinaryValueSetBuffer(data, buf, bufSize);
781     if(ret < 0) {
782         xmlSecInternalError2("xmlSecKeyDataBinaryValueSetBuffer",
783                              xmlSecKeyDataKlassGetName(id),
784                              "size=%d", bufSize);
785         xmlSecKeyDataDestroy(data);
786         return(-1);
787     }
788 
789     if(xmlSecKeyReqMatchKeyValue(&(keyInfoCtx->keyReq), data) != 1) {
790         xmlSecInternalError("xmlSecKeyReqMatchKeyValue",
791                             xmlSecKeyDataKlassGetName(id));
792         xmlSecKeyDataDestroy(data);
793         return(0);
794     }
795 
796     ret = xmlSecKeySetValue(key, data);
797     if(ret < 0) {
798         xmlSecInternalError("xmlSecKeySetValue",
799                             xmlSecKeyDataKlassGetName(id));
800         xmlSecKeyDataDestroy(data);
801         return(-1);
802     }
803 
804     return(0);
805 }
806 
807 /**
808  * xmlSecKeyDataBinaryValueBinWrite:
809  * @id:                 the data klass.
810  * @key:                the pointer to source key.
811  * @buf:                the destination binary buffer.
812  * @bufSize:            the destination binary buffer size.
813  * @keyInfoCtx:         the pointer to <dsig:KeyInfo/> element processing context.
814  *
815  * Writes binary key data of klass @id from the @key to @buf.
816  *
817  * Returns: 0 on success or a negative value otherwise.
818  */
819 int
xmlSecKeyDataBinaryValueBinWrite(xmlSecKeyDataId id,xmlSecKeyPtr key,xmlSecByte ** buf,xmlSecSize * bufSize,xmlSecKeyInfoCtxPtr keyInfoCtx)820 xmlSecKeyDataBinaryValueBinWrite(xmlSecKeyDataId id, xmlSecKeyPtr key,
821                                 xmlSecByte** buf, xmlSecSize* bufSize,
822                                 xmlSecKeyInfoCtxPtr keyInfoCtx) {
823     xmlSecKeyDataPtr value;
824     xmlSecBufferPtr buffer;
825 
826     xmlSecAssert2(id != xmlSecKeyDataIdUnknown, -1);
827     xmlSecAssert2(key != NULL, -1);
828     xmlSecAssert2(buf != NULL, -1);
829     xmlSecAssert2(bufSize != NULL, -1);
830     xmlSecAssert2(keyInfoCtx != NULL, -1);
831 
832     if((xmlSecKeyDataTypeSymmetric & keyInfoCtx->keyReq.keyType) == 0) {
833         /* we can have only symmetric key */
834         return(0);
835     }
836 
837     value = xmlSecKeyGetValue(key);
838     xmlSecAssert2(xmlSecKeyDataIsValid(value), -1);
839 
840     buffer = xmlSecKeyDataBinaryValueGetBuffer(key->value);
841     xmlSecAssert2(buffer != NULL, -1);
842 
843     (*bufSize) = xmlSecBufferGetSize(buffer);
844     (*buf) = (xmlSecByte*) xmlMalloc((*bufSize));
845     if((*buf) == NULL) {
846         xmlSecMallocError((*bufSize),
847                           xmlSecKeyDataKlassGetName(id));
848         return(-1);
849     }
850     memcpy((*buf), xmlSecBufferGetData(buffer), (*bufSize));
851     return(0);
852 }
853 
854 /**
855  * xmlSecKeyDataBinaryValueDebugDump:
856  * @data:               the pointer to binary key data.
857  * @output:             the pointer to output FILE.
858  *
859  * Prints binary key data debug information to @output.
860  */
861 void
xmlSecKeyDataBinaryValueDebugDump(xmlSecKeyDataPtr data,FILE * output)862 xmlSecKeyDataBinaryValueDebugDump(xmlSecKeyDataPtr data, FILE* output) {
863     xmlSecBufferPtr buffer;
864 
865     xmlSecAssert(xmlSecKeyDataIsValid(data));
866     xmlSecAssert(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize));
867     xmlSecAssert(data->id->dataNodeName != NULL);
868     xmlSecAssert(output != NULL);
869 
870     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
871     xmlSecAssert(buffer != NULL);
872 
873     /* print only size, everything else is sensitive */
874     fprintf(output, "=== %s: size=%d\n", data->id->dataNodeName,
875                                          xmlSecKeyDataGetSize(data));
876 }
877 
878 /**
879  * xmlSecKeyDataBinaryValueDebugXmlDump:
880  * @data:               the pointer to binary key data.
881  * @output:             the pointer to output FILE.
882  *
883  * Prints binary key data debug information to @output in XML format.
884  */
885 void
xmlSecKeyDataBinaryValueDebugXmlDump(xmlSecKeyDataPtr data,FILE * output)886 xmlSecKeyDataBinaryValueDebugXmlDump(xmlSecKeyDataPtr data, FILE* output) {
887     xmlSecBufferPtr buffer;
888 
889     xmlSecAssert(xmlSecKeyDataIsValid(data));
890     xmlSecAssert(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize));
891     xmlSecAssert(data->id->dataNodeName != NULL);
892     xmlSecAssert(output != NULL);
893 
894     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
895     xmlSecAssert(buffer != NULL);
896 
897     /* print only size, everything else is sensitive */
898     fprintf(output, "<%s size=\"%d\" />\n", data->id->dataNodeName,
899                                             xmlSecKeyDataGetSize(data));
900 }
901 
902 /**
903  * xmlSecKeyDataBinaryValueGetSize:
904  * @data:               the pointer to binary key data.
905  *
906  * Gets the binary key data size.
907  *
908  * Returns: binary key data size in bits.
909  */
910 xmlSecSize
xmlSecKeyDataBinaryValueGetSize(xmlSecKeyDataPtr data)911 xmlSecKeyDataBinaryValueGetSize(xmlSecKeyDataPtr data) {
912     xmlSecBufferPtr buffer;
913 
914     xmlSecAssert2(xmlSecKeyDataIsValid(data), 0);
915     xmlSecAssert2(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize), 0);
916 
917     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
918     xmlSecAssert2(buffer != NULL, 0);
919 
920     /* return size in bits */
921     return(8 * xmlSecBufferGetSize(buffer));
922 }
923 
924 /**
925  * xmlSecKeyDataBinaryValueGetBuffer:
926  * @data:               the pointer to binary key data.
927  *
928  * Gets the binary key data buffer.
929  *
930  * Returns: pointer to binary key data buffer.
931  */
932 xmlSecBufferPtr
xmlSecKeyDataBinaryValueGetBuffer(xmlSecKeyDataPtr data)933 xmlSecKeyDataBinaryValueGetBuffer(xmlSecKeyDataPtr data) {
934     xmlSecAssert2(xmlSecKeyDataIsValid(data), NULL);
935     xmlSecAssert2(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize), NULL);
936 
937     /* key (xmlSecBuffer) is located after xmlSecKeyData structure */
938     return((xmlSecBufferPtr)(((xmlSecByte*)data) + sizeof(xmlSecKeyData)));
939 }
940 
941 /**
942  * xmlSecKeyDataBinaryValueSetBuffer:
943  * @data:               the pointer to binary key data.
944  * @buf:                the pointer to binary buffer.
945  * @bufSize:            the binary buffer size.
946  *
947  * Sets the value of @data to @buf.
948  *
949  * Returns: 0 on success or a negative value otherwise.
950  */
951 int
xmlSecKeyDataBinaryValueSetBuffer(xmlSecKeyDataPtr data,const xmlSecByte * buf,xmlSecSize bufSize)952 xmlSecKeyDataBinaryValueSetBuffer(xmlSecKeyDataPtr data,
953                         const xmlSecByte* buf, xmlSecSize bufSize) {
954     xmlSecBufferPtr buffer;
955 
956     xmlSecAssert2(xmlSecKeyDataIsValid(data), -1);
957     xmlSecAssert2(xmlSecKeyDataCheckSize(data, xmlSecKeyDataBinarySize), -1);
958     xmlSecAssert2(buf != NULL, -1);
959     xmlSecAssert2(bufSize > 0, -1);
960 
961     buffer = xmlSecKeyDataBinaryValueGetBuffer(data);
962     xmlSecAssert2(buffer != NULL, -1);
963 
964     return(xmlSecBufferSetData(buffer, buf, bufSize));
965 }
966 
967 /***********************************************************************
968  *
969  * Keys Data list
970  *
971  **********************************************************************/
972 static xmlSecPtrListKlass xmlSecKeyDataListKlass = {
973     BAD_CAST "key-data-list",
974     (xmlSecPtrDuplicateItemMethod)xmlSecKeyDataDuplicate,       /* xmlSecPtrDuplicateItemMethod duplicateItem; */
975     (xmlSecPtrDestroyItemMethod)xmlSecKeyDataDestroy,           /* xmlSecPtrDestroyItemMethod destroyItem; */
976     (xmlSecPtrDebugDumpItemMethod)xmlSecKeyDataDebugDump,       /* xmlSecPtrDebugDumpItemMethod debugDumpItem; */
977     (xmlSecPtrDebugDumpItemMethod)xmlSecKeyDataDebugXmlDump,    /* xmlSecPtrDebugDumpItemMethod debugXmlDumpItem; */
978 };
979 
980 /**
981  * xmlSecKeyDataListGetKlass:
982  *
983  * The key data list klass.
984  *
985  * Returns: pointer to the key data list klass.
986  */
987 xmlSecPtrListId
xmlSecKeyDataListGetKlass(void)988 xmlSecKeyDataListGetKlass(void) {
989     return(&xmlSecKeyDataListKlass);
990 }
991 
992 
993 /***********************************************************************
994  *
995  * Keys Data Ids list
996  *
997  **********************************************************************/
998 static xmlSecPtrListKlass xmlSecKeyDataIdListKlass = {
999     BAD_CAST "key-data-ids-list",
1000     NULL,                                                       /* xmlSecPtrDuplicateItemMethod duplicateItem; */
1001     NULL,                                                       /* xmlSecPtrDestroyItemMethod destroyItem; */
1002     NULL,                                                       /* xmlSecPtrDebugDumpItemMethod debugDumpItem; */
1003     NULL,                                                       /* xmlSecPtrDebugDumpItemMethod debugXmlDumpItem; */
1004 };
1005 
1006 /**
1007  * xmlSecKeyDataIdListGetKlass:
1008  *
1009  * The key data id list klass.
1010  *
1011  * Returns: pointer to the key data id list klass.
1012  */
1013 xmlSecPtrListId
xmlSecKeyDataIdListGetKlass(void)1014 xmlSecKeyDataIdListGetKlass(void) {
1015     return(&xmlSecKeyDataIdListKlass);
1016 }
1017 
1018 /**
1019  * xmlSecKeyDataIdListFind:
1020  * @list:               the pointer to key data ids list.
1021  * @dataId:             the key data klass.
1022  *
1023  * Lookups @dataId in @list.
1024  *
1025  * Returns: 1 if @dataId is found in the @list, 0 if not and a negative
1026  * value if an error occurs.
1027  */
1028 int
xmlSecKeyDataIdListFind(xmlSecPtrListPtr list,xmlSecKeyDataId dataId)1029 xmlSecKeyDataIdListFind(xmlSecPtrListPtr list, xmlSecKeyDataId dataId) {
1030     xmlSecSize i, size;
1031 
1032     xmlSecAssert2(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId), 0);
1033     xmlSecAssert2(dataId != NULL, 0);
1034 
1035     size = xmlSecPtrListGetSize(list);
1036     for(i = 0; i < size; ++i) {
1037         if((xmlSecKeyDataId)xmlSecPtrListGetItem(list, i) == dataId) {
1038             return(1);
1039         }
1040     }
1041     return(0);
1042 }
1043 
1044 /**
1045  * xmlSecKeyDataIdListFindByNode:
1046  * @list:               the pointer to key data ids list.
1047  * @nodeName:           the desired key data klass XML node name.
1048  * @nodeNs:             the desired key data klass XML node namespace.
1049  * @usage:              the desired key data usage.
1050  *
1051  * Lookups data klass in the list with given @nodeName, @nodeNs and
1052  * @usage in the @list.
1053  *
1054  * Returns: key data klass is found and NULL otherwise.
1055  */
1056 xmlSecKeyDataId
xmlSecKeyDataIdListFindByNode(xmlSecPtrListPtr list,const xmlChar * nodeName,const xmlChar * nodeNs,xmlSecKeyDataUsage usage)1057 xmlSecKeyDataIdListFindByNode(xmlSecPtrListPtr list, const xmlChar* nodeName,
1058                             const xmlChar* nodeNs, xmlSecKeyDataUsage usage) {
1059     xmlSecKeyDataId dataId;
1060     xmlSecSize i, size;
1061 
1062     xmlSecAssert2(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId), xmlSecKeyDataIdUnknown);
1063     xmlSecAssert2(nodeName != NULL, xmlSecKeyDataIdUnknown);
1064 
1065     size = xmlSecPtrListGetSize(list);
1066     for(i = 0; i < size; ++i) {
1067         dataId = (xmlSecKeyDataId)xmlSecPtrListGetItem(list, i);
1068         xmlSecAssert2(dataId != xmlSecKeyDataIdUnknown, xmlSecKeyDataIdUnknown);
1069 
1070         if(((usage & dataId->usage) != 0) &&
1071            xmlStrEqual(nodeName, dataId->dataNodeName) &&
1072            xmlStrEqual(nodeNs, dataId->dataNodeNs)) {
1073 
1074            return(dataId);
1075         }
1076     }
1077     return(xmlSecKeyDataIdUnknown);
1078 }
1079 
1080 /**
1081  * xmlSecKeyDataIdListFindByHref:
1082  * @list:               the pointer to key data ids list.
1083  * @href:               the desired key data klass href.
1084  * @usage:              the desired key data usage.
1085  *
1086  * Lookups data klass in the list with given @href and @usage in @list.
1087  *
1088  * Returns: key data klass is found and NULL otherwise.
1089  */
1090 xmlSecKeyDataId
xmlSecKeyDataIdListFindByHref(xmlSecPtrListPtr list,const xmlChar * href,xmlSecKeyDataUsage usage)1091 xmlSecKeyDataIdListFindByHref(xmlSecPtrListPtr list, const xmlChar* href,
1092                             xmlSecKeyDataUsage usage) {
1093     xmlSecKeyDataId dataId;
1094     xmlSecSize i, size;
1095 
1096     xmlSecAssert2(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId), xmlSecKeyDataIdUnknown);
1097     xmlSecAssert2(href != NULL, xmlSecKeyDataIdUnknown);
1098 
1099     size = xmlSecPtrListGetSize(list);
1100     for(i = 0; i < size; ++i) {
1101         dataId = (xmlSecKeyDataId)xmlSecPtrListGetItem(list, i);
1102         xmlSecAssert2(dataId != xmlSecKeyDataIdUnknown, xmlSecKeyDataIdUnknown);
1103 
1104         if(((usage & dataId->usage) != 0) && (dataId->href != NULL) &&
1105            xmlStrEqual(href, dataId->href)) {
1106 
1107            return(dataId);
1108         }
1109     }
1110     return(xmlSecKeyDataIdUnknown);
1111 }
1112 
1113 /**
1114  * xmlSecKeyDataIdListFindByName:
1115  * @list:               the pointer to key data ids list.
1116  * @name:               the desired key data klass name.
1117  * @usage:              the desired key data usage.
1118  *
1119  * Lookups data klass in the list with given @name and @usage in @list.
1120  *
1121  * Returns: key data klass is found and NULL otherwise.
1122  */
1123 xmlSecKeyDataId
xmlSecKeyDataIdListFindByName(xmlSecPtrListPtr list,const xmlChar * name,xmlSecKeyDataUsage usage)1124 xmlSecKeyDataIdListFindByName(xmlSecPtrListPtr list, const xmlChar* name,
1125                             xmlSecKeyDataUsage usage) {
1126     xmlSecKeyDataId dataId;
1127     xmlSecSize i, size;
1128 
1129     xmlSecAssert2(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId), xmlSecKeyDataIdUnknown);
1130     xmlSecAssert2(name != NULL, xmlSecKeyDataIdUnknown);
1131 
1132     size = xmlSecPtrListGetSize(list);
1133     for(i = 0; i < size; ++i) {
1134         dataId = (xmlSecKeyDataId)xmlSecPtrListGetItem(list, i);
1135         xmlSecAssert2(dataId != xmlSecKeyDataIdUnknown, xmlSecKeyDataIdUnknown);
1136 
1137         if(((usage & dataId->usage) != 0) && (dataId->name != NULL) &&
1138            xmlStrEqual(name, BAD_CAST dataId->name)) {
1139 
1140            return(dataId);
1141         }
1142     }
1143     return(xmlSecKeyDataIdUnknown);
1144 }
1145 
1146 /**
1147  * xmlSecKeyDataIdListDebugDump:
1148  * @list:               the pointer to key data ids list.
1149  * @output:             the pointer to output FILE.
1150  *
1151  * Prints binary key data debug information to @output.
1152  */
1153 void
xmlSecKeyDataIdListDebugDump(xmlSecPtrListPtr list,FILE * output)1154 xmlSecKeyDataIdListDebugDump(xmlSecPtrListPtr list, FILE* output) {
1155     xmlSecKeyDataId dataId;
1156     xmlSecSize i, size;
1157 
1158     xmlSecAssert(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId));
1159     xmlSecAssert(output != NULL);
1160 
1161     size = xmlSecPtrListGetSize(list);
1162     for(i = 0; i < size; ++i) {
1163         dataId = (xmlSecKeyDataId)xmlSecPtrListGetItem(list, i);
1164         xmlSecAssert(dataId != NULL);
1165         xmlSecAssert(dataId->name != NULL);
1166 
1167         if(i > 0) {
1168             fprintf(output, ",\"%s\"", dataId->name);
1169         } else {
1170             fprintf(output, "\"%s\"", dataId->name);
1171         }
1172     }
1173     fprintf(output, "\n");
1174 }
1175 
1176 /**
1177  * xmlSecKeyDataIdListDebugXmlDump:
1178  * @list:               the pointer to key data ids list.
1179  * @output:             the pointer to output FILE.
1180  *
1181  * Prints binary key data debug information to @output in XML format.
1182  */
1183 void
xmlSecKeyDataIdListDebugXmlDump(xmlSecPtrListPtr list,FILE * output)1184 xmlSecKeyDataIdListDebugXmlDump(xmlSecPtrListPtr list, FILE* output) {
1185     xmlSecKeyDataId dataId;
1186     xmlSecSize i, size;
1187 
1188     xmlSecAssert(xmlSecPtrListCheckId(list, xmlSecKeyDataIdListId));
1189     xmlSecAssert(output != NULL);
1190 
1191     fprintf(output, "<KeyDataIdsList>\n");
1192     size = xmlSecPtrListGetSize(list);
1193     for(i = 0; i < size; ++i) {
1194         dataId = (xmlSecKeyDataId)xmlSecPtrListGetItem(list, i);
1195         xmlSecAssert(dataId != NULL);
1196         xmlSecAssert(dataId->name != NULL);
1197 
1198         fprintf(output, "<DataId name=\"");
1199         xmlSecPrintXmlString(output, dataId->name);
1200         fprintf(output, "\"/>");
1201     }
1202     fprintf(output, "</KeyDataIdsList>\n");
1203 }
1204 
1205 /**************************************************************************
1206  *
1207  * xmlSecKeyDataStore functions
1208  *
1209  *************************************************************************/
1210 /**
1211  * xmlSecKeyDataStoreCreate:
1212  * @id:                 the store id.
1213  *
1214  * Creates new key data store of the specified klass @id. Caller is responsible
1215  * for freeing returned object with #xmlSecKeyDataStoreDestroy function.
1216  *
1217  * Returns: the pointer to newly allocated key data store structure
1218  * or NULL if an error occurs.
1219  */
1220 xmlSecKeyDataStorePtr
xmlSecKeyDataStoreCreate(xmlSecKeyDataStoreId id)1221 xmlSecKeyDataStoreCreate(xmlSecKeyDataStoreId id)  {
1222     xmlSecKeyDataStorePtr store;
1223     int ret;
1224 
1225     xmlSecAssert2(id != NULL, NULL);
1226     xmlSecAssert2(id->objSize > 0, NULL);
1227 
1228     /* Allocate a new xmlSecKeyDataStore and fill the fields. */
1229     store = (xmlSecKeyDataStorePtr)xmlMalloc(id->objSize);
1230     if(store == NULL) {
1231         xmlSecMallocError(id->objSize,
1232                           xmlSecKeyDataStoreKlassGetName(id));
1233         return(NULL);
1234     }
1235     memset(store, 0, id->objSize);
1236     store->id = id;
1237 
1238     if(id->initialize != NULL) {
1239         ret = (id->initialize)(store);
1240         if(ret < 0) {
1241             xmlSecInternalError("id->initialize",
1242                                 xmlSecKeyDataStoreKlassGetName(id));
1243             xmlSecKeyDataStoreDestroy(store);
1244             return(NULL);
1245         }
1246     }
1247 
1248     return(store);
1249 }
1250 
1251 /**
1252  * xmlSecKeyDataStoreDestroy:
1253  * @store:              the pointer to the key data store..
1254  *
1255  * Destroys the key data store created with #xmlSecKeyDataStoreCreate
1256  * function.
1257  */
1258 void
xmlSecKeyDataStoreDestroy(xmlSecKeyDataStorePtr store)1259 xmlSecKeyDataStoreDestroy(xmlSecKeyDataStorePtr store) {
1260     xmlSecAssert(xmlSecKeyDataStoreIsValid(store));
1261     xmlSecAssert(store->id->objSize > 0);
1262 
1263     if(store->id->finalize != NULL) {
1264         (store->id->finalize)(store);
1265     }
1266     memset(store, 0, store->id->objSize);
1267     xmlFree(store);
1268 }
1269 
1270 /***********************************************************************
1271  *
1272  * Keys Data Store list
1273  *
1274  **********************************************************************/
1275 static xmlSecPtrListKlass xmlSecKeyDataStorePtrListKlass = {
1276     BAD_CAST "keys-data-store-list",
1277     NULL,                                                       /* xmlSecPtrDuplicateItemMethod duplicateItem; */
1278     (xmlSecPtrDestroyItemMethod)xmlSecKeyDataStoreDestroy,      /* xmlSecPtrDestroyItemMethod destroyItem; */
1279     NULL,                                                       /* xmlSecPtrDebugDumpItemMethod debugDumpItem; */
1280     NULL,                                                       /* xmlSecPtrDebugDumpItemMethod debugXmlDumpItem; */
1281 };
1282 
1283 /**
1284  * xmlSecKeyDataStorePtrListGetKlass:
1285  *
1286  * Key data stores list.
1287  *
1288  * Returns: key data stores list klass.
1289  */
1290 xmlSecPtrListId
xmlSecKeyDataStorePtrListGetKlass(void)1291 xmlSecKeyDataStorePtrListGetKlass(void) {
1292     return(&xmlSecKeyDataStorePtrListKlass);
1293 }
1294 
xmlSecImportSetPersistKey(void)1295 void xmlSecImportSetPersistKey(void) {
1296     xmlSecImportPersistKey = 1;
1297 }
1298 
xmlSecImportGetPersistKey(void)1299 int xmlSecImportGetPersistKey(void) {
1300     return xmlSecImportPersistKey;
1301 }
1302 
1303