Main Page Class Hierarchy Compound List File List Compound Members Related Pages

# keyval.h

    00001 //
    00002 // keyval.h
    00003 //
    00004 // Copyright (C) 1996 Limit Point Systems, Inc.
    00005 //
    00006 // Author: Curtis Janssen <cljanss@limitpt.com>
    00007 // Maintainer: LPS
    00008 //
    00009 // This file is part of the SC Toolkit.
    00010 //
    00011 // The SC Toolkit is free software; you can redistribute it and/or modify
    00012 // it under the terms of the GNU Library General Public License as published by
    00013 // the Free Software Foundation; either version 2, or (at your option)
    00014 // any later version.
    00015 //
    00016 // The SC Toolkit is distributed in the hope that it will be useful,
    00017 // but WITHOUT ANY WARRANTY; without even the implied warranty of
    00018 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    00019 // GNU Library General Public License for more details.
    00020 //
    00021 // You should have received a copy of the GNU Library General Public License
    00022 // along with the SC Toolkit; see the file COPYING.LIB.  If not, write to
    00023 // the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
    00024 //
    00025 // The U.S. Government is granted a limited license as per AL 91-7.
    00026 //
    00027
    00028 #ifndef _util_keyval_keyval_h
    00029 #define _util_keyval_keyval_h
    00030 #ifdef __GNUG__
    00031 #pragma interface
    00032 #endif
    00033
    00034 #include <iostream>
    00035 #include <string.h>
    00036 #include <stdlib.h>
    00037 #include <stdarg.h>
    00038
    00039 #include <util/container/avlmap.h>
    00040 #include <util/class/class.h>
    00041 #include <util/keyval/keyvalval.h>
    00042
    00043 namespace sc {
    00044
    00045 class KeyValKeyword {
    00046   private:
    00047     char* keyword_;
    00048   public:
    00049     KeyValKeyword();
    00050     KeyValKeyword(const char* name);
    00051     KeyValKeyword(const KeyValKeyword&);
    00052     ~KeyValKeyword();
    00053     KeyValKeyword& operator=(const KeyValKeyword&);
    00054     int operator==(const KeyValKeyword& ck) const;
    00055     int operator<(const KeyValKeyword& ck) const;
    00056     int hash() const;
    00057     inline int cmp(const KeyValKeyword&ck) const
    00058     {
    00059       if (!keyword_) {
    00060           if (!ck.keyword_) return 0;
    00061           return -1;
    00062         }
    00063       if (!ck.keyword_) return 1;
    00064       return strcmp(keyword_,ck.keyword_);
    00065     }
    00066     inline const char* name() const {return keyword_;}
    00067   };
    00068
    00091 class KeyVal: public RefCount {
    00092     // these classes need to directly access the key_value member
    00093     friend class AggregateKeyVal;
    00094     friend class PrefixKeyVal;
    00095   public:
    00096     enum {MaxKeywordLength = 256};
    00097     enum KeyValError { OK, HasNoValue, WrongType,
    00098                        UnknownKeyword, OperationFailed };
    00099   private:
    00100     KeyValError errcod;
    00101     // do not allow a copy constructor or assignment
    00102     KeyVal(const KeyVal&);
    00103     void operator=(const KeyVal&);
    00104   protected:
    00105     int verbose_;
    00106
    00107     KeyVal();
    00108
    00110     void seterror(KeyValError err);
    00112     void seterror(KeyValValue::KeyValValueError err);
    00113
    00115     virtual int    key_exists(const char*) = 0;
    00117     virtual int    key_count(const char* =0);
    00119     virtual Ref<KeyValValue> key_value(const char*,
    00120                                      const KeyValValue& def) = 0;
    00122     virtual int    key_booleanvalue(const char*,const KeyValValue& def);
    00124     virtual double key_doublevalue(const char* key,const KeyValValue& def);
    00126     virtual float  key_floatvalue(const char* key,const KeyValValue& def);
    00128     virtual char   key_charvalue(const char* key,const KeyValValue& def);
    00130     virtual int    key_intvalue(const char* key,const KeyValValue& def);
    00132     virtual size_t key_sizevalue(const char* key,const KeyValValue& def);
    00134     virtual char*  key_pcharvalue(const char* key,const KeyValValue& def);
    00136     virtual Ref<DescribedClass> key_describedclassvalue(const char* key,
    00137                                                       const KeyValValue& def);
    00138
    00139   public:
    00140     virtual ~KeyVal();
    00141
    00142     // For nonindexed things.   If a subclass defines one of these,
    00143     // then the overloaded functions will be hidden.  The key_... functions
    00144     // should be overridden instead.
    00145
    00148     int    exists(const char*);
    00153     int    count(const char* =0);
    00155     Ref<KeyValValue> value(const char* = 0,
    00156                          const KeyValValue& def=KeyValValue());
    00158     int    booleanvalue(const char* key = 0,
    00159                         const KeyValValue& def=KeyValValueboolean());
    00161     double doublevalue(const char* key = 0,
    00162                        const KeyValValue& def=KeyValValuedouble());
    00164     float  floatvalue(const char* key = 0,
    00165                       const KeyValValue& def=KeyValValuefloat());
    00167     char   charvalue(const char* key = 0,
    00168                      const KeyValValue& def=KeyValValuechar());
    00170     int    intvalue(const char* key = 0,
    00171                     const KeyValValue& def=KeyValValueint());
    00173     size_t sizevalue(const char* key = 0,
    00174                      const KeyValValue& def=KeyValValuesize());
    00177     char*  pcharvalue(const char* key = 0,
    00178                       const KeyValValue& def=KeyValValuepchar());
    00180     Ref<DescribedClass> describedclassvalue(const char* key = 0,
    00181                      const KeyValValue& def=KeyValValueRefDescribedClass());
    00182
    00183     // For vectors:
    00184     int    exists(const char*,int);
    00185     int    count(const char*,int);
    00186     int    booleanvalue(const char*,int,
    00187                         const KeyValValue& def=KeyValValueboolean());
    00188     double doublevalue(const char* key,int,
    00189                        const KeyValValue& def=KeyValValuedouble());
    00190     float  floatvalue(const char* key,int,
    00191                       const KeyValValue& def=KeyValValuefloat());
    00192     char   charvalue(const char* key,int,
    00193                      const KeyValValue& def=KeyValValuechar());
    00194     int    intvalue(const char* key,int,
    00195                     const KeyValValue& def=KeyValValueint());
    00196     size_t sizevalue(const char* key,int,
    00197                      const KeyValValue& def=KeyValValuesize());
    00198     char*  pcharvalue(const char* key,int,
    00199                       const KeyValValue& def=KeyValValuepchar());
    00200     Ref<DescribedClass> describedclassvalue(const char* key,int,
    00201                      const KeyValValue& def=KeyValValueRefDescribedClass());
    00202
    00203     int    exists(int i);
    00204     int    count(int i);
    00205     int    booleanvalue(int i,
    00206                         const KeyValValue& def=KeyValValueboolean());
    00207     double doublevalue(int i,
    00208                        const KeyValValue& def=KeyValValuedouble());
    00209     float  floatvalue(int i,
    00210                       const KeyValValue& def=KeyValValuefloat());
    00211     char   charvalue(int i,
    00212                      const KeyValValue& def=KeyValValuechar());
    00213     int    intvalue(int i,
    00214                     const KeyValValue& def=KeyValValueint());
    00215     size_t sizevalue(int i,
    00216                      const KeyValValue& def=KeyValValuesize());
    00217     char*  pcharvalue(int i,
    00218                       const KeyValValue& def=KeyValValuepchar());
    00219     Ref<DescribedClass> describedclassvalue(int i,
    00220                      const KeyValValue& def=KeyValValueRefDescribedClass());
    00221
    00222     // For arrays:
    00223     int    exists(const char*,int,int);
    00224     int    count(const char*,int,int);
    00225     int    booleanvalue(const char*,int,int,
    00226                         const KeyValValue& def=KeyValValueboolean());
    00227     double doublevalue(const char* key,int,int,
    00228                        const KeyValValue& def=KeyValValuedouble());
    00229     float  floatvalue(const char* key,int,int,
    00230                       const KeyValValue& def=KeyValValuefloat());
    00231     char   charvalue(const char* key,int,int,
    00232                      const KeyValValue& def=KeyValValuechar());
    00233     int    intvalue(const char* key,int,int,
    00234                     const KeyValValue& def=KeyValValueint());
    00235     size_t sizevalue(const char* key,int,int,
    00236                      const KeyValValue& def=KeyValValuesize());
    00237     char*  pcharvalue(const char* key,int,int,
    00238                       const KeyValValue& def=KeyValValuepchar());
    00239     Ref<DescribedClass> describedclassvalue(const char* key,int,int,
    00240                      const KeyValValue& def=KeyValValueRefDescribedClass());
    00241
    00242     int    exists(int i,int j);
    00243     int    count(int i,int j);
    00244     int    booleanvalue(int i,int j,
    00245                         const KeyValValue& def=KeyValValueboolean());
    00246     double doublevalue(int i,int j,
    00247                        const KeyValValue& def=KeyValValuedouble());
    00248     float  floatvalue(int i,int j,
    00249                       const KeyValValue& def=KeyValValuefloat());
    00250     char   charvalue(int i,int j,
    00251                      const KeyValValue& def=KeyValValuechar());
    00252     int    intvalue(int i,int j,
    00253                     const KeyValValue& def=KeyValValueint());
    00254     size_t sizevalue(int i,int j,
    00255                      const KeyValValue& def=KeyValValuesize());
    00256     char*  pcharvalue(int i,int j,
    00257                       const KeyValValue& def=KeyValValuepchar());
    00258     Ref<DescribedClass> describedclassvalue(int i,int j,
    00259                      const KeyValValue& def=KeyValValueRefDescribedClass());
    00260
    00261     // For all else:
    00262     int    Va_exists(const char*,int,...);
    00263     int    Va_count(const char*,int,...);
    00264     int    Va_booleanvalue(const char*,int,...);
    00265     double Va_doublevalue(const char* key,int,...);
    00266     float  Va_floatvalue(const char* key,int,...);
    00267     char   Va_charvalue(const char* key,int,...);
    00268     int    Va_intvalue(const char* key,int,...);
    00269     size_t Va_sizevalue(const char* key,int,...);
    00270     char*  Va_pcharvalue(const char* key,int,...);
    00271     Ref<DescribedClass> Va_describedclassvalue(const char* key,int,...);
    00272
    00274     KeyValError error();
    00276     const char*  errormsg(KeyValError err);
    00278     const char*  errormsg();
    00279
    00280     virtual void errortrace(std::ostream&fp=ExEnv::err0());
    00281     virtual void dump(std::ostream&fp=ExEnv::err0());
    00282
    00284     virtual void print_unseen(std::ostream&fp=ExEnv::out0());
    00288     virtual int have_unseen();
    00289
    00291     void verbose(int v) { verbose_ = v; }
    00293     int verbose() const { return verbose_; }
    00294 };
    00295
    00296
    00297
    00298 // this class allows keyval associations to be set up by the program,
    00299 // rather than determined by an external file
    00300 class AssignedKeyVal: public KeyVal {
    00301   private:
    00302     AVLMap<KeyValKeyword,Ref<KeyValValue> > _map;
    00303     // do not allow a copy constructor or assignment
    00304     AssignedKeyVal(const AssignedKeyVal&);
    00305     void operator=(const AssignedKeyVal&);
    00306   protected:
    00307     int    key_exists(const char*);
    00308     Ref<KeyValValue> key_value(const char*,
    00309                              const KeyValValue& def);
    00310   public:
    00311     AssignedKeyVal();
    00312     ~AssignedKeyVal();
    00313
    00314     void assign(const char*, const Ref<KeyValValue>&);
    00315     void assign(const char*, double);
    00316     void assignboolean(const char*, int);
    00317     void assign(const char*, float);
    00318     void assign(const char*, char);
    00319     void assign(const char*, int);
    00320     void assign(const char*, const char*);
    00321     void assign(const char*, const Ref<DescribedClass>&);
    00322
    00323     void clear();
    00324 };
    00325
    00326
    00327
    00328 class StringKeyVal: public KeyVal {
    00329   private:
    00330     // once a described class is found it is kept here so
    00331     // multiple references to it return the same instance
    00332     AVLMap<KeyValKeyword,Ref<KeyValValue> > _map;
    00333     // do not allow a copy constructor or assignment
    00334     StringKeyVal(const StringKeyVal&);
    00335     void operator=(const StringKeyVal&);
    00336   protected:
    00337     StringKeyVal();
    00338     int    key_exists(const char*);
    00339     Ref<KeyValValue> key_value(const char*,
    00340                              const KeyValValue& def);
    00341   public:
    00342     virtual ~StringKeyVal();
    00343     virtual const char* stringvalue(const char *) = 0;
    00344     // returns the name of the exact class the object at the keyword
    00345     virtual const char* classname(const char*);
    00346     // returns a string which is the actual keyword if some sort
    00347     // of variable substitution takes place (needed to make multiple
    00348     // references to the same object work in input files)
    00349     virtual const char* truekeyword(const char*);
    00350
    00351     virtual void errortrace(std::ostream&fp=ExEnv::err0());
    00352     virtual void dump(std::ostream&fp=ExEnv::err0());
    00353 };
    00354
    00355 class AggregateKeyVal : public KeyVal {
    00356   private:
    00357     enum { MaxKeyVal = 4 };
    00358     Ref<KeyVal> kv[MaxKeyVal];
    00359     Ref<KeyVal> getkeyval(const char*key);
    00360     // do not allow a copy constructor or assignment
    00361     AggregateKeyVal(const AggregateKeyVal&);
    00362     void operator=(const AggregateKeyVal&);
    00363   protected:
    00364     int    key_exists(const char*);
    00365     Ref<KeyValValue> key_value(const char*,
    00366                              const KeyValValue& def);
    00367   public:
    00368     AggregateKeyVal(const Ref<KeyVal>&);
    00369     AggregateKeyVal(const Ref<KeyVal>&,const Ref<KeyVal>&);
    00370     AggregateKeyVal(const Ref<KeyVal>&,const Ref<KeyVal>&,const Ref<KeyVal>&);
    00371     AggregateKeyVal(const Ref<KeyVal>&,const Ref<KeyVal>&,const Ref<KeyVal>&,
    00372                     const Ref<KeyVal>&);
    00373     ~AggregateKeyVal();
    00374     void errortrace(std::ostream&fp=ExEnv::err0());
    00375     void dump(std::ostream&fp=ExEnv::err0());
    00376 };
    00377
    00378 class PrefixKeyVal : public KeyVal {
    00379   private:
    00380     char* prefix;
    00381     Ref<KeyVal> keyval;
    00382     void setup(const char*,int,int,int,int,int);
    00383     int getnewprefixkey(const char*key,char*newkey);
    00384     // do not allow a copy constructor or assignment
    00385     PrefixKeyVal(const PrefixKeyVal&);
    00386     void operator=(const PrefixKeyVal&);
    00387     int    key_exists(const char*);
    00388     Ref<KeyValValue> key_value(const char*,
    00389                              const KeyValValue& def);
    00390   public:
    00391     PrefixKeyVal(const Ref<KeyVal>&,int);
    00392     PrefixKeyVal(const Ref<KeyVal>&,int,int);
    00393     PrefixKeyVal(const Ref<KeyVal>&,int,int,int);
    00394     PrefixKeyVal(const Ref<KeyVal>&,int,int,int,int);
    00395     PrefixKeyVal(const Ref<KeyVal>&,const char*);
    00396     PrefixKeyVal(const Ref<KeyVal>&,const char*,int);
    00397     PrefixKeyVal(const Ref<KeyVal>&,const char*,int,int);
    00398     PrefixKeyVal(const Ref<KeyVal>&,const char*,int,int,int);
    00399     PrefixKeyVal(const Ref<KeyVal>&,const char*,int,int,int,int);
    00400     // old CTOR syntax (use the above instead)
    00401     PrefixKeyVal(const char*,const Ref<KeyVal>&);
    00402     PrefixKeyVal(const char*,const Ref<KeyVal>&,int);
    00403     PrefixKeyVal(const char*,const Ref<KeyVal>&,int,int);
    00404     PrefixKeyVal(const char*,const Ref<KeyVal>&,int,int,int);
    00405     PrefixKeyVal(const char*,const Ref<KeyVal>&,int,int,int,int);
    00406     ~PrefixKeyVal();
    00407     void errortrace(std::ostream&fp=ExEnv::err0());
    00408     void dump(std::ostream&fp=ExEnv::err0());
    00409 };
    00410
    00411 class IPV2;
    00415 class ParsedKeyVal : public StringKeyVal {
    00416   private:
    00417     int nfile;
    00418     char**file;
    00419     int nfp;
    00420     IPV2* ipv2;
    00421     // do not allow a copy constructor or assignment
    00422     ParsedKeyVal(const ParsedKeyVal&);
    00423     void operator=(const ParsedKeyVal&);
    00424   public:
    00426     ParsedKeyVal();
    00428     ParsedKeyVal(const char*file);
    00430     ParsedKeyVal(std::istream&s);
    00433     ParsedKeyVal(IPV2*);
    00439     ParsedKeyVal(const char*,const Ref<KeyVal>&);
    00441     ~ParsedKeyVal();
    00442
    00445     static void cat_files(const char*,const Ref<KeyVal>&,std::ostream &o);
    00446
    00448     void read(const char*);
    00450     void read(std::istream&);
    00452     void parse_string(const char *);
    00453
    00454     // Overrides of parent members.
    00455     const char* stringvalue(const char*);
    00456     const char* classname(const char*);
    00457     const char* truekeyword(const char*);
    00458     void errortrace(std::ostream&fp=ExEnv::err0());
    00459     void dump(std::ostream&fp=ExEnv::err0());
    00460     void print_unseen(std::ostream&fp=ExEnv::out0());
    00461     int have_unseen();
    00462 };
    00463
    00464 }
    00465
    00466 #endif /* _KeyVal_h */
    00467
    00468 // Local Variables:
    00469 // mode: c++
    00470 // c-file-style: "CLJ"
    00471 // End: