1fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton/* Cell object implementation */
2fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
3fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton#include "Python.h"
4fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
5fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyObject *
6fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyCell_New(PyObject *obj)
7fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
8c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyCellObject *op;
9fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
10c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    op = (PyCellObject *)PyObject_GC_New(PyCellObject, &PyCell_Type);
11c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (op == NULL)
12c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return NULL;
13c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    op->ob_ref = obj;
14c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_XINCREF(obj);
15fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
16c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    _PyObject_GC_TRACK(op);
17c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return (PyObject *)op;
18fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
19fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
20fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyObject *
21fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyCell_Get(PyObject *op)
22fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
23c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (!PyCell_Check(op)) {
24c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        PyErr_BadInternalCall();
25c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return NULL;
26c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    }
27c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_XINCREF(((PyCellObject*)op)->ob_ref);
28c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return PyCell_GET(op);
29fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
30fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
31fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonint
32fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyCell_Set(PyObject *op, PyObject *obj)
33fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
34c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyObject* oldobj;
35c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (!PyCell_Check(op)) {
36c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        PyErr_BadInternalCall();
37c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return -1;
38c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    }
39c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    oldobj = PyCell_GET(op);
40c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_XINCREF(obj);
41c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyCell_SET(op, obj);
42c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_XDECREF(oldobj);
43c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return 0;
44fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
45fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
46fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonstatic void
47fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltoncell_dealloc(PyCellObject *op)
48fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
49c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    _PyObject_GC_UNTRACK(op);
50c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_XDECREF(op->ob_ref);
51c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyObject_GC_Del(op);
52fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
53fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
54fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonstatic int
55fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltoncell_compare(PyCellObject *a, PyCellObject *b)
56fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
57c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    /* Py3K warning for comparisons  */
58c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (PyErr_WarnPy3k("cell comparisons not supported in 3.x",
59c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou                       1) < 0) {
60c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return -2;
61c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    }
62c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou
63c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (a->ob_ref == NULL) {
64c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        if (b->ob_ref == NULL)
65c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou            return 0;
66c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return -1;
67c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    } else if (b->ob_ref == NULL)
68c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return 1;
69c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return PyObject_Compare(a->ob_ref, b->ob_ref);
70fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
71fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
72fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonstatic PyObject *
73fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltoncell_repr(PyCellObject *op)
74fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
75c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (op->ob_ref == NULL)
76c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return PyString_FromFormat("<cell at %p: empty>", op);
777ce3694a527afe425a2b9df65c049b0ef4e75960Barry Warsaw
78c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return PyString_FromFormat("<cell at %p: %.80s object at %p>",
79c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou                               op, op->ob_ref->ob_type->tp_name,
80c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou                               op->ob_ref);
81fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
82fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
83fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonstatic int
84fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltoncell_traverse(PyCellObject *op, visitproc visit, void *arg)
85fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
86c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_VISIT(op->ob_ref);
87c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return 0;
88fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
89fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
90fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltonstatic int
91fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hyltoncell_clear(PyCellObject *op)
92fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton{
93c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_CLEAR(op->ob_ref);
94c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return 0;
95fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton}
96fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton
97abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandlstatic PyObject *
98abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandlcell_get_contents(PyCellObject *op, void *closure)
99abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandl{
100c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    if (op->ob_ref == NULL)
101c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    {
102c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        PyErr_SetString(PyExc_ValueError, "Cell is empty");
103c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou        return NULL;
104c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    }
105c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    Py_INCREF(op->ob_ref);
106c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    return op->ob_ref;
107abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandl}
108abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandl
109abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandlstatic PyGetSetDef cell_getsetlist[] = {
110c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    {"cell_contents", (getter)cell_get_contents, NULL},
111c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    {NULL} /* sentinel */
112abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandl};
113abd1ff8f1f6f2840345756081837994fdefaa52bGeorg Brandl
114fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy HyltonPyTypeObject PyCell_Type = {
115c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyVarObject_HEAD_INIT(&PyType_Type, 0)
116c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    "cell",
117c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    sizeof(PyCellObject),
118c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,
119413a8e1b1b81d2de5283ca917eef4c8c7006cdb0Benjamin Peterson    (destructor)cell_dealloc,                   /* tp_dealloc */
120413a8e1b1b81d2de5283ca917eef4c8c7006cdb0Benjamin Peterson    0,                                          /* tp_print */
121c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_getattr */
122c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_setattr */
123c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    (cmpfunc)cell_compare,                      /* tp_compare */
124c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    (reprfunc)cell_repr,                        /* tp_repr */
125c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_as_number */
126c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_as_sequence */
127c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_as_mapping */
128c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_hash */
129c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_call */
130c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_str */
131c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    PyObject_GenericGetAttr,                    /* tp_getattro */
132c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_setattro */
133c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_as_buffer */
134413a8e1b1b81d2de5283ca917eef4c8c7006cdb0Benjamin Peterson    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,    /* tp_flags */
135c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_doc */
136c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    (traverseproc)cell_traverse,                /* tp_traverse */
137c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    (inquiry)cell_clear,                        /* tp_clear */
138c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_richcompare */
139c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_weaklistoffset */
140c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_iter */
141c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_iternext */
142c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_methods */
143c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    0,                                          /* tp_members */
144c83ea137d7e717f764e2f31fc2544f522de7d857Antoine Pitrou    cell_getsetlist,                            /* tp_getset */
145fbd849f201a4a8c17745a72eb9f0ee3bae34d330Jeremy Hylton};
146