Fix OSSL_PARAM_allocate_from_text() for EBCDIC
[openssl.git] / doc / man3 / OSSL_PARAM_allocate_from_text.pod
1 =pod
2
3 =head1 NAME
4
5 OSSL_PARAM_allocate_from_text
6 - OSSL_PARAM construction utilities
7
8 =head1 SYNOPSIS
9
10  #include <openssl/params.h>
11
12  int OSSL_PARAM_allocate_from_text(OSSL_PARAM *to,
13                                    const OSSL_PARAM *paramdefs,
14                                    const char *key, const char *value,
15                                    size_t value_n,
16                                    int *found);
17
18 =head1 DESCRIPTION
19
20 With OpenSSL before version 3.0, parameters were passed down to or
21 retrieved from algorithm implementations via control functions.
22 Some of these control functions existed in variants that took string
23 parameters, for example L<EVP_PKEY_CTX_ctrl_str(3)>.
24
25 OpenSSL 3.0 introduces a new mechanism to do the same thing with an
26 array of parameters that contain name, value, value type and value
27 size (see L<OSSL_PARAM(3)> for more information).
28
29 OSSL_PARAM_allocate_from_text() uses I<key> to look up an item in
30 I<paramdefs>.  If an item was found, it converts I<value> to something
31 suitable for that item's I<data_type>, and stores the result in
32 I<< to->data >> as well as its size in I<< to->data_size >>.
33 I<< to->key >> and I<< to->data_type >> are assigned the corresponding
34 values from the item that was found, and I<< to->return_size >> is set
35 to zero.
36
37 I<< to->data >> is always allocated using L<OPENSSL_zalloc(3)> and
38 needs to be freed by the caller when it's not useful any more, using
39 L<OPENSSL_free(3)>.
40
41 If I<found> is not NULL, I<*found> is set to 1 if I<key> could be
42 located in I<paramdefs>, and to 0 otherwise.
43
44 =head2 The use of I<key> and I<value> in detail
45
46 OSSL_PARAM_allocate_from_text() takes note if I<key> starts with
47 "hex", and will only use the rest of I<key> to look up an item in
48 I<paramdefs> in that case.  As an example, if I<key> is "hexid", "id"
49 will be looked up in I<paramdefs>.
50
51 When an item in I<paramdefs> has been found, I<value> is converted
52 depending on that item's I<data_type>, as follows:
53
54 =over 4
55
56 =item B<OSSL_PARAM_INTEGER> and B<OSSL_PARAM_UNSIGNED_INTEGER>
57
58 If I<key> started with "hex", I<value> is assumed to contain
59 I<value_n> hexadecimal characters, which are decoded, and the
60 resulting bytes become the number stored in the I<< to->data >>
61 storage.
62
63 If I<key> didn't start with "hex", I<value> is assumed to contain
64 I<value_n> decimal characters, which are decoded, and the resulting
65 bytes become the number stored in the I<< to->data >> storage.
66
67 If I<value> contains characters that couldn't be decoded as
68 hexadecimal or decimal characters, OSSL_PARAM_allocate_from_text()
69 considers that an error.
70
71 =item B<OSSL_PARAM_UTF8_STRING>
72
73 If I<key> started with "hex", OSSL_PARAM_allocate_from_text()
74 considers that an error.
75
76 Otherwise, I<value> is considered a C string and is copied to the
77 I<< to->data >> storage.
78 On systems where the native character encoding is EBCDIC, the bytes in
79 I<< to->data >> are converted to ASCII.
80
81 =item B<OSSL_PARAM_OCTET_STRING>
82
83 If I<key> started with "hex", I<value> is assumed to contain
84 I<value_n> hexadecimal characters, which are decoded, and the
85 resulting bytes are stored in the I<< to->data >> storage.
86 If I<value> contains characters that couldn't be decoded as
87 hexadecimal or decimal characters, OSSL_PARAM_allocate_from_text()
88 considers that an error.
89
90 If I<key> didn't start with "hex", I<value_n> bytes from I<value> are
91 copied to the I<< to->data >> storage.
92
93 =back
94
95 =head1 RETURN VALUES
96
97 OSSL_PARAM_allocate_from_text() returns 1 if I<key> was found in
98 I<paramdefs> and there was no other failure, otherwise 0.
99
100 =head1 NOTES
101
102 The parameter descriptor array comes from functions dedicated to
103 return them.
104 The following B<OSSL_PARAM> attributes are used:
105
106 =over 4
107
108 =item I<key>
109
110 =item I<data_type>
111
112 =item I<data_size>
113
114 =back
115
116 All other attributes are ignored.
117
118 The I<data_size> attribute can be zero, meaning that the parameter it
119 describes expects arbitrary length data.
120
121 =head1 EXAMPLES
122
123 Code that looked like this:
124
125   int mac_ctrl_string(EVP_PKEY_CTX *ctx, const char *value)
126   {
127       int rv;
128       char *stmp, *vtmp = NULL;
129
130       stmp = OPENSSL_strdup(value);
131       if (stmp == NULL)
132           return -1;
133       vtmp = strchr(stmp, ':');
134       if (vtmp != NULL)
135           *vtmp++ = '\0';
136       rv = EVP_MAC_ctrl_str(ctx, stmp, vtmp);
137       OPENSSL_free(stmp);
138       return rv;
139   }
140
141   ...
142
143
144   for (i = 0; i < sk_OPENSSL_STRING_num(macopts); i++) {
145       char *macopt = sk_OPENSSL_STRING_value(macopts, i);
146
147       if (pkey_ctrl_string(mac_ctx, macopt) <= 0) {
148           BIO_printf(bio_err,
149                      "MAC parameter error \"%s\"\n", macopt);
150           ERR_print_errors(bio_err);
151           goto mac_end;
152       }
153   }
154
155 Can be written like this instead:
156
157   OSSL_PARAM *params =
158       OPENSSL_zalloc(sizeof(*params)
159                      * (sk_OPENSSL_STRING_num(opts) + 1));
160   const OSSL_PARAM *paramdefs = EVP_MAC_settable_ctx_params(mac);
161   size_t params_n;
162   char *opt = "<unknown>";
163
164   for (params_n = 0; params_n < (size_t)sk_OPENSSL_STRING_num(opts);
165        params_n++) {
166       char *stmp, *vtmp = NULL;
167
168       opt = sk_OPENSSL_STRING_value(opts, (int)params_n);
169       if ((stmp = OPENSSL_strdup(opt)) == NULL
170               || (vtmp = strchr(stmp, ':')) == NULL)
171           goto err;
172
173       *vtmp++ = '\0';
174       if (!OSSL_PARAM_allocate_from_text(&params[params_n],
175                                          paramdefs, stmp,
176                                          vtmp, strlen(vtmp), NULL))
177           goto err;
178   }
179   params[params_n] = OSSL_PARAM_construct_end();
180   if (!EVP_MAC_CTX_set_params(ctx, params))
181       goto err;
182   while (params_n-- > 0)
183       OPENSSL_free(params[params_n].data);
184   OPENSSL_free(params);
185   /* ... */
186   return;
187
188  err:
189   BIO_printf(bio_err, "MAC parameter error '%s'\n", opt);
190   ERR_print_errors(bio_err);
191
192
193 =head1 SEE ALSO
194
195 L<OSSL_PARAM(3)>, L<OSSL_PARAM_int(3)>
196
197 =head1 COPYRIGHT
198
199 Copyright 2019-2020 The OpenSSL Project Authors. All Rights Reserved.
200
201 Licensed under the Apache License 2.0 (the "License").  You may not use
202 this file except in compliance with the License.  You can obtain a copy
203 in the file LICENSE in the source distribution or at
204 L<https://www.openssl.org/source/license.html>.
205
206 =cut