- Main Page
- Related Pages
- Modules
- Data Structures
- Files

- File List
- Globals

# python/rpmps-py.c

Go to the documentation of this file.

    00001
    00004 /*@-modunconnomods -evalorderuncon @*/
    00005
    00006 #include "system.h"
    00007
    00008 #include <rpmio.h>
    00009 #include <rpmcb.h>              /* XXX fnpyKey */
    00010 #define _RPMPS_INTERNAL /* XXX rpmps needs iterator */
    00011 #include <rpmlib.h>
    00012
    00013 #include "rpmdebug-py.c"
    00014
    00015 #include "rpmps-py.h"
    00016
    00017 #include "debug.h"
    00018
    00019 /*@access FILE @*/
    00020 /*@access rpmps @*/
    00021 /*@access rpmProblem @*/
    00022
    00023 static PyObject *
    00024 rpmps_iter(rpmpsObject * s)
    00025         /*@modifies s @*/
    00026 {
    00027 if (_rpmps_debug < 0)
    00028 fprintf(stderr, "*** rpmps_iter(%p)\n", s);
    00029     s->psi = rpmpsInitIterator(s->ps);
    00030     Py_INCREF(s);
    00031     return (PyObject *)s;
    00032 }
    00033
    00034 /*@null@*/
    00035 static PyObject *
    00036 rpmps_iternext(rpmpsObject * s)
    00037         /*@modifies s @*/
    00038 {
    00039     PyObject * result = NULL;
    00040
    00041 if (_rpmps_debug < 0)
    00042 fprintf(stderr, "*** rpmps_iternext(%p) ps %p psi %p\n", s, s->ps, s->psi);
    00043
    00044     /* Reset loop indices on 1st entry. */
    00045     if (s->psi == NULL)
    00046         s->psi = rpmpsInitIterator(s->ps);
    00047
    00048     /* If more to do, return a problem set string. */
    00049     if (rpmpsNextIterator(s->psi) >= 0)
    00050         result = Py_BuildValue("s", rpmProblemString(rpmpsProblem(s->psi)));
    00051     else
    00052         s->psi = rpmpsFreeIterator(s->psi);
    00053
    00054     return result;
    00055 }
    00056
    00063
    00064 /*@null@*/
    00065 static PyObject *
    00066 rpmps_Debug(/*@unused@*/ rpmpsObject * s, PyObject * args, PyObject * kwds)
    00067         /*@globals _Py_NoneStruct @*/
    00068         /*@modifies _Py_NoneStruct @*/
    00069 {
    00070     char * kwlist[] = {"debugLevel", NULL};
    00071
    00072     if (!PyArg_ParseTupleAndKeywords(args, kwds, "i", kwlist, &_rpmps_debug))
    00073         return NULL;
    00074
    00075     Py_INCREF(Py_None);
    00076     return Py_None;
    00077 }
    00078
    00079 static int
    00080 rpmps_Append(rpmpsObject * s, PyObject * value)
    00081 {
    00082     char *pkgNEVR, *altNEVR, *str1;
    00083     unsigned long ulong1;
    00084     int ignoreProblem;
    00085     rpmProblemType type;
    00086     fnpyKey key;
    00087
    00088     if (!PyArg_ParseTuple(value, "ssOiisN:rpmps value tuple",
    00089                         &pkgNEVR, &altNEVR, &key,
    00090                         &type, &ignoreProblem, &str1,
    00091                         &ulong1))
    00092     {
    00093         return -1;
    00094     }
    00095     rpmpsAppend(s->ps, type, pkgNEVR, key, str1, NULL, altNEVR, ulong1);
    00096     return 0;
    00097 }
    00098
    00101 /*@-fullinitblock@*/
    00102 /*@unchecked@*/ /*@observer@*/
    00103 static struct PyMethodDef rpmps_methods[] = {
    00104  {"Debug",      (PyCFunction)rpmps_Debug,       METH_VARARGS|METH_KEYWORDS,
    00105         NULL},
    00106  {"Append",     (PyCFunction)rpmps_Append,      METH_VARARGS|METH_KEYWORDS,
    00107         NULL},
    00108  {NULL,         NULL}           /* sentinel */
    00109 };
    00110 /*@=fullinitblock@*/
    00111
    00112 /* ---------- */
    00113
    00114 static void
    00115 rpmps_dealloc(rpmpsObject * s)
    00116         /*@modifies s @*/
    00117 {
    00118 if (_rpmps_debug < 0)
    00119 fprintf(stderr, "*** rpmps_dealloc(%p)\n", s);
    00120     if (s) {
    00121         s->ps = rpmpsFree(s->ps);
    00122         PyObject_Del(s);
    00123     }
    00124 }
    00125
    00126 static int
    00127 rpmps_print(rpmpsObject * s, FILE * fp, /*@unused@*/ int flags)
    00128         /*@globals fileSystem @*/
    00129         /*@modifies s, fp, fileSystem @*/
    00130 {
    00131 if (_rpmps_debug < 0)
    00132 fprintf(stderr, "*** rpmps_print(%p,%p,%x)\n", s, (void *)fp, flags);
    00133     if (s && s->ps)
    00134         rpmpsPrint(fp, s->ps);
    00135     return 0;
    00136 }
    00137
    00138 static PyObject * rpmps_getattro(PyObject * o, PyObject * n)
    00139         /*@*/
    00140 {
    00141 if (_rpmps_debug < 0)
    00142 fprintf(stderr, "*** rpmps_getattro(%p,%p)\n", o, n);
    00143     return PyObject_GenericGetAttr(o, n);
    00144 }
    00145
    00146 static int rpmps_setattro(PyObject * o, PyObject * n, PyObject * v)
    00147         /*@*/
    00148 {
    00149 if (_rpmps_debug < 0)
    00150 fprintf(stderr, "*** rpmps_setattro(%p,%p,%p)\n", o, n, v);
    00151     return PyObject_GenericSetAttr(o, n, v);
    00152 }
    00153
    00154 static int
    00155 rpmps_length(rpmpsObject * s)
    00156         /*@*/
    00157 {
    00158     int rc;
    00159     rc = rpmpsNumProblems(s->ps);
    00160 if (_rpmps_debug < 0)
    00161 fprintf(stderr, "*** rpmps_length(%p) rc %d\n", s, rc);
    00162     return rc;
    00163 }
    00164
    00165 /*@null@*/
    00166 static PyObject *
    00167 rpmps_subscript(rpmpsObject * s, PyObject * key)
    00168         /*@*/
    00169 {
    00170     PyObject * result = NULL;
    00171     rpmpsi psi;
    00172     int ix;
    00173     int i;
    00174
    00175     if (!PyInt_Check(key)) {
    00176 if (_rpmps_debug < 0)
    00177 fprintf(stderr, "*** rpmps_subscript(%p[%s],%p[%s])\n", s, lbl(s), key, lbl(key));
    00178         PyErr_SetString(PyExc_TypeError, "integer expected");
    00179         return NULL;
    00180     }
    00181
    00182     ix = (int) PyInt_AsLong(key);
    00183     /* XXX range check */
    00184
    00185     psi = rpmpsInitIterator(s->ps);
    00186     while ((i = rpmpsNextIterator(psi)) >= 0) {
    00187         if (i != ix)
    00188             continue;
    00189         result = Py_BuildValue("s", rpmProblemString(rpmpsProblem(psi)));
    00190 if (_rpmps_debug < 0)
    00191 fprintf(stderr, "*** rpmps_subscript(%p,%p) %s\n", s, key, PyString_AsString(result));
    00192         break;
    00193     }
    00194     psi = rpmpsFreeIterator(psi);
    00195
    00196     return result;
    00197 }
    00198
    00199 #define PERMIT_RPMPS_SUBSCRIPT  /* XXX likely buggy */
    00200 #if defined(PERMIT_RPMPS_SUBSCRIPT)
    00201 static int
    00202 rpmps_ass_sub(rpmpsObject * s, PyObject * key, PyObject * value)
    00203         /*@modifies s @*/
    00204 {
    00205     rpmps ps;
    00206     int ix;
    00207
    00208     if (!PyArg_Parse(key, "i:ass_sub", &ix)) {
    00209         PyErr_SetString(PyExc_TypeError, "rpmps key type must be integer");
    00210         return -1;
    00211     }
    00212
    00213     /* XXX get rid of negative indices */
    00214     if (ix < 0) ix = -ix;
    00215
    00216     ps = s->ps;
    00217
    00218 if (_rpmps_debug < 0)
    00219 fprintf(stderr, "*** rpmps_ass_sub(%p[%s],%p[%s],%p[%s]) ps %p[%d:%d:%d]\n", s, lbl(s), key, lbl(key), value, lbl(value), ps, ix, ps->numProblems, ps->numProblemsAlloced);
    00220
    00221     if (value == NULL) {
    00222         if (ix < ps->numProblems) {
    00223             rpmProblem op = ps->probs + ix;
    00224
    00225             op->pkgNEVR = _free(op->pkgNEVR);
    00226             op->altNEVR = _free(op->altNEVR);
    00227             op->str1 = _free(op->str1);
    00228
    00229             if ((ix+1) == ps->numProblems)
    00230                 memset(op, 0, sizeof(*op));
    00231             else
    00232                 memmove(op, op+1, (ps->numProblems - ix) * sizeof(*op));
    00233             if (ps->numProblems > 0)
    00234                 ps->numProblems--;
    00235         }
    00236     } else {
    00237         rpmProblem p = memset(alloca(sizeof(*p)), 0, sizeof(*p));
    00238         unsigned long ulong1 = p->ulong1;
    00239
    00240         if (!PyArg_ParseTuple(value, "ssOiisN:rpmps value tuple",
    00241                                 &p->pkgNEVR, &p->altNEVR, &p->key,
    00242                                 &p->type, &p->ignoreProblem, &p->str1,
    00243                                 &ulong1))
    00244         {
    00245             return -1;
    00246         }
    00247
    00248 /*@-branchstate@*/
    00249         if (ix >= ps->numProblems) {
    00250             /* XXX force append for indices out of range. */
    00251             rpmpsAppend(s->ps, p->type, p->pkgNEVR, p->key,
    00252                 p->str1, NULL, p->altNEVR, ulong1);
    00253         } else {
    00254             rpmProblem op = ps->probs + ix;
    00255
    00256             op->pkgNEVR = _free(op->pkgNEVR);
    00257             op->altNEVR = _free(op->altNEVR);
    00258             op->str1 = _free(op->str1);
    00259
    00260             p->pkgNEVR = (p->pkgNEVR && *p->pkgNEVR ? xstrdup(p->pkgNEVR) : NULL);
    00261             p->altNEVR = (p->altNEVR && *p->altNEVR ? xstrdup(p->altNEVR) : NULL);
    00262             p->str1 = (p->str1 && *p->str1 ? xstrdup(p->str1) : NULL);
    00263
    00264             *op = *p;   /* structure assignment */
    00265         }
    00266 /*@=branchstate@*/
    00267     }
    00268
    00269     return 0;
    00270 }
    00271 #endif
    00272
    00273 static PyMappingMethods rpmps_as_mapping = {
    00274         (inquiry) rpmps_length,         /* mp_length */
    00275         (binaryfunc) rpmps_subscript,   /* mp_subscript */
    00276 #if defined(PERMIT_RPMPS_SUBSCRIPT)
    00277         (objobjargproc) rpmps_ass_sub,  /* mp_ass_subscript */
    00278 #endif
    00279 };
    00280
    00283 static int rpmps_init(rpmpsObject * s, PyObject *args, PyObject *kwds)
    00284         /*@modifies s @*/
    00285 {
    00286     char * kwlist[] = {NULL};
    00287
    00288 if (_rpmps_debug < 0)
    00289 fprintf(stderr, "*** rpmps_init(%p,%p,%p)\n", s, args, kwds);
    00290
    00291     if (!PyArg_ParseTupleAndKeywords(args, kwds, ":rpmps_init", kwlist))
    00292         return -1;
    00293
    00294     s->ps = rpmpsCreate();
    00295     s->psi = NULL;
    00296
    00297     return 0;
    00298 }
    00299
    00302 static void rpmps_free(/*@only@*/ rpmpsObject * s)
    00303         /*@modifies s @*/
    00304 {
    00305 if (_rpmps_debug)
    00306 fprintf(stderr, "%p -- ps %p\n", s, s->ps);
    00307     s->ps = rpmpsFree(s->ps);
    00308
    00309     PyObject_Del((PyObject *)s);
    00310 }
    00311
    00314 static PyObject * rpmps_alloc(PyTypeObject * subtype, int nitems)
    00315         /*@*/
    00316 {
    00317     PyObject * s = PyType_GenericAlloc(subtype, nitems);
    00318
    00319 if (_rpmps_debug < 0)
    00320 fprintf(stderr, "*** rpmps_alloc(%p,%d) ret %p\n", subtype, nitems, s);
    00321     return s;
    00322 }
    00323
    00326 /*@null@*/
    00327 static PyObject * rpmps_new(PyTypeObject * subtype, PyObject *args, PyObject *kwds)
    00328         /*@*/
    00329 {
    00330     rpmpsObject * s = (void *) PyObject_New(rpmpsObject, subtype);
    00331
    00332     /* Perform additional initialization. */
    00333     if (rpmps_init(s, args, kwds) < 0) {
    00334         rpmps_free(s);
    00335         return NULL;
    00336     }
    00337
    00338 if (_rpmps_debug)
    00339 fprintf(stderr, "%p ++ ps %p\n", s, s->ps);
    00340
    00341     return (PyObject *)s;
    00342 }
    00343
    00346 /*@unchecked@*/ /*@observer@*/
    00347 static char rpmps_doc[] =
    00348 "";
    00349
    00350 /*@-fullinitblock@*/
    00351 PyTypeObject rpmps_Type = {
    00352         PyObject_HEAD_INIT(&PyType_Type)
    00353         0,                              /* ob_size */
    00354         "rpm.ps",                       /* tp_name */
    00355         sizeof(rpmpsObject),            /* tp_basicsize */
    00356         0,                              /* tp_itemsize */
    00357         /* methods */
    00358         (destructor) rpmps_dealloc,     /* tp_dealloc */
    00359         (printfunc) rpmps_print,        /* tp_print */
    00360         (getattrfunc)0,                 /* tp_getattr */
    00361         (setattrfunc)0,                 /* tp_setattr */
    00362         (cmpfunc)0,                     /* tp_compare */
    00363         (reprfunc)0,                    /* tp_repr */
    00364         0,                              /* tp_as_number */
    00365         0,                              /* tp_as_sequence */
    00366         &rpmps_as_mapping,              /* tp_as_mapping */
    00367         (hashfunc)0,                    /* tp_hash */
    00368         (ternaryfunc)0,                 /* tp_call */
    00369         (reprfunc)0,                    /* tp_str */
    00370         (getattrofunc) rpmps_getattro,  /* tp_getattro */
    00371         (setattrofunc) rpmps_setattro,  /* tp_setattro */
    00372         0,                              /* tp_as_buffer */
    00373         Py_TPFLAGS_DEFAULT,             /* tp_flags */
    00374         rpmps_doc,                      /* tp_doc */
    00375 #if Py_TPFLAGS_HAVE_ITER
    00376         0,                              /* tp_traverse */
    00377         0,                              /* tp_clear */
    00378         (richcmpfunc)0,                 /* tp_richcompare */
    00379         0,                              /* tp_weaklistoffset */
    00380         (getiterfunc) rpmps_iter,       /* tp_iter */
    00381         (iternextfunc) rpmps_iternext,  /* tp_iternext */
    00382         rpmps_methods,                  /* tp_methods */
    00383         0,                              /* tp_members */
    00384         0,                              /* tp_getset */
    00385         0,                              /* tp_base */
    00386         0,                              /* tp_dict */
    00387         0,                              /* tp_descr_get */
    00388         0,                              /* tp_descr_set */
    00389         0,                              /* tp_dictoffset */
    00390         (initproc) rpmps_init,          /* tp_init */
    00391         (allocfunc) rpmps_alloc,        /* tp_alloc */
    00392         (newfunc) rpmps_new,            /* tp_new */
    00393         (freefunc) rpmps_free,          /* tp_free */
    00394         0,                              /* tp_is_gc */
    00395 #endif
    00396 };
    00397 /*@=fullinitblock@*/
    00398
    00399 /* ---------- */
    00400
    00401 rpmps psFromPs(rpmpsObject * s)
    00402 {
    00403     return s->ps;
    00404 }
    00405
    00406 rpmpsObject *
    00407 rpmps_Wrap(rpmps ps)
    00408 {
    00409     rpmpsObject * s = PyObject_New(rpmpsObject, &rpmps_Type);
    00410
    00411     if (s == NULL)
    00412         return NULL;
    00413     s->ps = ps;
    00414     s->psi = NULL;
    00415     return s;
    00416 }
    00417 /*@=modunconnomods =evalorderuncon @*/