return tmpl_value(node->vpt);
}
+static ssize_t xlat_expr_print_unary(fr_sbuff_t *out, xlat_exp_t const *node, UNUSED void *inst, fr_sbuff_escape_rules_t const *e_rules)
+{
+ size_t at_in = fr_sbuff_used_total(out);
+
+ FR_SBUFF_IN_STRCPY_RETURN(out, fr_tokens[node->call.func->token]);
+ xlat_print_node(out, node->child, e_rules);
+
+ return fr_sbuff_used_total(out) - at_in;
+}
+
+static ssize_t xlat_expr_print_binary(fr_sbuff_t *out, xlat_exp_t const *node, UNUSED void *inst, fr_sbuff_escape_rules_t const *e_rules)
+{
+ size_t at_in = fr_sbuff_used_total(out);
+
+ FR_SBUFF_IN_CHAR_RETURN(out, '(');
+ xlat_print_node(out, node->child, e_rules); /* prints a space after the first argument */
+
+ /*
+ * @todo - when things like "+" support more than 2 arguments, print them all out
+ * here.
+ */
+ FR_SBUFF_IN_STRCPY_RETURN(out, fr_tokens[node->call.func->token]);
+ FR_SBUFF_IN_CHAR_RETURN(out, ' ');
+ xlat_print_node(out, node->child->next, e_rules);
+
+ FR_SBUFF_IN_CHAR_RETURN(out, ')');
+
+ return fr_sbuff_used_total(out) - at_in;
+}
+
/** Basic purify, but only for expressions and comparisons.
*
*/
if (!(xlat = xlat_register(NULL, "op_" STRINGIFY(_name), xlat_func_op_ ## _name, XLAT_FLAG_PURE))) return -1; \
xlat_func_args(xlat, binary_op_xlat_args); \
xlat_internal(xlat); \
+ xlat_print_set(xlat, xlat_expr_print_binary); \
xlat->token = _op; \
- xlat->expr_type = XLAT_EXPR_TYPE_BINARY; \
} while (0)
#undef XLAT_REGISTER_BINARY_CMP
if (!(xlat = xlat_register(NULL, "cmp_" STRINGIFY(_name), xlat_func_cmp_ ## _name, XLAT_FLAG_PURE))) return -1; \
xlat_func_args(xlat, binary_op_xlat_args); \
xlat_internal(xlat); \
+ xlat_print_set(xlat, xlat_expr_print_binary); \
xlat->token = _op; \
- xlat->expr_type = XLAT_EXPR_TYPE_BINARY; \
} while (0)
int xlat_register_expressions(void)
if (!(xlat = xlat_register(NULL, "logical_and", xlat_func_logical_and, XLAT_FLAG_PURE))) return -1;
xlat_func_args(xlat, short_circuit_xlat_args);
xlat_internal(xlat);
+ xlat_print_set(xlat, xlat_expr_print_binary); /* @todo - fix this when we fix the instantiation */
xlat->token = T_LAND;
- xlat->expr_type = XLAT_EXPR_TYPE_BINARY;
if (!(xlat = xlat_register(NULL, "logical_or", xlat_func_logical_or, XLAT_FLAG_PURE))) return -1;
xlat_func_args(xlat, short_circuit_xlat_args);
+ xlat_print_set(xlat, xlat_expr_print_binary); /* @todo - fix this when we fix the instantiation */
xlat_internal(xlat);
xlat->token = T_LOR;
- xlat->expr_type = XLAT_EXPR_TYPE_BINARY;
/*
* -EXPR
if (!(xlat = xlat_register(NULL, "unary_minus", xlat_func_unary_minus, XLAT_FLAG_PURE))) return -1;
xlat_func_args(xlat, unary_minus_xlat_args);
xlat_internal(xlat);
+ xlat_print_set(xlat, xlat_expr_print_unary);
xlat->token = T_SUB;
- xlat->expr_type = XLAT_EXPR_TYPE_UNARY;
if (!(xlat = xlat_register(NULL, "unary_not", xlat_func_unary_not, XLAT_FLAG_PURE))) return -1;
xlat_func_args(xlat, unary_not_xlat_args);
xlat_internal(xlat);
+ xlat_print_set(xlat, xlat_expr_print_unary);
xlat->token = T_NOT;
- xlat->expr_type = XLAT_EXPR_TYPE_UNARY;
return 0;
}
typedef ssize_t (*xlat_print_t)(fr_sbuff_t *in, xlat_exp_t const *self, void *inst, fr_sbuff_escape_rules_t const *e_rules);
-typedef enum {
- XLAT_EXPR_TYPE_NONE,
- XLAT_EXPR_TYPE_UNARY,
- XLAT_EXPR_TYPE_BINARY,
-} xlat_expr_type_t;
-
typedef struct xlat_s {
fr_rb_node_t node; //!< Entry in the xlat function tree.
char const *name; //!< Name of xlat function.
xlat_func_t func; //!< async xlat function (async unsafe).
bool internal; //!< If true, cannot be redefined.
- xlat_expr_type_t expr_type; //!< for expressions
fr_token_t token; //!< for expressions
module_inst_ctx_t const *mctx; //!< Original module instantiation ctx if this
int xlat_tokenize_function_args(TALLOC_CTX *ctx, xlat_exp_t **head, xlat_flags_t *flags, fr_sbuff_t *in,
tmpl_attr_rules_t const *rules);
+ssize_t xlat_print_node(fr_sbuff_t *out, xlat_exp_t const *head, fr_sbuff_escape_rules_t const *e_rules);
#ifdef __cplusplus
}
_xlat_debug(node, 0);
}
-static ssize_t xlat_print_node(fr_sbuff_t *out, xlat_exp_t const *head, fr_sbuff_escape_rules_t const *e_rules)
+ssize_t xlat_print_node(fr_sbuff_t *out, xlat_exp_t const *head, fr_sbuff_escape_rules_t const *e_rules)
{
ssize_t slen;
size_t at_in = fr_sbuff_used_total(out);
slen = node->call.func->print(out, node, node->call.inst->data, e_rules);
goto done;
}
-
- if (!node->call.func->internal || (node->call.func->expr_type == XLAT_EXPR_TYPE_NONE)) break;
-
- /*
- * Expressions and comparisons.
- */
- if (node->call.func->expr_type == XLAT_EXPR_TYPE_UNARY) {
- FR_SBUFF_IN_STRCPY_RETURN(out, fr_tokens[node->call.func->token]);
- xlat_print_node(out, node->child, e_rules);
-
- } else {
- FR_SBUFF_IN_STRCPY_LITERAL_RETURN(out, "(");
- xlat_print_node(out, node->child, e_rules); /* prints a space after the first argument */
-
- /*
- * @todo - when things like "+" support more than 2 arguments, print them all out
- * here.
- */
- FR_SBUFF_IN_STRCPY_RETURN(out, fr_tokens[node->call.func->token]);
- FR_SBUFF_IN_CHAR_RETURN(out, ' ');
- xlat_print_node(out, node->child->next, e_rules);
-
- FR_SBUFF_IN_STRCPY_LITERAL_RETURN(out, ")");
- }
- goto done;
+ break;
default:
break;