1 // Copyright 2021 The Dawn 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/dawn_node/binding/GPUShaderModule.h"
16 
17 #include <memory>
18 
19 #include "src/dawn_node/utils/Debug.h"
20 
21 namespace wgpu { namespace binding {
22 
23     ////////////////////////////////////////////////////////////////////////////////
24     // wgpu::bindings::GPUShaderModule
25     ////////////////////////////////////////////////////////////////////////////////
GPUShaderModule(wgpu::ShaderModule shader, std::shared_ptr<AsyncRunner> async)26     GPUShaderModule::GPUShaderModule(wgpu::ShaderModule shader, std::shared_ptr<AsyncRunner> async)
27         : shader_(std::move(shader)), async_(std::move(async)) {
28     }
29 
30     interop::Promise<interop::Interface<interop::GPUCompilationInfo>>
compilationInfo(Napi::Env env)31     GPUShaderModule::compilationInfo(Napi::Env env) {
32         struct GPUCompilationMessage : public interop::GPUCompilationMessage {
33             WGPUCompilationMessage message;
34 
35             GPUCompilationMessage(const WGPUCompilationMessage& m) : message(m) {
36             }
37             std::string getMessage(Napi::Env) override {
38                 return message.message;
39             }
40             interop::GPUCompilationMessageType getType(Napi::Env) override {
41                 switch (message.type) {
42                     case WGPUCompilationMessageType_Error:
43                         return interop::GPUCompilationMessageType::kError;
44                     case WGPUCompilationMessageType_Warning:
45                         return interop::GPUCompilationMessageType::kWarning;
46                     case WGPUCompilationMessageType_Info:
47                         return interop::GPUCompilationMessageType::kInfo;
48                     default:
49                         UNIMPLEMENTED();
50                 }
51             }
52             uint64_t getLineNum(Napi::Env) override {
53                 return message.lineNum;
54             }
55             uint64_t getLinePos(Napi::Env) override {
56                 return message.linePos;
57             }
58             uint64_t getOffset(Napi::Env) override {
59                 return message.offset;
60             }
61             uint64_t getLength(Napi::Env) override {
62                 return message.length;
63             }
64         };
65 
66         using Messages = std::vector<interop::Interface<interop::GPUCompilationMessage>>;
67 
68         struct GPUCompilationInfo : public interop::GPUCompilationInfo {
69             std::vector<Napi::ObjectReference> messages;
70 
71             GPUCompilationInfo(Napi::Env env, Messages msgs) {
72                 messages.reserve(msgs.size());
73                 for (auto& msg : msgs) {
74                     messages.emplace_back(Napi::Persistent(Napi::Object(env, msg)));
75                 }
76             }
77             Messages getMessages(Napi::Env) override {
78                 Messages out;
79                 out.reserve(messages.size());
80                 for (auto& msg : messages) {
81                     out.emplace_back(msg.Value());
82                 }
83                 return out;
84             }
85         };
86 
87         using Promise = interop::Promise<interop::Interface<interop::GPUCompilationInfo>>;
88 
89         struct Context {
90             Napi::Env env;
91             Promise promise;
92             AsyncTask task;
93         };
94         auto ctx = new Context{env, Promise(env, PROMISE_INFO), async_};
95         auto promise = ctx->promise;
96 
97         shader_.GetCompilationInfo(
98             [](WGPUCompilationInfoRequestStatus status, WGPUCompilationInfo const* compilationInfo,
99                void* userdata) {
100                 auto c = std::unique_ptr<Context>(static_cast<Context*>(userdata));
101 
102                 Messages messages(compilationInfo->messageCount);
103                 for (uint32_t i = 0; i < compilationInfo->messageCount; i++) {
104                     auto& msg = compilationInfo->messages[i];
105                     messages[i] =
106                         interop::GPUCompilationMessage::Create<GPUCompilationMessage>(c->env, msg);
107                 }
108 
109                 c->promise.Resolve(interop::GPUCompilationInfo::Create<GPUCompilationInfo>(
110                     c->env, c->env, std::move(messages)));
111             },
112             ctx);
113 
114         return promise;
115     }
116 
getLabel(Napi::Env)117     std::optional<std::string> GPUShaderModule::getLabel(Napi::Env) {
118         UNIMPLEMENTED();
119     }
120 
setLabel(Napi::Env, std::optional<std::string> value)121     void GPUShaderModule::setLabel(Napi::Env, std::optional<std::string> value) {
122         UNIMPLEMENTED();
123     }
124 
125 }}  // namespace wgpu::binding
126