// Copyright 2019 The Dawn Authors // // 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 "dawn/mock_webgpu.h" #include "gtest/gtest.h" #include // Definition of a "Lambda predicate matcher" for GMock to allow checking deep structures // are passed correctly by the wire. // Helper templates to extract the argument type of a lambda. template struct MatcherMethodArgument; template struct MatcherMethodArgument { using Type = Arg; }; template using MatcherLambdaArgument = typename MatcherMethodArgument::Type; // The matcher itself, unfortunately it isn't able to return detailed information like other // matchers do. template class LambdaMatcherImpl : public testing::MatcherInterface { public: explicit LambdaMatcherImpl(Lambda lambda) : mLambda(lambda) { } void DescribeTo(std::ostream* os) const override { *os << "with a custom matcher"; } bool MatchAndExplain(Arg value, testing::MatchResultListener* listener) const override { if (!mLambda(value)) { *listener << "which doesn't satisfy the custom predicate"; return false; } return true; } private: Lambda mLambda; }; // Use the MatchesLambda as follows: // // EXPECT_CALL(foo, Bar(MatchesLambda([](ArgType arg) -> bool { // return CheckPredicateOnArg(arg); // }))); template inline testing::Matcher> MatchesLambda(Lambda lambda) { return MakeMatcher(new LambdaMatcherImpl>(lambda)); } class StringMessageMatcher : public testing::MatcherInterface { public: explicit StringMessageMatcher() { } bool MatchAndExplain(const char* message, testing::MatchResultListener* listener) const override { if (message == nullptr) { *listener << "missing error message"; return false; } if (std::strlen(message) <= 1) { *listener << "message is truncated"; return false; } return true; } void DescribeTo(std::ostream* os) const override { *os << "valid error message"; } void DescribeNegationTo(std::ostream* os) const override { *os << "invalid error message"; } }; inline testing::Matcher ValidStringMessage() { return MakeMatcher(new StringMessageMatcher()); } namespace dawn_wire { class WireClient; class WireServer; namespace client { class MemoryTransferService; } // namespace client namespace server { class MemoryTransferService; } // namespace server } // namespace dawn_wire namespace utils { class TerribleCommandBuffer; } class WireTest : public testing::Test { protected: WireTest(); ~WireTest() override; void SetUp() override; void TearDown() override; void FlushClient(bool success = true); void FlushServer(bool success = true); void DefaultApiDeviceWasReleased(); testing::StrictMock api; WGPUDevice apiDevice; WGPUQueue apiQueue; WGPUDevice device; WGPUQueue queue; dawn_wire::WireServer* GetWireServer(); dawn_wire::WireClient* GetWireClient(); void DeleteServer(); void DeleteClient(); private: void SetupIgnoredCallExpectations(); virtual dawn_wire::client::MemoryTransferService* GetClientMemoryTransferService(); virtual dawn_wire::server::MemoryTransferService* GetServerMemoryTransferService(); std::unique_ptr mWireServer; std::unique_ptr mWireClient; std::unique_ptr mS2cBuf; std::unique_ptr mC2sBuf; };