Getting started with boost::python - Exception already!

Started by
12 comments, last by Ezbez 16 years, 10 months ago
Hi, I am trying to embed python with boost::python. Unfortunately, I've come unstuck already. Here's my code
	object main_module( ( handle<>( borrowed( PyImport_AddModule( "__main__" ) ) ) ) );

	object main_namespace = main_module.attr("__dict__");

	FILE* myPython = fopen( "myPython.py", "r" );

	handle<> ignored( ( PyRun_File( myPython, "myPython.py",
						Py_file_input, 
						main_namespace.ptr(), 
						main_namespace.ptr() ) ) );

	fclose( myPython );

and heres the exception: First-chance exception at 0x7c918fea in Server 20070601.exe: 0xC0000005: Access violation writing location 0x00000010. Unhandled exception at 0x7c918fea in Server 20070601.exe: 0xC0000005: Access violation writing location 0x00000010. What am I doing wrong? must be something simple :) Thanks! Simon EDIT: some info may help.... MSVC++ 2005 Express Boost 1.34 Python 2.52 [Edited by - sipickles on June 1, 2007 1:15:06 PM]
Advertisement
Doesn't the debugger point to the specific line it crashes on?
I've managed to make a little progress by using boost::python::exec_file, now available in boost 1.34.

Now I struggle to extract anything from a python function apart from std::string and int.

Here's what I am trying to do:

// C++python::dict global;python::object result = python::exec_file("myPython.py", global, global)lpython::object greet = global["greet"];std::string message = python::extract<std::string>(greet());// MYPYTHON.PYdef greet(self):    return "hello, world!"


The extract attempt gives 'error_already_set' exception.

Help!
If you run that stand-alone Python code, you'll see that it doesn't work, and raises an exception. Hint: that's not a function you've defined, that's a method.

(PS. Also copy and paste in your actual code, rather than typing it out separately, so that we can see if there are syntax errors that may contribute to the problem.)
Yes, you are right. I was foolishly copying code from the boost.org tutorials

Oh well! Guess I'll have to keep twiddling til I randomly hit upon the solution!

Here's the cut and paste code:

	try	{		// Run a python script in an empty environment.		python::dict global;		python::object result = python::exec_file("myPython.py", global, global);		int i= 0;		// Extract an object the script stored in the global dictionary.		i = python::extract<int>(global["number"]);		g_log->Log("success!! %d\n", i);		std::string animal = python::extract<std::string>(global["animal"]);		g_log->Log("animal == %s\n", animal.c_str());		// Create a reference to it.		python::object greet = global["greet"];		// Call it.		std::string message = python::extract<std::string>(greet);		g_log->Log("%s\n", message.c_str());	}	catch(python::error_already_set)	{		g_log->SYSTEM( "Python Error\n" );	}


number = 42animal = "aardvark"def greet():	return animal


it excepts on the line:

python::object greet = global["greet"];

I guess this means there is no greet object in the python global namespace...
It could mean anything. There'll be a way to get hold of that exception and find out what it means, so that would be worth looking into.
Though you seem to have gotten around this, you still might want to know. For some reason, PyRun_File can't take a regular FILE* for it's argument. I can't remember the actual reason. It's something about Python wanting one format of FILE but Windows has a different one. Put simply, you can't use PyRun_File. I'm not at home right now, but when I am, I'll try looking for where I found this.
Yeah, it depends whether the library was built with the same compiler as you are using. You can rebuild from source to overcome this, apparently!

Yes, yet another unfortunate side-effect of the Python C API being a mess.
Well, the solution turned out to be simple. Not sure I TOTALLY understand why, its like I had to instantiate a function, then extract the object produced:

	try	{		// Run a python script in an empty environment.		python::dict global;		python::object result = python::exec_file("myPython.py", global, global);		int i= 0;		// Extract an object the script stored in the global dictionary.		i = python::extract<int>(global["number"]);		g_log->Log("number = %d\n", i);		std::string animal = python::extract<std::string>(global["animal"]);		g_log->Log("string == %s\n", animal.c_str());		// Call it.		std::string message = python::extract<std::string>(global["passedFunc"]);		g_log->Log("%s\n", message.c_str());	}	catch(python::error_already_set)	{		g_log->SYSTEM( "Python Error\n" );	}


number = 42animal = "aardvark"def pythonFunc():	return "Hello from Python"passedFunc = pythonFunc()


Bingo! :P

This topic is closed to new replies.

Advertisement