| OLD | NEW |
| 1 # | 1 # |
| 2 # __COPYRIGHT__ | 2 # __COPYRIGHT__ |
| 3 # | 3 # |
| 4 # Permission is hereby granted, free of charge, to any person obtaining | 4 # Permission is hereby granted, free of charge, to any person obtaining |
| 5 # a copy of this software and associated documentation files (the | 5 # a copy of this software and associated documentation files (the |
| 6 # "Software"), to deal in the Software without restriction, including | 6 # "Software"), to deal in the Software without restriction, including |
| 7 # without limitation the rights to use, copy, modify, merge, publish, | 7 # without limitation the rights to use, copy, modify, merge, publish, |
| 8 # distribute, sublicense, and/or sell copies of the Software, and to | 8 # distribute, sublicense, and/or sell copies of the Software, and to |
| 9 # permit persons to whom the Software is furnished to do so, subject to | 9 # permit persons to whom the Software is furnished to do so, subject to |
| 10 # the following conditions: | 10 # the following conditions: |
| (...skipping 20 matching lines...) Expand all Loading... |
| 31 import md5 | 31 import md5 |
| 32 import os | 32 import os |
| 33 import random | 33 import random |
| 34 import re | 34 import re |
| 35 import UserList | 35 import UserList |
| 36 import xml.dom | 36 import xml.dom |
| 37 import xml.dom.minidom | 37 import xml.dom.minidom |
| 38 | 38 |
| 39 import SCons.Node.FS | 39 import SCons.Node.FS |
| 40 import SCons.Script | 40 import SCons.Script |
| 41 import SCons.Util |
| 41 | 42 |
| 42 from SCons.Debug import Trace | 43 from SCons.Debug import Trace |
| 43 TODO = 0 | 44 TODO = 0 |
| 44 | 45 |
| 45 # Initialize random number generator | 46 # Initialize random number generator |
| 46 random.seed() | 47 random.seed() |
| 47 | 48 |
| 48 | 49 |
| 49 #------------------------------------------------------------------------------ | 50 #------------------------------------------------------------------------------ |
| 50 # Entry point for supplying a fixed map of GUIDs for testing. | 51 # Entry point for supplying a fixed map of GUIDs for testing. |
| (...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 213 if not topdown: | 214 if not topdown: |
| 214 yield top, dirs, nondirs | 215 yield top, dirs, nondirs |
| 215 | 216 |
| 216 #------------------------------------------------------------------------------ | 217 #------------------------------------------------------------------------------ |
| 217 | 218 |
| 218 class _MSVSFolder(FileList): | 219 class _MSVSFolder(FileList): |
| 219 """Folder in a Visual Studio solution.""" | 220 """Folder in a Visual Studio solution.""" |
| 220 | 221 |
| 221 entry_type_guid = '{2150E333-8FDC-42A3-9474-1A3956D46DE8}' | 222 entry_type_guid = '{2150E333-8FDC-42A3-9474-1A3956D46DE8}' |
| 222 | 223 |
| 223 def initialize(self, path, name = None, entries = None, guid = None, items = N
one): | 224 def initialize(self, path, name=None, entries=None, guid=None, items=None): |
| 224 """Initializes the folder. | 225 """Initializes the folder. |
| 225 | 226 |
| 226 Args: | 227 Args: |
| 227 path: The unique name of the folder, by which other MSVS Nodes can | 228 path: The unique name of the folder, by which other MSVS Nodes can |
| 228 refer to it. This is not necessarily the name that gets printed | 229 refer to it. This is not necessarily the name that gets printed |
| 229 in the .sln file. | 230 in the .sln file. |
| 230 name: The name of this folder as actually written in a generated | 231 name: The name of this folder as actually written in a generated |
| 231 .sln file. The default is | 232 .sln file. The default is |
| 232 entries: List of folder entries to nest inside this folder. May contain | 233 entries: List of folder entries to nest inside this folder. May contain |
| 233 Folder or Project objects. May be None, if the folder is empty. | 234 Folder or Project objects. May be None, if the folder is empty. |
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 378 class MSVSTool(object): | 379 class MSVSTool(object): |
| 379 """Visual Studio tool.""" | 380 """Visual Studio tool.""" |
| 380 | 381 |
| 381 def __init__(self, Name, **attrs): | 382 def __init__(self, Name, **attrs): |
| 382 """Initializes the tool. | 383 """Initializes the tool. |
| 383 | 384 |
| 384 Args: | 385 Args: |
| 385 Name: Tool name. | 386 Name: Tool name. |
| 386 **attrs: Tool attributes. | 387 **attrs: Tool attributes. |
| 387 """ | 388 """ |
| 389 |
| 390 val = attrs.get('AdditionalDependencies') |
| 391 if val: |
| 392 if isinstance(val, list): |
| 393 val = ' '.join(val) |
| 394 attrs['AdditionalDependencies'] = val.replace('/', '\\') |
| 395 |
| 396 val = attrs.get('AdditionalIncludeDirectories') |
| 397 if val: |
| 398 if isinstance(val, list): |
| 399 val = ';'.join(val) |
| 400 attrs['AdditionalIncludeDirectories'] = val.replace('/', '\\') |
| 401 |
| 402 val = attrs.get('AdditionalManifestFiles') |
| 403 if val: |
| 404 if isinstance(val, list): |
| 405 val = ';'.join(val) |
| 406 attrs['AdditionalManifestFiles'] = val.replace('/', '\\') |
| 407 |
| 408 val = attrs.get('CommandLine') |
| 409 if val: |
| 410 if isinstance(val, list): |
| 411 val = '\r\n'.join(val) |
| 412 attrs['CommandLine'] = val.replace('/', '\\') |
| 413 |
| 414 val = attrs.get('PreprocessorDefinitions') |
| 415 if val: |
| 416 if isinstance(val, list): |
| 417 val = ';'.join(val) |
| 418 attrs['PreprocessorDefinitions'] = val |
| 419 |
| 420 for a in ('ImportLibrary', |
| 421 'ObjectFile', |
| 422 'OutputFile', |
| 423 'Outputs', |
| 424 'XMLDocumentationFileName'): |
| 425 val = attrs.get(a) |
| 426 if val: |
| 427 val = val.replace('/', '\\') |
| 428 attrs[a] = val |
| 429 |
| 388 self.Name = Name | 430 self.Name = Name |
| 389 self.attrs = attrs | 431 self.attrs = attrs |
| 390 | 432 |
| 391 def CreateElement(self, doc): | 433 def CreateElement(self, doc): |
| 392 """Creates an element for the tool. | 434 """Creates an element for the tool. |
| 393 | 435 |
| 394 Args: | 436 Args: |
| 395 doc: xml.dom.Document object to use for node creation. | 437 doc: xml.dom.Document object to use for node creation. |
| 396 | 438 |
| 397 Returns: | 439 Returns: |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 446 | 488 |
| 447 entry_type_guid = '{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}' | 489 entry_type_guid = '{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}' |
| 448 initialized = False | 490 initialized = False |
| 449 | 491 |
| 450 def initialize(self, env, path, name = None, | 492 def initialize(self, env, path, name = None, |
| 451 dependencies = None, | 493 dependencies = None, |
| 452 guid = None, | 494 guid = None, |
| 453 buildtargets = [], | 495 buildtargets = [], |
| 454 files = [], | 496 files = [], |
| 455 root_namespace = None, | 497 root_namespace = None, |
| 456 relative_path_prefix = '', | 498 keyword = None, |
| 499 relative_path_prefix = None, |
| 500 local_directory_prefix = None, |
| 501 relative_path_substitutions = [], |
| 457 tools = None, | 502 tools = None, |
| 458 configurations = None, | 503 configurations = None, |
| 459 **attrs): | 504 **attrs): |
| 460 """Initializes the project. | 505 """Initializes the project. |
| 461 | 506 |
| 462 Args: | 507 Args: |
| 463 path: Relative path to project file. | 508 path: Relative path to project file. |
| 464 name: Name of project. If None, the name will be the same as the base | 509 name: Name of project. If None, the name will be the same as the base |
| 465 name of the project file. | 510 name of the project file. |
| 466 dependencies: List of other Project objects this project is dependent | 511 dependencies: List of other Project objects this project is dependent |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 504 # pass | 549 # pass |
| 505 else: | 550 else: |
| 506 self.buildtargets = [] | 551 self.buildtargets = [] |
| 507 self.configurations = [] | 552 self.configurations = [] |
| 508 self.dependencies = [] | 553 self.dependencies = [] |
| 509 self.file_configurations = {} | 554 self.file_configurations = {} |
| 510 self.files = MSVSFiles([]) | 555 self.files = MSVSFiles([]) |
| 511 self.tool_files = [] | 556 self.tool_files = [] |
| 512 self.file_lists = [] | 557 self.file_lists = [] |
| 513 self.initialized = True | 558 self.initialized = True |
| 559 self.keyword = None |
| 560 self.local_directory_prefix = '' |
| 561 self.relative_path_prefix = '' |
| 562 self.relative_path_substitutions = [] |
| 563 self.root_namespace = name |
| 514 | 564 |
| 515 self.attrs = attrs | 565 self.attrs = attrs |
| 516 self.env = env | 566 self.env = env |
| 517 self.guid = guid | 567 self.guid = guid |
| 518 self.msvs_name = name | 568 self.msvs_name = name |
| 519 self.msvs_path = path | 569 self.msvs_path = path |
| 520 self.relative_path_prefix = relative_path_prefix | 570 if relative_path_prefix: |
| 521 self.root_namespace = root_namespace or self.msvs_name | 571 self.relative_path_prefix = relative_path_prefix |
| 572 if local_directory_prefix: |
| 573 self.local_directory_prefix = local_directory_prefix |
| 574 for left, right in relative_path_substitutions: |
| 575 t = (left.replace('/', '\\'), right.replace('/', '\\')) |
| 576 self.relative_path_substitutions.append(t) |
| 577 if root_namespace: |
| 578 self.root_namespace = root_namespace |
| 579 if keyword: |
| 580 self.keyword = keyword |
| 522 self.tools = tools | 581 self.tools = tools |
| 523 | 582 |
| 524 self.buildtargets.extend(buildtargets) | 583 self.buildtargets.extend(buildtargets) |
| 525 self.configurations.extend(configurations or []) | 584 self.configurations.extend(configurations or []) |
| 526 self.dependencies.extend(list(dependencies or [])) | 585 self.dependencies.extend(list(dependencies or [])) |
| 527 self.AddFiles(files) | 586 self.AddFiles(files) |
| 528 | 587 |
| 529 env.Command(self, [], MSVSProjectAction) | 588 env.Command(self, [], MSVSProjectAction) |
| 530 | 589 |
| 531 def args2nodes(self, entries): | 590 def args2nodes(self, entries): |
| 532 result = [] | 591 result = [] |
| 533 for entry in entries: | 592 for entry in entries: |
| 534 if SCons.Util.is_String(entry): | 593 if SCons.Util.is_String(entry): |
| 535 entry = self.env.File(entry) | 594 entry = self.env.File(entry) |
| 536 result.append(entry) | 595 result.append(entry.srcnode()) |
| 537 elif hasattr(entry, 'entries'): | 596 elif hasattr(entry, 'entries'): |
| 538 entry.entries = self.args2nodes(entry.entries) | 597 entry.entries = self.args2nodes(entry.entries) |
| 539 result.append(entry) | 598 result.append(entry) |
| 540 elif isinstance(entry, (list, UserList.UserList)): | 599 elif isinstance(entry, (list, UserList.UserList)): |
| 541 result.extend(self.args2nodes(entry)) | 600 result.extend(self.args2nodes(entry)) |
| 542 elif hasattr(entry, 'sources') and entry.sources: | 601 elif hasattr(entry, 'sources') and entry.sources: |
| 543 result.extend(entry.sources) | 602 result.extend(entry.sources) |
| 544 else: | 603 else: |
| 545 result.append(entry.srcnode()) | 604 result.append(entry.srcnode()) |
| 546 return result | 605 return result |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 587 # 4. We should be able to handle pre-built project files by reading the | 646 # 4. We should be able to handle pre-built project files by reading the |
| 588 # GUID from the files. | 647 # GUID from the files. |
| 589 guid = MakeGuid(self.msvs_path) | 648 guid = MakeGuid(self.msvs_path) |
| 590 self.guid = guid | 649 self.guid = guid |
| 591 return self.guid | 650 return self.guid |
| 592 | 651 |
| 593 def get_msvs_path(self, sln): | 652 def get_msvs_path(self, sln): |
| 594 return sln.rel_path(self).replace('/', '\\') | 653 return sln.rel_path(self).replace('/', '\\') |
| 595 | 654 |
| 596 def get_rel_path(self, node): | 655 def get_rel_path(self, node): |
| 597 result = self.relative_path_prefix + self.rel_path(node) | 656 result = self.rel_path(node) |
| 598 return result.replace('/', '\\') | 657 if self.relative_path_prefix: |
| 658 if not result.startswith('..'): |
| 659 result = self.relative_path_prefix + result |
| 660 elif not os.path.split(result)[0]: |
| 661 result = self.local_directory_prefix + result |
| 662 result = result.replace('/', '\\') |
| 663 for left, right in self.relative_path_substitutions: |
| 664 result = result.replace(left, right) |
| 665 return result |
| 599 | 666 |
| 600 def AddConfig(self, Name, tools=None, **attrs): | 667 def AddConfig(self, Name, tools=None, **attrs): |
| 601 """Adds a configuration to the parent node. | 668 """Adds a configuration to the parent node. |
| 602 | 669 |
| 603 Args: | 670 Args: |
| 604 Name: The name of the configuration. | 671 Name: The name of the configuration. |
| 605 tools: List of tools (strings or Tool objects); may be None. | 672 tools: List of tools (strings or Tool objects); may be None. |
| 606 **attrs: Configuration attributes. | 673 **attrs: Configuration attributes. |
| 607 """ | 674 """ |
| 608 if tools is None: | 675 if tools is None: |
| (...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 703 xml_impl = xml.dom.getDOMImplementation() | 770 xml_impl = xml.dom.getDOMImplementation() |
| 704 self.doc = xml_impl.createDocument(None, 'VisualStudioProject', None) | 771 self.doc = xml_impl.createDocument(None, 'VisualStudioProject', None) |
| 705 | 772 |
| 706 # Add attributes to root element | 773 # Add attributes to root element |
| 707 root = self.doc.documentElement | 774 root = self.doc.documentElement |
| 708 root.setAttribute('ProjectType', 'Visual C++') | 775 root.setAttribute('ProjectType', 'Visual C++') |
| 709 root.setAttribute('Version', '8.00') | 776 root.setAttribute('Version', '8.00') |
| 710 root.setAttribute('Name', self.msvs_name) | 777 root.setAttribute('Name', self.msvs_name) |
| 711 root.setAttribute('ProjectGUID', self.get_guid()) | 778 root.setAttribute('ProjectGUID', self.get_guid()) |
| 712 root.setAttribute('RootNamespace', self.root_namespace) | 779 root.setAttribute('RootNamespace', self.root_namespace) |
| 713 root.setAttribute('Keyword', 'Win32Proj') | 780 if self.keyword: |
| 781 root.setAttribute('Keyword', self.keyword) |
| 714 | 782 |
| 715 # Add platform list | 783 # Add platform list |
| 716 platforms = self.doc.createElement('Platforms') | 784 platforms = self.doc.createElement('Platforms') |
| 717 root.appendChild(platforms) | 785 root.appendChild(platforms) |
| 718 n = self.doc.createElement('Platform') | 786 n = self.doc.createElement('Platform') |
| 719 n.setAttribute('Name', 'Win32') | 787 n.setAttribute('Name', 'Win32') |
| 720 platforms.appendChild(n) | 788 platforms.appendChild(n) |
| 721 | 789 |
| 722 # Add tool files section | 790 # Add tool files section |
| 723 tool_files = self.doc.createElement('ToolFiles') | 791 tool_files = self.doc.createElement('ToolFiles') |
| (...skipping 364 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1088 'InheritedPropertySheets', | 1156 'InheritedPropertySheets', |
| 1089 ], | 1157 ], |
| 1090 'FileConfiguration' : [ | 1158 'FileConfiguration' : [ |
| 1091 'Name', | 1159 'Name', |
| 1092 'ExcludedFromBuild', | 1160 'ExcludedFromBuild', |
| 1093 ], | 1161 ], |
| 1094 'Tool' : [ | 1162 'Tool' : [ |
| 1095 'Name', | 1163 'Name', |
| 1096 'DisableSpecificWarnings', | 1164 'DisableSpecificWarnings', |
| 1097 | 1165 |
| 1166 'AdditionalIncludeDirectories', |
| 1167 'Description', |
| 1168 'CommandLine', |
| 1169 'OutputFile', |
| 1170 'ImportLibrary', |
| 1098 'PreprocessorDefinitions', | 1171 'PreprocessorDefinitions', |
| 1099 'UsePrecompiledHeader', | 1172 'UsePrecompiledHeader', |
| 1100 'PrecompiledHeaderThrough', | 1173 'PrecompiledHeaderThrough', |
| 1101 'ForcedIncludeFiles', | 1174 'ForcedIncludeFiles', |
| 1102 ], | 1175 ], |
| 1103 'VisualStudioProject' : [ | 1176 'VisualStudioProject' : [ |
| 1104 'ProjectType', | 1177 'ProjectType', |
| 1105 'Version', | 1178 'Version', |
| 1106 'Name', | 1179 'Name', |
| 1107 'ProjectGUID', | 1180 'ProjectGUID', |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1171 return result | 1244 return result |
| 1172 | 1245 |
| 1173 #------------------------------------------------------------------------------ | 1246 #------------------------------------------------------------------------------ |
| 1174 | 1247 |
| 1175 MSVSSolutionAction = SCons.Script.Action(MSVSAction, | 1248 MSVSSolutionAction = SCons.Script.Action(MSVSAction, |
| 1176 "Generating Visual Studio solution `$TA
RGET' ...") | 1249 "Generating Visual Studio solution `$TA
RGET' ...") |
| 1177 | 1250 |
| 1178 class _MSVSSolution(SCons.Node.FS.File): | 1251 class _MSVSSolution(SCons.Node.FS.File): |
| 1179 """Visual Studio solution.""" | 1252 """Visual Studio solution.""" |
| 1180 | 1253 |
| 1181 def initialize(self, env, path, entries = None, variants = None, websiteProper
ties = True): | 1254 def initialize(self, env, path, entries=None, variants=None, websiteProperties
=True): |
| 1182 """Initializes the solution. | 1255 """Initializes the solution. |
| 1183 | 1256 |
| 1184 Args: | 1257 Args: |
| 1185 path: Path to solution file. | 1258 path: Path to solution file. |
| 1186 entries: List of entries in solution. May contain Folder or Project | 1259 entries: List of entries in solution. May contain Folder or Project |
| 1187 objects. May be None, if the folder is empty. | 1260 objects. May be None, if the folder is empty. |
| 1188 variants: List of build variant strings. If none, a default list will | 1261 variants: List of build variant strings. If none, a default list will |
| 1189 be used. | 1262 be used. |
| 1190 """ | 1263 """ |
| 1191 self.msvs_path = path | 1264 self.msvs_path = path |
| (...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1363 | 1436 |
| 1364 def MSVSSolution(env, item, *args, **kw): | 1437 def MSVSSolution(env, item, *args, **kw): |
| 1365 if not SCons.Util.is_String(item): | 1438 if not SCons.Util.is_String(item): |
| 1366 return item | 1439 return item |
| 1367 item = env.subst(item) | 1440 item = env.subst(item) |
| 1368 result = env.fs._lookup(item, None, _MSVSSolution, create=1) | 1441 result = env.fs._lookup(item, None, _MSVSSolution, create=1) |
| 1369 result.initialize(env, item, *args, **kw) | 1442 result.initialize(env, item, *args, **kw) |
| 1370 LookupAdd(item, result) | 1443 LookupAdd(item, result) |
| 1371 return result | 1444 return result |
| 1372 | 1445 |
| 1446 class Derived(SCons.Util.Proxy): |
| 1447 def srcnode(self, *args, **kw): |
| 1448 return self |
| 1449 def __getattr__(self, name): |
| 1450 if name == 'sources': |
| 1451 return [] |
| 1452 return SCons.Util.Proxy.__getattr__(self, name) |
| 1453 def __hash__(self, *args, **kw): |
| 1454 return id(self) |
| 1455 |
| 1373 import __builtin__ | 1456 import __builtin__ |
| 1374 | 1457 |
| 1458 __builtin__.Derived = Derived |
| 1375 __builtin__.MSVSConfig = MSVSConfig | 1459 __builtin__.MSVSConfig = MSVSConfig |
| 1376 __builtin__.MSVSFilter = MSVSFilter | 1460 __builtin__.MSVSFilter = MSVSFilter |
| 1377 __builtin__.MSVSProject = MSVSProject | 1461 __builtin__.MSVSProject = MSVSProject |
| 1378 __builtin__.MSVSSolution = MSVSSolution | 1462 __builtin__.MSVSSolution = MSVSSolution |
| 1379 __builtin__.MSVSTool = MSVSTool | 1463 __builtin__.MSVSTool = MSVSTool |
| OLD | NEW |