[pypy-svn] r19297 - in pypy/dist/pypy/translator: c c/test tool
arigo at codespeak.net
arigo at codespeak.net
Mon Oct 31 20:52:27 CET 2005
Author: arigo
Date: Mon Oct 31 20:52:22 2005
New Revision: 19297
Modified:
pypy/dist/pypy/translator/c/genc.py
pypy/dist/pypy/translator/c/test/test_stackless.py
pypy/dist/pypy/translator/c/test/test_standalone.py
pypy/dist/pypy/translator/tool/cbuild.py
Log:
Generate a Makefile for stand-alone targets.
(cbuild.py is quite messy, so this involved some refactoring...)
Modified: pypy/dist/pypy/translator/c/genc.py
==============================================================================
--- pypy/dist/pypy/translator/c/genc.py (original)
+++ pypy/dist/pypy/translator/c/genc.py Mon Oct 31 20:52:22 2005
@@ -5,7 +5,7 @@
from pypy.translator.c.extfunc import pre_include_code_lines
from pypy.translator.gensupp import uniquemodulename, NameManager
from pypy.translator.tool.cbuild import compile_c_module
-from pypy.translator.tool.cbuild import build_executable
+from pypy.translator.tool.cbuild import build_executable, CCompiler
from pypy.translator.tool.cbuild import import_module_from_directory
from pypy.rpython.rmodel import getfunctionptr
from pypy.rpython.lltypesystem import lltype
@@ -76,6 +76,8 @@
defines = defines)
self.c_source_filename = py.path.local(cfile)
self.extrafiles = extra
+ if self.standalone:
+ self.gen_makefile(targetdir)
return cfile
@@ -120,16 +122,21 @@
# signature: list-of-strings -> int
return getfunctionptr(self.translator, self.translator.entrypoint)
- def compile(self):
- assert self.c_source_filename
- assert not self._compiled
+ def getccompiler(self, extra_includes):
# XXX for now, we always include Python.h
from distutils import sysconfig
python_inc = sysconfig.get_python_inc()
- self.executable_name = build_executable(
+ return CCompiler(
[self.c_source_filename] + self.extrafiles,
- include_dirs = [autopath.this_dir, python_inc, str(self.targetdir)],
- libraries=self.libraries)
+ include_dirs = [autopath.this_dir, python_inc] + extra_includes,
+ libraries = self.libraries)
+
+ def compile(self):
+ assert self.c_source_filename
+ assert not self._compiled
+ compiler = self.getccompiler(extra_includes=[str(self.targetdir)])
+ compiler.build()
+ self.executable_name = str(compiler.outputfilename)
self._compiled = True
return self.executable_name
@@ -137,6 +144,46 @@
assert self._compiled
return py.process.cmdexec('"%s" %s' % (self.executable_name, args))
+ def gen_makefile(self, targetdir):
+ def write_list(lst, prefix):
+ for i, fn in enumerate(lst):
+ print >> f, prefix, fn,
+ if i < len(lst)-1:
+ print >> f, '\\'
+ else:
+ print >> f
+ prefix = ' ' * len(prefix)
+
+ compiler = self.getccompiler(extra_includes=['.'])
+ cfiles = []
+ ofiles = []
+ for fn in compiler.cfilenames:
+ fn = py.path.local(fn).basename
+ assert fn.endswith('.c')
+ cfiles.append(fn)
+ ofiles.append(fn[:-2] + '.o')
+
+ f = targetdir.join('Makefile').open('w')
+ print >> f, '# automatically generated Makefile'
+ print >> f
+ print >> f, 'TARGET =', py.path.local(compiler.outputfilename).basename
+ print >> f
+ write_list(cfiles, 'SOURCES =')
+ print >> f
+ write_list(ofiles, 'OBJECTS =')
+ print >> f
+ args = ['-l'+libname for libname in compiler.libraries]
+ print >> f, 'LIBS =', ' '.join(args)
+ args = ['-L'+path for path in compiler.library_dirs]
+ print >> f, 'LIBDIRS =', ' '.join(args)
+ args = ['-I'+path for path in compiler.include_dirs]
+ write_list(args, 'INCLUDEDIRS =')
+ print >> f
+ print >> f, 'CFLAGS =', ' '.join(compiler.compile_extra)
+ print >> f, 'LDFLAGS =', ' '.join(compiler.link_extra)
+ print >> f, MAKEFILE.strip()
+ f.close()
+
def translator2database(translator):
pf = lltype.pyobjectptr(translator.entrypoint)
@@ -345,6 +392,7 @@
fc.close()
print >> f
+
# this function acts as the fallback for small sources for now.
# Maybe we drop this completely if source splitting is the way
# to go. Currently, I'm quite fine with keeping a working fallback.
@@ -655,3 +703,16 @@
extra_compile_args = extra_compile_args,
include_dirs = [PYPY_INCLUDE_DIR])])
'''
+
+MAKEFILE = '''
+CC = gcc
+
+$(TARGET): $(OBJECTS)
+\t$(CC) $(LDFLAGS) -o $@ $(OBJECTS) $(LIBDIRS) $(LIBS)
+
+%.o: %.c
+\t$(CC) $(CFLAGS) -o $@ -c $< $(INCLUDEDIRS)
+
+clean:
+\trm -f $(OBJECTS)
+'''
Modified: pypy/dist/pypy/translator/c/test/test_stackless.py
==============================================================================
--- pypy/dist/pypy/translator/c/test/test_stackless.py (original)
+++ pypy/dist/pypy/translator/c/test/test_stackless.py Mon Oct 31 20:52:22 2005
@@ -1,5 +1,4 @@
from pypy.translator.translator import Translator
-from pypy.translator.tool.cbuild import build_executable
from pypy.annotation.model import SomeList, SomeString
from pypy.annotation.listdef import ListDef
from pypy.rpython.rstack import stack_unwind, stack_frames_depth, stack_too_big
Modified: pypy/dist/pypy/translator/c/test/test_standalone.py
==============================================================================
--- pypy/dist/pypy/translator/c/test/test_standalone.py (original)
+++ pypy/dist/pypy/translator/c/test/test_standalone.py Mon Oct 31 20:52:22 2005
@@ -1,5 +1,4 @@
from pypy.translator.translator import Translator
-from pypy.translator.tool.cbuild import build_executable
from pypy.annotation.model import SomeList, SomeString
from pypy.annotation.listdef import ListDef
import os
Modified: pypy/dist/pypy/translator/tool/cbuild.py
==============================================================================
--- pypy/dist/pypy/translator/tool/cbuild.py (original)
+++ pypy/dist/pypy/translator/tool/cbuild.py Mon Oct 31 20:52:22 2005
@@ -254,55 +254,64 @@
return spawn(cmd, *args, **kwds)
return spawn_and_log
-def build_executable(cfilenames, outputfilename=None, include_dirs=None,
- libraries=[], library_dirs=None):
- from distutils.ccompiler import new_compiler
- ext = ''
- compile_extra = []
- link_extra = []
-
- if not include_dirs:
- include_dirs = []
- if not library_dirs:
- library_dirs = []
- if not sys.platform in ('win32', 'darwin'): # xxx
- libraries.append('m')
- libraries.append('pthread')
- compile_extra += ['-O2', '-pthread']
- link_extra += ['-pthread']
- if sys.platform == 'darwin':
- include_dirs.append('/sw/include')
- compile_extra += ['-O2']
-
- if outputfilename is None:
- outputfilename = py.path.local(cfilenames[0]).new(ext=ext)
- else:
- outputfilename = py.path.local(outputfilename)
-
- if sys.platform == 'darwin':
- library_dirs=['/sw/lib']
-
- compiler = new_compiler()
- compiler.spawn = log_spawned_cmd(compiler.spawn)
- objects = []
- for cfile in cfilenames:
- cfile = py.path.local(cfile)
- old = cfile.dirpath().chdir()
- try:
- res = compiler.compile([cfile.basename],
- include_dirs=include_dirs,
- extra_preargs=compile_extra)
- assert len(res) == 1
- cobjfile = py.path.local(res[0])
- assert cobjfile.check()
- objects.append(str(cobjfile))
- finally:
- old.chdir()
- compiler.link_executable(objects, str(outputfilename),
- libraries=libraries,
- extra_preargs=link_extra,
- library_dirs=library_dirs)
- return str(outputfilename)
+
+class CCompiler:
+
+ def __init__(self, cfilenames, outputfilename=None, include_dirs=[],
+ libraries=[], library_dirs=[]):
+ self.cfilenames = cfilenames
+ ext = ''
+ self.compile_extra = []
+ self.link_extra = []
+ self.libraries = list(libraries)
+ self.include_dirs = list(include_dirs)
+ self.library_dirs = list(library_dirs)
+ if not sys.platform in ('win32', 'darwin'): # xxx
+ if 'm' not in self.libraries:
+ self.libraries.append('m')
+ if 'pthread' not in self.libraries:
+ self.libraries.append('pthread')
+ self.compile_extra += ['-O2', '-pthread']
+ self.link_extra += ['-pthread']
+ if sys.platform == 'darwin':
+ if '/sw/include' not in self.include_dirs:
+ self.include_dirs.append('/sw/include')
+ if '/sw/lib' not in self.library_dirs:
+ self.library_dirs.append('/sw/lib')
+ self.compile_extra += ['-O2']
+
+ if outputfilename is None:
+ self.outputfilename = py.path.local(cfilenames[0]).new(ext=ext)
+ else:
+ self.outputfilename = py.path.local(outputfilename)
+
+ def build(self):
+ from distutils.ccompiler import new_compiler
+ compiler = new_compiler()
+ compiler.spawn = log_spawned_cmd(compiler.spawn)
+ objects = []
+ for cfile in self.cfilenames:
+ cfile = py.path.local(cfile)
+ old = cfile.dirpath().chdir()
+ try:
+ res = compiler.compile([cfile.basename],
+ include_dirs=self.include_dirs,
+ extra_preargs=self.compile_extra)
+ assert len(res) == 1
+ cobjfile = py.path.local(res[0])
+ assert cobjfile.check()
+ objects.append(str(cobjfile))
+ finally:
+ old.chdir()
+ compiler.link_executable(objects, str(self.outputfilename),
+ libraries=self.libraries,
+ extra_preargs=self.link_extra,
+ library_dirs=self.library_dirs)
+
+def build_executable(*args, **kwds):
+ compiler = CCompiler(*args, **kwds)
+ compiler.build()
+ return str(compiler.outputfilename)
def check_boehm_presence():
from pypy.tool.udir import udir
More information about the Pypy-commit
mailing list