summaryrefslogtreecommitdiff
path: root/expr.h
diff options
context:
space:
mode:
Diffstat (limited to 'expr.h')
-rw-r--r--expr.h156
1 files changed, 156 insertions, 0 deletions
diff --git a/expr.h b/expr.h
new file mode 100644
index 0000000..53b75b7
--- /dev/null
+++ b/expr.h
@@ -0,0 +1,156 @@
+/*
+ * This file is part of ltrace.
+ * Copyright (C) 2011,2012 Petr Machata, Red Hat Inc.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA
+ */
+
+#ifndef EXPR_H
+#define EXPR_H
+
+#include "value.h"
+#include "value_dict.h"
+
+/* Expressions serve as a way of encoding array lengths. */
+
+enum expr_node_kind {
+ EXPR_OP_SELF, /* reference to the variable in question */
+ EXPR_OP_NAMED, /* value of named argument */
+ EXPR_OP_ARGNO, /* value of numbered argument */
+ EXPR_OP_CONST, /* constant value */
+ EXPR_OP_INDEX, /* A[B] */
+ EXPR_OP_UP, /* reference to containing structure */
+ EXPR_OP_CALL1, /* internal callback with one operand */
+ EXPR_OP_CALL2, /* internal callback with two operands */
+};
+
+struct expr_node {
+ enum expr_node_kind kind;
+
+ struct expr_node *lhs;
+ int own_lhs;
+
+ union {
+ struct {
+ const char *s;
+ int own;
+ } name;
+ struct {
+ struct expr_node *n;
+ int own;
+ } node;
+ struct value value;
+ size_t num;
+ struct {
+ union {
+ int (*cb1)(struct value *ret_value,
+ struct value *lhs,
+ struct value_dict *arguments,
+ void *data);
+ int (*cb2)(struct value *ret_value,
+ struct value *lhs,
+ struct value *rhs,
+ struct value_dict *arguments,
+ void *data);
+ } u;
+ void *data;
+ struct expr_node *rhs;
+ int own_rhs;
+ } call;
+ } u;
+};
+
+/* Expression of type self just returns the value in consideration.
+ * For example, if what we seek is length of an array, then the value
+ * representing that array is returned by the expression. */
+void expr_init_self(struct expr_node *node);
+
+/* Expression that yields the value of an argument named NAME. NAME
+ * is owned if OWN_NAME. */
+void expr_init_named(struct expr_node *node,
+ const char *name, int own_name);
+
+/* Expression that yields the value of an argument number NUM. */
+void expr_init_argno(struct expr_node *node, size_t num);
+
+/* Constant expression always returns the same value VAL. VAL is
+ * copied into NODE and owned by it. */
+void expr_init_const(struct expr_node *node, struct value *val);
+void expr_init_const_word(struct expr_node *node, long l,
+ struct arg_type_info *type, int own_type);
+
+/* Expression LHS[RHS]. LHS and RHS are owned if, respectively,
+ * OWN_LHS and OWN_RHS. */
+void expr_init_index(struct expr_node *node,
+ struct expr_node *lhs, int own_lhs,
+ struct expr_node *rhs, int own_rhs);
+
+/* This expression returns the containing value of LHS (^LHS). LHS is
+ * owned if OWN_LHS. */
+void expr_init_up(struct expr_node *node, struct expr_node *lhs, int own_lhs);
+
+/* Callback expression calls CB(eval(LHS), DATA). LHS is owned if
+ * OWN_LHS. DATA is passed to callback verbatim. */
+void expr_init_cb1(struct expr_node *node,
+ int (*cb)(struct value *ret_value,
+ struct value *value,
+ struct value_dict *arguments,
+ void *data),
+ struct expr_node *lhs, int own_lhs, void *data);
+
+/* Callback expression calls CB(eval(LHS), eval(RHS), DATA). LHS and
+ * RHS are owned if, respectively, OWN_LHS and OWN_RHS. DATA is
+ * passed to callback verbatim. */
+void expr_init_cb2(struct expr_node *node,
+ int (*cb)(struct value *ret_value,
+ struct value *lhs, struct value *rhs,
+ struct value_dict *arguments,
+ void *data),
+ struct expr_node *lhs, int own_lhs,
+ struct expr_node *rhs, int own_rhs, void *data);
+
+/* Release the data inside NODE. Doesn't free NODE itself. */
+void expr_destroy(struct expr_node *node);
+
+/* Evaluate the expression NODE in context of VALUE. ARGUMENTS is a
+ * dictionary of named and numbered values that NODE may use. Returns
+ * 0 in case of success or a negative value on error. CONTEXT and
+ * ARGUMENTS may be NULL, but then the expression mustn't need them
+ * for evaluation. */
+int expr_eval(struct expr_node *node, struct value *context,
+ struct value_dict *arguments, struct value *ret_value);
+
+/* Evaluate compile-time expression. Returns 0 on success or negative
+ * value on failure. Computed value is passed back in *VALUEP. */
+int expr_eval_constant(struct expr_node *node, long *valuep);
+
+/* Evaluate expression, whose result should fit into a word. In order
+ * to easily support all the structure and array accesses, we simply
+ * operate on values represented by struct value. But eventually we need
+ * to be able to get out a word-size datum to use it as an index, a
+ * length, etc. */
+int expr_eval_word(struct expr_node *node, struct value *context,
+ struct value_dict *arguments, long *ret_value);
+
+/* Returns non-zero value if the expression is a compile-time
+ * constant. Currently this is only EXPR_OP_CONST, but eventually
+ * things like sizeof or simple expressions might be allowed. */
+int expr_is_compile_constant(struct expr_node *node);
+
+/* Returns a pre-computed expression "self". */
+struct expr_node *expr_self(void);
+
+#endif /* EXPR_H */