diff --git a/pytriqs/magic.py.in b/pytriqs/magic.py.in index 2b47ed24..4c459685 100644 --- a/pytriqs/magic.py.in +++ b/pytriqs/magic.py.in @@ -6,7 +6,7 @@ Triqs magic {TRIQS_DOC} """ -import imp,os,sys,subprocess, hashlib +import imp,os,sys,subprocess, hashlib,re from IPython.core.error import UsageError from IPython.core.magic import Magics, magics_class, line_magic, cell_magic from IPython.core import display, magic_arguments @@ -53,6 +53,7 @@ def desc_file(c_decl, use) : from wrap_generator import * module = module_(full_name = "ext", doc = "") module.add_include("") +module.add_include("") module.add_using("namespace triqs::arrays") module.add_preamble('#include "./ext.cpp"') """ @@ -137,9 +138,16 @@ class TriqsMagics(Magics): if '-v' in line: self.triqs.parser.set_defaults(verbosity=0) + ## Add GIL argument ? + use_GIL = False args = magic_arguments.parse_argstring(self.triqs, line) code = cell if cell.endswith('\n') else cell + '\n' + + #if not GIL, we replace std::cout by triqs::py_out for capture in the notebook + if not use_GIL : + code = re.sub("std::cout", "triqs::py_stream()", code) + key = code, line, sys.version_info, sys.executable c_decl = self.extract_signature(code) diff --git a/triqs/h5/serialization.hpp b/triqs/h5/serialization.hpp index 5d366a56..30f265d9 100644 --- a/triqs/h5/serialization.hpp +++ b/triqs/h5/serialization.hpp @@ -25,7 +25,7 @@ //#define CHECK_OR_THROW(Cond, Mess) #define CHECK_OR_THROW(Cond, Mess) \ - if (!Cond) TRIQS_RUNTIME_ERROR << "Error in h5 (de)serialization " << Mess; + if (!(Cond)) TRIQS_RUNTIME_ERROR << "Error in h5 (de)serialization " << Mess; namespace triqs { namespace h5 { diff --git a/triqs/python_tools/py_stream.cpp b/triqs/python_tools/py_stream.cpp new file mode 100644 index 00000000..41b48b69 --- /dev/null +++ b/triqs/python_tools/py_stream.cpp @@ -0,0 +1,36 @@ +/******************************************************************************* + * + * TRIQS: a Toolbox for Research in Interacting Quantum Systems + * + * Copyright (C) 2014 by O. Parcollet + * + * TRIQS 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 3 of the License, or (at your option) any later + * version. + * + * TRIQS 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 + * TRIQS. If not, see . + * + ******************************************************************************/ +#define TRIQS_LIB_CPP +#include "./py_stream.hpp" +#include "../utility/exceptions.hpp" + +namespace triqs { + +using py_tools::pyref; + +py_stream::py_stream() { + if (!Py_IsInitialized()) TRIQS_RUNTIME_ERROR << "Construction of a py_stream before the interpreter is initialized !!"; + sys = pyref::module("sys"); + sys_out = sys.attr("stdout"); +} + +void py_stream::_write(const char* s) { pyref res = PyObject_CallMethod(sys_out, "write", "s", s); } +} diff --git a/triqs/python_tools/py_stream.hpp b/triqs/python_tools/py_stream.hpp new file mode 100644 index 00000000..a11020cb --- /dev/null +++ b/triqs/python_tools/py_stream.hpp @@ -0,0 +1,58 @@ +/******************************************************************************* + * + * TRIQS: a Toolbox for Research in Interacting Quantum Systems + * + * Copyright (C) 2014 by O. Parcollet + * + * TRIQS 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 3 of the License, or (at your option) any later + * version. + * + * TRIQS 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 + * TRIQS. If not, see . + * + ******************************************************************************/ +#pragma once +#include +#include +#include "./pyref.hpp" + +namespace triqs { + +/** + */ +class py_stream { + + py_tools::pyref sys, sys_out; + void _write(const char* s); + + public: + py_stream(); + + template py_stream& operator<<(T const& x) { + std::stringstream fs; + fs << x; + _write(fs.str().c_str()); + return *this; + } + + // this is the type of std::cout + typedef std::basic_ostream> CoutType; + + // this is the function signature of std::endl + typedef CoutType& (*StandardEndLine)(CoutType&); + + // define an operator<< to take in std::endl + py_stream& operator<<(StandardEndLine manip) { + _write("\n"); + return *this; + } +}; + +} diff --git a/triqs/python_tools/pyref.hpp b/triqs/python_tools/pyref.hpp new file mode 100644 index 00000000..9087f1b6 --- /dev/null +++ b/triqs/python_tools/pyref.hpp @@ -0,0 +1,62 @@ +#pragma once +#include + +namespace triqs { +namespace py_tools { + + //--------------------- pyref ----------------------------- + + // a little class to hold an owned ref, make sure it is decref at destruction + class pyref { + PyObject *ob = NULL; + + public: + pyref() = default; + pyref(PyObject *new_ref) : ob(new_ref) {} + ~pyref() { Py_XDECREF(ob); } + operator PyObject *() const { return ob; } + PyObject *new_ref() const { + Py_XINCREF(ob); + return ob; + } + explicit operator bool() const { return (ob != NULL); } + bool is_null() const { return ob == NULL; } + bool is_None() const { return ob == Py_None; } + + pyref attr(const char *s) { + return (ob ? PyObject_GetAttrString(ob, s) : NULL); + } // NULL : pass the error in chain call x.attr().attr().... + + pyref operator()(PyObject *a1) { + return (ob ? PyObject_CallFunctionObjArgs(ob, a1, NULL) : NULL); + } // NULL : pass the error in chain call x.attr().attr().... + + pyref operator()(PyObject *a1, PyObject *a2) { + return (ob ? PyObject_CallFunctionObjArgs(ob, a1, a2, NULL) : NULL); + } // NULL : pass the error in chain call x.attr().attr().... + + pyref(pyref const &p) { + ob = p.ob; + Py_XINCREF(ob); + } + pyref(pyref &&p) { + ob = p.ob; + p.ob = NULL; + } + pyref &operator=(pyref const &) = delete; + pyref &operator=(pyref &&p) { + ob = p.ob; + p.ob = NULL; + return *this; + } + static pyref module(std::string const &module_name) { return PyImport_ImportModule(module_name.c_str()); } + static pyref string(std::string const &s) { return PyString_FromString(s.c_str()); } + }; + + inline pyref borrowed(PyObject *ob) { + Py_XINCREF(ob); + return {ob}; + } +} +} + diff --git a/triqs/python_tools/wrapper_tools.hpp b/triqs/python_tools/wrapper_tools.hpp index 618c10af..6dfe7217 100644 --- a/triqs/python_tools/wrapper_tools.hpp +++ b/triqs/python_tools/wrapper_tools.hpp @@ -5,6 +5,7 @@ #include #include #include +#include "./pyref.hpp" #pragma clang diagnostic ignored "-Wdeprecated-writable-strings" #pragma GCC diagnostic ignored "-Wwrite-strings" @@ -26,33 +27,6 @@ namespace triqs { namespace py_tools { -//--------------------- pyref ----------------------------- - -// a little class to hold an owned ref, make sure it is decref at destruction -class pyref { - PyObject * ob = NULL; - public: - pyref() = default; - pyref(PyObject *new_ref) : ob(new_ref){} - ~pyref() { Py_XDECREF(ob);} - operator PyObject *() const { return ob;} - PyObject * new_ref() const { Py_XINCREF(ob); return ob;} - explicit operator bool() const { return (ob!=NULL);} - bool is_null() const { return ob==NULL;} - bool is_None() const { return ob==Py_None;} - pyref attr(const char * s) { return (ob ? PyObject_GetAttrString(ob,s) : NULL);} // NULL : pass the error in chain call x.attr().attr().... - pyref operator()(PyObject * a1) { return (ob ? PyObject_CallFunctionObjArgs(ob,a1,NULL) : NULL);} // NULL : pass the error in chain call x.attr().attr().... - pyref operator()(PyObject * a1,PyObject * a2) { return (ob ? PyObject_CallFunctionObjArgs(ob,a1,a2,NULL) : NULL);} // NULL : pass the error in chain call x.attr().attr().... - pyref(pyref const&p) {ob = p.ob; Py_XINCREF(ob);} - pyref(pyref && p){ ob = p.ob; p.ob=NULL;} - pyref& operator =(pyref const&) = delete; - pyref& operator =(pyref &&p) {ob = p.ob; p.ob=NULL; return *this;} - static pyref module(std::string const &module_name) { return PyImport_ImportModule(module_name.c_str()); } - static pyref string(std::string const &s) { return PyString_FromString(s.c_str());} -}; - - inline pyref borrowed(PyObject * ob) { Py_XINCREF(ob); return {ob};} - //--------------------- py_converters ----------------------------- // default version for a wrapped type. To be specialized later.