You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucy.apache.org by ma...@apache.org on 2013/04/06 01:17:05 UTC

[lucy-commits] [1/3] git commit: refs/heads/python-bindings-wip1 - Use a different hack to get CC name.

Updated Branches:
  refs/heads/python-bindings-wip1 [created] f4377ad08


Use a different hack to get CC name.

Get the name of the C compiler by hacking into the innards of distutils
and accessing a non-public var, albeit one which hasn't moved in many
years.  This is slightly less awful than extracting a name from
sysconfig.


Project: http://git-wip-us.apache.org/repos/asf/lucy/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucy/commit/f1f2ca4c
Tree: http://git-wip-us.apache.org/repos/asf/lucy/tree/f1f2ca4c
Diff: http://git-wip-us.apache.org/repos/asf/lucy/diff/f1f2ca4c

Branch: refs/heads/python-bindings-wip1
Commit: f1f2ca4c46998551a683bf3f872549ade67bc193
Parents: 2961103
Author: Marvin Humphrey <ma...@rectangular.com>
Authored: Fri Apr 5 15:46:11 2013 -0700
Committer: Marvin Humphrey <ma...@rectangular.com>
Committed: Fri Apr 5 15:46:11 2013 -0700

----------------------------------------------------------------------
 clownfish/compiler/python/setup.py |   28 ++++++++++++++++------------
 1 files changed, 16 insertions(+), 12 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucy/blob/f1f2ca4c/clownfish/compiler/python/setup.py
----------------------------------------------------------------------
diff --git a/clownfish/compiler/python/setup.py b/clownfish/compiler/python/setup.py
index 721a0ed..a54b463 100644
--- a/clownfish/compiler/python/setup.py
+++ b/clownfish/compiler/python/setup.py
@@ -11,26 +11,30 @@ import shutil
 import subprocess
 import sysconfig
 
+# Get a compiler object and and strings representing the compiler type and
+# CFLAGS.
+compiler = distutils.ccompiler.new_compiler()
+cflags = sysconfig.get_config_var('CFLAGS')
+compiler_type = distutils.ccompiler.get_default_compiler()
+
+# There's no public way to get a string representing the compiler executable
+# out of distutils, but the member variable has been in the same place for a
+# long time, so violating encapsulation may be ok.
+compiler_name = " ".join(compiler.compiler)
+
 BASE_DIR = os.path.abspath(os.path.join(os.pardir, os.pardir, os.pardir))
 PARENT_DIR      = os.path.abspath(os.pardir)
 CFC_SOURCE_DIR  = os.path.join(PARENT_DIR, 'src')
 CFC_INCLUDE_DIR = os.path.join(PARENT_DIR, 'include')
 COMMON_SOURCE_DIR    = os.path.join(PARENT_DIR, 'common')
 CHARMONIZER_C        = os.path.join(COMMON_SOURCE_DIR, 'charmonizer.c')
-CHARMONIZER_EXE_NAME = 'charmonizer' + sysconfig.get_config_var("EXE")
+CHARMONIZER_EXE_NAME = compiler.executable_filename('charmonizer')
 CHARMONIZER_EXE_PATH = os.path.join(os.curdir, CHARMONIZER_EXE_NAME)
 CHARMONY_H_PATH      = 'charmony.h'
 LEMON_DIR = os.path.join(BASE_DIR, 'lemon')
-LEMON_EXE_NAME = 'lemon' + sysconfig.get_config_var("EXE")
+LEMON_EXE_NAME = compiler.executable_filename('lemon')
 LEMON_EXE_PATH = os.path.join(LEMON_DIR, LEMON_EXE_NAME)
 
-# There's no good way to get a string representing the compiler executable out
-# of distutils, so for now we'll kludge it and assume it's the same as the
-# compiler used to build python.
-python_compiler = sysconfig.get_config_var('CC')
-cflags = sysconfig.get_config_var('CFLAGS')
-compiler_type   = distutils.ccompiler.get_default_compiler()
-
 def _quotify(text):
     text = text.replace('\\', '\\\\')
     text = text.replace('"', '\\"')
@@ -61,7 +65,7 @@ class charmony(_Command):
     def run(self):
         # Compile charmonizer.
         if newer_group([CHARMONIZER_C], CHARMONIZER_EXE_PATH):
-            command = [python_compiler]
+            command = [compiler_name]
             if compiler_type == 'msvc':
                 command.append('/Fe' + CHARMONIZER_EXE_PATH)
             else:
@@ -74,7 +78,7 @@ class charmony(_Command):
         if newer_group([CHARMONIZER_EXE_PATH], CHARMONY_H_PATH):
             command = [
                 CHARMONIZER_EXE_PATH,
-                '--cc=' + _quotify(python_compiler),
+                '--cc=' + _quotify(compiler_name),
                 '--enable-c',
                 '--',
                 cflags
@@ -93,7 +97,7 @@ class lemon(_Command):
         pass
     def run(self):
         if not os.path.exists(LEMON_EXE_PATH):
-            _run_make(['CC=' + python_compiler], directory=LEMON_DIR)
+            _run_make(['CC=' + _quotify(compiler_name)], directory=LEMON_DIR)
 
 class my_clean(_clean):
     paths_to_clean = [


[lucy-commits] [3/3] git commit: refs/heads/python-bindings-wip1 - Add Python C binding for CFCHierarchy.

Posted by ma...@apache.org.
Add Python C binding for CFCHierarchy.


Project: http://git-wip-us.apache.org/repos/asf/lucy/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucy/commit/f4377ad0
Tree: http://git-wip-us.apache.org/repos/asf/lucy/tree/f4377ad0
Diff: http://git-wip-us.apache.org/repos/asf/lucy/diff/f4377ad0

Branch: refs/heads/python-bindings-wip1
Commit: f4377ad0840bb3d450243dcc80c721e6799eb570
Parents: 3e8f569
Author: Marvin Humphrey <ma...@rectangular.com>
Authored: Fri Apr 5 16:06:19 2013 -0700
Committer: Marvin Humphrey <ma...@rectangular.com>
Committed: Fri Apr 5 16:10:54 2013 -0700

----------------------------------------------------------------------
 clownfish/compiler/python/clownfish/_cfc.c         |  128 +++++++++++++++
 .../compiler/python/clownfish/cfc/__init__.py      |    2 +
 clownfish/compiler/python/setup.py                 |    5 +-
 3 files changed, 134 insertions(+), 1 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucy/blob/f4377ad0/clownfish/compiler/python/clownfish/_cfc.c
----------------------------------------------------------------------
diff --git a/clownfish/compiler/python/clownfish/_cfc.c b/clownfish/compiler/python/clownfish/_cfc.c
new file mode 100644
index 0000000..f4bd341
--- /dev/null
+++ b/clownfish/compiler/python/clownfish/_cfc.c
@@ -0,0 +1,128 @@
+
+#include "Python.h"
+#include "CFC.h"
+
+typedef struct {
+    PyObject_HEAD
+    void *cfc_obj;
+} CFCPyWrapper;
+
+static CFCHierarchy*
+S_extract_hierarchy(PyObject *wrapper) {
+    return (CFCHierarchy*)((CFCPyWrapper*)wrapper)->cfc_obj;
+}
+
+static CFCPyWrapper*
+S_CFCHierarchy_new(PyTypeObject *type, PyObject *args,
+                   PyObject *keyword_args) {
+    char *dest = NULL;
+    char *keywords[] = {"dest", NULL};
+    int result = PyArg_ParseTupleAndKeywords(args, keyword_args, "|s",
+                                             keywords, &dest);
+    if (!result) { return NULL; }
+    if (!dest) {
+        PyErr_SetString(PyExc_TypeError, "Missing required arg 'dest'");
+        return NULL;
+    }
+    CFCPyWrapper *wrapper = (CFCPyWrapper*)type->tp_alloc(type, 0);
+    if (wrapper) {
+        wrapper->cfc_obj = CFCHierarchy_new(dest);
+    }
+    return wrapper;
+}
+
+static void
+S_CFCHierarchy_dealloc(CFCPyWrapper *wrapper) {
+    CFCBase *temp = (CFCBase*)wrapper->cfc_obj;
+    wrapper->cfc_obj = NULL;
+    CFCBase_decref(temp);
+    Py_TYPE(wrapper)->tp_free(wrapper);
+}
+
+static PyObject*
+S_CFCHierarchy_add_include_dir(PyObject *wrapper, PyObject *dir) {
+    CFCHierarchy *wrapped  = S_extract_hierarchy(wrapper);
+    CFCHierarchy_add_include_dir(S_extract_hierarchy(wrapper),
+                                 PyUnicode_AsUTF8(dir));
+    Py_RETURN_NONE;
+}
+
+static PyModuleDef cfc_module_def = {
+    PyModuleDef_HEAD_INIT,
+    "clownfish.cfc",
+    "CFC: Clownfish compiler",
+    -1,
+    NULL, NULL, NULL, NULL, NULL
+};
+
+static PyModuleDef cfc_model_module_def = {
+    PyModuleDef_HEAD_INIT,
+    "clownfish.cfc.model",
+    "CFC classes which model language constructs",
+    -1,
+    NULL, NULL, NULL, NULL, NULL
+};
+
+static PyMethodDef hierarchy_methods[] = {
+    {"add_include_dir", (PyCFunction)S_CFCHierarchy_add_include_dir, METH_O,
+     NULL},
+    {NULL}
+};
+
+static PyTypeObject CFCHierarchy_pytype = {
+    PyVarObject_HEAD_INIT(NULL, 0)
+    "clownfish.cfc.model.Hierarchy",    // tp_name
+    sizeof(CFCPyWrapper),               // tp_basicsize
+    0,                                  // tp_itemsize
+    (destructor)S_CFCHierarchy_dealloc, // tp_dealloc
+    0,                                  // tp_print
+    0,                                  // tp_getattr
+    0,                                  // tp_setattr
+    0,                                  // tp_reserved
+    0,                                  // tp_repr
+    0,                                  // tp_as_number
+    0,                                  // tp_as_sequence
+    0,                                  // tp_as_mapping
+    0,                                  // tp_hash
+    0,                                  // tp_call
+    0,                                  // tp_str
+    0,                                  // tp_getattro
+    0,                                  // tp_setattro
+    0,                                  // tp_as_buffer
+    Py_TPFLAGS_DEFAULT,                 // tp_flags
+    "CFCHierarchy",                     // tp_doc
+    0,                                  // tp_traverse
+    0,                                  // tp_clear
+    0,                                  // tp_richcompare
+    0,                                  // tp_weaklistoffset
+    0,                                  // tp_iter
+    0,                                  // tp_iternext
+    hierarchy_methods,                  // tp_methods
+    0,                                  // tp_members
+    0,                                  // tp_getset
+    0,                                  // tp_base
+    0,                                  // tp_dict
+    0,                                  // tp_descr_get
+    0,                                  // tp_descr_set
+    0,                                  // tp_dictoffset
+    0,                                  // tp_init
+    0,                                  // tp_allow
+    (newfunc)S_CFCHierarchy_new         // tp_new
+};
+
+PyMODINIT_FUNC
+PyInit__cfc(void) {
+    if (PyType_Ready(&CFCHierarchy_pytype) < 0) {
+        return NULL;
+    }
+    PyObject *cfc_module = PyModule_Create(&cfc_module_def);
+    PyObject *cfc_model_module = PyModule_Create(&cfc_model_module_def);
+    PyModule_AddObject(cfc_module, "model", (PyObject*)cfc_model_module);
+    Py_INCREF(&CFCHierarchy_pytype);
+    PyModule_AddObject(cfc_model_module, "Hierarchy",
+                       (PyObject*)&CFCHierarchy_pytype);
+
+    return cfc_module;
+}
+
+

http://git-wip-us.apache.org/repos/asf/lucy/blob/f4377ad0/clownfish/compiler/python/clownfish/cfc/__init__.py
----------------------------------------------------------------------
diff --git a/clownfish/compiler/python/clownfish/cfc/__init__.py b/clownfish/compiler/python/clownfish/cfc/__init__.py
new file mode 100644
index 0000000..d539758
--- /dev/null
+++ b/clownfish/compiler/python/clownfish/cfc/__init__.py
@@ -0,0 +1,2 @@
+from clownfish._cfc import *
+

http://git-wip-us.apache.org/repos/asf/lucy/blob/f4377ad0/clownfish/compiler/python/setup.py
----------------------------------------------------------------------
diff --git a/clownfish/compiler/python/setup.py b/clownfish/compiler/python/setup.py
index 819eb7e..6596f80 100644
--- a/clownfish/compiler/python/setup.py
+++ b/clownfish/compiler/python/setup.py
@@ -44,6 +44,7 @@ paths_to_clean = [
     CHARMONY_H_PATH,
     '_charm*',
 ]
+c_filepaths.append(os.path.join('clownfish', '_cfc.c'))
 for (dirpath, dirnames, files) in os.walk(CFC_SOURCE_DIR):
     for filename in files:
         if filename.endswith('.y'):
@@ -159,7 +160,7 @@ class my_build(_build):
         self.run_command('parsers')
         _build.run(self)
 
-cfc_extension = Extension('clownfish.cfc',
+cfc_extension = Extension('clownfish._cfc',
                           define_macros = [('CFCPYTHON', None)],
                           include_dirs = [
                               CFC_INCLUDE_DIR,
@@ -174,6 +175,8 @@ setup(name = 'clownfish-cfc',
       author = 'Apache Lucy Project',
       author_email = 'dev at lucy dot apache dot org',
       url = 'http://lucy.apache.org',
+      packages = ['clownfish.cfc',
+                 ],
       cmdclass = {
           'build': my_build,
           'clean': my_clean,


[lucy-commits] [2/3] git commit: refs/heads/python-bindings-wip1 - Add setup.py command to build .y parsers.

Posted by ma...@apache.org.
Add setup.py command to build .y parsers.

Use lemon to build parsers.  Refactor accumulation of source file names.


Project: http://git-wip-us.apache.org/repos/asf/lucy/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucy/commit/3e8f5692
Tree: http://git-wip-us.apache.org/repos/asf/lucy/tree/3e8f5692
Diff: http://git-wip-us.apache.org/repos/asf/lucy/diff/3e8f5692

Branch: refs/heads/python-bindings-wip1
Commit: 3e8f56928b3489dd1f9172c6e696331d814601ea
Parents: f1f2ca4
Author: Marvin Humphrey <ma...@rectangular.com>
Authored: Fri Apr 5 15:56:06 2013 -0700
Committer: Marvin Humphrey <ma...@rectangular.com>
Committed: Fri Apr 5 15:56:06 2013 -0700

----------------------------------------------------------------------
 clownfish/compiler/python/setup.py |   56 ++++++++++++++++++++++++-------
 1 files changed, 44 insertions(+), 12 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucy/blob/3e8f5692/clownfish/compiler/python/setup.py
----------------------------------------------------------------------
diff --git a/clownfish/compiler/python/setup.py b/clownfish/compiler/python/setup.py
index a54b463..819eb7e 100644
--- a/clownfish/compiler/python/setup.py
+++ b/clownfish/compiler/python/setup.py
@@ -7,6 +7,7 @@ import distutils.ccompiler
 import os
 import glob
 import platform
+import re
 import shutil
 import subprocess
 import sysconfig
@@ -35,6 +36,32 @@ LEMON_DIR = os.path.join(BASE_DIR, 'lemon')
 LEMON_EXE_NAME = compiler.executable_filename('lemon')
 LEMON_EXE_PATH = os.path.join(LEMON_DIR, LEMON_EXE_NAME)
 
+# Accumulate lists of source files and target files.
+c_filepaths = []
+y_filepaths = []
+paths_to_clean = [
+    CHARMONIZER_EXE_PATH,
+    CHARMONY_H_PATH,
+    '_charm*',
+]
+for (dirpath, dirnames, files) in os.walk(CFC_SOURCE_DIR):
+    for filename in files:
+        if filename.endswith('.y'):
+            path = os.path.join(dirpath, filename)
+            y_filepaths.append(path)
+            path = re.sub(r'y$', 'h', path)
+            paths_to_clean.append(path)
+            path = re.sub(r'h$', 'c', path)
+            paths_to_clean.append(path)
+            c_filepaths.append(path)
+            path = compiler.object_filenames([path])[0]
+            paths_to_clean.append(path)
+        if filename.endswith('.c'):
+            path = os.path.join(dirpath, filename)
+            c_filepaths.append(path)
+            path = compiler.object_filenames([path])[0]
+            paths_to_clean.append(path)
+
 def _quotify(text):
     text = text.replace('\\', '\\\\')
     text = text.replace('"', '\\"')
@@ -99,16 +126,25 @@ class lemon(_Command):
         if not os.path.exists(LEMON_EXE_PATH):
             _run_make(['CC=' + _quotify(compiler_name)], directory=LEMON_DIR)
 
+class parsers(_Command):
+    description = "Run .y files through lemon"
+    user_options = []
+    def initialize_options(self):
+        pass
+    def finalize_options(self):
+        pass
+    def run(self):
+        for y_path in y_filepaths:
+            target = re.sub(r'y$', 'c', y_path)
+            if newer_group([y_path], target):
+                command = [LEMON_EXE_PATH, '-c', y_path]
+                subprocess.check_call(command)
+
 class my_clean(_clean):
-    paths_to_clean = [
-        CHARMONIZER_EXE_PATH,
-        CHARMONY_H_PATH,
-        '_charm*',
-    ]
     def run(self):
         _clean.run(self)
         _run_make(command=['clean'], directory=LEMON_DIR)
-        for elem in self.paths_to_clean:
+        for elem in paths_to_clean:
             for path in glob.glob(elem):
                 print("removing " + path)
                 if os.path.isdir(path):
@@ -120,14 +156,9 @@ class my_build(_build):
     def run(self):
         self.run_command('charmony')
         self.run_command('lemon')
+        self.run_command('parsers')
         _build.run(self)
 
-c_filepaths = []
-for (dirpath, dirnames, files) in os.walk(CFC_SOURCE_DIR):
-    for filename in files:
-        if (filename.endswith('.c')):
-            c_filepaths.append(os.path.join(dirpath, filename))
-
 cfc_extension = Extension('clownfish.cfc',
                           define_macros = [('CFCPYTHON', None)],
                           include_dirs = [
@@ -148,6 +179,7 @@ setup(name = 'clownfish-cfc',
           'clean': my_clean,
           'lemon': lemon,
           'charmony': charmony,
+          'parsers': parsers,
       },
       ext_modules = [cfc_extension])