Ignore:
Timestamp:
02/05/15 00:26:20 (9 years ago)
Author:
Maciej Komosinski
Message:

More strict parsing of int and float numbers from string

File:
1 edited

Legend:

Unmodified
Added
Removed
  • cpp/frams/util/extvalue.h

    r286 r325  
    1212
    1313#define EXTVALUEUNION
    14 template <int A,int B> struct CompileTimeMax {enum {val=A>B?A:B}; };
     14template <int A, int B> struct CompileTimeMax { enum { val = A > B ? A : B }; };
    1515#define EXTVALUEUNIONSIZE CompileTimeMax<sizeof(ExtObject),sizeof(SString)>::val
    1616
    1717enum ExtPType
    18 {TUnknown=0,TInt,TDouble,TString,TObj,TInvalid};
     18{
     19        TUnknown = 0, TInt, TDouble, TString, TObj, TInvalid
     20};
    1921
    2022/**
    2123   destructable object
    22  */
     24   */
    2325class DestrBase
    2426{
    2527public:
    26 int refcount;
    27 DestrBase():refcount(0) {}
    28 void incref() {refcount++;}
    29 void decref() {refcount--; if (refcount==0) delete this;}
    30 virtual ~DestrBase() {}
     28        int refcount;
     29        DestrBase() :refcount(0) {}
     30        void incref() { refcount++; }
     31        void decref() { refcount--; if (refcount == 0) delete this; }
     32        virtual ~DestrBase() {}
    3133};
    3234
    3335/**
    3436   object reference.
    35  */
     37   */
    3638class ExtObject
    3739{
    38 int subtype;                    //< 0/1=Generic/DPC Object,  0/2=Standalone/Shared Param
    39 void incref() const;
    40 void decref() const;
    41   public:
    42 union { void* object;           //< generic object, will use param
    43 DestrBase *dbobject;};  //< object with refcounting, will be deleted if refcount goes to 0
    44 union { Param* param;           //< if object!=0
    45         ParamInterface *paraminterface;}; //< if object==0
    46 
    47 void copyFrom(const ExtObject& src)  {subtype=src.subtype;object=src.object;param=src.param;}
    48 
    49 void* operator new(size_t s, void* mem) {return mem;}
     40        int subtype;                    //< 0/1=Generic/DPC Object,  0/2=Standalone/Shared Param
     41        void incref() const;
     42        void decref() const;
     43public:
     44        union {
     45                void* object;           //< generic object, will use param
     46                DestrBase *dbobject;    //< object with refcounting, will be deleted if refcount goes to 0
     47        };
     48        union {
     49                Param* param;           //< if object!=0
     50                ParamInterface *paraminterface; //< if object==0
     51        };
     52
     53        void copyFrom(const ExtObject& src)  { subtype = src.subtype; object = src.object; param = src.param; }
     54
     55        void* operator new(size_t s, void* mem){ return mem; }
    5056#ifdef _MSC_VER
    51 void operator delete(void* mem,void* t) {}
    52 #endif
    53 void* operator new(size_t s) {return malloc(sizeof(ExtObject));}
    54 void operator delete(void* mem) {free(mem);}
    55 ///@param tmp_param can be used for temporary storage, the result ParamInterface* is only valid for as long as tmp_param is valid
    56 ParamInterface *getParamInterface(Param &tmp_param) const  {if(subtype&2){tmp_param.setParamTab(param->getParamTab());tmp_param.select(object);return &tmp_param;} return paraminterface;}
    57 const char* interfaceName() const {if (isEmpty()) return "Empty"; return (subtype&2)?param->getName():paraminterface->getName();}
    58 bool matchesInterfaceName(ParamInterface* pi) const {return !strcmp(interfaceName(),pi->getName());}
    59 void* getTarget() const {return (subtype&1)?dbobject:object;}
    60 void* getTarget(const char* classname, bool through_barrier=true, bool warn=true) const;
    61 void setEmpty() {decref();subtype=0;param=NULL;object=NULL;}
    62 int isEmpty() const {return !param;}
    63 static const ExtObject& empty() { static const ExtObject& e((ParamInterface*)NULL); return e; }
    64 ExtObject(const ExtObject& src)      {src.incref();copyFrom(src);}
    65 void operator=(const ExtObject& src) {src.incref();decref();copyFrom(src);}
    66 bool makeUnique();//< @return false if nothing has changed
    67 
    68 bool operator==(const ExtObject& src) const;
    69 
    70 SString toString() const;
    71 SString serialize_inner() const;
    72 SString serialize() const;
    73 
    74 ExtObject(Param *p,void *o):subtype(2),object(o),param(p){}
    75 ExtObject(ParamInterface *p=0):subtype(0),object(0),paraminterface(p){}
    76 ExtObject(Param *p,DestrBase *o):subtype(1+2),dbobject(o),param(p){incref();}
    77 ExtObject(ParamInterface *p,DestrBase *o):subtype(1),dbobject(o),paraminterface(p){incref();}
    78 
    79 ~ExtObject(){decref();}
    80 
    81 class Serialization
    82 {
    83 std::vector<ExtObject> refs;
    84 int level;
    85   public:
    86 Serialization():level(0) {}
    87 void begin();
    88 void end();
    89 int add(const ExtObject& o);
    90 void replace(const ExtObject& o,const ExtObject& other);
    91 void remove(const ExtObject& o);
    92 const ExtObject* get(int ref);
    93 };
    94 
    95 static THREAD_LOCAL_DECL(Serialization,serialization);
     57                void operator delete(void* mem, void* t) {}
     58#endif
     59        void* operator new(size_t s){ return malloc(sizeof(ExtObject)); }
     60        void operator delete(void* mem) { free(mem); }
     61        ///@param tmp_param can be used for temporary storage, the result ParamInterface* is only valid for as long as tmp_param is valid
     62        ParamInterface *getParamInterface(Param &tmp_param) const  { if (subtype & 2){ tmp_param.setParamTab(param->getParamTab()); tmp_param.select(object); return &tmp_param; } return paraminterface; }
     63        const char* interfaceName() const { if (isEmpty()) return "Empty"; return (subtype & 2) ? param->getName() : paraminterface->getName(); }
     64        bool matchesInterfaceName(ParamInterface* pi) const { return !strcmp(interfaceName(), pi->getName()); }
     65        void* getTarget() const { return (subtype & 1) ? dbobject : object; }
     66        void* getTarget(const char* classname, bool through_barrier = true, bool warn = true) const;
     67        void setEmpty() { decref(); subtype = 0; param = NULL; object = NULL; }
     68        int isEmpty() const { return !param; }
     69        static const ExtObject& empty() { static const ExtObject& e((ParamInterface*)NULL); return e; }
     70        ExtObject(const ExtObject& src)      { src.incref(); copyFrom(src); }
     71        void operator=(const ExtObject& src) { src.incref(); decref(); copyFrom(src); }
     72        bool makeUnique();//< @return false if nothing has changed
     73
     74        bool operator==(const ExtObject& src) const;
     75
     76        SString toString() const;
     77        SString serialize_inner() const;
     78        SString serialize() const;
     79
     80        ExtObject(Param *p, void *o) :subtype(2), object(o), param(p){}
     81        ExtObject(ParamInterface *p = 0) :subtype(0), object(0), paraminterface(p){}
     82        ExtObject(Param *p, DestrBase *o) :subtype(1 + 2), dbobject(o), param(p){ incref(); }
     83        ExtObject(ParamInterface *p, DestrBase *o) :subtype(1), dbobject(o), paraminterface(p){ incref(); }
     84
     85        ~ExtObject(){ decref(); }
     86
     87        class Serialization
     88        {
     89                std::vector<ExtObject> refs;
     90                int level;
     91        public:
     92                Serialization() :level(0) {}
     93                void begin();
     94                void end();
     95                int add(const ExtObject& o);
     96                void replace(const ExtObject& o, const ExtObject& other);
     97                void remove(const ExtObject& o);
     98                const ExtObject* get(int ref);
     99        };
     100
     101        static THREAD_LOCAL_DECL(Serialization, serialization);
    96102};
    97103
     
    99105{
    100106public:
    101 ExtPType type;
     107        ExtPType type;
    102108#ifdef EXTVALUEUNION
    103 long data[(EXTVALUEUNIONSIZE+sizeof(long)-1)/sizeof(long)];
    104 paInt& idata() const {return (paInt&)data[0];};
    105 double& ddata() const {return *(double*)data;};
    106 ExtObject& odata() const {return *(ExtObject*)data;};
    107 SString& sdata() const {return *(SString*)data;};
     109        long data[(EXTVALUEUNIONSIZE + sizeof(long) - 1) / sizeof(long)];
     110        paInt& idata() const { return (paInt&)data[0]; };
     111        double& ddata() const { return *(double*)data; };
     112        ExtObject& odata() const { return *(ExtObject*)data; };
     113        SString& sdata() const { return *(SString*)data; };
    108114#else
    109 union {
    110 paInt i;
    111 double d;
    112 SString *s;
    113 ExtObject *o;
    114 };
    115 paInt& idata() const {return (paInt&)i;};
    116 double& ddata() const {return (double&)d;};
    117 ExtObject& odata() const {return *o;};
    118 SString& sdata() const {return *s;};
    119 #endif
    120 
    121 void* operator new(size_t s, void* mem) {return mem;}
    122 void* operator new(size_t s) {return ::operator new(s);}
    123 
    124 ExtValue():type(TUnknown){}
    125 ~ExtValue() {setEmpty();}
    126 ExtValue(paInt v) {seti(v);}
    127 ExtValue(double v) {setd(v);}
    128 ExtValue(const SString &v) {sets(v);}
    129 ExtValue(const ExtObject &srco) {seto(srco);}
    130 static ExtValue invalid() {ExtValue v; v.setInvalid(); return v;}
    131 static const ExtValue& empty() { static const ExtValue v; return v; }
    132 int compare(const ExtValue& src) const;
    133 int operator==(const ExtValue& src) const;
    134 void operator+=(const ExtValue& src);
    135 void operator-=(const ExtValue& src);
    136 void operator*=(const ExtValue& src);
    137 void operator/=(const ExtValue& src);
    138 void operator%=(const ExtValue& src);
    139 void operator=(const ExtValue& src)
    140         {setr(src);}
    141 ExtValue(const ExtValue& src)
    142         :type(TUnknown) {set(src);}
    143 void setEmpty();
    144 void setInvalid() {setEmpty();type=TInvalid;}
    145 bool makeUnique() {return (type==TObj) && odata().makeUnique();} //< @return false if nothing has changed
    146 ExtPType getType() {return type;}
    147 void *getObjectTarget(const char* classname,bool warn=true) const;
    148 void setInt(paInt v) {if (type!=TInt) setri(v); else idata()=v;}
    149 void setDouble(double v) {if (type!=TDouble) setrd(v); else ddata()=v;}
    150 void setString(const SString &v) {if (type!=TString) setrs(v); else sdata()=v;}
    151 void setObject(const ExtObject &src) {if (type!=TObj) setro(src); else odata()=src;}
    152 static paInt getInt(const char* s);
    153 static double getDouble(const char* s);
    154 paInt getInt() const;
    155 double getDouble() const;
    156 SString getString() const;
    157 const SString* getStringPtr() const;//< @return pointer to the internal sstring object or NULL if the current type is not string
    158 SString serialize() const;
    159 ExtObject getObject() const;
    160 bool isNull() const {return (type==TUnknown)||((type==TObj)&&odata().isEmpty());}
    161 SString typeDescription() const;//< @return human readable type name (used in error messages)
    162 const char* parseNumber(const char* in);
    163 const char* deserialize(const char* in);//< @return first character after the succesfully parsed string or NULL if failed
    164 const char* deserialize_inner(const char* in);
    165 static ParamInterface *findDeserializableClass(const char* name);
    166 static PtrListTempl<ParamInterface*> &getDeserializableClasses();
    167 template<typename T> class AddDeserializable
    168 {
    169   public:
    170 AddDeserializable() {ExtValue::getDeserializableClasses()+=&T::getStaticParam();}
    171 };
    172 
    173 static SString format(SString& fmt,const ExtValue **values,int count);
    174 
    175 ExtValue getExtType();
    176 
    177   private: // setrx - release and set, setx - assume released
    178 void setr(const ExtValue& src){setEmpty();set(src);}
    179 void set(const ExtValue& src);
    180 void setri(paInt v) {setEmpty();seti(v);}
    181 void setrd(double v) {setEmpty();setd(v);}
    182 void seti(paInt v) {type=TInt;idata()=v;}
    183 void setd(double v) {type=TDouble;ddata()=v;}
     115        union {
     116                paInt i;
     117                double d;
     118                SString *s;
     119                ExtObject *o;
     120        };
     121        paInt& idata() const {return (paInt&)i;};
     122        double& ddata() const {return (double&)d;};
     123        ExtObject& odata() const {return *o;};
     124        SString& sdata() const {return *s;};
     125#endif
     126
     127        void* operator new(size_t s, void* mem){ return mem; }
     128        void* operator new(size_t s){ return ::operator new(s); }
     129
     130                ExtValue() :type(TUnknown){}
     131        ~ExtValue() { setEmpty(); }
     132        ExtValue(paInt v) { seti(v); }
     133        ExtValue(double v) { setd(v); }
     134        ExtValue(const SString &v) { sets(v); }
     135        ExtValue(const ExtObject &srco) { seto(srco); }
     136        static ExtValue invalid() { ExtValue v; v.setInvalid(); return v; }
     137        static const ExtValue& empty() { static const ExtValue v; return v; }
     138        int compare(const ExtValue& src) const;
     139        int operator==(const ExtValue& src) const;
     140        void operator+=(const ExtValue& src);
     141        void operator-=(const ExtValue& src);
     142        void operator*=(const ExtValue& src);
     143        void operator/=(const ExtValue& src);
     144        void operator%=(const ExtValue& src);
     145        void operator=(const ExtValue& src)
     146        {
     147                setr(src);
     148        }
     149        ExtValue(const ExtValue& src)
     150                :type(TUnknown) {
     151                set(src);
     152        }
     153        void setEmpty();
     154        void setInvalid() { setEmpty(); type = TInvalid; }
     155        bool makeUnique() { return (type == TObj) && odata().makeUnique(); } //< @return false if nothing has changed
     156        ExtPType getType() { return type; }
     157        void *getObjectTarget(const char* classname, bool warn = true) const;
     158        void setInt(paInt v) { if (type != TInt) setri(v); else idata() = v; }
     159        void setDouble(double v) { if (type != TDouble) setrd(v); else ddata() = v; }
     160        void setString(const SString &v) { if (type != TString) setrs(v); else sdata() = v; }
     161        void setObject(const ExtObject &src) { if (type != TObj) setro(src); else odata() = src; }
     162        static bool parseInt(const char* s, paInt &result, bool strict = false);
     163        static bool parseDouble(const char* s, double &result);
     164        static paInt getInt(const char* s, bool strict = false);//< @param strict=true will fail on floating point
     165        static double getDouble(const char* s);
     166        paInt getInt() const;
     167        double getDouble() const;
     168        SString getString() const;
     169        const SString* getStringPtr() const;//< @return pointer to the internal sstring object or NULL if the current type is not string
     170        SString serialize() const;
     171        ExtObject getObject() const;
     172        bool isNull() const { return (type == TUnknown) || ((type == TObj) && odata().isEmpty()); }
     173        SString typeDescription() const;//< @return human readable type name (used in error messages)
     174        const char* parseNumber(const char* in, ExtPType strict_type = TUnknown);
     175        const char* deserialize(const char* in);//< @return first character after the succesfully parsed string or NULL if failed
     176        const char* deserialize_inner(const char* in);
     177        static ParamInterface *findDeserializableClass(const char* name);
     178        static PtrListTempl<ParamInterface*> &getDeserializableClasses();
     179        template<typename T> class AddDeserializable
     180        {
     181        public:
     182                AddDeserializable() { ExtValue::getDeserializableClasses() += &T::getStaticParam(); }
     183        };
     184
     185        static SString format(SString& fmt, const ExtValue **values, int count);
     186
     187        ExtValue getExtType();
     188
     189private: // setrx - release and set, setx - assume released
     190        void setr(const ExtValue& src){ setEmpty(); set(src); }
     191        void set(const ExtValue& src);
     192        void setri(paInt v) { setEmpty(); seti(v); }
     193        void setrd(double v) { setEmpty(); setd(v); }
     194        void seti(paInt v) { type = TInt; idata() = v; }
     195        void setd(double v) { type = TDouble; ddata() = v; }
    184196#ifdef EXTVALUEUNION
    185 void setrs(const SString &v) {setEmpty();sets(v);}
    186 void setro(const ExtObject &src) {setEmpty();seto(src);}
    187 void sets(const SString &v) {type=TString;new(data) SString(v);}
    188 void seto(const ExtObject &src) {type=TObj;new(data) ExtObject(src);}
     197        void setrs(const SString &v) { setEmpty(); sets(v); }
     198        void setro(const ExtObject &src) { setEmpty(); seto(src); }
     199        void sets(const SString &v) { type = TString; new(data)SString(v); }
     200        void seto(const ExtObject &src) { type = TObj; new(data)ExtObject(src); }
    189201#else
    190 void setrs(const SString &v) {setEmpty();sets(v);}
    191 void setro(const ExtObject &src) {setEmpty();seto(src);}
    192 void sets(const SString &v) {type=TString;s=new SString(v);}
    193 void seto(const ExtObject &src) {type=TObj;o=new ExtObject(src);}
     202        void setrs(const SString &v) {setEmpty();sets(v);}
     203        void setro(const ExtObject &src) {setEmpty();seto(src);}
     204        void sets(const SString &v) {type=TString;s=new SString(v);}
     205        void seto(const ExtObject &src) {type=TObj;o=new ExtObject(src);}
    194206#endif
    195207
Note: See TracChangeset for help on using the changeset viewer.