]> git.ipfire.org Git - thirdparty/openssl.git/blob - crypto/params.c
params: change OSSL_PARAM_set_unmodified() to operate on a params array
[thirdparty/openssl.git] / crypto / params.c
1 /*
2 * Copyright 2019-2020 The OpenSSL Project Authors. All Rights Reserved.
3 * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
4 *
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
9 */
10
11 #include <string.h>
12 #include <openssl/params.h>
13 #include "internal/thread_once.h"
14 #include "internal/numbers.h"
15
16 OSSL_PARAM *OSSL_PARAM_locate(OSSL_PARAM *p, const char *key)
17 {
18 if (p != NULL && key != NULL)
19 for (; p->key != NULL; p++)
20 if (strcmp(key, p->key) == 0)
21 return p;
22 return NULL;
23 }
24
25 const OSSL_PARAM *OSSL_PARAM_locate_const(const OSSL_PARAM *p, const char *key)
26 {
27 return OSSL_PARAM_locate((OSSL_PARAM *)p, key);
28 }
29
30 static OSSL_PARAM ossl_param_construct(const char *key, unsigned int data_type,
31 void *data, size_t data_size)
32 {
33 OSSL_PARAM res;
34
35 res.key = key;
36 res.data_type = data_type;
37 res.data = data;
38 res.data_size = data_size;
39 res.return_size = OSSL_PARAM_UNMODIFIED;
40 return res;
41 }
42
43 int OSSL_PARAM_modified(const OSSL_PARAM *p)
44 {
45 return p != NULL && p->return_size != OSSL_PARAM_UNMODIFIED;
46 }
47
48 void OSSL_PARAM_set_all_unmodified(OSSL_PARAM *p)
49 {
50 if (p != NULL)
51 while (p->key != NULL)
52 p++->return_size = OSSL_PARAM_UNMODIFIED;
53 }
54
55 int OSSL_PARAM_get_int(const OSSL_PARAM *p, int *val)
56 {
57 switch (sizeof(int)) {
58 case sizeof(int32_t):
59 return OSSL_PARAM_get_int32(p, (int32_t *)val);
60 case sizeof(int64_t):
61 return OSSL_PARAM_get_int64(p, (int64_t *)val);
62 }
63 return 0;
64 }
65
66 int OSSL_PARAM_set_int(OSSL_PARAM *p, int val)
67 {
68 switch (sizeof(int)) {
69 case sizeof(int32_t):
70 return OSSL_PARAM_set_int32(p, (int32_t)val);
71 case sizeof(int64_t):
72 return OSSL_PARAM_set_int64(p, (int64_t)val);
73 }
74 return 0;
75 }
76
77 OSSL_PARAM OSSL_PARAM_construct_int(const char *key, int *buf)
78 {
79 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(int));
80 }
81
82 int OSSL_PARAM_get_uint(const OSSL_PARAM *p, unsigned int *val)
83 {
84 switch (sizeof(unsigned int)) {
85 case sizeof(uint32_t):
86 return OSSL_PARAM_get_uint32(p, (uint32_t *)val);
87 case sizeof(uint64_t):
88 return OSSL_PARAM_get_uint64(p, (uint64_t *)val);
89 }
90 return 0;
91 }
92
93 int OSSL_PARAM_set_uint(OSSL_PARAM *p, unsigned int val)
94 {
95 switch (sizeof(unsigned int)) {
96 case sizeof(uint32_t):
97 return OSSL_PARAM_set_uint32(p, (uint32_t)val);
98 case sizeof(uint64_t):
99 return OSSL_PARAM_set_uint64(p, (uint64_t)val);
100 }
101 return 0;
102 }
103
104 OSSL_PARAM OSSL_PARAM_construct_uint(const char *key, unsigned int *buf)
105 {
106 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
107 sizeof(unsigned int));
108 }
109
110 int OSSL_PARAM_get_long(const OSSL_PARAM *p, long int *val)
111 {
112 switch (sizeof(long int)) {
113 case sizeof(int32_t):
114 return OSSL_PARAM_get_int32(p, (int32_t *)val);
115 case sizeof(int64_t):
116 return OSSL_PARAM_get_int64(p, (int64_t *)val);
117 }
118 return 0;
119 }
120
121 int OSSL_PARAM_set_long(OSSL_PARAM *p, long int val)
122 {
123 switch (sizeof(long int)) {
124 case sizeof(int32_t):
125 return OSSL_PARAM_set_int32(p, (int32_t)val);
126 case sizeof(int64_t):
127 return OSSL_PARAM_set_int64(p, (int64_t)val);
128 }
129 return 0;
130 }
131
132 OSSL_PARAM OSSL_PARAM_construct_long(const char *key, long int *buf)
133 {
134 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(long int));
135 }
136
137 int OSSL_PARAM_get_ulong(const OSSL_PARAM *p, unsigned long int *val)
138 {
139 switch (sizeof(unsigned long int)) {
140 case sizeof(uint32_t):
141 return OSSL_PARAM_get_uint32(p, (uint32_t *)val);
142 case sizeof(uint64_t):
143 return OSSL_PARAM_get_uint64(p, (uint64_t *)val);
144 }
145 return 0;
146 }
147
148 int OSSL_PARAM_set_ulong(OSSL_PARAM *p, unsigned long int val)
149 {
150 switch (sizeof(unsigned long int)) {
151 case sizeof(uint32_t):
152 return OSSL_PARAM_set_uint32(p, (uint32_t)val);
153 case sizeof(uint64_t):
154 return OSSL_PARAM_set_uint64(p, (uint64_t)val);
155 }
156 return 0;
157 }
158
159 OSSL_PARAM OSSL_PARAM_construct_ulong(const char *key, unsigned long int *buf)
160 {
161 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
162 sizeof(unsigned long int));
163 }
164
165 int OSSL_PARAM_get_int32(const OSSL_PARAM *p, int32_t *val)
166 {
167 int64_t i64;
168 uint32_t u32;
169 uint64_t u64;
170 double d;
171
172 if (val == NULL || p == NULL )
173 return 0;
174
175 if (p->data_type == OSSL_PARAM_INTEGER) {
176 switch (p->data_size) {
177 case sizeof(int32_t):
178 *val = *(const int32_t *)p->data;
179 return 1;
180 case sizeof(int64_t):
181 i64 = *(const int64_t *)p->data;
182 if (i64 >= INT32_MIN && i64 <= INT32_MAX) {
183 *val = (int32_t)i64;
184 return 1;
185 }
186 break;
187 }
188 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
189 switch (p->data_size) {
190 case sizeof(uint32_t):
191 u32 = *(const uint32_t *)p->data;
192 if (u32 <= INT32_MAX) {
193 *val = (int32_t)u32;
194 return 1;
195 }
196 break;
197 case sizeof(uint64_t):
198 u64 = *(const uint64_t *)p->data;
199 if (u64 <= INT32_MAX) {
200 *val = (int32_t)u64;
201 return 1;
202 }
203 break;
204 }
205 } else if (p->data_type == OSSL_PARAM_REAL) {
206 switch (p->data_size) {
207 case sizeof(double):
208 d = *(const double *)p->data;
209 if (d >= INT32_MIN && d <= INT32_MAX && d == (int32_t)d) {
210 *val = (int32_t)d;
211 return 1;
212 }
213 break;
214 }
215 }
216 return 0;
217 }
218
219 int OSSL_PARAM_set_int32(OSSL_PARAM *p, int32_t val)
220 {
221 if (p == NULL)
222 return 0;
223 p->return_size = 0;
224 if (p->data_type == OSSL_PARAM_INTEGER) {
225 p->return_size = sizeof(int32_t); /* Minimum expected size */
226 if (p->data == NULL)
227 return 1;
228 switch (p->data_size) {
229 case sizeof(int32_t):
230 *(int32_t *)p->data = val;
231 return 1;
232 case sizeof(int64_t):
233 p->return_size = sizeof(int64_t);
234 *(int64_t *)p->data = (int64_t)val;
235 return 1;
236 }
237 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER && val >= 0) {
238 p->return_size = sizeof(uint32_t); /* Minimum expected size */
239 if (p->data == NULL)
240 return 1;
241 switch (p->data_size) {
242 case sizeof(uint32_t):
243 *(uint32_t *)p->data = (uint32_t)val;
244 return 1;
245 case sizeof(uint64_t):
246 p->return_size = sizeof(uint64_t);
247 *(uint64_t *)p->data = (uint64_t)val;
248 return 1;
249 }
250 } else if (p->data_type == OSSL_PARAM_REAL) {
251 p->return_size = sizeof(double);
252 if (p->data == NULL)
253 return 1;
254 switch (p->data_size) {
255 case sizeof(double):
256 *(double *)p->data = (double)val;
257 return 1;
258 }
259 }
260 return 0;
261 }
262
263 OSSL_PARAM OSSL_PARAM_construct_int32(const char *key, int32_t *buf)
264 {
265 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf,
266 sizeof(int32_t));
267 }
268
269 int OSSL_PARAM_get_uint32(const OSSL_PARAM *p, uint32_t *val)
270 {
271 int32_t i32;
272 int64_t i64;
273 uint64_t u64;
274 double d;
275
276 if (val == NULL || p == NULL)
277 return 0;
278
279 if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
280 switch (p->data_size) {
281 case sizeof(uint32_t):
282 *val = *(const uint32_t *)p->data;
283 return 1;
284 case sizeof(uint64_t):
285 u64 = *(const uint64_t *)p->data;
286 if (u64 <= UINT32_MAX) {
287 *val = (uint32_t)u64;
288 return 1;
289 }
290 break;
291 }
292 } else if (p->data_type == OSSL_PARAM_INTEGER) {
293 switch (p->data_size) {
294 case sizeof(int32_t):
295 i32 = *(const int32_t *)p->data;
296 if (i32 >= 0) {
297 *val = i32;
298 return 1;
299 }
300 break;
301 case sizeof(int64_t):
302 i64 = *(const int64_t *)p->data;
303 if (i64 >= 0 && i64 <= UINT32_MAX) {
304 *val = (uint32_t)i64;
305 return 1;
306 }
307 break;
308 }
309 } else if (p->data_type == OSSL_PARAM_REAL) {
310 switch (p->data_size) {
311 case sizeof(double):
312 d = *(const double *)p->data;
313 if (d >= 0 && d <= UINT32_MAX && d == (uint32_t)d) {
314 *val = (uint32_t)d;
315 return 1;
316 }
317 break;
318 }
319 }
320 return 0;
321 }
322
323 int OSSL_PARAM_set_uint32(OSSL_PARAM *p, uint32_t val)
324 {
325 if (p == NULL)
326 return 0;
327 p->return_size = 0;
328
329 if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
330 p->return_size = sizeof(uint32_t); /* Minimum expected size */
331 if (p->data == NULL)
332 return 1;
333 switch (p->data_size) {
334 case sizeof(uint32_t):
335 *(uint32_t *)p->data = val;
336 return 1;
337 case sizeof(uint64_t):
338 p->return_size = sizeof(uint64_t);
339 *(uint64_t *)p->data = val;
340 return 1;
341 }
342 } else if (p->data_type == OSSL_PARAM_INTEGER) {
343 p->return_size = sizeof(int32_t); /* Minimum expected size */
344 if (p->data == NULL)
345 return 1;
346 switch (p->data_size) {
347 case sizeof(int32_t):
348 if (val <= INT32_MAX) {
349 *(int32_t *)p->data = (int32_t)val;
350 return 1;
351 }
352 break;
353 case sizeof(int64_t):
354 p->return_size = sizeof(int64_t);
355 *(int64_t *)p->data = (int64_t)val;
356 return 1;
357 }
358 } else if (p->data_type == OSSL_PARAM_REAL) {
359 p->return_size = sizeof(double);
360 if (p->data == NULL)
361 return 1;
362 switch (p->data_size) {
363 case sizeof(double):
364 *(double *)p->data = (double)val;
365 return 1;
366 }
367 }
368 return 0;
369 }
370
371 OSSL_PARAM OSSL_PARAM_construct_uint32(const char *key, uint32_t *buf)
372 {
373 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
374 sizeof(uint32_t));
375 }
376
377 int OSSL_PARAM_get_int64(const OSSL_PARAM *p, int64_t *val)
378 {
379 uint64_t u64;
380 double d;
381
382 if (val == NULL || p == NULL )
383 return 0;
384
385 if (p->data_type == OSSL_PARAM_INTEGER) {
386 switch (p->data_size) {
387 case sizeof(int32_t):
388 *val = *(const int32_t *)p->data;
389 return 1;
390 case sizeof(int64_t):
391 *val = *(const int64_t *)p->data;
392 return 1;
393 }
394 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
395 switch (p->data_size) {
396 case sizeof(uint32_t):
397 *val = *(const uint32_t *)p->data;
398 return 1;
399 case sizeof(uint64_t):
400 u64 = *(const uint64_t *)p->data;
401 if (u64 <= INT64_MAX) {
402 *val = (int64_t)u64;
403 return 1;
404 }
405 break;
406 }
407 } else if (p->data_type == OSSL_PARAM_REAL) {
408 switch (p->data_size) {
409 case sizeof(double):
410 d = *(const double *)p->data;
411 if (d >= INT64_MIN && d <= INT64_MAX && d == (int64_t)d) {
412 *val = (int64_t)d;
413 return 1;
414 }
415 break;
416 }
417 }
418 return 0;
419 }
420
421 int OSSL_PARAM_set_int64(OSSL_PARAM *p, int64_t val)
422 {
423 uint64_t u64;
424
425 if (p == NULL)
426 return 0;
427 p->return_size = 0;
428 if (p->data_type == OSSL_PARAM_INTEGER) {
429 p->return_size = sizeof(int64_t); /* Expected size */
430 if (p->data == NULL)
431 return 1;
432 switch (p->data_size) {
433 case sizeof(int32_t):
434 if (val >= INT32_MIN && val <= INT32_MAX) {
435 p->return_size = sizeof(int32_t);
436 *(int32_t *)p->data = (int32_t)val;
437 return 1;
438 }
439 break;
440 case sizeof(int64_t):
441 *(int64_t *)p->data = val;
442 return 1;
443 }
444 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER && val >= 0) {
445 p->return_size = sizeof(uint64_t); /* Expected size */
446 if (p->data == NULL)
447 return 1;
448 switch (p->data_size) {
449 case sizeof(uint32_t):
450 if (val <= UINT32_MAX) {
451 p->return_size = sizeof(uint32_t);
452 *(uint32_t *)p->data = (uint32_t)val;
453 return 1;
454 }
455 break;
456 case sizeof(uint64_t):
457 *(uint64_t *)p->data = (uint64_t)val;
458 return 1;
459 }
460 } else if (p->data_type == OSSL_PARAM_REAL) {
461 p->return_size = sizeof(double);
462 if (p->data == NULL)
463 return 1;
464 switch (p->data_size) {
465 case sizeof(double):
466 u64 = val < 0 ? -val : val;
467 if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
468 *(double *)p->data = (double)val;
469 return 1;
470 }
471 break;
472 }
473 }
474 return 0;
475 }
476
477 OSSL_PARAM OSSL_PARAM_construct_int64(const char *key, int64_t *buf)
478 {
479 return ossl_param_construct(key, OSSL_PARAM_INTEGER, buf, sizeof(int64_t));
480 }
481
482 int OSSL_PARAM_get_uint64(const OSSL_PARAM *p, uint64_t *val)
483 {
484 int32_t i32;
485 int64_t i64;
486 double d;
487
488 if (val == NULL || p == NULL)
489 return 0;
490
491 if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
492 switch (p->data_size) {
493 case sizeof(uint32_t):
494 *val = *(const uint32_t *)p->data;
495 return 1;
496 case sizeof(uint64_t):
497 *val = *(const uint64_t *)p->data;
498 return 1;
499 }
500 } else if (p->data_type == OSSL_PARAM_INTEGER) {
501 switch (p->data_size) {
502 case sizeof(int32_t):
503 i32 = *(const int32_t *)p->data;
504 if (i32 >= 0) {
505 *val = (uint64_t)i32;
506 return 1;
507 }
508 break;
509 case sizeof(int64_t):
510 i64 = *(const int64_t *)p->data;
511 if (i64 >= 0) {
512 *val = (uint64_t)i64;
513 return 1;
514 }
515 break;
516 }
517 } else if (p->data_type == OSSL_PARAM_REAL) {
518 switch (p->data_size) {
519 case sizeof(double):
520 d = *(const double *)p->data;
521 if (d >= 0 && d <= INT64_MAX && d == (uint64_t)d) {
522 *val = (uint64_t)d;
523 return 1;
524 }
525 break;
526 }
527 }
528 return 0;
529 }
530
531 int OSSL_PARAM_set_uint64(OSSL_PARAM *p, uint64_t val)
532 {
533 if (p == NULL)
534 return 0;
535 p->return_size = 0;
536
537 if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
538 p->return_size = sizeof(uint64_t); /* Expected size */
539 if (p->data == NULL)
540 return 1;
541 switch (p->data_size) {
542 case sizeof(uint32_t):
543 if (val <= UINT32_MAX) {
544 p->return_size = sizeof(uint32_t);
545 *(uint32_t *)p->data = (uint32_t)val;
546 return 1;
547 }
548 break;
549 case sizeof(uint64_t):
550 *(uint64_t *)p->data = val;
551 return 1;
552 }
553 } else if (p->data_type == OSSL_PARAM_INTEGER) {
554 p->return_size = sizeof(int64_t); /* Expected size */
555 if (p->data == NULL)
556 return 1;
557 switch (p->data_size) {
558 case sizeof(int32_t):
559 if (val <= INT32_MAX) {
560 p->return_size = sizeof(int32_t);
561 *(int32_t *)p->data = (int32_t)val;
562 return 1;
563 }
564 break;
565 case sizeof(int64_t):
566 if (val <= INT64_MAX) {
567 *(int64_t *)p->data = (int64_t)val;
568 return 1;
569 }
570 break;
571 }
572 } else if (p->data_type == OSSL_PARAM_REAL) {
573 p->return_size = sizeof(double);
574 switch (p->data_size) {
575 case sizeof(double):
576 if ((val >> 53) == 0) { /* 53 significant bits in the mantissa */
577 *(double *)p->data = (double)val;
578 return 1;
579 }
580 break;
581 }
582 }
583 return 0;
584 }
585
586 OSSL_PARAM OSSL_PARAM_construct_uint64(const char *key, uint64_t *buf)
587 {
588 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
589 sizeof(uint64_t));
590 }
591
592 int OSSL_PARAM_get_size_t(const OSSL_PARAM *p, size_t *val)
593 {
594 switch (sizeof(size_t)) {
595 case sizeof(uint32_t):
596 return OSSL_PARAM_get_uint32(p, (uint32_t *)val);
597 case sizeof(uint64_t):
598 return OSSL_PARAM_get_uint64(p, (uint64_t *)val);
599 }
600 return 0;
601 }
602
603 int OSSL_PARAM_set_size_t(OSSL_PARAM *p, size_t val)
604 {
605 switch (sizeof(size_t)) {
606 case sizeof(uint32_t):
607 return OSSL_PARAM_set_uint32(p, (uint32_t)val);
608 case sizeof(uint64_t):
609 return OSSL_PARAM_set_uint64(p, (uint64_t)val);
610 }
611 return 0;
612 }
613
614 OSSL_PARAM OSSL_PARAM_construct_size_t(const char *key, size_t *buf)
615 {
616 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER, buf,
617 sizeof(size_t));
618 }
619
620 int OSSL_PARAM_get_BN(const OSSL_PARAM *p, BIGNUM **val)
621 {
622 BIGNUM *b;
623
624 if (val == NULL
625 || p == NULL
626 || p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
627 return 0;
628
629 b = BN_native2bn(p->data, (int)p->data_size, *val);
630 if (b != NULL) {
631 *val = b;
632 return 1;
633 }
634 return 0;
635 }
636
637 int OSSL_PARAM_set_BN(OSSL_PARAM *p, const BIGNUM *val)
638 {
639 size_t bytes;
640
641 if (p == NULL)
642 return 0;
643 p->return_size = 0;
644 if (val == NULL || p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
645 return 0;
646
647 /* For the moment, only positive values are permitted */
648 if (BN_is_negative(val))
649 return 0;
650
651 bytes = (size_t)BN_num_bytes(val);
652 p->return_size = bytes;
653 if (p->data == NULL)
654 return 1;
655 if (p->data_size >= bytes) {
656 p->return_size = p->data_size;
657 return BN_bn2nativepad(val, p->data, p->data_size) >= 0;
658 }
659 return 0;
660 }
661
662 OSSL_PARAM OSSL_PARAM_construct_BN(const char *key, unsigned char *buf,
663 size_t bsize)
664 {
665 return ossl_param_construct(key, OSSL_PARAM_UNSIGNED_INTEGER,
666 buf, bsize);
667 }
668
669 int OSSL_PARAM_get_double(const OSSL_PARAM *p, double *val)
670 {
671 int64_t i64;
672 uint64_t u64;
673
674 if (val == NULL || p == NULL)
675 return 0;
676
677 if (p->data_type == OSSL_PARAM_REAL) {
678 switch (p->data_size) {
679 case sizeof(double):
680 *val = *(const double *)p->data;
681 return 1;
682 }
683 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
684 switch (p->data_size) {
685 case sizeof(uint32_t):
686 *val = *(const uint32_t *)p->data;
687 return 1;
688 case sizeof(uint64_t):
689 u64 = *(const uint64_t *)p->data;
690 if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
691 *val = (double)u64;
692 return 1;
693 }
694 break;
695 }
696 } else if (p->data_type == OSSL_PARAM_INTEGER) {
697 switch (p->data_size) {
698 case sizeof(int32_t):
699 *val = *(const int32_t *)p->data;
700 return 1;
701 case sizeof(int64_t):
702 i64 = *(const int64_t *)p->data;
703 u64 = i64 < 0 ? -i64 : i64;
704 if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
705 *val = 0.0 + i64;
706 return 1;
707 }
708 break;
709 }
710 }
711 return 0;
712 }
713
714 int OSSL_PARAM_set_double(OSSL_PARAM *p, double val)
715 {
716 if (p == NULL)
717 return 0;
718 p->return_size = 0;
719
720 if (p->data_type == OSSL_PARAM_REAL) {
721 p->return_size = sizeof(double);
722 if (p->data == NULL)
723 return 1;
724 switch (p->data_size) {
725 case sizeof(double):
726 *(double *)p->data = val;
727 return 1;
728 }
729 } else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER
730 && val == (ossl_uintmax_t)val) {
731 p->return_size = sizeof(double);
732 if (p->data == NULL)
733 return 1;
734 switch (p->data_size) {
735 case sizeof(uint32_t):
736 if (val >= 0 && val <= UINT32_MAX) {
737 p->return_size = sizeof(uint32_t);
738 *(uint32_t *)p->data = (uint32_t)val;
739 return 1;
740 }
741 break;
742 case sizeof(uint64_t):
743 if (val >= 0 && val <= UINT64_MAX) {
744 p->return_size = sizeof(uint64_t);
745 *(uint64_t *)p->data = (uint64_t)val;
746 return 1;
747 }
748 break; }
749 } else if (p->data_type == OSSL_PARAM_INTEGER && val == (ossl_intmax_t)val) {
750 p->return_size = sizeof(double);
751 if (p->data == NULL)
752 return 1;
753 switch (p->data_size) {
754 case sizeof(int32_t):
755 if (val >= INT32_MIN && val <= INT32_MAX) {
756 p->return_size = sizeof(int32_t);
757 *(int32_t *)p->data = (int32_t)val;
758 return 1;
759 }
760 break;
761 case sizeof(int64_t):
762 if (val >= INT64_MIN && val <= INT64_MAX) {
763 p->return_size = sizeof(int64_t);
764 *(int64_t *)p->data = (int64_t)val;
765 return 1;
766 }
767 break;
768 }
769 }
770 return 0;
771 }
772
773 OSSL_PARAM OSSL_PARAM_construct_double(const char *key, double *buf)
774 {
775 return ossl_param_construct(key, OSSL_PARAM_REAL, buf, sizeof(double));
776 }
777
778 static int get_string_internal(const OSSL_PARAM *p, void **val, size_t max_len,
779 size_t *used_len, unsigned int type)
780 {
781 size_t sz;
782
783 if (val == NULL || p == NULL || p->data_type != type)
784 return 0;
785
786 sz = p->data_size;
787
788 if (used_len != NULL)
789 *used_len = sz;
790
791 if (sz == 0)
792 return 1;
793 if (p->data == NULL)
794 return 0;
795
796 if (*val == NULL) {
797 char *const q = OPENSSL_malloc(sz);
798
799 if (q == NULL)
800 return 0;
801 *val = q;
802 memcpy(q, p->data, sz);
803 return 1;
804 }
805 if (max_len < sz)
806 return 0;
807 memcpy(*val, p->data, sz);
808 return 1;
809 }
810
811 int OSSL_PARAM_get_utf8_string(const OSSL_PARAM *p, char **val, size_t max_len)
812 {
813 return get_string_internal(p, (void **)val, max_len, NULL,
814 OSSL_PARAM_UTF8_STRING);
815 }
816
817 int OSSL_PARAM_get_octet_string(const OSSL_PARAM *p, void **val, size_t max_len,
818 size_t *used_len)
819 {
820 return get_string_internal(p, val, max_len, used_len,
821 OSSL_PARAM_OCTET_STRING);
822 }
823
824 static int set_string_internal(OSSL_PARAM *p, const void *val, size_t len,
825 unsigned int type)
826 {
827 p->return_size = len;
828 if (p->data == NULL)
829 return 1;
830 if (p->data_type != type || p->data_size < len)
831 return 0;
832
833 memcpy(p->data, val, len);
834 return 1;
835 }
836
837 int OSSL_PARAM_set_utf8_string(OSSL_PARAM *p, const char *val)
838 {
839 if (p == NULL)
840 return 0;
841
842 p->return_size = 0;
843 if (val == NULL)
844 return 0;
845 return set_string_internal(p, val, strlen(val) + 1, OSSL_PARAM_UTF8_STRING);
846 }
847
848 int OSSL_PARAM_set_octet_string(OSSL_PARAM *p, const void *val,
849 size_t len)
850 {
851 if (p == NULL)
852 return 0;
853
854 p->return_size = 0;
855 if (val == NULL)
856 return 0;
857 return set_string_internal(p, val, len, OSSL_PARAM_OCTET_STRING);
858 }
859
860 OSSL_PARAM OSSL_PARAM_construct_utf8_string(const char *key, char *buf,
861 size_t bsize)
862 {
863 if (buf != NULL && bsize == 0)
864 bsize = strlen(buf) + 1;
865 return ossl_param_construct(key, OSSL_PARAM_UTF8_STRING, buf, bsize);
866 }
867
868 OSSL_PARAM OSSL_PARAM_construct_octet_string(const char *key, void *buf,
869 size_t bsize)
870 {
871 return ossl_param_construct(key, OSSL_PARAM_OCTET_STRING, buf, bsize);
872 }
873
874 static int get_ptr_internal(const OSSL_PARAM *p, const void **val,
875 size_t *used_len, unsigned int type)
876 {
877 if (val == NULL || p == NULL || p->data_type != type)
878 return 0;
879 if (used_len != NULL)
880 *used_len = p->data_size;
881 *val = *(const void **)p->data;
882 return 1;
883 }
884
885 int OSSL_PARAM_get_utf8_ptr(const OSSL_PARAM *p, const char **val)
886 {
887 return get_ptr_internal(p, (const void **)val, NULL, OSSL_PARAM_UTF8_PTR);
888 }
889
890 int OSSL_PARAM_get_octet_ptr(const OSSL_PARAM *p, const void **val,
891 size_t *used_len)
892 {
893 return get_ptr_internal(p, val, used_len, OSSL_PARAM_OCTET_PTR);
894 }
895
896 static int set_ptr_internal(OSSL_PARAM *p, const void *val,
897 unsigned int type, size_t len)
898 {
899 p->return_size = len;
900 if (p->data_type != type)
901 return 0;
902 if (p->data != NULL)
903 *(const void **)p->data = val;
904 return 1;
905 }
906
907 int OSSL_PARAM_set_utf8_ptr(OSSL_PARAM *p, const char *val)
908 {
909 if (p == NULL)
910 return 0;
911 p->return_size = 0;
912 return set_ptr_internal(p, val, OSSL_PARAM_UTF8_PTR,
913 val == NULL ? 0 : strlen(val) + 1);
914 }
915
916 int OSSL_PARAM_set_octet_ptr(OSSL_PARAM *p, const void *val,
917 size_t used_len)
918 {
919 if (p == NULL)
920 return 0;
921 p->return_size = 0;
922 return set_ptr_internal(p, val, OSSL_PARAM_OCTET_PTR, used_len);
923 }
924
925 OSSL_PARAM OSSL_PARAM_construct_utf8_ptr(const char *key, char **buf,
926 size_t bsize)
927 {
928 return ossl_param_construct(key, OSSL_PARAM_UTF8_PTR, buf, bsize);
929 }
930
931 OSSL_PARAM OSSL_PARAM_construct_octet_ptr(const char *key, void **buf,
932 size_t bsize)
933 {
934 return ossl_param_construct(key, OSSL_PARAM_OCTET_PTR, buf, bsize);
935 }
936
937 OSSL_PARAM OSSL_PARAM_construct_end(void)
938 {
939 OSSL_PARAM end = OSSL_PARAM_END;
940
941 return end;
942 }