mirror of
https://github.com/GrammaticalFramework/gf-core.git
synced 2026-04-23 19:42:50 -06:00
Refactor modules in Python bindings. Start work on grammar-update functions, but without transactions.
This commit is contained in:
4
.gitignore
vendored
4
.gitignore
vendored
@@ -47,8 +47,8 @@ src/runtime/c/sg/.dirstamp
|
|||||||
src/runtime/c/stamp-h1
|
src/runtime/c/stamp-h1
|
||||||
src/runtime/java/.libs/
|
src/runtime/java/.libs/
|
||||||
src/runtime/python/build/
|
src/runtime/python/build/
|
||||||
src/runtime/python/__pycache__/
|
src/runtime/python/**/__pycache__/
|
||||||
src/runtime/python/.pytest_cache/
|
src/runtime/python/**/.pytest_cache/
|
||||||
.cabal-sandbox
|
.cabal-sandbox
|
||||||
cabal.sandbox.config
|
cabal.sandbox.config
|
||||||
.stack-work
|
.stack-work
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
#include <pgf/pgf.h>
|
#include <pgf/pgf.h>
|
||||||
#include "./expr.h"
|
#include "./expr.h"
|
||||||
#include "./marshaller.h"
|
#include "./ffi.h"
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|||||||
@@ -5,7 +5,25 @@
|
|||||||
|
|
||||||
#include <pgf/pgf.h>
|
#include <pgf/pgf.h>
|
||||||
#include "./expr.h"
|
#include "./expr.h"
|
||||||
#include "./marshaller.h"
|
#include "./ffi.h"
|
||||||
|
|
||||||
|
/* static */
|
||||||
|
PyObject *PGFError;
|
||||||
|
|
||||||
|
/* static */
|
||||||
|
PgfExnType handleError(PgfExn err)
|
||||||
|
{
|
||||||
|
if (err.type == PGF_EXN_SYSTEM_ERROR) {
|
||||||
|
errno = err.code;
|
||||||
|
PyErr_SetFromErrnoWithFilename(PyExc_IOError, err.msg);
|
||||||
|
} else if (err.type == PGF_EXN_PGF_ERROR) {
|
||||||
|
PyErr_SetString(PGFError, err.msg);
|
||||||
|
free((char*) err.msg);
|
||||||
|
} else if (err.type == PGF_EXN_OTHER_ERROR) {
|
||||||
|
PyErr_SetString(PGFError, "an unknown error occured");
|
||||||
|
}
|
||||||
|
return err.type;
|
||||||
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
@@ -6,6 +6,15 @@
|
|||||||
|
|
||||||
#include <pgf/pgf.h>
|
#include <pgf/pgf.h>
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
PyObject_HEAD
|
||||||
|
PgfDB *db;
|
||||||
|
PgfRevision revision;
|
||||||
|
} PGFObject;
|
||||||
|
|
||||||
|
extern PyObject *PGFError;
|
||||||
|
PgfExnType handleError(PgfExn err);
|
||||||
|
|
||||||
PgfText *PyUnicode_AsPgfText(PyObject *pystr);
|
PgfText *PyUnicode_AsPgfText(PyObject *pystr);
|
||||||
PyObject *PyUnicode_FromPgfText(PgfText *text);
|
PyObject *PyUnicode_FromPgfText(PgfText *text);
|
||||||
|
|
||||||
@@ -4,35 +4,13 @@
|
|||||||
|
|
||||||
#include <pgf/pgf.h>
|
#include <pgf/pgf.h>
|
||||||
#include "./expr.h"
|
#include "./expr.h"
|
||||||
#include "./marshaller.h"
|
#include "./ffi.h"
|
||||||
|
#include "./transactions.h"
|
||||||
static PyObject *PGFError;
|
|
||||||
|
|
||||||
static
|
|
||||||
PgfExnType handleError(PgfExn err)
|
|
||||||
{
|
|
||||||
if (err.type == PGF_EXN_SYSTEM_ERROR) {
|
|
||||||
errno = err.code;
|
|
||||||
PyErr_SetFromErrnoWithFilename(PyExc_IOError, err.msg);
|
|
||||||
} else if (err.type == PGF_EXN_PGF_ERROR) {
|
|
||||||
PyErr_SetString(PGFError, err.msg);
|
|
||||||
free((char*) err.msg);
|
|
||||||
} else if (err.type == PGF_EXN_OTHER_ERROR) {
|
|
||||||
PyErr_SetString(PGFError, "an unknown error occured");
|
|
||||||
}
|
|
||||||
return err.type;
|
|
||||||
}
|
|
||||||
|
|
||||||
// static PyObject* ParseError;
|
// static PyObject* ParseError;
|
||||||
|
|
||||||
// static PyObject* TypeError;
|
// static PyObject* TypeError;
|
||||||
|
|
||||||
typedef struct {
|
|
||||||
PyObject_HEAD
|
|
||||||
PgfDB *db;
|
|
||||||
PgfRevision revision;
|
|
||||||
} PGFObject;
|
|
||||||
|
|
||||||
// typedef struct IterObject {
|
// typedef struct IterObject {
|
||||||
// PyObject_HEAD
|
// PyObject_HEAD
|
||||||
// PyObject* source;
|
// PyObject* source;
|
||||||
@@ -1753,9 +1731,9 @@ typedef struct {
|
|||||||
// gu_buf_push((GuBuf*) clo->collection, PgfConcr*, concr);
|
// gu_buf_push((GuBuf*) clo->collection, PgfConcr*, concr);
|
||||||
// }
|
// }
|
||||||
|
|
||||||
static PyObject*
|
// static PyObject*
|
||||||
PGF_str(PGFObject *self)
|
// PGF_str(PGFObject *self)
|
||||||
{
|
// {
|
||||||
// GuPool* tmp_pool = gu_local_pool();
|
// GuPool* tmp_pool = gu_local_pool();
|
||||||
//
|
//
|
||||||
// GuExn* err = gu_exn(tmp_pool);
|
// GuExn* err = gu_exn(tmp_pool);
|
||||||
@@ -1776,8 +1754,8 @@ PGF_str(PGFObject *self)
|
|||||||
//
|
//
|
||||||
// gu_pool_free(tmp_pool);
|
// gu_pool_free(tmp_pool);
|
||||||
// return pystr;
|
// return pystr;
|
||||||
return NULL;
|
// return NULL;
|
||||||
}
|
// }
|
||||||
|
|
||||||
static PyObject*
|
static PyObject*
|
||||||
PGF_getAbstractName(PGFObject *self, void *closure)
|
PGF_getAbstractName(PGFObject *self, void *closure)
|
||||||
@@ -2410,6 +2388,21 @@ static PyMethodDef PGF_methods[] = {
|
|||||||
{"functionIsConstructor", (PyCFunction)PGF_functionIsConstructor, METH_VARARGS,
|
{"functionIsConstructor", (PyCFunction)PGF_functionIsConstructor, METH_VARARGS,
|
||||||
"Checks whether a function is a constructor"
|
"Checks whether a function is a constructor"
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
||||||
|
{"createFunction", (PyCFunction)PGF_createFunction, METH_VARARGS,
|
||||||
|
"Create function"
|
||||||
|
},
|
||||||
|
{"dropFunction", (PyCFunction)PGF_dropFunction, METH_VARARGS,
|
||||||
|
"Drop function"
|
||||||
|
},
|
||||||
|
{"createCategory", (PyCFunction)PGF_createCategory, METH_VARARGS,
|
||||||
|
"Create category"
|
||||||
|
},
|
||||||
|
{"dropCategory", (PyCFunction)PGF_dropCategory, METH_VARARGS,
|
||||||
|
"Drop category"
|
||||||
|
},
|
||||||
|
|
||||||
// {"generateAll", (PyCFunction)PGF_generateAll, METH_VARARGS | METH_KEYWORDS,
|
// {"generateAll", (PyCFunction)PGF_generateAll, METH_VARARGS | METH_KEYWORDS,
|
||||||
// "Generates abstract syntax trees of given category in decreasing probability order"
|
// "Generates abstract syntax trees of given category in decreasing probability order"
|
||||||
// },
|
// },
|
||||||
@@ -2454,7 +2447,7 @@ static PyTypeObject pgf_PGFType = {
|
|||||||
0, /*tp_as_mapping*/
|
0, /*tp_as_mapping*/
|
||||||
0, /*tp_hash */
|
0, /*tp_hash */
|
||||||
0, /*tp_call*/
|
0, /*tp_call*/
|
||||||
(reprfunc) PGF_str, /*tp_str*/
|
0, // (reprfunc) PGF_str, /*tp_str*/
|
||||||
0, /*tp_getattro*/
|
0, /*tp_getattro*/
|
||||||
0, /*tp_setattro*/
|
0, /*tp_setattro*/
|
||||||
0, /*tp_as_buffer*/
|
0, /*tp_as_buffer*/
|
||||||
@@ -2479,6 +2472,8 @@ static PyTypeObject pgf_PGFType = {
|
|||||||
0, /*tp_new */
|
0, /*tp_new */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
static PGFObject*
|
static PGFObject*
|
||||||
pgf_readPGF(PyObject *self, PyObject *args)
|
pgf_readPGF(PyObject *self, PyObject *args)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -10,7 +10,12 @@ if libraries==['']:
|
|||||||
|
|
||||||
pgf_module = Extension(
|
pgf_module = Extension(
|
||||||
'pgf',
|
'pgf',
|
||||||
sources = ['pypgf.c', 'marshaller.c', 'expr.c'],
|
sources = [
|
||||||
|
'pypgf.c',
|
||||||
|
'expr.c',
|
||||||
|
'ffi.c',
|
||||||
|
'transactions.c'
|
||||||
|
],
|
||||||
extra_compile_args = ['-std=c99', '-Werror', '-Wno-error=unused-variable', '-Wno-comment'],
|
extra_compile_args = ['-std=c99', '-Werror', '-Wno-error=unused-variable', '-Wno-comment'],
|
||||||
include_dirs = includes,
|
include_dirs = includes,
|
||||||
library_dirs = libraries,
|
library_dirs = libraries,
|
||||||
|
|||||||
41
src/runtime/python/tests/test_transactions.py
Normal file
41
src/runtime/python/tests/test_transactions.py
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
import pytest
|
||||||
|
from pgf import *
|
||||||
|
|
||||||
|
ty = readType("(N -> N) -> P (s z)")
|
||||||
|
pi = 3.142
|
||||||
|
|
||||||
|
# @pytest.fixture(scope="module")
|
||||||
|
# def gr1():
|
||||||
|
# return pgf.readPGF("../haskell/tests/basic.pgf")
|
||||||
|
#
|
||||||
|
# @pytest.fixture(scope="module")
|
||||||
|
# def gr2(gr1):
|
||||||
|
# transaction = [
|
||||||
|
# createFunction("foo", ty, 0, pi),
|
||||||
|
# createCategory("Q", [(BIND_TYPE_EXPLICIT, "x", ty)], pi)
|
||||||
|
# ]
|
||||||
|
# return gr1.modifyPGF(transaction)
|
||||||
|
#
|
||||||
|
# @pytest.fixture(scope="module")
|
||||||
|
# def gr3(gr1):
|
||||||
|
# transaction = [
|
||||||
|
# createFunction("bar", ty, 0, pi),
|
||||||
|
# createCategory("R", [(BIND_TYPE_EXPLICIT, "x", ty)], pi)
|
||||||
|
# ]
|
||||||
|
# return gr1.branchPGF("bar_branch", transaction)
|
||||||
|
#
|
||||||
|
# def original_functions(gr1):
|
||||||
|
# assert gr1.functions == ["c", "ind", "s", "z"]
|
||||||
|
#
|
||||||
|
# def extended_functions(gr2):
|
||||||
|
# assert gr2.functions == ["c", "foo", "ind", "s", "z"]
|
||||||
|
#
|
||||||
|
# def branched_functions(gr3):
|
||||||
|
# assert gr3.functions == ["bar", "c", "ind", "s", "z"]
|
||||||
|
|
||||||
|
def test_non_transactional():
|
||||||
|
gr1 = readPGF("../haskell/tests/basic.pgf")
|
||||||
|
assert gr1.functions == ["c", "ind", "s", "z"]
|
||||||
|
|
||||||
|
gr1.createFunction("foo", ty, 0, pi)
|
||||||
|
assert gr1.functions == ["c", "foo", "ind", "s", "z"]
|
||||||
102
src/runtime/python/transactions.c
Normal file
102
src/runtime/python/transactions.c
Normal file
@@ -0,0 +1,102 @@
|
|||||||
|
#define PY_SSIZE_T_CLEAN
|
||||||
|
#include <Python.h>
|
||||||
|
// #include <stdbool.h>
|
||||||
|
|
||||||
|
#include <pgf/pgf.h>
|
||||||
|
#include "./expr.h"
|
||||||
|
#include "./ffi.h"
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_createFunction(PGFObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
Py_ssize_t size;
|
||||||
|
TypeObject *type;
|
||||||
|
Py_ssize_t arity = 0;
|
||||||
|
float prob = 0.0;
|
||||||
|
if (!PyArg_ParseTuple(args, "s#O!nf", &s, &size, &pgf_TypeType, &type, &arity, &prob))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
PgfText *fname = (PgfText *)PyMem_Malloc(sizeof(PgfText)+size+1);
|
||||||
|
memcpy(fname->text, s, size+1);
|
||||||
|
fname->size = size;
|
||||||
|
|
||||||
|
PgfExn err;
|
||||||
|
pgf_create_function(self->db, self->revision, fname, (PgfType) type, arity, prob, &marshaller, &err);
|
||||||
|
PyMem_Free(fname);
|
||||||
|
if (handleError(err) != PGF_EXN_NONE) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
Py_RETURN_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_dropFunction(PGFObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
Py_ssize_t size;
|
||||||
|
if (!PyArg_ParseTuple(args, "s#", &s, &size))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
PgfText *fname = (PgfText *)PyMem_Malloc(sizeof(PgfText)+size+1);
|
||||||
|
memcpy(fname->text, s, size+1);
|
||||||
|
fname->size = size;
|
||||||
|
|
||||||
|
PgfExn err;
|
||||||
|
pgf_drop_category(self->db, self->revision, fname, &err);
|
||||||
|
PyMem_Free(fname);
|
||||||
|
if (handleError(err) != PGF_EXN_NONE) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
Py_RETURN_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_createCategory(PGFObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
Py_ssize_t size;
|
||||||
|
float prob = 0.0;
|
||||||
|
if (!PyArg_ParseTuple(args, "s#f", &s, &size, prob))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
PgfText *catname = (PgfText *)PyMem_Malloc(sizeof(PgfText)+size+1);
|
||||||
|
memcpy(catname->text, s, size+1);
|
||||||
|
catname->size = size;
|
||||||
|
|
||||||
|
Py_ssize_t n_hypos = 0;
|
||||||
|
PgfTypeHypo *context = NULL;
|
||||||
|
|
||||||
|
PgfExn err;
|
||||||
|
pgf_create_category(self->db, self->revision, catname, n_hypos, context, prob, &marshaller, &err);
|
||||||
|
PyMem_Free(catname);
|
||||||
|
if (handleError(err) != PGF_EXN_NONE) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
Py_RETURN_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_dropCategory(PGFObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
Py_ssize_t size;
|
||||||
|
if (!PyArg_ParseTuple(args, "s#", &s, &size))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
PgfText *catname = (PgfText *)PyMem_Malloc(sizeof(PgfText)+size+1);
|
||||||
|
memcpy(catname->text, s, size+1);
|
||||||
|
catname->size = size;
|
||||||
|
|
||||||
|
PgfExn err;
|
||||||
|
pgf_drop_function(self->db, self->revision, catname, &err);
|
||||||
|
PyMem_Free(catname);
|
||||||
|
if (handleError(err) != PGF_EXN_NONE) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
Py_RETURN_NONE;
|
||||||
|
}
|
||||||
38
src/runtime/python/transactions.h
Normal file
38
src/runtime/python/transactions.h
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
#ifndef PYPGF_TRANSACTIONS_H_
|
||||||
|
#define PYPGF_TRANSACTIONS_H_
|
||||||
|
|
||||||
|
#define PY_SSIZE_T_CLEAN
|
||||||
|
#include <Python.h>
|
||||||
|
|
||||||
|
#include <pgf/pgf.h>
|
||||||
|
|
||||||
|
// typedef struct {
|
||||||
|
// PyObject_HEAD
|
||||||
|
// PyObject *thing;
|
||||||
|
// } TransactionObject;
|
||||||
|
|
||||||
|
// modifyPGF
|
||||||
|
//
|
||||||
|
// branchPGF
|
||||||
|
//
|
||||||
|
// checkoutPGF
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_createFunction(PGFObject *self, PyObject *args);
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_dropFunction(PGFObject *self, PyObject *args);
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_createCategory(PGFObject *self, PyObject *args);
|
||||||
|
|
||||||
|
PyObject *
|
||||||
|
PGF_dropCategory(PGFObject *self, PyObject *args);
|
||||||
|
|
||||||
|
// setGlobalFlag
|
||||||
|
//
|
||||||
|
// setAbstractFlag
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif // PYPGF_TRANSACTIONS_H_
|
||||||
Reference in New Issue
Block a user