• Main Page
  • Classes
  • Files
  • File List

query.h

00001 //-< QUERY.H >-------------------------------------------------------*--------*
00002 // GigaBASE                  Version 1.0         (c) 1999  GARRET    *     ?  *
00003 // (Post Relational Database Management System)                      *   /\|  *
00004 //                                                                   *  /  \  *
00005 //                          Created:     20-Nov-98    K.A. Knizhnik  * / [] \ *
00006 //                          Last update: 10-Dec-98    K.A. Knizhnik  * GARRET *
00007 //-------------------------------------------------------------------*--------*
00008 // Constructing and hashing database query statements
00009 //-------------------------------------------------------------------*--------*
00010 
00011 #ifndef __QUERY_H__
00012 #define __QUERY_H__
00013 
00014 BEGIN_GIGABASE_NAMESPACE
00015 
00016 class dbSession;
00017 
00021 class GIGABASE_DLL_ENTRY dbQueryElement {
00022     friend class dbQuery;
00023     friend class dbCompiler;
00024     friend class dbSession;
00025     friend class dbQueryExpression;
00026     friend class dbQueryElementAllocator;
00027     friend class dbCLI;
00028   public:
00029     enum ElementType {
00030         qExpression, // part of SQL expression
00031         qVarBool,
00032         qVarInt1,
00033         qVarInt2,
00034         qVarInt4,
00035         qVarInt8,
00036         qVarReal4,
00037         qVarReal8,
00038         qVarString,
00039         qVarStringPtr,
00040         qVarReference,
00041         qVarRectangle, 
00042         qVarRectanglePtr, 
00043         qVarArrayOfRef, 
00044         qVarArrayOfInt4,
00045         qVarArrayOfInt8,
00046         qVarArrayOfRefPtr,
00047         qVarArrayOfInt4Ptr,
00048         qVarArrayOfInt8Ptr,
00049         qVarRawData,
00050         qVarRawDataPtr,
00051         qVarStdString,
00052         qVarMfcString,
00053         qVarUnknown
00054     };
00055 
00056     void* operator new (size_t size);
00057     void  operator delete(void* p);
00058 
00059     char_t* dump(char_t* buf);
00060     char_t* dumpValues(char_t* buf);
00061 
00062     dbQueryElement(ElementType t, void const* p,
00063                    dbTableDescriptor* table = NULL)
00064     {
00065         type = t;
00066         ptr  = p;
00067         ref  = table;
00068         next = NULL;
00069     }
00070   private:
00071     dbQueryElement*    next;
00072     void const*        ptr;
00073     ElementType        type;
00074     dbTableDescriptor* ref;
00075 };
00076 
00077 
00083 class GIGABASE_DLL_ENTRY dbQueryElementAllocator { 
00084     friend class dbDatabase;
00085     dbMutex         mutex;
00086     dbQueryElement* freeChain;
00087     
00088   public:
00089     void free(dbQueryElement* first, dbQueryElement** lastNext) { 
00090         dbCriticalSection cs(mutex);
00091         if (first != NULL) { 
00092             *lastNext = freeChain;
00093             freeChain = first;
00094         }
00095     }
00096         
00097     void* allocate(size_t size) { 
00098         dbCriticalSection cs(mutex);
00099         dbQueryElement* elem = freeChain;
00100         if (elem != NULL) {
00101             freeChain = elem->next;
00102             return elem;
00103         } else {
00104             return dbMalloc(size);
00105         }
00106     }
00107     dbQueryElementAllocator();
00108     ~dbQueryElementAllocator();
00109 
00110     static dbQueryElementAllocator instance;
00111 };
00112 
00113 
00133 class GIGABASE_DLL_ENTRY dbComponent {
00134   public:
00135     char_t const* structure;
00136     char_t const* field;
00137 
00138     dbComponent(char_t const* s, char_t const* f=NULL) : structure(s), field(f) {}
00139 };
00140 
00147 class GIGABASE_DLL_ENTRY dbQueryExpression {
00148     friend class dbQuery;
00149     dbQueryElement*  first;
00150     dbQueryElement** last;
00151     bool             operand;
00152 
00153   public:
00154     dbQueryExpression& add(dbQueryElement::ElementType type, void const* ptr, dbTableDescriptor* table = NULL) {
00155         last = &(*last = new dbQueryElement(type, ptr, table))->next;
00156         operand = (type == dbQueryElement::qExpression);
00157         return *this;
00158     }
00159 
00160     dbQueryExpression& operator = (char_t const* ptr) {
00161         first = NULL, last = &first;
00162         return add(dbQueryElement::qExpression, ptr);
00163     }
00164     dbQueryExpression& operator = (dbComponent const& comp);
00165 
00166     dbQueryExpression& operator = (dbQueryExpression const& expr);
00167 
00168     dbQueryExpression& operator,(int1 const& ptr) {
00169         return add(dbQueryElement::qVarInt1, &ptr);
00170     }
00171     dbQueryExpression& operator,(int2 const& ptr) {
00172         return add(dbQueryElement::qVarInt2, &ptr);
00173     }
00174     dbQueryExpression& operator,(int4 const& ptr) {
00175         return add(dbQueryElement::qVarInt4, &ptr);
00176     }
00177     dbQueryExpression& operator,(db_int8 const& ptr) {
00178         return add(dbQueryElement::qVarInt8, &ptr);
00179     }
00180     dbQueryExpression& operator,(nat1 const& ptr) {
00181         return add(dbQueryElement::qVarInt1, &ptr);
00182     }
00183     dbQueryExpression& operator,(nat2 const& ptr) {
00184         return add(dbQueryElement::qVarInt2, &ptr);
00185     }
00186     dbQueryExpression& operator,(nat4 const& ptr) {
00187         return add(dbQueryElement::qVarInt4, &ptr);
00188     }
00189     dbQueryExpression& operator,(db_nat8 const& ptr) {
00190         return add(dbQueryElement::qVarInt8, &ptr);
00191     }
00192 #if SIZEOF_LONG != 8 
00193     dbQueryExpression& operator,(long const& ptr) {
00194         return add(sizeof(long) == 4 ? dbQueryElement::qVarInt4 : dbQueryElement::qVarInt8, &ptr);
00195     }
00196     dbQueryExpression& operator,(unsigned long const& ptr) {
00197         return add(sizeof(long) == 4 ? dbQueryElement::qVarInt4 : dbQueryElement::qVarInt8, &ptr);
00198     }
00199 #endif
00200     dbQueryExpression& operator,(real4 const& ptr) {
00201         return add(dbQueryElement::qVarReal4, &ptr);
00202     }
00203     dbQueryExpression& operator,(real8 const& ptr) {
00204         return add(dbQueryElement::qVarReal8, &ptr);
00205     }
00206     dbQueryExpression& operator,(void const* ptr) { 
00207         return add(dbQueryElement::qVarRawData, ptr);
00208     }
00209     dbQueryExpression& operator,(void** ptr) { 
00210         return add(dbQueryElement::qVarRawDataPtr, ptr);
00211     }
00212 #ifndef bool
00213     dbQueryExpression& operator,(bool const& ptr) {
00214         return add(dbQueryElement::qVarBool, &ptr);
00215     }
00216 #endif
00217     dbQueryExpression& operator,(char_t const* ptr) {
00218         return add(operand ? dbQueryElement::qVarString
00219                    : dbQueryElement::qExpression, ptr);
00220     }
00221     dbQueryExpression& operator,(char_t const** ptr) {
00222         return add(dbQueryElement::qVarStringPtr, ptr);
00223     }
00224     dbQueryExpression& operator,(char_t** ptr) {
00225         return add(dbQueryElement::qVarStringPtr, ptr);
00226     }
00227     dbQueryExpression& operator,(rectangle const& rect) {
00228         return add(dbQueryElement::qVarRectangle, &rect);
00229     }
00230     dbQueryExpression& operator,(rectangle* rect) {
00231         return add(dbQueryElement::qVarRectanglePtr, &rect);
00232     }
00233 #ifdef USE_STD_STRING
00234     dbQueryExpression& operator,(STD_STRING const& str) {
00235         return add(dbQueryElement::qVarStdString, &str);
00236     }
00237 #endif
00238 #ifdef USE_MFC_STRING
00239     dbQueryExpression& operator,(MFC_STRING const& str) {
00240         return add(dbQueryElement::qVarMfcString, &str);
00241     }
00242 #endif
00243 
00244     dbQueryExpression& operator,(dbQueryExpression const& expr) {
00245         *last = new dbQueryElement(dbQueryElement::qExpression, _T("("));
00246         (*last)->next = expr.first;
00247         last = expr.last;
00248         *last = new dbQueryElement(dbQueryElement::qExpression, _T(")"));
00249         last = &(*last)->next;
00250         operand = false;
00251         return *this;
00252     }
00253     dbQueryExpression& operator,(dbComponent const& comp) {
00254         add(dbQueryElement::qExpression, comp.structure);
00255         if (comp.field != NULL) {
00256             add(dbQueryElement::qExpression, _T("."));
00257             add(dbQueryElement::qExpression, comp.field);
00258         }
00259         operand = false;
00260         return *this;
00261     }
00262     dbQueryExpression& operator += (dbComponent const& comp) { 
00263         return *this,comp;
00264     }
00265     dbQueryExpression& operator += (char const* ptr) { 
00266         return add(dbQueryElement::qExpression, ptr);
00267     }
00268 #ifndef NO_MEMBER_TEMPLATES
00269     template<class T>
00270     dbQueryExpression& operator,(dbReference<T> const& value) { 
00271         return add(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00272     }
00273 
00274     template<class T>
00275     inline dbQueryExpression& operator,(dbArray< dbReference<T> > const& value) { 
00276         return add(dbQueryElement::qVarArrayOfRef, &value, 
00277                       &T::dbDescriptor);
00278     }
00279 
00280     template<class T>
00281     inline dbQueryExpression& operator,(dbArray< dbReference<T> >const* const& value) { 
00282         return add(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00283     }
00284 #endif
00285 #if !defined(_MSC_VER) || _MSC_VER+0 >= 1300
00286     inline dbQueryExpression& operator,(dbArray<db_int4> const& value) { 
00287         return add(dbQueryElement::qVarArrayOfInt4, &value);
00288     }
00289 
00290     inline dbQueryExpression& operator,(dbArray<db_int4>const* const& value) { 
00291         return add(dbQueryElement::qVarArrayOfInt4Ptr, &value);
00292     }
00293 
00294     inline dbQueryExpression& operator,(dbArray<db_int8> const& value) { 
00295         return add(dbQueryElement::qVarArrayOfInt8, &value);
00296     }
00297 
00298     inline dbQueryExpression& operator,(dbArray<db_int8>const* const& value) { 
00299         return add(dbQueryElement::qVarArrayOfInt8Ptr, &value);
00300     }
00301 #endif
00302 };
00303 
00304 class dbExprNode;
00305 class dbOrderByNode;
00306 class dbFollowByNode;
00307 
00311 class GIGABASE_DLL_ENTRY dbCompiledQuery {
00312   public:
00313     dbExprNode*        tree;
00314     dbOrderByNode*     order;
00315     dbFollowByNode*    follow;
00316     dbTableDescriptor* table;
00317     int                schemeVersion;
00318 
00319     size_t             stmtLimitStart;
00320     size_t             stmtLimitLen;
00321     int4*              stmtLimitStartPtr;
00322     int4*              stmtLimitLenPtr;
00323     bool               limitSpecified;
00324 
00325     enum IteratorInit {
00326         StartFromAny,
00327         StartFromFirst,
00328         StartFromLast,
00329         StartFromRef,
00330         StartFromArray,
00331         StartFromArrayPtr
00332     };
00333     IteratorInit       startFrom;
00334     enum IteratorType { 
00335         UserDefined      = 0,
00336         TraverseForward  = 1, 
00337         TraverseBackward = 2
00338     };
00339     int  iterType;
00340 
00341     void const*        root;
00342 
00343     void destroy();
00344 
00345     bool compiled() { return tree != NULL; }
00346 
00347     dbCompiledQuery() {
00348         tree = NULL;
00349         order = NULL;
00350         follow = NULL;
00351         table = NULL;
00352         startFrom = StartFromAny;
00353         iterType = UserDefined;
00354         limitSpecified = false;
00355     }
00356 };
00357 
00362 class GIGABASE_DLL_ENTRY dbQuery : public dbCompiledQuery {
00363     friend class dbCompiler;
00364     friend class dbDatabase;
00365     friend class dbSession;
00366     friend class dbSubSql;
00367     friend class dbCLI;
00368   private:
00369     dbMutex            mutex;
00370     dbQueryElement*    elements;
00371     dbQueryElement**   nextElement;
00372     bool               operand;
00373     bool               mutexLocked;
00374     //
00375     // Prohibite query copying
00376     //
00377     dbQuery(dbQuery const&) : dbCompiledQuery() {}
00378     dbQuery& operator =(dbQuery const&) { return *this; }
00379 
00380   public:
00381     int                pos; // position of condition in statement
00382 
00383     bool compileError() { return !isEmpty() && !compiled(); }
00384 
00385     char_t* dump(char_t* buf) { 
00386         char_t* p = buf;
00387         for (dbQueryElement* elem = elements; elem != NULL; elem = elem->next) { 
00388             p = elem->dump(p);
00389         }
00390         return buf;
00391     }
00392 
00393     char_t* dumpValues(char_t* buf) { 
00394         char_t* p = buf;
00395         for (dbQueryElement* elem = elements; elem != NULL; elem = elem->next) { 
00396             p = elem->dumpValues(p);
00397         }
00398         return buf;
00399     }
00400 
00401     dbQuery& append(dbQueryElement::ElementType type, void const* ptr,
00402                     dbTableDescriptor* table = NULL)
00403     {
00404         nextElement = &(*nextElement=new dbQueryElement(type,ptr,table))->next;
00405         operand = (type == dbQueryElement::qExpression);
00406         return *this;
00407     }
00408 
00409     bool isEmpty() { 
00410         return elements == NULL 
00411             || (elements->next == NULL && elements->type == dbQueryElement::qExpression && *(char_t*)elements->ptr == 0);
00412     }
00413 
00414 
00415     dbQuery& reset();
00416 
00417     //
00418     // Redefined operator = and , make it possible to specify query in the
00419     // following way:
00420     //         int x, y;
00421     //         dbDataTime dt;
00422     //         dbQuery q;
00423     //         dbCursor<record> cursor;
00424     //         q = "x=",x,"and y=",y,"and",dt == "date";
00425     //         for (x = 0; x < max_x; x++) {
00426     //             for (y = 0; y < max_y; y++) {
00427     //                 cursor.select(q);
00428     //                 ...
00429     //             }
00430     //         }
00431 
00432     dbQuery& add(dbQueryExpression const& expr);
00433 
00434     dbQuery& And(dbQueryExpression const& expr) { 
00435         if (elements != NULL) { 
00436             append(dbQueryElement::qExpression, _T("and"));
00437         }
00438         return add(expr);
00439     }
00440 
00441     dbQuery& Or(dbQueryExpression const& expr) { 
00442         if (elements != NULL) { 
00443             append(dbQueryElement::qExpression, _T("or"));
00444         }
00445         return add(expr);
00446     }
00447 
00448     dbQuery& And(char_t const* str) {
00449         if (elements != NULL) {
00450             append(dbQueryElement::qExpression, _T("and"));
00451         }
00452         return append(dbQueryElement::qExpression, str);
00453     }
00454 
00455     dbQuery& Or(char_t const* str) {
00456         if (elements != NULL) {
00457             append(dbQueryElement::qExpression, _T("or"));
00458         }
00459         return append(dbQueryElement::qExpression, str);
00460     }
00461 
00462     dbQuery& add(char_t const* str) {
00463         return append(operand ? dbQueryElement::qVarString
00464                       : dbQueryElement::qExpression, str);
00465     }
00466     dbQuery& add(char_t const** str) {
00467         return append(dbQueryElement::qVarStringPtr, str);
00468     }
00469     dbQuery& add(char_t** str) {
00470         return append(dbQueryElement::qVarStringPtr, str);
00471     }
00472     dbQuery& add(rectangle const& rect) {
00473         return append(dbQueryElement::qVarRectangle, &rect);
00474     }
00475     dbQuery& add(rectangle* rect) {
00476         return append(dbQueryElement::qVarRectanglePtr, &rect);
00477     }
00478 #ifdef USE_STD_STRING
00479     dbQuery& add(STD_STRING const& str) { 
00480         return append(dbQueryElement::qVarStdString, &str);
00481     }
00482     dbQuery& operator,(STD_STRING const& str) { return add(str); }
00483 #endif
00484 #ifdef USE_MFC_STRING
00485     dbQuery& add(MFC_STRING const& str) { 
00486         return append(dbQueryElement::qVarMfcString, &str);
00487     }
00488     dbQuery& operator,(MFC_STRING const& str) { return add(str); }
00489 #endif
00490     dbQuery& add(int1 const& value) {
00491         return append(dbQueryElement::qVarInt1, &value);
00492     }
00493     dbQuery& add (int2 const& value) {
00494         return append(dbQueryElement::qVarInt2, &value);
00495     }
00496     dbQuery& add (int4 const& value) {
00497         return append(dbQueryElement::qVarInt4, &value);
00498     }
00499     dbQuery& add (db_int8 const& value) {
00500         return append(dbQueryElement::qVarInt8, &value);
00501     }
00502     dbQuery& add(nat1 const& value) {
00503         return append(dbQueryElement::qVarInt1, &value);
00504     }
00505     dbQuery& add (nat2 const& value) {
00506         return append(dbQueryElement::qVarInt2, &value);
00507     }
00508     dbQuery& add (nat4 const& value) {
00509         return append(dbQueryElement::qVarInt4, &value);
00510     }
00511     dbQuery& add (db_nat8 const& value) {
00512         return append(dbQueryElement::qVarInt8, &value);
00513     }
00514 #if SIZEOF_LONG != 8 
00515     dbQuery& add (long const& value) {
00516         return append(sizeof(long) == 4 ? dbQueryElement::qVarInt4 : dbQueryElement::qVarInt8, &value);
00517     }
00518     dbQuery& add (unsigned long const& value) {
00519         return append(sizeof(long) == 4 ? dbQueryElement::qVarInt4 : dbQueryElement::qVarInt8, &value);
00520     }
00521 #endif
00522     dbQuery& add (real4 const& value) {
00523         return append(dbQueryElement::qVarReal4, &value);
00524     }
00525     dbQuery& add(real8 const& value) {
00526         return append(dbQueryElement::qVarReal8, &value);
00527     }
00528     dbQuery& add(void const* value) { 
00529         return append(dbQueryElement::qVarRawData, value);
00530     }
00531     dbQuery& add(void** value) { 
00532         return append(dbQueryElement::qVarRawDataPtr, value);
00533     }
00534 #ifndef bool
00535     dbQuery& add(bool const& value) {
00536         return append(dbQueryElement::qVarBool, &value);
00537     }
00538     dbQuery& operator,(bool const&  value) { return add(value); }
00539 #endif
00540 
00541     dbQuery& operator,(char_t const*  value) { return add(value); }
00542     dbQuery& operator,(char_t const** value) { return add(value); }
00543     dbQuery& operator,(char_t** value) { return add(value); }
00544     dbQuery& operator,(int1 const&  value) { return add(value); }
00545     dbQuery& operator,(int2 const&  value) { return add(value); }
00546     dbQuery& operator,(int4 const&  value) { return add(value); }
00547     dbQuery& operator,(db_int8 const&  value) { return add(value); }
00548     dbQuery& operator,(nat1 const&  value) { return add(value); }
00549     dbQuery& operator,(nat2 const&  value) { return add(value); }
00550     dbQuery& operator,(nat4 const&  value) { return add(value); }
00551     dbQuery& operator,(db_nat8 const&  value) { return add(value); }
00552 #if SIZEOF_LONG != 8
00553     dbQuery& operator,(long const&  value) { return add(value); }
00554     dbQuery& operator,(unsigned long const&  value) { return add(value); }
00555 #endif
00556     dbQuery& operator,(real4 const& value) { return add(value); }
00557     dbQuery& operator,(real8 const& value) { return add(value); }
00558     dbQuery& operator,(void const*  value) { return add(value); }
00559     dbQuery& operator,(dbQueryExpression const& expr) { return add(expr); }
00560     dbQuery& operator,(rectangle const& rect) { return add(rect); }
00561 
00562     dbQuery& operator = (const char_t* str) {
00563         return reset().append(dbQueryElement::qExpression, str);
00564     }
00565 
00566 #if !defined(_MSC_VER) || _MSC_VER+0 >= 1300
00567     inline dbQuery& operator,(dbArray<db_int4> const& value) { 
00568         return append(dbQueryElement::qVarArrayOfInt4, &value);
00569     }
00570 
00571     inline dbQuery& operator,(dbArray<db_int4>const* const& value) { 
00572         return append(dbQueryElement::qVarArrayOfInt4Ptr, &value);
00573     }
00574 
00575     inline dbQuery& operator,(dbArray<db_int8> const& value) { 
00576         return append(dbQueryElement::qVarArrayOfInt8, &value);
00577     }
00578 
00579     inline dbQuery& operator,(dbArray<db_int8>const* const& value) { 
00580         return append(dbQueryElement::qVarArrayOfInt8Ptr, &value);
00581     }
00582 
00583     inline dbQuery& add(dbArray<db_int4> const& value) { 
00584         return append(dbQueryElement::qVarArrayOfInt4, &value);
00585     }
00586 
00587     inline dbQuery& add(dbArray<db_int4>const* const& value) { 
00588         return append(dbQueryElement::qVarArrayOfInt4Ptr, &value);
00589     }
00590 
00591     inline dbQuery& add(dbArray<db_int8> const& value) { 
00592         return append(dbQueryElement::qVarArrayOfInt8, &value);
00593     }
00594 
00595     inline dbQuery& add(dbArray<db_int8>const* const& value) { 
00596         return append(dbQueryElement::qVarArrayOfInt8Ptr, &value);
00597     }
00598 #endif
00599 
00600 #ifndef NO_MEMBER_TEMPLATES
00601     template<class T>
00602     dbQuery& operator,(dbReference<T> const& value) { 
00603         return append(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00604     }
00605 
00606     template<class T>
00607     dbQuery& operator,(dbArray< dbReference<T> > const& value) { 
00608         return append(dbQueryElement::qVarArrayOfRef, &value, 
00609                       &T::dbDescriptor);
00610     }
00611     template<class T>
00612     dbQuery& operator,(dbArray< dbReference<T> >const* const& value) { 
00613         return append(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00614     }
00615 
00616     template<class T>
00617     dbQuery& add(dbReference<T> const& value) { 
00618         return append(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00619     }
00620 
00621     template<class T>
00622     dbQuery& add(dbArray< dbReference<T> > const& value) { 
00623         return append(dbQueryElement::qVarArrayOfRef, &value, 
00624                       &T::dbDescriptor);
00625     }
00626 
00627     template<class T>
00628     dbQuery& add(dbArray< dbReference<T> >const* const& value) { 
00629         return append(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00630     }
00631 
00632     template<class T>
00633     dbQuery& operator = (T const& value) { 
00634         return reset().add(value);
00635     }   
00636 #else
00637     dbQuery& operator = (dbQueryExpression const& expr) {
00638         return reset().add(expr);
00639     }    
00640     dbQuery& operator = (rectangle const& expr) {
00641         return reset().add(expr);
00642     }    
00643 #endif
00644 
00645     dbQuery() {
00646         elements = NULL;
00647         nextElement = &elements;
00648         operand = false;
00649         pos = 0;
00650     }
00651     dbQuery(char_t const* str) {
00652         elements = new dbQueryElement(dbQueryElement::qExpression, str);
00653         nextElement = &elements->next;
00654         operand = true;
00655         pos = 0;
00656     }
00657     ~dbQuery() {
00658         reset();
00659     }
00660 };
00661 
00662 #ifdef NO_MEMBER_TEMPLATES
00663 template<class T>
00664 inline dbQueryExpression& operator,(dbQueryExpression& expr, dbReference<T> const& value) { 
00665     return expr.add(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00666 }
00667 template<class T>
00668 inline dbQueryExpression& operator,(dbQueryExpression& expr, dbArray< dbReference<T> > const& value) { 
00669     return expr.add(dbQueryElement::qVarArrayOfRef, &value, &T::dbDescriptor);
00670 }
00671 
00672 template<class T>
00673 inline dbQueryExpression& operator,(dbQueryExpression& expr, dbArray< dbReference<T> >const* const& value) { 
00674     return expr.add(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00675 }
00676 
00677 template<class T>
00678 inline dbQuery& operator,(dbQuery& query, dbReference<T> const& value) { 
00679     return query.append(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00680 }
00681 
00682 template<class T>
00683 inline dbQuery& operator,(dbQuery& query, dbArray< dbReference<T> > const& value) 
00684 { 
00685     return query.append(dbQueryElement::qVarArrayOfRef, &value, &T::dbDescriptor);
00686 }
00687 
00688 template<class T>
00689 inline dbQuery& operator,(dbQuery& query, 
00690                           dbArray< dbReference<T> >const* const& value) 
00691 { 
00692     return query.append(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00693 }
00694 
00695 template<class T>
00696 inline dbQuery& add(dbQuery& query, dbReference<T> const& value) { 
00697     return query.append(dbQueryElement::qVarReference, &value, &T::dbDescriptor);
00698 }
00699 
00700 template<class T>
00701 inline dbQuery& add(dbQuery& query, dbArray< dbReference<T> > const& value) { 
00702     return query.append(dbQueryElement::qVarArrayOfRef, &value, &T::dbDescriptor);
00703 }
00704 
00705 template<class T>
00706 inline dbQuery& add(dbQuery& query, dbArray< dbReference<T> >const* const& value) { 
00707     return query.append(dbQueryElement::qVarArrayOfRefPtr, &value, &T::dbDescriptor);
00708 }
00709 #endif
00710 
00711 #define USER_FUNC(f) static dbUserFunction f##_descriptor(&f, STRLITERAL(#f))
00712 
00713 class  dbInheritedAttribute;
00714 class  dbSynthesizedAttribute;
00715 
00720 class GIGABASE_DLL_ENTRY  dbUserFunctionArgument { 
00721   public:
00722     enum dbArgumentType { 
00723         atInteger, 
00724         atBoolean, 
00725         atString, 
00726         atReal, 
00727         atReference, 
00728         atRawBinary
00729     };  
00730     dbArgumentType type; 
00731     union {
00732         real8         realValue;
00733         db_int8       intValue;
00734         bool          boolValue;
00735         char_t const* strValue;
00736         oid_t         oidValue;
00737         void*         rawValue;
00738     } u;
00739 
00740   private:
00741     friend class dbDatabase;
00742     dbUserFunctionArgument(dbExprNode*             expr, 
00743                            dbInheritedAttribute&   iattr, 
00744                            dbSynthesizedAttribute& sattr, 
00745                            int                     i);
00746 };
00747 
00756 class GIGABASE_DLL_ENTRY dbUserFunction {
00757     friend class dbDatabase;
00758     friend class dbCompiler;
00759 
00760     void*   fptr;
00761     char_t* fname;
00762 
00763     dbUserFunction* next;
00764     static dbUserFunction* list;
00765 
00766     enum funcType {
00767         fInt2Bool,
00768         fReal2Bool,
00769         fStr2Bool,
00770         fInt2Int,
00771         fReal2Int,
00772         fStr2Int,
00773         fInt2Real,
00774         fReal2Real,
00775         fStr2Real,
00776         fInt2Str,
00777         fReal2Str,
00778         fStr2Str, 
00779         fArg2Bool, 
00780         fArg2Int, 
00781         fArg2Real, 
00782         fArg2Str, 
00783         fArgArg2Bool, 
00784         fArgArg2Int, 
00785         fArgArg2Real, 
00786         fArgArg2Str, 
00787         fArgArgArg2Bool, 
00788         fArgArgArg2Int, 
00789         fArgArgArg2Real, 
00790         fArgArgArg2Str
00791     };
00792     int type;
00793 
00794     void bind(char_t* name, void* f, funcType ftype);
00795 
00796   public:
00797 
00798     static dbUserFunction* find(char_t const* name) {
00799         for (dbUserFunction* func = list; func != NULL; func = func->next) {
00800             if (name == func->fname) {
00801                 return func;
00802             }
00803         }
00804         return NULL;
00805     }
00806 
00807     int getParameterType();
00808 
00809     int getNumberOfParameters();
00810 
00811     dbUserFunction(bool (__cdecl *f)(db_int8), char_t* name) {
00812         bind(name, (void*)f, fInt2Bool);
00813     }
00814     dbUserFunction(bool (__cdecl *f)(real8), char_t* name) {
00815         bind(name, (void*)f, fReal2Bool);
00816     }
00817     dbUserFunction(bool (__cdecl *f)(char_t const*), char_t* name) {
00818         bind(name, (void*)f, fStr2Bool);
00819     }
00820     dbUserFunction(db_int8 (__cdecl *f)(db_int8), char_t* name) {
00821         bind(name, (void*)f, fInt2Int);
00822     }
00823     dbUserFunction(db_int8 (__cdecl *f)(real8), char_t* name) {
00824         bind(name, (void*)f, fReal2Int);
00825     }
00826     dbUserFunction(db_int8 (__cdecl *f)(char_t const*), char_t* name) {
00827         bind(name, (void*)f, fStr2Int);
00828     }
00829     dbUserFunction(real8 (__cdecl *f)(db_int8), char_t* name) {
00830         bind(name, (void*)f, fInt2Real);
00831     }
00832     dbUserFunction(real8 (__cdecl *f)(real8), char_t* name) {
00833         bind(name, (void*)f, fReal2Real);
00834     }
00835     dbUserFunction(real8 (__cdecl *f)(char_t const*), char_t* name) {
00836         bind(name, (void*)f, fStr2Real);
00837     }
00838     dbUserFunction(char_t* (__cdecl *f)(db_int8), char_t* name) {
00839         bind(name, (void*)f, fInt2Str);
00840     }
00841     dbUserFunction(char_t* (__cdecl *f)(real8), char_t* name) {
00842         bind(name, (void*)f, fReal2Str);
00843     }
00844     dbUserFunction(char_t* (__cdecl *f)(char_t const*), char_t* name) {
00845         bind(name, (void*)f, fStr2Str);
00846     }
00847 
00848     dbUserFunction(bool (__cdecl *f)(dbUserFunctionArgument&), char_t* name) { 
00849         bind(name, (void*)f, fArg2Bool); 
00850     }
00851     dbUserFunction(char_t* (__cdecl *f)(dbUserFunctionArgument&), char_t* name) { 
00852         bind(name, (void*)f, fArg2Str); 
00853     }
00854     dbUserFunction(db_int8 (__cdecl *f)(dbUserFunctionArgument&), char_t* name) { 
00855         bind(name, (void*)f, fArg2Int); 
00856     }
00857     dbUserFunction(real8 (__cdecl *f)(dbUserFunctionArgument&), char_t* name) { 
00858         bind(name, (void*)f, fArg2Real); 
00859     }
00860 
00861     dbUserFunction(bool (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00862         bind(name, (void*)f, fArgArg2Bool); 
00863     }
00864     dbUserFunction(char_t* (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00865         bind(name, (void*)f, fArgArg2Str); 
00866     }
00867     dbUserFunction(db_int8 (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00868         bind(name, (void*)f, fArgArg2Int); 
00869     }
00870     dbUserFunction(real8 (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00871         bind(name, (void*)f, fArgArg2Real); 
00872     }
00873 
00874 
00875     dbUserFunction(bool (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00876         bind(name, (void*)f, fArgArgArg2Bool); 
00877     }
00878     dbUserFunction(char_t* (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00879         bind(name, (void*)f, fArgArgArg2Str); 
00880     }
00881     dbUserFunction(db_int8 (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00882         bind(name, (void*)f, fArgArgArg2Int); 
00883     }
00884     dbUserFunction(real8 (__cdecl *f)(dbUserFunctionArgument&, dbUserFunctionArgument&, dbUserFunctionArgument&), char_t* name) { 
00885         bind(name, (void*)f, fArgArgArg2Real); 
00886     }
00887 
00888     ~dbUserFunction();
00889 };
00890 
00891 END_GIGABASE_NAMESPACE
00892 
00893 
00894 #endif

Generated on Mon Aug 23 2010 00:04:01 for GigaBASE by  doxygen 1.7.1