00001
00002
00003
00004
00005
00006
#include "wvbdbhash.h"
00007
#include "wvhashtable.h"
00008
#include "wvstream.h"
00009
00010 typedef WvBdbHash<WvString,WvString> StrStrMap;
00011
00012
00013
00014
struct KeyVal
00015 {
00016
WvString key;
00017
WvString val;
00018 KeyVal(
WvStringParm k,
WvStringParm v) : key(k), val(v) { }
00019 };
00020
DeclareWvDict(KeyVal,
WvString, key);
00021 KeyValDict
keyvals(3);
00022 KeyValDict::Iter
gi(keyvals);
00023
00024 bool iterdone;
00025
00026 bool cmptest(
WvStringParm wantkey,
WvStringParm wantval,
WvStringParm gotkey,
00027
WvStringParm gotval)
00028 {
00029
if (wantkey != gotkey || wantval != gotval) {
00030
wvcon->
print(
"expect '%s'/'%s', got '%s'/'%s' - FAILED\n",
00031 wantkey, wantval, gotkey, gotval);
00032
return false;
00033 }
else {
00034
wvcon->
print(
"expect '%s'/'%s' - PASSED\n", wantkey, gotval);
00035
return true;
00036 }
00037 }
00038
00039 bool itertest(StrStrMap::Iter &i,
WvStringParm key,
WvStringParm want)
00040 {
00041 i.rewind(key); i.next();
00042
return cmptest(key, want, i.key(), i());
00043 }
00044
00045 bool itertest2(StrStrMap &ss,
WvStringParm key,
WvStringParm want)
00046 {
00047 StrStrMap::Iter i(ss);
00048
return itertest(i, key, want);
00049 }
00050
00051 void itertest3(
WvStream &s,
void *userdata)
00052 {
00053
StrStrMap &ss = *((
StrStrMap *) userdata);
00054
iterdone = !
gi.next();
00055
if (!
iterdone)
itertest2(ss,
gi->key,
gi->val);
00056 s.
alarm(0);
00057 }
00058
00059
00060 int alpha(
const KeyVal *a,
const KeyVal *b)
00061 {
00062
return strcmp(a->key, b->key);
00063 }
00064
00065
00066 bool runtests(StrStrMap &ss)
00067 {
00068
bool good =
true;
00069
00070 {
00071
wvcon->
print(
"\nSimple iter:\n");
00072 StrStrMap::Iter i1(ss);
00073 KeyValDict::Sorter i2(
keyvals,
alpha);
00074 i1.rewind(); i2.rewind();
00075
for (;;)
00076 {
00077
bool i1ok = i1.next();
00078
bool i2ok = i2.next();
00079
if (i1ok != i2ok)
00080
wvcon->
print(
"\nnext() return value out of sync: "
00081
"expected %s, got %s - FAILED\n", i2ok, i1ok);
00082
if (!i1ok || !i2ok)
break;
00083
00084 good =
cmptest(i2->key, i2->val, i1.key(), i1()) && good;
00085 }
00086 }
00087
00088 {
00089
wvcon->
print(
"\nMultiple rewinds:\n");
00090 StrStrMap::Iter i(ss);
00091 KeyValDict::Iter i2(
keyvals);
00092
for (i2.rewind(); i2.next(); )
00093 good =
itertest(i, i2->key, i2->val) && good;
00094 }
00095
00096 {
00097
wvcon->
print(
"\nRecreation of iter:\n");
00098 KeyValDict::Iter i2(
keyvals);
00099
for (i2.rewind(); i2.next(); )
00100 good =
itertest2(ss, i2->key, i2->val) && good;
00101 }
00102
00103 {
00104
wvcon->
print(
"\nRecreation of iter through a callback:\n");
00105
WvStream s;
00106 s.
setcallback(
itertest3, &ss);
00107 s.
alarm(0);
00108
gi.rewind();
00109
iterdone =
false;
00110
while (!
iterdone)
00111
if (s.
select(-1)) s.
callback();
00112 }
00113
00114 {
00115
wvcon->
print(
"\nNested iters:\n");
00116 StrStrMap::Iter i1(ss);
00117 KeyValDict::Sorter i2(
keyvals,
alpha);
00118 i2.rewind(); i1.rewind();
00119
for (;;)
00120 {
00121
bool i1ok = i1.next();
00122
bool i2ok = i2.next();
00123
if (i1ok != i2ok)
00124
wvcon->
print(
"\nnext() return value out of sync: "
00125
"expected %s, got %s - FAILED\n", i2ok, i1ok);
00126
if (!i1ok || !i2ok)
break;
00127
00128 fprintf(stderr,
"\n");
00129 good =
cmptest(i2->key, i2->val, i1.key(), i1()) && good;
00130 fprintf(stderr,
"\n");
00131 KeyValDict::Iter i3(
keyvals);
00132
for (i3.rewind(); i3.next(); )
00133 good =
itertest2(ss, i3->key, i3->val) && good;
00134 }
00135 }
00136
00137 {
00138
wvcon->
print(
"\nUpdate during an iter:\n");
00139 StrStrMap::Iter i1(ss);
00140 KeyValDict::Sorter i2(
keyvals,
alpha);
00141 i2.rewind(); i1.rewind();
00142
for (;;)
00143 {
00144
bool i1ok = i1.next();
00145
bool i2ok = i2.next();
00146
if (i1ok != i2ok)
00147
wvcon->
print(
"\nnext() return value out of sync: "
00148
"expected %s, got %s - FAILED\n", i2ok, i1ok);
00149
if (!i1ok || !i2ok)
break;
00150
00151
if (i1.key() ==
"hello") {
00152 i1() =
"everybody";
00153 i1.save();
00154 }
00155
00156
if (i2->key ==
"hello")
00157 good =
cmptest(i2->key,
"everybody", i1.key(), i1()) && good;
00158
else
00159 good =
cmptest(i2->key, i2->val, i1.key(), i1()) && good;
00160 }
00161 }
00162
00163 {
00164
wvcon->
print(
"\nDelete during an iter:\n");
00165 StrStrMap::Iter i1(ss);
00166 KeyValDict::Sorter i2(
keyvals,
alpha);
00167 i2.rewind(); i1.rewind();
00168
for (;;)
00169 {
00170
bool i1ok = i1.next();
00171
bool i2ok = i2.next();
00172
if (i1ok != i2ok)
00173
wvcon->
print(
"\nnext() return value out of sync: "
00174
"expected %s, got %s - FAILED\n", i2ok, i1ok);
00175
if (!i1ok || !i2ok)
break;
00176
00177
if (i1.key() ==
"hello")
00178 i1.xunlink();
00179
00180
if (i2->key ==
"hello") {
00181
00182
00183 }
00184
else
00185 good =
cmptest(i2->key, i2->val, i1.key(), i1()) && good;
00186 }
00187 }
00188
00189
return good;
00190 }
00191
00192 int main()
00193 {
00194
keyvals.add(
new KeyVal(
"hello",
"world"),
true);
00195
keyvals.add(
new KeyVal(
"i like",
"muffins"),
true);
00196
keyvals.add(
new KeyVal(
"/foo/bar",
"baz"),
true);
00197
keyvals.add(
new KeyVal(
"/",
"slash"),
true);
00198
keyvals.add(
new KeyVal(
"/foo",
"kung foo!"),
true);
00199
00200 {
00201
00202
StrStrMap ss(
"rewindfile");
00203
wvcon->
print(
"\nPopulating named db... ");
00204 ss.
zap();
00205 KeyValDict::Iter i(
keyvals);
00206
for (i.rewind(); i.next(); )
00207 ss.
add(i->key, i->val,
true);
00208
wvcon->
print(
"done\n");
00209
00210
runtests(ss);
00211
00212
00213 assert(ss.
isok());
00214 ss.
seterr(
"Fake err");
00215 assert(!ss.
isok());
00216 ss.
zap();
00217 fprintf(stderr,
"After zap, isok is %d (%s)\n", ss.
isok(), ss.
errstr().
cstr());
00218 }
00219
00220 {
00221
00222
StrStrMap ss;
00223
wvcon->
print(
"\nPopulating anon db... ");
00224 KeyValDict::Iter i(
keyvals);
00225
for (i.rewind(); i.next(); )
00226 ss.
add(i->key, i->val);
00227
wvcon->
print(
"done\n");
00228
00229
runtests(ss);
00230
00231
00232 assert(ss.
isok());
00233 ss.
seterr(
"Fake err");
00234 assert(!ss.
isok());
00235 ss.
zap();
00236 fprintf(stderr,
"After zap, isok is %d (%s)\n", ss.
isok(), ss.
errstr().
cstr());
00237 }
00238 }