Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "tools/gn/xcode_object.h" | 5 #include "tools/gn/xcode_object.h" |
| 6 | 6 |
| 7 #include <iomanip> | 7 #include <iomanip> |
| 8 #include <sstream> | 8 #include <sstream> |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 215 out << pair.first << " = "; | 215 out << pair.first << " = "; |
| 216 PrintValue(out, sub_rule, pair.second); | 216 PrintValue(out, sub_rule, pair.second); |
| 217 out << ";" << (rules.one_line ? " " : "\n"); | 217 out << ";" << (rules.one_line ? " " : "\n"); |
| 218 } | 218 } |
| 219 | 219 |
| 220 if (!rules.one_line && rules.level) | 220 if (!rules.one_line && rules.level) |
| 221 out << std::string(rules.level, '\t'); | 221 out << std::string(rules.level, '\t'); |
| 222 out << "}"; | 222 out << "}"; |
| 223 } | 223 } |
| 224 | 224 |
| 225 struct BuildSettingsValue | |
| 226 { | |
| 227 BuildSettingsValue(const std::string &s) : value(s) { } | |
| 228 std::string value; | |
| 229 }; | |
| 230 | |
| 231 // Build settings can contain multiple values represented by multiline string | |
| 232 void PrintValue(std::ostream& out, | |
| 233 IndentRules rules, | |
| 234 const BuildSettingsValue & buildSettingValue) { | |
| 235 const auto & value = buildSettingValue.value; | |
| 236 if (value.find('\n') == std::string::npos) { | |
| 237 PrintValue(out, rules, value); | |
| 238 } else { | |
| 239 // split and print as vector | |
|
matt.k
2016/06/10 07:35:11
Splitting the string to get multiple values is a h
| |
| 240 std::vector<std::string> values; | |
| 241 std::size_t start = 0, end = 0; | |
| 242 while ((end = value.find('\n', start)) != std::string::npos) { | |
| 243 std::string sub = value.substr(start, end - start); | |
| 244 if (!sub.empty()) values.push_back(sub); | |
| 245 start = end + 1; | |
| 246 } | |
| 247 std::string last = value.substr(start); | |
| 248 if (!last.empty()) { | |
| 249 values.push_back(last); | |
| 250 } | |
| 251 PrintValue(out, rules, values); | |
| 252 } | |
| 253 } | |
| 254 | |
| 225 template <typename ValueType> | 255 template <typename ValueType> |
| 226 void PrintProperty(std::ostream& out, | 256 void PrintProperty(std::ostream& out, |
| 227 IndentRules rules, | 257 IndentRules rules, |
| 228 const char* name, | 258 const char* name, |
| 229 ValueType&& value) { | 259 ValueType&& value) { |
| 230 if (!rules.one_line && rules.level) | 260 if (!rules.one_line && rules.level) |
| 231 out << std::string(rules.level, '\t'); | 261 out << std::string(rules.level, '\t'); |
| 232 | 262 |
| 233 out << name << " = "; | 263 out << name << " = "; |
| 234 PrintValue(out, rules, std::forward<ValueType>(value)); | 264 PrintValue(out, rules, std::forward<ValueType>(value)); |
| (...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 358 PrintProperty(out, rules, "buildPhases", build_phases_); | 388 PrintProperty(out, rules, "buildPhases", build_phases_); |
| 359 PrintProperty(out, rules, "dependencies", EmptyPBXObjectVector()); | 389 PrintProperty(out, rules, "dependencies", EmptyPBXObjectVector()); |
| 360 PrintProperty(out, rules, "name", name_); | 390 PrintProperty(out, rules, "name", name_); |
| 361 PrintProperty(out, rules, "productName", name_); | 391 PrintProperty(out, rules, "productName", name_); |
| 362 out << indent_str << "};\n"; | 392 out << indent_str << "};\n"; |
| 363 } | 393 } |
| 364 | 394 |
| 365 // PBXBuildFile --------------------------------------------------------------- | 395 // PBXBuildFile --------------------------------------------------------------- |
| 366 | 396 |
| 367 PBXBuildFile::PBXBuildFile(const PBXFileReference* file_reference, | 397 PBXBuildFile::PBXBuildFile(const PBXFileReference* file_reference, |
| 368 const PBXSourcesBuildPhase* build_phase) | 398 const PBXSourcesBuildPhase* build_phase, |
| 369 : file_reference_(file_reference), build_phase_(build_phase) { | 399 const std::string& cflags) |
| 400 : file_reference_(file_reference), build_phase_(build_phase), | |
| 401 cflags_(cflags) { | |
| 370 DCHECK(file_reference_); | 402 DCHECK(file_reference_); |
| 371 DCHECK(build_phase_); | 403 DCHECK(build_phase_); |
| 372 } | 404 } |
| 373 | 405 |
| 374 PBXBuildFile::~PBXBuildFile() {} | 406 PBXBuildFile::~PBXBuildFile() {} |
| 375 | 407 |
| 376 PBXObjectClass PBXBuildFile::Class() const { | 408 PBXObjectClass PBXBuildFile::Class() const { |
| 377 return PBXBuildFileClass; | 409 return PBXBuildFileClass; |
| 378 } | 410 } |
| 379 | 411 |
| 380 std::string PBXBuildFile::Name() const { | 412 std::string PBXBuildFile::Name() const { |
| 381 return file_reference_->Name() + " in " + build_phase_->Name(); | 413 return file_reference_->Name() + " in " + build_phase_->Name(); |
| 382 } | 414 } |
| 383 | 415 |
| 384 void PBXBuildFile::Print(std::ostream& out, unsigned indent) const { | 416 void PBXBuildFile::Print(std::ostream& out, unsigned indent) const { |
| 385 const std::string indent_str(indent, '\t'); | 417 const std::string indent_str(indent, '\t'); |
| 386 const IndentRules rules = {true, 0}; | 418 const IndentRules rules = {true, 0}; |
| 387 out << indent_str << Reference() << " = {"; | 419 out << indent_str << Reference() << " = {"; |
| 388 PrintProperty(out, rules, "isa", ToString(Class())); | 420 PrintProperty(out, rules, "isa", ToString(Class())); |
| 389 PrintProperty(out, rules, "fileRef", file_reference_); | 421 PrintProperty(out, rules, "fileRef", file_reference_); |
| 422 if (!cflags_.empty()) { | |
| 423 std::map<std::string, std::string> settings; | |
| 424 settings["COMPILER_FLAGS"] = cflags_; | |
| 425 PrintProperty(out, rules, "settings", settings); | |
| 426 } | |
| 390 out << "};\n"; | 427 out << "};\n"; |
| 391 } | 428 } |
| 392 | 429 |
| 393 // PBXFileReference ----------------------------------------------------------- | 430 // PBXFileReference ----------------------------------------------------------- |
| 394 | 431 |
| 395 PBXFileReference::PBXFileReference(const std::string& name, | 432 PBXFileReference::PBXFileReference(const std::string& name, |
| 396 const std::string& path, | 433 const std::string& path, |
| 397 const std::string& type) | 434 const std::string& type) |
| 398 : name_(name), path_(path), type_(type) {} | 435 : name_(name), path_(path), type_(type) {} |
| 399 | 436 |
| (...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 552 DCHECK(product_reference_); | 589 DCHECK(product_reference_); |
| 553 build_phases_.push_back(base::WrapUnique(new PBXSourcesBuildPhase)); | 590 build_phases_.push_back(base::WrapUnique(new PBXSourcesBuildPhase)); |
| 554 source_build_phase_ = | 591 source_build_phase_ = |
| 555 static_cast<PBXSourcesBuildPhase*>(build_phases_.back().get()); | 592 static_cast<PBXSourcesBuildPhase*>(build_phases_.back().get()); |
| 556 | 593 |
| 557 build_phases_.push_back(base::WrapUnique(new PBXFrameworksBuildPhase)); | 594 build_phases_.push_back(base::WrapUnique(new PBXFrameworksBuildPhase)); |
| 558 } | 595 } |
| 559 | 596 |
| 560 PBXNativeTarget::~PBXNativeTarget() {} | 597 PBXNativeTarget::~PBXNativeTarget() {} |
| 561 | 598 |
| 562 void PBXNativeTarget::AddFileForIndexing( | 599 void PBXNativeTarget::AddFileForIndexing(const PBXFileReference* file_reference, |
| 563 const PBXFileReference* file_reference) { | 600 const std::string& cflags) { |
| 564 DCHECK(file_reference); | 601 DCHECK(file_reference); |
| 565 source_build_phase_->AddBuildFile( | 602 source_build_phase_->AddBuildFile( |
| 566 base::WrapUnique(new PBXBuildFile(file_reference, source_build_phase_))); | 603 base::WrapUnique(new PBXBuildFile(file_reference, source_build_phase_, |
| 604 cflags))); | |
| 567 } | 605 } |
| 568 | 606 |
| 569 PBXObjectClass PBXNativeTarget::Class() const { | 607 PBXObjectClass PBXNativeTarget::Class() const { |
| 570 return PBXNativeTargetClass; | 608 return PBXNativeTargetClass; |
| 571 } | 609 } |
| 572 | 610 |
| 573 void PBXNativeTarget::Print(std::ostream& out, unsigned indent) const { | 611 void PBXNativeTarget::Print(std::ostream& out, unsigned indent) const { |
| 574 const std::string indent_str(indent, '\t'); | 612 const std::string indent_str(indent, '\t'); |
| 575 const IndentRules rules = {false, indent + 1}; | 613 const IndentRules rules = {false, indent + 1}; |
| 576 out << indent_str << Reference() << " = {\n"; | 614 out << indent_str << Reference() << " = {\n"; |
| (...skipping 23 matching lines...) Expand all Loading... | |
| 600 base::WrapUnique(new PBXGroup(source_path, "Source")))); | 638 base::WrapUnique(new PBXGroup(source_path, "Source")))); |
| 601 products_ = static_cast<PBXGroup*>(main_group_->AddChild( | 639 products_ = static_cast<PBXGroup*>(main_group_->AddChild( |
| 602 base::WrapUnique(new PBXGroup(std::string(), "Product")))); | 640 base::WrapUnique(new PBXGroup(std::string(), "Product")))); |
| 603 main_group_->AddChild(base::WrapUnique(new PBXGroup(std::string(), "Build"))); | 641 main_group_->AddChild(base::WrapUnique(new PBXGroup(std::string(), "Build"))); |
| 604 | 642 |
| 605 configurations_.reset(new XCConfigurationList(config_name, attributes, this)); | 643 configurations_.reset(new XCConfigurationList(config_name, attributes, this)); |
| 606 } | 644 } |
| 607 | 645 |
| 608 PBXProject::~PBXProject() {} | 646 PBXProject::~PBXProject() {} |
| 609 | 647 |
| 610 void PBXProject::AddSourceFile(const std::string& source_path) { | 648 bool PBXProject::SourceFileShouldBeIndexed(const std::string& source_path) { |
| 649 base::StringPiece ext = FindExtension(&source_path); | |
| 650 return IsSourceFileForIndexing(ext); | |
| 651 } | |
| 652 | |
| 653 void PBXProject::AddSourceFile(const std::string& source_path, | |
| 654 const std::string& cflags) { | |
| 611 PBXFileReference* file_reference = sources_->AddSourceFile(source_path); | 655 PBXFileReference* file_reference = sources_->AddSourceFile(source_path); |
| 612 base::StringPiece ext = FindExtension(&source_path); | 656 if (!SourceFileShouldBeIndexed(source_path)) |
| 613 if (!IsSourceFileForIndexing(ext)) | |
| 614 return; | 657 return; |
| 615 | 658 |
| 616 if (!target_for_indexing_) { | 659 if (!target_for_indexing_) { |
| 617 PBXAttributes attributes; | 660 PBXAttributes attributes; |
| 618 attributes["EXECUTABLE_PREFIX"] = ""; | 661 attributes["EXECUTABLE_PREFIX"] = ""; |
| 619 attributes["HEADER_SEARCH_PATHS"] = sources_->path(); | |
| 620 attributes["PRODUCT_NAME"] = name_; | 662 attributes["PRODUCT_NAME"] = name_; |
| 621 | 663 |
| 622 PBXFileReference* product_reference = static_cast<PBXFileReference*>( | 664 PBXFileReference* product_reference = static_cast<PBXFileReference*>( |
| 623 products_->AddChild(base::WrapUnique(new PBXFileReference( | 665 products_->AddChild(base::WrapUnique(new PBXFileReference( |
| 624 std::string(), name_, "compiled.mach-o.executable")))); | 666 std::string(), name_, "compiled.mach-o.executable")))); |
| 625 | 667 |
| 626 const char product_type[] = "com.apple.product-type.tool"; | 668 const char product_type[] = "com.apple.product-type.tool"; |
| 627 targets_.push_back(base::WrapUnique( | 669 targets_.push_back(base::WrapUnique( |
| 628 new PBXNativeTarget(name_, std::string(), config_name_, attributes, | 670 new PBXNativeTarget(name_, std::string(), config_name_, attributes, |
| 629 product_type, name_, product_reference))); | 671 product_type, name_, product_reference))); |
| 630 target_for_indexing_ = static_cast<PBXNativeTarget*>(targets_.back().get()); | 672 target_for_indexing_ = static_cast<PBXNativeTarget*>(targets_.back().get()); |
| 631 } | 673 } |
| 632 | 674 |
| 633 DCHECK(target_for_indexing_); | 675 DCHECK(target_for_indexing_); |
| 634 target_for_indexing_->AddFileForIndexing(file_reference); | 676 target_for_indexing_->AddFileForIndexing(file_reference, cflags); |
| 635 } | 677 } |
| 636 | 678 |
| 637 void PBXProject::AddAggregateTarget(const std::string& name, | 679 void PBXProject::AddAggregateTarget(const std::string& name, |
| 638 const std::string& shell_script) { | 680 const std::string& shell_script) { |
| 639 PBXAttributes attributes; | 681 PBXAttributes attributes; |
| 640 attributes["CODE_SIGNING_REQUIRED"] = "NO"; | 682 attributes["CODE_SIGNING_REQUIRED"] = "NO"; |
| 641 attributes["CONFIGURATION_BUILD_DIR"] = "."; | 683 attributes["CONFIGURATION_BUILD_DIR"] = "."; |
| 642 attributes["PRODUCT_NAME"] = name; | 684 attributes["PRODUCT_NAME"] = name; |
| 643 | 685 |
| 644 targets_.push_back(base::WrapUnique( | 686 targets_.push_back(base::WrapUnique( |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 811 | 853 |
| 812 std::string XCBuildConfiguration::Name() const { | 854 std::string XCBuildConfiguration::Name() const { |
| 813 return name_; | 855 return name_; |
| 814 } | 856 } |
| 815 | 857 |
| 816 void XCBuildConfiguration::Print(std::ostream& out, unsigned indent) const { | 858 void XCBuildConfiguration::Print(std::ostream& out, unsigned indent) const { |
| 817 const std::string indent_str(indent, '\t'); | 859 const std::string indent_str(indent, '\t'); |
| 818 const IndentRules rules = {false, indent + 1}; | 860 const IndentRules rules = {false, indent + 1}; |
| 819 out << indent_str << Reference() << " = {\n"; | 861 out << indent_str << Reference() << " = {\n"; |
| 820 PrintProperty(out, rules, "isa", ToString(Class())); | 862 PrintProperty(out, rules, "isa", ToString(Class())); |
| 821 PrintProperty(out, rules, "buildSettings", attributes_); | 863 std::map<std::string, BuildSettingsValue> build_settings; |
|
sdefresne
2016/06/10 08:52:34
I would use a multimap instead of splitting using
| |
| 864 for (const auto & pair : attributes_) { | |
| 865 build_settings.emplace(std::make_pair(pair.first, | |
| 866 BuildSettingsValue(pair.second))); | |
| 867 } | |
| 868 PrintProperty(out, rules, "buildSettings", build_settings); | |
| 822 PrintProperty(out, rules, "name", name_); | 869 PrintProperty(out, rules, "name", name_); |
| 823 out << indent_str << "};\n"; | 870 out << indent_str << "};\n"; |
| 824 } | 871 } |
| 825 | 872 |
| 826 // XCConfigurationList -------------------------------------------------------- | 873 // XCConfigurationList -------------------------------------------------------- |
| 827 | 874 |
| 828 XCConfigurationList::XCConfigurationList(const std::string& name, | 875 XCConfigurationList::XCConfigurationList(const std::string& name, |
| 829 const PBXAttributes& attributes, | 876 const PBXAttributes& attributes, |
| 830 const PBXObject* owner_reference) | 877 const PBXObject* owner_reference) |
| 831 : owner_reference_(owner_reference) { | 878 : owner_reference_(owner_reference) { |
| (...skipping 27 matching lines...) Expand all Loading... | |
| 859 const std::string indent_str(indent, '\t'); | 906 const std::string indent_str(indent, '\t'); |
| 860 const IndentRules rules = {false, indent + 1}; | 907 const IndentRules rules = {false, indent + 1}; |
| 861 out << indent_str << Reference() << " = {\n"; | 908 out << indent_str << Reference() << " = {\n"; |
| 862 PrintProperty(out, rules, "isa", ToString(Class())); | 909 PrintProperty(out, rules, "isa", ToString(Class())); |
| 863 PrintProperty(out, rules, "buildConfigurations", configurations_); | 910 PrintProperty(out, rules, "buildConfigurations", configurations_); |
| 864 PrintProperty(out, rules, "defaultConfigurationIsVisible", 1u); | 911 PrintProperty(out, rules, "defaultConfigurationIsVisible", 1u); |
| 865 PrintProperty(out, rules, "defaultConfigurationName", | 912 PrintProperty(out, rules, "defaultConfigurationName", |
| 866 configurations_[0]->Name()); | 913 configurations_[0]->Name()); |
| 867 out << indent_str << "};\n"; | 914 out << indent_str << "};\n"; |
| 868 } | 915 } |
| OLD | NEW |