36 #include "utils.h" |
36 #include "utils.h" |
37 #include "methods.h" |
37 #include "methods.h" |
38 #include "session.h" |
38 #include "session.h" |
39 #include "resource.h" |
39 #include "resource.h" |
40 |
40 |
41 DavResult* dav_statement_exec(DavSession *sn, DavQLStatement *st, ...) { |
41 DavResult dav_statement_exec(DavSession *sn, DavQLStatement *st, ...) { |
42 va_list ap; |
42 va_list ap; |
43 va_start(ap, st); |
43 va_start(ap, st); |
44 DavResult *result = dav_statement_execv(sn, st, ap); |
44 DavResult result = dav_statement_execv(sn, st, ap); |
45 va_end(ap); |
45 va_end(ap); |
46 return result; |
46 return result; |
47 } |
47 } |
48 |
48 |
49 DavResult* dav_statement_execv(DavSession *sn, DavQLStatement *st, va_list ap) { |
49 DavResult dav_statement_execv(DavSession *sn, DavQLStatement *st, va_list ap) { |
50 DavResult *result = dav_session_malloc(sn, sizeof(DavResult)); |
50 DavResult result; |
51 result->result = NULL; |
51 result.result = NULL; |
52 result->status = 1; |
52 result.status = 1; |
53 |
53 |
54 // make sure the statement was successfully parsed |
54 // make sure the statement was successfully parsed |
55 if(st->type == DAVQL_ERROR) { |
55 if(st->type == DAVQL_ERROR) { |
|
56 DavResult result; |
56 return result; |
57 return result; |
57 } |
58 } |
58 |
59 |
59 // get path string |
|
60 davqlerror_t error; |
|
61 sstr_t path = dav_format_string(sn->mp->allocator, st->path, ap, &error); |
|
62 |
|
63 if(st->type == DAVQL_SELECT) { |
60 if(st->type == DAVQL_SELECT) { |
64 *result = dav_exec_select(sn, st, path.ptr, ap); |
61 return dav_exec_select(sn, st, ap); |
65 } else { |
62 } else { |
66 // TODO |
63 // TODO |
67 } |
64 } |
68 |
65 |
69 return result; |
66 return result; |
343 cfield->code = code; |
341 cfield->code = code; |
344 cfieldlist = ucx_list_append_a(mp->allocator, cfieldlist, cfield); |
342 cfieldlist = ucx_list_append_a(mp->allocator, cfieldlist, cfield); |
345 } |
343 } |
346 } |
344 } |
347 |
345 |
|
346 // get path string |
|
347 davqlerror_t error; |
|
348 sstr_t path = dav_format_string(mp->allocator, st->path, ap, &error); |
|
349 if(error) { |
|
350 // TODO: cleanup |
|
351 return result; |
|
352 } |
|
353 |
|
354 int depth = st->depth == DAV_DEPTH_PLACEHOLDER ? va_arg(ap, int) : st->depth; |
|
355 |
348 UcxBuffer *where = dav_compile_expr(sn->context, mp->allocator, st->where, ap); |
356 UcxBuffer *where = dav_compile_expr(sn->context, mp->allocator, st->where, ap); |
349 if(!where) { |
357 if(st->where && !where) { |
350 ucx_mempool_destroy(mp); |
358 ucx_mempool_destroy(mp); |
351 return result; |
359 return result; |
352 } |
360 } |
353 |
361 |
354 DavResource *selroot = dav_resource_new(sn, path); |
362 DavResource *selroot = dav_resource_new(sn, path.ptr); |
355 |
363 |
356 UcxList *stack = NULL; // stack with DavResource* elements |
364 UcxList *stack = NULL; // stack with DavResource* elements |
357 // initialize the stack with the requested resource |
365 // initialize the stack with the requested resource |
358 DavQLRes *r = ucx_mempool_malloc(mp, sizeof(DavQLRes)); |
366 DavQLRes *r = ucx_mempool_malloc(mp, sizeof(DavQLRes)); |
359 r->resource = selroot; |
367 r->resource = selroot; |
791 int ret = 0; |
807 int ret = 0; |
792 for(size_t i=0;i<count;i++) { |
808 for(size_t i=0;i<count;i++) { |
793 DavQLCmd cmd = cmds[i]; |
809 DavQLCmd cmd = cmds[i]; |
794 switch(cmd.type) { |
810 switch(cmd.type) { |
795 case DAVQL_CMD_INT: { |
811 case DAVQL_CMD_INT: { |
796 printf("int %lld\n", cmd.data.integer); |
812 //printf("int %lld\n", cmd.data.integer); |
797 obj.type = 0; |
813 obj.type = 0; |
798 obj.length = 0; |
814 obj.length = 0; |
799 obj.data.integer = cmd.data.integer; |
815 obj.data.integer = cmd.data.integer; |
800 DAVQL_PUSH(obj); |
816 DAVQL_PUSH(obj); |
801 break; |
817 break; |
802 } |
818 } |
803 case DAVQL_CMD_STRING: { |
819 case DAVQL_CMD_STRING: { |
804 printf("string \"%.*s\"\n", cmd.data.string.length, cmd.data.string.ptr); |
820 //printf("string \"%.*s\"\n", cmd.data.string.length, cmd.data.string.ptr); |
805 obj.type = 1; |
821 obj.type = 1; |
806 obj.length = cmd.data.string.length; |
822 obj.length = cmd.data.string.length; |
807 obj.data.string = cmd.data.string.ptr; |
823 obj.data.string = cmd.data.string.ptr; |
808 DAVQL_PUSH(obj); |
824 DAVQL_PUSH(obj); |
809 break; |
825 break; |
810 } |
826 } |
811 case DAVQL_CMD_TIMESTAMP: { |
827 case DAVQL_CMD_TIMESTAMP: { |
812 printf("timestamp %d\n", cmd.data.timestamp); |
828 //printf("timestamp %d\n", cmd.data.timestamp); |
813 obj.type = 0; |
829 obj.type = 0; |
814 obj.length = 0; |
830 obj.length = 0; |
815 obj.data.integer = cmd.data.timestamp; |
831 obj.data.integer = (int)cmd.data.timestamp; |
816 DAVQL_PUSH(obj); |
832 DAVQL_PUSH(obj); |
817 break; |
833 break; |
818 } |
834 } |
819 case DAVQL_CMD_RES_IDENTIFIER: { |
835 case DAVQL_CMD_RES_IDENTIFIER: { |
820 char *rid[8] = {"name", "path", "href", "contentlength", "contenttype", "creationdate", "lastmodified", "iscollection"}; |
836 char *rid[8] = {"name", "path", "href", "contentlength", "contenttype", "creationdate", "lastmodified", "iscollection"}; |
821 printf("resprop %s\n", rid[cmd.data.resprop]); |
837 //printf("resprop %s\n", rid[cmd.data.resprop]); |
822 switch(cmd.data.resprop) { |
838 switch(cmd.data.resprop) { |
823 case DAVQL_RES_NAME: { |
839 case DAVQL_RES_NAME: { |
824 obj.type = 1; |
840 obj.type = 1; |
825 obj.length = strlen(res->name); |
841 obj.length = strlen(res->name); |
826 obj.data.string = res->name; |
842 obj.data.string = res->name; |
997 i = count; // end loop |
1013 i = count; // end loop |
998 } |
1014 } |
999 break; |
1015 break; |
1000 } |
1016 } |
1001 case DAVQL_CMD_OP_LOGICAL_NOT: { |
1017 case DAVQL_CMD_OP_LOGICAL_NOT: { |
1002 printf("not\n"); |
1018 //printf("not\n"); |
1003 break; |
1019 break; |
1004 } |
1020 } |
1005 case DAVQL_CMD_OP_LOGICAL_AND: { |
1021 case DAVQL_CMD_OP_LOGICAL_AND: { |
1006 printf("land\n"); |
1022 //printf("land\n"); |
1007 DavQLStackObj obj2 = DAVQL_POP(); |
1023 DavQLStackObj obj2 = DAVQL_POP(); |
1008 DavQLStackObj obj1 = DAVQL_POP(); |
1024 DavQLStackObj obj1 = DAVQL_POP(); |
1009 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1025 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1010 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1026 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1011 DAVQL_PUSH_INT(v1 && v2); |
1027 DAVQL_PUSH_INT(v1 && v2); |
1012 break; |
1028 break; |
1013 } |
1029 } |
1014 case DAVQL_CMD_OP_LOGICAL_OR_L: { |
1030 case DAVQL_CMD_OP_LOGICAL_OR_L: { |
1015 printf("or_l %d\n", cmd.data.integer); |
1031 //printf("or_l %d\n", cmd.data.integer); |
1016 DavQLStackObj obj1 = DAVQL_POP(); |
1032 DavQLStackObj obj1 = DAVQL_POP(); |
1017 if((obj1.type == 0 && obj1.data.integer) || (obj1.type == 1 && obj1.data.string)) { |
1033 if((obj1.type == 0 && obj1.data.integer) || (obj1.type == 1 && obj1.data.string)) { |
1018 DAVQL_PUSH_INT(1); |
1034 DAVQL_PUSH_INT(1); |
1019 i += cmd.data.integer; // jump, skip right subtree of 'or' |
1035 i += cmd.data.integer; // jump, skip right subtree of 'or' |
1020 } |
1036 } |
1021 break; |
1037 break; |
1022 } |
1038 } |
1023 case DAVQL_CMD_OP_LOGICAL_OR: { |
1039 case DAVQL_CMD_OP_LOGICAL_OR: { |
1024 printf("or\n"); |
1040 //printf("or\n"); |
1025 DavQLStackObj obj2 = DAVQL_POP(); |
1041 DavQLStackObj obj2 = DAVQL_POP(); |
1026 DavQLStackObj obj1 = DAVQL_POP(); |
1042 DavQLStackObj obj1 = DAVQL_POP(); |
1027 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1043 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1028 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1044 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1029 DAVQL_PUSH_INT(v1 || v2); |
1045 DAVQL_PUSH_INT(v1 || v2); |
1030 break; |
1046 break; |
1031 } |
1047 } |
1032 case DAVQL_CMD_OP_LOGICAL_XOR: { |
1048 case DAVQL_CMD_OP_LOGICAL_XOR: { |
1033 printf("lxor\n"); |
1049 //printf("lxor\n"); |
1034 DavQLStackObj obj2 = DAVQL_POP(); |
1050 DavQLStackObj obj2 = DAVQL_POP(); |
1035 DavQLStackObj obj1 = DAVQL_POP(); |
1051 DavQLStackObj obj1 = DAVQL_POP(); |
1036 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1052 int v1 = obj1.type == 0 ? (int)obj1.data.integer : (obj1.data.string ? 1 : 0); |
1037 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1053 int v2 = obj2.type == 0 ? (int)obj2.data.integer : (obj2.data.string ? 1 : 0); |
1038 DAVQL_PUSH_INT(!v1 != !v2); |
1054 DAVQL_PUSH_INT(!v1 != !v2); |
1039 break; |
1055 break; |
1040 } |
1056 } |
1041 case DAVQL_CMD_OP_EQ: { |
1057 case DAVQL_CMD_OP_EQ: { |
1042 printf("eq\n"); |
1058 //printf("eq\n"); |
1043 DavQLStackObj obj2 = DAVQL_POP(); |
1059 DavQLStackObj obj2 = DAVQL_POP(); |
1044 DavQLStackObj obj1 = DAVQL_POP(); |
1060 DavQLStackObj obj1 = DAVQL_POP(); |
1045 if(obj1.type == 0 && obj2.type == 0) { |
1061 if(obj1.type == 0 && obj2.type == 0) { |
1046 DAVQL_PUSH_INT(obj1.data.integer == obj2.data.integer); |
1062 DAVQL_PUSH_INT(obj1.data.integer == obj2.data.integer); |
1047 } else { |
1063 } else { |
1048 // TODO: string compare |
1064 // TODO: string compare |
1049 } |
1065 } |
1050 break; |
1066 break; |
1051 } |
1067 } |
1052 case DAVQL_CMD_OP_NEQ: { |
1068 case DAVQL_CMD_OP_NEQ: { |
1053 printf("neq\n"); |
1069 //printf("neq\n"); |
1054 DavQLStackObj obj2 = DAVQL_POP(); |
1070 DavQLStackObj obj2 = DAVQL_POP(); |
1055 DavQLStackObj obj1 = DAVQL_POP(); |
1071 DavQLStackObj obj1 = DAVQL_POP(); |
1056 if(obj1.type == 0 && obj2.type == 0) { |
1072 if(obj1.type == 0 && obj2.type == 0) { |
1057 DAVQL_PUSH_INT(obj1.data.integer != obj2.data.integer); |
1073 DAVQL_PUSH_INT(obj1.data.integer != obj2.data.integer); |
1058 } else { |
1074 } else { |
1059 // TODO: string compare |
1075 // TODO: string compare |
1060 } |
1076 } |
1061 break; |
1077 break; |
1062 } |
1078 } |
1063 case DAVQL_CMD_OP_LT: { |
1079 case DAVQL_CMD_OP_LT: { |
1064 printf("lt\n"); |
1080 //printf("lt\n"); |
1065 DavQLStackObj obj2 = DAVQL_POP(); |
1081 DavQLStackObj obj2 = DAVQL_POP(); |
1066 DavQLStackObj obj1 = DAVQL_POP(); |
1082 DavQLStackObj obj1 = DAVQL_POP(); |
1067 if(obj1.type == 0 && obj2.type == 0) { |
1083 if(obj1.type == 0 && obj2.type == 0) { |
1068 DAVQL_PUSH_INT(obj1.data.integer < obj2.data.integer); |
1084 DAVQL_PUSH_INT(obj1.data.integer < obj2.data.integer); |
1069 } else { |
1085 } else { |
1070 // TODO: string compare |
1086 // TODO: string compare |
1071 } |
1087 } |
1072 break; |
1088 break; |
1073 } |
1089 } |
1074 case DAVQL_CMD_OP_GT: { |
1090 case DAVQL_CMD_OP_GT: { |
1075 printf("gt\n"); |
1091 //printf("gt\n"); |
1076 DavQLStackObj obj2 = DAVQL_POP(); |
1092 DavQLStackObj obj2 = DAVQL_POP(); |
1077 DavQLStackObj obj1 = DAVQL_POP(); |
1093 DavQLStackObj obj1 = DAVQL_POP(); |
1078 if(obj1.type == 0 && obj2.type == 0) { |
1094 if(obj1.type == 0 && obj2.type == 0) { |
1079 DAVQL_PUSH_INT(obj1.data.integer > obj2.data.integer); |
1095 DAVQL_PUSH_INT(obj1.data.integer > obj2.data.integer); |
1080 } else { |
1096 } else { |
1081 // TODO: string compare |
1097 // TODO: string compare |
1082 } |
1098 } |
1083 break; |
1099 break; |
1084 } |
1100 } |
1085 case DAVQL_CMD_OP_LE: { |
1101 case DAVQL_CMD_OP_LE: { |
1086 printf("le\n"); |
1102 //printf("le\n"); |
1087 DavQLStackObj obj2 = DAVQL_POP(); |
1103 DavQLStackObj obj2 = DAVQL_POP(); |
1088 DavQLStackObj obj1 = DAVQL_POP(); |
1104 DavQLStackObj obj1 = DAVQL_POP(); |
1089 if(obj1.type == 0 && obj2.type == 0) { |
1105 if(obj1.type == 0 && obj2.type == 0) { |
1090 DAVQL_PUSH_INT(obj1.data.integer <= obj2.data.integer); |
1106 DAVQL_PUSH_INT(obj1.data.integer <= obj2.data.integer); |
1091 } else { |
1107 } else { |
1092 // TODO: string compare |
1108 // TODO: string compare |
1093 } |
1109 } |
1094 break; |
1110 break; |
1095 } |
1111 } |
1096 case DAVQL_CMD_OP_GE: { |
1112 case DAVQL_CMD_OP_GE: { |
1097 printf("ge\n"); |
1113 //printf("ge\n"); |
1098 DavQLStackObj obj2 = DAVQL_POP(); |
1114 DavQLStackObj obj2 = DAVQL_POP(); |
1099 DavQLStackObj obj1 = DAVQL_POP(); |
1115 DavQLStackObj obj1 = DAVQL_POP(); |
1100 if(obj1.type == 0 && obj2.type == 0) { |
1116 if(obj1.type == 0 && obj2.type == 0) { |
1101 DAVQL_PUSH_INT(obj1.data.integer >= obj2.data.integer); |
1117 DAVQL_PUSH_INT(obj1.data.integer >= obj2.data.integer); |
1102 } else { |
1118 } else { |
1103 // TODO: string compare |
1119 // TODO: string compare |
1104 } |
1120 } |
1105 break; |
1121 break; |
1106 } |
1122 } |
1107 case DAVQL_CMD_OP_LIKE: { |
1123 case DAVQL_CMD_OP_LIKE: { |
1108 printf("like\n"); |
1124 //printf("like\n"); |
1109 break; |
1125 break; |
1110 } |
1126 } |
1111 case DAVQL_CMD_OP_UNLIKE: { |
1127 case DAVQL_CMD_OP_UNLIKE: { |
1112 printf("unlike\n"); |
1128 //printf("unlike\n"); |
1113 break; |
1129 break; |
1114 } |
1130 } |
1115 case DAVQL_CMD_CALL: { |
1131 case DAVQL_CMD_CALL: { |
1116 printf("call %x\n", cmd.data.func); |
1132 //printf("call %x\n", cmd.data.func); |
1117 break; |
1133 break; |
1118 } |
1134 } |
1119 } |
1135 } |
1120 } |
1136 } |
1121 |
1137 |