mirror of
https://github.com/owntone/owntone-server.git
synced 2025-03-20 04:24:20 -04:00
Fixes for not, add startswith and endswith operators
This commit is contained in:
parent
a8e9e7bfd6
commit
24f40d7956
@ -132,7 +132,9 @@ typedef struct tag_sp_node {
|
|||||||
#define T_YEAR 0x0019
|
#define T_YEAR 0x0019
|
||||||
#define T_DATE 0x001a
|
#define T_DATE 0x001a
|
||||||
#define T_NOT 0x001b
|
#define T_NOT 0x001b
|
||||||
#define T_LAST 0x001c
|
#define T_STARTSWITH 0x001c
|
||||||
|
#define T_ENDSWITH 0x001d
|
||||||
|
#define T_LAST 0x001e
|
||||||
|
|
||||||
#define T_EOF 0x00fd
|
#define T_EOF 0x00fd
|
||||||
#define T_BOF 0x00fe
|
#define T_BOF 0x00fe
|
||||||
@ -166,7 +168,9 @@ char *sp_token_descr[] = {
|
|||||||
"month(s)",
|
"month(s)",
|
||||||
"year(s)",
|
"year(s)",
|
||||||
"date",
|
"date",
|
||||||
"not"
|
"not",
|
||||||
|
"like",
|
||||||
|
"like"
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct tag_fieldlookup {
|
typedef struct tag_fieldlookup {
|
||||||
@ -212,7 +216,7 @@ FIELDLOOKUP sp_fields[] = {
|
|||||||
{ T_INT_FIELD, "force_update" },
|
{ T_INT_FIELD, "force_update" },
|
||||||
{ T_STRING_FIELD, "codectype" },
|
{ T_STRING_FIELD, "codectype" },
|
||||||
{ T_INT_FIELD, "idx" },
|
{ T_INT_FIELD, "idx" },
|
||||||
|
|
||||||
/* end of db fields */
|
/* end of db fields */
|
||||||
{ T_OR, "or" },
|
{ T_OR, "or" },
|
||||||
{ T_AND, "and" },
|
{ T_AND, "and" },
|
||||||
@ -231,7 +235,9 @@ FIELDLOOKUP sp_fields[] = {
|
|||||||
{ T_YEAR, "years" },
|
{ T_YEAR, "years" },
|
||||||
{ T_YEAR, "year" },
|
{ T_YEAR, "year" },
|
||||||
{ T_NOT, "not" },
|
{ T_NOT, "not" },
|
||||||
|
{ T_STARTSWITH, "startswith" },
|
||||||
|
{ T_ENDSWITH, "endswith" },
|
||||||
|
|
||||||
/* end */
|
/* end */
|
||||||
{ 0, NULL },
|
{ 0, NULL },
|
||||||
};
|
};
|
||||||
@ -269,7 +275,7 @@ char *sp_errorstrings[] = {
|
|||||||
"Expecting '\"' (closing quote)",
|
"Expecting '\"' (closing quote)",
|
||||||
"Expecting literal string",
|
"Expecting literal string",
|
||||||
"Expecting '\"' (opening quote)",
|
"Expecting '\"' (opening quote)",
|
||||||
"Expecting integer comparison operator (=,<,>, etc)",
|
"Expecting integer comparison operator (=,<,>, etc)",
|
||||||
"Expecting integer",
|
"Expecting integer",
|
||||||
"Expecting date comparison operator (<,<=,>,>=)",
|
"Expecting date comparison operator (<,<=,>,>=)",
|
||||||
"Expecting interval comparison (before, after)",
|
"Expecting interval comparison (before, after)",
|
||||||
@ -312,8 +318,8 @@ void sp_enter_exit(PARSETREE tree, char *function, int enter, void *result) {
|
|||||||
tree->level--;
|
tree->level--;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* see if a string is actually a number
|
* see if a string is actually a number
|
||||||
*
|
*
|
||||||
@ -322,11 +328,11 @@ void sp_enter_exit(PARSETREE tree, char *function, int enter, void *result) {
|
|||||||
*/
|
*/
|
||||||
int sp_isnumber(char *string) {
|
int sp_isnumber(char *string) {
|
||||||
char *current=string;
|
char *current=string;
|
||||||
|
|
||||||
while(*current && (*current >= '0') && (*current <= '9')) {
|
while(*current && (*current >= '0') && (*current <= '9')) {
|
||||||
current++;
|
current++;
|
||||||
}
|
}
|
||||||
|
|
||||||
return *current ? 0 : 1;
|
return *current ? 0 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -340,12 +346,12 @@ int sp_isnumber(char *string) {
|
|||||||
time_t sp_isdate(char *string) {
|
time_t sp_isdate(char *string) {
|
||||||
struct tm date_time;
|
struct tm date_time;
|
||||||
time_t seconds=0;
|
time_t seconds=0;
|
||||||
|
|
||||||
memset((void*)&date_time,0,sizeof(date_time));
|
memset((void*)&date_time,0,sizeof(date_time));
|
||||||
if(strptime(string,"%Y-%m-%d",&date_time)) {
|
if(strptime(string,"%Y-%m-%d",&date_time)) {
|
||||||
seconds=timegm(&date_time);
|
seconds=timegm(&date_time);
|
||||||
}
|
}
|
||||||
|
|
||||||
return seconds;
|
return seconds;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -448,8 +454,8 @@ int sp_scan(PARSETREE tree) {
|
|||||||
tree->token.token_id = T_NOT;
|
tree->token.token_id = T_NOT;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if(*tree->current == '"') {
|
if(*tree->current == '"') {
|
||||||
advance = 1;
|
advance = 1;
|
||||||
@ -509,7 +515,8 @@ int sp_scan(PARSETREE tree) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* check for numberic? */
|
/* check for numberic? */
|
||||||
if(tree->token.token_id == T_STRING &&
|
if(tree->token.token_id == T_STRING &&
|
||||||
|
(!tree->in_string) &&
|
||||||
sp_isnumber(tree->token.data.cvalue)) {
|
sp_isnumber(tree->token.data.cvalue)) {
|
||||||
/* woops! */
|
/* woops! */
|
||||||
numval = atoi(tree->token.data.cvalue);
|
numval = atoi(tree->token.data.cvalue);
|
||||||
@ -517,15 +524,16 @@ int sp_scan(PARSETREE tree) {
|
|||||||
tree->token.data.ivalue = numval;
|
tree->token.data.ivalue = numval;
|
||||||
tree->token.token_id = T_NUMBER;
|
tree->token.token_id = T_NUMBER;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(tree->token.token_id == T_STRING &&
|
if(tree->token.token_id == T_STRING &&
|
||||||
|
(!tree->in_string) &&
|
||||||
(tval=sp_isdate(tree->token.data.cvalue))) {
|
(tval=sp_isdate(tree->token.data.cvalue))) {
|
||||||
free(tree->token.data.cvalue);
|
free(tree->token.data.cvalue);
|
||||||
tree->token.data.tvalue = tval;
|
tree->token.data.tvalue = tval;
|
||||||
tree->token.token_id = T_DATE;
|
tree->token.token_id = T_DATE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
tree->current=tail;
|
tree->current=tail;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -581,9 +589,9 @@ int sp_parse(PARSETREE tree, char *term) {
|
|||||||
tree->current=tree->term;
|
tree->current=tree->term;
|
||||||
tree->token.token_id=T_BOF;
|
tree->token.token_id=T_BOF;
|
||||||
|
|
||||||
if(tree->tree)
|
if(tree->tree)
|
||||||
sp_free_node(tree->tree);
|
sp_free_node(tree->tree);
|
||||||
|
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
tree->tree = sp_parse_phrase(tree);
|
tree->tree = sp_parse_phrase(tree);
|
||||||
|
|
||||||
@ -610,10 +618,10 @@ SP_NODE *sp_parse_phrase(PARSETREE tree) {
|
|||||||
SP_NODE *expr;
|
SP_NODE *expr;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_phrase",1,NULL);
|
sp_enter_exit(tree,"sp_parse_phrase",1,NULL);
|
||||||
|
|
||||||
DPRINTF(E_SPAM,L_PARSE,"%*s Entering sp_parse_phrase\n",tree->level," ");
|
DPRINTF(E_SPAM,L_PARSE,"%*s Entering sp_parse_phrase\n",tree->level," ");
|
||||||
tree->level++;
|
tree->level++;
|
||||||
|
|
||||||
expr = sp_parse_oexpr(tree);
|
expr = sp_parse_oexpr(tree);
|
||||||
if((!expr) || (tree->token.token_id != T_EOF)) {
|
if((!expr) || (tree->token.token_id != T_EOF)) {
|
||||||
sp_free_node(expr);
|
sp_free_node(expr);
|
||||||
@ -635,30 +643,30 @@ SP_NODE *sp_parse_phrase(PARSETREE tree) {
|
|||||||
SP_NODE *sp_parse_aexpr(PARSETREE tree) {
|
SP_NODE *sp_parse_aexpr(PARSETREE tree) {
|
||||||
SP_NODE *expr;
|
SP_NODE *expr;
|
||||||
SP_NODE *pnew;
|
SP_NODE *pnew;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_aexpr",1,NULL);
|
sp_enter_exit(tree,"sp_parse_aexpr",1,NULL);
|
||||||
|
|
||||||
expr = sp_parse_expr(tree);
|
expr = sp_parse_expr(tree);
|
||||||
|
|
||||||
while(expr && (tree->token.token_id == T_AND)) {
|
while(expr && (tree->token.token_id == T_AND)) {
|
||||||
pnew = (SP_NODE*)malloc(sizeof(SP_NODE));
|
pnew = (SP_NODE*)malloc(sizeof(SP_NODE));
|
||||||
if(!pnew) {
|
if(!pnew) {
|
||||||
DPRINTF(E_FATAL,L_PARSE,"Malloc error\n");
|
DPRINTF(E_FATAL,L_PARSE,"Malloc error\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
memset(pnew,0x00,sizeof(SP_NODE));
|
memset(pnew,0x00,sizeof(SP_NODE));
|
||||||
pnew->op=T_AND;
|
pnew->op=T_AND;
|
||||||
pnew->op_type = SP_OPTYPE_ANDOR;
|
pnew->op_type = SP_OPTYPE_ANDOR;
|
||||||
|
|
||||||
pnew->left.node = expr;
|
pnew->left.node = expr;
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
pnew->right.node = sp_parse_expr(tree);
|
pnew->right.node = sp_parse_expr(tree);
|
||||||
|
|
||||||
if(!pnew->right.node) {
|
if(!pnew->right.node) {
|
||||||
sp_free_node(pnew);
|
sp_free_node(pnew);
|
||||||
pnew=NULL;
|
pnew=NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
expr=pnew;
|
expr=pnew;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -677,30 +685,30 @@ SP_NODE *sp_parse_aexpr(PARSETREE tree) {
|
|||||||
SP_NODE *sp_parse_oexpr(PARSETREE tree) {
|
SP_NODE *sp_parse_oexpr(PARSETREE tree) {
|
||||||
SP_NODE *expr;
|
SP_NODE *expr;
|
||||||
SP_NODE *pnew;
|
SP_NODE *pnew;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_oexpr",1,NULL);
|
sp_enter_exit(tree,"sp_parse_oexpr",1,NULL);
|
||||||
|
|
||||||
expr = sp_parse_aexpr(tree);
|
expr = sp_parse_aexpr(tree);
|
||||||
|
|
||||||
while(expr && (tree->token.token_id == T_OR)) {
|
while(expr && (tree->token.token_id == T_OR)) {
|
||||||
pnew = (SP_NODE*)malloc(sizeof(SP_NODE));
|
pnew = (SP_NODE*)malloc(sizeof(SP_NODE));
|
||||||
if(!pnew) {
|
if(!pnew) {
|
||||||
DPRINTF(E_FATAL,L_PARSE,"Malloc error\n");
|
DPRINTF(E_FATAL,L_PARSE,"Malloc error\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
memset(pnew,0x00,sizeof(SP_NODE));
|
memset(pnew,0x00,sizeof(SP_NODE));
|
||||||
pnew->op=T_OR;
|
pnew->op=T_OR;
|
||||||
pnew->op_type = SP_OPTYPE_ANDOR;
|
pnew->op_type = SP_OPTYPE_ANDOR;
|
||||||
|
|
||||||
pnew->left.node = expr;
|
pnew->left.node = expr;
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
pnew->right.node = sp_parse_aexpr(tree);
|
pnew->right.node = sp_parse_aexpr(tree);
|
||||||
|
|
||||||
if(!pnew->right.node) {
|
if(!pnew->right.node) {
|
||||||
sp_free_node(pnew);
|
sp_free_node(pnew);
|
||||||
pnew=NULL;
|
pnew=NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
expr=pnew;
|
expr=pnew;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -720,7 +728,7 @@ SP_NODE *sp_parse_expr(PARSETREE tree) {
|
|||||||
SP_NODE *expr;
|
SP_NODE *expr;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_expr",1,NULL);
|
sp_enter_exit(tree,"sp_parse_expr",1,NULL);
|
||||||
|
|
||||||
if(tree->token.token_id == T_OPENPAREN) {
|
if(tree->token.token_id == T_OPENPAREN) {
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
expr = sp_parse_oexpr(tree);
|
expr = sp_parse_oexpr(tree);
|
||||||
@ -750,9 +758,9 @@ SP_NODE *sp_parse_expr(PARSETREE tree) {
|
|||||||
*/
|
*/
|
||||||
SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
||||||
SP_NODE *expr=NULL;
|
SP_NODE *expr=NULL;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_criterion",1,expr);
|
sp_enter_exit(tree,"sp_parse_criterion",1,expr);
|
||||||
|
|
||||||
switch(tree->token.token_id) {
|
switch(tree->token.token_id) {
|
||||||
case T_STRING_FIELD:
|
case T_STRING_FIELD:
|
||||||
expr = sp_parse_string_criterion(tree);
|
expr = sp_parse_string_criterion(tree);
|
||||||
@ -788,7 +796,7 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
SP_NODE *pnew = NULL;
|
SP_NODE *pnew = NULL;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_string_criterion",1,NULL);
|
sp_enter_exit(tree,"sp_parse_string_criterion",1,NULL);
|
||||||
|
|
||||||
pnew = malloc(sizeof(SP_NODE));
|
pnew = malloc(sizeof(SP_NODE));
|
||||||
if(!pnew) {
|
if(!pnew) {
|
||||||
DPRINTF(E_FATAL,L_PARSE,"Malloc Error\n");
|
DPRINTF(E_FATAL,L_PARSE,"Malloc Error\n");
|
||||||
@ -802,10 +810,12 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
pnew->not_flag=1;
|
pnew->not_flag=1;
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
}
|
}
|
||||||
|
|
||||||
switch(tree->token.token_id) {
|
switch(tree->token.token_id) {
|
||||||
case T_EQUAL:
|
case T_EQUAL:
|
||||||
case T_INCLUDES:
|
case T_INCLUDES:
|
||||||
|
case T_STARTSWITH:
|
||||||
|
case T_ENDSWITH:
|
||||||
pnew->op=tree->token.token_id;
|
pnew->op=tree->token.token_id;
|
||||||
pnew->op_type = SP_OPTYPE_STRING;
|
pnew->op_type = SP_OPTYPE_STRING;
|
||||||
result = 1;
|
result = 1;
|
||||||
@ -845,7 +855,7 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
|
|
||||||
if(!result) {
|
if(!result) {
|
||||||
sp_free_node(pnew);
|
sp_free_node(pnew);
|
||||||
pnew=NULL;
|
pnew=NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_string_criterion",0,pnew);
|
sp_enter_exit(tree,"sp_parse_string_criterion",0,pnew);
|
||||||
@ -861,7 +871,7 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
SP_NODE *sp_parse_int_criterion(PARSETREE tree) {
|
SP_NODE *sp_parse_int_criterion(PARSETREE tree) {
|
||||||
int result=0;
|
int result=0;
|
||||||
SP_NODE *pnew = NULL;
|
SP_NODE *pnew = NULL;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_int_criterion",1,pnew);
|
sp_enter_exit(tree,"sp_parse_int_criterion",1,pnew);
|
||||||
pnew = malloc(sizeof(SP_NODE));
|
pnew = malloc(sizeof(SP_NODE));
|
||||||
if(!pnew) {
|
if(!pnew) {
|
||||||
@ -915,7 +925,7 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
sp_free_node(pnew);
|
sp_free_node(pnew);
|
||||||
pnew=NULL;
|
pnew=NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_int_criterion",0,pnew);
|
sp_enter_exit(tree,"sp_parse_int_criterion",0,pnew);
|
||||||
|
|
||||||
return pnew;
|
return pnew;
|
||||||
@ -931,7 +941,7 @@ SP_NODE *sp_parse_criterion(PARSETREE tree) {
|
|||||||
SP_NODE *sp_parse_date_criterion(PARSETREE tree) {
|
SP_NODE *sp_parse_date_criterion(PARSETREE tree) {
|
||||||
SP_NODE *pnew=NULL;
|
SP_NODE *pnew=NULL;
|
||||||
int result=0;
|
int result=0;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date_criterion",1,pnew);
|
sp_enter_exit(tree,"sp_parse_date_criterion",1,pnew);
|
||||||
pnew = malloc(sizeof(SP_NODE));
|
pnew = malloc(sizeof(SP_NODE));
|
||||||
if(!pnew) {
|
if(!pnew) {
|
||||||
@ -989,7 +999,7 @@ SP_NODE *sp_parse_date_criterion(PARSETREE tree) {
|
|||||||
sp_free_node(pnew);
|
sp_free_node(pnew);
|
||||||
pnew=NULL;
|
pnew=NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date_criterion",0,pnew);
|
sp_enter_exit(tree,"sp_parse_date_criterion",0,pnew);
|
||||||
|
|
||||||
@ -999,7 +1009,7 @@ SP_NODE *sp_parse_date_criterion(PARSETREE tree) {
|
|||||||
/**
|
/**
|
||||||
* parse a date value for a date field comparison
|
* parse a date value for a date field comparison
|
||||||
*
|
*
|
||||||
* date -> T_TODAY | T_DATE |
|
* date -> T_TODAY | T_DATE |
|
||||||
* date_interval T_BEFORE date | date_interval T_AFTER date
|
* date_interval T_BEFORE date | date_interval T_AFTER date
|
||||||
* date_interval -> T_NUMBER ( T_DAY | T_WEEK | T_MONTH | T_YEAR)
|
* date_interval -> T_NUMBER ( T_DAY | T_WEEK | T_MONTH | T_YEAR)
|
||||||
* (T_BEFORE | T_AFTER) date
|
* (T_BEFORE | T_AFTER) date
|
||||||
@ -1011,7 +1021,7 @@ time_t sp_parse_date(PARSETREE tree) {
|
|||||||
time_t result=0;
|
time_t result=0;
|
||||||
time_t interval;
|
time_t interval;
|
||||||
int before;
|
int before;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date",1,(void*)result);
|
sp_enter_exit(tree,"sp_parse_date",1,(void*)result);
|
||||||
|
|
||||||
switch(tree->token.token_id) {
|
switch(tree->token.token_id) {
|
||||||
@ -1024,7 +1034,7 @@ time_t sp_parse_date(PARSETREE tree) {
|
|||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!result) {
|
if(!result) {
|
||||||
/* must be an interval */
|
/* must be an interval */
|
||||||
interval = sp_parse_date_interval(tree);
|
interval = sp_parse_date_interval(tree);
|
||||||
@ -1038,7 +1048,7 @@ time_t sp_parse_date(PARSETREE tree) {
|
|||||||
before = 1;
|
before = 1;
|
||||||
if(tree->token.token_id == T_AFTER)
|
if(tree->token.token_id == T_AFTER)
|
||||||
before = 0;
|
before = 0;
|
||||||
|
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
result = sp_parse_date(tree);
|
result = sp_parse_date(tree);
|
||||||
if(result) {
|
if(result) {
|
||||||
@ -1050,7 +1060,7 @@ time_t sp_parse_date(PARSETREE tree) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date_criterion",0,(void*)result);
|
sp_enter_exit(tree,"sp_parse_date_criterion",0,(void*)result);
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
@ -1066,12 +1076,12 @@ time_t sp_parse_date(PARSETREE tree) {
|
|||||||
time_t sp_parse_date_interval(PARSETREE tree) {
|
time_t sp_parse_date_interval(PARSETREE tree) {
|
||||||
time_t result=0;
|
time_t result=0;
|
||||||
int count;
|
int count;
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date_interval",1,(void*)result);
|
sp_enter_exit(tree,"sp_parse_date_interval",1,(void*)result);
|
||||||
|
|
||||||
if(tree->token.token_id != T_NUMBER) {
|
if(tree->token.token_id != T_NUMBER) {
|
||||||
result=0;
|
result=0;
|
||||||
sp_set_error(tree,SP_E_NUMBER);
|
sp_set_error(tree,SP_E_NUMBER);
|
||||||
} else {
|
} else {
|
||||||
count = tree->token.data.ivalue;
|
count = tree->token.data.ivalue;
|
||||||
sp_scan(tree);
|
sp_scan(tree);
|
||||||
@ -1098,12 +1108,12 @@ time_t sp_parse_date_interval(PARSETREE tree) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sp_enter_exit(tree,"sp_parse_date_interval",0,(void*)result);
|
sp_enter_exit(tree,"sp_parse_date_interval",0,(void*)result);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* free a node, and all left/right subnodes
|
* free a node, and all left/right subnodes
|
||||||
@ -1118,8 +1128,8 @@ void sp_free_node(SP_NODE *node) {
|
|||||||
if(node->left.node) {
|
if(node->left.node) {
|
||||||
sp_free_node(node->left.node);
|
sp_free_node(node->left.node);
|
||||||
node->left.node = NULL;
|
node->left.node = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->right.node) {
|
if(node->right.node) {
|
||||||
sp_free_node(node->right.node);
|
sp_free_node(node->right.node);
|
||||||
node->right.node = NULL;
|
node->right.node = NULL;
|
||||||
@ -1129,7 +1139,7 @@ void sp_free_node(SP_NODE *node) {
|
|||||||
free(node->left.field);
|
free(node->left.field);
|
||||||
node->left.field = NULL;
|
node->left.field = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_STRING) {
|
if(node->op_type == SP_OPTYPE_STRING) {
|
||||||
if(node->right.cvalue) {
|
if(node->right.cvalue) {
|
||||||
free(node->right.cvalue);
|
free(node->right.cvalue);
|
||||||
@ -1152,19 +1162,19 @@ void sp_free_node(SP_NODE *node) {
|
|||||||
int sp_dispose(PARSETREE tree) {
|
int sp_dispose(PARSETREE tree) {
|
||||||
if(tree->term)
|
if(tree->term)
|
||||||
free(tree->term);
|
free(tree->term);
|
||||||
|
|
||||||
if(tree->token.token_id & 0x2000)
|
if(tree->token.token_id & 0x2000)
|
||||||
free(tree->token.data.cvalue);
|
free(tree->token.data.cvalue);
|
||||||
|
|
||||||
if(tree->error)
|
if(tree->error)
|
||||||
free(tree->error);
|
free(tree->error);
|
||||||
|
|
||||||
free(tree);
|
free(tree);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* calculate the size required to render the tree as a
|
* calculate the size required to render the tree as a
|
||||||
* sql query.
|
* sql query.
|
||||||
*
|
*
|
||||||
* @parameter node node/tree to calculate
|
* @parameter node node/tree to calculate
|
||||||
@ -1172,7 +1182,7 @@ int sp_dispose(PARSETREE tree) {
|
|||||||
*/
|
*/
|
||||||
int sp_node_size(SP_NODE *node) {
|
int sp_node_size(SP_NODE *node) {
|
||||||
int size;
|
int size;
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_ANDOR) {
|
if(node->op_type == SP_OPTYPE_ANDOR) {
|
||||||
size = sp_node_size(node->left.node);
|
size = sp_node_size(node->left.node);
|
||||||
size += sp_node_size(node->right.node);
|
size += sp_node_size(node->right.node);
|
||||||
@ -1186,23 +1196,26 @@ int sp_node_size(SP_NODE *node) {
|
|||||||
} else {
|
} else {
|
||||||
size += strlen(sp_token_descr[node->op & 0x0FFF]);
|
size += strlen(sp_token_descr[node->op & 0x0FFF]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_STRING) {
|
if(node->op_type == SP_OPTYPE_STRING) {
|
||||||
size += (2 + strlen(node->right.cvalue));
|
size += (2 + strlen(node->right.cvalue));
|
||||||
if(node->op == T_INCLUDES) {
|
if(node->op == T_INCLUDES) {
|
||||||
size += 2; /* extra %'s */
|
size += 2; /* extra %'s */
|
||||||
}
|
}
|
||||||
|
if((node->op == T_STARTSWITH)||(node->op == T_ENDSWITH)) {
|
||||||
|
size += 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if((node->op_type == SP_OPTYPE_INT) || (node->op_type == SP_OPTYPE_DATE)) {
|
if((node->op_type == SP_OPTYPE_INT) || (node->op_type == SP_OPTYPE_DATE)) {
|
||||||
size += 40; /* what *is* the max size of int64? */
|
size += 40; /* what *is* the max size of int64? */
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->not_flag) {
|
if(node->not_flag) {
|
||||||
size += 5; /* " not " */
|
size += 5; /* " not " */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1214,7 +1227,7 @@ int sp_node_size(SP_NODE *node) {
|
|||||||
*/
|
*/
|
||||||
void sp_serialize_sql(SP_NODE *node, char *string) {
|
void sp_serialize_sql(SP_NODE *node, char *string) {
|
||||||
char buffer[40];
|
char buffer[40];
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_ANDOR) {
|
if(node->op_type == SP_OPTYPE_ANDOR) {
|
||||||
strcat(string,"(");
|
strcat(string,"(");
|
||||||
sp_serialize_sql(node->left.node,string);
|
sp_serialize_sql(node->left.node,string);
|
||||||
@ -1224,34 +1237,34 @@ void sp_serialize_sql(SP_NODE *node, char *string) {
|
|||||||
strcat(string,")");
|
strcat(string,")");
|
||||||
} else {
|
} else {
|
||||||
strcat(string,"(");
|
strcat(string,"(");
|
||||||
strcat(string,node->left.field);
|
|
||||||
strcat(string," ");
|
|
||||||
if(node->not_flag) {
|
if(node->not_flag) {
|
||||||
strcat(string,"not ");
|
strcat(string,"not ");
|
||||||
}
|
}
|
||||||
|
strcat(string,node->left.field);
|
||||||
|
strcat(string," ");
|
||||||
strcat(string,sp_token_descr[node->op & 0x0FFF]);
|
strcat(string,sp_token_descr[node->op & 0x0FFF]);
|
||||||
strcat(string," ");
|
strcat(string," ");
|
||||||
if(node->op_type == SP_OPTYPE_STRING) {
|
if(node->op_type == SP_OPTYPE_STRING) {
|
||||||
strcat(string,"'");
|
strcat(string,"'");
|
||||||
if(node->op == T_INCLUDES)
|
if((node->op == T_INCLUDES) || (node->op == T_ENDSWITH))
|
||||||
strcat(string,"%");
|
strcat(string,"%");
|
||||||
strcat(string,node->right.cvalue);
|
strcat(string,node->right.cvalue);
|
||||||
if(node->op == T_INCLUDES)
|
if((node->op == T_INCLUDES) || (node->op == T_STARTSWITH))
|
||||||
strcat(string,"%");
|
strcat(string,"%");
|
||||||
strcat(string,"'");
|
strcat(string,"'");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_INT) {
|
if(node->op_type == SP_OPTYPE_INT) {
|
||||||
sprintf(buffer,"%d",node->right.ivalue);
|
sprintf(buffer,"%d",node->right.ivalue);
|
||||||
strcat(string,buffer);
|
strcat(string,buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(node->op_type == SP_OPTYPE_DATE) {
|
if(node->op_type == SP_OPTYPE_DATE) {
|
||||||
sprintf(buffer,"%d",(int)node->right.tvalue);
|
sprintf(buffer,"%d",(int)node->right.tvalue);
|
||||||
strcat(string,buffer);
|
strcat(string,buffer);
|
||||||
}
|
}
|
||||||
strcat(string,")");
|
strcat(string,")");
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1269,10 +1282,10 @@ char *sp_sql_clause(PARSETREE tree) {
|
|||||||
|
|
||||||
size = sp_node_size(tree->tree);
|
size = sp_node_size(tree->tree);
|
||||||
sql = (char*)malloc(size+1);
|
sql = (char*)malloc(size+1);
|
||||||
|
|
||||||
memset(sql,0x00,size+1);
|
memset(sql,0x00,size+1);
|
||||||
sp_serialize_sql(tree->tree,sql);
|
sp_serialize_sql(tree->tree,sql);
|
||||||
|
|
||||||
return sql;
|
return sql;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1302,17 +1315,17 @@ char *sp_get_error(PARSETREE tree) {
|
|||||||
*/
|
*/
|
||||||
void sp_set_error(PARSETREE tree, int error) {
|
void sp_set_error(PARSETREE tree, int error) {
|
||||||
int len;
|
int len;
|
||||||
|
|
||||||
if(tree->error)
|
if(tree->error)
|
||||||
free(tree->error);
|
free(tree->error);
|
||||||
|
|
||||||
len = 10 + (tree->token_pos / 10) + 1 + strlen(sp_errorstrings[error]) + 1;
|
len = 10 + (tree->token_pos / 10) + 1 + strlen(sp_errorstrings[error]) + 1;
|
||||||
tree->error = (char*)malloc(len);
|
tree->error = (char*)malloc(len);
|
||||||
if(!tree->error) {
|
if(!tree->error) {
|
||||||
DPRINTF(E_FATAL,L_PARSE,"Malloc error");
|
DPRINTF(E_FATAL,L_PARSE,"Malloc error");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
sprintf(tree->error,"Offset %d: %s",tree->token_pos + 1,sp_errorstrings[error]);
|
sprintf(tree->error,"Offset %d: %s",tree->token_pos + 1,sp_errorstrings[error]);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user