fb1694dd40aa616e161678c8e32ec0d9648b4e9e
[openssl.git] / test / exdatatest.c
1 /*
2  * Copyright 2015-2017 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the OpenSSL license (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9
10 #include <stdio.h>
11 #include <string.h>
12 #include <stdlib.h>
13 #include <openssl/crypto.h>
14
15 #include "test_main.h"
16 #include "testutil.h"
17
18 static long saved_argl;
19 static void *saved_argp;
20 static int saved_idx;
21 static int gbl_result;
22
23 static void exnew(void *parent, void *ptr, CRYPTO_EX_DATA *ad,
24           int idx, long argl, void *argp)
25 {
26     if (!TEST_int_eq(idx, saved_idx)
27         || !TEST_long_eq(argl, saved_argl)
28         || !TEST_ptr_eq(argp, saved_argp)
29         || !TEST_ptr_null(ptr))
30         gbl_result = 0;
31 }
32
33 static int exdup(CRYPTO_EX_DATA *to, const CRYPTO_EX_DATA *from,
34           void *from_d, int idx, long argl, void *argp)
35 {
36     if (!TEST_int_eq(idx, saved_idx)
37         || !TEST_long_eq(argl, saved_argl)
38         || !TEST_ptr_eq(argp, saved_argp)
39         || !TEST_ptr(from_d))
40         gbl_result = 0;
41     return 1;
42 }
43
44 static void exfree(void *parent, void *ptr, CRYPTO_EX_DATA *ad,
45             int idx, long argl, void *argp)
46 {
47     if (!TEST_int_eq(idx, saved_idx)
48         || !TEST_long_eq(argl, saved_argl)
49         || !TEST_ptr_eq(argp, saved_argp))
50         gbl_result = 0;
51 }
52
53 typedef struct myobj_st {
54     CRYPTO_EX_DATA ex_data;
55     int id;
56     int st;
57 } MYOBJ;
58
59 static MYOBJ *MYOBJ_new()
60 {
61     static int count = 0;
62     MYOBJ *obj = OPENSSL_malloc(sizeof(*obj));
63
64     obj->id = ++count;
65     obj->st = CRYPTO_new_ex_data(CRYPTO_EX_INDEX_APP, obj, &obj->ex_data);
66     return obj;
67 }
68
69 static void MYOBJ_sethello(MYOBJ *obj, char *cp)
70 {
71     obj->st = CRYPTO_set_ex_data(&obj->ex_data, saved_idx, cp);
72     if (!TEST_int_eq(obj->st, 1))
73         gbl_result = 0;
74 }
75
76 static char *MYOBJ_gethello(MYOBJ *obj)
77 {
78     return CRYPTO_get_ex_data(&obj->ex_data, saved_idx);
79 }
80
81 static void MYOBJ_free(MYOBJ *obj)
82 {
83     CRYPTO_free_ex_data(CRYPTO_EX_INDEX_APP, obj, &obj->ex_data);
84     OPENSSL_free(obj);
85 }
86
87 static MYOBJ *MYOBJ_dup(MYOBJ *in)
88 {
89     MYOBJ *obj = MYOBJ_new();
90
91     obj->st |= CRYPTO_dup_ex_data(CRYPTO_EX_INDEX_APP, &obj->ex_data,
92                                  &in->ex_data);
93     return obj;
94 }
95
96 static int test_exdata(void)
97 {
98     MYOBJ *t1, *t2, *t3;
99     const char *cp;
100     char *p;
101
102     gbl_result = 1;
103
104     p = strdup("hello world");
105     saved_argl = 21;
106     saved_argp = malloc(1);
107     saved_idx = CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_APP,
108                                         saved_argl, saved_argp,
109                                         exnew, exdup, exfree);
110     t1 = MYOBJ_new();
111     t2 = MYOBJ_new();
112     if (!TEST_int_eq(t1->st, 1) || !TEST_int_eq(t2->st, 1))
113         return 0;
114
115     MYOBJ_sethello(t1, p);
116     cp = MYOBJ_gethello(t1);
117     if (!TEST_ptr_eq(cp, p))
118         return 0;
119
120     cp = MYOBJ_gethello(t2);
121     if (!TEST_ptr_null(cp))
122         return 0;
123
124     t3 = MYOBJ_dup(t1);
125     if (!TEST_int_eq(t3->st, 1))
126         return 0;
127
128     cp = MYOBJ_gethello(t3);
129     if (!TEST_ptr_eq(cp, p))
130         return 0;
131
132     MYOBJ_free(t1);
133     MYOBJ_free(t2);
134     MYOBJ_free(t3);
135     free(saved_argp);
136     free(p);
137
138     if (gbl_result)
139       return 1;
140     else
141       return 0;
142 }
143
144 void register_tests(void)
145 {
146     ADD_TEST(test_exdata);
147 }