#!@PERL@ -w -I @srcdir@/../../xapian-core/ # @configure_input@ # # generate-python-exceptions.in: generate error handling code for python # bindings # # Copyright (C) 2003,2004,2006,2007 Olly Betts # Copyright (C) 2007 Richard Boulton # # 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 use strict; use exception_data; my @allclasses = (@baseclasses, @classes); open FD, ">except.i" or die $!; print FD <<"EOF"; /* python/except.i: Custom Python exception handling. * Warning: This file is generated by $0 * - do not modify directly! * * Copyright 2007 Lemur Consulting Ltd * * 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 */ EOF print FD <<'EOF'; namespace Xapian { %exceptionclass Error; %ignore Error::get_description; %extend Error { std::string __str__() const { std::string desc($self->get_msg()); if (!$self->get_context().empty()) { desc += " (context: "; desc += $self->get_context(); desc += ')'; } if ($self->get_error_string()) { desc += " ("; desc += $self->get_error_string(); desc += ')'; } return desc; } } EOF for (@allclasses) { my ($class, $parent, $comment) = split /\t/, $_, 3; print FD "%exceptionclass $class;\n"; } print FD <<'EOF'; } %include "xapian/error.h" %{ static void XapianSetPythonException() { try { throw; } catch (Swig::DirectorException &e) { /* This happens if a director raised an exception. The original Python * error state should still be set, so we don't need to do anything. */ EOF for (reverse @allclasses) { my ($class, $parent, $comment) = split /\t/, $_, 3; print FD <<"EOF"; } catch (const Xapian::$class &e) { SWIG_Python_Raise(SWIG_NewPointerObj((new Xapian::$class(e)), SWIGTYPE_p_Xapian__$class, SWIG_POINTER_OWN), "Xapian::$class", SWIGTYPE_p_Xapian__$class); EOF } print FD <<'EOF'; } catch (const Xapian::Error &e) { SWIG_Python_Raise(SWIG_NewPointerObj((new Xapian::Error(e)), SWIGTYPE_p_Xapian__Error, SWIG_POINTER_OWN), "Xapian::Error", SWIGTYPE_p_Xapian__Error); } catch (const std::exception& e) { SWIG_Error(SWIG_RuntimeError, e.what()); } catch (...) { SWIG_Error(SWIG_UnknownError, "unknown error in Xapian"); } } %} /* Note that we have to re-acquire the GIL in the catch() here, because * XapianSetPythonException accesses Python datastructures. */ %exception { try { $action } catch (...) { SWIG_PYTHON_THREAD_END_ALLOW; XapianSetPythonException(); SWIG_fail; } } /* The following exception directives are for the methods defined by * director classes, which don't drop the GIL in the first place. */ %exception Xapian::MatchDecider::operator() { try { $action } catch (...) { XapianSetPythonException(); SWIG_fail; } } %exception Xapian::ExpandDecider::operator() { try { $action } catch (...) { XapianSetPythonException(); SWIG_fail; } } %exception Xapian::Stopper::operator() { try { $action } catch (...) { XapianSetPythonException(); SWIG_fail; } } %exception Xapian::Stopper::get_description { try { $action } catch (...) { XapianSetPythonException(); SWIG_fail; } } /* If a Python error is raised by a call to a director function, the following * code should cause a C++ exception to be thrown. */ %feature("director:except") { if ($error != NULL) { throw Swig::DirectorMethodException(); } } /* vim:syntax=cpp:set noexpandtab: */ EOF close FD or die $!;