source: trunk/ext/_syckmodule.c @ 14

Revision 14, 44.3 KB checked in by xi, 9 years ago (diff)

Add _syck.Seq and _syck.Map.

Line 
1
2#include <Python.h>
3#include <syck.h>
4
5/****************************************************************************
6 * Python 2.2 compatibility.
7 ****************************************************************************/
8
9#ifndef PyDoc_STR
10#define PyDoc_VAR(name)         static char name[]
11#define PyDoc_STR(str)          (str)
12#define PyDoc_STRVAR(name, str) PyDoc_VAR(name) = PyDoc_STR(str)
13#endif
14
15#ifndef PyMODINIT_FUNC
16#define PyMODINIT_FUNC  void
17#endif
18
19/****************************************************************************
20 * Global objects: _syck.error, 'scalar', 'seq', 'map',
21 * '1quote', '2quote', 'fold', 'literal', 'plain', '+', '-'.
22 ****************************************************************************/
23
24static PyObject *PySyck_Error;
25
26static PyObject *PySyck_ScalarKind;
27static PyObject *PySyck_SeqKind;
28static PyObject *PySyck_MapKind;
29
30static PyObject *PySyck_1QuoteStyle;
31static PyObject *PySyck_2QuoteStyle;
32static PyObject *PySyck_FoldStyle;
33static PyObject *PySyck_LiteralStyle;
34static PyObject *PySyck_PlainStyle;
35
36static PyObject *PySyck_StripChomp;
37static PyObject *PySyck_KeepChomp;
38
39/****************************************************************************
40 * The type _syck.Node.
41 ****************************************************************************/
42
43PyDoc_STRVAR(PySyckNode_doc,
44    "The base Node type\n\n"
45    "_syck.Node is an abstract type. It is a base type for _syck.Scalar,\n"
46    "_syck.Seq, and _syck.Map. You cannot create an instance of _syck.Node\n"
47    "directly. You may use _syck.Node for type checking.\n");
48
49typedef struct {
50    PyObject_HEAD
51    /* Common fields for all Node types: */
52    PyObject *value;    /* always an object */
53    PyObject *tag;      /* a string object or NULL */
54    PyObject *anchor;   /* a string object or NULL */
55} PySyckNodeObject;
56
57
58static int
59PySyckNode_clear(PySyckNodeObject *self)
60{
61    PyObject *tmp;
62
63    tmp = self->value;
64    self->value = NULL;
65    Py_XDECREF(tmp);
66
67    tmp = self->tag;
68    self->tag = NULL;
69    Py_XDECREF(tmp);
70
71    tmp = self->anchor;
72    self->value = NULL;
73    Py_XDECREF(tmp);
74
75    return 0;
76}
77
78static int
79PySyckNode_traverse(PySyckNodeObject *self, visitproc visit, void *arg)
80{
81    int ret;
82
83    if (self->value)
84        if ((ret = visit(self->value, arg)) != 0)
85            return ret;
86
87    if (self->tag)
88        if ((ret = visit(self->tag, arg)) != 0)
89            return ret;
90
91    if (self->anchor)
92        if ((ret = visit(self->anchor, arg)) != 0)
93            return ret;
94
95    return 0;
96}
97
98static void
99PySyckNode_dealloc(PySyckNodeObject *self)
100{
101    PySyckNode_clear(self);
102    self->ob_type->tp_free((PyObject *)self);
103}
104
105static PyObject *
106PySyckNode_getkind(PySyckNodeObject *self, PyObject **closure)
107{
108    Py_INCREF(*closure);
109    return *closure;
110}
111
112static PyObject *
113PySyckNode_getvalue(PySyckNodeObject *self, void *closure)
114{
115    Py_INCREF(self->value);
116    return self->value;
117}
118
119static PyObject *
120PySyckNode_gettag(PySyckNodeObject *self, void *closure)
121{
122    PyObject *value = self->tag ? self->tag : Py_None;
123    Py_INCREF(value);
124    return value;
125}
126
127static int
128PySyckNode_settag(PySyckNodeObject *self, PyObject *value, void *closure)
129{
130    if (!value) {
131        PyErr_SetString(PyExc_TypeError, "cannot delete 'tag'");
132        return -1;
133    }
134
135    if (value == Py_None) {
136        Py_XDECREF(self->tag);
137        self->tag = NULL;
138        return 0;
139    }
140
141    if (!PyString_Check(value)) {
142        PyErr_SetString(PyExc_TypeError, "'tag' must be a string");
143        return -1;
144    }
145
146    Py_XDECREF(self->tag);
147    Py_INCREF(value);
148    self->tag = value;
149
150    return 0;
151}
152
153static PyObject *
154PySyckNode_getanchor(PySyckNodeObject *self, void *closure)
155{
156    PyObject *value = self->anchor ? self->anchor : Py_None;
157    Py_INCREF(value);
158    return value;
159}
160
161static int
162PySyckNode_setanchor(PySyckNodeObject *self, PyObject *value, void *closure)
163{
164    if (!value) {
165        PyErr_SetString(PyExc_TypeError, "cannot delete 'anchor'");
166        return -1;
167    }
168
169    if (value == Py_None) {
170        Py_XDECREF(self->anchor);
171        self->anchor = NULL;
172        return 0;
173    }
174
175    if (!PyString_Check(value)) {
176        PyErr_SetString(PyExc_TypeError, "'anchor' must be a string");
177        return -1;
178    }
179
180    Py_XDECREF(self->anchor);
181    Py_INCREF(value);
182    self->anchor = value;
183
184    return 0;
185}
186
187static PyTypeObject PySyckNode_Type = {
188    PyObject_HEAD_INIT(NULL)
189    0,                                          /* ob_size */
190    "_syck.Node",                               /* tp_name */
191    sizeof(PySyckNodeObject),                   /* tp_basicsize */
192    0,                                          /* tp_itemsize */
193    (destructor)PySyckNode_dealloc,             /* tp_dealloc */
194    0,                                          /* tp_print */
195    0,                                          /* tp_getattr */
196    0,                                          /* tp_setattr */
197    0,                                          /* tp_compare */
198    0,                                          /* tp_repr */
199    0,                                          /* tp_as_number */
200    0,                                          /* tp_as_sequence */
201    0,                                          /* tp_as_mapping */
202    0,                                          /* tp_hash */
203    0,                                          /* tp_call */
204    0,                                          /* tp_str */
205    0,                                          /* tp_getattro */
206    0,                                          /* tp_setattro */
207    0,                                          /* tp_as_buffer */
208    Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE|Py_TPFLAGS_HAVE_GC,  /* tp_flags */
209    PySyckNode_doc,                             /* tp_doc */
210    (traverseproc)PySyckNode_traverse,          /* tp_traverse */
211    (inquiry)PySyckNode_clear,                  /* tp_clear */
212};
213
214/****************************************************************************
215 * The type _syck.Scalar.
216 ****************************************************************************/
217
218PyDoc_STRVAR(PySyckScalar_doc,
219    "Scalar(value='', tag=None, style=None, indent=0, width=0, chomp=None)\n"
220    "      -> a Scalar node\n\n"
221    "_syck.Scalar represents a scalar node in Syck parser and emitter\n"
222    "graphs. A scalar node points to a single string value.\n\n"
223    "Attributes:\n\n"
224    "kind -- always 'scalar'; read-only\n"
225    "value -- the node value, a string\n"
226    "tag -- the node tag; a string or None\n"
227    "anchor -- the name of the node anchor or None; read-only\n"
228    "style -- the node style; None (means literal or plain),\n"
229    "         '1quote', '2quote', 'fold', 'literal', 'plain'\n"
230    "indent -- indentation, an integer; 0 means default\n"
231    "width -- the preferred width; 0 means default\n"
232    "chomp -- None (clip), '-' (strip), or '+' (keep)\n");
233
234typedef struct {
235    PyObject_HEAD
236    /* Common fields for all Node types: */
237    PyObject *value;    /* always a string object */
238    PyObject *tag;      /* a string object or NULL */
239    PyObject *anchor;   /* a string object or NULL */
240    /* Scalar-specific fields: */
241    enum scalar_style style;
242    int indent;
243    int width;
244    char chomp;
245} PySyckScalarObject;
246
247static PyObject *
248PySyckScalar_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
249{
250    PySyckScalarObject *self;
251
252    self = (PySyckScalarObject *)type->tp_alloc(type, 0);
253    if (!self) return NULL;
254
255    self->value = PyString_FromString("");
256    if (!self->value) {
257        Py_DECREF(self);
258        return NULL;
259    }
260
261    self->tag = NULL;
262    self->anchor = NULL;
263    self->style = scalar_none;
264    self->indent = 0;
265    self->width = 0;
266    self->chomp = 0;
267
268    return (PyObject *)self;
269}
270
271static int
272PySyckScalar_setvalue(PySyckScalarObject *self, PyObject *value, void *closure)
273{
274    if (!value) {
275        PyErr_SetString(PyExc_TypeError, "cannot delete 'value'");
276        return -1;
277    }
278    if (!PyString_Check(value)) {
279        PyErr_SetString(PyExc_TypeError, "'value' must be a string");
280        return -1;
281    }
282
283    Py_DECREF(self->value);
284    Py_INCREF(value);
285    self->value = value;
286
287    return 0;
288}
289
290static PyObject *
291PySyckScalar_getstyle(PySyckScalarObject *self, void *closure)
292{
293    PyObject *value;
294
295    switch (self->style) {
296        case scalar_1quote: value = PySyck_1QuoteStyle; break;
297        case scalar_2quote: value = PySyck_2QuoteStyle; break;
298        case scalar_fold: value = PySyck_FoldStyle; break;
299        case scalar_literal: value = PySyck_LiteralStyle; break;
300        case scalar_plain: value = PySyck_PlainStyle; break;
301        default: value = Py_None;
302    }
303
304    Py_INCREF(value);
305    return value;
306}
307
308static int
309PySyckScalar_setstyle(PySyckScalarObject *self, PyObject *value, void *closure)
310{
311    char *str;
312
313    if (!value) {
314        PyErr_SetString(PyExc_TypeError, "cannot delete 'style'");
315        return -1;
316    }
317
318    if (value == Py_None) {
319        self->style = scalar_none;
320        return 0;
321    }
322
323    if (!PyString_Check(value)) {
324        PyErr_SetString(PyExc_TypeError, "'style' must be a string or None");
325        return -1;
326    }
327
328    str = PyString_AsString(value);
329    if (!str) return -1;
330
331    if (strcmp(str, "1quote") == 0)
332        self->style = scalar_1quote;
333    else if (strcmp(str, "2quote") == 0)
334        self->style = scalar_2quote;
335    else if (strcmp(str, "fold") == 0)
336        self->style = scalar_fold;
337    else if (strcmp(str, "literal") == 0)
338        self->style = scalar_literal;
339    else if (strcmp(str, "plain") == 0)
340        self->style = scalar_plain;
341    else {
342        PyErr_SetString(PyExc_TypeError, "unknown 'style'");
343        return -1;
344    }
345
346    return 0;
347}
348
349static PyObject *
350PySyckScalar_getindent(PySyckScalarObject *self, void *closure)
351{
352    return PyInt_FromLong(self->indent);
353}
354
355static int
356PySyckScalar_setindent(PySyckScalarObject *self, PyObject *value, void *closure)
357{
358    if (!value) {
359        PyErr_SetString(PyExc_TypeError, "cannot delete 'indent'");
360        return -1;
361    }
362
363    if (!PyInt_Check(value)) {
364        PyErr_SetString(PyExc_TypeError, "'indent' must be an integer");
365        return -1;
366    }
367
368    self->indent = PyInt_AS_LONG(value);
369
370    return 0;
371}
372
373static PyObject *
374PySyckScalar_getwidth(PySyckScalarObject *self, void *closure)
375{
376    return PyInt_FromLong(self->width);
377}
378
379static int
380PySyckScalar_setwidth(PySyckScalarObject *self, PyObject *value, void *closure)
381{
382    if (!value) {
383        PyErr_SetString(PyExc_TypeError, "cannot delete 'width'");
384        return -1;
385    }
386
387    if (!PyInt_Check(value)) {
388        PyErr_SetString(PyExc_TypeError, "'width' must be an integer");
389        return -1;
390    }
391
392    self->width = PyInt_AS_LONG(value);
393
394    return 0;
395}
396
397static PyObject *
398PySyckScalar_getchomp(PySyckScalarObject *self, void *closure)
399{
400    PyObject *value;
401
402    switch (self->chomp) {
403        case NL_CHOMP: value = PySyck_StripChomp; break;
404        case NL_KEEP: value = PySyck_KeepChomp; break;
405        default: value = Py_None;
406    }
407
408    Py_INCREF(value);
409    return value;
410}
411
412static int
413PySyckScalar_setchomp(PySyckScalarObject *self, PyObject *value, void *closure)
414{
415    char *str;
416
417    if (!value) {
418        PyErr_SetString(PyExc_TypeError, "cannot delete 'chomp'");
419        return -1;
420    }
421
422    if (value == Py_None) {
423        self->chomp = 0;
424        return 0;
425    }
426
427    if (!PyString_Check(value)) {
428        PyErr_SetString(PyExc_TypeError, "'chomp' must be '+', '-', or None");
429        return -1;
430    }
431
432    str = PyString_AsString(value);
433    if (!str) return -1;
434
435    if (strcmp(str, "-") == 0)
436        self->chomp = NL_CHOMP;
437    else if (strcmp(str, "+") == 0)
438        self->chomp = NL_KEEP;
439    else {
440        PyErr_SetString(PyExc_TypeError, "'chomp' must be '+', '-', or None");
441        return -1;
442    }
443
444    return 0;
445}
446
447static int
448PySyckScalar_init(PySyckScalarObject *self, PyObject *args, PyObject *kwds)
449{
450    PyObject *value = NULL;
451    PyObject *tag = NULL;
452    PyObject *anchor = NULL;
453    PyObject *style = NULL;
454    PyObject *indent = NULL;
455    PyObject *width = NULL;
456    PyObject *chomp = NULL;
457
458    static char *kwdlist[] = {"value", "tag", "anchor",
459        "style", "indent", "width", "chomp", NULL};
460
461    if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OOOOOOO", kwdlist,
462                &value, &tag, &anchor, &style, &indent, &width, &chomp))
463        return -1;
464
465    if (value && PySyckScalar_setvalue(self, value, NULL) < 0)
466        return -1;
467
468    if (tag && PySyckNode_settag((PySyckNodeObject *)self, tag, NULL) < 0)
469        return -1;
470
471    if (anchor && PySyckNode_setanchor((PySyckNodeObject *)self, anchor, NULL) < 0)
472        return -1;
473
474    if (style && PySyckScalar_setstyle(self, style, NULL) < 0)
475        return -1;
476
477    if (indent && PySyckScalar_setindent(self, indent, NULL) < 0)
478        return -1;
479
480    if (width && PySyckScalar_setwidth(self, width, NULL) < 0)
481        return -1;
482
483    if (chomp && PySyckScalar_setchomp(self, chomp, NULL) < 0)
484        return -1;
485
486    return 0;
487}
488
489static PyGetSetDef PySyckScalar_getsetters[] = {
490    {"kind", (getter)PySyckNode_getkind, NULL,
491        "the node kind", &PySyck_ScalarKind},
492    {"value", (getter)PySyckNode_getvalue, (setter)PySyckScalar_setvalue,
493        "the node value", NULL},
494    {"tag", (getter)PySyckNode_gettag, (setter)PySyckNode_settag,
495        "the node tag", NULL},
496    {"anchor", (getter)PySyckNode_getanchor, (setter)PySyckNode_setanchor,
497        "the node anchor", NULL},
498    {"style", (getter)PySyckScalar_getstyle, (setter)PySyckScalar_setstyle,
499        "the node style", NULL},
500    {"indent", (getter)PySyckScalar_getindent, (setter)PySyckScalar_setindent,
501        "the field indentation", NULL},
502    {"width", (getter)PySyckScalar_getwidth, (setter)PySyckScalar_setwidth,
503        "the field width", NULL},
504    {"chomp", (getter)PySyckScalar_getchomp, (setter)PySyckScalar_setchomp,
505        "the chomping method", NULL},
506    {NULL}  /* Sentinel */
507};
508
509static PyTypeObject PySyckScalar_Type = {
510    PyObject_HEAD_INIT(NULL)
511    0,                                          /* ob_size */
512    "_syck.Scalar",                             /* tp_name */
513    sizeof(PySyckScalarObject),                 /* tp_basicsize */
514    0,                                          /* tp_itemsize */
515    0,                                          /* tp_dealloc */
516    0,                                          /* tp_print */
517    0,                                          /* tp_getattr */
518    0,                                          /* tp_setattr */
519    0,                                          /* tp_compare */
520    0,                                          /* tp_repr */
521    0,                                          /* tp_as_number */
522    0,                                          /* tp_as_sequence */
523    0,                                          /* tp_as_mapping */
524    0,                                          /* tp_hash */
525    0,                                          /* tp_call */
526    0,                                          /* tp_str */
527    0,                                          /* tp_getattro */
528    0,                                          /* tp_setattro */
529    0,                                          /* tp_as_buffer */
530    Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE,     /* tp_flags */
531    PySyckScalar_doc,                           /* tp_doc */
532    0,                                          /* tp_traverse */
533    0,                                          /* tp_clear */
534    0,                                          /* tp_richcompare */
535    0,                                          /* tp_weaklistoffset */
536    0,                                          /* tp_iter */
537    0,                                          /* tp_iternext */
538    0,                                          /* tp_methods */
539    0,                                          /* tp_members */
540    PySyckScalar_getsetters,                    /* tp_getset */
541    &PySyckNode_Type,                           /* tp_base */
542    0,                                          /* tp_dict */
543    0,                                          /* tp_descr_get */
544    0,                                          /* tp_descr_set */
545    0,                                          /* tp_dictoffset */
546    (initproc)PySyckScalar_init,                /* tp_init */
547    0,                                          /* tp_alloc */
548    PySyckScalar_new,                           /* tp_new */
549};
550
551/****************************************************************************
552 * The type _syck.Seq.
553 ****************************************************************************/
554
555PyDoc_STRVAR(PySyckSeq_doc,
556    "Seq(value=[], tag=None, inline=False) -> a Seq node\n\n"
557    "_syck.Seq represents a sequence node in Syck parser and emitter\n"
558    "graphs. A sequence node points to an ordered set of subnodes.\n\n"
559    "Attributes:\n\n"
560    "kind -- always 'seq'; read-only\n"
561    "value -- the node value, a list\n"
562    "tag -- the node tag; a string or None\n"
563    "anchor -- the name of the node anchor or None; read-only\n"
564    "inline -- is the node inline? False or True\n");
565
566typedef struct {
567    PyObject_HEAD
568    /* Common fields for all Node types: */
569    PyObject *value;    /* always an object */
570    PyObject *tag;      /* a string object or NULL */
571    PyObject *anchor;   /* a string object or NULL */
572    /* Seq-specific fields: */
573    enum seq_style style;
574} PySyckSeqObject;
575
576static PyObject *
577PySyckSeq_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
578{
579    PySyckSeqObject *self;
580
581    self = (PySyckSeqObject *)type->tp_alloc(type, 0);
582    if (!self) return NULL;
583
584    self->value = PyList_New(0);
585    if (!self->value) {
586        Py_DECREF(self);
587        return NULL;
588    }
589
590    self->tag = NULL;
591    self->anchor = NULL;
592    self->style = seq_none;
593
594    return (PyObject *)self;
595}
596
597static int
598PySyckSeq_setvalue(PySyckSeqObject *self, PyObject *value, void *closure)
599{
600    if (!value) {
601        PyErr_SetString(PyExc_TypeError, "cannot delete 'value'");
602        return -1;
603    }
604    if (!PySequence_Check(value)) { /* PySequence_Check always succeeds */
605        PyErr_SetString(PyExc_TypeError, "'value' must be a sequence");
606        return -1;
607    }
608
609    Py_DECREF(self->value);
610    Py_INCREF(value);
611    self->value = value;
612
613    return 0;
614}
615
616static PyObject *
617PySyckSeq_getinline(PySyckSeqObject *self, void *closure)
618{
619    PyObject *value = (self->style == seq_inline) ? Py_True : Py_False;
620
621    Py_INCREF(value);
622    return value;
623}
624
625static int
626PySyckSeq_setinline(PySyckSeqObject *self, PyObject *value, void *closure)
627{
628    if (!value) {
629        PyErr_SetString(PyExc_TypeError, "cannot delete 'inline'");
630        return -1;
631    }
632
633    if (!PyInt_Check(value)) {
634        PyErr_SetString(PyExc_TypeError, "'inline' must be a Boolean object");
635        return -1;
636    }
637
638    self->style = PyInt_AS_LONG(value) ? seq_inline : seq_none;
639
640    return 0;
641}
642
643static int
644PySyckSeq_init(PySyckSeqObject *self, PyObject *args, PyObject *kwds)
645{
646    PyObject *value = NULL;
647    PyObject *tag = NULL;
648    PyObject *anchor = NULL;
649    PyObject *inline_ = NULL;
650
651    static char *kwdlist[] = {"value", "tag", "anchor", "inline", NULL};
652
653    if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OOOO", kwdlist,
654                &value, &tag, &anchor, &inline_))
655        return -1;
656
657    if (value && PySyckSeq_setvalue(self, value, NULL) < 0)
658        return -1;
659
660    if (tag && PySyckNode_settag((PySyckNodeObject *)self, tag, NULL) < 0)
661        return -1;
662
663    if (anchor && PySyckNode_setanchor((PySyckNodeObject *)self, anchor, NULL) < 0)
664        return -1;
665
666    if (inline_ && PySyckSeq_setinline(self, inline_, NULL) < 0)
667        return -1;
668
669    return 0;
670}
671
672static PyGetSetDef PySyckSeq_getsetters[] = {
673    {"kind", (getter)PySyckNode_getkind, NULL,
674        "the node kind", &PySyck_SeqKind},
675    {"value", (getter)PySyckNode_getvalue, (setter)PySyckSeq_setvalue,
676        "the node value", NULL},
677    {"tag", (getter)PySyckNode_gettag, (setter)PySyckNode_settag,
678        "the node tag", NULL},
679    {"anchor", (getter)PySyckNode_getanchor, (setter)PySyckNode_setanchor,
680        "the node anchor", NULL},
681    {"inline", (getter)PySyckSeq_getinline, (setter)PySyckSeq_setinline,
682        "the node style", NULL},
683    {NULL}  /* Sentinel */
684};
685
686static PyTypeObject PySyckSeq_Type = {
687    PyObject_HEAD_INIT(NULL)
688    0,                                          /* ob_size */
689    "_syck.Seq",                                /* tp_name */
690    sizeof(PySyckSeqObject),                    /* tp_basicsize */
691    0,                                          /* tp_itemsize */
692    0,                                          /* tp_dealloc */
693    0,                                          /* tp_print */
694    0,                                          /* tp_getattr */
695    0,                                          /* tp_setattr */
696    0,                                          /* tp_compare */
697    0,                                          /* tp_repr */
698    0,                                          /* tp_as_number */
699    0,                                          /* tp_as_sequence */
700    0,                                          /* tp_as_mapping */
701    0,                                          /* tp_hash */
702    0,                                          /* tp_call */
703    0,                                          /* tp_str */
704    0,                                          /* tp_getattro */
705    0,                                          /* tp_setattro */
706    0,                                          /* tp_as_buffer */
707    Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE|Py_TPFLAGS_HAVE_GC,  /* tp_flags */
708    PySyckSeq_doc,                              /* tp_doc */
709    (traverseproc)PySyckNode_traverse,          /* tp_traverse */
710    (inquiry)PySyckNode_clear,                  /* tp_clear */
711    0,                                          /* tp_richcompare */
712    0,                                          /* tp_weaklistoffset */
713    0,                                          /* tp_iter */
714    0,                                          /* tp_iternext */
715    0,                                          /* tp_methods */
716    0,                                          /* tp_members */
717    PySyckSeq_getsetters,                       /* tp_getset */
718    &PySyckNode_Type,                           /* tp_base */
719    0,                                          /* tp_dict */
720    0,                                          /* tp_descr_get */
721    0,                                          /* tp_descr_set */
722    0,                                          /* tp_dictoffset */
723    (initproc)PySyckSeq_init,                   /* tp_init */
724    0,                                          /* tp_alloc */
725    PySyckSeq_new,                              /* tp_new */
726};
727
728/****************************************************************************
729 * The type _syck.Map.
730 ****************************************************************************/
731
732PyDoc_STRVAR(PySyckMap_doc,
733    "Map(value='', tag=None, inline=False) -> a Map node\n\n"
734    "_syck.Map represents a mapping node in Syck parser and emitter\n"
735    "graphs. A mapping node points to an unordered collections of pairs.\n\n"
736    "Attributes:\n\n"
737    "kind -- always 'map'; read-only\n"
738    "value -- the node value, a dictionary\n"
739    "tag -- the node tag; a string or None\n"
740    "anchor -- the name of the node anchor or None; read-only\n"
741    "inline -- is the node inline? False or True\n");
742
743typedef struct {
744    PyObject_HEAD
745    /* Common fields for all Node types: */
746    PyObject *value;    /* always an object */
747    PyObject *tag;      /* a string object or NULL */
748    PyObject *anchor;   /* a string object or NULL */
749    /* Map-specific fields: */
750    enum map_style style;
751} PySyckMapObject;
752
753static PyObject *
754PySyckMap_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
755{
756    PySyckMapObject *self;
757
758    self = (PySyckMapObject *)type->tp_alloc(type, 0);
759    if (!self) return NULL;
760
761    self->value = PyDict_New();
762    if (!self->value) {
763        Py_DECREF(self);
764        return NULL;
765    }
766
767    self->tag = NULL;
768    self->anchor = NULL;
769    self->style = seq_none;
770
771    return (PyObject *)self;
772}
773
774static int
775PySyckMap_setvalue(PySyckMapObject *self, PyObject *value, void *closure)
776{
777    if (!value) {
778        PyErr_SetString(PyExc_TypeError, "cannot delete 'value'");
779        return -1;
780    }
781    if (!PyMapping_Check(value)) { /* PyMapping_Check always succeeds */
782        PyErr_SetString(PyExc_TypeError, "'value' must be a mapping");
783        return -1;
784    }
785
786    Py_DECREF(self->value);
787    Py_INCREF(value);
788    self->value = value;
789
790    return 0;
791}
792
793static PyObject *
794PySyckMap_getinline(PySyckMapObject *self, void *closure)
795{
796    PyObject *value = (self->style == map_inline) ? Py_True : Py_False;
797
798    Py_INCREF(value);
799    return value;
800}
801
802static int
803PySyckMap_setinline(PySyckMapObject *self, PyObject *value, void *closure)
804{
805    if (!value) {
806        PyErr_SetString(PyExc_TypeError, "cannot delete 'inline'");
807        return -1;
808    }
809
810    if (!PyInt_Check(value)) {
811        PyErr_SetString(PyExc_TypeError, "'inline' must be a Boolean object");
812        return -1;
813    }
814
815    self->style = PyInt_AS_LONG(value) ? map_inline : map_none;
816
817    return 0;
818}
819
820static int
821PySyckMap_init(PySyckMapObject *self, PyObject *args, PyObject *kwds)
822{
823    PyObject *value = NULL;
824    PyObject *tag = NULL;
825    PyObject *anchor = NULL;
826    PyObject *inline_ = NULL;
827
828    static char *kwdlist[] = {"value", "tag", "anchor", "inline", NULL};
829
830    if (!PyArg_ParseTupleAndKeywords(args, kwds, "|OOOO", kwdlist,
831                &value, &tag, &anchor, &inline_))
832        return -1;
833
834    if (value && PySyckMap_setvalue(self, value, NULL) < 0)
835        return -1;
836
837    if (tag && PySyckNode_settag((PySyckNodeObject *)self, tag, NULL) < 0)
838        return -1;
839
840    if (anchor && PySyckNode_setanchor((PySyckNodeObject *)self, anchor, NULL) < 0)
841        return -1;
842
843    if (inline_ && PySyckMap_setinline(self, inline_, NULL) < 0)
844        return -1;
845
846    return 0;
847}
848
849static PyGetSetDef PySyckMap_getsetters[] = {
850    {"kind", (getter)PySyckNode_getkind, NULL,
851        "the node kind", &PySyck_MapKind},
852    {"value", (getter)PySyckNode_getvalue, (setter)PySyckMap_setvalue,
853        "the node value", NULL},
854    {"tag", (getter)PySyckNode_gettag, (setter)PySyckNode_settag,
855        "the node tag", NULL},
856    {"anchor", (getter)PySyckNode_getanchor, (setter)PySyckNode_setanchor,
857        "the node anchor", NULL},
858    {"inline", (getter)PySyckMap_getinline, (setter)PySyckMap_setinline,
859        "the node style", NULL},
860    {NULL}  /* Sentinel */
861};
862
863static PyTypeObject PySyckMap_Type = {
864    PyObject_HEAD_INIT(NULL)
865    0,                                          /* ob_size */
866    "_syck.Map",                                /* tp_name */
867    sizeof(PySyckMapObject),                    /* tp_basicsize */
868    0,                                          /* tp_itemsize */
869    0,                                          /* tp_dealloc */
870    0,                                          /* tp_print */
871    0,                                          /* tp_getattr */
872    0,                                          /* tp_setattr */
873    0,                                          /* tp_compare */
874    0,                                          /* tp_repr */
875    0,                                          /* tp_as_number */
876    0,                                          /* tp_as_sequence */
877    0,                                          /* tp_as_mapping */
878    0,                                          /* tp_hash */
879    0,                                          /* tp_call */
880    0,                                          /* tp_str */
881    0,                                          /* tp_getattro */
882    0,                                          /* tp_setattro */
883    0,                                          /* tp_as_buffer */
884    Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE|Py_TPFLAGS_HAVE_GC,  /* tp_flags */
885    PySyckMap_doc,                              /* tp_doc */
886    (traverseproc)PySyckNode_traverse,          /* tp_traverse */
887    (inquiry)PySyckNode_clear,                  /* tp_clear */
888    0,                                          /* tp_richcompare */
889    0,                                          /* tp_weaklistoffset */
890    0,                                          /* tp_iter */
891    0,                                          /* tp_iternext */
892    0,                                          /* tp_methods */
893    0,                                          /* tp_members */
894    PySyckMap_getsetters,                       /* tp_getset */
895    &PySyckNode_Type,                           /* tp_base */
896    0,                                          /* tp_dict */
897    0,                                          /* tp_descr_get */
898    0,                                          /* tp_descr_set */
899    0,                                          /* tp_dictoffset */
900    (initproc)PySyckMap_init,                   /* tp_init */
901    0,                                          /* tp_alloc */
902    PySyckMap_new,                              /* tp_new */
903};
904
905
906/*
907typedef struct {
908    PyObject_HEAD
909    PyObject *kind;
910    PyObject *type_id;
911    PyObject *value;
912} PySyckNodeObject;
913
914static void
915PySyckNode_dealloc(PySyckNodeObject *self)
916{
917    Py_XDECREF(self->kind);
918    Py_XDECREF(self->type_id);
919    Py_XDECREF(self->value);
920    PyObject_Del(self);
921}
922
923static PyObject *
924PySyckNode_getattr(PySyckNodeObject *self, char *name)
925{
926    PyObject *value;
927
928    if (strcmp(name, "kind") == 0)
929        value = self->kind;
930    else if (strcmp(name, "type_id") == 0)
931        value = self->type_id;
932    else if (strcmp(name, "value") == 0)
933        value = self->value;
934    else {
935        PyErr_SetString(PyExc_AttributeError, name);
936        return NULL;
937    }
938
939    Py_INCREF(value);
940    return value;
941}
942
943
944*/
945#if 0
946   
947static PyTypeObject PySyckNode_Type = {
948    PyObject_HEAD_INIT(NULL)
949    0,                                  /* ob_size */
950    "_syck.Node",                       /* tp_name */
951    sizeof(PySyckNodeObject),           /* tp_basicsize */
952    0,                                  /* tp_itemsize */
953    (destructor)PySyckNode_dealloc,     /* tp_dealloc */
954    0,                                  /* tp_print */
955    (getattrfunc)PySyckNode_getattr,    /* tp_getattr */
956    0,                                  /* tp_setattr */
957    0,                                  /* tp_compare */
958    0,                                  /* tp_repr */
959    0,                                  /* tp_as_number */
960    0,                                  /* tp_as_sequence */
961    0,                                  /* tp_as_mapping */
962    0,                                  /* tp_hash */
963    0,                                  /* tp_call */
964    0,                                  /* tp_str */
965    0,                                  /* tp_getattro */
966    0,                                  /* tp_setattro */
967    0,                                  /* tp_as_buffer */
968    Py_TPFLAGS_DEFAULT,                 /* tp_flags */
969    PySyckNode_doc,                     /* tp_doc */
970};
971
972static PyObject *
973PySyckNode_New(char *type_id, PyObject *value) /* Note: steals the reference to the value. */
974{
975    PySyckNodeObject *self;
976    PyObject *kind;
977
978    self = PyObject_NEW(PySyckNodeObject, &PySyckNode_Type);
979    if (!self) {
980        Py_XDECREF(value);
981        return NULL;
982    }
983
984    self->value = value;
985
986    if (PyList_Check(value))
987        kind = PySyck_SeqKind;
988    else if (PyDict_Check(value))
989        kind = PySyck_MapKind;
990    else
991        kind = PySyck_ScalarKind;
992    Py_INCREF(kind);
993    self->kind = kind;
994
995    if (type_id) {
996        self->type_id = PyString_FromString(type_id);
997        if (!self->type_id) {
998            Py_DECREF(self);
999            return NULL;
1000        }
1001    }
1002    else {
1003        Py_INCREF(Py_None);
1004        self->type_id = Py_None;
1005    }
1006
1007    return (PyObject *)self;
1008}
1009
1010static PyObject *
1011PySyck_Node(PyObject *self, PyObject *args)
1012{
1013    if (!PyArg_ParseTuple(args, ":_syck.Node"))
1014        return NULL;
1015
1016    PyErr_SetString(PyExc_TypeError, "Node object cannot be created explicitly. Use _syck.Parser.parse() instead.");
1017    return NULL;
1018}
1019
1020static char PySyck_Node_doc[] =
1021    "Node object cannot be created explicitly. Use _syck.Parser.parse() instead.";
1022
1023
1024*/
1025
1026/* Parser type. */
1027
1028typedef struct {
1029    PyObject_HEAD
1030    PyObject *source;
1031    PyObject *resolver;
1032    PyObject *symbols;
1033    SyckParser *syck;
1034    int error;
1035} PySyckParserObject;
1036
1037static void
1038PySyckParser_free(PySyckParserObject *parser)
1039{
1040    Py_XDECREF(parser->source);
1041    parser->source = NULL;
1042    Py_XDECREF(parser->resolver);
1043    parser->resolver = NULL;
1044    Py_XDECREF(parser->symbols);
1045    parser->symbols = NULL;
1046    if (parser->syck) {
1047        syck_free_parser(parser->syck);
1048        parser->syck = NULL;
1049    }
1050}
1051
1052static PyObject *
1053PySyckParser_parse(PySyckParserObject *parser, PyObject *args)
1054{
1055    SYMID index;
1056    PyObject *value;
1057
1058    if (!PyArg_ParseTuple(args, ":parse"))
1059        return NULL;
1060
1061    if (!parser->syck) {
1062        Py_INCREF(Py_None);
1063        return Py_None;
1064    }
1065
1066    if (parser->symbols) {
1067        PyErr_SetString(PyExc_RuntimeError, "do not call Parser.parse while it is running");
1068        return NULL;
1069    }
1070
1071    parser->symbols = PyList_New(0);
1072    if (!parser->symbols) {
1073        return NULL;
1074    }
1075
1076    index = syck_parse(parser->syck);
1077
1078    if (parser->error) {
1079        PySyckParser_free(parser);
1080        return NULL;
1081    }
1082
1083    if (parser->syck->eof) {
1084        PySyckParser_free(parser);
1085        Py_INCREF(Py_None);
1086        return Py_None;
1087    }
1088
1089    value = PyList_GetItem(parser->symbols, index);
1090
1091    Py_DECREF(parser->symbols);
1092    parser->symbols = NULL;
1093
1094    return value;
1095}
1096
1097static char PySyckParser_parse_doc[] =
1098    "Parses the next document in the YAML stream, return the root Node object or None on EOF.";
1099
1100static PyObject *
1101PySyckParser_eof(PySyckParserObject *parser, PyObject *args)
1102{
1103    PyObject *value;
1104
1105    if (!PyArg_ParseTuple(args, ":eof"))
1106        return NULL;
1107
1108    value = parser->syck ? Py_False : Py_True;
1109
1110    Py_INCREF(value);
1111    return value;
1112}
1113
1114static char PySyckParser_eof_doc[] =
1115    "Checks if the parser is stopped.";
1116
1117static PyMethodDef PySyckParser_methods[] = {
1118    {"parse",  (PyCFunction)PySyckParser_parse, METH_VARARGS, PySyckParser_parse_doc},
1119    {"eof",  (PyCFunction)PySyckParser_eof, METH_VARARGS, PySyckParser_eof_doc},
1120    {NULL}  /* Sentinel */
1121};
1122
1123static void
1124PySyckParser_dealloc(PySyckParserObject *parser)
1125{
1126    PySyckParser_free(parser);
1127    PyObject_Del(parser);
1128}
1129
1130static PyObject *
1131PySyckParser_getattr(PySyckParserObject *parser, char *name)
1132{
1133    return Py_FindMethod(PySyckParser_methods, (PyObject *)parser, name);
1134}
1135
1136static char PySyckParser_doc[] =
1137    "_syck.Parser(yaml_string_or_file, resolver=None, implicit_typing=True, taguri_expansion=True) -> Parser object\n"
1138    "\n"
1139    "Methods of the Parser object:\n\n"
1140    "parse() -- Parses the next document in the YAML stream, return the root Node object or None on EOF.\n"
1141    "eof() -- Checks if the parser is stopped.\n";
1142
1143static PyTypeObject PySyckParser_Type = {
1144    PyObject_HEAD_INIT(NULL)
1145    0,                                  /* ob_size */
1146    "_syck.Parser",                     /* tp_name */
1147    sizeof(PySyckParserObject),         /* tp_basicsize */
1148    0,                                  /* tp_itemsize */
1149    (destructor)PySyckParser_dealloc,   /* tp_dealloc */
1150    0,                                  /* tp_print */
1151    (getattrfunc)PySyckParser_getattr,  /* tp_getattr */
1152    0,                                  /* tp_setattr */
1153    0,                                  /* tp_compare */
1154    0,                                  /* tp_repr */
1155    0,                                  /* tp_as_number */
1156    0,                                  /* tp_as_sequence */
1157    0,                                  /* tp_as_mapping */
1158    0,                                  /* tp_hash */
1159    0,                                  /* tp_call */
1160    0,                                  /* tp_str */
1161    0,                                  /* tp_getattro */
1162    0,                                  /* tp_setattro */
1163    0,                                  /* tp_as_buffer */
1164    Py_TPFLAGS_DEFAULT,                 /* tp_flags */
1165    PySyckParser_doc,                   /* tp_doc */
1166};
1167
1168static long
1169PySyckParser_read_handler(char *buf, SyckIoFile *file, long max_size, long skip)
1170{
1171    PySyckParserObject *parser = (PySyckParserObject *)file->ptr;
1172
1173    PyObject *value;
1174
1175    char *str;
1176    int length;
1177
1178    buf[skip] = '\0';
1179
1180    if (parser->error) {
1181        return skip;
1182    }
1183   
1184    max_size -= skip;
1185
1186    value = PyObject_CallMethod(parser->source, "read", "(i)", max_size);
1187    if (!value) {
1188        parser->error = 1;
1189        return skip;
1190    }
1191
1192    if (!PyString_Check(value)) {
1193        Py_DECREF(value);
1194        PyErr_SetString(PyExc_TypeError, "file-like object should return a string");
1195        parser->error = 1;
1196       
1197        return skip;
1198    }
1199
1200    str = PyString_AS_STRING(value);
1201    length = PyString_GET_SIZE(value);
1202    if (!length) {
1203        Py_DECREF(value);
1204        return skip;
1205    }
1206
1207    if (length > max_size) {
1208        Py_DECREF(value);
1209        PyErr_SetString(PyExc_ValueError, "read returns an overly long string");
1210        parser->error = 1;
1211        return skip;
1212    }
1213
1214    memcpy(buf+skip, str, length);
1215    length += skip;
1216    buf[length] = '\0';
1217
1218    Py_DECREF(value);
1219
1220    return length;
1221}
1222
1223static SYMID
1224PySyckParser_node_handler(SyckParser *syck, SyckNode *node)
1225{
1226    PySyckParserObject *parser = (PySyckParserObject *)syck->bonus;
1227
1228    SYMID index;
1229    PyObject *object = NULL;
1230
1231    PyObject *key, *value, *item;
1232    int k;
1233
1234    if (parser->error)
1235        return -1;
1236
1237    switch (node->kind) {
1238
1239        case syck_str_kind:
1240            object = PyString_FromStringAndSize(node->data.str->ptr,
1241                    node->data.str->len);
1242            if (!object) goto error;
1243            break;
1244
1245        case syck_seq_kind:
1246            object = PyList_New(node->data.list->idx);
1247            if (!object) goto error;
1248            for (k = 0; k < node->data.list->idx; k++) {
1249                index = syck_seq_read(node, k);
1250                item = PyList_GetItem(parser->symbols, index);
1251                if (!item) goto error;
1252                Py_INCREF(item);
1253                PyList_SET_ITEM(object, k, item);
1254            }
1255            break;
1256
1257        case syck_map_kind:
1258            object = PyDict_New();
1259            if (!object) goto error;
1260            for (k = 0; k < node->data.pairs->idx; k++)
1261            {
1262                index = syck_map_read(node, map_key, k);
1263                key = PyList_GetItem(parser->symbols, index);
1264                if (!key) goto error;
1265                index = syck_map_read(node, map_value, k);
1266                value = PyList_GetItem(parser->symbols, index);
1267                if (!value) goto error;
1268                if (PyDict_SetItem(object, key, value) < 0)
1269                    goto error;
1270            }
1271            break;
1272    }
1273
1274    object = PySyckNode_New(node->type_id, object);
1275    if (!object) goto error;
1276
1277    if (parser->resolver) {
1278        value = PyObject_CallFunction(parser->resolver, "(O)", object);
1279        if (!value) goto error;
1280        Py_DECREF(object);
1281        object = value;
1282    }
1283
1284    if (PyList_Append(parser->symbols, object) < 0)
1285        goto error;
1286
1287    index = PyList_Size(parser->symbols)-1;
1288    return index;
1289
1290error:
1291    Py_XDECREF(object);
1292    parser->error = 1;
1293    return -1;
1294}
1295
1296static void
1297PySyckParser_error_handler(SyckParser *syck, char *str)
1298{
1299    PySyckParserObject *parser = (PySyckParserObject *)syck->bonus;
1300    PyObject *value;
1301
1302    if (parser->error) return;
1303
1304    parser->error = 1;
1305
1306    value = Py_BuildValue("(sii)", str, syck->linect, syck->cursor-syck->lineptr);
1307    if (value) {
1308        PyErr_SetObject(PySyck_Error, value);
1309    }
1310}
1311
1312static PyObject *
1313PySyck_Parser(PyObject *self, PyObject *args, PyObject *kwds)
1314{
1315    PySyckParserObject *parser;
1316    PyObject *source;
1317    PyObject *resolver = NULL;
1318    int implicit_typing = 1;
1319    int taguri_expansion = 1;
1320
1321    static char *kwdlist[] = {"source", "resolver", "implicit_typing", "taguri_expansion", NULL};
1322
1323    if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|Oii", kwdlist,
1324                &source, &resolver, &implicit_typing, &taguri_expansion))
1325        return NULL;
1326
1327    parser = PyObject_NEW(PySyckParserObject, &PySyckParser_Type);
1328    if (!parser)
1329        return NULL;
1330
1331    parser->error = 0;
1332    parser->symbols = NULL;
1333
1334    Py_INCREF(source);
1335    parser->source = source;
1336
1337    if (resolver == Py_None)
1338        resolver = NULL;
1339    Py_XINCREF(resolver);
1340    parser->resolver = resolver;
1341
1342    parser->syck = syck_new_parser();
1343    parser->syck->bonus = parser;
1344
1345    if (PyString_Check(source)) {
1346        syck_parser_str(parser->syck, PyString_AS_STRING(source), PyString_GET_SIZE(source), NULL);
1347    }
1348    else {
1349        syck_parser_file(parser->syck, (FILE *)parser, PySyckParser_read_handler);
1350    }
1351    syck_parser_implicit_typing(parser->syck, implicit_typing);
1352    syck_parser_taguri_expansion(parser->syck, taguri_expansion);
1353
1354    syck_parser_handler(parser->syck, PySyckParser_node_handler);
1355    syck_parser_error_handler(parser->syck, PySyckParser_error_handler);
1356    /*
1357    syck_parser_bad_anchor_handler(parser, PySyckParser_bad_anchor_handler);
1358    */
1359
1360    return (PyObject *)parser;
1361}
1362
1363static char PySyck_Parser_doc[] =
1364    "Creates a new Parser object.";
1365
1366/* The module definitions. */
1367
1368static PyMethodDef PySyck_methods[] = {
1369    {"Node",  (PyCFunction)PySyck_Node, METH_VARARGS, PySyck_Node_doc},
1370    {"Parser",  (PyCFunction)PySyck_Parser, METH_VARARGS|METH_KEYWORDS, PySyck_Parser_doc},
1371    {NULL}  /* Sentinel */
1372};
1373
1374static char PySyck_doc[] =
1375    "This module provides low-level access to the Syck parser and emitter.\n"
1376    "Do not use this module directly, use the package 'syck' instead.\n";
1377
1378/* PyMODINIT_FUNC - does not work with versions <2.3 */
1379void
1380init_syck(void)
1381{
1382    PyObject *m;
1383
1384    PySyckNode_Type.ob_type = &PyType_Type;
1385    PySyckParser_Type.ob_type = &PyType_Type;
1386
1387    PySyck_Error = PyErr_NewException("_syck.error", NULL, NULL);
1388    if (!PySyck_Error)
1389        return;
1390
1391    PySyck_ScalarKind = PyString_FromString("scalar");
1392    if (!PySyck_ScalarKind)
1393        return;
1394    PySyck_SeqKind = PyString_FromString("seq");
1395    if (!PySyck_SeqKind)
1396        return;
1397    PySyck_MapKind = PyString_FromString("map");
1398    if (!PySyck_MapKind)
1399        return;
1400
1401    m = Py_InitModule3("_syck", PySyck_methods, PySyck_doc);
1402
1403    Py_INCREF(PySyck_Error);
1404    if (!PyModule_AddObject(m, "error", PySyck_Error) < 0)
1405        return;
1406
1407    Py_INCREF(&PySyckNode_Type);
1408    if (PyModule_AddObject(m, "NodeType", (PyObject *)&PySyckNode_Type) < 0)
1409        return;
1410
1411    Py_INCREF(&PySyckParser_Type);
1412    if (PyModule_AddObject(m, "ParserType", (PyObject *)&PySyckParser_Type) < 0)
1413        return;
1414}
1415
1416#endif
1417
1418/* The module _syck. */
1419
1420static PyMethodDef PySyck_methods[] = {
1421    {NULL}  /* Sentinel */
1422};
1423
1424PyDoc_STRVAR(PySyck_doc,
1425    "The low-level wrapper for the Syck YAML parser and emitter\n\n"
1426    "Types:\n\n"
1427    "Node -- the base Node type\n");
1428
1429PyMODINIT_FUNC
1430init_syck(void)
1431{
1432    PyObject *m;
1433
1434    if (PyType_Ready(&PySyckNode_Type) < 0)
1435        return;
1436    if (PyType_Ready(&PySyckScalar_Type) < 0)
1437        return;
1438    if (PyType_Ready(&PySyckSeq_Type) < 0)
1439        return;
1440    if (PyType_Ready(&PySyckMap_Type) < 0)
1441        return;
1442   
1443    PySyck_Error = PyErr_NewException("_syck.error", NULL, NULL);
1444    if (!PySyck_Error) return;
1445
1446    PySyck_ScalarKind = PyString_FromString("scalar");
1447    if (!PySyck_ScalarKind) return;
1448    PySyck_SeqKind = PyString_FromString("seq");
1449    if (!PySyck_SeqKind) return;
1450    PySyck_MapKind = PyString_FromString("map");
1451    if (!PySyck_MapKind) return;
1452
1453    PySyck_1QuoteStyle = PyString_FromString("1quote");
1454    if (!PySyck_1QuoteStyle) return;
1455    PySyck_2QuoteStyle = PyString_FromString("2quote");
1456    if (!PySyck_2QuoteStyle) return;
1457    PySyck_FoldStyle = PyString_FromString("fold");
1458    if (!PySyck_FoldStyle) return;
1459    PySyck_LiteralStyle = PyString_FromString("literal");
1460    if (!PySyck_LiteralStyle) return;
1461    PySyck_PlainStyle = PyString_FromString("plain");
1462    if (!PySyck_PlainStyle) return;
1463
1464    PySyck_StripChomp = PyString_FromString("-");
1465    if (!PySyck_StripChomp) return;
1466    PySyck_KeepChomp = PyString_FromString("+");
1467    if (!PySyck_KeepChomp) return;
1468
1469    m = Py_InitModule3("_syck", PySyck_methods, PySyck_doc);
1470
1471    Py_INCREF(&PySyckNode_Type);
1472    if (PyModule_AddObject(m, "Node", (PyObject *)&PySyckNode_Type) < 0)
1473        return;
1474
1475    Py_INCREF(&PySyckScalar_Type);
1476    if (PyModule_AddObject(m, "Scalar", (PyObject *)&PySyckScalar_Type) < 0)
1477        return;
1478
1479    Py_INCREF(&PySyckSeq_Type);
1480    if (PyModule_AddObject(m, "Seq", (PyObject *)&PySyckSeq_Type) < 0)
1481        return;
1482
1483    Py_INCREF(&PySyckMap_Type);
1484    if (PyModule_AddObject(m, "Map", (PyObject *)&PySyckMap_Type) < 0)
1485        return;
1486}
1487
1488
Note: See TracBrowser for help on using the repository browser.