]> git.ipfire.org Git - thirdparty/squid.git/blame - test-suite/splay.cc
SourceFormat Enforcement
[thirdparty/squid.git] / test-suite / splay.cc
CommitLineData
4e0938ef 1/*
4ac4a490 2 * Copyright (C) 1996-2017 The Squid Software Foundation and contributors
4e0938ef
AJ
3 *
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
7 */
8
b67e2c8c 9/*
b67e2c8c 10 * based on ftp://ftp.cs.cmu.edu/user/sleator/splaying/top-down-splay.c
11 * http://bobo.link.cs.cmu.edu/cgi-bin/splay/splay-cgi.pl
12 */
13
f7f3304a 14#include "squid.h"
61bf2627
AJ
15#include "splay.h"
16#include "util.h"
b67e2c8c 17
074d6a40 18#include <cstdlib>
b67e2c8c 19#if HAVE_UNISTD_H
20#include <unistd.h>
21#endif
61bf2627 22#include <random>
42a503bd 23
24class intnode
25{
26
27public:
26ac0430 28 intnode() : i(0) {}
42a503bd 29
30 intnode (int anInt) : i (anInt) {}
31
b67e2c8c 32 int i;
42a503bd 33};
b67e2c8c 34
35int
29b17d63 36compareintvoid(void * const &a, void * const &n)
b67e2c8c 37{
38 intnode *A = (intnode *)a;
39 intnode *B = (intnode *)n;
b67e2c8c 40 return A->i - B->i;
41}
42
29b17d63 43int
44compareint(intnode * const &a, intnode * const &b)
45{
46 return a->i - b->i;
47}
48
23087cb8 49class SplayCheck
50{
42a503bd 51
52public:
23087cb8 53 static void BeginWalk();
54 static int LastValue;
55 static bool ExpectedFail;
56 static void WalkVoid(void *const &, void *);
57 static void WalkNode(intnode *const &, void *);
58 static void WalkNodeRef(intnode const &, void *);
59 static void CheckNode(intnode const &);
60};
61
62int SplayCheck::LastValue (0);
63bool SplayCheck::ExpectedFail (false);
64
b67e2c8c 65void
23087cb8 66SplayCheck::BeginWalk()
b67e2c8c 67{
23087cb8 68 LastValue = 0;
b67e2c8c 69}
70
29b17d63 71void
23087cb8 72SplayCheck::WalkVoid(void *const &node, void *state)
29b17d63 73{
23087cb8 74 intnode *A = (intnode *)node;
75 CheckNode(*A);
76}
77
78void
79SplayCheck::CheckNode(intnode const &A)
80{
81 if (LastValue > A.i) {
42a503bd 82 /* failure */
83
84 if (!ExpectedFail)
85 exit (1);
23087cb8 86 } else
42a503bd 87 /* success */
88 if (ExpectedFail)
89 exit (1);
90
23087cb8 91 LastValue = A.i;
92}
93
94void
95SplayCheck::WalkNode (intnode *const &a, void *state)
96{
97 CheckNode (*a);
98}
99
100void
101SplayCheck::WalkNodeRef (intnode const &a, void *state)
102{
103 CheckNode (a);
29b17d63 104}
105
106void
107destintvoid(void * &data)
108{
109 intnode *i = (intnode *)data;
110 xfree (i);
111}
112
113void
114destint(intnode * &data)
115{
116 delete data;
117}
118
119int
120compareintref(intnode const &a, intnode const &b)
121{
122 return a.i - b.i;
123}
124
29b17d63 125void
126destintref (intnode &)
42a503bd 127{}
29b17d63 128
b67e2c8c 129int
130main(int argc, char *argv[])
131{
61bf2627 132 std::mt19937 generator;
8ed8fa40 133 xuniform_int_distribution<int> distribution;
61bf2627
AJ
134 auto nextRandom = std::bind (distribution, generator);
135
42a503bd 136 {
42a503bd 137 /* test void * splay containers */
138 splayNode *top = NULL;
42a503bd 139
61bf2627
AJ
140 for (int i = 0; i < 100; ++i) {
141 intnode *I = (intnode *)xcalloc(sizeof(intnode), 1);
142 I->i = nextRandom();
bf0e740b
FC
143 if (top)
144 top = top->insert(I, compareintvoid);
145 else
146 top = new splayNode(static_cast<void*>(new intnode(101)));
42a503bd 147 }
148
149 SplayCheck::BeginWalk();
b001e822 150 top->walk(SplayCheck::WalkVoid, NULL);
42a503bd 151
152 SplayCheck::BeginWalk();
153 top->walk(SplayCheck::WalkVoid, NULL);
154 top->destroy(destintvoid);
29b17d63 155 }
42a503bd 156
29b17d63 157 /* test typesafe splay containers */
42a503bd 158 {
159 /* intnode* */
bf0e740b 160 SplayNode<intnode *> *safeTop = new SplayNode<intnode *>(new intnode(101));
42a503bd 161
14942edd 162 for ( int i = 0; i < 100; ++i) {
42a503bd 163 intnode *I;
164 I = new intnode;
61bf2627 165 I->i = nextRandom();
42a503bd 166 safeTop = safeTop->insert(I, compareint);
167 }
168
169 SplayCheck::BeginWalk();
170 safeTop->walk(SplayCheck::WalkNode, NULL);
171
172 safeTop->destroy(destint);
29b17d63 173 }
42a503bd 174 {
175 /* intnode */
bf0e740b 176 SplayNode<intnode> *safeTop = new SplayNode<intnode>(101);
42a503bd 177
14942edd 178 for (int i = 0; i < 100; ++i) {
42a503bd 179 intnode I;
61bf2627 180 I.i = nextRandom();
42a503bd 181 safeTop = safeTop->insert(I, compareintref);
182 }
183
184 SplayCheck::BeginWalk();
185 safeTop->walk(SplayCheck::WalkNodeRef, NULL);
186
187 safeTop->destroy(destintref);
b67e2c8c 188 }
9dca980d 189
23087cb8 190 /* check the check routine */
9dca980d
AJ
191 {
192 SplayCheck::BeginWalk();
193 intnode I;
194 I.i = 1;
195 /* check we don't segfault on NULL splay calls */
196 SplayCheck::WalkNodeRef(I, NULL);
197 I.i = 0;
198 SplayCheck::ExpectedFail = true;
199 SplayCheck::WalkNodeRef(I, NULL);
200 }
42a503bd 201
4c50505b 202 {
42a503bd 203 /* check for begin() */
bf0e740b 204 Splay<intnode> *safeTop = new Splay<intnode>();
42a503bd 205
206 if (safeTop->start() != NULL)
207 exit (1);
208
ccd33084 209 if (safeTop->finish() != NULL)
42a503bd 210 exit (1);
211
14942edd 212 for (int i = 0; i < 100; ++i) {
42a503bd 213 intnode I;
61bf2627 214 I.i = nextRandom();
42a503bd 215
216 if (I.i > 50 && I.i < 10000000)
bf0e740b 217 safeTop->insert(I, compareintref);
42a503bd 218 }
219
220 {
221 intnode I;
222 I.i = 50;
bf0e740b 223 safeTop->insert (I, compareintref);
42a503bd 224 I.i = 10000000;
bf0e740b 225 safeTop->insert (I, compareintref);
42a503bd 226 }
227
228 if (!safeTop->start())
229 exit (1);
230
231 if (safeTop->start()->data.i != 50)
232 exit (1);
233
ccd33084 234 if (!safeTop->finish())
42a503bd 235 exit (1);
236
ccd33084 237 if (safeTop->finish()->data.i != 10000000)
42a503bd 238 exit (1);
239
240 safeTop->destroy(destintref);
4c50505b 241 }
42a503bd 242
4c50505b 243 {
42a503bd 244 Splay<intnode *> aSplay;
245
246 if (aSplay.start() != NULL)
247 exit (1);
248
249 if (aSplay.size() != 0)
250 exit (1);
251
252 aSplay.insert (new intnode(5), compareint);
253
254 if (aSplay.start() == NULL)
255 exit (1);
256
257 if (aSplay.size() != 1)
258 exit (1);
259
260 aSplay.destroy(destint);
261
262 if (aSplay.start() != NULL)
263 exit (1);
264
265 if (aSplay.size() != 0)
266 exit (1);
4c50505b 267 }
42a503bd 268
cb1e2244 269 /* TODO: also test the other Splay API */
bf0e740b 270
b67e2c8c 271 return 0;
272}
f53969cc 273