source: inundation/ga/storm_surge/pyvolution/compile.py @ 826

Last change on this file since 826 was 756, checked in by ole, 20 years ago

Fixed wrong flag for 64 bit stuff

File size: 7.5 KB
Line 
1"""compile.py - compile Python C-extension
2
3   Commandline usage:
4     python compile.py <filename>
5
6   Usage from within Python:
7     import compile
8     compile.compile(<filename>,..)
9
10   Ole Nielsen, Oct 2001     
11"""     
12
13 
14def compile(FNs=None, CC=None, LD = None, SFLAG = None, verbose = 1):
15  """compile(FNs=None, CC=None, LD = None, SFLAG = None):
16 
17     Compile FN(s) using compiler CC (e.g. mpicc),
18     Loader LD and shared flag SFLAG.
19     If CC is absent use default compiler dependent on platform
20     if LD is absent CC is used.
21     if SFLAG is absent platform default is used
22     FNs can be either one filename or a list of filenames
23     In the latter case, the first will be used to name so file.
24  """
25 
26 
27  ###########################jhdsgfjgdjfg
28 
29  import os, string, sys, types
30 
31  # Input check
32  #
33  assert not FNs is None, "No filename provided"
34
35  if not type(FNs) == types.ListType:
36    FNs = [FNs]
37
38
39  libext = 'so' #Default extension (Unix)
40  libs = ''
41  version = sys.version[:3]
42 
43  # Determine platform and compiler
44  #
45  if sys.platform == 'sunos5':  #Solaris
46    if CC:
47      compiler = CC
48    else: 
49      compiler = 'gcc'
50    if LD:
51      loader = LD
52    else: 
53      loader = compiler
54    if SFLAG:
55      sharedflag = SFLAG
56    else: 
57      sharedflag = 'G'
58     
59  elif sys.platform == 'osf1V5':  #Compaq AlphaServer
60    if CC:
61      compiler = CC
62    else: 
63      compiler = 'cc'
64    if LD:
65      loader = LD
66    else: 
67      loader = compiler
68    if SFLAG:
69      sharedflag = SFLAG
70    else: 
71      sharedflag = 'shared'   
72     
73  elif sys.platform == 'linux2':  #Linux
74    if CC:
75      compiler = CC
76    else: 
77      compiler = 'gcc'
78    if LD:
79      loader = LD
80    else: 
81      loader = compiler
82    if SFLAG:
83      sharedflag = SFLAG
84    else: 
85      sharedflag = 'shared'   
86     
87  elif sys.platform == 'darwin':  #Mac OS X:
88    if CC:
89      compiler = CC
90    else: 
91      compiler = 'cc'
92    if LD:
93      loader = LD
94    else: 
95      loader = compiler
96    if SFLAG:
97      sharedflag = SFLAG
98    else: 
99      sharedflag = 'bundle -flat_namespace -undefined suppress'
100
101  elif sys.platform == 'cygwin':  #Cygwin (compilation same as linux)
102    if CC:
103      compiler = CC
104    else: 
105      compiler = 'gcc'
106    if LD:
107      loader = LD
108    else: 
109      loader = compiler
110    if SFLAG:
111      sharedflag = SFLAG
112    else: 
113      sharedflag = 'shared'
114    libext = 'dll'
115    libs = '/lib/python%s/config/libpython%s.dll.a' %(version,version)
116     
117  elif sys.platform == 'win32':  #Windows
118    if CC:
119      compiler = CC
120    else: 
121      compiler = 'gcc'
122    if LD:
123      loader = LD
124    else: 
125      loader = compiler
126    if SFLAG:
127      sharedflag = SFLAG
128    else: 
129      sharedflag = 'shared'
130    libext = 'dll'
131
132    v = version.replace('.','')
133    dllfilename = 'python%s.dll' %(v)
134    libs = os.path.join(sys.exec_prefix,dllfilename)
135     
136     
137  else:
138    if verbose: print "Unrecognised platform %s - revert to default"\
139                %sys.platform
140   
141    if CC:
142      compiler = CC
143    else: 
144      compiler = 'cc'
145    if LD:
146      loader = LD
147    else: 
148      loader = 'ld'
149    if SFLAG:
150      sharedflag = SFLAG
151    else: 
152      sharedflag = 'G'
153
154           
155  # Find location of include files
156  #
157  if sys.platform == 'win32':  #Windows
158    include = os.path.join(sys.exec_prefix, 'include')   
159  else: 
160    include = os.path.join(os.path.join(sys.exec_prefix, 'include'),
161                           'python'+version)
162
163  # Check existence of Python.h
164  #
165  headerfile = include + os.sep +'Python.h'
166  try:
167    open(headerfile, 'r')
168  except:
169    raise """Did not find Python header file %s.
170    Make sure files for Python C-extensions are installed.
171    In debian linux, for example, you need to install a
172    package called something like python2.3-dev""" %headerfile
173 
174 
175  # Check filename(s)
176  #
177  object_files = ''
178  for FN in FNs:       
179    root, ext = os.path.splitext(FN)
180    if ext == '':
181      FN = FN + '.c'
182    elif ext.lower() != '.c':
183      raise Exception, "Unrecognised extension: " + FN
184   
185    try:
186      open(FN,'r')
187    except:   
188      raise Exception, "Could not open: " + FN
189
190    if not object_files: root1 = root  #Remember first filename       
191    object_files += root + '.o ' 
192 
193 
194    # Compile
195    #
196    s = "%s -c %s -I%s -o %s.o -Wall -O3" %(compiler, FN, include, root)
197
198    if os.name == 'posix' and os.uname()[4] == 'x86_64':
199      #Extra flags for 64 bit architectures
200
201      #FIXME: Which one?
202      #s += ' -fPIC'
203      s += ' -fPIC -m64' 
204     
205     
206    if verbose:
207      print s
208    else:
209      s = s + ' 2> /dev/null' #Suppress errors
210 
211    try:
212      err = os.system(s)
213      if err != 0:
214          raise 'Attempting to compile %s failed - please try manually' %FN
215    except:
216      raise 'Could not compile %s - please try manually' %FN 
217
218 
219  # Make shared library (*.so or *.dll)
220 
221  s = "%s -%s %s -o %s.%s %s -lm" %(loader, sharedflag, object_files, root1, libext, libs)
222  if verbose:
223    print s
224  else:
225    s = s + ' 2> /dev/null' #Suppress warnings
226 
227  try: 
228    err=os.system(s)
229    if err != 0:       
230        raise 'Atempting to link %s failed - please try manually' %root1     
231  except:
232    raise 'Could not link %s - please try manually' %root1
233   
234
235def can_use_C_extension(filename):
236    """Determine whether specified C-extension
237    can and should be used.
238    """
239
240    from config import use_extensions
241
242    from os.path import splitext
243
244    root, ext = splitext(filename)
245   
246    C=False
247    if use_extensions:
248        try:
249            s = 'import %s' %root
250            #print s
251            exec(s)
252        except:
253            try:
254                open(filename)
255            except:
256                msg = 'C extension %s cannot be opened' %filename
257                print msg               
258            else:   
259                print '------- Trying to compile c-extension %s' %filename
260           
261                try:
262                    compile(filename)
263                except:
264                    print 'WARNING: Could not compile C-extension %s'\
265                          %filename
266                else:
267                    try:
268                        exec('import %s' %root)
269                    except:
270                        msg = 'C extension %s seems to compile OK, '
271                        msg += 'but it can still not be imported.'
272                        raise msg
273                    else:
274                        C=True
275        else:
276            C=True
277           
278    if not C:
279        pass
280        print 'NOTICE: C-extension %s not used' %filename
281
282    return C
283
284
285
286
287if __name__ == '__main__':
288
289
290  import sys, os
291  from os.path import splitext
292 
293  if len(sys.argv) > 1:
294      files = sys.argv[1:]
295      for filename in files:
296          root, ext = splitext(filename)
297
298          if ext <> '.c':
299              print 'WARNING (compile.py): Skipping %s. I only compile C-files.' %filename
300     
301  else: 
302      #path = os.path.split(sys.argv[0])[0] or os.getcwd()
303      path = '.'
304      files = os.listdir(path)
305     
306     
307
308  for filename in files:
309      root, ext = splitext(filename)
310
311      if ext == '.c':
312          for x in ['.dll', '.so']:
313              try:
314                  os.remove(root + x)
315              except:
316                  pass
317
318          print '--------------- Trying to compile c-extension %s' %filename
319          try:
320              compile(filename)
321          except:
322              print 'Could not compile C extension %s' %filename           
323          else:
324              print 'C extension %s OK' %filename
325          print   
326       
327
Note: See TracBrowser for help on using the repository browser.