/*
 * GNOME Basic Evaluator class.
 *
 * Author:
 *    Michael Meeks <mmeeks@gnu.org>
 *
 * Copyright 2000, Helix Code, Inc.
 */
#ifndef GB_EVAL_H
#define GB_EVAL_H

#include <gb/gb.h>
#include <gb/gb-expr.h>

struct _GBOnError {
	enum { GB_ON_ERROR_FLAG, GB_ON_ERROR_NEXT, GB_ON_ERROR_GOTO } type;
	const char *label;
};

#define GB_TYPE_EVAL_CONTEXT            (gb_eval_context_get_type ())
#define GB_EVAL_CONTEXT(obj)            (GTK_CHECK_CAST ((obj), GB_TYPE_EVAL_CONTEXT, GBEvalContext))
#define GB_EVAL_CONTEXT_CLASS(klass)    (GTK_CHECK_CLASS_CAST ((klass), GB_TYPE_EVAL_CONTEXT, GBEvalContextClass))
#define GB_IS_EVAL_CONTEXT(obj)		(GTK_CHECK_TYPE ((obj), GB_TYPE_EVAL_CONTEXT))
#define GB_IS_EVAL_CONTEXT_CLASS(klass)	(GTK_CHECK_CLASS_TYPE ((klass), GB_TYPE_EVAL_CONTEXT))

struct _GBEvalContext {
	GtkObject       object;

	char           *exception;
	int             line;
};

struct _GBEvalContextClass {
	GtkObjectClass  klass;

	/* Non constant evaluation */
	GBValue *(*eval)     (GBEvalContext *ec,
			      const GBExpr  *expr);

	/* Exceptions */
	void     (*fire)     (GBEvalContext *ec, const char *txt);
	char    *(*get_text) (GBEvalContext *ec);
	void     (*reset)    (GBEvalContext *ec);
};

GtkType        gb_eval_context_get_type (void);
GBEvalContext *gb_eval_context_new      (void);
GBValue       *gb_eval_context_eval     (GBEvalContext *ec,
					 const GBExpr  *expr);
gboolean       gb_eval_exception        (GBEvalContext *ec);
GBValue       *gb_eval_exception_fire   (GBEvalContext *ec,
					 const char *txt);
GBValue       *gb_eval_exception_firev  (GBEvalContext *ec,
					 const char *format, ...);
#define        gb_eval_context_set_line(e,i) ((e)->line = (i))
char          *gb_eval_context_get_text (GBEvalContext *ec);
void           gb_eval_context_reset    (GBEvalContext *ec);

gboolean       gb_eval_compare (GBEvalContext *ec,
				const GBValue *l, GBExprType t,
				const GBValue *r, GBBoolean *result);

/* Generic manipulation functions */
GBValue *gb_eval_sub              (const GBValue *, const GBValue *);
GBValue *gb_eval_add              (const GBValue *, const GBValue *);
GBValue *gb_eval_mult             (const GBValue *, const GBValue *);
GBValue *gb_eval_div              (const GBValue *, const GBValue *);
GBValue *gb_eval_int_div          (const GBValue *, const GBValue *);
GBValue *gb_eval_pow              (const GBValue *, const GBValue *);
GBValue *gb_eval_concat           (const GBValue *, const GBValue *);
GBValue *gb_eval_eqv              (const GBValue *, const GBValue *);
GBValue *gb_eval_and              (const GBValue *, const GBValue *);
GBValue *gb_eval_or               (const GBValue *, const GBValue *);
GBValue *gb_eval_xor              (const GBValue *, const GBValue *);
GBValue *gb_eval_imp              (const GBValue *, const GBValue *);

GBValue *gb_eval_not              (const GBValue *);
GBValue *gb_eval_neg              (const GBValue *);

#endif /* GB_EVAL_H */
