From 0aedd7b2181c507db489ff2a6ec0511df06f8144 Mon Sep 17 00:00:00 2001 From: "jordi.saludes" Date: Thu, 10 Jun 2010 14:54:18 +0000 Subject: [PATCH] Created py-bindings. --- contrib/py-bindings/Makefile | 22 ++++++ contrib/py-bindings/gfmodule.c | 137 +++++++++++++++++++++++++++++++++ contrib/py-bindings/script.py | 9 +++ 3 files changed, 168 insertions(+) create mode 100644 contrib/py-bindings/Makefile create mode 100644 contrib/py-bindings/gfmodule.c create mode 100644 contrib/py-bindings/script.py diff --git a/contrib/py-bindings/Makefile b/contrib/py-bindings/Makefile new file mode 100644 index 000000000..fafbdbb2b --- /dev/null +++ b/contrib/py-bindings/Makefile @@ -0,0 +1,22 @@ +src=../../src +import=-i$src/runtime/haskell:$src/compiler +cbind=../c-bindings +pythoninc=/usr/include/python2.5 + +conf: + ln -s $(cbind)/PGFFFI.hs + ln -s $(cbind)/pgf.h +Build: gf.so + +gf.so: PGFFFI.hs gfmodule.c + gf --make ../../examples/tutorial/embedded/QueryEng.gf + ghc $(import) --make -fglasgow-exts -O2 -no-hs-main -c $< + ghc -O2 --make -fglasgow-exts -no-hs-main -optl '-shared' \ + -optc '-DMODULE=PGFFFI' -optc '-I$(pythoninc)' -o $@ $^ +clean: + rm -f *.hi *.o + rm -f *_stub.* + +superclean: + rm -f PGFFFI.hs pgf.h Query.pgf + rm -f gf.so \ No newline at end of file diff --git a/contrib/py-bindings/gfmodule.c b/contrib/py-bindings/gfmodule.c new file mode 100644 index 000000000..1f983c6df --- /dev/null +++ b/contrib/py-bindings/gfmodule.c @@ -0,0 +1,137 @@ +#define CAT(a,b) XCAT(a,b) +#define XCAT(a,b) a ## b + +#include +#include +#include "pgf.h" +#include + +static PyObject* +readPGF(PyObject *self, PyObject *args) +{ + char *path; + if (!PyArg_ParseTuple(args, "s", &path)) + return NULL; + GF_PGF pgf = gf_readPGF(path); + return PyCObject_FromVoidPtr(pgf, gf_freePGF); +} + +static PyObject* +readLanguage(PyObject *self, PyObject *args) +{ + char *module_name; + if (!PyArg_ParseTuple(args, "s", &module_name)) + return NULL; + GF_Language lang = gf_readLanguage(module_name); + return PyCObject_FromVoidPtr(lang, gf_freeLanguage); +} + +static PyObject* +showExpr(PyObject *self, PyObject *args) +{ + PyObject *co_exp; + GF_Expr exp; + if (!PyArg_ParseTuple(args, "O", &co_exp)) + return NULL; + if (!PyCObject_Check(co_exp)) { + PyErr_SetString(PyExc_TypeError, "Expected an expression."); + return NULL; + } + exp = (GF_Expr)PyCObject_AsVoidPtr(co_exp); + char *str = gf_showExpr(exp); + return Py_BuildValue("s",str); +} + + +static PyObject* +startCat(PyObject *self, PyObject *args) +{ + PyObject *cobj; + GF_PGF pgf; + if (!PyArg_ParseTuple(args, "O", &cobj)) + return NULL; + if (!PyCObject_Check(cobj)) { + PyErr_SetString(PyExc_TypeError, "Expected a pgf object"); + return NULL; + } + pgf = (GF_PGF)PyCObject_AsVoidPtr(cobj); + GF_Type cat = gf_startCat(pgf); + return PyCObject_FromVoidPtr(cat, gf_freeType); +} + +static PyObject* +parse(PyObject *self, PyObject *args) +{ + PyObject *co_pgf, *co_lang, *co_cat; + GF_PGF pgf; + GF_Language lang; + GF_Type cat; + char *lexed; + if (!PyArg_ParseTuple(args, "OOOs", &co_pgf, &co_lang, &co_cat, &lexed)) + return NULL; + if (!PyCObject_Check(co_pgf)) { + PyErr_SetString(PyExc_TypeError, "Expected a PGF object"); + return NULL; + } + if (!PyCObject_Check(co_lang)) { + PyErr_SetString(PyExc_TypeError, "Expected a Language object"); + return NULL; + } + if (!PyCObject_Check(co_cat)) { + PyErr_SetString(PyExc_TypeError, "Expected a Type object"); + return NULL; + } + pgf = (GF_PGF)PyCObject_AsVoidPtr(co_pgf); + lang = (GF_Language)PyCObject_AsVoidPtr(co_lang); + cat = (GF_Type)PyCObject_AsVoidPtr(co_cat); + GF_Tree *result = gf_parse(pgf, lang, cat, lexed); + GF_Tree *p = result; + PyObject *parsed = PyList_New(0); + if (*p) { + do { + GF_Expr exp = *(p++); + PyObject *co_exp = PyCObject_FromVoidPtr(exp,gf_freeExpr); + PyList_Append(parsed, co_exp); + /* char *str = gf_showExpr(exp); + puts(str); + free(str); */ + } while (*p); + } + return parsed; +} + + + + + +static PyMethodDef GfMethods[] = { + {"read_pgf", readPGF, METH_VARARGS, + "Read pgf file"}, + {"read_lang", readLanguage, METH_VARARGS, + "Get language from pgf."}, + {"startcat", startCat, METH_VARARGS, + "Get start category from pgf."}, + {"parse", parse, METH_VARARGS, + "Parse string for language and given start category."}, + {"show_expr", showExpr, METH_VARARGS, + "show an expression."}, + {NULL, NULL, 0, NULL} +} ; + +PyMODINIT_FUNC +initgf(void) +{ + PyObject *m = Py_InitModule("gf", GfMethods); + static char *argv[] = { "gf.so", 0 }, **argv_ = argv; + static int argc = 1; + + gf_init (&argc, &argv_); + hs_add_root (CAT (__stginit_, MODULE)); + printf("Started gf\n"); + if (m == NULL) return; + + /* gfError = PyErr_NewException("gf.error", NULL, NULL); + Py_INCREF(gfError); + PyModule_AddObject(m, "error", gfError); + */ +} diff --git a/contrib/py-bindings/script.py b/contrib/py-bindings/script.py new file mode 100644 index 000000000..6148fadea --- /dev/null +++ b/contrib/py-bindings/script.py @@ -0,0 +1,9 @@ +#!/usr/bin/env python +from gf import * +query = read_pgf("Query.pgf") +lang = read_lang('QueryEng') +cat = startcat(query) +lexed = "is 2 prime" +print "Parsing '%s':" % lexed +for e in parse(query, lang, cat, lexed): + print '\t',show_expr(e)