mirror of
https://github.com/johnkerl/miller.git
synced 2026-07-26 01:15:27 +00:00
bitwise operators
This commit is contained in:
parent
11ccb84ebf
commit
2ad4f85286
7 changed files with 138 additions and 25 deletions
|
|
@ -20,6 +20,19 @@
|
|||
return FILTER_DSL_AND;
|
||||
}
|
||||
|
||||
"|" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return FILTER_DSL_BIT_OR;
|
||||
}
|
||||
"^" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return FILTER_DSL_BIT_XOR;
|
||||
}
|
||||
"&" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return FILTER_DSL_BIT_AND;
|
||||
}
|
||||
|
||||
"=~" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return FILTER_DSL_MATCHES;
|
||||
|
|
|
|||
|
|
@ -43,6 +43,7 @@ filter_dsl_body(A) ::= filter_dsl_bool_expr(B). {
|
|||
past->proot = A;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
filter_dsl_bool_expr(A) ::= filter_dsl_or_term(B). {
|
||||
A = B;
|
||||
}
|
||||
|
|
@ -50,7 +51,6 @@ filter_dsl_bool_expr(A) ::= filter_dsl_bool_expr(B) FILTER_DSL_OR(O) filter_dsl_
|
|||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
filter_dsl_or_term(A) ::= filter_dsl_and_term(B). {
|
||||
A = B;
|
||||
}
|
||||
|
|
@ -58,20 +58,43 @@ filter_dsl_or_term(A) ::= filter_dsl_or_term(B) FILTER_DSL_AND(O) filter_dsl_and
|
|||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
filter_dsl_and_term(A) ::= filter_dsl_eqne_term(B). {
|
||||
|
||||
filter_dsl_and_term(A) ::= filter_dsl_bit_or_term(B). {
|
||||
A = B;
|
||||
}
|
||||
filter_dsl_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_MATCHES(O) filter_dsl_eqne_term(C). {
|
||||
filter_dsl_and_term(A) ::= filter_dsl_and_term(B) FILTER_DSL_BIT_OR(O) filter_dsl_bit_or_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_DOES_NOT_MATCH(O) filter_dsl_eqne_term(C). {
|
||||
|
||||
|
||||
filter_dsl_bit_or_term(A) ::= filter_dsl_bit_xor_term(B). {
|
||||
A = B;
|
||||
}
|
||||
filter_dsl_bit_or_term(A) ::= filter_dsl_bit_or_term(B) FILTER_DSL_BIT_XOR(O) filter_dsl_bit_xor_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_EQ(O) filter_dsl_eqne_term(C). {
|
||||
|
||||
filter_dsl_bit_xor_term(A) ::= filter_dsl_bit_and_term(B). {
|
||||
A = B;
|
||||
}
|
||||
filter_dsl_bit_xor_term(A) ::= filter_dsl_bit_xor_term(B) FILTER_DSL_BIT_AND(O) filter_dsl_bit_and_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_NE(O) filter_dsl_eqne_term(C). {
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
filter_dsl_bit_and_term(A) ::= filter_dsl_eqne_term(B). {
|
||||
A = B;
|
||||
}
|
||||
filter_dsl_bit_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_MATCHES(O) filter_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_bit_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_DOES_NOT_MATCH(O) filter_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_bit_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_EQ(O) filter_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
filter_dsl_bit_and_term(A) ::= filter_dsl_eqne_term(B) FILTER_DSL_NE(O) filter_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -124,14 +124,29 @@
|
|||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_MOD;
|
||||
}
|
||||
"&&" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_MOD;
|
||||
}
|
||||
|
||||
"||" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_MOD;
|
||||
}
|
||||
"&&" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_MOD;
|
||||
}
|
||||
|
||||
"|" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_BIT_OR;
|
||||
}
|
||||
"^" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_BIT_XOR;
|
||||
}
|
||||
"&" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_BIT_AND;
|
||||
}
|
||||
|
||||
"==" {
|
||||
*yyextra = mlr_dsl_ast_node_alloc(yytext, MLR_DSL_AST_NODE_TYPE_OPERATOR);
|
||||
return PUT_DSL_MOD;
|
||||
|
|
|
|||
|
|
@ -57,32 +57,62 @@ put_dsl_assignment(A) ::= PUT_DSL_FIELD_NAME(B) PUT_DSL_ASSIGN(O) put_dsl_bool_
|
|||
sllv_add(pasts, A);
|
||||
}
|
||||
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
put_dsl_bool_expr(A) ::= put_dsl_bool_expr(B) FILTER_DSL_OR(O) put_dsl_or_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_bool_expr(A) ::= put_dsl_or_term(B). {
|
||||
A = B;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
put_dsl_or_term(A) ::= put_dsl_or_term(B) FILTER_DSL_AND(O) put_dsl_and_term(C). {
|
||||
put_dsl_bool_expr(A) ::= put_dsl_bool_expr(B) PUT_DSL_OR(O) put_dsl_or_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
put_dsl_or_term(A) ::= put_dsl_and_term(B). {
|
||||
A = B;
|
||||
}
|
||||
put_dsl_or_term(A) ::= put_dsl_or_term(B) PUT_DSL_AND(O) put_dsl_and_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
put_dsl_and_term(A) ::= put_dsl_eqne_term(B) FILTER_DSL_EQ(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_and_term(A) ::= put_dsl_eqne_term(B) FILTER_DSL_NE(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_and_term(A) ::= put_dsl_eqne_term(B). {
|
||||
|
||||
put_dsl_and_term(A) ::= put_dsl_bit_or_term(B). {
|
||||
A = B;
|
||||
}
|
||||
put_dsl_and_term(A) ::= put_dsl_and_term(B) PUT_DSL_BIT_OR(O) put_dsl_bit_or_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
|
||||
put_dsl_bit_or_term(A) ::= put_dsl_bit_xor_term(B). {
|
||||
A = B;
|
||||
}
|
||||
put_dsl_bit_or_term(A) ::= put_dsl_bit_or_term(B) PUT_DSL_BIT_XOR(O) put_dsl_bit_xor_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
put_dsl_bit_xor_term(A) ::= put_dsl_bit_and_term(B). {
|
||||
A = B;
|
||||
}
|
||||
put_dsl_bit_xor_term(A) ::= put_dsl_bit_xor_term(B) PUT_DSL_BIT_AND(O) put_dsl_bit_and_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
put_dsl_bit_and_term(A) ::= put_dsl_eqne_term(B). {
|
||||
A = B;
|
||||
}
|
||||
put_dsl_bit_and_term(A) ::= put_dsl_eqne_term(B) PUT_DSL_MATCHES(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_bit_and_term(A) ::= put_dsl_eqne_term(B) PUT_DSL_DOES_NOT_MATCH(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_bit_and_term(A) ::= put_dsl_eqne_term(B) PUT_DSL_EQ(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
put_dsl_bit_and_term(A) ::= put_dsl_eqne_term(B) PUT_DSL_NE(O) put_dsl_eqne_term(C). {
|
||||
A = mlr_dsl_ast_node_alloc_binary(O->text, MLR_DSL_AST_NODE_TYPE_OPERATOR, B, C);
|
||||
}
|
||||
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
put_dsl_eqne_term(A) ::= put_dsl_expr(B). {
|
||||
|
|
|
|||
|
|
@ -1078,6 +1078,9 @@ static function_lookup_t FUNCTION_LOOKUP_TABLE[] = {
|
|||
{ FUNC_CLASS_MATH, "//", 2 , "Interger division."},
|
||||
{ FUNC_CLASS_MATH, "%", 2 , "Remainder; never negative-valued."},
|
||||
{ FUNC_CLASS_MATH, "**", 2 , "Exponentiation; same as pow."},
|
||||
{ FUNC_CLASS_MATH, "|", 2 , "Bitwise OR."},
|
||||
{ FUNC_CLASS_MATH, "^", 2 , "Bitwise XOR."},
|
||||
{ FUNC_CLASS_MATH, "&", 2 , "Bitwise AND."},
|
||||
|
||||
{ FUNC_CLASS_BOOLEAN, "=~", 2 , "String (left-hand side) matches regex (right-hand side), e.g. '$name =~ \"^a.*b$\"'."},
|
||||
{ FUNC_CLASS_BOOLEAN, "!=~", 2 , "String (left-hand side) does not match regex (right-hand side), e.g. '$name !=~ \"^a.*b$\"'."},
|
||||
|
|
@ -1322,6 +1325,9 @@ lrec_evaluator_t* lrec_evaluator_alloc_from_binary_func_name(char* fnnm,
|
|||
} else if (streq(fnnm, "roundm")) { return lrec_evaluator_alloc_from_n_nn_func(n_nn_roundm_func, parg1, parg2);
|
||||
} else if (streq(fnnm, "fmtnum")) { return lrec_evaluator_alloc_from_s_xs_func(s_xs_fmtnum_func, parg1, parg2);
|
||||
} else if (streq(fnnm, "urandint")) { return lrec_evaluator_alloc_from_i_ii_func(i_ii_urandint_func, parg1, parg2);
|
||||
} else if (streq(fnnm, "|")) { return lrec_evaluator_alloc_from_i_ii_func(i_ii_bitwise_or_func, parg1, parg2);
|
||||
} else if (streq(fnnm, "^")) { return lrec_evaluator_alloc_from_i_ii_func(i_ii_bitwise_xor_func, parg1, parg2);
|
||||
} else if (streq(fnnm, "&")) { return lrec_evaluator_alloc_from_i_ii_func(i_ii_bitwise_and_func, parg1, parg2);
|
||||
} else { return NULL; }
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -186,6 +186,16 @@ static inline mv_t i_ii_urandint_func(mv_t* pval1, mv_t* pval2) {
|
|||
return (mv_t) {.type = MT_INT, .u.intv = u};
|
||||
}
|
||||
|
||||
static inline mv_t i_ii_bitwise_or_func(mv_t* pval1, mv_t* pval2) {
|
||||
return (mv_t) {.type = MT_INT, .u.intv = pval1->u.intv | pval2->u.intv};
|
||||
}
|
||||
static inline mv_t i_ii_bitwise_xor_func(mv_t* pval1, mv_t* pval2) {
|
||||
return (mv_t) {.type = MT_INT, .u.intv = pval1->u.intv ^ pval2->u.intv};
|
||||
}
|
||||
static inline mv_t i_ii_bitwise_and_func(mv_t* pval1, mv_t* pval2) {
|
||||
return (mv_t) {.type = MT_INT, .u.intv = pval1->u.intv & pval2->u.intv};
|
||||
}
|
||||
|
||||
mv_t i_iii_modadd_func(mv_t* pval1, mv_t* pval2, mv_t* pval3);
|
||||
mv_t i_iii_modsub_func(mv_t* pval1, mv_t* pval2, mv_t* pval3);
|
||||
mv_t i_iii_modmul_func(mv_t* pval1, mv_t* pval2, mv_t* pval3);
|
||||
|
|
|
|||
16
c/todo.txt
16
c/todo.txt
|
|
@ -28,6 +28,22 @@ TOP OF LIST
|
|||
|
||||
o now is a good time to look at bitops. first get the precedence right.
|
||||
|
||||
* mlr doc precedence:
|
||||
Operators Associativity
|
||||
--------- -------------
|
||||
|| left to right
|
||||
&& left to right
|
||||
| left to right
|
||||
^ left to right
|
||||
& left to right
|
||||
== != left to right
|
||||
< <= > >= left to right
|
||||
<< >> left to right
|
||||
binary+ binary- left to right
|
||||
binary* / % left to right
|
||||
! ~ ++ -- unary+ unary- & right to left
|
||||
() left to right
|
||||
|
||||
* packaging:
|
||||
- brew version bump?!?
|
||||
- cut a release w/ manpage
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue