[ FILTER_OP_GE_DOUBLE ] = &&LABEL_FILTER_OP_GE_DOUBLE,
[ FILTER_OP_LE_DOUBLE ] = &&LABEL_FILTER_OP_LE_DOUBLE,
+ /* Mixed S64-double binary comparators */
+ [ FILTER_OP_EQ_DOUBLE_S64 ] = &&LABEL_FILTER_OP_EQ_DOUBLE_S64,
+ [ FILTER_OP_NE_DOUBLE_S64 ] = &&LABEL_FILTER_OP_NE_DOUBLE_S64,
+ [ FILTER_OP_GT_DOUBLE_S64 ] = &&LABEL_FILTER_OP_GT_DOUBLE_S64,
+ [ FILTER_OP_LT_DOUBLE_S64 ] = &&LABEL_FILTER_OP_LT_DOUBLE_S64,
+ [ FILTER_OP_GE_DOUBLE_S64 ] = &&LABEL_FILTER_OP_GE_DOUBLE_S64,
+ [ FILTER_OP_LE_DOUBLE_S64 ] = &&LABEL_FILTER_OP_LE_DOUBLE_S64,
+
+ [ FILTER_OP_EQ_S64_DOUBLE ] = &&LABEL_FILTER_OP_EQ_S64_DOUBLE,
+ [ FILTER_OP_NE_S64_DOUBLE ] = &&LABEL_FILTER_OP_NE_S64_DOUBLE,
+ [ FILTER_OP_GT_S64_DOUBLE ] = &&LABEL_FILTER_OP_GT_S64_DOUBLE,
+ [ FILTER_OP_LT_S64_DOUBLE ] = &&LABEL_FILTER_OP_LT_S64_DOUBLE,
+ [ FILTER_OP_GE_S64_DOUBLE ] = &&LABEL_FILTER_OP_GE_S64_DOUBLE,
+ [ FILTER_OP_LE_S64_DOUBLE ] = &&LABEL_FILTER_OP_LE_S64_DOUBLE,
+
/* unary */
[ FILTER_OP_UNARY_PLUS ] = &&LABEL_FILTER_OP_UNARY_PLUS,
[ FILTER_OP_UNARY_MINUS ] = &&LABEL_FILTER_OP_UNARY_MINUS,
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v == estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d == estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v != estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d != estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v > estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d > estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v < estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d < estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v >= estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d >= estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
{
int res;
- if (unlikely(estack_ax(stack)->type == REG_S64))
- estack_ax(stack)->u.d = (double) estack_ax(stack)->u.v;
- else if (unlikely(estack_bx(stack)->type == REG_S64))
- estack_bx(stack)->u.d = (double) estack_bx(stack)->u.v;
- res = (estack_bx(stack)->u.v <= estack_ax(stack)->u.v);
+ res = (estack_bx(stack)->u.d <= estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+
+ /* Mixed S64-double binary comparators */
+ OP(FILTER_OP_EQ_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d == estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_NE_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d != estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_GT_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d > estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_LT_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d < estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_GE_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d >= estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_LE_DOUBLE_S64):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.d <= estack_ax(stack)->u.v);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+
+ OP(FILTER_OP_EQ_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v == estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_NE_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v != estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_GT_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v > estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_LT_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v < estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_GE_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v >= estack_ax(stack)->u.d);
+ estack_pop(stack);
+ estack_ax(stack)->u.v = res;
+ estack_ax(stack)->type = REG_S64;
+ next_pc += sizeof(struct binary_op);
+ PO;
+ }
+ OP(FILTER_OP_LE_S64_DOUBLE):
+ {
+ int res;
+
+ res = (estack_bx(stack)->u.v <= estack_ax(stack)->u.d);
estack_pop(stack);
estack_ax(stack)->u.v = res;
estack_ax(stack)->type = REG_S64;
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_EQ_S64;
else
- insn->op = FILTER_OP_EQ_DOUBLE;
+ insn->op = FILTER_OP_EQ_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_EQ_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_EQ_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_EQ_DOUBLE;
break;
}
/* Pop 2, push 1 */
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_NE_S64;
else
- insn->op = FILTER_OP_NE_DOUBLE;
+ insn->op = FILTER_OP_NE_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_NE_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_NE_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_NE_DOUBLE;
break;
}
/* Pop 2, push 1 */
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_GT_S64;
else
- insn->op = FILTER_OP_GT_DOUBLE;
+ insn->op = FILTER_OP_GT_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_GT_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_GT_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_GT_DOUBLE;
break;
}
/* Pop 2, push 1 */
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_LT_S64;
else
- insn->op = FILTER_OP_LT_DOUBLE;
+ insn->op = FILTER_OP_LT_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_LT_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_LT_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_LT_DOUBLE;
break;
}
/* Pop 2, push 1 */
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_GE_S64;
else
- insn->op = FILTER_OP_GE_DOUBLE;
+ insn->op = FILTER_OP_GE_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_GE_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_GE_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_GE_DOUBLE;
break;
}
/* Pop 2, push 1 */
if (vstack_bx(stack)->type == REG_S64)
insn->op = FILTER_OP_LE_S64;
else
- insn->op = FILTER_OP_LE_DOUBLE;
+ insn->op = FILTER_OP_LE_DOUBLE_S64;
break;
case REG_DOUBLE:
- insn->op = FILTER_OP_LE_DOUBLE;
+ if (vstack_bx(stack)->type == REG_S64)
+ insn->op = FILTER_OP_LE_S64_DOUBLE;
+ else
+ insn->op = FILTER_OP_LE_DOUBLE;
break;
}
vstack_ax(stack)->type = REG_S64;
case FILTER_OP_LT_DOUBLE:
case FILTER_OP_GE_DOUBLE:
case FILTER_OP_LE_DOUBLE:
+ case FILTER_OP_EQ_DOUBLE_S64:
+ case FILTER_OP_NE_DOUBLE_S64:
+ case FILTER_OP_GT_DOUBLE_S64:
+ case FILTER_OP_LT_DOUBLE_S64:
+ case FILTER_OP_GE_DOUBLE_S64:
+ case FILTER_OP_LE_DOUBLE_S64:
+ case FILTER_OP_EQ_S64_DOUBLE:
+ case FILTER_OP_NE_S64_DOUBLE:
+ case FILTER_OP_GT_S64_DOUBLE:
+ case FILTER_OP_LT_S64_DOUBLE:
+ case FILTER_OP_GE_S64_DOUBLE:
+ case FILTER_OP_LE_S64_DOUBLE:
{
/* Pop 2, push 1 */
if (vstack_pop(stack)) {
case FILTER_OP_LT_DOUBLE:
case FILTER_OP_GE_DOUBLE:
case FILTER_OP_LE_DOUBLE:
+ case FILTER_OP_EQ_DOUBLE_S64:
+ case FILTER_OP_NE_DOUBLE_S64:
+ case FILTER_OP_GT_DOUBLE_S64:
+ case FILTER_OP_LT_DOUBLE_S64:
+ case FILTER_OP_GE_DOUBLE_S64:
+ case FILTER_OP_LE_DOUBLE_S64:
+ case FILTER_OP_EQ_S64_DOUBLE:
+ case FILTER_OP_NE_S64_DOUBLE:
+ case FILTER_OP_GT_S64_DOUBLE:
+ case FILTER_OP_LT_S64_DOUBLE:
+ case FILTER_OP_GE_S64_DOUBLE:
+ case FILTER_OP_LE_S64_DOUBLE:
{
if (unlikely(pc + sizeof(struct binary_op)
> start_pc + bytecode->len)) {
ret = -EINVAL;
goto end;
}
- if ((vstack_ax(stack)->type != REG_DOUBLE && vstack_ax(stack)->type != REG_S64)
- || (vstack_bx(stack)-> type != REG_DOUBLE && vstack_bx(stack)->type != REG_S64)) {
- ERR("Unexpected register type for double comparator\n");
+ if (vstack_ax(stack)->type != REG_DOUBLE && vstack_bx(stack)->type != REG_DOUBLE) {
+ ERR("Double operator should have two double registers\n");
ret = -EINVAL;
goto end;
}
- if (vstack_ax(stack)->type != REG_DOUBLE && vstack_bx(stack)->type != REG_DOUBLE) {
- ERR("Double operator should have at least one double register\n");
+ break;
+ }
+
+ case FILTER_OP_EQ_DOUBLE_S64:
+ case FILTER_OP_NE_DOUBLE_S64:
+ case FILTER_OP_GT_DOUBLE_S64:
+ case FILTER_OP_LT_DOUBLE_S64:
+ case FILTER_OP_GE_DOUBLE_S64:
+ case FILTER_OP_LE_DOUBLE_S64:
+ {
+ if (!vstack_ax(stack) || !vstack_bx(stack)) {
+ ERR("Empty stack\n");
+ ret = -EINVAL;
+ goto end;
+ }
+ if (vstack_ax(stack)->type != REG_S64 && vstack_bx(stack)->type != REG_DOUBLE) {
+ ERR("Double-S64 operator has unexpected register types\n");
+ ret = -EINVAL;
+ goto end;
+ }
+ break;
+ }
+
+ case FILTER_OP_EQ_S64_DOUBLE:
+ case FILTER_OP_NE_S64_DOUBLE:
+ case FILTER_OP_GT_S64_DOUBLE:
+ case FILTER_OP_LT_S64_DOUBLE:
+ case FILTER_OP_GE_S64_DOUBLE:
+ case FILTER_OP_LE_S64_DOUBLE:
+ {
+ if (!vstack_ax(stack) || !vstack_bx(stack)) {
+ ERR("Empty stack\n");
+ ret = -EINVAL;
+ goto end;
+ }
+ if (vstack_ax(stack)->type != REG_DOUBLE && vstack_bx(stack)->type != REG_S64) {
+ ERR("S64-Double operator has unexpected register types\n");
ret = -EINVAL;
goto end;
}
case FILTER_OP_LT_DOUBLE:
case FILTER_OP_GE_DOUBLE:
case FILTER_OP_LE_DOUBLE:
+ case FILTER_OP_EQ_DOUBLE_S64:
+ case FILTER_OP_NE_DOUBLE_S64:
+ case FILTER_OP_GT_DOUBLE_S64:
+ case FILTER_OP_LT_DOUBLE_S64:
+ case FILTER_OP_GE_DOUBLE_S64:
+ case FILTER_OP_LE_DOUBLE_S64:
+ case FILTER_OP_EQ_S64_DOUBLE:
+ case FILTER_OP_NE_S64_DOUBLE:
+ case FILTER_OP_GT_S64_DOUBLE:
+ case FILTER_OP_LT_S64_DOUBLE:
+ case FILTER_OP_GE_S64_DOUBLE:
+ case FILTER_OP_LE_S64_DOUBLE:
{
/* Pop 2, push 1 */
if (vstack_pop(stack)) {