1*636210b0Stb.\" $OpenBSD: RSA_get_ex_new_index.3,v 1.13 2023/11/19 21:08:04 tb Exp $ 28974101aSjmc.\" 33748f3d7Sschwarze.\" Copyright (c) 2023 Ingo Schwarze <schwarze@openbsd.org> 4860a60ecSschwarze.\" 53748f3d7Sschwarze.\" Permission to use, copy, modify, and distribute this software for any 63748f3d7Sschwarze.\" purpose with or without fee is hereby granted, provided that the above 73748f3d7Sschwarze.\" copyright notice and this permission notice appear in all copies. 8860a60ecSschwarze.\" 93748f3d7Sschwarze.\" THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 103748f3d7Sschwarze.\" WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 113748f3d7Sschwarze.\" MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 123748f3d7Sschwarze.\" ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 133748f3d7Sschwarze.\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 143748f3d7Sschwarze.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 153748f3d7Sschwarze.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16860a60ecSschwarze.\" 17*636210b0Stb.Dd $Mdocdate: November 19 2023 $ 1829ab75b0Sschwarze.Dt RSA_GET_EX_NEW_INDEX 3 1929ab75b0Sschwarze.Os 2029ab75b0Sschwarze.Sh NAME 2129ab75b0Sschwarze.Nm RSA_get_ex_new_index , 2229ab75b0Sschwarze.Nm RSA_set_ex_data , 233748f3d7Sschwarze.Nm RSA_get_ex_data 243748f3d7Sschwarze.Nd add application specific data to RSA objects 2529ab75b0Sschwarze.Sh SYNOPSIS 2629ab75b0Sschwarze.In openssl/rsa.h 2729ab75b0Sschwarze.Ft int 2829ab75b0Sschwarze.Fo RSA_get_ex_new_index 2929ab75b0Sschwarze.Fa "long argl" 3029ab75b0Sschwarze.Fa "void *argp" 3129ab75b0Sschwarze.Fa "CRYPTO_EX_new *new_func" 3229ab75b0Sschwarze.Fa "CRYPTO_EX_dup *dup_func" 3329ab75b0Sschwarze.Fa "CRYPTO_EX_free *free_func" 3429ab75b0Sschwarze.Fc 3529ab75b0Sschwarze.Ft int 3629ab75b0Sschwarze.Fo RSA_set_ex_data 373748f3d7Sschwarze.Fa "RSA *rsa" 3829ab75b0Sschwarze.Fa "int idx" 393748f3d7Sschwarze.Fa "void *data" 4029ab75b0Sschwarze.Fc 4129ab75b0Sschwarze.Ft void * 4229ab75b0Sschwarze.Fo RSA_get_ex_data 433748f3d7Sschwarze.Fa "RSA *rsa" 4429ab75b0Sschwarze.Fa "int idx" 4529ab75b0Sschwarze.Fc 4629ab75b0Sschwarze.Sh DESCRIPTION 473748f3d7SschwarzeThe following parent objects can have application specific data called 483748f3d7Sschwarze.Dq ex_data 493748f3d7Sschwarzeattached to them: 50*636210b0Stb.Vt BIO , DH , DSA , EC_KEY , RSA , 513748f3d7Sschwarze.Vt SSL , SSL_CTX , SSL_SESSION , UI , X509 , X509_STORE , 523748f3d7Sschwarzeand 533748f3d7Sschwarze.Vt X509_STORE_CTX . 543748f3d7Sschwarze.\" CRYPTO_EX_INDEX_APP and CRYPTO_EX_INDEX_UI_METHOD are unused. 553748f3d7SschwarzeThe present manual page documents the related API functions taking the 563748f3d7Sschwarze.Vt RSA 573748f3d7Sschwarzeobject type as an example. 583748f3d7SschwarzeThe functions for the other object types work in exactly the same way: 593748f3d7Sschwarzejust replace the string 603748f3d7Sschwarze.Qq RSA 613748f3d7Sschwarzewith the name of the respective object type 623748f3d7Sschwarzethroughout the rest of this manual page. 6329ab75b0Sschwarze.Pp 643748f3d7SschwarzeBy default, each individual 653748f3d7Sschwarze.Vt RSA 663748f3d7Sschwarzeobject can store one 6729ab75b0Sschwarze.Vt void * 683748f3d7Sschwarzepointing to application specific data. 693748f3d7SschwarzeThat specific pointer is identified by an 7029ab75b0Sschwarze.Fa idx 713748f3d7Sschwarzeargument of 0. 723748f3d7Sschwarze.Pp 7329ab75b0Sschwarze.Fn RSA_get_ex_new_index 743748f3d7Sschwarzereserves the next consecutive 7529ab75b0Sschwarze.Fa idx 763748f3d7Sschwarzeargument, enabling storage of one additional 773748f3d7Sschwarze.Vt void * 783748f3d7Sschwarzeper 793748f3d7Sschwarze.Vt RSA 803748f3d7Sschwarzeobject. 813748f3d7SschwarzeIt is typically called at program startup. 823748f3d7SschwarzeIt can be called more than once if some 833748f3d7Sschwarze.Vt RSA 843748f3d7Sschwarzeobjects need to store more than two application specific pointers. 853748f3d7SschwarzeReserving an additional index for one parent object type, for example for 863748f3d7Sschwarze.Vt RSA , 873748f3d7Sschwarzedoes not change the numbers of indices that can be used 883748f3d7Sschwarzewith any other parent object type. 893748f3d7Sschwarze.Pp 903748f3d7SschwarzeIt is strongly recommended to always pass three 913748f3d7Sschwarze.Dv NULL 923748f3d7Sschwarzepointers for the arguments 933748f3d7Sschwarze.Fa new_func , 943748f3d7Sschwarze.Fa dup_func , 953748f3d7Sschwarzeand 963748f3d7Sschwarze.Fa free_func . 973748f3d7SschwarzeWhen following this recommendation, the arguments 9829ab75b0Sschwarze.Fa argl 9929ab75b0Sschwarzeand 10029ab75b0Sschwarze.Fa argp 1013748f3d7Sschwarzeare ignored; conventionally, passing 0 and 1023748f3d7Sschwarze.Dv NULL 1033748f3d7Sschwarzeis recommended. 1043748f3d7SschwarzeBecause using them is discouraged, the three function callback types 1053748f3d7Sschwarzeare only documented in the low-level 1063748f3d7Sschwarze.Xr CRYPTO_EX_new 3 1073748f3d7Sschwarzemanual page. 10829ab75b0Sschwarze.Pp 10929ab75b0Sschwarze.Fn RSA_set_ex_data 1103748f3d7Sschwarzestores the 1113748f3d7Sschwarze.Fa data 1123748f3d7Sschwarzepointer as application specific data at the given 1133748f3d7Sschwarze.Fa idx 1143748f3d7Sschwarzein the given 1153748f3d7Sschwarze.Fa rsa 1163748f3d7Sschwarzeobject. 1173748f3d7SschwarzeThe meaning of the data pointed to is up to the application. 1183748f3d7SschwarzeThe caller retains ownership of the 1193748f3d7Sschwarze.Fa data 1203748f3d7Sschwarzeand is responsible for freeing it when neither the caller nor the 1213748f3d7Sschwarze.Fa rsa 1223748f3d7Sschwarzeobject need it any longer. 1233748f3d7SschwarzeAny other pointer that was previously stored at the same 1243748f3d7Sschwarze.Fa idx 1253748f3d7Sschwarzein the same 1263748f3d7Sschwarze.Fa rsa 1273748f3d7Sschwarzeobject is silently overwritten. 1283748f3d7SschwarzePassing a 1293748f3d7Sschwarze.Dv NULL 1303748f3d7Sschwarzepointer for the 1313748f3d7Sschwarze.Fa data 1323748f3d7Sschwarzeargument is valid and indicates that no application specific data 1333748f3d7Sschwarzecurrently needs to be stored at the given 1343748f3d7Sschwarze.Fa idx . 13529ab75b0Sschwarze.Pp 13629ab75b0Sschwarze.Fn RSA_get_ex_data 1373748f3d7Sschwarzeretrieves the last pointer that was stored using 1383748f3d7Sschwarze.Fn RSA_set_ex_data 1393748f3d7Sschwarzeat the given 14029ab75b0Sschwarze.Fa idx 1413748f3d7Sschwarzein the given 1423748f3d7Sschwarze.Fa rsa 1433748f3d7Sschwarzeobject. 1443748f3d7Sschwarze.Sh RETURN VALUES 1453748f3d7Sschwarze.Fn RSA_get_ex_new_index 1463748f3d7Sschwarzereturns a new index equal to or greater than 1 1473748f3d7Sschwarzeor \-1 if memory allocation fails. 14829ab75b0Sschwarze.Pp 1493748f3d7Sschwarze.Fn RSA_set_ex_data 1503748f3d7Sschwarzereturns 1 on success or 0 if memory allocation fails. 1513748f3d7Sschwarze.Pp 1523748f3d7Sschwarze.Fn RSA_get_ex_data 1533748f3d7Sschwarzereturns the application specific data or 1543748f3d7Sschwarze.Dv NULL 1553748f3d7Sschwarzeif 1563748f3d7Sschwarze.Fa rsa 1573748f3d7Sschwarzedoes not contain application specific data at the given 1583748f3d7Sschwarze.Fa idx . 1593748f3d7Sschwarze.Sh ERRORS 1603748f3d7SschwarzeAfter failure of 1613748f3d7Sschwarze.Fn RSA_get_ex_new_index 1623748f3d7Sschwarzeor 1633748f3d7Sschwarze.Fn RSA_set_ex_data , 1643748f3d7Sschwarzethe following diagnostic can be retrieved with 1653748f3d7Sschwarze.Xr ERR_get_error 3 , 1663748f3d7Sschwarze.Xr ERR_GET_REASON 3 , 16729ab75b0Sschwarzeand 1683748f3d7Sschwarze.Xr ERR_reason_error_string 3 : 1693748f3d7Sschwarze.Bl -tag -width Ds 1703748f3d7Sschwarze.It Dv ERR_R_MALLOC_FAILURE Qq "malloc failure" 1713748f3d7SschwarzeMemory allocation failed. 1723748f3d7Sschwarze.El 17329ab75b0Sschwarze.Pp 1743748f3d7SschwarzeIn a few unusual failure cases, 1753748f3d7Sschwarze.Xr ERR_get_error 3 1763748f3d7Sschwarzemay report different errors caused by 1773748f3d7Sschwarze.Xr OPENSSL_init_crypto 3 1783748f3d7Sschwarzeor even none at all. 1793748f3d7Sschwarze.Pp 1803748f3d7Sschwarze.Fn RSA_get_ex_data 1813748f3d7Sschwarzedoes not distinguish success from failure. 1823748f3d7SschwarzeConsequently, after 1833748f3d7Sschwarze.Fn RSA_get_ex_data 1843748f3d7Sschwarzereturns 1853748f3d7Sschwarze.Dv NULL , 1863748f3d7Sschwarze.Xr ERR_get_error 3 1873748f3d7Sschwarzereturns 0 unless there is still an earlier error in the queue. 18829ab75b0Sschwarze.Sh SEE ALSO 189dc754f73Sschwarze.Xr BIO_set_ex_data 3 , 19029ab75b0Sschwarze.Xr CRYPTO_set_ex_data 3 , 191dc754f73Sschwarze.Xr DH_set_ex_data 3 , 192dc754f73Sschwarze.Xr DSA_set_ex_data 3 , 193dc754f73Sschwarze.Xr RSA_new 3 , 194baea8044Sschwarze.Xr SSL_CTX_set_ex_data 3 , 195baea8044Sschwarze.Xr SSL_SESSION_set_ex_data 3 , 196baea8044Sschwarze.Xr SSL_set_ex_data 3 , 197baea8044Sschwarze.Xr X509_STORE_CTX_set_ex_data 3 , 198baea8044Sschwarze.Xr X509_STORE_set_ex_data 3 19929ab75b0Sschwarze.Sh HISTORY 2004b12da35SschwarzeThese functions first appeared in SSLeay 0.9.0 2014b12da35Sschwarzeand have been available since 2026b430279Sschwarze.Ox 2.4 . 2033748f3d7Sschwarze.Sh CAVEATS 2043748f3d7SschwarzeA relatively small minority of application programs 2053748f3d7Sschwarzeattempt to change the API contract such that 2063748f3d7Sschwarze.Fn RSA_set_ex_data 2073748f3d7Sschwarzetransfers ownership of the 2083748f3d7Sschwarze.Fa data 2093748f3d7Sschwarzeto the 2103748f3d7Sschwarze.Fa rsa 2113748f3d7Sschwarzeobject. 2123748f3d7SschwarzeThey do this by providing a 2133748f3d7Sschwarze.Fa free_func 2143748f3d7Sschwarzethat calls 2153748f3d7Sschwarze.Xr free 3 2163748f3d7Sschwarzeor higher-level 2173748f3d7Sschwarze.Fn *_free 2183748f3d7Sschwarzefunctions on the 2193748f3d7Sschwarze.Fa data 2203748f3d7Sschwarzeand sometimes also attempt additional cleanup work as a side effect. 2213748f3d7Sschwarze.Pp 2223748f3d7SschwarzeThis practice is discouraged for several reasons: 2233748f3d7Sschwarze.Bl -enum 2243748f3d7Sschwarze.It 2253748f3d7SschwarzeDue to a massive design mistake in the low-level API function 2263748f3d7Sschwarze.Xr CRYPTO_free_ex_data 3 , 2273748f3d7Sschwarzethis practice creates a possibility that 2283748f3d7Sschwarze.Xr RSA_free 3 2293748f3d7Sschwarzemay fail due to memory allocation failure, consequently leaking the 2303748f3d7Sschwarzememory containing the application specific data and silently skipping 2313748f3d7Sschwarzeany additional cleanup work the 2323748f3d7Sschwarze.Fa free_func 2333748f3d7Sschwarzewas supposed to do, leaving the application in an undetectably 2343748f3d7Sschwarzeinconsistent state. 2353748f3d7SschwarzeArguably, leaking additional memory while trying to free some 2363748f3d7Sschwarzeis most unfortunate especially when the program 2373748f3d7Sschwarzeis already starved for memory. 2383748f3d7Sschwarze.It 2393748f3d7SschwarzeThis practice introduces a risk of use-after-free and double-free 2403748f3d7Sschwarzebugs in case the 2413748f3d7Sschwarze.Fa rsa 2423748f3d7Sschwarzeobject gets destructed while a caller of 2433748f3d7Sschwarze.Fn RSA_set_ex_data 2443748f3d7Sschwarzeor 2453748f3d7Sschwarze.Fn RSA_get_ex_data 2463748f3d7Sschwarzestill holds a 2473748f3d7Sschwarze.Fa data 2483748f3d7Sschwarzepointer. 2493748f3d7SschwarzeNo such risk exists when no 2503748f3d7Sschwarze.Fa free_func 2513748f3d7Sschwarzeis installed. 2523748f3d7Sschwarze.It 2533748f3d7SschwarzeAttempting additional cleanup work in 2543748f3d7Sschwarze.Fa free_func 2553748f3d7Sschwarzeis an even worse idea because 2563748f3d7Sschwarze.Fa free_func 2573748f3d7Sschwarzeis unable to report any issues it might detect while doing that work. 2583748f3d7SschwarzeInstead, if any additional cleanup work is needed, it is recommended 2593748f3d7Sschwarzethat the calling code takes care of that before calling 2603748f3d7Sschwarze.Xr RSA_free 3 . 2613748f3d7Sschwarze.El 2623748f3d7Sschwarze.Pp 2633748f3d7SschwarzeEven fewer application programs install a 2643748f3d7Sschwarze.Fa new_func 2653748f3d7Sschwarzethat allocates memory and stores a pointer to it in the 2663748f3d7Sschwarze.Fa rsa 2673748f3d7Sschwarzeobject by calling 2683748f3d7Sschwarze.Xr CRYPTO_set_ex_data 3 . 2693748f3d7SschwarzeThat is useless because 2703748f3d7Sschwarze.Fa new_func 2713748f3d7Sschwarzedoes not have access to any useful information it could store in such memory 2723748f3d7Sschwarzeand because the default return value of 2733748f3d7Sschwarze.Dv NULL 2743748f3d7Sschwarzefrom 2753748f3d7Sschwarze.Fn RSA_get_ex_data 2763748f3d7Sschwarzeis sufficient to indicate 2773748f3d7Sschwarzethat no application specific data has been stored yet. 2783748f3d7SschwarzeIn addition, allocating memory in 2793748f3d7Sschwarze.Fa new_func 2803748f3d7Sschwarzeis also inadvisable because it introduces an additional responsibility 2813748f3d7Sschwarzefor callers of 2823748f3d7Sschwarze.Fn RSA_set_ex_data 2833748f3d7Sschwarzeto always call 2843748f3d7Sschwarze.Fn RSA_get_ex_data 2853748f3d7Sschwarzefirst, even when it is the first time the application wants to set 2863748f3d7Sschwarzeapplication specific data in a particular 2873748f3d7Sschwarze.Fa rsa 2883748f3d7Sschwarzeobject, and to either modify whatever 2893748f3d7Sschwarze.Fn RSA_get_ex_data 2903748f3d7Sschwarzereturns or to free it before calling 2913748f3d7Sschwarze.Fn RSA_set_ex_data . 2923748f3d7SschwarzeIf that is forgotten, a memory leak results. 2933748f3d7Sschwarze.Pp 2943748f3d7SschwarzeConsequently, allocating any required memory 2953748f3d7Sschwarzeis better left to the application code that calls 2963748f3d7Sschwarze.Fn RSA_set_ex_data . 2973748f3d7Sschwarze.Pp 2983748f3d7SschwarzeInstalling a 29929ab75b0Sschwarze.Fa dup_func 3003748f3d7Sschwarzeis often seen in combination with installing a 3013748f3d7Sschwarze.Fa free_func , 3023748f3d7Sschwarzefor obvious reasons. 3033748f3d7SschwarzeIt is rarely useful because for most parent object types 3043748f3d7Sschwarzethat support ex_data, including for 3053748f3d7Sschwarze.Vt RSA , 3063748f3d7Sschwarzethe library does not provide a copying API function in the first place, and 3073748f3d7Sschwarzeeven where copying functions exist, they tend to be fragile and error-prone. 3083748f3d7SschwarzeWhen a new object is needed, it is usually advisable to construct it from 3093748f3d7Sschwarzescratch whenever possible, rather than attempting a copy operation. 31029ab75b0Sschwarze.Pp 3113748f3d7SschwarzeOn top of that, if 3123748f3d7Sschwarze.Fa dup_func 3133748f3d7Sschwarzefails, for example because of a memory allocation failure, the 3143748f3d7Sschwarzefailure is neither reported nor detectable in any way, leaving the 3153748f3d7Sschwarzenew parent object with incomplete data and potentially in an 3163748f3d7Sschwarzeinconsistent state. 3173748f3d7Sschwarze.Sh BUGS 3183748f3d7SschwarzeIf 3193748f3d7Sschwarze.Fn RSA_set_ex_data 3203748f3d7Sschwarzefails, recovery is very difficult. 3213748f3d7SschwarzeIn particular, calling 3223748f3d7Sschwarze.Xr RSA_free 3 3233748f3d7Sschwarzeon the parent 3243748f3d7Sschwarze.Fa rsa 3253748f3d7Sschwarzeobject right afterwards is likely to also hit a memory allocation 3263748f3d7Sschwarzefailure, leaking all memory internally allocated by all earlier calls of 3273748f3d7Sschwarze.Fn RSA_set_ex_data 3283748f3d7Sschwarzeon 3293748f3d7Sschwarze.Fa rsa 3303748f3d7Sschwarzerather than freeing that memory. 3313748f3d7SschwarzeIn order to recover, the application program 3323748f3d7Sschwarzewould have to free a sufficient amount of 3333748f3d7Sschwarze.Em other 3343748f3d7Sschwarzememory before calling 3353748f3d7Sschwarze.Xr RSA_free 3 , 3363748f3d7Sschwarzewhich will rarely be feasible. 3373748f3d7SschwarzeConsequently, after a failure of 3383748f3d7Sschwarze.Fn RSA_set_ex_data , 3393748f3d7Sschwarzeterminating the program is likely the only reasonable option. 34029ab75b0Sschwarze.Pp 3413748f3d7SschwarzeIf 3423748f3d7Sschwarze.Fn RSA_set_ex_data 3433748f3d7Sschwarzeis called with an 3443748f3d7Sschwarze.Fa idx 3453748f3d7Sschwarzeargument greater than the last one previously returned from 3463748f3d7Sschwarze.Fn RSA_get_ex_new_index , 3473748f3d7Sschwarzeit may still succeed, and though that is not guaranteed by the API, 3483748f3d7Sschwarzeretrieving the 3493748f3d7Sschwarze.Fa data 3503748f3d7Sschwarzefrom such a bogus 3513748f3d7Sschwarze.Fa idx 3523748f3d7Sschwarzemay even be possible with 3533748f3d7Sschwarze.Fn RSA_get_ex_data , 3543748f3d7Sschwarzehiding the bug in the application program that caused passing the bogus 3553748f3d7Sschwarze.Fa idx 3563748f3d7Sschwarzeto 3573748f3d7Sschwarze.Fn RSA_set_ex_data 3583748f3d7Sschwarzein the first place. 3593748f3d7Sschwarze.Pp 3603748f3d7SschwarzeIf the bogus 3613748f3d7Sschwarze.Fa idx 3623748f3d7Sschwarzeargument is large, 3633748f3d7Sschwarze.Fn RSA_set_ex_data 3643748f3d7Sschwarzemay uselessly allocate a large amount of memory. 3653748f3d7SschwarzeCalling 3663748f3d7Sschwarze.Xr RSA_free 3 3673748f3d7Sschwarzeon the parent 3683748f3d7Sschwarze.Fa rsa 3693748f3d7Sschwarzeobject is the only way to recover that memory. 3703748f3d7Sschwarze.Pp 3713748f3d7SschwarzeIf the bogus 3723748f3d7Sschwarze.Fa idx 3733748f3d7Sschwarzeargument is very large, 3743748f3d7Sschwarze.Fn RSA_set_ex_data 3753748f3d7Sschwarzeis likely to cause a significant delay before eventually failing 3763748f3d7Sschwarzedue to memory exhaustion. 3773748f3d7SschwarzeIt is likely to return without releasing the memory already 3783748f3d7Sschwarzeallocated, causing any subsequent attempt to allocate memory 3793748f3d7Sschwarzefor other purposes to fail, too. 3803748f3d7SschwarzeIn this situation, what was said above about failure of 3813748f3d7Sschwarze.Fn RSA_set_ex_data 3823748f3d7Sschwarzeapplies, so terminating the program is likely the only reasonable option. 383