2 * Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
3 * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
5 * Licensed under the Apache License 2.0 (the "License"). You may not use
6 * this file except in compliance with the License. You can obtain a copy
7 * in the file LICENSE in the source distribution or at
8 * https://www.openssl.org/source/license.html
12 #include <openssl/params.h>
13 #include "internal/thread_once.h"
15 #define SET_RETURN_SIZE(p, sz) \
16 if ((p)->return_size != NULL) \
17 *(p)->return_size = (sz)
19 const OSSL_PARAM *OSSL_PARAM_locate(const OSSL_PARAM *p, const char *key)
21 if (p != NULL && key != NULL)
22 for (; p->key != NULL; p++)
23 if (strcmp(key, p->key) == 0)
28 static OSSL_PARAM ossl_param_construct(const char *key, unsigned int data_type,
29 void *data, size_t data_size,
35 res.data_type = data_type;
37 res.data_size = data_size;
38 res.return_size = return_size;
42 int OSSL_PARAM_get_int(const OSSL_PARAM *p, int *val)
44 if (val == NULL || p == NULL || p->data_type != OSSL_PARAM_INTEGER)
47 switch (p->data_size) {
49 if (sizeof(int) >= sizeof(int32_t)) {
50 *val = (int)*(const int32_t *)p->data;
55 if (sizeof(int) >= sizeof(int64_t)) {
56 *val = (int)*(const int64_t *)p->data;
64 int OSSL_PARAM_set_int(const OSSL_PARAM *p, int val)
68 SET_RETURN_SIZE(p, 0);
69 if (p->data_type != OSSL_PARAM_INTEGER)
72 SET_RETURN_SIZE(p, sizeof(int)); /* Minimum expected size */
73 switch (p->data_size) {
75 if (sizeof(int32_t) >= sizeof(int)) {
76 SET_RETURN_SIZE(p, sizeof(int32_t));
77 *(int32_t *)p->data = (int32_t)val;
82 if (sizeof(int64_t) >= sizeof(int)) {
83 SET_RETURN_SIZE(p, sizeof(int64_t));
84 *(int64_t *)p->data = (int64_t)val;
92 OSSL_PARAM OSSL_PARAM_construct_int(const char *key, int *buf, size_t *rsize)
94 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(int),
98 int OSSL_PARAM_get_uint(const OSSL_PARAM *p, unsigned int *val)
102 || (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
105 switch (p->data_size) {
106 case sizeof(uint32_t):
107 if (sizeof(unsigned int) >= sizeof(uint32_t)) {
108 *val = (unsigned int)*(const uint32_t *)p->data;
112 case sizeof(uint64_t):
113 if (sizeof(unsigned int) >= sizeof(uint64_t)) {
114 *val = (unsigned int)*(const uint64_t *)p->data;
122 int OSSL_PARAM_set_uint(const OSSL_PARAM *p, unsigned int val)
126 SET_RETURN_SIZE(p, 0);
127 if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
130 SET_RETURN_SIZE(p, sizeof(unsigned int)); /* Minimum expected size */
131 switch (p->data_size) {
132 case sizeof(uint32_t):
133 if (sizeof(uint32_t) >= sizeof(unsigned int)) {
134 SET_RETURN_SIZE(p, sizeof(uint32_t));
135 *(uint32_t *)p->data = (uint32_t)val;
139 case sizeof(uint64_t):
140 if (sizeof(uint64_t) >= sizeof(unsigned int)) {
141 SET_RETURN_SIZE(p, sizeof(uint64_t));
142 *(uint64_t *)p->data = (uint64_t)val;
150 OSSL_PARAM OSSL_PARAM_construct_uint(const char *key, unsigned int *buf,
153 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
154 sizeof(unsigned int), rsize);
157 int OSSL_PARAM_get_long(const OSSL_PARAM *p, long int *val)
159 if (val == NULL || p == NULL || (p->data_type != OSSL_PARAM_INTEGER))
162 switch (p->data_size) {
163 case sizeof(int32_t):
164 if (sizeof(long int) >= sizeof(int32_t)) {
165 *val = (long int)*(const int32_t *)p->data;
168 case sizeof(int64_t):
169 if (sizeof(long int) >= sizeof(int64_t)) {
170 *val = (long int)*(const int64_t *)p->data;
178 int OSSL_PARAM_set_long(const OSSL_PARAM *p, long int val)
182 SET_RETURN_SIZE(p, 0);
183 if (p->data_type != OSSL_PARAM_INTEGER)
186 SET_RETURN_SIZE(p, sizeof(long int)); /* Minimum expected size */
187 switch (p->data_size) {
188 case sizeof(int32_t):
189 if (sizeof(int32_t) >= sizeof(long int)) {
190 SET_RETURN_SIZE(p, sizeof(int32_t));
191 *(int32_t *)p->data = (int32_t)val;
195 case sizeof(int64_t):
196 if (sizeof(int64_t) >= sizeof(long int)) {
197 SET_RETURN_SIZE(p, sizeof(int64_t));
198 *(int64_t *)p->data = (int64_t)val;
206 OSSL_PARAM OSSL_PARAM_construct_long(const char *key, long int *buf,
209 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(long int),
213 int OSSL_PARAM_get_ulong(const OSSL_PARAM *p, unsigned long int *val)
217 || (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
220 switch (p->data_size) {
221 case sizeof(uint32_t):
222 if (sizeof(unsigned long int) >= sizeof(uint32_t)) {
223 *val = (unsigned long int)*(const uint32_t *)p->data;
227 case sizeof(uint64_t):
228 if (sizeof(unsigned long int) >= sizeof(uint64_t)) {
229 *val = (unsigned long int)*(const uint64_t *)p->data;
237 int OSSL_PARAM_set_ulong(const OSSL_PARAM *p, unsigned long int val)
241 SET_RETURN_SIZE(p, 0);
242 if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
245 SET_RETURN_SIZE(p, sizeof(unsigned long int)); /* Minimum exp size */
246 switch (p->data_size) {
247 case sizeof(uint32_t):
248 if (sizeof(uint32_t) >= sizeof(unsigned long int)) {
249 SET_RETURN_SIZE(p, sizeof(uint32_t));
250 *(uint32_t *)p->data = (uint32_t)val;
254 case sizeof(uint64_t):
255 if (sizeof(uint64_t) >= sizeof(unsigned long int)) {
256 SET_RETURN_SIZE(p, sizeof(uint64_t));
257 *(uint64_t *)p->data = (uint64_t)val;
265 OSSL_PARAM OSSL_PARAM_construct_ulong(const char *key, unsigned long int *buf,
268 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
269 sizeof(unsigned long int), rsize);
272 int OSSL_PARAM_get_int32(const OSSL_PARAM *p, int32_t *val)
274 if (val == NULL || p == NULL || (p->data_type != OSSL_PARAM_INTEGER))
277 if (p->data_size == sizeof(int32_t)) {
278 *val = *(const int32_t *)p->data;
284 int OSSL_PARAM_set_int32(const OSSL_PARAM *p, int32_t val)
288 SET_RETURN_SIZE(p, 0);
289 if (p->data_type != OSSL_PARAM_INTEGER)
292 SET_RETURN_SIZE(p, sizeof(int32_t)); /* Minimum expected size */
293 switch (p->data_size) {
294 case sizeof(int32_t):
295 SET_RETURN_SIZE(p, sizeof(int32_t));
296 *(int32_t *)p->data = val;
298 case sizeof(int64_t):
299 SET_RETURN_SIZE(p, sizeof(int64_t));
300 *(int64_t *)p->data = (int64_t)val;
306 OSSL_PARAM OSSL_PARAM_construct_int32(const char *key, int32_t *buf,
309 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf,
310 sizeof(int32_t), rsize);
313 int OSSL_PARAM_get_uint32(const OSSL_PARAM *p, uint32_t *val)
317 || (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
320 if (p->data_size == sizeof(uint32_t)) {
321 *val = *(const uint32_t *)p->data;
327 int OSSL_PARAM_set_uint32(const OSSL_PARAM *p, uint32_t val)
329 if (p == NULL) return 0;
330 SET_RETURN_SIZE(p, 0);
331 if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
334 SET_RETURN_SIZE(p, sizeof(uint32_t)); /* Minimum expected size */
335 switch (p->data_size) {
336 case sizeof(uint32_t):
337 SET_RETURN_SIZE(p, sizeof(uint32_t));
338 *(uint32_t *)p->data = val;
340 case sizeof(uint64_t):
341 SET_RETURN_SIZE(p, sizeof(uint64_t));
342 *(uint64_t *)p->data = (uint64_t)val;
348 OSSL_PARAM OSSL_PARAM_construct_uint32(const char *key, uint32_t *buf,
351 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
352 sizeof(uint32_t), rsize);
355 int OSSL_PARAM_get_int64(const OSSL_PARAM *p, int64_t *val)
357 if (val == NULL || p == NULL || (p->data_type != OSSL_PARAM_INTEGER))
360 switch (p->data_size) {
361 case sizeof(int32_t):
362 *val = (int64_t)*(const int32_t *)p->data;
364 case sizeof(int64_t):
365 *val = *(const int64_t *)p->data;
371 int OSSL_PARAM_set_int64(const OSSL_PARAM *p, int64_t val)
375 SET_RETURN_SIZE(p, 0);
376 if (p->data_type != OSSL_PARAM_INTEGER)
379 SET_RETURN_SIZE(p, sizeof(int64_t)); /* Minimum expected size */
380 switch (p->data_size) {
381 case sizeof(int64_t):
382 SET_RETURN_SIZE(p, sizeof(int64_t));
383 *(int64_t *)p->data = val;
389 OSSL_PARAM OSSL_PARAM_construct_int64(const char *key, int64_t *buf,
392 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(int64_t),
396 int OSSL_PARAM_get_uint64(const OSSL_PARAM *p, uint64_t *val)
400 || (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
403 switch (p->data_size) {
404 case sizeof(uint32_t):
405 *val = (uint64_t)*(const uint32_t *)p->data;
407 case sizeof(uint64_t):
408 *val = *(const uint64_t *)p->data;
414 int OSSL_PARAM_set_uint64(const OSSL_PARAM *p, uint64_t val)
418 SET_RETURN_SIZE(p, 0);
419 if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
422 SET_RETURN_SIZE(p, sizeof(uint64_t)); /* Minimum expected size */
423 switch (p->data_size) {
424 case sizeof(uint64_t):
425 SET_RETURN_SIZE(p, sizeof(uint64_t));
426 *(uint64_t *)p->data = val;
432 OSSL_PARAM OSSL_PARAM_construct_uint64(const char *key, uint64_t *buf,
434 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
435 sizeof(uint64_t), rsize);
438 int OSSL_PARAM_get_size_t(const OSSL_PARAM *p, size_t *val)
442 || p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
445 switch (p->data_size) {
446 case sizeof(uint32_t):
447 if (sizeof(size_t) >= sizeof(uint32_t)) {
448 *val = (size_t)*(const uint32_t *)p->data;
452 case sizeof(uint64_t):
453 if (sizeof(size_t) >= sizeof(uint64_t)) {
454 *val = (size_t)*(const uint64_t *)p->data;
462 int OSSL_PARAM_set_size_t(const OSSL_PARAM *p, size_t val)
466 SET_RETURN_SIZE(p, 0);
467 if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
470 SET_RETURN_SIZE(p, sizeof(size_t)); /* Minimum expected size */
471 switch (p->data_size) {
472 case sizeof(uint32_t):
473 if (sizeof(uint32_t) >= sizeof(size_t)) {
474 SET_RETURN_SIZE(p, sizeof(uint32_t));
475 *(uint32_t *)p->data = (uint32_t)val;
479 case sizeof(uint64_t):
480 SET_RETURN_SIZE(p, sizeof(uint64_t));
481 if (sizeof(uint64_t) >= sizeof(size_t)) {
482 *(uint64_t *)p->data = (uint64_t)val;
490 OSSL_PARAM OSSL_PARAM_construct_size_t(const char *key, size_t *buf,
493 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
494 sizeof(size_t), rsize); }
496 int OSSL_PARAM_get_BN(const OSSL_PARAM *p, BIGNUM **val)
502 || p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
505 b = BN_native2bn(p->data, (int)p->data_size, *val);
513 int OSSL_PARAM_set_BN(const OSSL_PARAM *p, const BIGNUM *val)
519 SET_RETURN_SIZE(p, 0);
520 if (val == NULL || p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
523 bytes = (size_t)BN_num_bytes(val);
524 SET_RETURN_SIZE(p, bytes);
525 return p->data_size >= bytes
526 && BN_bn2nativepad(val, p->data, bytes) >= 0;
529 OSSL_PARAM OSSL_PARAM_construct_BN(const char *key, unsigned char *buf,
530 size_t bsize, size_t *rsize)
532 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER,
536 int OSSL_PARAM_get_double(const OSSL_PARAM *p, double *val)
538 if (val == NULL || p == NULL || p->data_type != OSSL_PARAM_REAL)
541 switch (p->data_size) {
543 *val = *(const double *)p->data;
549 int OSSL_PARAM_set_double(const OSSL_PARAM *p, double val)
553 SET_RETURN_SIZE(p, 0);
554 if (p->data_type != OSSL_PARAM_REAL)
557 switch (p->data_size) {
559 SET_RETURN_SIZE(p, sizeof(double));
560 *(double *)p->data = val;
566 OSSL_PARAM OSSL_PARAM_construct_double(const char *key, double *buf,
569 return ossl_param_construct(key, OSSL_PARAM_REAL, buf, sizeof(double),
573 static int get_string_internal(const OSSL_PARAM *p, void **val, size_t max_len,
574 size_t *used_len, unsigned int type)
578 if (val == NULL || p == NULL || p->data_type != type)
583 if (used_len != NULL)
587 char *const q = OPENSSL_malloc(sz);
592 memcpy(q, p->data, sz);
597 memcpy(*val, p->data, sz);
601 int OSSL_PARAM_get_utf8_string(const OSSL_PARAM *p, char **val, size_t max_len)
603 return get_string_internal(p, (void **)val, max_len, NULL,
604 OSSL_PARAM_UTF8_STRING);
607 int OSSL_PARAM_get_octet_string(const OSSL_PARAM *p, void **val, size_t max_len,
610 return get_string_internal(p, val, max_len, used_len,
611 OSSL_PARAM_OCTET_STRING);
614 static int set_string_internal(const OSSL_PARAM *p, const void *val, size_t len,
617 SET_RETURN_SIZE(p, len);
618 if (p->data_type != type || p->data_size < len)
621 memcpy(p->data, val, len);
625 int OSSL_PARAM_set_utf8_string(const OSSL_PARAM *p, const char *val)
630 SET_RETURN_SIZE(p, 0);
633 return set_string_internal(p, val, strlen(val) + 1, OSSL_PARAM_UTF8_STRING);
636 int OSSL_PARAM_set_octet_string(const OSSL_PARAM *p, const void *val,
642 SET_RETURN_SIZE(p, 0);
645 return set_string_internal(p, val, len, OSSL_PARAM_OCTET_STRING);
648 OSSL_PARAM OSSL_PARAM_construct_utf8_string(const char *key, char *buf,
649 size_t bsize, size_t *rsize)
651 return ossl_param_construct(key, OSSL_PARAM_UTF8_STRING, buf, bsize,
655 OSSL_PARAM OSSL_PARAM_construct_octet_string(const char *key, void *buf,
656 size_t bsize, size_t *rsize)
658 return ossl_param_construct(key, OSSL_PARAM_OCTET_STRING, buf, bsize,
662 static int get_ptr_internal(const OSSL_PARAM *p, const void **val,
663 size_t *used_len, unsigned int type)
665 if (val == NULL || p == NULL || p->data_type != type)
667 if (used_len != NULL)
668 *used_len = p->data_size;
669 *val = *(const void **)p->data;
673 int OSSL_PARAM_get_utf8_ptr(const OSSL_PARAM *p, const char **val)
675 return get_ptr_internal(p, (const void **)val, NULL, OSSL_PARAM_UTF8_PTR);
678 int OSSL_PARAM_get_octet_ptr(const OSSL_PARAM *p, const void **val,
681 return get_ptr_internal(p, val, used_len, OSSL_PARAM_OCTET_PTR);
684 static int set_ptr_internal(const OSSL_PARAM *p, const void *val,
685 unsigned int type, size_t len)
687 SET_RETURN_SIZE(p, len);
688 if (p->data_type != type)
690 *(const void **)p->data = val;
694 int OSSL_PARAM_set_utf8_ptr(const OSSL_PARAM *p, const char *val)
698 SET_RETURN_SIZE(p, 0);
701 return set_ptr_internal(p, val, OSSL_PARAM_UTF8_PTR, strlen(val) + 1);
704 int OSSL_PARAM_set_octet_ptr(const OSSL_PARAM *p, const void *val,
709 SET_RETURN_SIZE(p, 0);
712 return set_ptr_internal(p, val, OSSL_PARAM_OCTET_PTR, used_len);
715 OSSL_PARAM OSSL_PARAM_construct_utf8_ptr(const char *key, char **buf,
718 return ossl_param_construct(key, OSSL_PARAM_UTF8_PTR, buf, 0, rsize);
721 OSSL_PARAM OSSL_PARAM_construct_octet_ptr(const char *key, void **buf,
724 return ossl_param_construct(key, OSSL_PARAM_OCTET_PTR, buf, 0, rsize);