mirror of
https://github.com/python/cpython.git
synced 2024-11-28 08:20:55 +01:00
0e04eecdbf
And these can now be vectored through glue routines (by defining USE_TOOLBOX_OBJECT_GLUE) which will do the necessary imports, whereupon the module's init routine will tell the glue routine about the real conversion routine address and everything is fine again.
199 lines
4.8 KiB
Python
199 lines
4.8 KiB
Python
# This script will generate the Resources interface for Python.
|
|
# It uses the "bgen" package to generate C code.
|
|
# It execs the file resgen.py which contain the function definitions
|
|
# (resgen.py was generated by resscan.py, scanning the <Resources.h> header file).
|
|
|
|
from macsupport import *
|
|
|
|
|
|
class ResMixIn:
|
|
|
|
def checkit(self):
|
|
OutLbrace()
|
|
Output("OSErr _err = ResError();")
|
|
Output("if (_err != noErr) return PyMac_Error(_err);")
|
|
OutRbrace()
|
|
FunctionGenerator.checkit(self) # XXX
|
|
|
|
class ResFunction(ResMixIn, FunctionGenerator): pass
|
|
class ResMethod(ResMixIn, MethodGenerator): pass
|
|
|
|
RsrcChainLocation = Type("RsrcChainLocation", "h")
|
|
|
|
# includestuff etc. are imported from macsupport
|
|
|
|
includestuff = includestuff + """
|
|
#include <Resources.h>
|
|
#include <string.h>
|
|
|
|
#ifdef USE_TOOLBOX_OBJECT_GLUE
|
|
extern PyObject *_ResObj_New(Handle);
|
|
extern int _ResObj_Convert(PyObject *, Handle *);
|
|
extern PyObject *_OptResObj_New(Handle);
|
|
extern int _OptResObj_Convert(PyObject *, Handle *);
|
|
#define ResObj_New _ResObj_New
|
|
#define ResObj_Convert _ResObj_Convert
|
|
#define OptResObj_New _OptResObj_New
|
|
#define OptResObj_Convert _OptResObj_Convert
|
|
#endif
|
|
|
|
/* Function to dispose a resource, with a "normal" calling sequence */
|
|
static void
|
|
PyMac_AutoDisposeHandle(Handle h)
|
|
{
|
|
DisposeHandle(h);
|
|
}
|
|
"""
|
|
|
|
finalstuff = finalstuff + """
|
|
|
|
/* Alternative version of ResObj_New, which returns None for null argument */
|
|
PyObject *OptResObj_New(itself)
|
|
Handle itself;
|
|
{
|
|
if (itself == NULL) {
|
|
Py_INCREF(Py_None);
|
|
return Py_None;
|
|
}
|
|
return ResObj_New(itself);
|
|
}
|
|
|
|
OptResObj_Convert(v, p_itself)
|
|
PyObject *v;
|
|
Handle *p_itself;
|
|
{
|
|
PyObject *tmp;
|
|
|
|
if ( v == Py_None ) {
|
|
*p_itself = NULL;
|
|
return 1;
|
|
}
|
|
if (ResObj_Check(v))
|
|
{
|
|
*p_itself = ((ResourceObject *)v)->ob_itself;
|
|
return 1;
|
|
}
|
|
/* If it isn't a resource yet see whether it is convertible */
|
|
if ( (tmp=PyObject_CallMethod(v, "as_Resource", "")) ) {
|
|
*p_itself = ((ResourceObject *)tmp)->ob_itself;
|
|
Py_DECREF(tmp);
|
|
return 1;
|
|
}
|
|
PyErr_Clear();
|
|
PyErr_SetString(PyExc_TypeError, "Resource required");
|
|
return 0;
|
|
}
|
|
"""
|
|
|
|
initstuff = initstuff + """
|
|
PyMac_INIT_TOOLBOX_OBJECT_NEW(ResObj_New);
|
|
PyMac_INIT_TOOLBOX_OBJECT_CONVERT(ResObj_Convert);
|
|
PyMac_INIT_TOOLBOX_OBJECT_NEW(OptResObj_New);
|
|
PyMac_INIT_TOOLBOX_OBJECT_CONVERT(OptResObj_Convert);
|
|
"""
|
|
|
|
module = MacModule('Res', 'Res', includestuff, finalstuff, initstuff)
|
|
|
|
getattrHookCode = """
|
|
if (strcmp(name, "size") == 0)
|
|
return PyInt_FromLong(GetHandleSize(self->ob_itself));
|
|
if (strcmp(name, "data") == 0) {
|
|
PyObject *res;
|
|
char state;
|
|
state = HGetState(self->ob_itself);
|
|
HLock(self->ob_itself);
|
|
res = PyString_FromStringAndSize(
|
|
*self->ob_itself,
|
|
GetHandleSize(self->ob_itself));
|
|
HUnlock(self->ob_itself);
|
|
HSetState(self->ob_itself, state);
|
|
return res;
|
|
}
|
|
if (strcmp(name, "__members__") == 0)
|
|
return Py_BuildValue("[ss]", "data", "size");
|
|
"""
|
|
|
|
setattrCode = """
|
|
static int
|
|
ResObj_setattr(self, name, value)
|
|
ResourceObject *self;
|
|
char *name;
|
|
PyObject *value;
|
|
{
|
|
char *data;
|
|
long size;
|
|
|
|
if (strcmp(name, "data") != 0 || value == NULL )
|
|
return -1;
|
|
if ( !PyString_Check(value) )
|
|
return -1;
|
|
size = PyString_Size(value);
|
|
data = PyString_AsString(value);
|
|
/* XXXX Do I need the GetState/SetState calls? */
|
|
SetHandleSize(self->ob_itself, size);
|
|
if ( MemError())
|
|
return -1;
|
|
HLock(self->ob_itself);
|
|
memcpy((char *)*self->ob_itself, data, size);
|
|
HUnlock(self->ob_itself);
|
|
/* XXXX Should I do the Changed call immedeately? */
|
|
return 0;
|
|
}
|
|
"""
|
|
|
|
class ResDefinition(GlobalObjectDefinition):
|
|
|
|
def outputCheckNewArg(self):
|
|
Output("if (itself == NULL) return PyMac_Error(resNotFound);")
|
|
|
|
def outputCheckConvertArg(self):
|
|
# if it isn't a resource we may be able to coerce it
|
|
Output("if (!%s_Check(v))", self.prefix)
|
|
OutLbrace()
|
|
Output("PyObject *tmp;")
|
|
Output('if ( (tmp=PyObject_CallMethod(v, "as_Resource", "")) )')
|
|
OutLbrace()
|
|
Output("*p_itself = ((ResourceObject *)tmp)->ob_itself;")
|
|
Output("Py_DECREF(tmp);")
|
|
Output("return 1;")
|
|
OutRbrace()
|
|
Output("PyErr_Clear();")
|
|
OutRbrace()
|
|
|
|
def outputGetattrHook(self):
|
|
Output(getattrHookCode)
|
|
|
|
def outputSetattr(self):
|
|
Output(setattrCode)
|
|
|
|
def outputStructMembers(self):
|
|
GlobalObjectDefinition.outputStructMembers(self)
|
|
Output("void (*ob_freeit)(%s ptr);", self.itselftype)
|
|
|
|
def outputInitStructMembers(self):
|
|
GlobalObjectDefinition.outputInitStructMembers(self)
|
|
Output("it->ob_freeit = NULL;")
|
|
|
|
def outputCleanupStructMembers(self):
|
|
Output("if (self->ob_freeit && self->ob_itself)")
|
|
OutLbrace()
|
|
Output("self->ob_freeit(self->ob_itself);")
|
|
OutRbrace()
|
|
Output("self->ob_itself = NULL;")
|
|
|
|
|
|
resobject = ResDefinition('Resource', 'ResObj', 'Handle')
|
|
module.addobject(resobject)
|
|
|
|
functions = []
|
|
resmethods = []
|
|
|
|
execfile('resgen.py')
|
|
execfile('resedit.py')
|
|
|
|
for f in functions: module.add(f)
|
|
for f in resmethods: resobject.add(f)
|
|
|
|
SetOutputFileName('Resmodule.c')
|
|
module.generate()
|