

SWIGRUNTIME bool SWIG_check_num_args(const char *func_name, int num_args, int max_args, int min_args, int varargs) {
  if (num_args > max_args && !varargs)
    error("function %s takes at most %i arguments", func_name, max_args);
  else if (num_args < min_args)
    error("function %s requires at least %i arguments", func_name, min_args);
  else
    return true;
  return false;
}

SWIGRUNTIME octave_value_list *SWIG_Octave_AppendOutput(octave_value_list *ovl, const octave_value &ov) {
  ovl->append(ov);
  return ovl;
}

SWIGRUNTIME octave_value SWIG_ErrorType(int code) {
  switch (code) {
  case SWIG_MemoryError:
    return "SWIG_MemoryError";
  case SWIG_IOError:
    return "SWIG_IOError";
  case SWIG_RuntimeError:
    return "SWIG_RuntimeError";
  case SWIG_IndexError:
    return "SWIG_IndexError";
  case SWIG_TypeError:
    return "SWIG_TypeError";
  case SWIG_DivisionByZero:
    return "SWIG_DivisionByZero";
  case SWIG_OverflowError:
    return "SWIG_OverflowError";
  case SWIG_SyntaxError:
    return "SWIG_SyntaxError";
  case SWIG_ValueError:
    return "SWIG_ValueError";
  case SWIG_SystemError:
    return "SWIG_SystemError";
  case SWIG_AttributeError:
    return "SWIG_AttributeError";
  }
  return "SWIG unknown error";
}

SWIGRUNTIME octave_value SWIG_Error(int code, const char *msg) {
  octave_value type(SWIG_ErrorType(code));
  std::string r = msg;
  r += " (" + type.string_value() + ")";
  error(r.c_str());
  return octave_value(r);
}

#define SWIG_fail                                       goto fail

#define SWIG_Octave_ConvertPtr(obj, pptr, type, flags)  SWIG_Octave_ConvertPtrAndOwn(obj, pptr, type, flags, 0)
#define SWIG_ConvertPtr(obj, pptr, type, flags)         SWIG_Octave_ConvertPtr(obj, pptr, type, flags)
#define SWIG_ConvertPtrAndOwn(obj,pptr,type,flags,own)  SWIG_Octave_ConvertPtrAndOwn(obj, pptr, type, flags, own)
#define SWIG_ConvertPtr(obj, pptr, type, flags)         SWIG_Octave_ConvertPtr(obj, pptr, type, flags)
#define SWIG_NewPointerObj(ptr, type, flags)            SWIG_Octave_NewPointerObj(ptr, type, flags)
#define swig_owntype                                    int

#define SWIG_ConvertPacked(obj, ptr, sz, ty)            SWIG_Octave_ConvertPacked(obj, ptr, sz, ty)
#define SWIG_NewPackedObj(ptr, sz, type)                SWIG_Octave_NewPackedObj(ptr, sz, type)

#define SWIG_ConvertFunctionPtr(obj, pptr, type)        SWIG_ConvertPtr(obj, pptr, type, 0)
#define SWIG_NewFunctionPtrObj(ptr, type)               SWIG_NewPointerObj(ptr, type, 0)

#define SWIG_ConvertMember(obj, ptr, sz, ty)            SWIG_Octave_ConvertPacked(obj, ptr, sz, ty)
#define SWIG_NewMemberObj(ptr, sz, type)                SWIG_Octave_NewPackedObj(ptr, sz, type)

#define SWIG_GetModule(clientdata) SWIG_Octave_GetModule(clientdata)
#define SWIG_SetModule(clientdata, pointer) SWIG_Octave_SetModule(clientdata,pointer);
#define SWIG_MODULE_CLIENTDATA_TYPE void*

#define Octave_Error_Occurred() 0
#define SWIG_Octave_AddErrorMsg(msg) {;}

// For backward compatibility only
#define SWIG_POINTER_EXCEPTION  0
#define SWIG_arg_fail(arg)      0

SWIGRUNTIME swig_module_info *SWIG_Octave_GetModule(void *clientdata) {
  octave_value tmp = get_global_value("__SWIG_MODULE__" SWIG_TYPE_TABLE_NAME SWIG_RUNTIME_VERSION, true);
  if (!tmp.is_defined() || !tmp.is_uint64_type())
    return 0;
  unsigned long r = tmp.uint64_scalar_value().value();
  assert(sizeof(r) == sizeof(swig_module_info *));
  return (swig_module_info *) r;
}

SWIGRUNTIME void SWIG_Octave_SetModule(void *clientdata, swig_module_info *pointer) {
  unsigned long r = (unsigned long) pointer;
  assert(sizeof(r) == sizeof(swig_module_info *));
  const char *module_var = "__SWIG_MODULE__" SWIG_TYPE_TABLE_NAME SWIG_RUNTIME_VERSION;
  link_to_global_variable(curr_sym_tab->lookup(module_var, true));
  set_global_value(module_var, octave_uint64(r));
}

// Runtime API implementation

#include <map>
#include <vector>
#include <string>
#include <ext/hash_map>

namespace {

  typedef octave_value_list(*octave_func) (const octave_value_list &, int);
  class octave_swig_type;

  namespace Swig {
    class Director;

    void swig_register_director(octave_swig_type *self, void *ptr, Director *d);
    void swig_director_destroyed(octave_swig_type *self, Director *d);
    void swig_director_set_self(Director *d, octave_swig_type *self);

    octave_base_value *swig_value_ref(octave_swig_type *ost);
    octave_swig_type *swig_value_deref(const octave_value &ov);
    octave_swig_type *swig_value_deref(const octave_base_value &ov);

    struct hash_voidptr {
      int operator() (void *p) const {
	return (int) p;
      }
    };
    typedef __gnu_cxx::hash_map < void *, Director *, hash_voidptr > rtdir_map;

    using namespace __gnu_cxx;
    SWIGINTERN rtdir_map &get_rtdir_map() {
      static swig_module_info *module = 0;
      if (!module)
	module = SWIG_GetModule(0);
      assert(module);
      if (!module->clientdata)
	module->clientdata = new rtdir_map;
      return *(rtdir_map *) module->clientdata;
    }

    SWIGINTERNINLINE void set_rtdir(void *vptr, Director *d) {
      get_rtdir_map()[vptr] = d;
    }

    SWIGINTERNINLINE void erase_rtdir(void *vptr) {
      get_rtdir_map().erase(vptr);
    }

    SWIGINTERNINLINE Director *get_rtdir(void *vptr) {
      rtdir_map::const_iterator pos = get_rtdir_map().find(vptr);
      Director *rtdir = (pos != get_rtdir_map().end())? pos->second : 0;
      return rtdir;
    }
  }

  struct swig_octave_member {
    const char *name;
    octave_func method;
    octave_func get_method;
    octave_func set_method;
    int flags;			// 1 static, 2 global
    const char *doc;
    bool is_static() const {
      return flags &1;
    } bool is_global() const {
      return flags &2;
    }
  };

  struct swig_octave_class {
    const char *name;
    swig_type_info **type;
    int director;
    octave_func constructor;
    const char *constructor_doc;
    octave_func destructor;
    const swig_octave_member *members;
    const char **base_names;
    const swig_type_info **base;
  };

  // octave_swig_type plays the role of both the shadow class and the class 
  // representation within Octave, since there is no support for classes.
  //
  // These should really be decoupled, with the class support added to Octave
  // and the shadow class given by an m-file script. That would dramatically 
  // reduce the runtime complexity, and be more in line w/ other modules.

  class octave_swig_type:public octave_base_value {
    struct cpp_ptr {
      void *ptr;
      bool destroyed;
      cpp_ptr(void *_ptr):ptr(_ptr), destroyed(false) {
      }};
    typedef std::pair < const swig_type_info *, cpp_ptr > type_ptr_pair;

    swig_module_info *module;

    const swig_type_info *construct_type;	// type of special type object
    std::vector < type_ptr_pair > types;	// our c++ base classes
    int own;			// whether we call c++ destructors when we die

    typedef std::pair < const swig_octave_member *, octave_value > member_value_pair;
    typedef std::map < std::string, member_value_pair > member_map;
    member_map members;

    const swig_octave_member *find_member(const swig_type_info *type, const std::string &name) {
      if (!type->clientdata)
	return 0;
      swig_octave_class *c = (swig_octave_class *) type->clientdata;
      const swig_octave_member *m;
      for (m = c->members; m->name; ++m)
	if (m->name == name)
	  return m;
      for (int j = 0; c->base_names[j]; ++j) {
	if (!c->base[j]) {
	  if (!module)
	    module = SWIG_GetModule(0);
	  assert(module);
	  c->base[j] = SWIG_MangledTypeQueryModule(module, module, c->base_names[j]);
	}
	if (!c->base[j])
	  return 0;
	if ((m = find_member(c->base[j], name)))
	  return m;
      }
      return 0;
    }

    member_value_pair *find_member(const std::string &name, bool insert_if_not_found) {
      member_map::iterator it = members.find(name);
      if (it != members.end())
	return &it->second;
      const swig_octave_member *m;
      for (unsigned int j = 0; j < types.size(); ++j)
	if ((m = find_member(types[j].first, name)))
	  return &members.insert(std::make_pair(name, std::make_pair(m, octave_value()))).first->second;
      if (!insert_if_not_found)
	return 0;
      return &members[name];
    }

    const swig_type_info *find_base(const std::string &name, const swig_type_info *base) {
      if (!base) {
	for (unsigned int j = 0; j < types.size(); ++j) {
	  assert(types[j].first->clientdata);
	  swig_octave_class *cj = (swig_octave_class *) types[j].first->clientdata;
	  if (cj->name == name)
	    return types[j].first;
	}
	return 0;
      }
      assert(base->clientdata);
      swig_octave_class *c = (swig_octave_class *) base->clientdata;
      for (int j = 0; c->base_names[j]; ++j) {
	if (!c->base[j]) {
	  if (!module)
	    module = SWIG_GetModule(0);
	  assert(module);
	  c->base[j] = SWIG_MangledTypeQueryModule(module, module, c->base_names[j]);
	}
	if (!c->base[j])
	  return 0;
	assert(c->base[j]->clientdata);
	swig_octave_class *cj = (swig_octave_class *) c->base[j]->clientdata;
	if (cj->name == name)
	  return c->base[j];
      }
      return 0;
    }

    octave_value_list member_invoke(member_value_pair *m, const octave_value_list &args, int nargout) {
      if (m->second.is_defined())
	return m->second.subsref("(", std::list < octave_value_list > (1, args), nargout);
      else if (m->first && m->first->method)
	return m->first->method(args, nargout);
      error("member not defined or not invocable");
      return octave_value_list();
    }

    bool dispatch_unary_op(const std::string &symbol, octave_value &ret) {
      member_value_pair *m = find_member(symbol, false);
      if (!m || m->first->is_static() || m->first->is_global())
	return false;
      octave_value_list args;
      args.append(as_value());
      octave_value_list argout(member_invoke(m, args, 1));
      if (argout.length() < 1)
	return false;
      ret = argout(0);
      return true;
    }

    bool dispatch_binary_op(const std::string &symbol, const octave_base_value &rhs, octave_value &ret) {
      member_value_pair *m = find_member(symbol, false);
      if (!m || m->first->is_static() || m->first->is_global())
	return false;
      octave_value_list args;
      args.append(as_value());
      args.append(make_value_hack(rhs));
      octave_value_list argout(member_invoke(m, args, 1));
      if (argout.length() < 1)
	return false;
      ret = argout(0);
      return true;
    }

    bool dispatch_index_op(const std::string &symbol, const octave_value_list &rhs, octave_value_list &ret) {
      member_value_pair *m = find_member(symbol, false);
      if (!m || m->first->is_static() || m->first->is_global())
	return false;
      octave_value_list args;
      args.append(as_value());
      args.append(rhs);
      octave_value_list argout(member_invoke(m, args, 1));
      if (argout.length() >= 1)
	ret = argout(0);
      return true;
    }

    octave_value_list member_deref(member_value_pair *m, const octave_value_list &args) {
      if (m->second.is_defined())
	return m->second;
      else if (m->first) {
	if (m->first->get_method)
	  return m->first->get_method(args, 1);
	else if (m->first->method)
	  return octave_value(new octave_builtin(m->first->method));
      }
      error("undefined member");
      return octave_value_list();
    }

    static octave_value make_value_hack(const octave_base_value &x) {
      ((octave_swig_type &) x).count++;
      return octave_value((octave_base_value *) &x);
    }

    octave_swig_type(const octave_swig_type &x);
    octave_swig_type &operator=(const octave_swig_type &rhs);
  public:

    octave_swig_type(void *_ptr = 0, const swig_type_info *_type = 0, int _own = 0)
      :	module(0), construct_type(_ptr ? 0 : _type), own(_own) {
      if (_type || _ptr)
	types.push_back(std::make_pair(_type, _ptr));
      if (_ptr) {
	Swig::Director *d = Swig::get_rtdir(_ptr);
	if (d)
	  Swig::swig_director_set_self(d, this);
      }
    }

    ~octave_swig_type() {
      if (own) {
	++count;
	for (unsigned int j = 0; j < types.size(); ++j) {
	  if (!types[j].first || !types[j].first->clientdata)
	    continue;
	  swig_octave_class *c = (swig_octave_class *) types[j].first->clientdata;
	  if (c->destructor && !types[j].second.destroyed && types[j].second.ptr) {
	    c->destructor(as_value(), 0);
	  }
	}
      }
      for (unsigned int j = 0; j < types.size(); ++j)
	Swig::erase_rtdir(types[j].second.ptr);
    }

    octave_value as_value() {
      ++count;
      return Swig::swig_value_ref(this);
    }

    void incref() {
      ++count;
    }

    void decref() {
      if (!--count)
	delete this;
    }

    long swig_this() const {
      if (!types.size())
	return (long) this;
      return (long) types[0].second.ptr;
    }
    const char* help_text() const {
      if (!types.size())
	return 0;
      if (!types[0].first->clientdata)
	return 0;
      swig_octave_class *c = (swig_octave_class *) types[0].first->clientdata;
      return c->constructor_doc;
    }

    std::string swig_type_name() const {
      // * need some way to manually name subclasses.
      // * eg optional first arg to subclass(), or named_subclass()
      std::string ret;
      for (unsigned int j = 0; j < types.size(); ++j) {
	if (j)
	  ret += "_";
	if (types[j].first->clientdata) {
	  swig_octave_class *c = (swig_octave_class *) types[j].first->clientdata;
	  ret += c->name;
	} else
	  ret += types[j].first->name;
      }
      return ret;
    }

    void merge(octave_swig_type &rhs) {
      rhs.own = 0;
      for (unsigned int j = 0; j < rhs.types.size(); ++j) {
	assert(!rhs.types[j].second.destroyed);
	Swig::Director *d = Swig::get_rtdir(rhs.types[j].second.ptr);
	if (d)
	  Swig::swig_director_set_self(d, this);
      }
      types.insert(types.end(), rhs.types.begin(), rhs.types.end());
      members.insert(rhs.members.begin(), rhs.members.end());
      rhs.types.clear();
      rhs.members.clear();
    }

    void install_global() {
      for (member_map::const_iterator it = members.begin(); it != members.end(); ++it) {
	if (it->second.first && it->second.first->method)
	  install_builtin_function(it->second.first->method, it->first,
				   it->second.first->doc?it->second.first->doc:std::string());
	else if (it->second.second.is_defined()) {
	  link_to_global_variable(curr_sym_tab->lookup(it->first, true));
	  set_global_value(it->first, it->second.second);
	  
	  octave_swig_type *ost = Swig::swig_value_deref(it->second.second);
	  if (ost) {
	    const char* h = ost->help_text();
	    if (h) {
	      symbol_record *sr = global_sym_tab->lookup (it->first, true);
	      sr->document(h);
	    }
	  }
	}
      }
    }

    void *cast(swig_type_info *type, int *_own, int flags) {
      if (_own)
	*_own = own;
      if (flags &SWIG_POINTER_DISOWN)
	own = 0;
      if (!type && types.size())
	return types[0].second.ptr;
      for (unsigned int j = 0; j < types.size(); ++j)
	if (type == types[j].first)
	  return types[j].second.ptr;
      for (unsigned int j = 0; j < types.size(); ++j) {
	swig_cast_info *tc = SWIG_TypeCheck(types[j].first->name, type);
	if (!tc)
	  continue;
	int newmemory = 0;
	void *vptr = SWIG_TypeCast(tc, types[j].second.ptr, &newmemory);
	assert(!newmemory);	// newmemory handling not yet implemented
	return vptr;
      }
      return 0;
    }

    bool is_owned() const {
      return own;
    }

    void director_destroyed(Swig::Director *d) {
      bool found = false;
      for (unsigned int j = 0; j < types.size(); ++j) {
	Swig::Director *dj = Swig::get_rtdir(types[j].second.ptr);
	if (dj == d) {
	  types[j].second.destroyed = true;
	  found = true;
	}
      }
      assert(found);
    }

    void assign(const std::string &name, const octave_value &ov) {
      members[name] = std::make_pair((const swig_octave_member *) 0, ov);
    }

    void assign(const std::string &name, const swig_octave_member *m) {
      members[name] = std::make_pair(m, octave_value());
    }

    octave_base_value *clone() const {
      // pass-by-value is probably not desired, and is harder;
      // requires calling copy constructors of contained types etc.
      assert(0);
      *(int *) 0 = 0;
      return 0;
    }

    octave_base_value *empty_clone() const {
      return new octave_swig_type();
    }

    bool is_defined() const {
      return true;
    }

    virtual bool is_map() const {
      return true;
    }

    virtual octave_value subsref(const std::string &ops, const std::list < octave_value_list > &idx) {
      octave_value_list ovl = subsref(ops, idx, 1);
      return ovl.length()? ovl(0) : octave_value();
    }

    virtual octave_value_list subsref(const std::string &ops, const std::list < octave_value_list > &idx, int nargout) {
      assert(ops.size() > 0);
      assert(ops.size() == idx.size());

      std::list < octave_value_list >::const_iterator idx_it = idx.begin();
      int skip = 0;
      octave_value_list sub_ovl;

      // constructor invocation
      if (ops[skip] == '(' && construct_type) {
	assert(construct_type->clientdata);
	swig_octave_class *c = (swig_octave_class *) construct_type->clientdata;
	if (!c->constructor) {
	  error("cannot create instance");
	  return octave_value_list();
	}
	octave_value_list args;
	if (c->director)
	  args.append(Swig::swig_value_ref(new octave_swig_type(this, 0, 0)));
	args.append(*idx_it++);
	++skip;
	sub_ovl = c->constructor(args, nargout);
      }
      // member dereference or invocation
      else if (ops[skip] == '.') {
	std::string subname;
	const swig_type_info *base = 0;	// eg, a.base.base_cpp_mem
	for (;;) {
	  octave_value_list subname_ovl(*idx_it++);
	  ++skip;
	  assert(subname_ovl.length() == 1 && subname_ovl(0).is_string());
	  subname = subname_ovl(0).string_value();

	  const swig_type_info *next_base = find_base(subname, base);
	  if (!next_base || skip >= (int) ops.size() || ops[skip] != '.')
	    break;
	  base = next_base;
	}

	member_value_pair tmp, *m = &tmp;
	if (!base || !(m->first = find_member(base, subname)))
	  m = find_member(subname, false);
	if (!m) {
	  error("member not found");
	  return octave_value_list();
	}

	octave_value_list args;
	if (!m->first || (!m->first->is_static() && !m->first->is_global()))
	  args.append(as_value());
	if (skip < (int) ops.size() && ops[skip] == '(' && ((m->first && m->first->method) || m->second.is_function() || m->second.is_function_handle())) {
	  args.append(*idx_it++);
	  ++skip;
	  sub_ovl = member_invoke(m, args, nargout);
	} else {
	  sub_ovl = member_deref(m, args);
	}
      }
      // index operator
      else {
	if (ops[skip] == '(' || ops[skip] == '{') {
	  const char *op_name = ops[skip] == '(' ? "__paren" : "__brace";
	  octave_value_list args;
	  args.append(*idx_it++);
	  ++skip;
	  if (!dispatch_index_op(op_name, args, sub_ovl)) {
	    error("error evaluating index operator");
	    return octave_value_list();
	  }
	} else {
	  error("unsupported subsref");
	  return octave_value_list();
	}
      }

      if (skip >= (int) ops.size())
	return sub_ovl;
      if (sub_ovl.length() < 1) {
	error("bad subs ref");
	return octave_value_list();
      }
      return sub_ovl(0).next_subsref(nargout, ops, idx, skip);
    }

    octave_value subsasgn(const std::string &ops, const std::list < octave_value_list > &idx, const octave_value &rhs) {
      assert(ops.size() > 0);
      assert(ops.size() == idx.size());

      std::list < octave_value_list >::const_iterator idx_it = idx.begin();
      int skip = 0;

      if (ops.size() > 1) {
	std::list < octave_value_list >::const_iterator last = idx.end();
	--last;
	std::list < octave_value_list > next_idx(idx.begin(), last);
	octave_value next_ov = subsref(ops.substr(0, ops.size() - 1), next_idx);
	next_ov.subsasgn(ops.substr(ops.size() - 1), std::list < octave_value_list > (1, *last), rhs);
      }

      else if (ops[skip] == '(' || ops[skip] == '{') {
	const char *op_name = ops[skip] == '(' ? "__paren_asgn" : "__brace_asgn";
	member_value_pair *m = find_member(op_name, false);
	if (m) {
	  octave_value_list args;
	  args.append(as_value());
	  args.append(*idx_it);
	  args.append(rhs);
	  member_invoke(m, args, 1);
	} else
	  error("%s member not found", op_name);
      }

      else if (ops[skip] == '.') {
	octave_value_list subname_ovl(*idx_it++);
	++skip;
	assert(subname_ovl.length() == 1 &&subname_ovl(0).is_string());
	std::string subname = subname_ovl(0).string_value();

	member_value_pair *m = find_member(subname, true);
	if (!m->first || !m->first->set_method) {
	  m->first = 0;
	  m->second = rhs;
	} else if (m->first->set_method) {
	  octave_value_list args;
	  if (!m->first->is_static() && !m->first->is_global())
	    args.append(as_value());
	  args.append(rhs);
	  m->first->set_method(args, 1);
	} else
	  error("member not assignable");
      } else
	error("unsupported subsasgn");

      return as_value();
    }

    virtual bool is_string() const {
      octave_swig_type *nc_this = const_cast < octave_swig_type *>(this);
      return !!nc_this->find_member("__str", false);
    }

    virtual std::string string_value(bool force = false) const {
      octave_swig_type *nc_this = const_cast < octave_swig_type *>(this);
      member_value_pair *m = nc_this->find_member("__str", false);
      if (!m) {
	error("__str method not defined");
	return std::string();
      }
      octave_value_list outarg = nc_this->member_invoke(m, octave_value_list(nc_this->as_value()), 1);
      if (outarg.length() < 1 || !outarg(0).is_string()) {
	error("__str method did not return a string");
	return std::string();
      }
      return outarg(0).string_value();
    }

    virtual octave_value convert_to_str(bool pad = false, bool force = false, char type = '"') const {
      return string_value();
    }

    virtual octave_value convert_to_str_internal(bool pad, bool force, char type) const {
      return string_value();
    }

    static bool dispatch_global_op(const std::string &symbol, const octave_value_list &args, octave_value &ret) {
      // we assume that "op_"-prefixed functions are installed in global namespace
      // (rather than any module namespace).

      octave_value fcn = get_global_value(symbol, true);
      if (!fcn.is_function() && !fcn.is_function_handle())
	return false;
      ret = fcn.subsref("(", std::list < octave_value_list > (1, args));
      return true;
    }

    static octave_value dispatch_unary_op(const octave_base_value &x, const char *op_name) {
      octave_swig_type *ost = Swig::swig_value_deref(x);
      assert(ost);

      octave_value ret;
      if (ost->dispatch_unary_op(std::string("__") + op_name, ret))
	return ret;
      std::string symbol = "op_" + ost->swig_type_name() + "_" + op_name;
      octave_value_list args;
      args.append(make_value_hack(x));
      if (dispatch_global_op(symbol, args, ret))
	return ret;

      error("could not dispatch unary operator");
      return octave_value();
    }

    static octave_value dispatch_binary_op(const octave_base_value &lhs, const octave_base_value &rhs, const char *op_name) {
      octave_swig_type *lhs_ost = Swig::swig_value_deref(lhs);
      octave_swig_type *rhs_ost = Swig::swig_value_deref(rhs);

      octave_value ret;
      if (lhs_ost && lhs_ost->dispatch_binary_op(std::string("__") + op_name, rhs, ret))
	return ret;

      std::string symbol;
      octave_value_list args;
      args.append(make_value_hack(lhs));
      args.append(make_value_hack(rhs));

      symbol = "op_";
      symbol += lhs_ost ? lhs_ost->swig_type_name() : lhs.type_name();
      symbol += "_";
      symbol += op_name;
      symbol += "_";
      symbol += rhs_ost ? rhs_ost->swig_type_name() : rhs.type_name();
      if (dispatch_global_op(symbol, args, ret))
	return ret;

      symbol = "op_";
      symbol += lhs_ost ? lhs_ost->swig_type_name() : lhs.type_name();
      symbol += "_";
      symbol += op_name;
      symbol += "_";
      symbol += "any";
      if (dispatch_global_op(symbol, args, ret))
	return ret;

      symbol = "op_";
      symbol += "any";
      symbol += "_";
      symbol += op_name;
      symbol += "_";
      symbol += rhs_ost ? rhs_ost->swig_type_name() : rhs.type_name();
      if (dispatch_global_op(symbol, args, ret))
	return ret;

      error("could not dispatch binary operator");
      return octave_value();
    }

    void print(std::ostream &os, bool pr_as_read_syntax = false) const {
      if (is_string()) {
	os << string_value();
	return;
      }

      os << "{" << std::endl;
      for (unsigned int j = 0; j < types.size(); ++j) {
	if (types[j].first->clientdata) {
	  const swig_octave_class *c = (const swig_octave_class *) types[j].first->clientdata;
	  os << "  " << c->name << ", ptr = " << types[j].second.ptr << std::endl;
	} else {
	  os << "  " << types[j].first->name << ", ptr = " << types[j].second.ptr << std::endl;
	}
      }
      for (member_map::const_iterator it = members.begin(); it != members.end(); ++it) {
	if (it->second.first) {
	  const char *objtype = it->second.first->method ? "method" : "variable";
	  const char *modifier = (it->second.first->flags &1) ? "static" : (it->second.first->flags &2) ? "global" : "";
	  os << it->second.first->name << " (c++ " << modifier << " " << objtype << ")" << std::endl;
	  assert(it->second.first->name == it->first);
	} else {
	  os << it->first << " (octave value)" << std::endl;
	}
      }
      os << "}" << std::endl;
    }
  };

  // Octave tries hard to preserve pass-by-value semantics. Eg, assignments
  // will call clone() via make_unique() if there is more than one outstanding 
  // reference to the lhs, and forces the clone's reference count to 1 
  // (so you can't just increment your own count and return this).
  //
  // One way to fix this (without modifying Octave) is to add a level of
  // indirection such that clone copies ref-counted pointer and we keep 
  // pass-by-ref semantics (which are more natural/expected for C++ bindings).
  //
  // Supporting both pass-by-{ref,value} and toggling via %feature/option 
  // might be nice.

  class octave_swig_ref:public octave_base_value {
    octave_swig_type *ptr;
  public:
    octave_swig_ref(octave_swig_type *_ptr = 0)
      :ptr(_ptr) { }

    ~octave_swig_ref()
      { if (ptr) ptr->decref(); }

    octave_swig_type *get_ptr() const
      { return ptr; }

    octave_base_value *clone() const
      { if (ptr) ptr->incref(); return new octave_swig_ref(ptr); }

    octave_base_value *empty_clone() const
      { return new octave_swig_ref(0); }

    bool is_defined() const
      { return ptr->is_defined(); }

    virtual bool is_map() const 
      { return ptr->is_map(); }

    virtual octave_value subsref(const std::string &ops, const std::list < octave_value_list > &idx) 
      { return ptr->subsref(ops, idx); }

    virtual octave_value_list subsref(const std::string &ops, const std::list < octave_value_list > &idx, int nargout)
      { return ptr->subsref(ops, idx, nargout); }

    octave_value subsasgn(const std::string &ops, const std::list < octave_value_list > &idx, const octave_value &rhs)
      { return ptr->subsasgn(ops, idx, rhs); }

    virtual bool is_string() const 
      { return ptr->is_string(); }

    virtual std::string string_value(bool force = false) const 
      { return ptr->string_value(force); }

    virtual octave_value convert_to_str(bool pad = false, bool force = false, char type = '"') const
      { return ptr->convert_to_str(pad, force, type); }

    virtual octave_value convert_to_str_internal(bool pad, bool force, char type) const
      { return ptr->convert_to_str_internal(pad, force, type); }

    void print(std::ostream &os, bool pr_as_read_syntax = false) const
      { return ptr->print(os, pr_as_read_syntax); }

  private:
    DECLARE_OCTAVE_ALLOCATOR;
    DECLARE_OV_TYPEID_FUNCTIONS_AND_DATA;
  };
  DEFINE_OCTAVE_ALLOCATOR(octave_swig_ref);
  DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA(octave_swig_ref, "swig_ref", "swig_ref");

  class octave_swig_packed:public octave_base_value {
    swig_type_info *type;
    std::vector < char > buf;
  public:

    octave_swig_packed(swig_type_info *_type = 0, const char *_buf = 0, size_t _buf_len = 0)
      :	type(_type), buf(_buf, _buf + _buf_len) {
    }

    bool copy(swig_type_info *outtype, char *ptr, size_t sz) {
      if (outtype && outtype != type)
	return false;
      assert(sz <= buf.size());
      std::copy(&buf[0], &buf[sz], ptr);
      return true;
    }

    octave_base_value *clone() const {
      return new octave_swig_packed(*this);
    }

    octave_base_value *empty_clone() const {
      return new octave_swig_packed();
    }

    bool is_defined() const {
      return true;
    }

    void print(std::ostream &os, bool pr_as_read_syntax = false) const {
      os << "swig packed type: name = " << type->name << ", len = " << buf.size() << std::endl;
    }
  private:
    DECLARE_OCTAVE_ALLOCATOR;
    DECLARE_OV_TYPEID_FUNCTIONS_AND_DATA;
  };
  DEFINE_OCTAVE_ALLOCATOR(octave_swig_packed);
  DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA(octave_swig_packed, "swig_packed", "swig_packed");

  static octave_value_list octave_set_immutable(const octave_value_list &args, int nargout) {
    error("attempt to set immutable member variable");
    return octave_value_list();
  }

  struct octave_value_ref {
    const octave_value_list &ovl;
    int j;

    octave_value_ref(const octave_value_list &_ovl, int _j)
      :ovl(_ovl), j(_j) { }

    operator  octave_value() const {
      return ovl(j);
    }

    octave_value operator*() const {
      return ovl(j);
    }
  };

  octave_value_list swig_subclass(const octave_value_list &args, int nargout) {
    octave_swig_type *top = new octave_swig_type;
    for (int j = 0; j < args.length(); ++j) {
      if (args(j).type_id() == octave_swig_ref::static_type_id()) {
	octave_swig_ref *osr = static_cast < octave_swig_ref *>(args(j).internal_rep());
	octave_swig_type *ost = osr->get_ptr();
	if (!ost->is_owned()) {
	  error("cannot subclass object not constructed on octave side");
	  return octave_value_list();
	}
	top->merge(*ost);
      } else if (args(j).is_function_handle()) {
	top->assign(args(j).fcn_handle_value()->fcn_name(), args(j));
      } else if (args(j).is_string()) {
	if (j + 1 >= args.length()) {
	  error("member assignments must be of string,value form");
	  return octave_value_list();
	}
	top->assign(args(j).string_value(), args(j + 1));
	++j;
      } else {
	error("invalid arguments to subclass");
	return octave_value_list();
      }
    }
    return octave_value(Swig::swig_value_ref(top));
  }

  octave_value_list swig_type(const octave_value_list &args, int nargout) {
    if (args.length() != 1) {
      error("swig_typeinfo must be called with only a single object");
      return octave_value_list();
    }
    octave_swig_type *ost = Swig::swig_value_deref(args(0));
    if (!ost) {
      error("object is not a swig_ref");
      return octave_value_list();
    }
    return octave_value(ost->swig_type_name());
  }

  octave_value_list swig_typequery(const octave_value_list &args, int nargout) {
    if (args.length() != 1 || !args(0).is_string()) {
      error("swig_typeinfo must be called with single string argument");
      return octave_value_list();
    }
    swig_module_info *module = SWIG_GetModule(0);
    swig_type_info *type = SWIG_TypeQueryModule(module, module, args(0).string_value().c_str());
    if (!type)
      return octave_value("<unknown>");
    return octave_value(type->name);
  }

  octave_value_list swig_this(const octave_value_list &args, int nargout) {
    if (args.length() != 1) {
      error("swig_typeinfo must be called with only a single object");
      return octave_value_list();
    }
    octave_swig_type *ost = Swig::swig_value_deref(args(0));
    if (!ost) {
      error("object is not a swig_ref");
      return octave_value_list();
    }
    return octave_value(octave_uint64((unsigned long long) ost->swig_this()));
  }


#define SWIG_DIRECTORS

  struct Director;
  class octave_swig_type;

  namespace Swig {
    class Director {
      octave_swig_type *self;
      bool disowned;

      Director(const Director &x);
      Director &operator=(const Director &rhs);
    public:

      Director(void *vptr):self(0), disowned(false) {
	set_rtdir(vptr, this);
      }

      ~Director() {
	swig_director_destroyed(self, this);
	if (disowned)
	  self->decref();
      }

      void swig_set_self(octave_swig_type *new_self) {
	assert(!disowned);
	self = new_self;
      }

      octave_swig_type *swig_get_self() const {
	return self;
      }

      void swig_disown() {
	if (disowned)
	  return;
	disowned = true;
	self->incref();
      }
    };

    struct DirectorTypeMismatchException {
      static void raise(const char *msg) {
	// ... todo
	throw(DirectorTypeMismatchException());
      }

      static void raise(const octave_value &ov, const char *msg) {
	// ... todo
	raise(msg);
      }
    };
    struct DirectorPureVirtualException {
      static void raise(const char *msg) {
	// ... todo
	throw(DirectorPureVirtualException());
      }

      static void raise(const octave_value &ov, const char *msg) {
	// ... todo
	raise(msg);
      }
    };

  }

  void swig_acquire_ownership(void *vptr) {
    //  assert(0);
    // ... todo
  }

  void swig_acquire_ownership_array(void *vptr) {
    //  assert(0);
    // ... todo
  }

  void swig_acquire_ownership_obj(void *vptr, int own) {
    //  assert(0);
    // ... todo
  }

  namespace Swig {
    void swig_director_destroyed(octave_swig_type *self, Director *d) {
      self->director_destroyed(d);
    }

    void swig_director_set_self(Director *d, octave_swig_type *self) {
      d->swig_set_self(self);
    }

    octave_base_value *swig_value_ref(octave_swig_type *ost) {
      return new octave_swig_ref(ost);
    }

    octave_swig_type *swig_value_deref(const octave_value &ov) {
      return swig_value_deref(*ov.internal_rep());
    }

    octave_swig_type *swig_value_deref(const octave_base_value &ov) {
      if (ov.type_id() != octave_swig_ref::static_type_id())
	return 0;
      const octave_swig_ref *osr = static_cast < const octave_swig_ref *>(&ov);
      return osr->get_ptr();
    }

  }

  SWIGRUNTIME octave_value SWIG_Octave_NewPointerObj(void *ptr, swig_type_info *type, int flags) {
    int own = (flags &SWIG_POINTER_OWN) ? SWIG_POINTER_OWN : 0;

    Swig::Director *d = Swig::get_rtdir(ptr);
    if (d && d->swig_get_self())
      return d->swig_get_self()->as_value();
    return Swig::swig_value_ref(new octave_swig_type(ptr, type, own));
  }

  SWIGRUNTIME int SWIG_Octave_ConvertPtrAndOwn(const octave_value &ov, void **ptr, swig_type_info *type, int flags, int *own) {
    if (!ov.is_defined()) {
      if (ptr)
	*ptr = 0;
      return SWIG_OK;
    }
    if (ov.type_id() != octave_swig_ref::static_type_id())
      return SWIG_TypeError;
    octave_swig_ref *osr = static_cast < octave_swig_ref *>(ov.internal_rep());
    octave_swig_type *ost = osr->get_ptr();
    void *vptr = ost->cast(type, own, flags);
    if (!vptr)
      return SWIG_TypeError;
    if (ptr)
      *ptr = vptr;
    return SWIG_OK;
  }

  SWIGRUNTIMEINLINE octave_value SWIG_Octave_NewPackedObj(void *ptr, size_t sz, swig_type_info *type) {
    return new octave_swig_packed(type, (char *) ptr, sz);
  }

  SWIGRUNTIME int SWIG_Octave_ConvertPacked(const octave_value &ov, void *ptr, size_t sz, swig_type_info *type) {
    if (!ov.is_defined())
      return SWIG_TypeError;
    if (ov.type_id() != octave_swig_packed::static_type_id())
      return SWIG_TypeError;
    octave_swig_packed *ost = static_cast < octave_swig_packed *>(ov.internal_rep());
    return ost->copy(type, (char *) ptr, sz) ? SWIG_OK : SWIG_TypeError;
  }

  void SWIG_Octave_SetConstant(octave_swig_type *module_ns, const std::string &name, const octave_value &ov) {
    module_ns->assign(name, ov);
  }


#define swig_unary_op(name) \
octave_value swig_unary_op_##name(const octave_base_value &x) { \
  return octave_swig_type::dispatch_unary_op(x,#name); \
}
#define swig_binary_op(name) \
octave_value swig_binary_op_##name(const octave_base_value&lhs,const octave_base_value &rhs) { \
  return octave_swig_type::dispatch_binary_op(lhs,rhs,#name); \
}
#define swigreg_unary_op(name) \
if (!octave_value_typeinfo::lookup_unary_op(octave_value::op_##name,tid)) \
octave_value_typeinfo::register_unary_op(octave_value::op_##name,tid,swig_unary_op_##name);
#define swigreg_binary_op(name) \
if (!octave_value_typeinfo::lookup_binary_op(octave_value::op_##name,tid1,tid2)) \
octave_value_typeinfo::register_binary_op(octave_value::op_##name,tid1,tid2,swig_binary_op_##name);

  swig_unary_op(not);
  swig_unary_op(uplus);
  swig_unary_op(uminus);
  swig_unary_op(transpose);
  swig_unary_op(hermitian);
  swig_unary_op(incr);
  swig_unary_op(decr);

  swig_binary_op(add);
  swig_binary_op(sub);
  swig_binary_op(mul);
  swig_binary_op(div);
  swig_binary_op(pow);
  swig_binary_op(ldiv);
  swig_binary_op(lshift);
  swig_binary_op(rshift);
  swig_binary_op(lt);
  swig_binary_op(le);
  swig_binary_op(eq);
  swig_binary_op(ge);
  swig_binary_op(gt);
  swig_binary_op(ne);
  swig_binary_op(el_mul);
  swig_binary_op(el_div);
  swig_binary_op(el_pow);
  swig_binary_op(el_ldiv);
  swig_binary_op(el_and);
  swig_binary_op(el_or);

  void swig_install_unary_ops(int tid) {
    swigreg_unary_op(not);
    swigreg_unary_op(uplus);
    swigreg_unary_op(uminus);
    swigreg_unary_op(transpose);
    swigreg_unary_op(hermitian);
    swigreg_unary_op(incr);
    swigreg_unary_op(decr);
  }
  void swig_install_binary_ops(int tid1, int tid2) {
    swigreg_binary_op(add);
    swigreg_binary_op(sub);
    swigreg_binary_op(mul);
    swigreg_binary_op(div);
    swigreg_binary_op(pow);
    swigreg_binary_op(ldiv);
    swigreg_binary_op(lshift);
    swigreg_binary_op(rshift);
    swigreg_binary_op(lt);
    swigreg_binary_op(le);
    swigreg_binary_op(eq);
    swigreg_binary_op(ge);
    swigreg_binary_op(gt);
    swigreg_binary_op(ne);
    swigreg_binary_op(el_mul);
    swigreg_binary_op(el_div);
    swigreg_binary_op(el_pow);
    swigreg_binary_op(el_ldiv);
    swigreg_binary_op(el_and);
    swigreg_binary_op(el_or);
  }
  void swig_install_ops(int tid) {
    // here we assume that tid are conseq integers increasing from zero, and 
    // that our tid is the last one. might be better to have explicit string 
    // list of types we should bind to, and use lookup_type to resolve their tid.

    swig_install_unary_ops(tid);
    swig_install_binary_ops(tid, tid);
    for (int j = 0; j < tid; ++j) {
      swig_install_binary_ops(j, tid);
      swig_install_binary_ops(tid, j);
    }
  }

}
