00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #ifndef _SWQ_H_INCLUDED_
00021 #define _SWQ_H_INCLUDED_
00022
00023 #include "cpl_conv.h"
00024 #include "cpl_string.h"
00025
00026 #if defined(_WIN32) && !defined(_WIN32_WCE)
00027 # define strcasecmp stricmp
00028 #elif defined(_WIN32_WCE)
00029 # define strcasecmp _stricmp
00030 #endif
00031
00032 typedef enum {
00033 SWQ_OR,
00034 SWQ_AND,
00035 SWQ_NOT,
00036 SWQ_EQ,
00037 SWQ_NE,
00038 SWQ_GE,
00039 SWQ_LE,
00040 SWQ_LT,
00041 SWQ_GT,
00042 SWQ_LIKE,
00043 SWQ_ISNULL,
00044 SWQ_IN,
00045 SWQ_BETWEEN,
00046 SWQ_ADD,
00047 SWQ_SUBTRACT,
00048 SWQ_MULTIPLY,
00049 SWQ_DIVIDE,
00050 SWQ_MODULUS,
00051 SWQ_CONCAT,
00052 SWQ_SUBSTR,
00053 SWQ_AVG,
00054 SWQ_MIN,
00055 SWQ_MAX,
00056 SWQ_COUNT,
00057 SWQ_SUM,
00058 SWQ_CAST,
00059 SWQ_FUNC_DEFINED,
00060 SWQ_UNKNOWN
00061 } swq_op;
00062
00063 typedef enum {
00064 SWQ_INTEGER,
00065 SWQ_FLOAT,
00066 SWQ_STRING,
00067 SWQ_BOOLEAN,
00068 SWQ_DATE,
00069 SWQ_TIME,
00070 SWQ_TIMESTAMP,
00071 SWQ_NULL,
00072 SWQ_OTHER,
00073 SWQ_ERROR
00074 } swq_field_type;
00075
00076 typedef enum {
00077 SNT_CONSTANT,
00078 SNT_COLUMN,
00079 SNT_OPERATION
00080 } swq_node_type;
00081
00082
00083 class swq_field_list;
00084 class swq_expr_node;
00085 class swq_select;
00086
00087 typedef swq_expr_node *(*swq_field_fetcher)( swq_expr_node *op,
00088 void *record_handle );
00089 typedef swq_expr_node *(*swq_op_evaluator)(swq_expr_node *op,
00090 swq_expr_node **sub_field_values );
00091 typedef swq_field_type (*swq_op_checker)( swq_expr_node *op );
00092
00093 class swq_expr_node {
00094 static void Quote( CPLString &, char chQuote = '\'' );
00095 public:
00096 swq_expr_node();
00097
00098 swq_expr_node( const char * );
00099 swq_expr_node( int );
00100 swq_expr_node( double );
00101 swq_expr_node( swq_op );
00102
00103 ~swq_expr_node();
00104
00105 void Initialize();
00106 char *Unparse( swq_field_list *, char chColumnQuote );
00107 void Dump( FILE *fp, int depth );
00108 swq_field_type Check( swq_field_list * );
00109 swq_expr_node* Evaluate( swq_field_fetcher pfnFetcher,
00110 void *record );
00111
00112 swq_node_type eNodeType;
00113 swq_field_type field_type;
00114
00115
00116 void PushSubExpression( swq_expr_node * );
00117 void ReverseSubExpressions();
00118 int nOperation;
00119 int nSubExprCount;
00120 swq_expr_node **papoSubExpr;
00121
00122
00123 int field_index;
00124 int table_index;
00125
00126
00127 int is_null;
00128 char *string_value;
00129 int int_value;
00130 double float_value;
00131 };
00132
00133 class swq_operation {
00134 public:
00135 swq_operation() {}
00136 ~swq_operation() {}
00137
00138 swq_op eOperation;
00139 CPLString osName;
00140 swq_op_evaluator pfnEvaluator;
00141 swq_op_checker pfnChecker;
00142 };
00143
00144 class swq_op_registrar {
00145 public:
00146 static const swq_operation *GetOperator( const char * );
00147 static const swq_operation *GetOperator( swq_op eOperation );
00148 static void Initialize();
00149 static void DeInitialize();
00150 static void AddOperator( const char *pszName, swq_op eOpCode,
00151 swq_op_evaluator pfnEvaluator = NULL,
00152 swq_op_checker pfnChecker = NULL );
00153 };
00154
00155 typedef struct {
00156 char *data_source;
00157 char *table_name;
00158 char *table_alias;
00159 } swq_table_def;
00160
00161 class swq_field_list {
00162 public:
00163 int count;
00164 char **names;
00165 swq_field_type *types;
00166 int *table_ids;
00167 int *ids;
00168
00169 int table_count;
00170 swq_table_def *table_defs;
00171 };
00172
00173 class swq_parse_context {
00174 public:
00175 swq_parse_context() : nStartToken(0), poRoot(NULL), poSelect(NULL) {}
00176
00177 int nStartToken;
00178 const char *pszInput;
00179 const char *pszNext;
00180
00181 swq_expr_node *poRoot;
00182
00183 swq_select *poSelect;
00184 };
00185
00186
00187
00188
00189
00190 int swqparse( swq_parse_context *context );
00191 int swqlex( swq_expr_node **ppNode, swq_parse_context *context );
00192
00193 int swq_identify_field( const char *token, swq_field_list *field_list,
00194 swq_field_type *this_type, int *table_id );
00195
00196 CPLErr swq_expr_compile( const char *where_clause,
00197 int field_count,
00198 char **field_list,
00199 swq_field_type *field_types,
00200 swq_expr_node **expr_root );
00201
00202 CPLErr swq_expr_compile2( const char *where_clause,
00203 swq_field_list *field_list,
00204 swq_expr_node **expr_root );
00205
00206
00207
00208
00209 int swq_test_like( const char *input, const char *pattern );
00210
00211 swq_expr_node *SWQGeneralEvaluator( swq_expr_node *, swq_expr_node **);
00212 swq_field_type SWQGeneralChecker( swq_expr_node *node );
00213 swq_expr_node *SWQCastEvaluator( swq_expr_node *, swq_expr_node **);
00214 swq_field_type SWQCastChecker( swq_expr_node *node );
00215
00216
00217
00218 #define SWQP_ALLOW_UNDEFINED_COL_FUNCS 0x01
00219
00220 #define SWQM_SUMMARY_RECORD 1
00221 #define SWQM_RECORDSET 2
00222 #define SWQM_DISTINCT_LIST 3
00223
00224 typedef enum {
00225 SWQCF_NONE = 0,
00226 SWQCF_AVG = SWQ_AVG,
00227 SWQCF_MIN = SWQ_MIN,
00228 SWQCF_MAX = SWQ_MAX,
00229 SWQCF_COUNT = SWQ_COUNT,
00230 SWQCF_SUM = SWQ_SUM,
00231 SWQCF_CUSTOM
00232 } swq_col_func;
00233
00234 typedef struct {
00235 swq_col_func col_func;
00236 char *field_name;
00237 char *field_alias;
00238 int table_index;
00239 int field_index;
00240 swq_field_type field_type;
00241 swq_field_type target_type;
00242 int field_length;
00243 int field_precision;
00244 int distinct_flag;
00245 swq_expr_node *expr;
00246 } swq_col_def;
00247
00248 typedef struct {
00249 int count;
00250
00251 char **distinct_list;
00252 double sum;
00253 double min;
00254 double max;
00255 } swq_summary;
00256
00257 typedef struct {
00258 char *field_name;
00259 int table_index;
00260 int field_index;
00261 int ascending_flag;
00262 } swq_order_def;
00263
00264 typedef struct {
00265 int secondary_table;
00266
00267 char *primary_field_name;
00268 int primary_field;
00269
00270 swq_op op;
00271
00272 char *secondary_field_name;
00273 int secondary_field;
00274 } swq_join_def;
00275
00276 class swq_select
00277 {
00278 public:
00279 swq_select();
00280 ~swq_select();
00281
00282 int query_mode;
00283
00284 char *raw_select;
00285
00286 int PushField( swq_expr_node *poExpr, const char *pszAlias=NULL,
00287 int distinct_flag = FALSE );
00288 int result_columns;
00289 swq_col_def *column_defs;
00290 swq_summary *column_summary;
00291
00292 int PushTableDef( const char *pszDataSource,
00293 const char *pszTableName,
00294 const char *pszAlias );
00295 int table_count;
00296 swq_table_def *table_defs;
00297
00298 void PushJoin( int iSecondaryTable,
00299 const char *pszPrimaryField,
00300 const char *pszSecondaryField );
00301 int join_count;
00302 swq_join_def *join_defs;
00303
00304 swq_expr_node *where_expr;
00305
00306 void PushOrderBy( const char *pszFieldName, int bAscending );
00307 int order_specs;
00308 swq_order_def *order_defs;
00309
00310 CPLErr preparse( const char *select_statement );
00311 CPLErr expand_wildcard( swq_field_list *field_list );
00312 CPLErr parse( swq_field_list *field_list, int parse_flags );
00313
00314 void Dump( FILE * );
00315 };
00316
00317 CPLErr swq_select_parse( swq_select *select_info,
00318 swq_field_list *field_list,
00319 int parse_flags );
00320
00321 const char *swq_select_finish_summarize( swq_select *select_info );
00322 const char *swq_select_summarize( swq_select *select_info,
00323 int dest_column,
00324 const char *value );
00325
00326 int swq_is_reserved_keyword(const char* pszStr);
00327
00328 #endif