Line data Source code
1 : /*
2 : Unix SMB/CIFS implementation.
3 :
4 : local testing of idtree routines.
5 :
6 : Copyright (C) Andrew Tridgell 2004
7 :
8 : This program is free software; you can redistribute it and/or modify
9 : it under the terms of the GNU General Public License as published by
10 : the Free Software Foundation; either version 3 of the License, or
11 : (at your option) any later version.
12 :
13 : This program is distributed in the hope that it will be useful,
14 : but WITHOUT ANY WARRANTY; without even the implied warranty of
15 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 : GNU General Public License for more details.
17 :
18 : You should have received a copy of the GNU General Public License
19 : along with this program. If not, see <http://www.gnu.org/licenses/>.
20 : */
21 :
22 : #include "includes.h"
23 : #include "torture/torture.h"
24 : #include "torture/local/proto.h"
25 :
26 0 : static bool torture_local_idtree_simple(struct torture_context *tctx)
27 : {
28 : struct idr_context *idr;
29 : int i, ret;
30 : int *ids;
31 : int *present;
32 : extern int torture_numops;
33 0 : int n = torture_numops;
34 0 : TALLOC_CTX *mem_ctx = tctx;
35 :
36 0 : idr = idr_init(mem_ctx);
37 :
38 0 : ids = talloc_zero_array(mem_ctx, int, n);
39 0 : present = talloc_zero_array(mem_ctx, int, n);
40 :
41 0 : for (i=0;i<n;i++) {
42 0 : ids[i] = -1;
43 : }
44 :
45 0 : for (i=0;i<n;i++) {
46 0 : int ii = random() % n;
47 0 : void *p = idr_find(idr, ids[ii]);
48 0 : if (present[ii]) {
49 0 : if (p != &ids[ii]) {
50 0 : torture_fail(tctx, talloc_asprintf(tctx,
51 : "wrong ptr at %d - %p should be %p",
52 : ii, p, &ids[ii]));
53 : }
54 0 : if (random() % 7 == 0) {
55 0 : if (idr_remove(idr, ids[ii]) != 0) {
56 0 : torture_fail(tctx, talloc_asprintf(tctx,
57 : "remove failed at %d (id=%d)",
58 : i, ids[ii]));
59 : }
60 0 : present[ii] = 0;
61 0 : ids[ii] = -1;
62 : }
63 : } else {
64 0 : if (p != NULL) {
65 0 : torture_fail(tctx,
66 : talloc_asprintf(tctx,
67 : "non-present at %d gave %p (would be %d)",
68 : ii, p,
69 : (int)((((char *)p) - (char *)(&ids[0])) / sizeof(int))));
70 : }
71 0 : if (random() % 5) {
72 0 : ids[ii] = idr_get_new(idr, &ids[ii], n);
73 0 : if (ids[ii] < 0) {
74 0 : torture_fail(tctx, talloc_asprintf(tctx,
75 : "alloc failure at %d (ret=%d)",
76 : ii, ids[ii]));
77 : } else {
78 0 : present[ii] = 1;
79 : }
80 : }
81 : }
82 : }
83 :
84 0 : torture_comment(tctx, "done %d random ops\n", i);
85 :
86 0 : for (i=0;i<n;i++) {
87 0 : if (present[i]) {
88 0 : if (idr_remove(idr, ids[i]) != 0) {
89 0 : torture_fail(tctx, talloc_asprintf(tctx,
90 : "delete failed on cleanup at %d (id=%d)",
91 : i, ids[i]));
92 : }
93 : }
94 : }
95 :
96 : /* now test some limits */
97 0 : for (i=0;i<25000;i++) {
98 0 : ret = idr_get_new_above(idr, &ids[0], random() % 25000, 0x10000-3);
99 0 : torture_assert(tctx, ret != -1, "idr_get_new_above failed");
100 : }
101 :
102 0 : ret = idr_get_new_above(idr, &ids[0], 0x10000-2, 0x10000);
103 0 : torture_assert_int_equal(tctx, ret, 0x10000-2, "idr_get_new_above failed");
104 0 : ret = idr_get_new_above(idr, &ids[0], 0x10000-1, 0x10000);
105 0 : torture_assert_int_equal(tctx, ret, 0x10000-1, "idr_get_new_above failed");
106 0 : ret = idr_get_new_above(idr, &ids[0], 0x10000, 0x10000);
107 0 : torture_assert_int_equal(tctx, ret, 0x10000, "idr_get_new_above failed");
108 0 : ret = idr_get_new_above(idr, &ids[0], 0x10000+1, 0x10000);
109 0 : torture_assert_int_equal(tctx, ret, -1, "idr_get_new_above succeeded above limit");
110 0 : ret = idr_get_new_above(idr, &ids[0], 0x10000+2, 0x10000);
111 0 : torture_assert_int_equal(tctx, ret, -1, "idr_get_new_above succeeded above limit");
112 :
113 0 : torture_comment(tctx, "cleaned up\n");
114 0 : return true;
115 : }
116 :
117 964 : struct torture_suite *torture_local_idtree(TALLOC_CTX *mem_ctx)
118 : {
119 964 : struct torture_suite *suite = torture_suite_create(mem_ctx, "idtree");
120 964 : torture_suite_add_simple_test(suite, "idtree", torture_local_idtree_simple);
121 964 : return suite;
122 : }
|