[vulkan_loader] Add integration test
Route /pkg from a component as system-lib, and use that to test whether
vulkan-loader can load executable VMOs.
Change-Id: I7cfade3e989e56b0629b79db5ef47da1c1d9555d
Reviewed-on: https://fuchsia-review.googlesource.com/c/fuchsia/+/490017
Fuchsia-Auto-Submit: John Bauman <jbauman@google.com>
Reviewed-by: Bryan Henry <bryanhenry@google.com>
Reviewed-by: Craig Stout <cstout@google.com>
Commit-Queue: Auto-Submit <auto-submit@fuchsia-infra.iam.gserviceaccount.com>
diff --git a/src/graphics/BUILD.gn b/src/graphics/BUILD.gn
index 0b6a803..c2dc26e 100644
--- a/src/graphics/BUILD.gn
+++ b/src/graphics/BUILD.gn
@@ -12,6 +12,7 @@
group("tests") {
testonly = true
deps = [
+ "bin/vulkan_loader:tests",
"display:tests",
"drivers:tests",
"lib/compute:tests",
diff --git a/src/graphics/bin/vulkan_loader/BUILD.gn b/src/graphics/bin/vulkan_loader/BUILD.gn
index e5bc6c1..f3652b0 100644
--- a/src/graphics/bin/vulkan_loader/BUILD.gn
+++ b/src/graphics/bin/vulkan_loader/BUILD.gn
@@ -4,6 +4,11 @@
import("//src/sys/build/components.gni")
+group("tests") {
+ testonly = true
+ deps = [ ":vulkan_loader_tests" ]
+}
+
executable("bin") {
output_name = "vulkan_loader"
@@ -30,3 +35,65 @@
fuchsia_package("vulkan_loader") {
deps = [ ":vulkan_loader_cmp" ]
}
+
+executable("test_bin") {
+ testonly = true
+ output_name = "vulkan_loader_test"
+ sources = [ "test.cc" ]
+ deps = [
+ "//sdk/fidl/fuchsia.vulkan.loader",
+ "//sdk/lib/fdio",
+ "//src/lib/fxl",
+ "//src/lib/fxl/test:gtest_main",
+ "//third_party/googletest:gtest",
+ ]
+}
+
+executable("pkg-server-bin") {
+ testonly = true
+ output_name = "pkg-server"
+
+ sources = [ "pkg-server-main.cc" ]
+
+ deps = [
+ "//sdk/fidl/fuchsia.io",
+ "//sdk/lib/fdio",
+ "//sdk/lib/fidl/cpp",
+ "//sdk/lib/sys/cpp",
+ "//src/lib/fxl",
+ "//src/lib/storage/vfs/cpp",
+ "//zircon/system/ulib/async-loop:async-loop-cpp",
+ "//zircon/system/ulib/async-loop:async-loop-default",
+ ]
+}
+
+fuchsia_component("vulkan_loader_test_driver") {
+ testonly = true
+ manifest = "meta/vulkan_loader_test_driver.cml"
+ deps = [ ":test_bin" ]
+}
+
+fuchsia_component("vulkan_loader_test_lib_provider") {
+ testonly = true
+ manifest = "meta/vulkan_loader_test_lib_provider.cml"
+ deps = [ ":pkg-server-bin" ]
+}
+
+fuchsia_component("vulkan_loader_test") {
+ testonly = true
+ manifest = "meta/vulkan_loader_test.cml"
+}
+
+fuchsia_test_package("vulkan_loader_tests") {
+ test_components = [ ":vulkan_loader_test" ]
+ deps = [
+ ":vulkan_loader_cmp",
+ ":vulkan_loader_test_driver",
+ ":vulkan_loader_test_lib_provider",
+ ]
+ test_specs = {
+ log_settings = {
+ max_severity = "ERROR"
+ }
+ }
+}
diff --git a/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test.cml b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test.cml
new file mode 100644
index 0000000..f257270
--- /dev/null
+++ b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test.cml
@@ -0,0 +1,46 @@
+{
+ children: [
+ {
+ name: "test_driver",
+ url: "fuchsia-pkg://fuchsia.com/vulkan_loader_tests#meta/vulkan_loader_test_driver.cm",
+ },
+ {
+ name: "vulkan_loader",
+ url: "fuchsia-pkg://fuchsia.com/vulkan_loader_tests#meta/vulkan_loader.cm",
+ },
+ {
+ name: "test_lib_provider",
+ url: "fuchsia-pkg://fuchsia.com/vulkan_loader_tests#meta/vulkan_loader_test_lib_provider.cm",
+ },
+ ],
+ offer: [
+ {
+ protocol: [
+ "fuchsia.logger.Log",
+ "fuchsia.logger.LogSink",
+ ],
+ from: "parent",
+ to: [
+ "#test_driver",
+ "#test_lib_provider",
+ "#vulkan_loader",
+ ],
+ },
+ {
+ protocol: "fuchsia.vulkan.loader.Loader",
+ from: "#vulkan_loader",
+ to: [ "#test_driver" ],
+ },
+ {
+ directory: "system-lib",
+ from: "#test_lib_provider",
+ to: [ "#vulkan_loader" ],
+ },
+ ],
+ expose: [
+ {
+ protocol: "fuchsia.test.Suite",
+ from: "#test_driver",
+ },
+ ],
+}
diff --git a/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_driver.cml b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_driver.cml
new file mode 100644
index 0000000..0ba0cda
--- /dev/null
+++ b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_driver.cml
@@ -0,0 +1,12 @@
+{
+ include: [
+ "sdk/lib/diagnostics/syslog/client.shard.cml",
+ "src/sys/test_runners/gtest/default.shard.cml",
+ ],
+ program: {
+ binary: "bin/vulkan_loader_test",
+ },
+ use: [
+ { protocol: "fuchsia.vulkan.loader.Loader" },
+ ],
+}
diff --git a/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_lib_provider.cml b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_lib_provider.cml
new file mode 100644
index 0000000..e9c67bd
--- /dev/null
+++ b/src/graphics/bin/vulkan_loader/meta/vulkan_loader_test_lib_provider.cml
@@ -0,0 +1,25 @@
+{
+ include: [
+ "sdk/lib/diagnostics/syslog/client.shard.cml",
+ "sdk/lib/diagnostics/syslog/elf_stdio.shard.cml",
+ ],
+ program: {
+ binary: "bin/pkg-server",
+ },
+ capabilities: [
+ {
+ // Use /bin because we know that the pkg-server executable will always be there.
+ directory: "bin",
+ rights: [ "rx*" ],
+ path: "/pkg/bin",
+ },
+ ],
+ expose: [
+ {
+ directory: "bin",
+ from: "self",
+ as: "system-lib",
+ rights: [ "rx*" ],
+ },
+ ],
+}
diff --git a/src/graphics/bin/vulkan_loader/pkg-server-main.cc b/src/graphics/bin/vulkan_loader/pkg-server-main.cc
new file mode 100644
index 0000000..7cbe63e
--- /dev/null
+++ b/src/graphics/bin/vulkan_loader/pkg-server-main.cc
@@ -0,0 +1,52 @@
+// Copyright 2021 The Fuchsia 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 <fuchsia/io/cpp/fidl.h>
+#include <lib/async-loop/cpp/loop.h>
+#include <lib/async-loop/default.h>
+#include <lib/fdio/directory.h>
+#include <lib/fdio/io.h>
+#include <lib/sys/cpp/component_context.h>
+#include <lib/syslog/cpp/macros.h>
+#include <zircon/processargs.h>
+
+#include "src/lib/fxl/command_line.h"
+#include "src/lib/fxl/log_settings_command_line.h"
+#include "src/lib/storage/vfs/cpp/pseudo_dir.h"
+#include "src/lib/storage/vfs/cpp/remote_dir.h"
+#include "src/lib/storage/vfs/cpp/synchronous_vfs.h"
+#include "src/lib/storage/vfs/cpp/vfs.h"
+#include "src/lib/storage/vfs/cpp/vfs_types.h"
+
+// Serve /pkg as the outgoing directory.
+int main(int argc, const char* const* argv) {
+ async::Loop loop(&kAsyncLoopConfigAttachToCurrentThread);
+ fxl::SetLogSettingsFromCommandLine(fxl::CommandLineFromArgcArgv(argc, argv));
+ fidl::InterfaceHandle<fuchsia::io::Directory> pkg_dir;
+ zx_status_t status;
+ status = fdio_open("/pkg", fuchsia::io::OPEN_RIGHT_READABLE,
+ pkg_dir.NewRequest().TakeChannel().release());
+ if (status != ZX_OK) {
+ FX_PLOGST(FATAL, nullptr, status) << "Failed to open package";
+ return -1;
+ }
+
+ // Use fs:: instead of vfs:: because vfs doesn't support executable directories.
+ fs::SynchronousVfs vfs(loop.dispatcher());
+ auto root = fbl::MakeRefCounted<fs::PseudoDir>();
+ auto remote = fbl::MakeRefCounted<fs::RemoteDir>(
+ fidl::ClientEnd<fuchsia_io::Directory>(pkg_dir.TakeChannel()));
+ root->AddEntry("pkg", remote);
+ zx::channel dir_request = zx::channel(zx_take_startup_handle(PA_DIRECTORY_REQUEST));
+ status = vfs.Serve(root, fidl::ServerEnd<fuchsia_io::Node>(std::move(dir_request)),
+ fs::VnodeConnectionOptions::ReadExec());
+
+ if (status != ZX_OK) {
+ FX_PLOGST(FATAL, nullptr, status) << "Failed to serve outgoing.";
+ return -1;
+ }
+
+ loop.Run();
+ return 0;
+}
diff --git a/src/graphics/bin/vulkan_loader/test.cc b/src/graphics/bin/vulkan_loader/test.cc
new file mode 100644
index 0000000..3fbc69b
--- /dev/null
+++ b/src/graphics/bin/vulkan_loader/test.cc
@@ -0,0 +1,26 @@
+// Copyright 2021 The Fuchsia 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 <fuchsia/vulkan/loader/cpp/fidl.h>
+#include <lib/fdio/directory.h>
+#include <lib/zx/vmo.h>
+
+#include <gtest/gtest.h>
+
+TEST(VulkanLoader, SystemLoad) {
+ fuchsia::vulkan::loader::LoaderSyncPtr loader;
+ EXPECT_EQ(ZX_OK, fdio_service_connect("/svc/fuchsia.vulkan.loader.Loader",
+ loader.NewRequest().TakeChannel().release()));
+
+ zx::vmo vmo_out;
+ // The test instance reads from /pkg/bin, and this executable is guaranteed to be there.
+ EXPECT_EQ(ZX_OK, loader->Get("pkg-server", &vmo_out));
+ EXPECT_TRUE(vmo_out.is_valid());
+ zx_info_handle_basic_t handle_info;
+ EXPECT_EQ(ZX_OK, vmo_out.get_info(ZX_INFO_HANDLE_BASIC, &handle_info, sizeof(handle_info),
+ nullptr, nullptr));
+ EXPECT_TRUE(handle_info.rights & ZX_RIGHT_EXECUTE);
+ EXPECT_EQ(ZX_OK, loader->Get("not-present", &vmo_out));
+ EXPECT_FALSE(vmo_out.is_valid());
+}