]>
crepu.dev Git - config.git/blob - djavu-asus/elpy/rpc-venv/lib/python3.11/site-packages/setuptools/_distutils/bcppcompiler.py
1 """distutils.bcppcompiler
3 Contains BorlandCCompiler, an implementation of the abstract CCompiler class
4 for the Borland C++ compiler.
7 # This implementation by Lyle Johnson, based on the original msvccompiler.py
8 # module and using the directions originally published by Gordon Williams.
10 # XXX looks like there's a LOT of overlap between these two classes:
11 # someone should sit down and factor out the common code as
12 # WindowsCCompiler! --GPW
25 from .ccompiler
import CCompiler
, gen_preprocess_options
26 from .file_util
import write_file
27 from .dep_util
import newer
32 "bcppcompiler is deprecated and slated to be removed "
33 "in the future. Please discontinue use or file an issue "
34 "with pypa/distutils describing your use case.",
39 class BCPPCompiler(CCompiler
):
40 """Concrete class that implements an interface to the Borland C/C++
41 compiler, as defined by the CCompiler abstract class.
44 compiler_type
= 'bcpp'
46 # Just set this so CCompiler's constructor doesn't barf. We currently
47 # don't use the 'set_executables()' bureaucracy provided by CCompiler,
48 # as it really isn't necessary for this sort of single-compiler class.
49 # Would be nice to have a consistent interface with UnixCCompiler,
50 # though, so it's worth thinking about.
53 # Private class data (need to distinguish C from C++ source for compiler)
54 _c_extensions
= ['.c']
55 _cpp_extensions
= ['.cc', '.cpp', '.cxx']
57 # Needed for the filename generation methods provided by the
58 # base class, CCompiler.
59 src_extensions
= _c_extensions
+ _cpp_extensions
60 obj_extension
= '.obj'
61 static_lib_extension
= '.lib'
62 shared_lib_extension
= '.dll'
63 static_lib_format
= shared_lib_format
= '%s%s'
64 exe_extension
= '.exe'
66 def __init__(self
, verbose
=0, dry_run
=0, force
=0):
68 super().__init
__(verbose
, dry_run
, force
)
70 # These executables are assumed to all be in the path.
71 # Borland doesn't seem to use any special registry settings to
72 # indicate their installation locations.
75 self
.linker
= "ilink32.exe"
78 self
.preprocess_options
= None
79 self
.compile_options
= ['/tWM', '/O2', '/q', '/g0']
80 self
.compile_options_debug
= ['/tWM', '/Od', '/q', '/g0']
82 self
.ldflags_shared
= ['/Tpd', '/Gn', '/q', '/x']
83 self
.ldflags_shared_debug
= ['/Tpd', '/Gn', '/q', '/x']
84 self
.ldflags_static
= []
85 self
.ldflags_exe
= ['/Gn', '/q', '/x']
86 self
.ldflags_exe_debug
= ['/Gn', '/q', '/x', '/r']
88 # -- Worker methods ------------------------------------------------
90 def compile( # noqa: C901
102 macros
, objects
, extra_postargs
, pp_opts
, build
= self
._setup
_compile
(
103 output_dir
, macros
, include_dirs
, sources
, depends
, extra_postargs
105 compile_opts
= extra_preargs
or []
106 compile_opts
.append('-c')
108 compile_opts
.extend(self
.compile_options_debug
)
110 compile_opts
.extend(self
.compile_options
)
114 src
, ext
= build
[obj
]
117 # XXX why do the normpath here?
118 src
= os
.path
.normpath(src
)
119 obj
= os
.path
.normpath(obj
)
120 # XXX _setup_compile() did a mkpath() too but before the normpath.
121 # Is it possible to skip the normpath?
122 self
.mkpath(os
.path
.dirname(obj
))
125 # This is already a binary file -- skip it.
126 continue # the 'for' loop
128 # This needs to be compiled to a .res file -- do it now.
130 self
.spawn(["brcc32", "-fo", obj
, src
])
131 except DistutilsExecError
as msg
:
132 raise CompileError(msg
)
133 continue # the 'for' loop
135 # The next two are both for the real compiler.
136 if ext
in self
._c
_extensions
:
138 elif ext
in self
._cpp
_extensions
:
141 # Unknown file type -- no extra options. The compiler
142 # will probably fail, but let it just in case this is a
143 # file the compiler recognizes even if we don't.
146 output_opt
= "-o" + obj
148 # Compiler command line syntax is: "bcc32 [options] file(s)".
149 # Note that the source file names must appear at the end of
156 + [input_opt
, output_opt
]
160 except DistutilsExecError
as msg
:
161 raise CompileError(msg
)
167 def create_static_lib(
168 self
, objects
, output_libname
, output_dir
=None, debug
=0, target_lang
=None
171 (objects
, output_dir
) = self
._fix
_object
_args
(objects
, output_dir
)
172 output_filename
= self
.library_filename(output_libname
, output_dir
=output_dir
)
174 if self
._need
_link
(objects
, output_filename
):
175 lib_args
= [output_filename
, '/u'] + objects
177 pass # XXX what goes here?
179 self
.spawn([self
.lib
] + lib_args
)
180 except DistutilsExecError
as msg
:
183 log
.debug("skipping %s (up-to-date)", output_filename
)
185 # create_static_lib ()
187 def link( # noqa: C901
195 runtime_library_dirs
=None,
204 # XXX this ignores 'build_temp'! should follow the lead of
207 (objects
, output_dir
) = self
._fix
_object
_args
(objects
, output_dir
)
208 (libraries
, library_dirs
, runtime_library_dirs
) = self
._fix
_lib
_args
(
209 libraries
, library_dirs
, runtime_library_dirs
212 if runtime_library_dirs
:
214 "I don't know what to do with 'runtime_library_dirs': %s",
215 str(runtime_library_dirs
),
218 if output_dir
is not None:
219 output_filename
= os
.path
.join(output_dir
, output_filename
)
221 if self
._need
_link
(objects
, output_filename
):
223 # Figure out linker args based on type of target.
224 if target_desc
== CCompiler
.EXECUTABLE
:
225 startup_obj
= 'c0w32'
227 ld_args
= self
.ldflags_exe_debug
[:]
229 ld_args
= self
.ldflags_exe
[:]
231 startup_obj
= 'c0d32'
233 ld_args
= self
.ldflags_shared_debug
[:]
235 ld_args
= self
.ldflags_shared
[:]
237 # Create a temporary exports file for use by the linker
238 if export_symbols
is None:
241 head
, tail
= os
.path
.split(output_filename
)
242 modname
, ext
= os
.path
.splitext(tail
)
243 temp_dir
= os
.path
.dirname(objects
[0]) # preserve tree structure
244 def_file
= os
.path
.join(temp_dir
, '%s.def' % modname
)
245 contents
= ['EXPORTS']
246 for sym
in export_symbols
or []:
247 contents
.append(' {}=_{}'.format(sym
, sym
))
248 self
.execute(write_file
, (def_file
, contents
), "writing %s" % def_file
)
250 # Borland C++ has problems with '/' in paths
251 objects2
= map(os
.path
.normpath
, objects
)
252 # split objects in .obj and .res files
253 # Borland C++ needs them at different positions in the command line
254 objects
= [startup_obj
]
256 for file in objects2
:
257 (base
, ext
) = os
.path
.splitext(os
.path
.normcase(file))
259 resources
.append(file)
263 for ell
in library_dirs
:
264 ld_args
.append("/L%s" % os
.path
.normpath(ell
))
265 ld_args
.append("/L.") # we sometimes use relative paths
267 # list of object files
268 ld_args
.extend(objects
)
270 # XXX the command-line syntax for Borland C++ is a bit wonky;
271 # certain filenames are jammed together in one big string, but
272 # comma-delimited. This doesn't mesh too well with the
273 # Unix-centric attitude (with a DOS/Windows quoting hack) of
274 # 'spawn()', so constructing the argument list is a bit
275 # awkward. Note that doing the obvious thing and jamming all
276 # the filenames and commas into one argument would be wrong,
277 # because 'spawn()' would quote any filenames with spaces in
278 # them. Arghghh!. Apparently it works fine as coded...
280 # name of dll/exe file
281 ld_args
.extend([',', output_filename
])
282 # no map file and start libraries
285 for lib
in libraries
:
286 # see if we find it and if there is a bcpp specific lib
288 libfile
= self
.find_library_file(library_dirs
, lib
, debug
)
291 # probably a BCPP internal library -- don't warn
293 # full name which prefers bcpp_xxx.lib over xxx.lib
294 ld_args
.append(libfile
)
296 # some default libraries
297 ld_args
.append('import32')
298 ld_args
.append('cw32mt')
300 # def file for export symbols
301 ld_args
.extend([',', def_file
])
304 ld_args
.extend(resources
)
307 ld_args
[:0] = extra_preargs
309 ld_args
.extend(extra_postargs
)
311 self
.mkpath(os
.path
.dirname(output_filename
))
313 self
.spawn([self
.linker
] + ld_args
)
314 except DistutilsExecError
as msg
:
318 log
.debug("skipping %s (up-to-date)", output_filename
)
322 # -- Miscellaneous methods -----------------------------------------
324 def find_library_file(self
, dirs
, lib
, debug
=0):
325 # List of effective library names to try, in order of preference:
326 # xxx_bcpp.lib is better than xxx.lib
327 # and xxx_d.lib is better than xxx.lib if debug is set
329 # The "_bcpp" suffix is to handle a Python installation for people
330 # with multiple compilers (primarily Distutils hackers, I suspect
331 # ;-). The idea is they'd have one static library for each
332 # compiler they care about, since (almost?) every Windows compiler
333 # seems to have a different format for static libraries.
336 try_names
= (dlib
+ "_bcpp", lib
+ "_bcpp", dlib
, lib
)
338 try_names
= (lib
+ "_bcpp", lib
)
341 for name
in try_names
:
342 libfile
= os
.path
.join(dir, self
.library_filename(name
))
343 if os
.path
.exists(libfile
):
346 # Oops, didn't find it in *any* of 'dirs'
349 # overwrite the one from CCompiler to support rc and res-files
350 def object_filenames(self
, source_filenames
, strip_dir
=0, output_dir
=''):
351 if output_dir
is None:
354 for src_name
in source_filenames
:
355 # use normcase to make sure '.rc' is really '.rc' and not '.RC'
356 (base
, ext
) = os
.path
.splitext(os
.path
.normcase(src_name
))
357 if ext
not in (self
.src_extensions
+ ['.rc', '.res']):
358 raise UnknownFileError(
359 "unknown file type '{}' (from '{}')".format(ext
, src_name
)
362 base
= os
.path
.basename(base
)
364 # these can go unchanged
365 obj_names
.append(os
.path
.join(output_dir
, base
+ ext
))
367 # these need to be compiled to .res-files
368 obj_names
.append(os
.path
.join(output_dir
, base
+ '.res'))
370 obj_names
.append(os
.path
.join(output_dir
, base
+ self
.obj_extension
))
373 # object_filenames ()
385 (_
, macros
, include_dirs
) = self
._fix
_compile
_args
(None, macros
, include_dirs
)
386 pp_opts
= gen_preprocess_options(macros
, include_dirs
)
387 pp_args
= ['cpp32.exe'] + pp_opts
388 if output_file
is not None:
389 pp_args
.append('-o' + output_file
)
391 pp_args
[:0] = extra_preargs
393 pp_args
.extend(extra_postargs
)
394 pp_args
.append(source
)
396 # We need to preprocess: either we're being forced to, or the
397 # source file is newer than the target (or the target doesn't
399 if self
.force
or output_file
is None or newer(source
, output_file
):
401 self
.mkpath(os
.path
.dirname(output_file
))
404 except DistutilsExecError
as msg
:
406 raise CompileError(msg
)