Rearrange the python scripting support a bit.
[screen-lua.git] / src / python.c
blobb9ec7ff85a9018294d9c1b0aa7bd33568223e2af
1 /* Python scripting support
3 * Copyright (c) 2009 Sadrul Habib Chowdhury (sadrul@users.sf.net)
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 3, or (at your option)
8 * any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program (see the file COPYING); if not, write to the
17 * Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA
20 ****************************************************************
22 #include <sys/types.h>
24 #include "config.h"
25 #include "screen.h"
26 #include "script.h"
27 #include <sys/stat.h>
28 #include <unistd.h>
30 #include <stdio.h>
31 #include <string.h>
32 #include <stdlib.h>
34 #include "extern.h"
35 #include "logfile.h"
37 #include <Python.h>
38 #include <structmember.h>
40 extern struct win *windows;
42 static PyObject * SPy_Get(PyObject *obj, void *closure);
43 static PyObject * SPy_Set(PyObject *obj, PyObject *value, void *closure);
45 typedef struct
47 char *name;
48 char *doc;
50 int type;
51 size_t offset1;
52 size_t offset2;
53 PyObject * (*conv)(void *);
54 } SPyClosure;
56 #define REGISTER_TYPE(type, Type, closures) \
57 static int \
58 register_##type(PyObject *module) \
59 { \
60 static PyGetSetDef getsets[sizeof(closures)]; \
61 int i, count = sizeof(closures); \
62 for (i = 0; i < count; i++) \
63 { \
64 getsets[i].name = closures[i].name; \
65 getsets[i].doc = closures[i].doc; \
66 getsets[i].closure = &closures[i]; \
67 getsets[i].get = SPy_Get; \
68 getsets[i].set = SPy_Set; \
69 } \
70 PyType##Type.tp_getset = getsets; \
71 PyType_Ready(&PyType##Type); \
72 Py_INCREF(&PyType##Type); \
73 PyModule_AddObject(module, #Type, (PyObject *)&PyType##Type); \
74 return 1; \
77 /** Window {{{ */
78 typedef struct
80 PyObject_HEAD
81 struct win *_obj;
82 } PyWindow;
84 static PyTypeObject PyTypeWindow =
86 PyObject_HEAD_INIT(NULL)
87 .ob_size = 0,
88 .tp_name = "screen.window",
89 .tp_basicsize = sizeof(PyWindow),
90 .tp_flags = Py_TPFLAGS_DEFAULT,
91 .tp_doc = "Window object",
92 .tp_methods = NULL,
93 .tp_getset = NULL,
96 #define SPY_CLOSURE(name, doc, type, member, func) \
97 {name, doc, type, offsetof(PyWindow, _obj), offsetof(struct win, member), func}
98 static SPyClosure wclosures[] =
100 SPY_CLOSURE("title", "Window title", T_STRING, w_title, PyString_FromString),
101 SPY_CLOSURE("number", "Window number", T_INT, w_number, PyInt_FromLong),
102 {NULL}
104 REGISTER_TYPE(window, Window, wclosures)
105 #undef SPY_CLOSURE
107 static PyObject *
108 PyWindow_FromWindow(struct win *w)
110 PyWindow *obj = PyTypeWindow.tp_alloc(&PyTypeWindow, 0);
111 obj->_obj = w;
112 return (PyObject *)obj;
115 /** }}} */
117 static PyObject *
118 SPy_Get(PyObject *obj, void *closure)
120 SPyClosure *sc = closure;
121 char **first = (char *)obj + sc->offset1;
122 char **second = (char *)*first + sc->offset2;
123 return sc->conv(*second);
126 static PyObject *
127 SPy_Set(PyObject *obj, PyObject *value, void *closure)
129 return NULL;
132 static PyObject *
133 screen_windows(PyObject *self)
135 struct win *w = windows;
136 int count = 0;
137 for (; w; w = w->w_next)
138 ++count;
139 PyObject *tuple = PyTuple_New(count);
141 for (w = windows, count = 0; w; w = w->w_next, ++count)
142 PyTuple_SetItem(tuple, count, PyWindow_FromWindow(w));
144 return tuple;
147 const PyMethodDef py_methods[] = {
148 {"windows", (PyCFunction)screen_windows, METH_NOARGS, NULL},
149 {NULL, NULL, 0, NULL}
152 static int
153 SPyInit(void)
155 PyObject *m;
157 Py_Initialize();
159 m = Py_InitModule3 ("screen", py_methods, NULL);
160 register_window(m);
162 return 0;
165 static int
166 SPyFinit(void)
168 /*Py_Finalize(); // Crashes -- why? */
169 return 0;
172 static int
173 SPySource(const char *file, int async)
175 FILE *f = fopen(file, "rb");
176 int ret = PyRun_SimpleFile(f, file);
177 fclose(f);
179 if (ret == 0)
180 return 1; /* Success */
182 if (PyErr_Occurred())
184 PyErr_Print();
185 return 0;
188 return 1;
191 struct binding py_binding =
193 "python",
196 SPyInit,
197 SPyFinit,
199 SPySource,