Add new target for spirv-lint (#4446)

This PR adds a new executable spirv-lint with a simple "Hello, world!"
program, along with its associated library and a dummy unit test.

For now, only adds to CMake and Bazel; other build systems will be added
in a future PR.

Issue: #3196
This commit is contained in:
dong-ja 2021-08-06 13:03:59 -05:00 committed by GitHub
parent 3510a14cfc
commit 706dc27a62
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 290 additions and 1 deletions

View File

@ -14,6 +14,7 @@ load(
"generate_vendor_tables",
"generate_vendor_tables_local",
"link_test",
"lint_test",
"opt_test",
"reduce_test",
"util_test",
@ -233,6 +234,19 @@ cc_library(
],
)
cc_library(
name = "spirv_tools_lint",
srcs = glob(["source/lint/*.cpp"]),
hdrs = ["include/spirv-tools/linter.hpp"],
copts = COMMON_COPTS,
linkstatic = 1,
visibility = ["//visibility:public"],
deps = [
":spirv_tools",
":spirv_tools_opt",
],
)
cc_library(
name = "tools_util",
srcs = glob(["tools/util/*.cpp"]),
@ -330,6 +344,20 @@ cc_binary(
],
)
cc_binary(
name = "spirv-lint",
srcs = [
"tools/lint/lint.cpp",
],
copts = COMMON_COPTS,
visibility = ["//visibility:public"],
deps = [
":spirv_tools",
":spirv_tools_lint",
":tools_util",
],
)
cc_binary(
name = "spirv-cfg",
srcs = [
@ -473,6 +501,13 @@ base_test(
["test/link/*.cpp"],
)]
[lint_test(
name = f[10:-4], # strip test/lint/, .cpp
srcs = [f],
) for f in glob(
["test/lint/*.cpp"],
)]
[opt_test(
name = f[9:-4], # strip test/opt/, .cpp
srcs = [f],

View File

@ -224,6 +224,23 @@ def base_test(name, srcs, deps = []):
] + deps,
)
def lint_test(name, srcs, deps = []):
if name[-5:] != "_test":
name = name + "_test"
native.cc_test(
name = "lint_" + name,
srcs = srcs,
compatible_with = [],
copts = TEST_COPTS,
size = "large",
deps = [
":spirv_tools_lint",
"@com_google_googletest//:gtest_main",
"@com_google_googletest//:gtest",
"@com_google_effcee//:effcee",
] + deps,
)
def link_test(name, srcs, deps = []):
if name[-5:] != "_test":
name = name + "_test"

View File

@ -0,0 +1,48 @@
// Copyright (c) 2021 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.
#ifndef INCLUDE_SPIRV_TOOLS_LINTER_HPP_
#define INCLUDE_SPIRV_TOOLS_LINTER_HPP_
#include "libspirv.hpp"
namespace spvtools {
// C++ interface for SPIR-V linting functionalities. It wraps the context
// (including target environment and the corresponding SPIR-V grammar) and
// provides a method for linting.
//
// Instances of this class provides basic thread-safety guarantee.
class Linter {
public:
explicit Linter(spv_target_env env);
~Linter();
// Sets the message consumer to the given |consumer|. The |consumer| will be
// invoked once for each message communicated from the library.
void SetMessageConsumer(MessageConsumer consumer);
// Returns a reference to the registered message consumer.
const MessageConsumer& consumer() const;
bool Run(const uint32_t* binary, size_t binary_size);
private:
struct Impl;
std::unique_ptr<Impl> impl_;
};
} // namespace spvtools
#endif // INCLUDE_SPIRV_TOOLS_LINTER_HPP_

View File

@ -219,6 +219,7 @@ add_subdirectory(opt)
add_subdirectory(reduce)
add_subdirectory(fuzz)
add_subdirectory(link)
add_subdirectory(lint)
set(SPIRV_SOURCES
${spirv-tools_SOURCE_DIR}/include/spirv-tools/libspirv.h

View File

@ -0,0 +1,58 @@
# Copyright (c) 2021 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.
set(SPIRV_TOOLS_LINT_SOURCES
linter.cpp
)
if(MSVC AND (NOT ("${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")))
# Enable parallel builds across four cores for this lib.
add_definitions(/MP4)
endif()
spvtools_pch(SPIRV_TOOLS_LINT_SOURCES pch_source_lint)
add_library(SPIRV-Tools-lint ${SPIRV_TOOLS_LIBRARY_TYPE} ${SPIRV_TOOLS_LINT_SOURCES})
spvtools_default_compile_options(SPIRV-Tools-lint)
target_include_directories(SPIRV-Tools-lint
PUBLIC
$<BUILD_INTERFACE:${spirv-tools_SOURCE_DIR}/include>
$<BUILD_INTERFACE:${SPIRV_HEADER_INCLUDE_DIR}>
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
PRIVATE ${spirv-tools_BINARY_DIR}
)
# We need the assembling and disassembling functionalities in the main library.
target_link_libraries(SPIRV-Tools-lint
PUBLIC ${SPIRV_TOOLS_FULL_VISIBILITY})
# We need the internals of spirv-opt.
target_link_libraries(SPIRV-Tools-lint
PUBLIC SPIRV-Tools-opt)
set_property(TARGET SPIRV-Tools-lint PROPERTY FOLDER "SPIRV-Tools libraries")
spvtools_check_symbol_exports(SPIRV-Tools-lint)
if(ENABLE_SPIRV_TOOLS_INSTALL)
install(TARGETS SPIRV-Tools-lint EXPORT SPIRV-Tools-lintTargets
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR})
export(EXPORT SPIRV-Tools-lintTargets FILE SPIRV-Tools-lintTargets.cmake)
spvtools_config_package_dir(SPIRV-Tools-lint PACKAGE_DIR)
install(EXPORT SPIRV-Tools-lintTargets FILE SPIRV-Tools-lintTargets.cmake
DESTINATION ${PACKAGE_DIR})
spvtools_generate_config_file(SPIRV-Tools-lint)
install(FILES ${CMAKE_BINARY_DIR}/SPIRV-Tools-lintConfig.cmake DESTINATION ${PACKAGE_DIR})
endif(ENABLE_SPIRV_TOOLS_INSTALL)

51
source/lint/linter.cpp Normal file
View File

@ -0,0 +1,51 @@
// Copyright (c) 2021 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 "spirv-tools/linter.hpp"
namespace spvtools {
struct Linter::Impl {
explicit Impl(spv_target_env env) : target_env(env) {
message_consumer = [](spv_message_level_t /*level*/, const char* /*source*/,
const spv_position_t& /*position*/,
const char* /*message*/) {};
}
spv_target_env target_env; // Target environment.
MessageConsumer message_consumer; // Message consumer.
};
Linter::Linter(spv_target_env env) : impl_(new Impl(env)) {}
Linter::~Linter() {}
void Linter::SetMessageConsumer(MessageConsumer consumer) {
impl_->message_consumer = consumer;
}
const MessageConsumer& Linter::consumer() const {
return impl_->message_consumer;
}
bool Linter::Run(const uint32_t* binary, size_t binary_size) {
(void)binary;
(void)binary_size;
consumer()(SPV_MSG_INFO, "", {0, 0, 0}, "Hello, world!");
return true;
}
} // namespace spvtools

View File

@ -186,6 +186,7 @@ endif()
add_subdirectory(link)
add_subdirectory(lint)
add_subdirectory(opt)
add_subdirectory(reduce)
add_subdirectory(fuzz)

18
test/lint/CMakeLists.txt Normal file
View File

@ -0,0 +1,18 @@
# Copyright (c) 2021 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.
add_spvtools_unittest(TARGET lint
SRCS placeholder_test.cpp
LIBS SPIRV-Tools-lint SPIRV-Tools-opt
)

View File

@ -0,0 +1,25 @@
// Copyright (c) 2021 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 "gtest/gtest.h"
namespace spvtools {
namespace lint {
namespace {
TEST(PlaceholderTest, PlaceholderTest) { ASSERT_TRUE(true); }
} // namespace
} // namespace lint
} // namespace spvtools

View File

@ -48,6 +48,7 @@ if (NOT ${SPIRV_SKIP_EXECUTABLES})
add_spvtools_tool(TARGET spirv-reduce SRCS reduce/reduce.cpp util/cli_consumer.cpp LIBS SPIRV-Tools-reduce ${SPIRV_TOOLS_FULL_VISIBILITY})
endif()
add_spvtools_tool(TARGET spirv-link SRCS link/linker.cpp LIBS SPIRV-Tools-link ${SPIRV_TOOLS_FULL_VISIBILITY})
add_spvtools_tool(TARGET spirv-lint SRCS lint/lint.cpp util/cli_consumer.cpp LIBS SPIRV-Tools-lint SPIRV-Tools-opt ${SPIRV_TOOLS_FULL_VISIBILITY})
add_spvtools_tool(TARGET spirv-cfg
SRCS cfg/cfg.cpp
cfg/bin_to_dot.h
@ -56,7 +57,7 @@ if (NOT ${SPIRV_SKIP_EXECUTABLES})
target_include_directories(spirv-cfg PRIVATE ${spirv-tools_SOURCE_DIR}
${SPIRV_HEADER_INCLUDE_DIR})
set(SPIRV_INSTALL_TARGETS spirv-as spirv-dis spirv-val spirv-opt
spirv-cfg spirv-link)
spirv-cfg spirv-link spirv-lint)
if(NOT DEFINED IOS_PLATFORM)
set(SPIRV_INSTALL_TARGETS ${SPIRV_INSTALL_TARGETS} spirv-reduce)
endif()

34
tools/lint/lint.cpp Normal file
View File

@ -0,0 +1,34 @@
// Copyright (c) 2021 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 <iostream>
#include "spirv-tools/linter.hpp"
#include "tools/util/cli_consumer.h"
const auto kDefaultEnvironment = SPV_ENV_UNIVERSAL_1_5;
int main(int argc, const char** argv) {
(void)argc;
(void)argv;
spv_target_env target_env = kDefaultEnvironment;
spvtools::Linter linter(target_env);
linter.SetMessageConsumer(spvtools::utils::CLIMessageConsumer);
bool ok = linter.Run(nullptr, 0);
return ok ? 0 : 1;
}