| // Copyright 2020 The Chromium Authors. All rights reserved. | |
| // Use of this source code is governed by a BSD-style license that can be | |
| // found in the LICENSE file. | |
| #include "gn/rust_project_writer_helpers.h" | |
| #include "base/strings/string_util.h" | |
| #include "gn/filesystem_utils.h" | |
| #include "gn/string_output_buffer.h" | |
| #include "gn/test_with_scheduler.h" | |
| #include "gn/test_with_scope.h" | |
| #include "util/build_config.h" | |
| #include "util/test/test.h" | |
| static void ExpectEqOrShowDiff(const char* expected, | |
| const std::string& actual) { | |
| if (expected != actual) { | |
| printf("\nExpected: >>>\n%s<<<\n", expected); | |
| printf(" Actual: >>>\n%s<<<\n", actual.c_str()); | |
| } | |
| EXPECT_EQ(expected, actual); | |
| } | |
| using RustProjectWriterHelper = TestWithScheduler; | |
| TEST_F(RustProjectWriterHelper, WriteCrates) { | |
| TestWithScope setup; | |
| std::optional<std::string> sysroot; | |
| CrateList crates; | |
| Crate dep = Crate(SourceFile("/root/tortoise/lib.rs"), {}, 0, | |
| "//tortoise:bar", "2015"); | |
| Crate target = | |
| Crate(SourceFile("/root/hare/lib.rs"), | |
| {SourceDir("//out/Debug/gendir/hare")}, 1, "//hare:bar", "2015"); | |
| target.AddDependency(0, "tortoise"); | |
| target.AddConfigItem("unix"); | |
| target.AddConfigItem("feature=\"test\""); | |
| crates.push_back(dep); | |
| crates.push_back(target); | |
| std::ostringstream stream; | |
| WriteCrates(setup.build_settings(), crates, sysroot, stream); | |
| std::string out = stream.str(); | |
| #if defined(OS_WIN) | |
| base::ReplaceSubstringsAfterOffset(&out, 0, "\r\n", "\n"); | |
| #endif | |
| const char expected_json[] = | |
| "{\n" | |
| " \"crates\": [\n" | |
| " {\n" | |
| " \"crate_id\": 0,\n" | |
| " \"root_module\": \"/root/tortoise/lib.rs\",\n" | |
| " \"label\": \"//tortoise:bar\",\n" | |
| " \"source\": {\n" | |
| " \"include_dirs\": [\n" | |
| " \"/root/tortoise/\"\n" | |
| " ],\n" | |
| " \"exclude_dirs\": []\n" | |
| " },\n" | |
| " \"deps\": [\n" | |
| " ],\n" | |
| " \"edition\": \"2015\",\n" | |
| " \"cfg\": [\n" | |
| " ]\n" | |
| " },\n" | |
| " {\n" | |
| " \"crate_id\": 1,\n" | |
| " \"root_module\": \"/root/hare/lib.rs\",\n" | |
| " \"label\": \"//hare:bar\",\n" | |
| " \"source\": {\n" | |
| " \"include_dirs\": [\n" | |
| " \"/root/hare/\",\n" | |
| " \"out/Debug/gendir/hare/\"\n" | |
| " ],\n" | |
| " \"exclude_dirs\": []\n" | |
| " },\n" | |
| " \"deps\": [\n" | |
| " {\n" | |
| " \"crate\": 0,\n" | |
| " \"name\": \"tortoise\"\n" | |
| " }\n" | |
| " ],\n" | |
| " \"edition\": \"2015\",\n" | |
| " \"cfg\": [\n" | |
| " \"unix\",\n" | |
| " \"feature=\\\"test\\\"\"\n" | |
| " ]\n" | |
| " }\n" | |
| " ]\n" | |
| "}\n"; | |
| ExpectEqOrShowDiff(expected_json, out); | |
| } | |
| TEST_F(RustProjectWriterHelper, SysrootDepsAreCorrect) { | |
| TestWithScope setup; | |
| setup.build_settings()->SetRootPath(UTF8ToFilePath("/root")); | |
| std::optional<std::string> sysroot = "sysroot"; | |
| CrateList crates; | |
| std::ostringstream stream; | |
| WriteCrates(setup.build_settings(), crates, sysroot, stream); | |
| std::string out = stream.str(); | |
| #if defined(OS_WIN) | |
| base::ReplaceSubstringsAfterOffset(&out, 0, "\r\n", "\n"); | |
| #endif | |
| const char expected_json[] = | |
| "{\n" | |
| " \"sysroot\": \"/root/out/Debug/sysroot\",\n" | |
| " \"sysroot_src\": " | |
| "\"/root/out/Debug/sysroot/lib/rustlib/src/rust/library\",\n" | |
| " \"crates\": [\n" | |
| " ]\n" | |
| "}\n"; | |
| ExpectEqOrShowDiff(expected_json, out); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractCompilerTargetTupleSimple) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg=feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--target"); | |
| target.config_values().rustflags().push_back("x86-someos"); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::optional<std::string> result = FindArgValue("--target", args); | |
| auto expected = std::optional<std::string>{"x86-someos"}; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractCompilerTargetTupleMissing) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back( | |
| "--cfg=featur4e=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("x86-someos"); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::optional<std::string> result = FindArgValue("--target", args); | |
| auto expected = std::nullopt; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractCompilerTargetTupleDontFallOffEnd) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg=feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| target.config_values().rustflags().push_back("--target"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::optional<std::string> result = FindArgValue("--target", args); | |
| auto expected = std::nullopt; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractFirstArgValueWithPrefixMissing) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg=feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| target.config_values().rustflags().push_back("--target"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::optional<std::string> result = | |
| FindArgValueAfterPrefix("--missing", args); | |
| auto expected = std::nullopt; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractFirstArgValueWithPrefix) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg=feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| target.config_values().rustflags().push_back("--target"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::optional<std::string> result = | |
| FindArgValueAfterPrefix("--edition=", args); | |
| auto expected = std::optional<std::string>{"2018"}; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, ExtractAllArgValueWithPrefix) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg=feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| target.config_values().rustflags().push_back("--cfg=feature=\"bar_enabled\""); | |
| target.config_values().rustflags().push_back("--target"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::vector<std::string> result = FindAllArgValuesAfterPrefix("--cfg=", args); | |
| std::vector<std::string> expected = {"feature=\"foo_enabled\"", | |
| "feature=\"bar_enabled\""}; | |
| EXPECT_EQ(expected, result); | |
| } | |
| TEST_F(RustProjectWriterHelper, FindAllArgValues) { | |
| TestWithScope setup; | |
| Target target(setup.settings(), Label(SourceDir("//foo/"), "bar")); | |
| target.set_output_type(Target::RUST_LIBRARY); | |
| target.visibility().SetPublic(); | |
| SourceFile lib("//foo/lib.rs"); | |
| target.sources().push_back(lib); | |
| target.source_types_used().Set(SourceFile::SOURCE_RS); | |
| target.rust_values().set_crate_root(lib); | |
| target.rust_values().crate_name() = "foo"; | |
| target.config_values().rustflags().push_back("--cfg"); | |
| target.config_values().rustflags().push_back("feature=\"foo_enabled\""); | |
| target.config_values().rustflags().push_back("--edition=2018"); | |
| target.config_values().rustflags().push_back("--cfg"); | |
| target.config_values().rustflags().push_back("feature=\"bar_enabled\""); | |
| target.config_values().rustflags().push_back("--target"); | |
| auto args = ExtractCompilerArgs(&target); | |
| std::vector<std::string> result = FindAllArgValues("--cfg", args); | |
| std::vector<std::string> expected = {"feature=\"foo_enabled\"", | |
| "feature=\"bar_enabled\""}; | |
| EXPECT_EQ(expected, result); | |
| } |