Repair memory leaks in plpython.
[pgsql.git] / contrib / pgcrypto / openssl.c
blob448db331a0f1e7e2f4b14e0a547ce385f4100b69
1 /*
2 * openssl.c
3 * Wrapper for OpenSSL library.
5 * Copyright (c) 2001 Marko Kreen
6 * All rights reserved.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
29 * contrib/pgcrypto/openssl.c
32 #include "postgres.h"
34 #include <openssl/evp.h>
35 #include <openssl/err.h>
36 #include <openssl/rand.h>
38 #include "px.h"
39 #include "utils/memutils.h"
40 #include "utils/resowner.h"
43 * Max lengths we might want to handle.
45 #define MAX_KEY (512/8)
46 #define MAX_IV (128/8)
49 * Hashes
53 * To make sure we don't leak OpenSSL handles, we use the ResourceOwner
54 * mechanism to free them on abort.
56 typedef struct OSSLDigest
58 const EVP_MD *algo;
59 EVP_MD_CTX *ctx;
61 ResourceOwner owner;
62 } OSSLDigest;
64 /* ResourceOwner callbacks to hold OpenSSL digest handles */
65 static void ResOwnerReleaseOSSLDigest(Datum res);
67 static const ResourceOwnerDesc ossldigest_resowner_desc =
69 .name = "pgcrypto OpenSSL digest handle",
70 .release_phase = RESOURCE_RELEASE_BEFORE_LOCKS,
71 .release_priority = RELEASE_PRIO_FIRST,
72 .ReleaseResource = ResOwnerReleaseOSSLDigest,
73 .DebugPrint = NULL, /* default message is fine */
76 /* Convenience wrappers over ResourceOwnerRemember/Forget */
77 static inline void
78 ResourceOwnerRememberOSSLDigest(ResourceOwner owner, OSSLDigest *digest)
80 ResourceOwnerRemember(owner, PointerGetDatum(digest), &ossldigest_resowner_desc);
82 static inline void
83 ResourceOwnerForgetOSSLDigest(ResourceOwner owner, OSSLDigest *digest)
85 ResourceOwnerForget(owner, PointerGetDatum(digest), &ossldigest_resowner_desc);
88 static void
89 free_openssl_digest(OSSLDigest *digest)
91 EVP_MD_CTX_destroy(digest->ctx);
92 if (digest->owner != NULL)
93 ResourceOwnerForgetOSSLDigest(digest->owner, digest);
94 pfree(digest);
97 static unsigned
98 digest_result_size(PX_MD *h)
100 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
101 int result = EVP_MD_CTX_size(digest->ctx);
103 if (result < 0)
104 elog(ERROR, "EVP_MD_CTX_size() failed");
106 return result;
109 static unsigned
110 digest_block_size(PX_MD *h)
112 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
113 int result = EVP_MD_CTX_block_size(digest->ctx);
115 if (result < 0)
116 elog(ERROR, "EVP_MD_CTX_block_size() failed");
118 return result;
121 static void
122 digest_reset(PX_MD *h)
124 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
126 if (!EVP_DigestInit_ex(digest->ctx, digest->algo, NULL))
127 elog(ERROR, "EVP_DigestInit_ex() failed");
130 static void
131 digest_update(PX_MD *h, const uint8 *data, unsigned dlen)
133 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
135 if (!EVP_DigestUpdate(digest->ctx, data, dlen))
136 elog(ERROR, "EVP_DigestUpdate() failed");
139 static void
140 digest_finish(PX_MD *h, uint8 *dst)
142 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
144 if (!EVP_DigestFinal_ex(digest->ctx, dst, NULL))
145 elog(ERROR, "EVP_DigestFinal_ex() failed");
148 static void
149 digest_free(PX_MD *h)
151 OSSLDigest *digest = (OSSLDigest *) h->p.ptr;
153 free_openssl_digest(digest);
154 pfree(h);
157 /* PUBLIC functions */
160 px_find_digest(const char *name, PX_MD **res)
162 const EVP_MD *md;
163 EVP_MD_CTX *ctx;
164 PX_MD *h;
165 OSSLDigest *digest;
167 md = EVP_get_digestbyname(name);
168 if (md == NULL)
169 return PXE_NO_HASH;
171 ResourceOwnerEnlarge(CurrentResourceOwner);
174 * Create an OSSLDigest object, an OpenSSL MD object, and a PX_MD object.
175 * The order is crucial, to make sure we don't leak anything on
176 * out-of-memory or other error.
178 digest = MemoryContextAlloc(TopMemoryContext, sizeof(*digest));
180 ctx = EVP_MD_CTX_create();
181 if (!ctx)
183 pfree(digest);
184 return PXE_CIPHER_INIT;
186 if (EVP_DigestInit_ex(ctx, md, NULL) == 0)
188 EVP_MD_CTX_destroy(ctx);
189 pfree(digest);
190 return PXE_CIPHER_INIT;
193 digest->algo = md;
194 digest->ctx = ctx;
195 digest->owner = CurrentResourceOwner;
196 ResourceOwnerRememberOSSLDigest(digest->owner, digest);
198 /* The PX_MD object is allocated in the current memory context. */
199 h = palloc(sizeof(*h));
200 h->result_size = digest_result_size;
201 h->block_size = digest_block_size;
202 h->reset = digest_reset;
203 h->update = digest_update;
204 h->finish = digest_finish;
205 h->free = digest_free;
206 h->p.ptr = digest;
208 *res = h;
209 return 0;
212 /* ResourceOwner callbacks for OSSLDigest */
214 static void
215 ResOwnerReleaseOSSLDigest(Datum res)
217 OSSLDigest *digest = (OSSLDigest *) DatumGetPointer(res);
219 digest->owner = NULL;
220 free_openssl_digest(digest);
224 * Ciphers
226 * We use OpenSSL's EVP* family of functions for these.
230 * prototype for the EVP functions that return an algorithm, e.g.
231 * EVP_aes_128_cbc().
233 typedef const EVP_CIPHER *(*ossl_EVP_cipher_func) (void);
236 * ossl_cipher contains the static information about each cipher.
238 struct ossl_cipher
240 int (*init) (PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv);
241 ossl_EVP_cipher_func cipher_func;
242 int block_size;
243 int max_key_size;
247 * OSSLCipher contains the state for using a cipher. A separate OSSLCipher
248 * object is allocated in each px_find_cipher() call.
250 * To make sure we don't leak OpenSSL handles, we use the ResourceOwner
251 * mechanism to free them on abort.
253 typedef struct OSSLCipher
255 EVP_CIPHER_CTX *evp_ctx;
256 const EVP_CIPHER *evp_ciph;
257 uint8 key[MAX_KEY];
258 uint8 iv[MAX_IV];
259 unsigned klen;
260 unsigned init;
261 const struct ossl_cipher *ciph;
263 ResourceOwner owner;
264 } OSSLCipher;
266 /* ResourceOwner callbacks to hold OpenSSL cipher state */
267 static void ResOwnerReleaseOSSLCipher(Datum res);
269 static const ResourceOwnerDesc osslcipher_resowner_desc =
271 .name = "pgcrypto OpenSSL cipher handle",
272 .release_phase = RESOURCE_RELEASE_BEFORE_LOCKS,
273 .release_priority = RELEASE_PRIO_FIRST,
274 .ReleaseResource = ResOwnerReleaseOSSLCipher,
275 .DebugPrint = NULL, /* default message is fine */
278 /* Convenience wrappers over ResourceOwnerRemember/Forget */
279 static inline void
280 ResourceOwnerRememberOSSLCipher(ResourceOwner owner, OSSLCipher *od)
282 ResourceOwnerRemember(owner, PointerGetDatum(od), &osslcipher_resowner_desc);
284 static inline void
285 ResourceOwnerForgetOSSLCipher(ResourceOwner owner, OSSLCipher *od)
287 ResourceOwnerForget(owner, PointerGetDatum(od), &osslcipher_resowner_desc);
290 static void
291 free_openssl_cipher(OSSLCipher *od)
293 EVP_CIPHER_CTX_free(od->evp_ctx);
294 if (od->owner != NULL)
295 ResourceOwnerForgetOSSLCipher(od->owner, od);
296 pfree(od);
299 /* Common routines for all algorithms */
301 static unsigned
302 gen_ossl_block_size(PX_Cipher *c)
304 OSSLCipher *od = (OSSLCipher *) c->ptr;
306 return od->ciph->block_size;
309 static unsigned
310 gen_ossl_key_size(PX_Cipher *c)
312 OSSLCipher *od = (OSSLCipher *) c->ptr;
314 return od->ciph->max_key_size;
317 static unsigned
318 gen_ossl_iv_size(PX_Cipher *c)
320 unsigned ivlen;
321 OSSLCipher *od = (OSSLCipher *) c->ptr;
323 ivlen = od->ciph->block_size;
324 return ivlen;
327 static void
328 gen_ossl_free(PX_Cipher *c)
330 OSSLCipher *od = (OSSLCipher *) c->ptr;
332 free_openssl_cipher(od);
333 pfree(c);
336 static int
337 gen_ossl_decrypt(PX_Cipher *c, int padding, const uint8 *data, unsigned dlen,
338 uint8 *res, unsigned *rlen)
340 OSSLCipher *od = c->ptr;
341 int outlen,
342 outlen2;
344 if (!od->init)
346 if (!EVP_DecryptInit_ex(od->evp_ctx, od->evp_ciph, NULL, NULL, NULL))
347 return PXE_CIPHER_INIT;
348 if (!EVP_CIPHER_CTX_set_padding(od->evp_ctx, padding))
349 return PXE_CIPHER_INIT;
350 if (!EVP_CIPHER_CTX_set_key_length(od->evp_ctx, od->klen))
351 return PXE_CIPHER_INIT;
352 if (!EVP_DecryptInit_ex(od->evp_ctx, NULL, NULL, od->key, od->iv))
353 return PXE_CIPHER_INIT;
354 od->init = true;
357 if (!EVP_DecryptUpdate(od->evp_ctx, res, &outlen, data, dlen))
358 return PXE_DECRYPT_FAILED;
359 if (!EVP_DecryptFinal_ex(od->evp_ctx, res + outlen, &outlen2))
360 return PXE_DECRYPT_FAILED;
361 *rlen = outlen + outlen2;
363 return 0;
366 static int
367 gen_ossl_encrypt(PX_Cipher *c, int padding, const uint8 *data, unsigned dlen,
368 uint8 *res, unsigned *rlen)
370 OSSLCipher *od = c->ptr;
371 int outlen,
372 outlen2;
374 if (!od->init)
376 if (!EVP_EncryptInit_ex(od->evp_ctx, od->evp_ciph, NULL, NULL, NULL))
377 return PXE_CIPHER_INIT;
378 if (!EVP_CIPHER_CTX_set_padding(od->evp_ctx, padding))
379 return PXE_CIPHER_INIT;
380 if (!EVP_CIPHER_CTX_set_key_length(od->evp_ctx, od->klen))
381 return PXE_CIPHER_INIT;
382 if (!EVP_EncryptInit_ex(od->evp_ctx, NULL, NULL, od->key, od->iv))
383 return PXE_CIPHER_INIT;
384 od->init = true;
387 if (!EVP_EncryptUpdate(od->evp_ctx, res, &outlen, data, dlen))
388 return PXE_ENCRYPT_FAILED;
389 if (!EVP_EncryptFinal_ex(od->evp_ctx, res + outlen, &outlen2))
390 return PXE_ENCRYPT_FAILED;
391 *rlen = outlen + outlen2;
393 return 0;
396 /* Blowfish */
399 * Check if strong crypto is supported. Some OpenSSL installations
400 * support only short keys and unfortunately BF_set_key does not return any
401 * error value. This function tests if is possible to use strong key.
403 static int
404 bf_check_supported_key_len(void)
406 static const uint8 key[56] = {
407 0xf0, 0xe1, 0xd2, 0xc3, 0xb4, 0xa5, 0x96, 0x87, 0x78, 0x69,
408 0x5a, 0x4b, 0x3c, 0x2d, 0x1e, 0x0f, 0x00, 0x11, 0x22, 0x33,
409 0x44, 0x55, 0x66, 0x77, 0x04, 0x68, 0x91, 0x04, 0xc2, 0xfd,
410 0x3b, 0x2f, 0x58, 0x40, 0x23, 0x64, 0x1a, 0xba, 0x61, 0x76,
411 0x1f, 0x1f, 0x1f, 0x1f, 0x0e, 0x0e, 0x0e, 0x0e, 0xff, 0xff,
412 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
415 static const uint8 data[8] = {0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10};
416 static const uint8 res[8] = {0xc0, 0x45, 0x04, 0x01, 0x2e, 0x4e, 0x1f, 0x53};
417 uint8 out[8];
418 EVP_CIPHER_CTX *evp_ctx;
419 int outlen;
420 int status = 0;
422 /* encrypt with 448bits key and verify output */
423 evp_ctx = EVP_CIPHER_CTX_new();
424 if (!evp_ctx)
425 return 0;
426 if (!EVP_EncryptInit_ex(evp_ctx, EVP_bf_ecb(), NULL, NULL, NULL))
427 goto leave;
428 if (!EVP_CIPHER_CTX_set_key_length(evp_ctx, 56))
429 goto leave;
430 if (!EVP_EncryptInit_ex(evp_ctx, NULL, NULL, key, NULL))
431 goto leave;
433 if (!EVP_EncryptUpdate(evp_ctx, out, &outlen, data, 8))
434 goto leave;
436 if (memcmp(out, res, 8) != 0)
437 goto leave; /* Output does not match -> strong cipher is
438 * not supported */
439 status = 1;
441 leave:
442 EVP_CIPHER_CTX_free(evp_ctx);
443 return status;
446 static int
447 bf_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
449 OSSLCipher *od = c->ptr;
450 unsigned bs = gen_ossl_block_size(c);
451 static int bf_is_strong = -1;
454 * Test if key len is supported. BF_set_key silently cut large keys and it
455 * could be a problem when user transfer encrypted data from one server to
456 * another.
459 if (bf_is_strong == -1)
460 bf_is_strong = bf_check_supported_key_len();
462 if (!bf_is_strong && klen > 16)
463 return PXE_KEY_TOO_BIG;
465 /* Key len is supported. We can use it. */
466 od->klen = klen;
467 memcpy(od->key, key, klen);
469 if (iv)
470 memcpy(od->iv, iv, bs);
471 else
472 memset(od->iv, 0, bs);
473 return 0;
476 /* DES */
478 static int
479 ossl_des_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
481 OSSLCipher *od = c->ptr;
482 unsigned bs = gen_ossl_block_size(c);
484 od->klen = 8;
485 memset(od->key, 0, 8);
486 memcpy(od->key, key, klen > 8 ? 8 : klen);
488 if (iv)
489 memcpy(od->iv, iv, bs);
490 else
491 memset(od->iv, 0, bs);
492 return 0;
495 /* DES3 */
497 static int
498 ossl_des3_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
500 OSSLCipher *od = c->ptr;
501 unsigned bs = gen_ossl_block_size(c);
503 od->klen = 24;
504 memset(od->key, 0, 24);
505 memcpy(od->key, key, klen > 24 ? 24 : klen);
507 if (iv)
508 memcpy(od->iv, iv, bs);
509 else
510 memset(od->iv, 0, bs);
511 return 0;
514 /* CAST5 */
516 static int
517 ossl_cast_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
519 OSSLCipher *od = c->ptr;
520 unsigned bs = gen_ossl_block_size(c);
522 od->klen = klen;
523 memcpy(od->key, key, klen);
525 if (iv)
526 memcpy(od->iv, iv, bs);
527 else
528 memset(od->iv, 0, bs);
529 return 0;
532 /* AES */
534 static int
535 ossl_aes_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
537 OSSLCipher *od = c->ptr;
538 unsigned bs = gen_ossl_block_size(c);
540 if (klen <= 128 / 8)
541 od->klen = 128 / 8;
542 else if (klen <= 192 / 8)
543 od->klen = 192 / 8;
544 else if (klen <= 256 / 8)
545 od->klen = 256 / 8;
546 else
547 return PXE_KEY_TOO_BIG;
549 memcpy(od->key, key, klen);
551 if (iv)
552 memcpy(od->iv, iv, bs);
553 else
554 memset(od->iv, 0, bs);
556 return 0;
559 static int
560 ossl_aes_ecb_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
562 OSSLCipher *od = c->ptr;
563 int err;
565 err = ossl_aes_init(c, key, klen, iv);
566 if (err)
567 return err;
569 switch (od->klen)
571 case 128 / 8:
572 od->evp_ciph = EVP_aes_128_ecb();
573 break;
574 case 192 / 8:
575 od->evp_ciph = EVP_aes_192_ecb();
576 break;
577 case 256 / 8:
578 od->evp_ciph = EVP_aes_256_ecb();
579 break;
580 default:
581 /* shouldn't happen */
582 err = PXE_CIPHER_INIT;
583 break;
586 return err;
589 static int
590 ossl_aes_cbc_init(PX_Cipher *c, const uint8 *key, unsigned klen, const uint8 *iv)
592 OSSLCipher *od = c->ptr;
593 int err;
595 err = ossl_aes_init(c, key, klen, iv);
596 if (err)
597 return err;
599 switch (od->klen)
601 case 128 / 8:
602 od->evp_ciph = EVP_aes_128_cbc();
603 break;
604 case 192 / 8:
605 od->evp_ciph = EVP_aes_192_cbc();
606 break;
607 case 256 / 8:
608 od->evp_ciph = EVP_aes_256_cbc();
609 break;
610 default:
611 /* shouldn't happen */
612 err = PXE_CIPHER_INIT;
613 break;
616 return err;
620 * aliases
623 static PX_Alias ossl_aliases[] = {
624 {"bf", "bf-cbc"},
625 {"blowfish", "bf-cbc"},
626 {"blowfish-cbc", "bf-cbc"},
627 {"blowfish-ecb", "bf-ecb"},
628 {"blowfish-cfb", "bf-cfb"},
629 {"des", "des-cbc"},
630 {"3des", "des3-cbc"},
631 {"3des-ecb", "des3-ecb"},
632 {"3des-cbc", "des3-cbc"},
633 {"cast5", "cast5-cbc"},
634 {"aes", "aes-cbc"},
635 {"rijndael", "aes-cbc"},
636 {"rijndael-cbc", "aes-cbc"},
637 {"rijndael-ecb", "aes-ecb"},
638 {NULL}
641 static const struct ossl_cipher ossl_bf_cbc = {
642 bf_init,
643 EVP_bf_cbc,
644 64 / 8, 448 / 8
647 static const struct ossl_cipher ossl_bf_ecb = {
648 bf_init,
649 EVP_bf_ecb,
650 64 / 8, 448 / 8
653 static const struct ossl_cipher ossl_bf_cfb = {
654 bf_init,
655 EVP_bf_cfb,
656 64 / 8, 448 / 8
659 static const struct ossl_cipher ossl_des_ecb = {
660 ossl_des_init,
661 EVP_des_ecb,
662 64 / 8, 64 / 8
665 static const struct ossl_cipher ossl_des_cbc = {
666 ossl_des_init,
667 EVP_des_cbc,
668 64 / 8, 64 / 8
671 static const struct ossl_cipher ossl_des3_ecb = {
672 ossl_des3_init,
673 EVP_des_ede3_ecb,
674 64 / 8, 192 / 8
677 static const struct ossl_cipher ossl_des3_cbc = {
678 ossl_des3_init,
679 EVP_des_ede3_cbc,
680 64 / 8, 192 / 8
683 static const struct ossl_cipher ossl_cast_ecb = {
684 ossl_cast_init,
685 EVP_cast5_ecb,
686 64 / 8, 128 / 8
689 static const struct ossl_cipher ossl_cast_cbc = {
690 ossl_cast_init,
691 EVP_cast5_cbc,
692 64 / 8, 128 / 8
695 static const struct ossl_cipher ossl_aes_ecb = {
696 ossl_aes_ecb_init,
697 NULL, /* EVP_aes_XXX_ecb(), determined in init
698 * function */
699 128 / 8, 256 / 8
702 static const struct ossl_cipher ossl_aes_cbc = {
703 ossl_aes_cbc_init,
704 NULL, /* EVP_aes_XXX_cbc(), determined in init
705 * function */
706 128 / 8, 256 / 8
710 * Special handlers
712 struct ossl_cipher_lookup
714 const char *name;
715 const struct ossl_cipher *ciph;
718 static const struct ossl_cipher_lookup ossl_cipher_types[] = {
719 {"bf-cbc", &ossl_bf_cbc},
720 {"bf-ecb", &ossl_bf_ecb},
721 {"bf-cfb", &ossl_bf_cfb},
722 {"des-ecb", &ossl_des_ecb},
723 {"des-cbc", &ossl_des_cbc},
724 {"des3-ecb", &ossl_des3_ecb},
725 {"des3-cbc", &ossl_des3_cbc},
726 {"cast5-ecb", &ossl_cast_ecb},
727 {"cast5-cbc", &ossl_cast_cbc},
728 {"aes-ecb", &ossl_aes_ecb},
729 {"aes-cbc", &ossl_aes_cbc},
730 {NULL}
733 /* PUBLIC functions */
736 px_find_cipher(const char *name, PX_Cipher **res)
738 const struct ossl_cipher_lookup *i;
739 PX_Cipher *c = NULL;
740 EVP_CIPHER_CTX *ctx;
741 OSSLCipher *od;
743 name = px_resolve_alias(ossl_aliases, name);
744 for (i = ossl_cipher_types; i->name; i++)
745 if (strcmp(i->name, name) == 0)
746 break;
747 if (i->name == NULL)
748 return PXE_NO_CIPHER;
750 ResourceOwnerEnlarge(CurrentResourceOwner);
753 * Create an OSSLCipher object, an EVP_CIPHER_CTX object and a PX_Cipher.
754 * The order is crucial, to make sure we don't leak anything on
755 * out-of-memory or other error.
757 od = MemoryContextAllocZero(TopMemoryContext, sizeof(*od));
758 od->ciph = i->ciph;
760 /* Allocate an EVP_CIPHER_CTX object. */
761 ctx = EVP_CIPHER_CTX_new();
762 if (!ctx)
764 pfree(od);
765 return PXE_CIPHER_INIT;
768 od->evp_ctx = ctx;
769 od->owner = CurrentResourceOwner;
770 ResourceOwnerRememberOSSLCipher(od->owner, od);
772 if (i->ciph->cipher_func)
773 od->evp_ciph = i->ciph->cipher_func();
775 /* The PX_Cipher is allocated in current memory context */
776 c = palloc(sizeof(*c));
777 c->block_size = gen_ossl_block_size;
778 c->key_size = gen_ossl_key_size;
779 c->iv_size = gen_ossl_iv_size;
780 c->free = gen_ossl_free;
781 c->init = od->ciph->init;
782 c->encrypt = gen_ossl_encrypt;
783 c->decrypt = gen_ossl_decrypt;
784 c->ptr = od;
786 *res = c;
787 return 0;
790 /* ResourceOwner callbacks for OSSLCipher */
792 static void
793 ResOwnerReleaseOSSLCipher(Datum res)
795 free_openssl_cipher((OSSLCipher *) DatumGetPointer(res));