config.py revision 290f32ab4cdac8866be121c3da33bb187333f4ab
1# -*- coding: utf-8 -*-
2
3import os
4import copy
5import platform
6import multiprocessing
7
8from common import which, DEQP_DIR
9
10try:
11	import _winreg
12except:
13	_winreg = None
14
15class BuildConfig:
16	def __init__ (self, buildDir, buildType, args, srcPath = DEQP_DIR):
17		self.srcPath		= srcPath
18		self.buildDir		= buildDir
19		self.buildType		= buildType
20		self.args			= copy.copy(args)
21
22	def getSrcPath (self):
23		return self.srcPath
24
25	def getBuildDir (self):
26		return self.buildDir
27
28	def getBuildType (self):
29		return self.buildType
30
31	def getArgs (self):
32		return self.args
33
34class CMakeGenerator:
35	def __init__ (self, name, isMultiConfig = False, extraBuildArgs = []):
36		self.name			= name
37		self.isMultiConfig	= isMultiConfig
38		self.extraBuildArgs	= copy.copy(extraBuildArgs)
39
40	def getName (self):
41		return self.name
42
43	def getGenerateArgs (self, buildType):
44		args = ['-G', self.name]
45		if not self.isMultiConfig:
46			args.append('-DCMAKE_BUILD_TYPE=%s' % buildType)
47		return args
48
49	def getBuildArgs (self, buildType):
50		args = []
51		if self.isMultiConfig:
52			args += ['--config', buildType]
53		if len(self.extraBuildArgs) > 0:
54			args += ['--'] + self.extraBuildArgs
55		return args
56
57	def getBinaryPath (self, buildType, basePath):
58		return basePath
59
60class UnixMakefileGenerator(CMakeGenerator):
61	def __init__(self):
62		CMakeGenerator.__init__(self, "Unix Makefiles", extraBuildArgs = ["-j%d" % multiprocessing.cpu_count()])
63
64	def isAvailable (self):
65		return which('make') != None
66
67class NinjaGenerator(CMakeGenerator):
68	def __init__(self):
69		CMakeGenerator.__init__(self, "Ninja")
70
71	def isAvailable (self):
72		return which('ninja') != None
73
74class VSProjectGenerator(CMakeGenerator):
75	ARCH_32BIT	= 0
76	ARCH_64BIT	= 1
77
78	def __init__(self, version, arch):
79		name = "Visual Studio %d" % version
80		if arch == self.ARCH_64BIT:
81			name += " Win64"
82
83		CMakeGenerator.__init__(self, name, isMultiConfig = True, extraBuildArgs = ['/m'])
84		self.version		= version
85		self.arch			= arch
86
87	def getBinaryPath (self, buildType, basePath):
88		return os.path.join(os.path.dirname(basePath), buildType, os.path.basename(basePath) + ".exe")
89
90	@staticmethod
91	def getNativeArch ():
92		arch = platform.machine().lower()
93
94		if arch == 'x86':
95			return VSProjectGenerator.ARCH_32BIT
96		elif arch == 'amd64':
97			return VSProjectGenerator.ARCH_64BIT
98		else:
99			raise Exception("Unhandled arch '%s'" % arch)
100
101	@staticmethod
102	def registryKeyAvailable (root, arch, name):
103		try:
104			key = _winreg.OpenKey(root, name, 0, _winreg.KEY_READ | arch)
105			_winreg.CloseKey(key)
106			return True
107		except:
108			return False
109
110	def isAvailable (self):
111		if _winreg != None:
112			nativeArch = VSProjectGenerator.getNativeArch()
113			if nativeArch == self.ARCH_32BIT and self.arch == self.ARCH_64BIT:
114				return False
115
116			arch = _winreg.KEY_WOW64_32KEY if nativeArch == self.ARCH_64BIT else 0
117			keyMap = {
118				10:		[(_winreg.HKEY_CLASSES_ROOT, "VisualStudio.DTE.10.0"), (_winreg.HKEY_LOCAL_MACHINE, "Software\\Microsoft\\VCExpress\\10.0")],
119				11:		[(_winreg.HKEY_CLASSES_ROOT, "VisualStudio.DTE.11.0"), (_winreg.HKEY_LOCAL_MACHINE, "Software\\Microsoft\\VCExpress\\11.0")],
120				12:		[(_winreg.HKEY_CLASSES_ROOT, "VisualStudio.DTE.12.0"), (_winreg.HKEY_LOCAL_MACHINE, "Software\\Microsoft\\VCExpress\\12.0")],
121			}
122
123			if not self.version in keyMap:
124				raise Exception("Unsupported VS version %d" % self.version)
125
126			keys = keyMap[self.version]
127			for root, name in keys:
128				if VSProjectGenerator.registryKeyAvailable(root, arch, name):
129					return True
130			return False
131		else:
132			return False
133
134# Pre-defined generators
135
136MAKEFILE_GENERATOR		= UnixMakefileGenerator()
137NINJA_GENERATOR			= NinjaGenerator()
138VS2010_X32_GENERATOR	= VSProjectGenerator(10, VSProjectGenerator.ARCH_32BIT)
139VS2010_X64_GENERATOR	= VSProjectGenerator(10, VSProjectGenerator.ARCH_64BIT)
140VS2012_X32_GENERATOR	= VSProjectGenerator(11, VSProjectGenerator.ARCH_32BIT)
141VS2012_X64_GENERATOR	= VSProjectGenerator(11, VSProjectGenerator.ARCH_64BIT)
142VS2013_X32_GENERATOR	= VSProjectGenerator(12, VSProjectGenerator.ARCH_32BIT)
143VS2013_X64_GENERATOR	= VSProjectGenerator(12, VSProjectGenerator.ARCH_64BIT)
144
145def selectFirstAvailableGenerator (generators):
146	for generator in generators:
147		if generator.isAvailable():
148			return generator
149	return None
150
151ANY_VS_X32_GENERATOR	= selectFirstAvailableGenerator([
152								VS2013_X32_GENERATOR,
153								VS2012_X32_GENERATOR,
154								VS2010_X32_GENERATOR,
155							])
156ANY_VS_X64_GENERATOR	= selectFirstAvailableGenerator([
157								VS2013_X64_GENERATOR,
158								VS2012_X64_GENERATOR,
159								VS2010_X64_GENERATOR,
160							])
161ANY_UNIX_GENERATOR		= selectFirstAvailableGenerator([
162								NINJA_GENERATOR,
163								MAKEFILE_GENERATOR,
164							])
165