Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 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/filesystem_utils.h" | 5 #include "tools/gn/filesystem_utils.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/files/file_util.h" | 9 #include "base/files/file_util.h" |
| 10 #include "base/logging.h" | 10 #include "base/logging.h" |
| (...skipping 402 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 413 | 413 |
| 414 dest->assign("//"); // Result is source root relative. | 414 dest->assign("//"); // Result is source root relative. |
| 415 dest->append(&path.data()[first_after_slash], | 415 dest->append(&path.data()[first_after_slash], |
| 416 path.size() - first_after_slash); | 416 path.size() - first_after_slash); |
| 417 return true; | 417 return true; |
| 418 } | 418 } |
| 419 return false; | 419 return false; |
| 420 #endif | 420 #endif |
| 421 } | 421 } |
| 422 | 422 |
| 423 std::string InvertDir(const SourceDir& path) { | |
| 424 const std::string value = path.value(); | |
| 425 if (value.empty()) | |
| 426 return std::string(); | |
| 427 | |
| 428 DCHECK(value[0] == '/'); | |
| 429 size_t begin_index = 1; | |
| 430 | |
| 431 // If the input begins with two slashes, skip over both (this is a | |
| 432 // source-relative dir). These must be forward slashes only. | |
| 433 if (value.size() > 1 && value[1] == '/') | |
| 434 begin_index = 2; | |
| 435 | |
| 436 std::string ret; | |
| 437 for (size_t i = begin_index; i < value.size(); i++) { | |
| 438 if (IsSlash(value[i])) | |
| 439 ret.append("../"); | |
| 440 } | |
| 441 return ret; | |
| 442 } | |
| 443 | |
| 444 void NormalizePath(std::string* path) { | 423 void NormalizePath(std::string* path) { |
| 445 char* pathbuf = path->empty() ? NULL : &(*path)[0]; | 424 char* pathbuf = path->empty() ? NULL : &(*path)[0]; |
| 446 | 425 |
| 447 // top_index is the first character we can modify in the path. Anything | 426 // top_index is the first character we can modify in the path. Anything |
| 448 // before this indicates where the path is relative to. | 427 // before this indicates where the path is relative to. |
| 449 size_t top_index = 0; | 428 size_t top_index = 0; |
| 450 bool is_relative = true; | 429 bool is_relative = true; |
| 451 if (!path->empty() && pathbuf[0] == '/') { | 430 if (!path->empty() && pathbuf[0] == '/') { |
| 452 is_relative = false; | 431 is_relative = false; |
| 453 | 432 |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 531 | 510 |
| 532 void ConvertPathToSystem(std::string* path) { | 511 void ConvertPathToSystem(std::string* path) { |
| 533 #if defined(OS_WIN) | 512 #if defined(OS_WIN) |
| 534 for (size_t i = 0; i < path->size(); i++) { | 513 for (size_t i = 0; i < path->size(); i++) { |
| 535 if ((*path)[i] == '/') | 514 if ((*path)[i] == '/') |
| 536 (*path)[i] = '\\'; | 515 (*path)[i] = '\\'; |
| 537 } | 516 } |
| 538 #endif | 517 #endif |
| 539 } | 518 } |
| 540 | 519 |
| 541 std::string RebaseSourceAbsolutePath(const std::string& input, | 520 std::string MakeRelativePath(const std::string& input, |
| 542 const SourceDir& dest_dir) { | 521 const std::string& dest) { |
| 543 CHECK(input.size() >= 2 && input[0] == '/' && input[1] == '/') | 522 std::string ret; |
| 544 << "Input to rebase isn't source-absolute: " << input; | |
| 545 CHECK(dest_dir.is_source_absolute()) | |
| 546 << "Dir to rebase to isn't source-absolute: " << dest_dir.value(); | |
| 547 | |
| 548 const std::string& dest = dest_dir.value(); | |
| 549 | 523 |
| 550 // Skip the common prefixes of the source and dest as long as they end in | 524 // Skip the common prefixes of the source and dest as long as they end in |
| 551 // a [back]slash. | 525 // a [back]slash. |
| 552 size_t common_prefix_len = 2; // The beginning two "//" are always the same. | 526 size_t common_prefix_len = 0; |
| 553 size_t max_common_length = std::min(input.size(), dest.size()); | 527 size_t max_common_length = std::min(input.size(), dest.size()); |
| 554 for (size_t i = common_prefix_len; i < max_common_length; i++) { | 528 for (size_t i = common_prefix_len; i < max_common_length; i++) { |
| 555 if (IsSlash(input[i]) && IsSlash(dest[i])) | 529 if (IsSlash(input[i]) && IsSlash(dest[i])) |
| 556 common_prefix_len = i + 1; | 530 common_prefix_len = i + 1; |
| 557 else if (input[i] != dest[i]) | 531 else if (input[i] != dest[i]) |
| 558 break; | 532 break; |
| 559 } | 533 } |
| 560 | 534 |
| 561 // Invert the dest dir starting from the end of the common prefix. | 535 // Invert the dest dir starting from the end of the common prefix. |
| 562 std::string ret; | |
| 563 for (size_t i = common_prefix_len; i < dest.size(); i++) { | 536 for (size_t i = common_prefix_len; i < dest.size(); i++) { |
| 564 if (IsSlash(dest[i])) | 537 if (IsSlash(dest[i])) |
| 565 ret.append("../"); | 538 ret.append("../"); |
| 566 } | 539 } |
| 567 | 540 |
| 568 // Append any remaining unique input. | 541 // Append any remaining unique input. |
| 569 ret.append(&input[common_prefix_len], input.size() - common_prefix_len); | 542 ret.append(&input[common_prefix_len], input.size() - common_prefix_len); |
| 570 | 543 |
| 571 // If the result is still empty, the paths are the same. | 544 // If the result is still empty, the paths are the same. |
| 572 if (ret.empty()) | 545 if (ret.empty()) |
| 573 ret.push_back('.'); | 546 ret.push_back('.'); |
| 574 | 547 |
| 575 return ret; | 548 return ret; |
| 576 } | 549 } |
| 577 | 550 |
| 551 std::string RebaseSourceAbsolutePath(const std::string& input, | |
| 552 const SourceDir& dest_dir, | |
| 553 const base::FilePath& source_root) { | |
| 554 std::string ret; | |
| 555 bool input_is_source_path = (input.size() >= 2 && | |
| 556 input[0] == '/' && input[1] == '/'); | |
| 557 | |
| 558 if (!input_is_source_path || !dest_dir.is_source_absolute()) { | |
| 559 std::string input_full; | |
| 560 std::string dest_full; | |
| 561 if (input_is_source_path) | |
| 562 input_full = source_root.Append(input.substr(2)).value(); | |
| 563 else | |
| 564 input_full = input; | |
| 565 if (dest_dir.is_source_absolute()) | |
| 566 dest_full = source_root.Append(dest_dir.value().substr(2)).value(); | |
| 567 else | |
| 568 dest_full = dest_dir.value(); | |
| 569 bool remove_slash = false; | |
| 570 if (!EndsWithSlash(input_full)) { | |
| 571 input_full.push_back('/'); | |
| 572 remove_slash = true; | |
| 573 } | |
| 574 if (!EndsWithSlash(dest_full)) | |
| 575 dest_full.push_back('/'); | |
| 576 | |
| 577 ret = MakeRelativePath(input_full, dest_full); | |
| 578 if (remove_slash && ret.size() > 1) | |
| 579 ret.pop_back(); | |
|
brettw
2014/10/07 17:51:36
I get a compiler error that this function doesn't
zeuthen
2014/10/07 18:14:38
It's a C++-11-ism, sorry. I'll change it.
| |
| 580 return ret; | |
| 581 } | |
| 582 | |
| 583 ret = MakeRelativePath(input, dest_dir.value()); | |
| 584 return ret; | |
| 585 } | |
| 586 | |
| 578 std::string DirectoryWithNoLastSlash(const SourceDir& dir) { | 587 std::string DirectoryWithNoLastSlash(const SourceDir& dir) { |
| 579 std::string ret; | 588 std::string ret; |
| 580 | 589 |
| 581 if (dir.value().empty()) { | 590 if (dir.value().empty()) { |
| 582 // Just keep input the same. | 591 // Just keep input the same. |
| 583 } else if (dir.value() == "/") { | 592 } else if (dir.value() == "/") { |
| 584 ret.assign("/."); | 593 ret.assign("/."); |
| 585 } else if (dir.value() == "//") { | 594 } else if (dir.value() == "//") { |
| 586 ret.assign("//."); | 595 ret.assign("//."); |
| 587 } else { | 596 } else { |
| (...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 690 OutputFile GetOutputDirForSourceDirAsOutputFile(const Settings* settings, | 699 OutputFile GetOutputDirForSourceDirAsOutputFile(const Settings* settings, |
| 691 const SourceDir& source_dir) { | 700 const SourceDir& source_dir) { |
| 692 OutputFile result = settings->toolchain_output_subdir(); | 701 OutputFile result = settings->toolchain_output_subdir(); |
| 693 result.value().append("obj/"); | 702 result.value().append("obj/"); |
| 694 | 703 |
| 695 if (source_dir.is_source_absolute()) { | 704 if (source_dir.is_source_absolute()) { |
| 696 // The source dir is source-absolute, so we trim off the two leading | 705 // The source dir is source-absolute, so we trim off the two leading |
| 697 // slashes to append to the toolchain object directory. | 706 // slashes to append to the toolchain object directory. |
| 698 result.value().append(&source_dir.value()[2], | 707 result.value().append(&source_dir.value()[2], |
| 699 source_dir.value().size() - 2); | 708 source_dir.value().size() - 2); |
| 709 } else { | |
| 710 // system-absolute | |
| 711 const std::string& build_dir = | |
| 712 settings->build_settings()->build_dir().value(); | |
| 713 | |
| 714 if (StartsWithASCII(source_dir.value(), build_dir, true)) { | |
| 715 size_t build_dir_size = build_dir.size(); | |
| 716 result.value().append(&source_dir.value()[build_dir_size], | |
| 717 source_dir.value().size() - build_dir_size); | |
| 718 } | |
| 700 } | 719 } |
| 701 return result; | 720 return result; |
| 702 } | 721 } |
| 703 | 722 |
| 704 SourceDir GetGenDirForSourceDir(const Settings* settings, | 723 SourceDir GetGenDirForSourceDir(const Settings* settings, |
| 705 const SourceDir& source_dir) { | 724 const SourceDir& source_dir) { |
| 706 return GetGenDirForSourceDirAsOutputFile(settings, source_dir).AsSourceDir( | 725 return GetGenDirForSourceDirAsOutputFile(settings, source_dir).AsSourceDir( |
| 707 settings->build_settings()); | 726 settings->build_settings()); |
| 708 } | 727 } |
| 709 | 728 |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 744 | 763 |
| 745 SourceDir GetCurrentOutputDir(const Scope* scope) { | 764 SourceDir GetCurrentOutputDir(const Scope* scope) { |
| 746 return GetOutputDirForSourceDirAsOutputFile( | 765 return GetOutputDirForSourceDirAsOutputFile( |
| 747 scope->settings(), scope->GetSourceDir()).AsSourceDir( | 766 scope->settings(), scope->GetSourceDir()).AsSourceDir( |
| 748 scope->settings()->build_settings()); | 767 scope->settings()->build_settings()); |
| 749 } | 768 } |
| 750 | 769 |
| 751 SourceDir GetCurrentGenDir(const Scope* scope) { | 770 SourceDir GetCurrentGenDir(const Scope* scope) { |
| 752 return GetGenDirForSourceDir(scope->settings(), scope->GetSourceDir()); | 771 return GetGenDirForSourceDir(scope->settings(), scope->GetSourceDir()); |
| 753 } | 772 } |
| OLD | NEW |