From b02061a3d2901037e24691dbb7f4a5543f5c990e Mon Sep 17 00:00:00 2001 From: Christian Blichmann Date: Tue, 9 Jun 2020 12:24:30 +0200 Subject: [PATCH] Add scaffolding and first test for Clang-based generator - Fix `GetIncludeGuard()` to always uppercase --- .../tools/clang_generator/CMakeLists.txt | 15 +++++ .../tools/clang_generator/emitter.cc | 14 +++-- sandboxed_api/tools/clang_generator/emitter.h | 2 +- .../tools/clang_generator/emitter_test.cc | 55 +++++++++++++++++++ 4 files changed, 79 insertions(+), 7 deletions(-) create mode 100644 sandboxed_api/tools/clang_generator/emitter_test.cc diff --git a/sandboxed_api/tools/clang_generator/CMakeLists.txt b/sandboxed_api/tools/clang_generator/CMakeLists.txt index f0e59a2..d6bbc2a 100644 --- a/sandboxed_api/tools/clang_generator/CMakeLists.txt +++ b/sandboxed_api/tools/clang_generator/CMakeLists.txt @@ -60,3 +60,18 @@ target_link_libraries(sapi_generator_tool PRIVATE sapi::generator ) +if(SAPI_ENABLE_TESTS) + add_executable(sapi_generator_test + emitter_test.cc + ) + target_link_libraries(sapi_generator_test PRIVATE + absl::memory + benchmark + sapi::sapi + sapi::generator + sapi::status + sapi::status_matchers + sapi::test_main + ) + gtest_discover_tests(sapi_generator_test) +endif() diff --git a/sandboxed_api/tools/clang_generator/emitter.cc b/sandboxed_api/tools/clang_generator/emitter.cc index 035a744..0a8157f 100644 --- a/sandboxed_api/tools/clang_generator/emitter.cc +++ b/sandboxed_api/tools/clang_generator/emitter.cc @@ -46,9 +46,9 @@ constexpr absl::string_view kHeaderProlog = #include "absl/base/macros.h" #include "absl/status/status.h" #include "sandboxed_api/sandbox.h" -#include "sandboxed_api/vars.h" #include "sandboxed_api/util/status_macros.h" #include "sandboxed_api/util/statusor.h" +#include "sandboxed_api/vars.h" )"; constexpr absl::string_view kHeaderEpilog = @@ -110,15 +110,17 @@ std::string GetIncludeGuard(absl::string_view filename) { return absl::StrCat( // Copybara will transform the string. This is intentional. "SANDBOXED_API_GENERATED_HEADER_", - absl::Hex(absl::Uniform(*bit_gen), absl::kZeroPad16), "_"); + absl::AsciiStrToUpper(absl::StrCat( + absl::Hex(absl::Uniform(*bit_gen), absl::kZeroPad16))), + "_"); } - constexpr absl::string_view kUnderscorePrefix = "SAPI"; + constexpr absl::string_view kUnderscorePrefix = "SAPI_"; std::string guard; guard.reserve(filename.size() + kUnderscorePrefix.size() + 1); for (auto c : filename) { if (absl::ascii_isalpha(c)) { - guard += c; + guard += absl::ascii_toupper(c); continue; } if (guard.empty()) { @@ -234,8 +236,8 @@ sapi::StatusOr EmitFunction(const clang::FunctionDecl* decl) { ");\n"); } } - absl::StrAppend(&out, "\nSAPI_RETURN_IF_ERROR(sandbox_->Call(\"", function_name, - "\", &v_ret_"); + absl::StrAppend(&out, "\nSAPI_RETURN_IF_ERROR(sandbox_->Call(\"", + function_name, "\", &v_ret_"); for (const auto& [qual, name] : params) { absl::StrAppend(&out, ", ", IsPointerOrReference(qual) ? "" : "&v_", name); } diff --git a/sandboxed_api/tools/clang_generator/emitter.h b/sandboxed_api/tools/clang_generator/emitter.h index c9a267c..42ba92d 100644 --- a/sandboxed_api/tools/clang_generator/emitter.h +++ b/sandboxed_api/tools/clang_generator/emitter.h @@ -28,7 +28,7 @@ namespace sapi { // Constructs an include guard name for the given filename. The name is of the -// same for as the include guards in this project. +// same form as the include guards in this project. // For example, // sandboxed_api/examples/zlib/zlib-sapi.sapi.h // will be mapped to diff --git a/sandboxed_api/tools/clang_generator/emitter_test.cc b/sandboxed_api/tools/clang_generator/emitter_test.cc new file mode 100644 index 0000000..fd523b5 --- /dev/null +++ b/sandboxed_api/tools/clang_generator/emitter_test.cc @@ -0,0 +1,55 @@ +// Copyright 2020 Google LLC +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include "sandboxed_api/tools/clang_generator/emitter.h" + +#include "absl/strings/string_view.h" +#include "gtest/gtest.h" +#include "gmock/gmock.h" +#include "sandboxed_api/util/status_matchers.h" + +namespace sapi { +namespace { + +using ::testing::MatchesRegex; +using ::testing::StrEq; + +TEST(IncludeGuard, CreatesRandomizedGuardForEmptyFilename) { + // Copybara will transform the string. This is intentional. + constexpr absl::string_view kGeneratedHeaderPrefix = + "SANDBOXED_API_GENERATED_HEADER_"; + + const std::string include_guard = GetIncludeGuard(""); + EXPECT_THAT(include_guard, MatchesRegex(absl::StrCat(kGeneratedHeaderPrefix, + R"([0-9A-F]+_)"))); +} + +TEST(IncludeGuard, BasicFunctionality) { + EXPECT_THAT(GetIncludeGuard("boost/graph/compressed_sparse_row_graph.hpp"), + StrEq("BOOST_GRAPH_COMPRESSED_SPARSE_ROW_GRAPH_HPP_")); + + // "SAPI_" prefix is there to avoid generating guards starting with "_" + EXPECT_THAT(GetIncludeGuard("/usr/include/unistd.h"), + StrEq("SAPI_USR_INCLUDE_UNISTD_H_")); +} + +TEST(IncludeGuard, AvoidReservedIdentifiers) { + EXPECT_THAT(GetIncludeGuard("9p.h"), StrEq("SAPI_9P_H_")); + EXPECT_THAT(GetIncludeGuard("double__under.h"), StrEq("DOUBLE_UNDER_H_")); + EXPECT_THAT(GetIncludeGuard("_single.h"), StrEq("SAPI_SINGLE_H_")); + EXPECT_THAT(GetIncludeGuard("__double.h"), StrEq("SAPI_DOUBLE_H_")); +} + +} // namespace +} // namespace sapi