| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | import os | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  | import os.path | 
					
						
							|  |  |  | import re | 
					
						
							|  |  |  | import glob | 
					
						
							|  |  |  | import subprocess | 
					
						
							| 
									
										
										
										
											2018-11-24 21:09:40 +09:00
										 |  |  | from compat import iteritems, isbasestring, decode_utf8 | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 19:05:14 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-07-22 13:57:39 +02:00
										 |  |  | def add_source_files(self, sources, files, warn_duplicates=True): | 
					
						
							|  |  |  |     # Convert string to list of absolute paths (including expanding wildcard) | 
					
						
							|  |  |  |     if isbasestring(files): | 
					
						
							|  |  |  |         # Keep SCons project-absolute path as they are (no wildcard support) | 
					
						
							|  |  |  |         if files.startswith('#'): | 
					
						
							|  |  |  |             if '*' in files: | 
					
						
							|  |  |  |                 print("ERROR: Wildcards can't be expanded in SCons project-absolute path: '{}'".format(files)) | 
					
						
							|  |  |  |                 return | 
					
						
							|  |  |  |             files = [files] | 
					
						
							|  |  |  |         else: | 
					
						
							|  |  |  |             dir_path = self.Dir('.').abspath | 
					
						
							|  |  |  |             files = sorted(glob.glob(dir_path + "/" + files)) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     # Add each path as compiled Object following environment (self) configuration | 
					
						
							|  |  |  |     for path in files: | 
					
						
							|  |  |  |         obj = self.Object(path) | 
					
						
							|  |  |  |         if obj in sources: | 
					
						
							|  |  |  |             if warn_duplicates: | 
					
						
							|  |  |  |                 print("WARNING: Object \"{}\" already included in environment sources.".format(obj)) | 
					
						
							|  |  |  |             else: | 
					
						
							|  |  |  |                 continue | 
					
						
							|  |  |  |         sources.append(obj) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-09-28 13:29:52 +02:00
										 |  |  | def disable_warnings(self): | 
					
						
							|  |  |  |     # 'self' is the environment | 
					
						
							|  |  |  |     if self.msvc: | 
					
						
							| 
									
										
										
										
											2018-10-03 13:38:09 +02:00
										 |  |  |         # We have to remove existing warning level defines before appending /w, | 
					
						
							|  |  |  |         # otherwise we get: "warning D9025 : overriding '/W3' with '/w'" | 
					
						
							|  |  |  |         warn_flags = ['/Wall', '/W4', '/W3', '/W2', '/W1', '/WX'] | 
					
						
							| 
									
										
										
										
											2018-09-28 13:29:52 +02:00
										 |  |  |         self.Append(CCFLAGS=['/w']) | 
					
						
							| 
									
										
										
										
											2019-04-24 07:35:12 +02:00
										 |  |  |         self.Append(CFLAGS=['/w']) | 
					
						
							| 
									
										
										
										
											2019-07-03 09:16:20 +02:00
										 |  |  |         self.Append(CXXFLAGS=['/w']) | 
					
						
							| 
									
										
										
										
											2019-04-24 07:35:12 +02:00
										 |  |  |         self['CCFLAGS'] = [x for x in self['CCFLAGS'] if not x in warn_flags] | 
					
						
							|  |  |  |         self['CFLAGS'] = [x for x in self['CFLAGS'] if not x in warn_flags] | 
					
						
							| 
									
										
										
										
											2019-04-24 16:49:12 +02:00
										 |  |  |         self['CXXFLAGS'] = [x for x in self['CXXFLAGS'] if not x in warn_flags] | 
					
						
							| 
									
										
										
										
											2018-09-28 13:29:52 +02:00
										 |  |  |     else: | 
					
						
							|  |  |  |         self.Append(CCFLAGS=['-w']) | 
					
						
							| 
									
										
										
										
											2019-04-24 07:35:12 +02:00
										 |  |  |         self.Append(CFLAGS=['-w']) | 
					
						
							| 
									
										
										
										
											2019-04-24 16:49:12 +02:00
										 |  |  |         self.Append(CXXFLAGS=['-w']) | 
					
						
							| 
									
										
										
										
											2018-09-28 13:29:52 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-11-01 23:12:28 -03:00
										 |  |  | def add_module_version_string(self,s): | 
					
						
							| 
									
										
										
										
											2017-11-19 21:18:01 +01:00
										 |  |  |     self.module_version_string += "." + s | 
					
						
							| 
									
										
										
										
											2017-11-01 23:12:28 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-11-01 23:12:28 -03:00
										 |  |  | def update_version(module_version_string=""): | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-11-19 21:26:05 +01:00
										 |  |  |     build_name = "custom_build" | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |     if os.getenv("BUILD_NAME") != None: | 
					
						
							| 
									
										
										
										
											2017-11-19 21:26:05 +01:00
										 |  |  |         build_name = os.getenv("BUILD_NAME") | 
					
						
							|  |  |  |         print("Using custom build name: " + build_name) | 
					
						
							| 
									
										
										
										
											2016-04-02 20:26:12 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     import version | 
					
						
							| 
									
										
										
										
											2016-04-02 20:26:12 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |     # NOTE: It is safe to generate this file here, since this is still executed serially | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |     f = open("core/version_generated.gen.h", "w") | 
					
						
							| 
									
										
										
										
											2017-11-19 21:18:01 +01:00
										 |  |  |     f.write("#define VERSION_SHORT_NAME \"" + str(version.short_name) + "\"\n") | 
					
						
							|  |  |  |     f.write("#define VERSION_NAME \"" + str(version.name) + "\"\n") | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     f.write("#define VERSION_MAJOR " + str(version.major) + "\n") | 
					
						
							|  |  |  |     f.write("#define VERSION_MINOR " + str(version.minor) + "\n") | 
					
						
							| 
									
										
										
										
											2019-11-30 17:22:22 +01:00
										 |  |  |     f.write("#define VERSION_PATCH " + str(version.patch) + "\n") | 
					
						
							| 
									
										
										
										
											2017-11-19 21:18:01 +01:00
										 |  |  |     f.write("#define VERSION_STATUS \"" + str(version.status) + "\"\n") | 
					
						
							| 
									
										
										
										
											2017-11-19 21:26:05 +01:00
										 |  |  |     f.write("#define VERSION_BUILD \"" + str(build_name) + "\"\n") | 
					
						
							| 
									
										
										
										
											2017-11-01 23:12:28 -03:00
										 |  |  |     f.write("#define VERSION_MODULE_CONFIG \"" + str(version.module_config) + module_version_string + "\"\n") | 
					
						
							| 
									
										
										
										
											2019-03-05 23:06:24 +01:00
										 |  |  |     f.write("#define VERSION_YEAR " + str(version.year) + "\n") | 
					
						
							| 
									
										
										
										
											2019-05-28 11:19:21 +02:00
										 |  |  |     f.write("#define VERSION_WEBSITE \"" + str(version.website) + "\"\n") | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |     f.close() | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |     # NOTE: It is safe to generate this file here, since this is still executed serially | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |     fhash = open("core/version_hash.gen.h", "w") | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |     githash = "" | 
					
						
							| 
									
										
										
										
											2019-02-08 16:17:07 -02:00
										 |  |  |     gitfolder = ".git" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if os.path.isfile(".git"): | 
					
						
							|  |  |  |         module_folder = open(".git", "r").readline().strip() | 
					
						
							|  |  |  |         if module_folder.startswith("gitdir: "): | 
					
						
							|  |  |  |             gitfolder = module_folder[8:] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if os.path.isfile(os.path.join(gitfolder, "HEAD")): | 
					
						
							|  |  |  |         head = open(os.path.join(gitfolder, "HEAD"), "r").readline().strip() | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |         if head.startswith("ref: "): | 
					
						
							| 
									
										
										
										
											2019-02-08 16:17:07 -02:00
										 |  |  |             head = os.path.join(gitfolder, head[5:]) | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |             if os.path.isfile(head): | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |                 githash = open(head, "r").readline().strip() | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |         else: | 
					
						
							|  |  |  |             githash = head | 
					
						
							| 
									
										
										
										
											2019-02-08 16:17:07 -02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-07-10 15:47:38 +07:00
										 |  |  |     fhash.write("#define VERSION_HASH \"" + githash + "\"") | 
					
						
							|  |  |  |     fhash.close() | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 19:05:14 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | def parse_cg_file(fname, uniforms, sizes, conditionals): | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     fs = open(fname, "r") | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     line = fs.readline() | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     while line: | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         if re.match(r"^\s*uniform", line): | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |             res = re.match(r"uniform ([\d\w]*) ([\d\w]*)") | 
					
						
							|  |  |  |             type = res.groups(1) | 
					
						
							|  |  |  |             name = res.groups(2) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |             uniforms.append(name) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |             if type.find("texobj") != -1: | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |                 sizes.append(1) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |             else: | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |                 t = re.match(r"float(\d)x(\d)", type) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |                 if t: | 
					
						
							|  |  |  |                     sizes.append(int(t.groups(1)) * int(t.groups(2))) | 
					
						
							|  |  |  |                 else: | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |                     t = re.match(r"float(\d)", type) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |                     sizes.append(int(t.groups(1))) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |             if line.find("[branch]") != -1: | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |                 conditionals.append(name) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-11-01 00:24:30 +01:00
										 |  |  |         line = fs.readline() | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-10 18:37:33 +01:00
										 |  |  |     fs.close() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | def detect_modules(): | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     module_list = [] | 
					
						
							|  |  |  |     includes_cpp = "" | 
					
						
							|  |  |  |     register_cpp = "" | 
					
						
							|  |  |  |     unregister_cpp = "" | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |     files = glob.glob("modules/*") | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     files.sort()  # so register_module_types does not change that often, and also plugins are registered in alphabetic order | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     for x in files: | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |         if not os.path.isdir(x): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |             continue | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |         if not os.path.exists(x + "/config.py"): | 
					
						
							| 
									
										
										
										
											2018-01-07 15:56:18 +01:00
										 |  |  |             continue | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |         x = x.replace("modules/", "")  # rest of world | 
					
						
							|  |  |  |         x = x.replace("modules\\", "")  # win32 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         module_list.append(x) | 
					
						
							|  |  |  |         try: | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |             with open("modules/" + x + "/register_types.h"): | 
					
						
							|  |  |  |                 includes_cpp += '#include "modules/' + x + '/register_types.h"\n' | 
					
						
							|  |  |  |                 register_cpp += '#ifdef MODULE_' + x.upper() + '_ENABLED\n' | 
					
						
							|  |  |  |                 register_cpp += '\tregister_' + x + '_types();\n' | 
					
						
							|  |  |  |                 register_cpp += '#endif\n' | 
					
						
							|  |  |  |                 unregister_cpp += '#ifdef MODULE_' + x.upper() + '_ENABLED\n' | 
					
						
							|  |  |  |                 unregister_cpp += '\tunregister_' + x + '_types();\n' | 
					
						
							|  |  |  |                 unregister_cpp += '#endif\n' | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         except IOError: | 
					
						
							|  |  |  |             pass | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     modules_cpp = """
 | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | // modules.cpp - THIS FILE IS GENERATED, DO NOT EDIT!!!!!!! | 
					
						
							|  |  |  | #include "register_module_types.h" | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | """ + includes_cpp + """ | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  | void register_module_types() { | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | """ + register_cpp + """ | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | void unregister_module_types() { | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | """ + unregister_cpp + """ | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | } | 
					
						
							|  |  |  | """
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |     # NOTE: It is safe to generate this file here, since this is still executed serially | 
					
						
							| 
									
										
										
										
											2018-03-10 18:37:33 +01:00
										 |  |  |     with open("modules/register_module_types.gen.cpp", "w") as f: | 
					
						
							|  |  |  |         f.write(modules_cpp) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     return module_list | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def win32_spawn(sh, escape, cmd, args, env): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     import subprocess | 
					
						
							|  |  |  |     newargs = ' '.join(args[1:]) | 
					
						
							|  |  |  |     cmdline = cmd + " " + newargs | 
					
						
							|  |  |  |     startupinfo = subprocess.STARTUPINFO() | 
					
						
							|  |  |  |     for e in env: | 
					
						
							|  |  |  |         if type(env[e]) != type(""): | 
					
						
							|  |  |  |             env[e] = str(env[e]) | 
					
						
							|  |  |  |     proc = subprocess.Popen(cmdline, stdin=subprocess.PIPE, stdout=subprocess.PIPE, | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |                             stderr=subprocess.PIPE, startupinfo=startupinfo, shell=False, env=env) | 
					
						
							| 
									
										
										
										
											2019-06-28 21:19:49 -04:00
										 |  |  |     _, err = proc.communicate() | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     rv = proc.wait() | 
					
						
							|  |  |  |     if rv: | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |         print("=====") | 
					
						
							|  |  |  |         print(err) | 
					
						
							|  |  |  |         print("=====") | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     return rv | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  | """
 | 
					
						
							|  |  |  | def win32_spawn(sh, escape, cmd, args, spawnenv): | 
					
						
							|  |  |  | 	import win32file | 
					
						
							|  |  |  | 	import win32event | 
					
						
							|  |  |  | 	import win32process | 
					
						
							|  |  |  | 	import win32security | 
					
						
							|  |  |  | 	for var in spawnenv: | 
					
						
							|  |  |  | 		spawnenv[var] = spawnenv[var].encode('ascii', 'replace') | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	sAttrs = win32security.SECURITY_ATTRIBUTES() | 
					
						
							|  |  |  | 	StartupInfo = win32process.STARTUPINFO() | 
					
						
							|  |  |  | 	newargs = ' '.join(map(escape, args[1:])) | 
					
						
							|  |  |  | 	cmdline = cmd + " " + newargs | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	# check for any special operating system commands | 
					
						
							|  |  |  | 	if cmd == 'del': | 
					
						
							|  |  |  | 		for arg in args[1:]: | 
					
						
							|  |  |  | 			win32file.DeleteFile(arg) | 
					
						
							|  |  |  | 		exit_code = 0 | 
					
						
							|  |  |  | 	else: | 
					
						
							|  |  |  | 		# otherwise execute the command. | 
					
						
							|  |  |  | 		hProcess, hThread, dwPid, dwTid = win32process.CreateProcess(None, cmdline, None, None, 1, 0, spawnenv, None, StartupInfo) | 
					
						
							|  |  |  | 		win32event.WaitForSingleObject(hProcess, win32event.INFINITE) | 
					
						
							|  |  |  | 		exit_code = win32process.GetExitCodeProcess(hProcess) | 
					
						
							|  |  |  | 		win32file.CloseHandle(hProcess); | 
					
						
							|  |  |  | 		win32file.CloseHandle(hThread); | 
					
						
							|  |  |  | 	return exit_code | 
					
						
							|  |  |  | """
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def disable_module(self): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     self.disabled_modules.append(self.current_module) | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-06-14 11:27:16 -03:00
										 |  |  | def use_windows_spawn_fix(self, platform=None): | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     if (os.name != "nt"): | 
					
						
							|  |  |  |         return  # not needed, only for windows | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-29 03:34:53 +02:00
										 |  |  |     # On Windows, due to the limited command line length, when creating a static library | 
					
						
							|  |  |  |     # from a very high number of objects SCons will invoke "ar" once per object file; | 
					
						
							|  |  |  |     # that makes object files with same names to be overwritten so the last wins and | 
					
						
							|  |  |  |     # the library looses symbols defined by overwritten objects. | 
					
						
							|  |  |  |     # By enabling quick append instead of the default mode (replacing), libraries will | 
					
						
							| 
									
										
										
										
											2018-02-21 11:30:55 -05:00
										 |  |  |     # got built correctly regardless the invocation strategy. | 
					
						
							| 
									
										
										
										
											2016-10-29 03:34:53 +02:00
										 |  |  |     # Furthermore, since SCons will rebuild the library from scratch when an object file | 
					
						
							|  |  |  |     # changes, no multiple versions of the same object file will be present. | 
					
						
							|  |  |  |     self.Replace(ARFLAGS='q') | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     def mySubProcess(cmdline, env): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |         startupinfo = subprocess.STARTUPINFO() | 
					
						
							|  |  |  |         startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW | 
					
						
							| 
									
										
										
										
											2018-03-21 15:51:44 +01:00
										 |  |  |         proc = subprocess.Popen(cmdline, stdin=subprocess.PIPE, stdout=subprocess.PIPE, | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |                                 stderr=subprocess.PIPE, startupinfo=startupinfo, shell=False, env=env) | 
					
						
							| 
									
										
										
										
											2019-06-28 21:19:49 -04:00
										 |  |  |         _, err = proc.communicate() | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         rv = proc.wait() | 
					
						
							|  |  |  |         if rv: | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |             print("=====") | 
					
						
							|  |  |  |             print(err) | 
					
						
							|  |  |  |             print("=====") | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         return rv | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  |     def mySpawn(sh, escape, cmd, args, env): | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         newargs = ' '.join(args[1:]) | 
					
						
							|  |  |  |         cmdline = cmd + " " + newargs | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |         rv = 0 | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |         env = {str(key): str(value) for key, value in iteritems(env)} | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |         if len(cmdline) > 32000 and cmd.endswith("ar"): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |             cmdline = cmd + " " + args[1] + " " + args[2] + " " | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |             for i in range(3, len(args)): | 
					
						
							|  |  |  |                 rv = mySubProcess(cmdline + args[i], env) | 
					
						
							|  |  |  |                 if rv: | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |                     break | 
					
						
							|  |  |  |         else: | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |             rv = mySubProcess(cmdline, env) | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         return rv | 
					
						
							| 
									
										
										
										
											2016-01-25 00:21:04 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  |     self['SPAWN'] = mySpawn | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  | def split_lib(self, libname, src_list = None, env_lib = None): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     env = self | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     num = 0 | 
					
						
							|  |  |  |     cur_base = "" | 
					
						
							|  |  |  |     max_src = 64 | 
					
						
							|  |  |  |     list = [] | 
					
						
							|  |  |  |     lib_list = [] | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-10-27 01:18:15 +02:00
										 |  |  |     if src_list is None: | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  |         src_list = getattr(env, libname + "_sources") | 
					
						
							| 
									
										
										
										
											2018-01-24 21:45:18 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  |     if type(env_lib) == type(None): | 
					
						
							|  |  |  |         env_lib = env | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  | 
 | 
					
						
							|  |  |  |     for f in src_list: | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         fname = "" | 
					
						
							|  |  |  |         if type(f) == type(""): | 
					
						
							|  |  |  |             fname = env.File(f).path | 
					
						
							|  |  |  |         else: | 
					
						
							|  |  |  |             fname = env.File(f)[0].path | 
					
						
							|  |  |  |         fname = fname.replace("\\", "/") | 
					
						
							| 
									
										
										
										
											2019-12-09 19:22:08 +01:00
										 |  |  |         base = "/".join(fname.split("/")[:2]) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |         if base != cur_base and len(list) > max_src: | 
					
						
							|  |  |  |             if num > 0: | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  |                 lib = env_lib.add_library(libname + str(num), list) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |                 lib_list.append(lib) | 
					
						
							|  |  |  |                 list = [] | 
					
						
							|  |  |  |             num = num + 1 | 
					
						
							|  |  |  |         cur_base = base | 
					
						
							|  |  |  |         list.append(f) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  |     lib = env_lib.add_library(libname + str(num), list) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     lib_list.append(lib) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     lib_base = [] | 
					
						
							| 
									
										
										
										
											2018-01-24 19:06:35 -03:00
										 |  |  |     env_lib.add_source_files(lib_base, "*.cpp") | 
					
						
							|  |  |  |     lib = env_lib.add_library(libname, lib_base) | 
					
						
							| 
									
										
										
										
											2017-11-27 09:39:05 -04:00
										 |  |  |     lib_list.insert(0, lib) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     env.Prepend(LIBS=lib_list) | 
					
						
							| 
									
										
										
										
											2016-10-30 17:04:07 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-12-09 19:22:08 +01:00
										 |  |  |     # When we split modules into arbitrary chunks, we end up with linking issues | 
					
						
							|  |  |  |     # due to symbol dependencies split over several libs, which may not be linked | 
					
						
							|  |  |  |     # in the required order. We use --start-group and --end-group to tell the | 
					
						
							|  |  |  |     # linker that those archives should be searched repeatedly to resolve all | 
					
						
							|  |  |  |     # undefined references. | 
					
						
							|  |  |  |     # As SCons doesn't give us much control over how inserting libs in LIBS | 
					
						
							|  |  |  |     # impacts the linker call, we need to hack our way into the linking commands | 
					
						
							|  |  |  |     # LINKCOM and SHLINKCOM to set those flags. | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if '-Wl,--start-group' in env['LINKCOM'] and '-Wl,--start-group' in env['SHLINKCOM']: | 
					
						
							|  |  |  |         # Already added by a previous call, skip. | 
					
						
							|  |  |  |         return | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     env['LINKCOM'] = str(env['LINKCOM']).replace('$_LIBFLAGS', | 
					
						
							|  |  |  |             '-Wl,--start-group $_LIBFLAGS -Wl,--end-group') | 
					
						
							|  |  |  |     env['SHLINKCOM'] = str(env['LINKCOM']).replace('$_LIBFLAGS', | 
					
						
							|  |  |  |             '-Wl,--start-group $_LIBFLAGS -Wl,--end-group') | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 17:04:07 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | def save_active_platforms(apnames, ap): | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     for x in ap: | 
					
						
							| 
									
										
										
										
											2017-05-25 20:57:13 +02:00
										 |  |  |         names = ['logo'] | 
					
						
							|  |  |  |         if os.path.isfile(x + "/run_icon.png"): | 
					
						
							|  |  |  |             names.append('run_icon') | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-05-25 20:57:13 +02:00
										 |  |  |         for name in names: | 
					
						
							|  |  |  |             pngf = open(x + "/" + name + ".png", "rb") | 
					
						
							|  |  |  |             b = pngf.read(1) | 
					
						
							|  |  |  |             str = " /* AUTOGENERATED FILE, DO NOT EDIT */ \n" | 
					
						
							|  |  |  |             str += " static const unsigned char _" + x[9:] + "_" + name + "[]={" | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |             while len(b) == 1: | 
					
						
							| 
									
										
										
										
											2017-05-25 20:57:13 +02:00
										 |  |  |                 str += hex(ord(b)) | 
					
						
							|  |  |  |                 b = pngf.read(1) | 
					
						
							|  |  |  |                 if (len(b) == 1): | 
					
						
							|  |  |  |                     str += "," | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |             str += "};\n" | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-10 18:37:33 +01:00
										 |  |  |             pngf.close() | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |             # NOTE: It is safe to generate this file here, since this is still executed serially | 
					
						
							| 
									
										
										
										
											2017-05-25 20:57:13 +02:00
										 |  |  |             wf = x + "/" + name + ".gen.h" | 
					
						
							| 
									
										
										
										
											2018-03-10 18:37:33 +01:00
										 |  |  |             with open(wf, "w") as pngw: | 
					
						
							|  |  |  |                 pngw.write(str) | 
					
						
							| 
									
										
										
										
											2014-02-09 22:10:30 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-12 12:54:17 +08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  | def no_verbose(sys, env): | 
					
						
							| 
									
										
										
										
											2015-01-12 12:54:17 +08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     colors = {} | 
					
						
							| 
									
										
										
										
											2018-01-13 17:56:41 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |     # Colors are disabled in non-TTY environments such as pipes. This means | 
					
						
							|  |  |  |     # that if output is redirected to a file, it will not contain color codes | 
					
						
							|  |  |  |     if sys.stdout.isatty(): | 
					
						
							|  |  |  |         colors['cyan'] = '\033[96m' | 
					
						
							|  |  |  |         colors['purple'] = '\033[95m' | 
					
						
							|  |  |  |         colors['blue'] = '\033[94m' | 
					
						
							|  |  |  |         colors['green'] = '\033[92m' | 
					
						
							|  |  |  |         colors['yellow'] = '\033[93m' | 
					
						
							|  |  |  |         colors['red'] = '\033[91m' | 
					
						
							|  |  |  |         colors['end'] = '\033[0m' | 
					
						
							|  |  |  |     else: | 
					
						
							|  |  |  |         colors['cyan'] = '' | 
					
						
							|  |  |  |         colors['purple'] = '' | 
					
						
							|  |  |  |         colors['blue'] = '' | 
					
						
							|  |  |  |         colors['green'] = '' | 
					
						
							|  |  |  |         colors['yellow'] = '' | 
					
						
							|  |  |  |         colors['red'] = '' | 
					
						
							|  |  |  |         colors['end'] = '' | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     compile_source_message = '%sCompiling %s==> %s$SOURCE%s' % (colors['blue'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  |     java_compile_source_message = '%sCompiling %s==> %s$SOURCE%s' % (colors['blue'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     compile_shared_source_message = '%sCompiling shared %s==> %s$SOURCE%s' % (colors['blue'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:57:40 +01:00
										 |  |  |     link_program_message = '%sLinking Program        %s==> %s$TARGET%s' % (colors['red'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  |     link_library_message = '%sLinking Static Library %s==> %s$TARGET%s' % (colors['red'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  |     ranlib_library_message = '%sRanlib Library         %s==> %s$TARGET%s' % (colors['red'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  |     link_shared_library_message = '%sLinking Shared Library %s==> %s$TARGET%s' % (colors['red'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  |     java_library_message = '%sCreating Java Archive  %s==> %s$TARGET%s' % (colors['red'], colors['purple'], colors['yellow'], colors['end']) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     env.Append(CXXCOMSTR=[compile_source_message]) | 
					
						
							|  |  |  |     env.Append(CCCOMSTR=[compile_source_message]) | 
					
						
							|  |  |  |     env.Append(SHCCCOMSTR=[compile_shared_source_message]) | 
					
						
							|  |  |  |     env.Append(SHCXXCOMSTR=[compile_shared_source_message]) | 
					
						
							|  |  |  |     env.Append(ARCOMSTR=[link_library_message]) | 
					
						
							|  |  |  |     env.Append(RANLIBCOMSTR=[ranlib_library_message]) | 
					
						
							|  |  |  |     env.Append(SHLINKCOMSTR=[link_shared_library_message]) | 
					
						
							|  |  |  |     env.Append(LINKCOMSTR=[link_program_message]) | 
					
						
							|  |  |  |     env.Append(JARCOMSTR=[java_library_message]) | 
					
						
							|  |  |  |     env.Append(JAVACCOMSTR=[java_compile_source_message]) | 
					
						
							| 
									
										
										
										
											2015-01-12 12:54:17 +08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 19:05:14 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-09-03 19:25:43 -03:00
										 |  |  | def detect_visual_c_compiler_version(tools_env): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     # tools_env is the variable scons uses to call tools that execute tasks, SCons's env['ENV'] that executes tasks... | 
					
						
							|  |  |  |     # (see the SCons documentation for more information on what it does)... | 
					
						
							| 
									
										
										
										
											2017-03-24 21:45:31 +01:00
										 |  |  |     # in order for this function to be well encapsulated i choose to force it to receive SCons's TOOLS env (env['ENV'] | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     # and not scons setup environment (env)... so make sure you call the right environment on it or it will fail to detect | 
					
						
							| 
									
										
										
										
											2017-03-24 21:45:31 +01:00
										 |  |  |     # the proper vc version that will be called | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-01-18 21:13:48 -06:00
										 |  |  |     # There is no flag to give to visual c compilers to set the architecture, ie scons bits argument (32,64,ARM etc) | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     # There are many different cl.exe files that are run, and each one compiles & links to a different architecture | 
					
						
							|  |  |  |     # As far as I know, the only way to figure out what compiler will be run when Scons calls cl.exe via Program() | 
					
						
							| 
									
										
										
										
											2018-02-21 11:30:55 -05:00
										 |  |  |     # is to check the PATH variable and figure out which one will be called first. Code below does that and returns: | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     # the following string values: | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     # ""              Compiler not detected | 
					
						
							|  |  |  |     # "amd64"         Native 64 bit compiler | 
					
						
							|  |  |  |     # "amd64_x86"     64 bit Cross Compiler for 32 bit | 
					
						
							|  |  |  |     # "x86"           Native 32 bit compiler | 
					
						
							|  |  |  |     # "x86_amd64"     32 bit Cross Compiler for 64 bit | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     # There are other architectures, but Godot does not support them currently, so this function does not detect arm/amd64_arm | 
					
						
							|  |  |  |     # and similar architectures/compilers | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     # Set chosen compiler to "not detected" | 
					
						
							|  |  |  |     vc_chosen_compiler_index = -1 | 
					
						
							|  |  |  |     vc_chosen_compiler_str = "" | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-05-23 21:50:06 +10:00
										 |  |  |     # Start with Pre VS 2017 checks which uses VCINSTALLDIR: | 
					
						
							|  |  |  |     if 'VCINSTALLDIR' in tools_env: | 
					
						
							| 
									
										
										
										
											2017-08-26 18:53:49 +02:00
										 |  |  |         # print("Checking VCINSTALLDIR") | 
					
						
							| 
									
										
										
										
											2017-05-23 21:50:06 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-02-21 11:30:55 -05:00
										 |  |  |         # find() works with -1 so big ifs below are needed... the simplest solution, in fact | 
					
						
							| 
									
										
										
										
											2017-05-23 21:50:06 +10:00
										 |  |  |         # First test if amd64 and amd64_x86 compilers are present in the path | 
					
						
							|  |  |  |         vc_amd64_compiler_detection_index = tools_env["PATH"].find(tools_env["VCINSTALLDIR"] + "BIN\\amd64;") | 
					
						
							|  |  |  |         if(vc_amd64_compiler_detection_index > -1): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_amd64_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "amd64" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         vc_amd64_x86_compiler_detection_index = tools_env["PATH"].find(tools_env["VCINSTALLDIR"] + "BIN\\amd64_x86;") | 
					
						
							|  |  |  |         if(vc_amd64_x86_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_amd64_x86_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_amd64_x86_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "amd64_x86" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         # Now check the 32 bit compilers | 
					
						
							|  |  |  |         vc_x86_compiler_detection_index = tools_env["PATH"].find(tools_env["VCINSTALLDIR"] + "BIN;") | 
					
						
							|  |  |  |         if(vc_x86_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_x86_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_x86_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "x86" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         vc_x86_amd64_compiler_detection_index = tools_env["PATH"].find(tools_env['VCINSTALLDIR'] + "BIN\\x86_amd64;") | 
					
						
							|  |  |  |         if(vc_x86_amd64_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_x86_amd64_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_x86_amd64_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "x86_amd64" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     # and for VS 2017 and newer we check VCTOOLSINSTALLDIR: | 
					
						
							|  |  |  |     if 'VCTOOLSINSTALLDIR' in tools_env: | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         # Newer versions have a different path available | 
					
						
							|  |  |  |         vc_amd64_compiler_detection_index = tools_env["PATH"].upper().find(tools_env['VCTOOLSINSTALLDIR'].upper() + "BIN\\HOSTX64\\X64;") | 
					
						
							|  |  |  |         if(vc_amd64_compiler_detection_index > -1): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_amd64_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "amd64" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         vc_amd64_x86_compiler_detection_index = tools_env["PATH"].upper().find(tools_env['VCTOOLSINSTALLDIR'].upper() + "BIN\\HOSTX64\\X86;") | 
					
						
							|  |  |  |         if(vc_amd64_x86_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_amd64_x86_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_amd64_x86_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "amd64_x86" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         vc_x86_compiler_detection_index = tools_env["PATH"].upper().find(tools_env['VCTOOLSINSTALLDIR'].upper() + "BIN\\HOSTX86\\X86;") | 
					
						
							|  |  |  |         if(vc_x86_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_x86_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_x86_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "x86" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         vc_x86_amd64_compiler_detection_index = tools_env["PATH"].upper().find(tools_env['VCTOOLSINSTALLDIR'].upper() + "BIN\\HOSTX86\\X64;") | 
					
						
							|  |  |  |         if(vc_x86_amd64_compiler_detection_index > -1 | 
					
						
							|  |  |  |            and (vc_chosen_compiler_index == -1 | 
					
						
							|  |  |  |                 or vc_chosen_compiler_index > vc_x86_amd64_compiler_detection_index)): | 
					
						
							|  |  |  |             vc_chosen_compiler_index = vc_x86_amd64_compiler_detection_index | 
					
						
							|  |  |  |             vc_chosen_compiler_str = "x86_amd64" | 
					
						
							| 
									
										
										
										
											2017-05-19 11:27:17 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     return vc_chosen_compiler_str | 
					
						
							| 
									
										
										
										
											2016-09-03 19:25:43 -03:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  | def find_visual_c_batch_file(env): | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |     from SCons.Tool.MSCommon.vc import get_default_version, get_host_target, find_batch_file | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |     version = get_default_version(env) | 
					
						
							| 
									
										
										
										
											2019-06-28 21:19:49 -04:00
										 |  |  |     (host_platform, target_platform, _) = get_host_target(env) | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  |     return find_batch_file(env, version, host_platform, target_platform)[0] | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-11-18 18:09:18 +01:00
										 |  |  | def generate_cpp_hint_file(filename): | 
					
						
							|  |  |  |     if os.path.isfile(filename): | 
					
						
							|  |  |  |         # Don't overwrite an existing hint file since the user may have customized it. | 
					
						
							|  |  |  |         pass | 
					
						
							|  |  |  |     else: | 
					
						
							|  |  |  |         try: | 
					
						
							| 
									
										
										
										
											2018-03-10 18:37:33 +01:00
										 |  |  |             with open(filename, "w") as fd: | 
					
						
							|  |  |  |                 fd.write("#define GDCLASS(m_class, m_inherits)\n") | 
					
						
							| 
									
										
										
										
											2017-11-18 18:09:18 +01:00
										 |  |  |         except IOError: | 
					
						
							|  |  |  |             print("Could not write cpp.hint file.") | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | def generate_vs_project(env, num_jobs): | 
					
						
							|  |  |  |     batch_file = find_visual_c_batch_file(env) | 
					
						
							|  |  |  |     if batch_file: | 
					
						
							|  |  |  |         def build_commandline(commands): | 
					
						
							|  |  |  |             common_build_prefix = ['cmd /V /C set "plat=$(PlatformTarget)"', | 
					
						
							|  |  |  |                                     '(if "$(PlatformTarget)"=="x64" (set "plat=x86_amd64"))', | 
					
						
							|  |  |  |                                     'set "tools=yes"', | 
					
						
							|  |  |  |                                     '(if "$(Configuration)"=="release" (set "tools=no"))', | 
					
						
							|  |  |  |                                     'call "' + batch_file + '" !plat!'] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |             result = " ^& ".join(common_build_prefix + [commands]) | 
					
						
							|  |  |  |             return result | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         env.AddToVSProject(env.core_sources) | 
					
						
							|  |  |  |         env.AddToVSProject(env.main_sources) | 
					
						
							|  |  |  |         env.AddToVSProject(env.modules_sources) | 
					
						
							|  |  |  |         env.AddToVSProject(env.scene_sources) | 
					
						
							|  |  |  |         env.AddToVSProject(env.servers_sources) | 
					
						
							|  |  |  |         env.AddToVSProject(env.editor_sources) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-10-29 21:10:44 +00:00
										 |  |  |         # windows allows us to have spaces in paths, so we need | 
					
						
							|  |  |  |         # to double quote off the directory. However, the path ends | 
					
						
							|  |  |  |         # in a backslash, so we need to remove this, lest it escape the | 
					
						
							|  |  |  |         # last double quote off, confusing MSBuild | 
					
						
							| 
									
										
										
										
											2017-11-18 17:51:24 +01:00
										 |  |  |         env['MSVSBUILDCOM'] = build_commandline('scons --directory="$(ProjectDir.TrimEnd(\'\\\'))" platform=windows progress=no target=$(Configuration) tools=!tools! -j' + str(num_jobs)) | 
					
						
							|  |  |  |         env['MSVSREBUILDCOM'] = build_commandline('scons --directory="$(ProjectDir.TrimEnd(\'\\\'))" platform=windows progress=no target=$(Configuration) tools=!tools! vsproj=yes -j' + str(num_jobs)) | 
					
						
							|  |  |  |         env['MSVSCLEANCOM'] = build_commandline('scons --directory="$(ProjectDir.TrimEnd(\'\\\'))" --clean platform=windows progress=no target=$(Configuration) tools=!tools! -j' + str(num_jobs)) | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |         # This version information (Win32, x64, Debug, Release, Release_Debug seems to be | 
					
						
							|  |  |  |         # required for Visual Studio to understand that it needs to generate an NMAKE | 
					
						
							|  |  |  |         # project. Do not modify without knowing what you are doing. | 
					
						
							|  |  |  |         debug_variants = ['debug|Win32'] + ['debug|x64'] | 
					
						
							|  |  |  |         release_variants = ['release|Win32'] + ['release|x64'] | 
					
						
							|  |  |  |         release_debug_variants = ['release_debug|Win32'] + ['release_debug|x64'] | 
					
						
							|  |  |  |         variants = debug_variants + release_variants + release_debug_variants | 
					
						
							|  |  |  |         debug_targets = ['bin\\godot.windows.tools.32.exe'] + ['bin\\godot.windows.tools.64.exe'] | 
					
						
							|  |  |  |         release_targets = ['bin\\godot.windows.opt.32.exe'] + ['bin\\godot.windows.opt.64.exe'] | 
					
						
							|  |  |  |         release_debug_targets = ['bin\\godot.windows.opt.tools.32.exe'] + ['bin\\godot.windows.opt.tools.64.exe'] | 
					
						
							|  |  |  |         targets = debug_targets + release_targets + release_debug_targets | 
					
						
							| 
									
										
										
										
											2018-09-13 03:42:52 -07:00
										 |  |  |         if not env.get('MSVS'): | 
					
						
							| 
									
										
										
										
											2018-11-20 11:14:07 +01:00
										 |  |  |             env['MSVS']['PROJECTSUFFIX'] = '.vcxproj' | 
					
						
							| 
									
										
										
										
											2018-09-13 03:42:52 -07:00
										 |  |  |             env['MSVS']['SOLUTIONSUFFIX'] = '.sln' | 
					
						
							| 
									
										
										
										
											2018-03-17 23:23:55 +01:00
										 |  |  |         env.MSVSProject( | 
					
						
							|  |  |  |             target=['#godot' + env['MSVSPROJECTSUFFIX']], | 
					
						
							|  |  |  |             incs=env.vs_incs, | 
					
						
							|  |  |  |             srcs=env.vs_srcs, | 
					
						
							|  |  |  |             runfile=targets, | 
					
						
							|  |  |  |             buildtarget=targets, | 
					
						
							|  |  |  |             auto_build_solution=1, | 
					
						
							|  |  |  |             variant=variants) | 
					
						
							| 
									
										
										
										
											2017-08-28 17:17:26 +02:00
										 |  |  |     else: | 
					
						
							|  |  |  |         print("Could not locate Visual Studio batch file for setting up the build environment. Not generating VS project.") | 
					
						
							| 
									
										
										
										
											2016-09-15 18:04:26 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-09-03 19:25:43 -03:00
										 |  |  | def precious_program(env, program, sources, **args): | 
					
						
							| 
									
										
										
										
											2016-10-30 18:44:57 +01:00
										 |  |  |     program = env.ProgramOriginal(program, sources, **args) | 
					
						
							|  |  |  |     env.Precious(program) | 
					
						
							|  |  |  |     return program | 
					
						
							| 
									
										
										
										
											2017-11-28 16:27:57 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | def add_shared_library(env, name, sources, **args): | 
					
						
							| 
									
										
										
										
											2017-12-18 18:01:09 -04:00
										 |  |  |     library = env.SharedLibrary(name, sources, **args) | 
					
						
							|  |  |  |     env.NoCache(library) | 
					
						
							|  |  |  |     return library | 
					
						
							| 
									
										
										
										
											2017-11-28 16:27:57 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | def add_library(env, name, sources, **args): | 
					
						
							| 
									
										
										
										
											2017-12-18 18:01:09 -04:00
										 |  |  |     library = env.Library(name, sources, **args) | 
					
						
							|  |  |  |     env.NoCache(library) | 
					
						
							|  |  |  |     return library | 
					
						
							| 
									
										
										
										
											2017-11-28 16:27:57 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | def add_program(env, name, sources, **args): | 
					
						
							| 
									
										
										
										
											2017-12-18 18:01:09 -04:00
										 |  |  |     program = env.Program(name, sources, **args) | 
					
						
							|  |  |  |     env.NoCache(program) | 
					
						
							|  |  |  |     return program | 
					
						
							| 
									
										
										
										
											2018-06-21 00:33:25 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | def CommandNoCache(env, target, sources, command, **args): | 
					
						
							|  |  |  |     result = env.Command(target, sources, command, **args) | 
					
						
							|  |  |  |     env.NoCache(result) | 
					
						
							|  |  |  |     return result | 
					
						
							| 
									
										
										
										
											2018-08-24 02:03:57 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | def detect_darwin_sdk_path(platform, env): | 
					
						
							|  |  |  |     sdk_name = '' | 
					
						
							|  |  |  |     if platform == 'osx': | 
					
						
							|  |  |  |         sdk_name = 'macosx' | 
					
						
							|  |  |  |         var_name = 'MACOS_SDK_PATH' | 
					
						
							|  |  |  |     elif platform == 'iphone': | 
					
						
							|  |  |  |         sdk_name = 'iphoneos' | 
					
						
							|  |  |  |         var_name = 'IPHONESDK' | 
					
						
							|  |  |  |     elif platform == 'iphonesimulator': | 
					
						
							|  |  |  |         sdk_name = 'iphonesimulator' | 
					
						
							|  |  |  |         var_name = 'IPHONESDK' | 
					
						
							|  |  |  |     else: | 
					
						
							|  |  |  |         raise Exception("Invalid platform argument passed to detect_darwin_sdk_path") | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if not env[var_name]: | 
					
						
							|  |  |  |         try: | 
					
						
							| 
									
										
										
										
											2018-11-24 21:09:40 +09:00
										 |  |  |             sdk_path = decode_utf8(subprocess.check_output(['xcrun', '--sdk', sdk_name, '--show-sdk-path']).strip()) | 
					
						
							| 
									
										
										
										
											2018-08-24 02:03:57 +02:00
										 |  |  |             if sdk_path: | 
					
						
							|  |  |  |                 env[var_name] = sdk_path | 
					
						
							| 
									
										
										
										
											2019-06-28 21:19:49 -04:00
										 |  |  |         except (subprocess.CalledProcessError, OSError): | 
					
						
							| 
									
										
										
										
											2018-08-24 02:03:57 +02:00
										 |  |  |             print("Failed to find SDK path while running xcrun --sdk {} --show-sdk-path.".format(sdk_name)) | 
					
						
							|  |  |  |             raise | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-02-12 21:10:08 +01:00
										 |  |  | def get_compiler_version(env): | 
					
						
							| 
									
										
										
										
											2019-07-25 23:59:25 +03:00
										 |  |  |     # Not using this method on clang because it returns 4.2.1 # https://reviews.llvm.org/D56803 | 
					
						
							|  |  |  |     if using_gcc(env): | 
					
						
							|  |  |  |         version = decode_utf8(subprocess.check_output([env['CXX'], '-dumpversion']).strip()) | 
					
						
							|  |  |  |     else: | 
					
						
							|  |  |  |         version = decode_utf8(subprocess.check_output([env['CXX'], '--version']).strip()) | 
					
						
							| 
									
										
										
										
											2019-02-12 21:10:08 +01:00
										 |  |  |     match = re.search('[0-9][0-9.]*', version) | 
					
						
							|  |  |  |     if match is not None: | 
					
						
							|  |  |  |         return match.group().split('.') | 
					
						
							|  |  |  |     else: | 
					
						
							|  |  |  |         return None | 
					
						
							| 
									
										
										
										
											2019-02-22 15:41:31 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-04-05 12:51:15 +02:00
										 |  |  | def using_gcc(env): | 
					
						
							| 
									
										
										
										
											2019-02-22 15:41:31 +01:00
										 |  |  |     return 'gcc' in os.path.basename(env["CC"]) | 
					
						
							| 
									
										
										
										
											2019-04-05 12:51:15 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | def using_clang(env): | 
					
						
							|  |  |  |     return 'clang' in os.path.basename(env["CC"]) |