1 // Copyright 2020 The Amber Authors.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "src/debug.h"
16
17 #include <functional>
18 #include <memory>
19 #include <string>
20 #include <vector>
21
22 #include "src/make_unique.h"
23
24 namespace amber {
25 namespace debug {
26
27 namespace {
28
29 class ScriptImpl : public Script {
30 public:
Run(Events * e) const31 void Run(Events* e) const override {
32 for (auto f : sequence_) {
33 f(e);
34 }
35 }
36
BreakOnComputeGlobalInvocation(uint32_t x,uint32_t y,uint32_t z,const std::shared_ptr<const ThreadScript> & thread)37 void BreakOnComputeGlobalInvocation(
38 uint32_t x,
39 uint32_t y,
40 uint32_t z,
41 const std::shared_ptr<const ThreadScript>& thread) override {
42 sequence_.emplace_back([=](Events* events) {
43 events->BreakOnComputeGlobalInvocation(x, y, z, thread);
44 });
45 }
46
BreakOnVertexIndex(uint32_t index,const std::shared_ptr<const ThreadScript> & thread)47 void BreakOnVertexIndex(
48 uint32_t index,
49 const std::shared_ptr<const ThreadScript>& thread) override {
50 sequence_.emplace_back(
51 [=](Events* events) { events->BreakOnVertexIndex(index, thread); });
52 }
53
BreakOnFragmentWindowSpacePosition(uint32_t x,uint32_t y,const std::shared_ptr<const ThreadScript> & thread)54 void BreakOnFragmentWindowSpacePosition(
55 uint32_t x,
56 uint32_t y,
57 const std::shared_ptr<const ThreadScript>& thread) override {
58 sequence_.emplace_back([=](Events* events) {
59 events->BreakOnFragmentWindowSpacePosition(x, y, thread);
60 });
61 }
62
63 private:
64 using Event = std::function<void(Events*)>;
65 std::vector<Event> sequence_;
66 };
67
68 class ThreadScriptImpl : public ThreadScript {
69 public:
Run(Thread * thread) const70 void Run(Thread* thread) const override {
71 for (auto f : sequence_) {
72 f(thread);
73 }
74 }
75
76 // Thread compliance
StepOver()77 void StepOver() override {
78 sequence_.emplace_back([](Thread* t) { t->StepOver(); });
79 }
80
StepIn()81 void StepIn() override {
82 sequence_.emplace_back([](Thread* t) { t->StepIn(); });
83 }
84
StepOut()85 void StepOut() override {
86 sequence_.emplace_back([](Thread* t) { t->StepOut(); });
87 }
88
Continue()89 void Continue() override {
90 sequence_.emplace_back([](Thread* t) { t->Continue(); });
91 }
92
ExpectLocation(const Location & location,const std::string & line)93 void ExpectLocation(const Location& location,
94 const std::string& line) override {
95 sequence_.emplace_back(
96 [=](Thread* t) { t->ExpectLocation(location, line); });
97 }
98
ExpectCallstack(const std::vector<StackFrame> & callstack)99 void ExpectCallstack(const std::vector<StackFrame>& callstack) override {
100 sequence_.emplace_back([=](Thread* t) { t->ExpectCallstack(callstack); });
101 }
102
ExpectLocal(const std::string & name,int64_t value)103 void ExpectLocal(const std::string& name, int64_t value) override {
104 sequence_.emplace_back([=](Thread* t) { t->ExpectLocal(name, value); });
105 }
106
ExpectLocal(const std::string & name,double value)107 void ExpectLocal(const std::string& name, double value) override {
108 sequence_.emplace_back([=](Thread* t) { t->ExpectLocal(name, value); });
109 }
110
ExpectLocal(const std::string & name,const std::string & value)111 void ExpectLocal(const std::string& name, const std::string& value) override {
112 sequence_.emplace_back([=](Thread* t) { t->ExpectLocal(name, value); });
113 }
114
115 private:
116 using Event = std::function<void(Thread*)>;
117 std::vector<Event> sequence_;
118 };
119
120 } // namespace
121
122 Thread::~Thread() = default;
123 Events::~Events() = default;
124 ThreadScript::~ThreadScript() = default;
125 Script::~Script() = default;
126
Create()127 std::shared_ptr<ThreadScript> ThreadScript::Create() {
128 return std::make_shared<ThreadScriptImpl>();
129 }
130
Create()131 std::unique_ptr<Script> Script::Create() {
132 return MakeUnique<ScriptImpl>();
133 }
134
135 } // namespace debug
136 } // namespace amber
137