222 lines
5.1 KiB
C
222 lines
5.1 KiB
C
/** \ingroup py_c
|
|
* \file python/rpmtd-py.c
|
|
*/
|
|
|
|
#include "rpmsystem-py.h"
|
|
#include <rpm/rpmtd.h>
|
|
#include <rpm/header.h>
|
|
#include "rpmtd-py.h"
|
|
#include "header-py.h"
|
|
|
|
/*
|
|
* Convert single tag data item to python object of suitable type
|
|
*/
|
|
PyObject * rpmtd_ItemAsPyobj(rpmtd td, rpmTagClass tclass)
|
|
{
|
|
PyObject *res = NULL;
|
|
|
|
switch (tclass) {
|
|
case RPM_STRING_CLASS:
|
|
res = PyBytes_FromString(rpmtdGetString(td));
|
|
break;
|
|
case RPM_NUMERIC_CLASS:
|
|
res = PyLong_FromLongLong(rpmtdGetNumber(td));
|
|
break;
|
|
case RPM_BINARY_CLASS:
|
|
res = PyBytes_FromStringAndSize(td->data, td->count);
|
|
break;
|
|
default:
|
|
PyErr_SetString(PyExc_KeyError, "unknown data type");
|
|
break;
|
|
}
|
|
return res;
|
|
}
|
|
|
|
PyObject *rpmtd_AsPyobj(rpmtd td)
|
|
{
|
|
PyObject *res = NULL;
|
|
int array = (rpmTagGetReturnType(td->tag) == RPM_ARRAY_RETURN_TYPE);
|
|
rpmTagClass tclass = rpmtdClass(td);
|
|
|
|
if (!array && rpmtdCount(td) < 1) {
|
|
Py_RETURN_NONE;
|
|
}
|
|
|
|
if (array) {
|
|
int ix;
|
|
res = PyList_New(rpmtdCount(td));
|
|
if (!res) {
|
|
return NULL;
|
|
}
|
|
while ((ix = rpmtdNext(td)) >= 0) {
|
|
PyObject *item = rpmtd_ItemAsPyobj(td, tclass);
|
|
if (!item) {
|
|
Py_DECREF(res);
|
|
return NULL;
|
|
}
|
|
PyList_SET_ITEM(res, ix, item);
|
|
}
|
|
} else {
|
|
res = rpmtd_ItemAsPyobj(td, tclass);
|
|
}
|
|
return res;
|
|
}
|
|
|
|
#if 0
|
|
struct rpmtdObject_s {
|
|
PyObject_HEAD
|
|
PyObject *md_dict;
|
|
struct rpmtd_s td;
|
|
};
|
|
|
|
/* string format should never fail but do regular repr just in case it does */
|
|
static PyObject *rpmtd_str(rpmtdObject *s)
|
|
{
|
|
PyObject *res = NULL;
|
|
char *str = rpmtdFormat(&(s->td), RPMTD_FORMAT_STRING, NULL);
|
|
if (str) {
|
|
res = PyBytes_FromString(str);
|
|
free(str);
|
|
} else {
|
|
res = PyObject_Repr((PyObject *)s);
|
|
}
|
|
return res;
|
|
}
|
|
|
|
static PyObject *rpmtd_iternext(rpmtdObject *s)
|
|
{
|
|
PyObject *next = NULL;
|
|
|
|
if (rpmtdNext(&(s->td)) >= 0) {
|
|
Py_INCREF(s);
|
|
next = (PyObject*) s;
|
|
}
|
|
return next;
|
|
}
|
|
|
|
static PyObject *rpmtd_new(PyTypeObject * subtype, PyObject *args, PyObject *kwds)
|
|
{
|
|
rpmtdObject *s = NULL;
|
|
Header h = NULL;
|
|
rpmTagVal tag;
|
|
int raw = 0;
|
|
int noext = 0;
|
|
headerGetFlags flags = (HEADERGET_EXT | HEADERGET_ALLOC);
|
|
char *kwlist[] = { "header", "tag", "raw", "noext", NULL };
|
|
|
|
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O&O&|ii", kwlist,
|
|
hdrFromPyObject, &h, tagNumFromPyObject, &tag,
|
|
&raw, &noext))
|
|
return NULL;
|
|
|
|
if (raw) {
|
|
flags |= HEADERGET_RAW;
|
|
noext = 1; /* extensions with raw dont make sense */
|
|
}
|
|
if (noext) flags &= ~HEADERGET_EXT;
|
|
|
|
if ((s = (rpmtdObject *)subtype->tp_alloc(subtype, 0)) == NULL)
|
|
return NULL;
|
|
|
|
headerGet(h, tag, &(s->td), flags);
|
|
|
|
return (PyObject *) s;
|
|
}
|
|
|
|
static void rpmtd_dealloc(rpmtdObject * s)
|
|
{
|
|
rpmtdFreeData(&(s->td));
|
|
Py_TYPE(s)->tp_free((PyObject *)s);
|
|
}
|
|
|
|
static int rpmtd_length(rpmtdObject *s)
|
|
{
|
|
return rpmtdCount(&(s->td));
|
|
}
|
|
|
|
static PyMappingMethods rpmtd_as_mapping = {
|
|
(lenfunc) rpmtd_length, /* mp_length */
|
|
};
|
|
|
|
static PyMemberDef rpmtd_members[] = {
|
|
{ "type", T_INT, offsetof(rpmtdObject, td.type), READONLY, NULL },
|
|
{ NULL }
|
|
};
|
|
|
|
static PyObject *rpmtd_get_tag(rpmtdObject *s, void *closure)
|
|
{
|
|
return Py_BuildValue("i", rpmtdTag(&(s->td)));
|
|
}
|
|
|
|
static int rpmtd_set_tag(rpmtdObject *s, PyObject *value, void *closure)
|
|
{
|
|
rpmTagVal tag;
|
|
if (!tagNumFromPyObject(value, &tag)) return -1;
|
|
|
|
if (!rpmtdSetTag(&(s->td), tag)) {
|
|
PyErr_SetString(PyExc_ValueError, "incompatible tag for data");
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
static PyGetSetDef rpmtd_getseters[] = {
|
|
{ "tag", (getter)rpmtd_get_tag, (setter)rpmtd_set_tag, NULL },
|
|
{ NULL }
|
|
};
|
|
|
|
PyTypeObject rpmtd_Type = {
|
|
PyVarObject_HEAD_INIT(&PyType_Type, 0)
|
|
"rpm.td", /* tp_name */
|
|
sizeof(rpmtdObject), /* tp_size */
|
|
0, /* tp_itemsize */
|
|
(destructor) rpmtd_dealloc, /* tp_dealloc */
|
|
0, /* tp_print */
|
|
(getattrfunc)0, /* tp_getattr */
|
|
0, /* tp_setattr */
|
|
0, /* tp_compare */
|
|
0, /* tp_repr */
|
|
0, /* tp_as_number */
|
|
0, /* tp_as_sequence */
|
|
&rpmtd_as_mapping, /* tp_as_mapping */
|
|
0, /* tp_hash */
|
|
0, /* tp_call */
|
|
(reprfunc)rpmtd_str, /* tp_str */
|
|
PyObject_GenericGetAttr, /* tp_getattro */
|
|
PyObject_GenericSetAttr, /* tp_setattro */
|
|
0, /* tp_as_buffer */
|
|
Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, /* tp_flags */
|
|
0, /* tp_doc */
|
|
0, /* tp_traverse */
|
|
0, /* tp_clear */
|
|
0, /* tp_richcompare */
|
|
0, /* tp_weaklistoffset */
|
|
PyObject_SelfIter, /* tp_iter */
|
|
(iternextfunc)rpmtd_iternext, /* tp_iternext */
|
|
0, /* tp_methods */
|
|
rpmtd_members, /* tp_members */
|
|
rpmtd_getseters, /* tp_getset */
|
|
0, /* tp_base */
|
|
0, /* tp_dict */
|
|
0, /* tp_descr_get */
|
|
0, /* tp_descr_set */
|
|
0, /* tp_dictoffset */
|
|
0, /* tp_init */
|
|
0, /* tp_alloc */
|
|
rpmtd_new, /* tp_new */
|
|
0, /* tp_free */
|
|
0, /* tp_is_gc */
|
|
};
|
|
|
|
int rpmtdFromPyObject(PyObject *obj, rpmtd *td)
|
|
{
|
|
if (rpmtdObject_Check(obj)) {
|
|
*td = &(((rpmtdObject *)obj)->td);
|
|
return 1;
|
|
} else {
|
|
PyErr_SetString(PyExc_TypeError, "rpm.td type expected");
|
|
return 0;
|
|
}
|
|
}
|
|
#endif
|