I'm trying to create a script in python that sends data through a parallel port. I'm creating my own module in C language.
The problem is: when I try to execute my module, python crashes. No errors, no data, nothing. It simply closes.
This is my module:
#include <Python.h>
#include <sys/io.h>
#define BaseAddr 0x378
/*----------------------------------------------------------------------------------
Este es un módulo destinado a controlar el puerto paralelo.
Probablemente tenga que ser ejecutado como administrador.
Created by markmb
------------------------------------------------------------------------------------*/
static PyObject *
paralelo(PyObject *self, PyObject *args){
int pin;
ioperm(BaseAddr,3,1);
if (!PyArg_ParseTuple(args, "i", &pin))
return NULL;
outb(pin,BaseAddr);
ioperm(BaseAddr,3,0);
return 1
}
PyMethodDef methods[] = {
{"paralelo", paralelo, METH_VARARGS, "Sends data through a parallel port"},
{NULL, NULL, 0, NULL}
};
PyMODINIT_FUNC
initparalelo(void){
(void) Py_InitModule("paralelo", methods);
}
(It works without all python mess) I compile it through distutils and then, in terminal (using xubuntu), I put:
import paralelo
while True:
paralelo.paralelo(255)
And here, it goes out of python, it puts "markmb@..."
Thanks in advance!
Any code that you write using any compiled language like C, C++, or Java can be integrated or imported into another Python script. This code is considered as an "extension." A Python extension module is nothing more than a normal C library. On Unix machines, these libraries usually end in .
A file containing Python code, for example: test.py , is called a module, and its name would be test . There are various methods of writing modules, but the simplest way is to create a file with a . py extension which contains functions and variables.
Python allows the writer of a C extension module to define new types that can be manipulated from Python code, much like the built-in str and list types. The code for all extension types follows a pattern, but there are some details that you need to understand before you can get started.
Returning NULL to the python/c API indicates that an error has occurred. But since you didn't actually set an exception you get the error:
SystemError: error return without exception set
If you are trying to return None, use:
return Py_BuildValue("");
All python functions should return a PyObject, unless when they want to raise an exception, as explained: here http://docs.python.org/extending/extending.html#intermezzo-errors-and-exceptions
The error message you get SystemError: error return without exception set
, is trying to tell you that your function returned NULL (=error, raise an exception) but did not inform the python interpreter what exception you wanted to raise.
When you don't want to return a value from a python function you make it return None (which is same thing that happens if you in python code have a function that runs to the end or does a simple return without any value).
In the cpython api you do this by returning the Py_None object, and don't forget to increment its refcount. To help you not forgetting the refcount there is a macro to do it for you: http://docs.python.org/c-api/none.html#Py_RETURN_NONE.
So a function skeleton for a function returning nothing (=returning None) you look something like this:
static PyObject *
myfunction(PyObject *self, PyObject *args){
if (!PyArg_ParseTuple(args, "i", ...))
return NULL;
/* .... */
Py_RETURN_NONE;
}
Finally, for the record: there is a python module for doing the ioperm/outb calls already: http://pypi.python.org/pypi/portio
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With