00001
00002
00003
00004
00005
00006
00007 #include "unimountgen.h"
00008 #include "wvmoniker.h"
00009
00010
00011
00012 WvString UniMountGen::get(const UniConfKey &key)
00013 {
00014 UniGenMount *found = findmount(key);
00015 if (!found)
00016 return WvString::null;
00017
00018 return found->gen->get(trimkey(found->key, key));
00019 }
00020
00021
00022 void UniMountGen::set(const UniConfKey &key, WvStringParm value)
00023 {
00024 UniGenMount *found = findmount(key);
00025 if (!found)
00026 return;
00027
00028 found->gen->set(trimkey(found->key, key), value);
00029 }
00030
00031
00032 bool UniMountGen::exists(const UniConfKey &key)
00033 {
00034 UniGenMount *found = findmount(key);
00035 if (!found)
00036 return false;
00037
00038 return found->gen->exists(trimkey(found->key, key));
00039 }
00040
00041
00042 bool UniMountGen::haschildren(const UniConfKey &key)
00043 {
00044 UniGenMount *found = findmount(key);
00045 if (!found)
00046 return false;
00047
00048 if (found->gen->haschildren(trimkey(found->key, key)))
00049 return true;
00050
00051
00052
00053
00054 MountList::Iter i(mounts);
00055 for (i.rewind(); i.next(); )
00056 {
00057 if (key.suborsame(i->key))
00058 return true;
00059
00060
00061
00062 if (i->gen == found->gen)
00063 break;
00064 }
00065
00066 return false;
00067 }
00068
00069
00070 bool UniMountGen::refresh()
00071 {
00072 hold_delta();
00073
00074 bool result = true;
00075
00076 MountList::Iter i(mounts);
00077 for (i.rewind(); i.next(); )
00078 result = result && i->gen->refresh();
00079
00080 unhold_delta();
00081 return result;
00082 }
00083
00084
00085 void UniMountGen::commit()
00086 {
00087 hold_delta();
00088
00089 MountList::Iter i(mounts);
00090 for (i.rewind(); i.next();)
00091 i->gen->commit();
00092
00093 unhold_delta();
00094 }
00095
00096
00097 UniConfGen *UniMountGen::mount(const UniConfKey &key,
00098 WvStringParm moniker, bool refresh)
00099 {
00100 UniConfGen *gen = wvcreate<UniConfGen>(moniker);
00101 if (gen)
00102 mountgen(key, gen, refresh);
00103
00104 assert(gen && "Moniker doesn't get us a generator!");
00105 return gen;
00106 }
00107
00108
00109 UniConfGen *UniMountGen::mountgen(const UniConfKey &key,
00110 UniConfGen *gen, bool refresh)
00111 {
00112 if (!gen)
00113 return NULL;
00114
00115 UniGenMount *newgen = new UniGenMount(gen, key);
00116 gen->setcallback(UniConfGenCallback(this,
00117 &UniMountGen::gencallback), &newgen->key);
00118
00119 hold_delta();
00120 delta(key, WvString());
00121
00122 makemount(key);
00123
00124 if (gen && refresh)
00125 gen->refresh();
00126
00127 mounts.prepend(newgen, true);
00128
00129 delta(key, get(key));
00130 unhold_delta();
00131 return gen;
00132 }
00133
00134
00135 void UniMountGen::unmount(UniConfGen *gen, bool commit)
00136 {
00137 if (!gen)
00138 return;
00139
00140 MountList::Iter i(mounts);
00141
00142 for (i.rewind(); i.next() && i->gen != gen; )
00143 ;
00144
00145 if (i->gen != gen)
00146 return;
00147
00148 hold_delta();
00149
00150 if (commit)
00151 gen->commit();
00152 gen->setcallback(UniConfGenCallback(), NULL);
00153
00154 UniConfKey key(i->key);
00155 UniConfGen *next = NULL;
00156
00157 delta(key, WvString());
00158
00159
00160
00161
00162
00163 i.xunlink();
00164 if (i.next())
00165 next = i->gen;
00166
00167 for (i.rewind(); i.next() && i->gen != next; )
00168 {
00169 if (key.suborsame(i->key) && key != i->key)
00170 {
00171 makemount(i->key);
00172 delta(i->key, get(i->key));
00173 }
00174 }
00175
00176 unhold_delta();
00177 }
00178
00179
00180 UniConfGen *UniMountGen::whichmount(const UniConfKey &key,
00181 UniConfKey *mountpoint)
00182 {
00183 MountList::Iter i(mounts);
00184
00185 for (i.rewind(); i.next(); )
00186 {
00187 if (i->key.suborsame(key))
00188 {
00189 if (mountpoint)
00190 *mountpoint = key;
00191 return i->gen;
00192 }
00193 }
00194
00195 return NULL;
00196 }
00197
00198
00199 bool UniMountGen::ismountpoint(const UniConfKey &key)
00200 {
00201 MountList::Iter i(mounts);
00202
00203 for (i.rewind(); i.next(); )
00204 {
00205 if (i->key == key)
00206 return true;
00207 }
00208
00209 return false;
00210 }
00211
00212
00213 UniMountGen::Iter *UniMountGen::iterator(const UniConfKey &key)
00214 {
00215 UniGenMount *found = findmount(key);
00216 if (found)
00217 return found->gen->iterator(trimkey(found->key, key));
00218 return new NullIter;
00219 }
00220
00221
00222 UniMountGen::UniGenMount *UniMountGen::findmount(const UniConfKey &key)
00223 {
00224
00225 MountList::Iter i(mounts);
00226 for (i.rewind(); i.next(); )
00227 {
00228 if (i->key.suborsame(key))
00229 return i.ptr();
00230 }
00231
00232 return NULL;
00233 }
00234
00235
00236 void UniMountGen::gencallback(const UniConfKey &key, WvStringParm value,
00237 void *userdata)
00238 {
00239 UniConfKey *base = static_cast<UniConfKey*>(userdata);
00240 delta(UniConfKey(*base, key), value);
00241 }
00242
00243
00244 void UniMountGen::makemount(const UniConfKey &key)
00245 {
00246
00247
00248 UniConfKey::Iter i(key);
00249 UniConfKey points;
00250
00251 for (i.rewind(); i.next(); )
00252 {
00253 points.append(*i);
00254 if (get(points).isnull())
00255 set(points, "");
00256 }
00257
00258
00259
00260
00261 UniGenMount *found = findmount(points.removelast());
00262 if (!found)
00263 return;
00264
00265 if (found->gen->get(trimkey(found->key, key)).isnull())
00266 found->gen->set(trimkey(found->key, key), "");
00267 }