blob: 27c08dbf19deb5046591ec1e4d91f1b41149cf7e [file] [log] [blame]
Fred Drake522af3a1999-01-06 16:28:34 +00001"""Provide access to Python's configuration information. The specific names
2defined in the module depend heavily on the platform and configuration.
Greg Ward1190ee31998-12-18 23:46:33 +00003
4Written by: Fred L. Drake, Jr.
5Email: <fdrake@acm.org>
6Initial date: 17-Dec-1998
7"""
8
Greg Ward82d71ca2000-06-03 00:44:30 +00009__revision__ = "$Id$"
Greg Ward1190ee31998-12-18 23:46:33 +000010
Greg Ward9ddaaa11999-01-06 14:46:06 +000011import os
12import re
13import string
14import sys
Greg Ward1190ee31998-12-18 23:46:33 +000015
Fred Drakec1ee39a2000-03-09 15:54:52 +000016from errors import DistutilsPlatformError
Greg Warda0ca3f22000-02-02 00:05:14 +000017
Greg Ward1190ee31998-12-18 23:46:33 +000018
Greg Wardcf6bea32000-04-10 01:15:06 +000019PREFIX = os.path.normpath(sys.prefix)
20EXEC_PREFIX = os.path.normpath(sys.exec_prefix)
Fred Drakec1ee39a2000-03-09 15:54:52 +000021
22
Greg Wardd38e6f72000-04-10 01:17:49 +000023def get_python_inc(plat_specific=0, prefix=None):
Greg Ward7d73b9e2000-03-09 03:16:05 +000024 """Return the directory containing installed Python header files.
Fred Drakec1ee39a2000-03-09 15:54:52 +000025
26 If 'plat_specific' is false (the default), this is the path to the
27 non-platform-specific header files, i.e. Python.h and so on;
28 otherwise, this is the path to platform-specific header files
29 (namely config.h).
30
Greg Wardd38e6f72000-04-10 01:17:49 +000031 If 'prefix' is supplied, use it instead of sys.prefix or
32 sys.exec_prefix -- i.e., ignore 'plat_specific'.
Fred Drakec1ee39a2000-03-09 15:54:52 +000033 """
Greg Wardd38e6f72000-04-10 01:17:49 +000034 if prefix is None:
35 prefix = (plat_specific and EXEC_PREFIX or PREFIX)
Greg Ward7d73b9e2000-03-09 03:16:05 +000036 if os.name == "posix":
Greg Wardcf6bea32000-04-10 01:15:06 +000037 return os.path.join(prefix, "include", "python" + sys.version[:3])
Greg Ward7d73b9e2000-03-09 03:16:05 +000038 elif os.name == "nt":
Greg Wardcf6bea32000-04-10 01:15:06 +000039 return os.path.join(prefix, "Include") # include or Include?
Greg Ward7d73b9e2000-03-09 03:16:05 +000040 elif os.name == "mac":
Greg Wardcf6bea32000-04-10 01:15:06 +000041 return os.path.join(prefix, "Include")
Greg Ward7d73b9e2000-03-09 03:16:05 +000042 else:
43 raise DistutilsPlatformError, \
44 ("I don't know where Python installs its C header files " +
45 "on platform '%s'") % os.name
46
47
Greg Wardd38e6f72000-04-10 01:17:49 +000048def get_python_lib(plat_specific=0, standard_lib=0, prefix=None):
Greg Ward7d73b9e2000-03-09 03:16:05 +000049 """Return the directory containing the Python library (standard or
Fred Drakec1ee39a2000-03-09 15:54:52 +000050 site additions).
Greg Ward7d73b9e2000-03-09 03:16:05 +000051
Fred Drakec1ee39a2000-03-09 15:54:52 +000052 If 'plat_specific' is true, return the directory containing
53 platform-specific modules, i.e. any module from a non-pure-Python
54 module distribution; otherwise, return the platform-shared library
55 directory. If 'standard_lib' is true, return the directory
56 containing standard Python library modules; otherwise, return the
57 directory for site-specific modules.
58
Greg Wardd38e6f72000-04-10 01:17:49 +000059 If 'prefix' is supplied, use it instead of sys.prefix or
60 sys.exec_prefix -- i.e., ignore 'plat_specific'.
Fred Drakec1ee39a2000-03-09 15:54:52 +000061 """
Greg Wardd38e6f72000-04-10 01:17:49 +000062 if prefix is None:
63 prefix = (plat_specific and EXEC_PREFIX or PREFIX)
Greg Ward7d73b9e2000-03-09 03:16:05 +000064
65 if os.name == "posix":
Greg Wardcf6bea32000-04-10 01:15:06 +000066 libpython = os.path.join(prefix,
Fred Drakec1ee39a2000-03-09 15:54:52 +000067 "lib", "python" + sys.version[:3])
Greg Ward7d73b9e2000-03-09 03:16:05 +000068 if standard_lib:
69 return libpython
70 else:
Fred Drakec1ee39a2000-03-09 15:54:52 +000071 return os.path.join(libpython, "site-packages")
Greg Ward7d73b9e2000-03-09 03:16:05 +000072
73 elif os.name == "nt":
74 if standard_lib:
Greg Wardcf6bea32000-04-10 01:15:06 +000075 return os.path.join(PREFIX, "Lib")
Greg Ward7d73b9e2000-03-09 03:16:05 +000076 else:
Greg Wardcf6bea32000-04-10 01:15:06 +000077 return prefix
Greg Ward7d73b9e2000-03-09 03:16:05 +000078
79 elif os.name == "mac":
Greg Warddc9fe8a2000-08-02 01:49:40 +000080 if plat_specific:
Greg Ward7d73b9e2000-03-09 03:16:05 +000081 if standard_lib:
Greg Wardcf6bea32000-04-10 01:15:06 +000082 return os.path.join(EXEC_PREFIX, "Mac", "Plugins")
Greg Ward7d73b9e2000-03-09 03:16:05 +000083 else:
84 raise DistutilsPlatformError, \
85 "OK, where DO site-specific extensions go on the Mac?"
86 else:
87 if standard_lib:
Greg Wardcf6bea32000-04-10 01:15:06 +000088 return os.path.join(PREFIX, "Lib")
Greg Ward7d73b9e2000-03-09 03:16:05 +000089 else:
90 raise DistutilsPlatformError, \
91 "OK, where DO site-specific modules go on the Mac?"
92 else:
93 raise DistutilsPlatformError, \
94 ("I don't know where Python installs its library " +
95 "on platform '%s'") % os.name
96
Fred Drakec1ee39a2000-03-09 15:54:52 +000097# get_python_lib()
Greg Ward7d73b9e2000-03-09 03:16:05 +000098
99
Greg Wardbb7baa72000-06-25 02:09:14 +0000100def customize_compiler (compiler):
101 """Do any platform-specific customization of the CCompiler instance
102 'compiler'. Mainly needed on Unix, so we can plug in the information
103 that varies across Unices and is stored in Python's Makefile.
104 """
105 if compiler.compiler_type == "unix":
106 cc_cmd = CC + ' ' + OPT
107 compiler.set_executables(
108 preprocessor=CC + " -E", # not always!
109 compiler=cc_cmd,
110 compiler_so=cc_cmd + ' ' + CCSHARED,
111 linker_so=LDSHARED,
112 linker_exe=CC)
113
114 compiler.shared_lib_extension = SO
115
116
Greg Ward9ddaaa11999-01-06 14:46:06 +0000117def get_config_h_filename():
Fred Drake522af3a1999-01-06 16:28:34 +0000118 """Return full pathname of installed config.h file."""
Fred Drakec1ee39a2000-03-09 15:54:52 +0000119 inc_dir = get_python_inc(plat_specific=1)
120 return os.path.join(inc_dir, "config.h")
Greg Ward7d73b9e2000-03-09 03:16:05 +0000121
Greg Ward1190ee31998-12-18 23:46:33 +0000122
Greg Ward9ddaaa11999-01-06 14:46:06 +0000123def get_makefile_filename():
Fred Drake522af3a1999-01-06 16:28:34 +0000124 """Return full pathname of installed Makefile from the Python build."""
Fred Drakec1ee39a2000-03-09 15:54:52 +0000125 lib_dir = get_python_lib(plat_specific=1, standard_lib=1)
126 return os.path.join(lib_dir, "config", "Makefile")
Greg Ward7d73b9e2000-03-09 03:16:05 +0000127
Greg Ward1190ee31998-12-18 23:46:33 +0000128
Greg Ward9ddaaa11999-01-06 14:46:06 +0000129def parse_config_h(fp, g=None):
Fred Drakec1ee39a2000-03-09 15:54:52 +0000130 """Parse a config.h-style file.
131
132 A dictionary containing name/value pairs is returned. If an
133 optional dictionary is passed in as the second argument, it is
134 used instead of a new dictionary.
Fred Drake522af3a1999-01-06 16:28:34 +0000135 """
Greg Ward9ddaaa11999-01-06 14:46:06 +0000136 if g is None:
137 g = {}
Greg Ward1190ee31998-12-18 23:46:33 +0000138 define_rx = re.compile("#define ([A-Z][A-Z0-9_]+) (.*)\n")
139 undef_rx = re.compile("/[*] #undef ([A-Z][A-Z0-9_]+) [*]/\n")
Greg Ward9ddaaa11999-01-06 14:46:06 +0000140 #
Greg Ward1190ee31998-12-18 23:46:33 +0000141 while 1:
142 line = fp.readline()
143 if not line:
144 break
145 m = define_rx.match(line)
146 if m:
147 n, v = m.group(1, 2)
Greg Ward3c8e54b1998-12-22 12:42:04 +0000148 try: v = string.atoi(v)
149 except ValueError: pass
150 g[n] = v
Greg Ward1190ee31998-12-18 23:46:33 +0000151 else:
152 m = undef_rx.match(line)
153 if m:
154 g[m.group(1)] = 0
Greg Ward9ddaaa11999-01-06 14:46:06 +0000155 return g
Greg Ward1190ee31998-12-18 23:46:33 +0000156
Greg Ward3fff8d22000-09-15 00:03:13 +0000157def parse_makefile(fn, g=None):
Fred Drakec1ee39a2000-03-09 15:54:52 +0000158 """Parse a Makefile-style file.
159
160 A dictionary containing name/value pairs is returned. If an
161 optional dictionary is passed in as the second argument, it is
162 used instead of a new dictionary.
163
Fred Drake522af3a1999-01-06 16:28:34 +0000164 """
Greg Ward3fff8d22000-09-15 00:03:13 +0000165 from distutils.text_file import TextFile
166 fp = TextFile(fn, strip_comments=1, join_lines=1)
167
Greg Ward9ddaaa11999-01-06 14:46:06 +0000168 if g is None:
169 g = {}
Greg Ward3fff8d22000-09-15 00:03:13 +0000170 variable_rx = re.compile("([a-zA-Z][a-zA-Z0-9_]+)\s*=\s*(.*)")
Greg Ward1190ee31998-12-18 23:46:33 +0000171 done = {}
172 notdone = {}
Greg Ward3fff8d22000-09-15 00:03:13 +0000173
Greg Ward1190ee31998-12-18 23:46:33 +0000174 while 1:
175 line = fp.readline()
Greg Ward3fff8d22000-09-15 00:03:13 +0000176 if line is None:
Greg Ward1190ee31998-12-18 23:46:33 +0000177 break
178 m = variable_rx.match(line)
179 if m:
180 n, v = m.group(1, 2)
Greg Ward3c8e54b1998-12-22 12:42:04 +0000181 v = string.strip(v)
Greg Ward1190ee31998-12-18 23:46:33 +0000182 if "$" in v:
183 notdone[n] = v
184 else:
Greg Ward3c8e54b1998-12-22 12:42:04 +0000185 try: v = string.atoi(v)
186 except ValueError: pass
Greg Ward1190ee31998-12-18 23:46:33 +0000187 done[n] = v
188
189 # do variable interpolation here
190 findvar1_rx = re.compile(r"\$\(([A-Za-z][A-Za-z0-9_]*)\)")
191 findvar2_rx = re.compile(r"\${([A-Za-z][A-Za-z0-9_]*)}")
192 while notdone:
193 for name in notdone.keys():
194 value = notdone[name]
195 m = findvar1_rx.search(value)
196 if not m:
197 m = findvar2_rx.search(value)
198 if m:
199 n = m.group(1)
200 if done.has_key(n):
201 after = value[m.end():]
202 value = value[:m.start()] + done[n] + after
203 if "$" in after:
204 notdone[name] = value
205 else:
Greg Ward3c8e54b1998-12-22 12:42:04 +0000206 try: value = string.atoi(value)
207 except ValueError: pass
208 done[name] = string.strip(value)
Greg Ward1190ee31998-12-18 23:46:33 +0000209 del notdone[name]
210 elif notdone.has_key(n):
211 # get it on a subsequent round
212 pass
213 else:
214 done[n] = ""
215 after = value[m.end():]
216 value = value[:m.start()] + after
217 if "$" in after:
218 notdone[name] = value
219 else:
Greg Ward3c8e54b1998-12-22 12:42:04 +0000220 try: value = string.atoi(value)
221 except ValueError: pass
222 done[name] = string.strip(value)
Greg Ward1190ee31998-12-18 23:46:33 +0000223 del notdone[name]
224 else:
Greg Ward3c8e54b1998-12-22 12:42:04 +0000225 # bogus variable reference; just drop it since we can't deal
Greg Ward1190ee31998-12-18 23:46:33 +0000226 del notdone[name]
227
228 # save the results in the global dictionary
229 g.update(done)
Greg Ward9ddaaa11999-01-06 14:46:06 +0000230 return g
Greg Ward1190ee31998-12-18 23:46:33 +0000231
232
Greg Ward9ddaaa11999-01-06 14:46:06 +0000233def _init_posix():
Fred Drake522af3a1999-01-06 16:28:34 +0000234 """Initialize the module as appropriate for POSIX systems."""
Greg Ward9ddaaa11999-01-06 14:46:06 +0000235 g = globals()
Greg Warda0ca3f22000-02-02 00:05:14 +0000236 # load the installed Makefile:
Greg Warda570c052000-05-23 23:14:00 +0000237 try:
238 filename = get_makefile_filename()
Greg Ward3fff8d22000-09-15 00:03:13 +0000239 parse_makefile(filename, g)
Greg Warda570c052000-05-23 23:14:00 +0000240 except IOError, msg:
241 my_msg = "invalid Python installation: unable to open %s" % filename
242 if hasattr(msg, "strerror"):
243 my_msg = my_msg + " (%s)" % msg.strerror
244
245 raise DistutilsPlatformError, my_msg
246
Greg Ward4f880282000-06-27 01:59:06 +0000247
248 # On AIX, there are wrong paths to the linker scripts in the Makefile
249 # -- these paths are relative to the Python source, but when installed
250 # the scripts are in another directory.
Greg Wardb231e1a2000-06-27 01:59:43 +0000251 if sys.platform == 'aix4': # what about AIX 3.x ?
Greg Ward4f880282000-06-27 01:59:06 +0000252 # Linker script is in the config directory, not in Modules as the
253 # Makefile says.
254 python_lib = get_python_lib(standard_lib=1)
255 ld_so_aix = os.path.join(python_lib, 'config', 'ld_so_aix')
256 python_exp = os.path.join(python_lib, 'config', 'python.exp')
257
258 g['LDSHARED'] = "%s %s -bI:%s" % (ld_so_aix, g['CC'], python_exp)
Greg Ward9ddaaa11999-01-06 14:46:06 +0000259
Greg Ward66e966f2000-09-01 01:23:26 +0000260 if sys.platform == 'beos':
261
262 # Linker script is in the config directory. In the Makefile it is
263 # relative to the srcdir, which after installation no longer makes
264 # sense.
265 python_lib = get_python_lib(standard_lib=1)
266 linkerscript_name = os.path.basename(string.split(g['LDSHARED'])[0])
267 linkerscript = os.path.join(python_lib, 'config', linkerscript_name)
268
269 # XXX this isn't the right place to do this: adding the Python
270 # library to the link, if needed, should be in the "build_ext"
271 # command. (It's also needed for non-MS compilers on Windows, and
272 # it's taken care of for them by the 'build_ext.get_libraries()'
273 # method.)
274 g['LDSHARED'] = ("%s -L%s/lib -lpython%s" %
275 (linkerscript, sys.prefix, sys.version[0:3]))
276
Greg Ward9ddaaa11999-01-06 14:46:06 +0000277
Greg Ward4d74d731999-06-08 01:58:36 +0000278def _init_nt():
279 """Initialize the module as appropriate for NT"""
Fred Drake69e2c6e2000-02-08 15:55:42 +0000280 g = globals()
Greg Ward4d74d731999-06-08 01:58:36 +0000281 # set basic install directories
Fred Drakec1ee39a2000-03-09 15:54:52 +0000282 g['LIBDEST'] = get_python_lib(plat_specific=0, standard_lib=1)
283 g['BINLIBDEST'] = get_python_lib(plat_specific=1, standard_lib=1)
Greg Ward4d74d731999-06-08 01:58:36 +0000284
Greg Ward32162e81999-08-29 18:22:13 +0000285 # XXX hmmm.. a normal install puts include files here
Fred Drakec1ee39a2000-03-09 15:54:52 +0000286 g['INCLUDEPY'] = get_python_inc(plat_specific=0)
Greg Ward32162e81999-08-29 18:22:13 +0000287
Fred Drake69e2c6e2000-02-08 15:55:42 +0000288 g['SO'] = '.pyd'
Greg Ward82d71ca2000-06-03 00:44:30 +0000289 g['EXE'] = ".exe"
Greg Ward1d526dd2000-08-02 01:09:11 +0000290 g['exec_prefix'] = EXEC_PREFIX
Greg Ward82d71ca2000-06-03 00:44:30 +0000291
Fred Drake69e2c6e2000-02-08 15:55:42 +0000292
Greg Ward0eff87a2000-03-07 03:30:09 +0000293def _init_mac():
294 """Initialize the module as appropriate for Macintosh systems"""
295 g = globals()
Greg Ward0eff87a2000-03-07 03:30:09 +0000296 # set basic install directories
Fred Drakec1ee39a2000-03-09 15:54:52 +0000297 g['LIBDEST'] = get_python_lib(plat_specific=0, standard_lib=1)
298 g['BINLIBDEST'] = get_python_lib(plat_specific=1, standard_lib=1)
Greg Ward0eff87a2000-03-07 03:30:09 +0000299
300 # XXX hmmm.. a normal install puts include files here
Fred Drakec1ee39a2000-03-09 15:54:52 +0000301 g['INCLUDEPY'] = get_python_inc(plat_specific=0)
Greg Ward0eff87a2000-03-07 03:30:09 +0000302
303 g['SO'] = '.ppc.slb'
Greg Wardcf6bea32000-04-10 01:15:06 +0000304 g['exec_prefix'] = EXEC_PREFIX
305 print sys.prefix, PREFIX
Greg Ward7d73b9e2000-03-09 03:16:05 +0000306
307 # XXX are these used anywhere?
Greg Wardcf6bea32000-04-10 01:15:06 +0000308 g['install_lib'] = os.path.join(EXEC_PREFIX, "Lib")
309 g['install_platlib'] = os.path.join(EXEC_PREFIX, "Mac", "Lib")
Greg Ward0eff87a2000-03-07 03:30:09 +0000310
311
Greg Ward9ddaaa11999-01-06 14:46:06 +0000312try:
313 exec "_init_" + os.name
314except NameError:
315 # not needed for this platform
316 pass
317else:
318 exec "_init_%s()" % os.name
319
Fred Drake69e2c6e2000-02-08 15:55:42 +0000320
Greg Ward1190ee31998-12-18 23:46:33 +0000321del _init_posix
Greg Ward4d74d731999-06-08 01:58:36 +0000322del _init_nt
Greg Ward0eff87a2000-03-07 03:30:09 +0000323del _init_mac