4 * This is free software; see Copyright file in the source
5 * distribution for preciese wording.
7 * Copyright (C) 2002-2003 Aleksey Sanin <aleksey@aleksey.com>
13 #include <gnutls/gnutls.h>
16 #include <xmlsec/xmlsec.h>
17 #include <xmlsec/keys.h>
18 #include <xmlsec/transforms.h>
19 #include <xmlsec/errors.h>
21 #include <xmlsec/gnutls/crypto.h>
23 /**************************************************************************
25 * Internal GnuTLS Block cipher CTX
27 *****************************************************************************/
28 typedef struct _xmlSecGnuTLSBlockCipherCtx xmlSecGnuTLSBlockCipherCtx,
29 *xmlSecGnuTLSBlockCipherCtxPtr;
30 struct _xmlSecGnuTLSBlockCipherCtx {
33 GcryCipherHd cipherCtx;
34 xmlSecKeyDataId keyId;
39 static int xmlSecGnuTLSBlockCipherCtxInit (xmlSecGnuTLSBlockCipherCtxPtr ctx,
43 const xmlChar* cipherName,
44 xmlSecTransformCtxPtr transformCtx);
45 static int xmlSecGnuTLSBlockCipherCtxUpdate (xmlSecGnuTLSBlockCipherCtxPtr ctx,
49 const xmlChar* cipherName,
50 xmlSecTransformCtxPtr transformCtx);
51 static int xmlSecGnuTLSBlockCipherCtxFinal (xmlSecGnuTLSBlockCipherCtxPtr ctx,
55 const xmlChar* cipherName,
56 xmlSecTransformCtxPtr transformCtx);
58 xmlSecGnuTLSBlockCipherCtxInit(xmlSecGnuTLSBlockCipherCtxPtr ctx,
59 xmlSecBufferPtr in, xmlSecBufferPtr out,
61 const xmlChar* cipherName,
62 xmlSecTransformCtxPtr transformCtx) {
66 xmlSecAssert2(ctx != NULL, -1);
67 xmlSecAssert2(ctx->cipher != 0, -1);
68 xmlSecAssert2(ctx->cipherCtx != NULL, -1);
69 xmlSecAssert2(ctx->keyInitialized != 0, -1);
70 xmlSecAssert2(ctx->ctxInitialized == 0, -1);
71 xmlSecAssert2(in != NULL, -1);
72 xmlSecAssert2(out != NULL, -1);
73 xmlSecAssert2(transformCtx != NULL, -1);
75 /* iv len == block len */
76 blockLen = gcry_cipher_get_algo_blklen(ctx->cipher);
77 xmlSecAssert2(blockLen > 0, -1);
83 /* allocate space for IV */
84 outSize = xmlSecBufferGetSize(out);
85 ret = xmlSecBufferSetSize(out, outSize + blockLen);
87 xmlSecError(XMLSEC_ERRORS_HERE,
88 xmlSecErrorsSafeString(cipherName),
89 "xmlSecBufferSetSize",
90 XMLSEC_ERRORS_R_XMLSEC_FAILED,
91 "size=%d", outSize + blockLen);
94 iv = xmlSecBufferGetData(out) + outSize;
96 /* generate and use random iv */
97 gcry_randomize(iv, blockLen, GCRY_STRONG_RANDOM);
98 ret = gcry_cipher_setiv(ctx->cipherCtx, iv, blockLen);
100 xmlSecError(XMLSEC_ERRORS_HERE,
101 xmlSecErrorsSafeString(cipherName),
103 XMLSEC_ERRORS_R_CRYPTO_FAILED,
108 /* if we don't have enough data, exit and hope that
109 * we'll have iv next time */
110 if(xmlSecBufferGetSize(in) < (xmlSecSize)blockLen) {
113 xmlSecAssert2(xmlSecBufferGetData(in) != NULL, -1);
116 ret = gcry_cipher_setiv(ctx->cipherCtx, xmlSecBufferGetData(in), blockLen);
118 xmlSecError(XMLSEC_ERRORS_HERE,
119 xmlSecErrorsSafeString(cipherName),
121 XMLSEC_ERRORS_R_CRYPTO_FAILED,
126 /* and remove from input */
127 ret = xmlSecBufferRemoveHead(in, blockLen);
129 xmlSecError(XMLSEC_ERRORS_HERE,
130 xmlSecErrorsSafeString(cipherName),
131 "xmlSecBufferRemoveHead",
132 XMLSEC_ERRORS_R_XMLSEC_FAILED,
133 "size=%d", blockLen);
138 ctx->ctxInitialized = 1;
143 xmlSecGnuTLSBlockCipherCtxUpdate(xmlSecGnuTLSBlockCipherCtxPtr ctx,
144 xmlSecBufferPtr in, xmlSecBufferPtr out,
146 const xmlChar* cipherName,
147 xmlSecTransformCtxPtr transformCtx) {
148 xmlSecSize inSize, inBlocks, outSize;
153 xmlSecAssert2(ctx != NULL, -1);
154 xmlSecAssert2(ctx->cipher != 0, -1);
155 xmlSecAssert2(ctx->cipherCtx != NULL, -1);
156 xmlSecAssert2(ctx->ctxInitialized != 0, -1);
157 xmlSecAssert2(in != NULL, -1);
158 xmlSecAssert2(out != NULL, -1);
159 xmlSecAssert2(transformCtx != NULL, -1);
161 blockLen = gcry_cipher_get_algo_blklen(ctx->cipher);
162 xmlSecAssert2(blockLen > 0, -1);
164 inSize = xmlSecBufferGetSize(in);
165 outSize = xmlSecBufferGetSize(out);
167 if(inSize < (xmlSecSize)blockLen) {
172 inBlocks = inSize / ((xmlSecSize)blockLen);
174 /* we want to have the last block in the input buffer
175 * for padding check */
176 inBlocks = (inSize - 1) / ((xmlSecSize)blockLen);
178 inSize = inBlocks * ((xmlSecSize)blockLen);
180 /* we write out the input size plus may be one block */
181 ret = xmlSecBufferSetMaxSize(out, outSize + inSize + blockLen);
183 xmlSecError(XMLSEC_ERRORS_HERE,
184 xmlSecErrorsSafeString(cipherName),
185 "xmlSecBufferSetMaxSize",
186 XMLSEC_ERRORS_R_XMLSEC_FAILED,
187 "size=%d", outSize + inSize + blockLen);
190 outBuf = xmlSecBufferGetData(out) + outSize;
193 ret = gcry_cipher_encrypt(ctx->cipherCtx, outBuf, inSize + blockLen,
194 xmlSecBufferGetData(in), inSize);
196 xmlSecError(XMLSEC_ERRORS_HERE,
197 xmlSecErrorsSafeString(cipherName),
198 "gcry_cipher_encrypt",
199 XMLSEC_ERRORS_R_CRYPTO_FAILED,
204 ret = gcry_cipher_decrypt(ctx->cipherCtx, outBuf, inSize + blockLen,
205 xmlSecBufferGetData(in), inSize);
207 xmlSecError(XMLSEC_ERRORS_HERE,
208 xmlSecErrorsSafeString(cipherName),
209 "gcry_cipher_decrypt",
210 XMLSEC_ERRORS_R_CRYPTO_FAILED,
216 /* set correct output buffer size */
217 ret = xmlSecBufferSetSize(out, outSize + inSize);
219 xmlSecError(XMLSEC_ERRORS_HERE,
220 xmlSecErrorsSafeString(cipherName),
221 "xmlSecBufferSetSize",
222 XMLSEC_ERRORS_R_XMLSEC_FAILED,
223 "size=%d", outSize + inSize);
227 /* remove the processed block from input */
228 ret = xmlSecBufferRemoveHead(in, inSize);
230 xmlSecError(XMLSEC_ERRORS_HERE,
231 xmlSecErrorsSafeString(cipherName),
232 "xmlSecBufferRemoveHead",
233 XMLSEC_ERRORS_R_XMLSEC_FAILED,
241 xmlSecGnuTLSBlockCipherCtxFinal(xmlSecGnuTLSBlockCipherCtxPtr ctx,
245 const xmlChar* cipherName,
246 xmlSecTransformCtxPtr transformCtx) {
247 xmlSecSize inSize, outSize;
248 int blockLen, outLen = 0;
253 xmlSecAssert2(ctx != NULL, -1);
254 xmlSecAssert2(ctx->cipher != 0, -1);
255 xmlSecAssert2(ctx->cipherCtx != NULL, -1);
256 xmlSecAssert2(ctx->ctxInitialized != 0, -1);
257 xmlSecAssert2(in != NULL, -1);
258 xmlSecAssert2(out != NULL, -1);
259 xmlSecAssert2(transformCtx != NULL, -1);
261 blockLen = gcry_cipher_get_algo_blklen(ctx->cipher);
262 xmlSecAssert2(blockLen > 0, -1);
264 inSize = xmlSecBufferGetSize(in);
265 outSize = xmlSecBufferGetSize(out);
268 xmlSecAssert2(inSize < (xmlSecSize)blockLen, -1);
271 ret = xmlSecBufferSetMaxSize(in, blockLen);
273 xmlSecError(XMLSEC_ERRORS_HERE,
274 xmlSecErrorsSafeString(cipherName),
275 "xmlSecBufferSetMaxSize",
276 XMLSEC_ERRORS_R_XMLSEC_FAILED,
277 "size=%d", blockLen);
280 inBuf = xmlSecBufferGetData(in);
282 /* create random padding */
283 if((xmlSecSize)blockLen > (inSize + 1)) {
284 gcry_randomize(inBuf + inSize, blockLen - inSize - 1,
285 GCRY_STRONG_RANDOM); /* as usual, we are paranoid */
287 inBuf[blockLen - 1] = blockLen - inSize;
290 if(inSize != (xmlSecSize)blockLen) {
291 xmlSecError(XMLSEC_ERRORS_HERE,
292 xmlSecErrorsSafeString(cipherName),
294 XMLSEC_ERRORS_R_INVALID_DATA,
295 "data=%d;block=%d", inSize, blockLen);
300 /* process last block */
301 ret = xmlSecBufferSetMaxSize(out, outSize + 2 * blockLen);
303 xmlSecError(XMLSEC_ERRORS_HERE,
304 xmlSecErrorsSafeString(cipherName),
305 "xmlSecBufferSetMaxSize",
306 XMLSEC_ERRORS_R_XMLSEC_FAILED,
307 "size=%d", outSize + 2 * blockLen);
310 outBuf = xmlSecBufferGetData(out) + outSize;
313 ret = gcry_cipher_encrypt(ctx->cipherCtx, outBuf, inSize + blockLen,
314 xmlSecBufferGetData(in), inSize);
316 xmlSecError(XMLSEC_ERRORS_HERE,
317 xmlSecErrorsSafeString(cipherName),
318 "gcry_cipher_encrypt",
319 XMLSEC_ERRORS_R_CRYPTO_FAILED,
324 ret = gcry_cipher_decrypt(ctx->cipherCtx, outBuf, inSize + blockLen,
325 xmlSecBufferGetData(in), inSize);
327 xmlSecError(XMLSEC_ERRORS_HERE,
328 xmlSecErrorsSafeString(cipherName),
329 "gcry_cipher_decrypt",
330 XMLSEC_ERRORS_R_CRYPTO_FAILED,
338 if(inSize < outBuf[blockLen - 1]) {
339 xmlSecError(XMLSEC_ERRORS_HERE,
340 xmlSecErrorsSafeString(cipherName),
342 XMLSEC_ERRORS_R_INVALID_DATA,
343 "padding=%d;buffer=%d",
344 outBuf[blockLen - 1], inSize);
347 outLen = inSize - outBuf[blockLen - 1];
352 /* set correct output buffer size */
353 ret = xmlSecBufferSetSize(out, outSize + outLen);
355 xmlSecError(XMLSEC_ERRORS_HERE,
356 xmlSecErrorsSafeString(cipherName),
357 "xmlSecBufferSetSize",
358 XMLSEC_ERRORS_R_XMLSEC_FAILED,
359 "size=%d", outSize + outLen);
363 /* remove the processed block from input */
364 ret = xmlSecBufferRemoveHead(in, inSize);
366 xmlSecError(XMLSEC_ERRORS_HERE,
367 xmlSecErrorsSafeString(cipherName),
368 "xmlSecBufferRemoveHead",
369 XMLSEC_ERRORS_R_XMLSEC_FAILED,
375 /* set correct output buffer size */
376 ret = xmlSecBufferSetSize(out, outSize + outLen);
378 xmlSecError(XMLSEC_ERRORS_HERE,
379 xmlSecErrorsSafeString(cipherName),
380 "xmlSecBufferSetSize",
381 XMLSEC_ERRORS_R_XMLSEC_FAILED,
382 "size=%d", outSize + outLen);
386 /* remove the processed block from input */
387 ret = xmlSecBufferRemoveHead(in, inSize);
389 xmlSecError(XMLSEC_ERRORS_HERE,
390 xmlSecErrorsSafeString(cipherName),
391 "xmlSecBufferRemoveHead",
392 XMLSEC_ERRORS_R_XMLSEC_FAILED,
401 /******************************************************************************
403 * Block Cipher transforms
405 * xmlSecGnuTLSBlockCipherCtx block is located after xmlSecTransform structure
407 *****************************************************************************/
408 #define xmlSecGnuTLSBlockCipherSize \
409 (sizeof(xmlSecTransform) + sizeof(xmlSecGnuTLSBlockCipherCtx))
410 #define xmlSecGnuTLSBlockCipherGetCtx(transform) \
411 ((xmlSecGnuTLSBlockCipherCtxPtr)(((xmlSecByte*)(transform)) + sizeof(xmlSecTransform)))
413 static int xmlSecGnuTLSBlockCipherInitialize (xmlSecTransformPtr transform);
414 static void xmlSecGnuTLSBlockCipherFinalize (xmlSecTransformPtr transform);
415 static int xmlSecGnuTLSBlockCipherSetKeyReq (xmlSecTransformPtr transform,
416 xmlSecKeyReqPtr keyReq);
417 static int xmlSecGnuTLSBlockCipherSetKey (xmlSecTransformPtr transform,
419 static int xmlSecGnuTLSBlockCipherExecute (xmlSecTransformPtr transform,
421 xmlSecTransformCtxPtr transformCtx);
422 static int xmlSecGnuTLSBlockCipherCheckId (xmlSecTransformPtr transform);
427 xmlSecGnuTLSBlockCipherCheckId(xmlSecTransformPtr transform) {
428 #ifndef XMLSEC_NO_DES
429 if(xmlSecTransformCheckId(transform, xmlSecGnuTLSTransformDes3CbcId)) {
432 #endif /* XMLSEC_NO_DES */
434 #ifndef XMLSEC_NO_AES
435 if(xmlSecTransformCheckId(transform, xmlSecGnuTLSTransformAes128CbcId) ||
436 xmlSecTransformCheckId(transform, xmlSecGnuTLSTransformAes192CbcId) ||
437 xmlSecTransformCheckId(transform, xmlSecGnuTLSTransformAes256CbcId)) {
441 #endif /* XMLSEC_NO_AES */
447 xmlSecGnuTLSBlockCipherInitialize(xmlSecTransformPtr transform) {
448 xmlSecGnuTLSBlockCipherCtxPtr ctx;
449 #ifndef XMLSEC_GNUTLS_OLD
451 #endif /* XMLSEC_GNUTLS_OLD */
453 xmlSecAssert2(xmlSecGnuTLSBlockCipherCheckId(transform), -1);
454 xmlSecAssert2(xmlSecTransformCheckSize(transform, xmlSecGnuTLSBlockCipherSize), -1);
456 ctx = xmlSecGnuTLSBlockCipherGetCtx(transform);
457 xmlSecAssert2(ctx != NULL, -1);
459 memset(ctx, 0, sizeof(xmlSecGnuTLSBlockCipherCtx));
461 #ifndef XMLSEC_NO_DES
462 if(transform->id == xmlSecGnuTLSTransformDes3CbcId) {
463 ctx->cipher = GCRY_CIPHER_3DES;
464 ctx->mode = GCRY_CIPHER_MODE_CBC;
465 ctx->keyId = xmlSecGnuTLSKeyDataDesId;
467 #endif /* XMLSEC_NO_DES */
469 #ifndef XMLSEC_NO_AES
470 if(transform->id == xmlSecGnuTLSTransformAes128CbcId) {
471 ctx->cipher = GCRY_CIPHER_AES128;
472 ctx->mode = GCRY_CIPHER_MODE_CBC;
473 ctx->keyId = xmlSecGnuTLSKeyDataAesId;
474 } else if(transform->id == xmlSecGnuTLSTransformAes192CbcId) {
475 ctx->cipher = GCRY_CIPHER_AES192;
476 ctx->mode = GCRY_CIPHER_MODE_CBC;
477 ctx->keyId = xmlSecGnuTLSKeyDataAesId;
478 } else if(transform->id == xmlSecGnuTLSTransformAes256CbcId) {
479 ctx->cipher = GCRY_CIPHER_AES256;
480 ctx->mode = GCRY_CIPHER_MODE_CBC;
481 ctx->keyId = xmlSecGnuTLSKeyDataAesId;
483 #endif /* XMLSEC_NO_AES */
486 xmlSecError(XMLSEC_ERRORS_HERE,
487 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
489 XMLSEC_ERRORS_R_INVALID_TRANSFORM,
490 XMLSEC_ERRORS_NO_MESSAGE);
494 #ifndef XMLSEC_GNUTLS_OLD
495 ret = gcry_cipher_open(&ctx->cipherCtx, ctx->cipher, ctx->mode, GCRY_CIPHER_SECURE); /* we are paranoid */
496 if(ret != GPG_ERR_NO_ERROR) {
497 #else /* XMLSEC_GNUTLS_OLD */
498 ctx->cipherCtx = gcry_cipher_open(ctx->cipher, ctx->mode, GCRY_CIPHER_SECURE); /* we are paranoid */
499 if(ctx->cipherCtx == NULL) {
500 #endif /* XMLSEC_GNUTLS_OLD */
501 xmlSecError(XMLSEC_ERRORS_HERE,
502 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
504 XMLSEC_ERRORS_R_CRYPTO_FAILED,
505 XMLSEC_ERRORS_NO_MESSAGE);
512 xmlSecGnuTLSBlockCipherFinalize(xmlSecTransformPtr transform) {
513 xmlSecGnuTLSBlockCipherCtxPtr ctx;
515 xmlSecAssert(xmlSecGnuTLSBlockCipherCheckId(transform));
516 xmlSecAssert(xmlSecTransformCheckSize(transform, xmlSecGnuTLSBlockCipherSize));
518 ctx = xmlSecGnuTLSBlockCipherGetCtx(transform);
519 xmlSecAssert(ctx != NULL);
521 if(ctx->cipherCtx != NULL) {
522 gcry_cipher_close(ctx->cipherCtx);
525 memset(ctx, 0, sizeof(xmlSecGnuTLSBlockCipherCtx));
529 xmlSecGnuTLSBlockCipherSetKeyReq(xmlSecTransformPtr transform, xmlSecKeyReqPtr keyReq) {
530 xmlSecGnuTLSBlockCipherCtxPtr ctx;
532 xmlSecAssert2(xmlSecGnuTLSBlockCipherCheckId(transform), -1);
533 xmlSecAssert2((transform->operation == xmlSecTransformOperationEncrypt) || (transform->operation == xmlSecTransformOperationDecrypt), -1);
534 xmlSecAssert2(xmlSecTransformCheckSize(transform, xmlSecGnuTLSBlockCipherSize), -1);
535 xmlSecAssert2(keyReq != NULL, -1);
537 ctx = xmlSecGnuTLSBlockCipherGetCtx(transform);
538 xmlSecAssert2(ctx != NULL, -1);
539 xmlSecAssert2(ctx->cipher != 0, -1);
540 xmlSecAssert2(ctx->keyId != NULL, -1);
542 keyReq->keyId = ctx->keyId;
543 keyReq->keyType = xmlSecKeyDataTypeSymmetric;
544 if(transform->operation == xmlSecTransformOperationEncrypt) {
545 keyReq->keyUsage = xmlSecKeyUsageEncrypt;
547 keyReq->keyUsage = xmlSecKeyUsageDecrypt;
550 keyReq->keyBitsSize = 8 * gcry_cipher_get_algo_keylen(ctx->cipher);
555 xmlSecGnuTLSBlockCipherSetKey(xmlSecTransformPtr transform, xmlSecKeyPtr key) {
556 xmlSecGnuTLSBlockCipherCtxPtr ctx;
557 xmlSecBufferPtr buffer;
561 xmlSecAssert2(xmlSecGnuTLSBlockCipherCheckId(transform), -1);
562 xmlSecAssert2((transform->operation == xmlSecTransformOperationEncrypt) || (transform->operation == xmlSecTransformOperationDecrypt), -1);
563 xmlSecAssert2(xmlSecTransformCheckSize(transform, xmlSecGnuTLSBlockCipherSize), -1);
564 xmlSecAssert2(key != NULL, -1);
566 ctx = xmlSecGnuTLSBlockCipherGetCtx(transform);
567 xmlSecAssert2(ctx != NULL, -1);
568 xmlSecAssert2(ctx->cipherCtx != NULL, -1);
569 xmlSecAssert2(ctx->cipher != 0, -1);
570 xmlSecAssert2(ctx->keyInitialized == 0, -1);
571 xmlSecAssert2(ctx->keyId != NULL, -1);
572 xmlSecAssert2(xmlSecKeyCheckId(key, ctx->keyId), -1);
574 keySize = gcry_cipher_get_algo_keylen(ctx->cipher);
575 xmlSecAssert2(keySize > 0, -1);
577 buffer = xmlSecKeyDataBinaryValueGetBuffer(xmlSecKeyGetValue(key));
578 xmlSecAssert2(buffer != NULL, -1);
580 if(xmlSecBufferGetSize(buffer) < keySize) {
581 xmlSecError(XMLSEC_ERRORS_HERE,
582 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
584 XMLSEC_ERRORS_R_INVALID_KEY_DATA_SIZE,
585 "keySize=%d;expected=%d",
586 xmlSecBufferGetSize(buffer), keySize);
590 xmlSecAssert2(xmlSecBufferGetData(buffer) != NULL, -1);
591 ret = gcry_cipher_setkey(ctx->cipherCtx, xmlSecBufferGetData(buffer), keySize);
593 xmlSecError(XMLSEC_ERRORS_HERE,
594 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
595 "gcry_cipher_setkey",
596 XMLSEC_ERRORS_R_CRYPTO_FAILED,
601 ctx->keyInitialized = 1;
606 xmlSecGnuTLSBlockCipherExecute(xmlSecTransformPtr transform, int last, xmlSecTransformCtxPtr transformCtx) {
607 xmlSecGnuTLSBlockCipherCtxPtr ctx;
608 xmlSecBufferPtr in, out;
611 xmlSecAssert2(xmlSecGnuTLSBlockCipherCheckId(transform), -1);
612 xmlSecAssert2((transform->operation == xmlSecTransformOperationEncrypt) || (transform->operation == xmlSecTransformOperationDecrypt), -1);
613 xmlSecAssert2(xmlSecTransformCheckSize(transform, xmlSecGnuTLSBlockCipherSize), -1);
614 xmlSecAssert2(transformCtx != NULL, -1);
616 in = &(transform->inBuf);
617 out = &(transform->outBuf);
619 ctx = xmlSecGnuTLSBlockCipherGetCtx(transform);
620 xmlSecAssert2(ctx != NULL, -1);
622 if(transform->status == xmlSecTransformStatusNone) {
623 transform->status = xmlSecTransformStatusWorking;
626 if(transform->status == xmlSecTransformStatusWorking) {
627 if(ctx->ctxInitialized == 0) {
628 ret = xmlSecGnuTLSBlockCipherCtxInit(ctx, in, out,
629 (transform->operation == xmlSecTransformOperationEncrypt) ? 1 : 0,
630 xmlSecTransformGetName(transform), transformCtx);
632 xmlSecError(XMLSEC_ERRORS_HERE,
633 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
634 "xmlSecGnuTLSBlockCipherCtxInit",
635 XMLSEC_ERRORS_R_XMLSEC_FAILED,
636 XMLSEC_ERRORS_NO_MESSAGE);
640 if((ctx->ctxInitialized == 0) && (last != 0)) {
641 xmlSecError(XMLSEC_ERRORS_HERE,
642 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
644 XMLSEC_ERRORS_R_INVALID_DATA,
645 "not enough data to initialize transform");
648 if(ctx->ctxInitialized != 0) {
649 ret = xmlSecGnuTLSBlockCipherCtxUpdate(ctx, in, out,
650 (transform->operation == xmlSecTransformOperationEncrypt) ? 1 : 0,
651 xmlSecTransformGetName(transform), transformCtx);
653 xmlSecError(XMLSEC_ERRORS_HERE,
654 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
655 "xmlSecGnuTLSBlockCipherCtxUpdate",
656 XMLSEC_ERRORS_R_XMLSEC_FAILED,
657 XMLSEC_ERRORS_NO_MESSAGE);
663 ret = xmlSecGnuTLSBlockCipherCtxFinal(ctx, in, out,
664 (transform->operation == xmlSecTransformOperationEncrypt) ? 1 : 0,
665 xmlSecTransformGetName(transform), transformCtx);
667 xmlSecError(XMLSEC_ERRORS_HERE,
668 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
669 "xmlSecGnuTLSBlockCipherCtxFinal",
670 XMLSEC_ERRORS_R_XMLSEC_FAILED,
671 XMLSEC_ERRORS_NO_MESSAGE);
674 transform->status = xmlSecTransformStatusFinished;
676 } else if(transform->status == xmlSecTransformStatusFinished) {
677 /* the only way we can get here is if there is no input */
678 xmlSecAssert2(xmlSecBufferGetSize(in) == 0, -1);
679 } else if(transform->status == xmlSecTransformStatusNone) {
680 /* the only way we can get here is if there is no enough data in the input */
681 xmlSecAssert2(last == 0, -1);
683 xmlSecError(XMLSEC_ERRORS_HERE,
684 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)),
686 XMLSEC_ERRORS_R_INVALID_STATUS,
687 "status=%d", transform->status);
695 #ifndef XMLSEC_NO_AES
696 /*********************************************************************
698 * AES CBC cipher transforms
700 ********************************************************************/
701 static xmlSecTransformKlass xmlSecGnuTLSAes128CbcKlass = {
702 /* klass/object sizes */
703 sizeof(xmlSecTransformKlass), /* xmlSecSize klassSize */
704 xmlSecGnuTLSBlockCipherSize, /* xmlSecSize objSize */
706 xmlSecNameAes128Cbc, /* const xmlChar* name; */
707 xmlSecHrefAes128Cbc, /* const xmlChar* href; */
708 xmlSecTransformUsageEncryptionMethod, /* xmlSecAlgorithmUsage usage; */
710 xmlSecGnuTLSBlockCipherInitialize, /* xmlSecTransformInitializeMethod initialize; */
711 xmlSecGnuTLSBlockCipherFinalize, /* xmlSecTransformFinalizeMethod finalize; */
712 NULL, /* xmlSecTransformNodeReadMethod readNode; */
713 NULL, /* xmlSecTransformNodeWriteMethod writeNode; */
714 xmlSecGnuTLSBlockCipherSetKeyReq, /* xmlSecTransformSetKeyMethod setKeyReq; */
715 xmlSecGnuTLSBlockCipherSetKey, /* xmlSecTransformSetKeyMethod setKey; */
716 NULL, /* xmlSecTransformValidateMethod validate; */
717 xmlSecTransformDefaultGetDataType, /* xmlSecTransformGetDataTypeMethod getDataType; */
718 xmlSecTransformDefaultPushBin, /* xmlSecTransformPushBinMethod pushBin; */
719 xmlSecTransformDefaultPopBin, /* xmlSecTransformPopBinMethod popBin; */
720 NULL, /* xmlSecTransformPushXmlMethod pushXml; */
721 NULL, /* xmlSecTransformPopXmlMethod popXml; */
722 xmlSecGnuTLSBlockCipherExecute, /* xmlSecTransformExecuteMethod execute; */
724 NULL, /* void* reserved0; */
725 NULL, /* void* reserved1; */
729 * xmlSecGnuTLSTransformAes128CbcGetKlass:
731 * AES 128 CBC encryption transform klass.
733 * Returns: pointer to AES 128 CBC encryption transform.
736 xmlSecGnuTLSTransformAes128CbcGetKlass(void) {
737 return(&xmlSecGnuTLSAes128CbcKlass);
740 static xmlSecTransformKlass xmlSecGnuTLSAes192CbcKlass = {
741 /* klass/object sizes */
742 sizeof(xmlSecTransformKlass), /* xmlSecSize klassSize */
743 xmlSecGnuTLSBlockCipherSize, /* xmlSecSize objSize */
745 xmlSecNameAes192Cbc, /* const xmlChar* name; */
746 xmlSecHrefAes192Cbc, /* const xmlChar* href; */
747 xmlSecTransformUsageEncryptionMethod, /* xmlSecAlgorithmUsage usage; */
749 xmlSecGnuTLSBlockCipherInitialize, /* xmlSecTransformInitializeMethod initialize; */
750 xmlSecGnuTLSBlockCipherFinalize, /* xmlSecTransformFinalizeMethod finalize; */
751 NULL, /* xmlSecTransformNodeReadMethod readNode; */
752 NULL, /* xmlSecTransformNodeWriteMethod writeNode; */
753 xmlSecGnuTLSBlockCipherSetKeyReq, /* xmlSecTransformSetKeyMethod setKeyReq; */
754 xmlSecGnuTLSBlockCipherSetKey, /* xmlSecTransformSetKeyMethod setKey; */
755 NULL, /* xmlSecTransformValidateMethod validate; */
756 xmlSecTransformDefaultGetDataType, /* xmlSecTransformGetDataTypeMethod getDataType; */
757 xmlSecTransformDefaultPushBin, /* xmlSecTransformPushBinMethod pushBin; */
758 xmlSecTransformDefaultPopBin, /* xmlSecTransformPopBinMethod popBin; */
759 NULL, /* xmlSecTransformPushXmlMethod pushXml; */
760 NULL, /* xmlSecTransformPopXmlMethod popXml; */
761 xmlSecGnuTLSBlockCipherExecute, /* xmlSecTransformExecuteMethod execute; */
763 NULL, /* void* reserved0; */
764 NULL, /* void* reserved1; */
768 * xmlSecGnuTLSTransformAes192CbcGetKlass:
770 * AES 192 CBC encryption transform klass.
772 * Returns: pointer to AES 192 CBC encryption transform.
775 xmlSecGnuTLSTransformAes192CbcGetKlass(void) {
776 return(&xmlSecGnuTLSAes192CbcKlass);
779 static xmlSecTransformKlass xmlSecGnuTLSAes256CbcKlass = {
780 /* klass/object sizes */
781 sizeof(xmlSecTransformKlass), /* xmlSecSize klassSize */
782 xmlSecGnuTLSBlockCipherSize, /* xmlSecSize objSize */
784 xmlSecNameAes256Cbc, /* const xmlChar* name; */
785 xmlSecHrefAes256Cbc, /* const xmlChar* href; */
786 xmlSecTransformUsageEncryptionMethod, /* xmlSecAlgorithmUsage usage; */
788 xmlSecGnuTLSBlockCipherInitialize, /* xmlSecTransformInitializeMethod initialize; */
789 xmlSecGnuTLSBlockCipherFinalize, /* xmlSecTransformFinalizeMethod finalize; */
790 NULL, /* xmlSecTransformNodeReadMethod readNode; */
791 NULL, /* xmlSecTransformNodeWriteMethod writeNode; */
792 xmlSecGnuTLSBlockCipherSetKeyReq, /* xmlSecTransformSetKeyMethod setKeyReq; */
793 xmlSecGnuTLSBlockCipherSetKey, /* xmlSecTransformSetKeyMethod setKey; */
794 NULL, /* xmlSecTransformValidateMethod validate; */
795 xmlSecTransformDefaultGetDataType, /* xmlSecTransformGetDataTypeMethod getDataType; */
796 xmlSecTransformDefaultPushBin, /* xmlSecTransformPushBinMethod pushBin; */
797 xmlSecTransformDefaultPopBin, /* xmlSecTransformPopBinMethod popBin; */
798 NULL, /* xmlSecTransformPushXmlMethod pushXml; */
799 NULL, /* xmlSecTransformPopXmlMethod popXml; */
800 xmlSecGnuTLSBlockCipherExecute, /* xmlSecTransformExecuteMethod execute; */
802 NULL, /* void* reserved0; */
803 NULL, /* void* reserved1; */
807 * xmlSecGnuTLSTransformAes256CbcGetKlass:
809 * AES 256 CBC encryption transform klass.
811 * Returns: pointer to AES 256 CBC encryption transform.
814 xmlSecGnuTLSTransformAes256CbcGetKlass(void) {
815 return(&xmlSecGnuTLSAes256CbcKlass);
818 #endif /* XMLSEC_NO_AES */
820 #ifndef XMLSEC_NO_DES
821 static xmlSecTransformKlass xmlSecGnuTLSDes3CbcKlass = {
822 /* klass/object sizes */
823 sizeof(xmlSecTransformKlass), /* xmlSecSize klassSize */
824 xmlSecGnuTLSBlockCipherSize, /* xmlSecSize objSize */
826 xmlSecNameDes3Cbc, /* const xmlChar* name; */
827 xmlSecHrefDes3Cbc, /* const xmlChar* href; */
828 xmlSecTransformUsageEncryptionMethod, /* xmlSecAlgorithmUsage usage; */
830 xmlSecGnuTLSBlockCipherInitialize, /* xmlSecTransformInitializeMethod initialize; */
831 xmlSecGnuTLSBlockCipherFinalize, /* xmlSecTransformFinalizeMethod finalize; */
832 NULL, /* xmlSecTransformNodeReadMethod readNode; */
833 NULL, /* xmlSecTransformNodeWriteMethod writeNode; */
834 xmlSecGnuTLSBlockCipherSetKeyReq, /* xmlSecTransformSetKeyMethod setKeyReq; */
835 xmlSecGnuTLSBlockCipherSetKey, /* xmlSecTransformSetKeyMethod setKey; */
836 NULL, /* xmlSecTransformValidateMethod validate; */
837 xmlSecTransformDefaultGetDataType, /* xmlSecTransformGetDataTypeMethod getDataType; */
838 xmlSecTransformDefaultPushBin, /* xmlSecTransformPushBinMethod pushBin; */
839 xmlSecTransformDefaultPopBin, /* xmlSecTransformPopBinMethod popBin; */
840 NULL, /* xmlSecTransformPushXmlMethod pushXml; */
841 NULL, /* xmlSecTransformPopXmlMethod popXml; */
842 xmlSecGnuTLSBlockCipherExecute, /* xmlSecTransformExecuteMethod execute; */
844 NULL, /* void* reserved0; */
845 NULL, /* void* reserved1; */
849 * xmlSecGnuTLSTransformDes3CbcGetKlass:
851 * Triple DES CBC encryption transform klass.
853 * Returns: pointer to Triple DES encryption transform.
856 xmlSecGnuTLSTransformDes3CbcGetKlass(void) {
857 return(&xmlSecGnuTLSDes3CbcKlass);
859 #endif /* XMLSEC_NO_DES */