R
Robin Becker
As part of some django usage I need to get some ReportLab C extensions into a
state where they can be safely used with mod_python.
Unfortunately we have C code that seems incompatible with mod_python and I'm
looking for ways to improve the situation.
Basically the main things that are wrong are all privately cached copies of
python variables. This sample code
static PyObject *_pdfmetrics_fonts = NULL;
static PyObject *_pdfmetrics_ffar = NULL;
...........
if(!_pdfmetrics_fonts){
res = PyImport_ImportModule("reportlab.pdfbase.pdfmetrics");
if(!res) ERROR_EXIT();
_o1 = _GetAttrString(res,"_fonts");
if(!_o1) ERROR_EXIT();
_o2 = _GetAttrString(res,"findFontAndRegister");
if(!_o2) ERROR_EXIT();
_pdfmetrics_fonts = _o1;
_pdfmetrics_ffar = _o2;
Py_DECREF(res); _o1 = _o2 = res = NULL;
}
if((res = PyObject_GetItem(_pdfmetrics_fonts,fontName))) return res;
............
illustrates the general problem. If called first by interpreter A I'll get the
values from interpreter A. When later called by interpreter B I'll be using the
wrong values and _pdfmetrics_ffar can alter the wrong interpreter's data.
The functions themselves are fairly small, but may be called many times so
they're worth speeding up.
Is there a simple/cheap way for C code to cache these sorts of module level
globals on a per interpreter basis? Is there even a way to tell which
interpreter I'm being called in?
Anything too costly will probably bust any speedup. Luckily I don't think we
have too many of these cached variables so it's possible we may be able to get
away with just dropping the caching for some and eliminating others.
state where they can be safely used with mod_python.
Unfortunately we have C code that seems incompatible with mod_python and I'm
looking for ways to improve the situation.
Basically the main things that are wrong are all privately cached copies of
python variables. This sample code
static PyObject *_pdfmetrics_fonts = NULL;
static PyObject *_pdfmetrics_ffar = NULL;
...........
if(!_pdfmetrics_fonts){
res = PyImport_ImportModule("reportlab.pdfbase.pdfmetrics");
if(!res) ERROR_EXIT();
_o1 = _GetAttrString(res,"_fonts");
if(!_o1) ERROR_EXIT();
_o2 = _GetAttrString(res,"findFontAndRegister");
if(!_o2) ERROR_EXIT();
_pdfmetrics_fonts = _o1;
_pdfmetrics_ffar = _o2;
Py_DECREF(res); _o1 = _o2 = res = NULL;
}
if((res = PyObject_GetItem(_pdfmetrics_fonts,fontName))) return res;
............
illustrates the general problem. If called first by interpreter A I'll get the
values from interpreter A. When later called by interpreter B I'll be using the
wrong values and _pdfmetrics_ffar can alter the wrong interpreter's data.
The functions themselves are fairly small, but may be called many times so
they're worth speeding up.
Is there a simple/cheap way for C code to cache these sorts of module level
globals on a per interpreter basis? Is there even a way to tell which
interpreter I'm being called in?
Anything too costly will probably bust any speedup. Luckily I don't think we
have too many of these cached variables so it's possible we may be able to get
away with just dropping the caching for some and eliminating others.