| 1253 | } |
| 1254 | |
| 1255 | static Node * |
| 1256 | transformAExprBetween(ParseState *pstate, A_Expr *a) |
| 1257 | { |
| 1258 | Node *aexpr; |
| 1259 | Node *bexpr; |
| 1260 | Node *cexpr; |
| 1261 | Node *result; |
| 1262 | Node *sub1; |
| 1263 | Node *sub2; |
| 1264 | List *args; |
| 1265 | |
| 1266 | /* Deconstruct A_Expr into three subexprs */ |
| 1267 | aexpr = a->lexpr; |
| 1268 | args = castNode(List, a->rexpr); |
| 1269 | Assert(list_length(args) == 2); |
| 1270 | bexpr = (Node *) linitial(args); |
| 1271 | cexpr = (Node *) lsecond(args); |
| 1272 | |
| 1273 | /* |
| 1274 | * Build the equivalent comparison expression. Make copies of |
| 1275 | * multiply-referenced subexpressions for safety. (XXX this is really |
| 1276 | * wrong since it results in multiple runtime evaluations of what may be |
| 1277 | * volatile expressions ...) |
| 1278 | * |
| 1279 | * Ideally we would not use hard-wired operators here but instead use |
| 1280 | * opclasses. However, mixed data types and other issues make this |
| 1281 | * difficult: |
| 1282 | * http://archives.postgresql.org/pgsql-hackers/2008-08/msg01142.php |
| 1283 | */ |
| 1284 | switch (a->kind) |
| 1285 | { |
| 1286 | case AEXPR_BETWEEN: |
| 1287 | args = list_make2(makeSimpleA_Expr(AEXPR_OP, ">=", |
| 1288 | aexpr, bexpr, |
| 1289 | a->location), |
| 1290 | makeSimpleA_Expr(AEXPR_OP, "<=", |
| 1291 | copyObject(aexpr), cexpr, |
| 1292 | a->location)); |
| 1293 | result = (Node *) makeBoolExpr(AND_EXPR, args, a->location); |
| 1294 | break; |
| 1295 | case AEXPR_NOT_BETWEEN: |
| 1296 | args = list_make2(makeSimpleA_Expr(AEXPR_OP, "<", |
| 1297 | aexpr, bexpr, |
| 1298 | a->location), |
| 1299 | makeSimpleA_Expr(AEXPR_OP, ">", |
| 1300 | copyObject(aexpr), cexpr, |
| 1301 | a->location)); |
| 1302 | result = (Node *) makeBoolExpr(OR_EXPR, args, a->location); |
| 1303 | break; |
| 1304 | case AEXPR_BETWEEN_SYM: |
| 1305 | args = list_make2(makeSimpleA_Expr(AEXPR_OP, ">=", |
| 1306 | aexpr, bexpr, |
| 1307 | a->location), |
| 1308 | makeSimpleA_Expr(AEXPR_OP, "<=", |
| 1309 | copyObject(aexpr), cexpr, |
| 1310 | a->location)); |
| 1311 | sub1 = (Node *) makeBoolExpr(AND_EXPR, args, a->location); |
| 1312 | args = list_make2(makeSimpleA_Expr(AEXPR_OP, ">=", |
no test coverage detected