diff --git a/generator/templates/dawn_wire/WireClient.cpp b/generator/templates/dawn_wire/WireClient.cpp index ba74c66099..ce708e4eee 100644 --- a/generator/templates/dawn_wire/WireClient.cpp +++ b/generator/templates/dawn_wire/WireClient.cpp @@ -349,7 +349,8 @@ namespace dawn_wire { obj->builderCallback.Call(DAWN_BUILDER_ERROR_STATUS_UNKNOWN, "Unknown"); - {{as_MethodSuffix(type.name, Name("destroy"))}}Cmd cmd; + DestroyObjectCmd cmd; + cmd.objectType = ObjectType::{{type.name.CamelCase()}}; cmd.objectId = obj->id; auto allocCmd = static_cast(obj->device->GetCmdSpace(sizeof(cmd))); diff --git a/generator/templates/dawn_wire/WireCmd.h b/generator/templates/dawn_wire/WireCmd.h index a0052b7961..28bc1ae5d8 100644 --- a/generator/templates/dawn_wire/WireCmd.h +++ b/generator/templates/dawn_wire/WireCmd.h @@ -53,16 +53,22 @@ namespace dawn_wire { {% endfor %} }; + enum class ObjectType : uint32_t { + {% for type in by_category["object"] %} + {{type.name.CamelCase()}}, + {% endfor %} + }; + //* Enum used as a prefix to each command on the wire format. enum class WireCmd : uint32_t { {% for type in by_category["object"] %} {% for method in type.methods %} {{as_MethodSuffix(type.name, method.name)}}, {% endfor %} - {{as_MethodSuffix(type.name, Name("destroy"))}}, {% endfor %} BufferMapAsync, BufferUpdateMappedDataCmd, + DestroyObject, }; {% for type in by_category["object"] %} @@ -110,14 +116,6 @@ namespace dawn_wire { {% endfor %} }; {% endfor %} - - //* The command structure used when sending that an ID is destroyed. - {% set Suffix = as_MethodSuffix(type.name, Name("destroy")) %} - struct {{Suffix}}Cmd { - WireCmd commandId = WireCmd::{{Suffix}}; - ObjectId objectId; - }; - {% endfor %} //* Enum used as a prefix to each command on the return wire format. diff --git a/generator/templates/dawn_wire/WireServer.cpp b/generator/templates/dawn_wire/WireServer.cpp index 99d91d6a30..9ea671ac1e 100644 --- a/generator/templates/dawn_wire/WireServer.cpp +++ b/generator/templates/dawn_wire/WireServer.cpp @@ -406,10 +406,6 @@ namespace dawn_wire { break; {% endif %} {% endfor %} - {% set Suffix = as_MethodSuffix(type.name, Name("destroy")) %} - case WireCmd::{{Suffix}}: - success = Handle{{Suffix}}(&commands, &size); - break; {% endfor %} case WireCmd::BufferMapAsync: success = HandleBufferMapAsync(&commands, &size); @@ -417,7 +413,9 @@ namespace dawn_wire { case WireCmd::BufferUpdateMappedDataCmd: success = HandleBufferUpdateMappedData(&commands, &size); break; - + case WireCmd::DestroyObject: + success = HandleDestroyObject(&commands, &size); + break; default: success = false; } @@ -632,45 +630,6 @@ namespace dawn_wire { } {% endif %} {% endfor %} - - //* Handlers for the destruction of objects: clients do the tracking of the - //* reference / release and only send destroy on refcount = 0. - {% set Suffix = as_MethodSuffix(type.name, Name("destroy")) %} - bool Handle{{Suffix}}(const char** commands, size_t* size) { - - //* Freeing the device has to be done out of band. - {% if type.name.canonical_case() == "device" %} - return false; - {% endif %} - - const auto* cmd = GetCommand<{{Suffix}}Cmd>(commands, size); - if (cmd == nullptr) { - return false; - } - - ObjectId objectId = cmd->objectId; - - //* ID 0 are reserved for nullptr and cannot be destroyed. - if (objectId == 0) { - return false; - } - - auto* data = mKnown{{type.name.CamelCase()}}.Get(objectId); - if (data == nullptr) { - return false; - } - - {% if type.name.CamelCase() in reverse_lookup_object_types %} - m{{type.name.CamelCase()}}IdTable.Remove(data->handle); - {% endif %} - - if (data->handle != nullptr) { - mProcs.{{as_varName(type.name, Name("release"))}}(data->handle); - } - - mKnown{{type.name.CamelCase()}}.Free(objectId); - return true; - } {% endfor %} bool HandleBufferMapAsync(const char** commands, size_t* size) { @@ -755,6 +714,48 @@ namespace dawn_wire { return true; } + + bool HandleDestroyObject(const char** commands, size_t* size) { + const auto* cmd = GetCommand(commands, size); + if (cmd == nullptr) { + return false; + } + + ObjectId objectId = cmd->objectId; + //* ID 0 are reserved for nullptr and cannot be destroyed. + if (objectId == 0) { + return false; + } + + switch (cmd->objectType) { + {% for type in by_category["object"] %} + {% set ObjectType = type.name.CamelCase() %} + case ObjectType::{{ObjectType}}: { + {% if ObjectType == "Device" %} + //* Freeing the device has to be done out of band. + return false; + {% else %} + auto* data = mKnown{{type.name.CamelCase()}}.Get(objectId); + if (data == nullptr) { + return false; + } + {% if type.name.CamelCase() in reverse_lookup_object_types %} + m{{type.name.CamelCase()}}IdTable.Remove(data->handle); + {% endif %} + + if (data->handle != nullptr) { + mProcs.{{as_varName(type.name, Name("release"))}}(data->handle); + } + + mKnown{{type.name.CamelCase()}}.Free(objectId); + return true; + {% endif %} + } + {% endfor %} + default: + UNREACHABLE(); + } + } }; void ForwardDeviceErrorToServer(const char* message, dawnCallbackUserdata userdata) { diff --git a/src/dawn_wire/WireCmd.h b/src/dawn_wire/WireCmd.h index 5d6c37113e..3dfe6b9ff1 100644 --- a/src/dawn_wire/WireCmd.h +++ b/src/dawn_wire/WireCmd.h @@ -71,6 +71,13 @@ namespace dawn_wire { uint32_t dataLength; }; + struct DestroyObjectCmd { + WireCmd commandId = WireCmd::DestroyObject; + + ObjectType objectType; + ObjectId objectId; + }; + } // namespace dawn_wire #endif // DAWNWIRE_WIRECMD_H_