1 =pod 2 3 =head1 NAME 4 5 ASN1_EXTERN_FUNCS, ASN1_ex_d2i, ASN1_ex_d2i_ex, ASN1_ex_i2d, ASN1_ex_new_func, 6 ASN1_ex_new_ex_func, ASN1_ex_free_func, ASN1_ex_print_func, 7 IMPLEMENT_EXTERN_ASN1 8 - ASN.1 external function support 9 10 =head1 SYNOPSIS 11 12 #include <openssl/asn1t.h> 13 14 typedef int ASN1_ex_d2i(ASN1_VALUE **pval, const unsigned char **in, long len, 15 const ASN1_ITEM *it, int tag, int aclass, char opt, 16 ASN1_TLC *ctx); 17 typedef int ASN1_ex_d2i_ex(ASN1_VALUE **pval, const unsigned char **in, long len, 18 const ASN1_ITEM *it, int tag, int aclass, char opt, 19 ASN1_TLC *ctx, OSSL_LIB_CTX *libctx, 20 const char *propq); 21 typedef int ASN1_ex_i2d(const ASN1_VALUE **pval, unsigned char **out, 22 const ASN1_ITEM *it, int tag, int aclass); 23 typedef int ASN1_ex_new_func(ASN1_VALUE **pval, const ASN1_ITEM *it); 24 typedef int ASN1_ex_new_ex_func(ASN1_VALUE **pval, const ASN1_ITEM *it, 25 OSSL_LIB_CTX *libctx, const char *propq); 26 typedef void ASN1_ex_free_func(ASN1_VALUE **pval, const ASN1_ITEM *it); 27 typedef int ASN1_ex_print_func(BIO *out, const ASN1_VALUE **pval, 28 int indent, const char *fname, 29 const ASN1_PCTX *pctx); 30 31 struct ASN1_EXTERN_FUNCS_st { 32 void *app_data; 33 ASN1_ex_new_func *asn1_ex_new; 34 ASN1_ex_free_func *asn1_ex_free; 35 ASN1_ex_free_func *asn1_ex_clear; 36 ASN1_ex_d2i *asn1_ex_d2i; 37 ASN1_ex_i2d *asn1_ex_i2d; 38 ASN1_ex_print_func *asn1_ex_print; 39 ASN1_ex_new_ex_func *asn1_ex_new_ex; 40 ASN1_ex_d2i_ex *asn1_ex_d2i_ex; 41 }; 42 typedef struct ASN1_EXTERN_FUNCS_st ASN1_EXTERN_FUNCS; 43 44 #define IMPLEMENT_EXTERN_ASN1(sname, tag, fptrs) 45 46 =head1 DESCRIPTION 47 48 ASN.1 data structures templates are typically defined in OpenSSL using a series 49 of macros such as ASN1_SEQUENCE(), ASN1_SEQUENCE_END() and so on. Instead 50 templates can also be defined based entirely on external functions. These 51 external functions are called to perform operations such as creating a new 52 B<ASN1_VALUE> or converting an B<ASN1_VALUE> to or from DER encoding. 53 54 The macro IMPLEMENT_EXTERN_ASN1() can be used to create such an externally 55 defined structure. The name of the structure should be supplied in the I<sname> 56 parameter. The tag for the structure (e.g. typically B<V_ASN1_SEQUENCE>) should 57 be supplied in the I<tag> parameter. Finally a pointer to an 58 B<ASN1_EXTERN_FUNCS> structure should be supplied in the I<fptrs> parameter. 59 60 The B<ASN1_EXTERN_FUNCS> structure has the following entries. 61 62 =over 4 63 64 =item I<app_data> 65 66 A pointer to arbitrary application specific data. 67 68 =item I<asn1_ex_new> 69 70 A "new" function responsible for constructing a new B<ASN1_VALUE> object. The 71 newly constructed value should be stored in I<*pval>. The I<it> parameter is a 72 pointer to the B<ASN1_ITEM> template object created via the 73 IMPLEMENT_EXTERN_ASN1() macro. 74 75 Returns a positive value on success or 0 on error. 76 77 =item I<asn1_ex_free> 78 79 A "free" function responsible for freeing the B<ASN1_VALUE> passed in I<*pval> 80 that was previously allocated via a "new" function. The I<it> parameter is a 81 pointer to the B<ASN1_ITEM> template object created via the 82 IMPLEMENT_EXTERN_ASN1() macro. 83 84 =item I<asn1_ex_clear> 85 86 A "clear" function responsible for clearing any data in the B<ASN1_VALUE> passed 87 in I<*pval> and making it suitable for reuse. The I<it> parameter is a pointer 88 to the B<ASN1_ITEM> template object created via the IMPLEMENT_EXTERN_ASN1() 89 macro. 90 91 =item I<asn1_ex_d2i> 92 93 A "d2i" function responsible for converting DER data with the tag I<tag> and 94 class I<class> into an B<ASN1_VALUE>. If I<*pval> is non-NULL then the 95 B<ASN_VALUE> it points to should be reused. Otherwise a new B<ASN1_VALUE> 96 should be allocated and stored in I<*pval>. I<*in> points to the DER data to be 97 decoded and I<len> is the length of that data. After decoding I<*in> should be 98 updated to point at the next byte after the decoded data. If the B<ASN1_VALUE> 99 is considered optional in this context then I<opt> will be nonzero. Otherwise 100 it will be zero. The I<it> parameter is a pointer to the B<ASN1_ITEM> template 101 object created via the IMPLEMENT_EXTERN_ASN1() macro. A pointer to the current 102 B<ASN1_TLC> context (which may be required for other ASN1 function calls) is 103 passed in the I<ctx> parameter. 104 105 The I<asn1_ex_d2i> entry may be NULL if I<asn1_ex_d2i_ex> has been specified 106 instead. 107 108 Returns <= 0 on error or a positive value on success. 109 110 =item I<asn1_ex_i2d> 111 112 An "i2d" function responsible for converting an B<ASN1_VALUE> into DER encoding. 113 On entry I<*pval> will contain the B<ASN1_VALUE> to be encoded. If default 114 tagging is to be used then I<tag> will be -1 on entry. Otherwise if implicit 115 tagging should be used then I<tag> and I<aclass> will be the tag and associated 116 class. 117 118 If I<out> is not NULL then this function should write the DER encoded data to 119 the buffer in I<*out>, and then increment I<*out> to point to immediately after 120 the data just written. 121 122 If I<out> is NULL then no data should be written but the length calculated and 123 returned as if it were. 124 125 The I<asn1_ex_i2d> entry may be NULL if I<asn1_ex_i2d_ex> has been specified 126 instead. 127 128 The return value should be negative if a fatal error occurred, or 0 if a 129 non-fatal error occurred. Otherwise it should return the length of the encoded 130 data. 131 132 =item I<asn1_ex_print> 133 134 A "print" function. I<out> is the BIO to print the output to. I<*pval> is the 135 B<ASN1_VALUE> to be printed. I<indent> is the number of spaces of indenting to 136 be printed before any data is printed. I<fname> is currently unused and is 137 always "". I<pctx> is a pointer to the B<ASN1_PCTX> for the print operation. 138 139 Returns 0 on error or a positive value on success. If the return value is 2 then 140 an additional newline will be printed after the data printed by this function. 141 142 =item I<asn1_ex_new_ex> 143 144 This is the same as I<asn1_ex_new> except that it is additionally passed the 145 OSSL_LIB_CTX to be used in I<libctx> and any property query string to be used 146 for algorithm fetching in the I<propq> parameter. See 147 L<crypto(7)/ALGORITHM FETCHING> for further details. If I<asn1_ex_new_ex> is 148 non NULL, then it will always be called in preference to I<asn1_ex_new>. 149 150 =item I<asn1_ex_d2i_ex> 151 152 This is the same as I<asn1_ex_d2i> except that it is additionally passed the 153 OSSL_LIB_CTX to be used in I<libctx> and any property query string to be used 154 for algorithm fetching in the I<propq> parameter. See 155 L<crypto(7)/ALGORITHM FETCHING> for further details. If I<asn1_ex_d2i_ex> is 156 non NULL, then it will always be called in preference to I<asn1_ex_d2i>. 157 158 =back 159 160 =head1 RETURN VALUES 161 162 Return values for the various callbacks are as described above. 163 164 =head1 SEE ALSO 165 166 L<ASN1_item_new_ex(3)> 167 168 =head1 HISTORY 169 170 The I<asn1_ex_new_ex> and I<asn1_ex_d2i_ex> callbacks were added in OpenSSL 3.0. 171 172 =head1 COPYRIGHT 173 174 Copyright 2021 The OpenSSL Project Authors. All Rights Reserved. 175 176 Licensed under the Apache License 2.0 (the "License"). You may not use 177 this file except in compliance with the License. You can obtain a copy 178 in the file LICENSE in the source distribution or at 179 L<https://www.openssl.org/source/license.html>. 180 181 =cut 182