]> git.ipfire.org Git - thirdparty/squid.git/blame - src/tests/testUfs.cc
Bug 3686: cache_dir max-size default fails
[thirdparty/squid.git] / src / tests / testUfs.cc
CommitLineData
8e46cda5 1#define SQUID_UNIT_TEST 1
ff173e9a 2#include "squid.h"
c8f4eac4 3#include "testUfs.h"
c8f4eac4 4#include "Store.h"
5#include "SwapDir.h"
6#include "DiskIO/DiskIOModule.h"
7#include "fs/ufs/ufscommon.h"
8#include "Mem.h"
aa839030 9#include "MemObject.h"
c8f4eac4 10#include "HttpHeader.h"
11#include "HttpReply.h"
8ff3fa2e 12#include "testStoreSupport.h"
c8f4eac4 13
27e059d4
AJ
14#if HAVE_STDEXCEPT
15#include <stdexcept>
16#endif
17
2e050051 18#define TESTDIR "testUfs__testUfsSearch"
19
c8f4eac4 20CPPUNIT_TEST_SUITE_REGISTRATION( testUfs );
21
22typedef RefCount<UFSSwapDir> SwapDirPointer;
adf8c195 23extern REMOVALPOLICYCREATE createRemovalPolicy_lru; /* XXX fails with --enable-removal-policies=heap */
c8f4eac4 24
25static void
26addSwapDir(SwapDirPointer aStore)
27{
28 allocate_new_swapdir(&Config.cacheSwap);
29 Config.cacheSwap.swapDirs[Config.cacheSwap.n_configured] = aStore.getRaw();
30 ++Config.cacheSwap.n_configured;
31}
32
33/* TODO make this a cbdata class */
34
35static bool cbcalled;
36
37static void
38searchCallback(void *cbdata)
39{
40 cbcalled = true;
41}
42
43void
b7717b61 44testUfs::commonInit()
c8f4eac4 45{
b7717b61 46 static bool inited = false;
c8f4eac4 47
b7717b61 48 if (inited)
49 return;
c8f4eac4 50
51 Config.Store.avgObjectSize = 1024;
52
53 Config.Store.objectsPerBucket = 20;
54
55 Config.Store.maxObjectSize = 2048;
56
57 Config.store_dir_select_algorithm = xstrdup("round-robin");
58
59 Config.replPolicy = new RemovalPolicySettings;
60
61 Config.replPolicy->type = xstrdup ("lru");
62
63 /* garh garh */
64 storeReplAdd("lru", createRemovalPolicy_lru);
65
66 Mem::Init();
67
c8f4eac4 68 comm_init();
69
70 httpHeaderInitModule(); /* must go before any header processing (e.g. the one in errorInitialize) */
71
72 httpReplyInitModule(); /* must go before accepting replies */
73
b7717b61 74 inited = true;
75}
76
77void
78testUfs::testUfsSearch()
79{
80 /* test sequence
81 * make a valid working ufs swapdir
82 * put two entries in it and sync logs
83 * search the ufs dir
84 * check the entries we find are what we want
85 */
86
87 if (0 > system ("rm -rf " TESTDIR))
88 throw std::runtime_error("Failed to clean test work directory");
89
4be0b9a1 90 Store::Root(new StoreController);
b7717b61 91
92 SwapDirPointer aStore (new UFSSwapDir("ufs", "Blocking"));
93
94 aStore->IO = new UFSStrategy(DiskIOModule::Find("Blocking")->createStrategy());
95
96 addSwapDir(aStore);
97
98 commonInit();
c8f4eac4 99 mem_policy = createRemovalPolicy(Config.replPolicy);
100
b7717b61 101
2e050051 102 char *path=xstrdup(TESTDIR);
c8f4eac4 103
104 char *config_line=xstrdup("foo 100 1 1");
105
474dfa84 106 visible_appname_string = xstrdup(PACKAGE "/" VERSION);
107
c8f4eac4 108 strtok(config_line, w_space);
109
110 aStore->parse(0, path);
6c2358fc 111 store_maxobjsize = 1024*1024*2;
c8f4eac4 112
113 safe_free(path);
114
115 safe_free(config_line);
116
117 /* ok, ready to create */
118 aStore->create();
119
8ff3fa2e 120 /* ok, ready to use - inits store & hash too */
c8f4eac4 121 Store::Root().init();
122
bef81ea5 123 /* our swapdir must be scheduled to rebuild */
1f8dc0fb 124 CPPUNIT_ASSERT_EQUAL(2, StoreController::store_dirs_rebuilding);
bef81ea5 125
8ff3fa2e 126 /* rebuild is a scheduled event */
127 StockEventLoop loop;
128
1f8dc0fb 129 while (StoreController::store_dirs_rebuilding > 1)
bef81ea5 130 loop.runOnce();
c8f4eac4 131
bef81ea5 132 /* cannot use loop.run(); as the loop will never idle: the store-dir
26ac0430 133 * clean() scheduled event prevents it
bef81ea5 134 */
c8f4eac4 135
bef81ea5 136 /* nothing left to rebuild */
1f8dc0fb 137 CPPUNIT_ASSERT_EQUAL(1, StoreController::store_dirs_rebuilding);
c8f4eac4 138
139 /* add an entry */
140 {
141 /* Create "vary" base object */
142 request_flags flags;
143 flags.cachable = 1;
144 StoreEntry *pe = storeCreateEntry("dummy url", "dummy log url", flags, METHOD_GET);
f46fe759 145 HttpReply *rep = (HttpReply *) pe->getReply(); // bypass const
6c2358fc 146 rep->setHeaders(HTTP_OK, "dummy test object", "x-squid-internal/test", 0, -1, squid_curtime + 100000);
c8f4eac4 147
d88e3c49 148 pe->setPublicKey();
c8f4eac4 149
3900307b 150 pe->buffer();
c8f4eac4 151 /* TODO: remove this when the metadata is separated */
152 {
153 Packer p;
154 packerToStoreInit(&p, pe);
f46fe759 155 pe->getReply()->packHeadersInto(&p);
c8f4eac4 156 packerClean(&p);
157 }
158
3900307b 159 pe->flush();
160 pe->timestampsSet();
c8f4eac4 161 pe->complete();
c07cbbf4 162 pe->swapOut();
c8f4eac4 163 CPPUNIT_ASSERT(pe->swap_dirn == 0);
164 CPPUNIT_ASSERT(pe->swap_filen == 0);
97b5e68f 165 pe->unlock();
c8f4eac4 166 }
167
168 storeDirWriteCleanLogs(0);
169
170 /* here we cheat: we know that UFSSwapDirs search off disk. If we did an init call to a new
171 * swapdir instance, we'd not be testing a clean build.
172 */
173 StoreSearchPointer search = aStore->search (NULL, NULL); /* search for everything in the store */
174
175 /* nothing should be immediately available */
176#if 0
177
178 CPPUNIT_ASSERT(search->next() == false);
179#endif
180
181 CPPUNIT_ASSERT(search->error() == false);
182 CPPUNIT_ASSERT(search->isDone() == false);
183 CPPUNIT_ASSERT(search->currentItem() == NULL);
184
185 /* trigger a callback */
186 cbcalled = false;
187 search->next(searchCallback, NULL);
188 CPPUNIT_ASSERT(cbcalled == true);
189
190 /* we should have access to a entry now, that matches the entry we had before */
191 //CPPUNIT_ASSERT(search->next() == false);
192 CPPUNIT_ASSERT(search->error() == false);
193 CPPUNIT_ASSERT(search->isDone() == false);
194 CPPUNIT_ASSERT(search->currentItem() != NULL);
195
196 /* trigger another callback */
197 cbcalled = false;
198 search->next(searchCallback, NULL);
199 CPPUNIT_ASSERT(cbcalled == true);
200
201 /* now we should have no error, we should have finished and have no current item */
202 //CPPUNIT_ASSERT(search->next() == false);
203 CPPUNIT_ASSERT(search->error() == false);
204 CPPUNIT_ASSERT(search->isDone() == true);
205 CPPUNIT_ASSERT(search->currentItem() == NULL);
206
4be0b9a1
AR
207 Store::Root(NULL);
208
c8f4eac4 209 free_cachedir(&Config.cacheSwap);
210
211 /* todo: here we should test a dirty rebuild */
212
b7717b61 213 safe_free(Config.replPolicy->type);
214 delete Config.replPolicy;
215
216 if (0 > system ("rm -rf " TESTDIR))
217 throw std::runtime_error("Failed to clean test work directory");
218}
219
26ac0430 220/* The UFS store should always configure an IO engine even if none is
b7717b61 221 * supplied on the configuration line.
222 */
223void
224testUfs::testUfsDefaultEngine()
225{
226 /* boring common test boilerplate */
227 if (0 > system ("rm -rf " TESTDIR))
228 throw std::runtime_error("Failed to clean test work directory");
229
fe36168c 230 // This assertion may fail if previous test cases fail.
231 // Apparently, CPPUNIT_ASSERT* failure may prevent destructors of local
232 // objects such as "StorePointer aRoot" from being called.
233 CPPUNIT_ASSERT(!store_table); // or StoreHashIndex ctor will abort below
234
4be0b9a1 235 Store::Root(new StoreController);
b7717b61 236 SwapDirPointer aStore (new UFSSwapDir("ufs", "Blocking"));
237 addSwapDir(aStore);
238 commonInit();
239 Config.replPolicy = new RemovalPolicySettings;
240 Config.replPolicy->type = xstrdup ("lru");
241 mem_policy = createRemovalPolicy(Config.replPolicy);
242
243 char *path=xstrdup(TESTDIR);
244 char *config_line=xstrdup("foo 100 1 1");
245 strtok(config_line, w_space);
246 aStore->parse(0, path);
247 safe_free(path);
248 safe_free(config_line);
249 CPPUNIT_ASSERT(aStore->IO->io != NULL);
250
b7717b61 251 Store::Root(NULL);
4be0b9a1 252 free_cachedir(&Config.cacheSwap);
c8f4eac4 253 safe_free(Config.replPolicy->type);
254 delete Config.replPolicy;
255
2e050051 256 if (0 > system ("rm -rf " TESTDIR))
c8f4eac4 257 throw std::runtime_error("Failed to clean test work directory");
258}