Fix several warnings that appear in gcc 4.3.2.
[wvstreams.git] / uniconf / unidefgen.cc
blob92782ab656776fe7c9d6e984e517780adfa8d3db
1 /*
2 * Worldvisions Weaver Software:
3 * Copyright (C) 2002 Net Integration Technologies, Inc.
4 *
5 * UniDefGen is a UniConfGen for retrieving data with defaults
6 */
7 #include "unidefgen.h"
8 #include "wvmoniker.h"
9 //#include "wvstream.h"
10 #include <ctype.h>
11 #include <stdlib.h>
13 #include "wvlinkerhack.h"
15 WV_LINK(UniDefGen);
18 // if 'obj' is non-NULL and is a UniConfGen, wrap that; otherwise wrap the
19 // given moniker.
20 static IUniConfGen *creator(WvStringParm s, IObject *_obj)
22 return new UniDefGen(wvcreate<IUniConfGen>(s, _obj));
25 // this name is too confusing. We should deprecate it.
26 static WvMoniker<IUniConfGen> reg("default", creator);
28 // a better name for the same thing.
29 static WvMoniker<IUniConfGen> reg2("wildcard", creator);
32 UniConfKey UniDefGen::finddefault(const UniConfKey &key, char *p, char *q)
34 UniConfKey result;
36 if (!p)
38 q++;
39 if (inner() && inner()->exists(q))
40 return q;
41 else
42 return UniConfKey();
45 // pop the first segment of p to r
46 char *r = strchr(p, '/');
47 if (r)
48 *r++ = '\0';
50 // append p to q
51 char *s = strchr(q, '\0');
52 *s++ = '/';
53 *s = 0;
54 q = strcat(q, p);
56 // try this literal path
57 result = finddefault(key, r, q);
58 if (result.numsegments())
59 return result;
61 // replace what used to be p with a *
62 *s++ = '*';
63 *s = '\0';
64 result = finddefault(key, r, q);
66 if (r)
67 *--r = '/';
69 return result;
73 WvString UniDefGen::replacewildcard(const UniConfKey &key,
74 const UniConfKey &defkey, WvStringParm in)
76 // check if the result wants a wildcard ('*n')
77 if (in.len() < 2 || in[0] != '*')
78 return in;
80 const char *s = in.cstr();
81 int idx = atoi(s+1);
82 if (idx == 0)
83 return in;
85 // search backwards for segment num of the n'th wildcard
86 UniConfKey k(defkey);
87 int loc = key.numsegments();
88 for (int i = 0; i < idx; i++)
90 if (i != 0)
92 k = k.removelast();
93 loc--;
95 while (!k.last().iswild())
97 k = k.removelast();
98 loc--;
99 if (k.isempty())
101 // oops, ran out of segments!
102 return WvString();
108 // pull the literal from that segment num of the key
109 return key.segment(loc-1);
113 bool UniDefGen::keymap(const UniConfKey &unmapped_key, UniConfKey &mapped_key)
115 WvString tmp_key(unmapped_key), tmp("");
116 char *p = tmp_key.edit();
118 tmp.setsize(strlen(tmp_key) * 2);
119 char *q = tmp.edit();
120 *q = '\0';
122 mapped_key = finddefault(unmapped_key, p, q);
123 if (!mapped_key.numsegments())
124 mapped_key = unmapped_key;
125 // fprintf(stderr, "mapping '%s' -> '%s'\n", key.cstr(), result.cstr());
127 return true;
131 WvString UniDefGen::get(const UniConfKey &key)
133 UniConfKey mapped_key;
134 if (keymap(key, mapped_key))
135 return replacewildcard(key, mapped_key,
136 inner() ? inner()->get(mapped_key) : WvString());
137 else
138 return WvString::null;
142 void UniDefGen::set(const UniConfKey &key, WvStringParm value)
144 // no keymap() on set()
145 if (inner())
146 inner()->set(key, value);