[wire] Update wire to remove remaining spanification remnants. - Removes the remaining support for blocklisting spanification in the wire after updating the remaining paths that required fixed-extent Spans now that they are available. - There are still some vestiges of the spanification notably in WireCmd.cpp where because the Cmds are using C structs we cannot spanify them entirely yet because serializing and deserialization of the raw C structs still require directly reading/writing to the pointers. - This will be addressed in a follow up where I am going to try to generated a Dawn level version of the wgpu_structs_autogen.h file that doesn't convert the C types to implementation specific types, but does spanify the structs and relevant members. Implementations can then provide an additional namespace specific override of the structs that further refine the types to the implementations, specifying ToAPI and FromAPI helpers in a respective dawn_platform.h generated file. Bug: 526537254 Change-Id: If461c05fd8dd9c1433f796b8a25d1248f4686291 Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/330035 Reviewed-by: Corentin Wallez <cwallez@chromium.org> Commit-Queue: Loko Kung <lokokung@google.com>
diff --git a/generator/templates/dawn/wire/WireCmd.cpp b/generator/templates/dawn/wire/WireCmd.cpp index 3269a52..043b0f0 100644 --- a/generator/templates/dawn/wire/WireCmd.cpp +++ b/generator/templates/dawn/wire/WireCmd.cpp
@@ -46,10 +46,10 @@ //* Helper macros so that the main [de]serialization functions can be written in a generic manner. //* Outputs an rvalue that's the number of elements a pointer member points to. -{%- macro member_length(member, record_accessor, spanify=False) -%} +{%- macro member_length(member, record_accessor, is_cmd=False) -%} {%- if member.length == "constant" -%} {{member.constant_length}}u - {%- elif spanify -%} + {%- elif is_cmd -%} {{record_accessor}}{{as_varName(member.name)}}.size() {%- else -%} {{record_accessor}}{{as_varName(member.length.name)}} @@ -134,7 +134,6 @@ {%- set Return = "Return" if is_return_command else "" -%} {%- set Cmd = "Cmd" if is_cmd else "" -%} {%- set RecordName = Return + name + Cmd -%} - {%- set spanify = is_cmd and RecordName not in cmd_spanification_blocklist -%} {%- set Inherits = " : CmdHeader" if is_cmd else "" %} {%- set TransferStructName = Return + name + "Transfer" -%} @@ -232,11 +231,17 @@ //* Normal handling for pointer members and structs. {% if member.annotation != "value" %} {% if member.type.category != "object" and member.optional %} - if (record.{{as_varName(member.name)}} != nullptr) + {% if is_cmd and member.length and member.length != "constant" %} + if (!record.{{as_varName(member.name)}}.empty()) + {% elif is_cmd and member.length == "constant" and member.constant_length != 1 %} + if (record.{{as_varName(member.name)}}.data() != nullptr) + {% else %} + if (record.{{as_varName(member.name)}} != nullptr) + {% endif %} {% endif %} { {% do assert(member.annotation != "const*const*", "const*const* not valid here") %} - auto memberLength = {{member_length(member, "record.", spanify)}}; + auto memberLength = {{member_length(member, "record.", is_cmd)}}; auto size = WireAlignSizeofN<{{member_transfer_type(member.type)}}>(checked_cast<size_t>(memberLength)); DAWN_ASSERT(size); result += *size; @@ -333,8 +338,10 @@ //* Allocate space and write the non-value arguments in it. {% do assert(member.annotation != "const*const*") %} {% if member.type.category != "object" and member.optional %} - {% if spanify and member.length and member.length != "constant" %} + {% if is_cmd and member.length and member.length != "constant" %} bool has_{{memberName}} = !record.{{memberName}}.empty(); + {% elif is_cmd and member.length == "constant" and member.constant_length != 1 %} + bool has_{{memberName}} = record.{{memberName}}.data() != nullptr; {% else %} bool has_{{memberName}} = record.{{memberName}} != nullptr; {% endif %} @@ -343,7 +350,7 @@ {% else %} { {% endif %} - auto memberLength = {{member_length(member, "record.", spanify)}}; + auto memberLength = {{member_length(member, "record.", is_cmd)}}; {% if member.length != "constant" %} {{serialize_member(member.length.type, false, "memberLength", "transfer->" + as_varName(member.length.name))}} {% endif %} @@ -357,9 +364,7 @@ } WIRE_TRY(buffer->NextN(checked_cast<size_t>(memberLength), &memberBuffer)); - //* TODO(https://crbug.com/526537254): Remove this branch once all the commands have been spanified. - {% if spanify and member.length and member.length != "constant" %} - {{serialize_member(member.length.type, false, "memberLength", "transfer->" + as_varName(member.length.name))}} + {% if is_cmd and member.length and member.constant_length != 1 %} {% if member.type.is_wire_transparent %} if (memberLength != 0) { SpanAsWritableBytes(memberBuffer).CopyFrom(SpanAsBytes(record.{{memberName}})); @@ -473,7 +478,7 @@ {% set memberName = as_varName(member.name) %} //* Value types are directly in the transfer record, objects being replaced with their IDs. {% if member.annotation == "value" %} - {% if spanify and member.is_length %} + {% if is_cmd and member.is_length %} //* Skipped deserializing length {{ memberName }} as it is included in the span. {% continue %} {% endif %} @@ -491,7 +496,7 @@ //* uninitialized pointer. {% do assert(member.length == "constant") %} bool has_{{memberName}} = transfer->has_{{memberName}}; - {% if spanify and member.length and member.length != "constant" %} + {% if is_cmd and member.length and member.constant_length != 1 %} record->{{memberName}} = {}; {% else %} record->{{memberName}} = nullptr; @@ -507,8 +512,7 @@ Span<const volatile {{member_transfer_type(member.type)}}> memberBuffer; WIRE_TRY(deserializeBuffer->ReadN(checked_cast<size_t>(memberLength), &memberBuffer)); - //* TODO(https://crbug.com/526537254): Remove this branch once all the commands have been spanified. - {% if spanify and member.length and member.length != "constant" %} + {% if is_cmd and member.length and member.constant_length != 1 %} //* For data-only members (e.g. "data" in WriteBuffer and WriteTexture), they are //* not security sensitive so we can directly refer the data inside the transfer //* buffer in dawn_native. For other members, as prevention of TOCTOU attacks is an @@ -518,13 +522,18 @@ {% do assert(member.annotation == "const*") %} record->{{memberName}} = memberBuffer; {% else %} - Span<{{as_cType(member.type.name, spanify)}}> copiedMembers; - WIRE_TRY(GetSpace(allocator, memberBuffer.size(), &copiedMembers)); + {% if member.length == "constant" %} + Span<{{as_cType(member.type.name, True)}}, {{member.constant_length}}> copiedMembers; + WIRE_TRY(GetSpace(allocator, &copiedMembers)); + {% else %} + Span<{{as_cType(member.type.name, True)}}> copiedMembers; + WIRE_TRY(GetSpace(allocator, memberBuffer.size(), &copiedMembers)); + {% endif %} record->{{memberName}} = copiedMembers; {% if member.type.is_wire_transparent %} if (!memberBuffer.empty()) { - copiedMembers.CopyFrom(memberBuffer); + SpanAsWritableBytes(copiedMembers).CopyFrom(SpanAsBytes(memberBuffer)); } {% else %} for (auto [i, member] : Enumerate(memberBuffer)) { @@ -667,6 +676,14 @@ return WireResult::Success; } +template <typename T, size_t N> +WireResult GetSpace(DeserializeAllocator* allocator, Span<T, N>* out) { + Span<T> dynamicSpan; + WIRE_TRY(GetSpace(allocator, N, &dynamicSpan)); + *out = dynamicSpan; + return WireResult::Success; +} + template <typename T> WireResult GetSpace(DeserializeAllocator* allocator, T** out) { Span<T> span;
diff --git a/generator/templates/dawn/wire/WireCmd.h b/generator/templates/dawn/wire/WireCmd.h index 9ed8a00..6ba1a67 100644 --- a/generator/templates/dawn/wire/WireCmd.h +++ b/generator/templates/dawn/wire/WireCmd.h
@@ -115,7 +115,6 @@ {% macro write_command_struct(command, is_return_command) %} {% set Return = "Return" if is_return_command else "" %} {% set CmdName = Return + command.name.CamelCase() + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} struct {{CmdName}} { //* From a filled structure, compute how much size will be used in the serialization buffer. size_t GetRequiredSize() const; @@ -144,17 +143,19 @@ {% endif %} {% for member in command.members %} - {% if spanify and member.is_length %} + {% if member.is_length %} //* Skip as it's included in the span just below. - {% elif spanify and member.length and member.length != "constant" %} - //* TODO(https://crbug.com/524405497): Support fixed-length spans. - {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, spanify), member) + ">" %} + {% elif member.length and member.constant_length != 1 %} + {% set length = "dawn::detail::DynamicExtent<size_t>" %} + {% if member.length == "constant" %} + {% set length = member.constant_length %} + {% endif %} + {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, True), member) + ">" %} {% if is_wire_data_only(member) %} //* If the member is data only, we do not copy the data, so it will be volatile. {% set element_type = "volatile " + element_type %} {% endif %} - {% set index_type = member.length.type.name.canonical_case() %} - ityp::span<{{index_type}}, {{element_type}}> {{as_varName(member.name)}}; + ityp::span<size_t, {{element_type}}, {{length}}> {{as_varName(member.name)}}; {% else %} {{as_annotated_cType(member)}}; {% endif %}
diff --git a/generator/templates/dawn/wire/client/ApiProcs.cpp b/generator/templates/dawn/wire/client/ApiProcs.cpp index 1c0e856..7d5f1f6 100644 --- a/generator/templates/dawn/wire/client/ApiProcs.cpp +++ b/generator/templates/dawn/wire/client/ApiProcs.cpp
@@ -42,15 +42,13 @@ #include "src/utils/span.h" {%- macro convert_arguments_and_call(function, suffix, call_receiver, first_arg = None) -%} - {% set cppify = not suffix in function_cpp_blocklist %} {% set client = "dawn::wire::client" %} {% for arg in function.arguments %} {% set varName = as_varName(arg.name) %} - {% if cppify and arg.is_length %} + {% if arg.is_length %} //* Skip as it's included in the span just below. - {% elif cppify and arg.length and arg.length != "constant" %} - // TODO(https://crbug.com/524405497): Support fixed-length spans. + {% elif arg.length and arg.length != "constant" %} {% if arg.type.name.canonical_case() == "void" %} using {{varName}}SpanT = {% if arg.annotation == "const*" %}const {% endif %}std::byte; auto {{varName}}Ptr = reinterpret_cast<{{varName}}SpanT*>({{varName}}); @@ -60,13 +58,13 @@ {% endif %} // SAFETY: The webgpu.h user is required to pass valid ranges of objects. auto {{varName}}_ = DAWN_UNSAFE_BUFFERS(dawn::Span<{{varName}}SpanT>({{varName}}Ptr, {{as_varName(arg.length.name)}})); - {% elif cppify and arg.type.category == "structure" %} + {% elif arg.type.category == "structure" %} auto {{varName}}_ = {{client}}::FromAPI({{varName}}); - {% elif cppify and arg.type.category in ["enum", "bitmask"] and arg.annotation == "value" %} + {% elif arg.type.category in ["enum", "bitmask"] and arg.annotation == "value" %} auto {{varName}}_ = static_cast<{{as_wire_clientType(arg.type)}}>({{varName}}); - {% elif cppify and arg.type.category == "object" %} + {% elif arg.type.category == "object" %} auto {{varName}}_ = {{client}}::FromAPI({{varName}}); - {% elif cppify and arg.annotation != "value" %} + {% elif arg.annotation != "value" %} auto {{varName}}_ = reinterpret_cast<{{decorate(as_wire_clientType(arg.type), arg)}}>({{varName}}); {% else %} auto {{varName}}_ = {{as_varName(arg.name)}}; @@ -80,20 +78,16 @@ {%- if first_arg -%} {{first_arg}} {%- if len(function.arguments) != 0 %}, {% endif -%} {%- endif -%} - {%- for arg in function.arguments if (not cppify or not arg.is_length) -%} + {%- for arg in function.arguments if not arg.is_length -%} {%- if not loop.first %}, {% endif -%} {{as_varName(arg.name)}}_ {%- endfor -%} ); {% if function.returns %} - {% if cppify %} - {% if function.returns.type.category in ["object", "enum", "bitmask"] %} - return {{client}}::ToAPI(result); - {% elif function.returns.type.category in ["structure"] %} - return *{{client}}::ToAPI(&result); - {% else %} - return result; - {% endif %} + {% if function.returns.type.category in ["object", "enum", "bitmask"] %} + return {{client}}::ToAPI(result); + {% elif function.returns.type.category in ["structure"] %} + return *{{client}}::ToAPI(&result); {% else %} return result; {% endif %} @@ -160,12 +154,17 @@ {% set varName = as_varName(arg.name) %} {% if arg.is_length %} //* Skipped as it is included in the span below. - {% elif arg.length and arg.length != "constant" %} + {% elif arg.length and arg.constant_length != 1 %} using {{varName}}SpanT = std::remove_pointer_t<{{decorate(as_cType(arg.type.name, True), arg)}}>; - size_t {{varName}}SizeV = dawn::checked_cast<size_t>({{as_varName(arg.length.name)}}); auto* {{varName}}Ptr = reinterpret_cast<{{varName}}SpanT*>({{varName}}); - // SAFETY: The webgpu.h user is required to pass valid ranges of objects. - cmd.{{varName}} = DAWN_UNSAFE_BUFFERS(dawn::Span<{{varName}}SpanT>({{varName}}Ptr, {{varName}}SizeV)); + {% if arg.length == "constant" %} + // SAFETY: The webgpu.h user is required to pass valid ranges of objects. + cmd.{{varName}} = DAWN_UNSAFE_BUFFERS(dawn::Span<{{varName}}SpanT, {{arg.constant_length}}>({{varName}}Ptr)); + {% else %} + size_t {{varName}}SizeV = dawn::checked_cast<size_t>({{as_varName(arg.length.name)}}); + // SAFETY: The webgpu.h user is required to pass valid ranges of objects. + cmd.{{varName}} = DAWN_UNSAFE_BUFFERS(dawn::Span<{{varName}}SpanT>({{varName}}Ptr, {{varName}}SizeV)); + {% endif %} {% else %} cmd.{{varName}} = {{varName}}; {% endif %}
diff --git a/generator/templates/dawn/wire/client/ClientHandlers.cpp b/generator/templates/dawn/wire/client/ClientHandlers.cpp index ad65c5d..9cc9f39 100644 --- a/generator/templates/dawn/wire/client/ClientHandlers.cpp +++ b/generator/templates/dawn/wire/client/ClientHandlers.cpp
@@ -33,7 +33,6 @@ namespace dawn::wire::client { {% for command in cmd_records["return command"] %} {% set CmdName = "Return" + command.name.CamelCase() + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} WireResult Client::Handle{{command.name.CamelCase()}}(DeserializeBuffer* deserializeBuffer) { Return{{command.name.CamelCase()}}Cmd cmd; WIRE_TRY(cmd.Deserialize(deserializeBuffer, &mAllocator)); @@ -51,7 +50,7 @@ {% endfor %} return Do{{command.name.CamelCase()}}( - {%- for member in command.members if (not spanify or not member.is_length) -%} + {%- for member in command.members if not member.is_length -%} {%- if not loop.first -%}, {% endif %} {%- if member.handle_type -%} {{as_varName(member.name)}}
diff --git a/generator/templates/dawn/wire/client/ClientPrototypes.inc b/generator/templates/dawn/wire/client/ClientPrototypes.inc index 49b9adc..5302b86 100644 --- a/generator/templates/dawn/wire/client/ClientPrototypes.inc +++ b/generator/templates/dawn/wire/client/ClientPrototypes.inc
@@ -29,17 +29,19 @@ {% for command in cmd_records["return command"] %} {% set Suffix = command.name.CamelCase() %} {% set CmdName = "Return" + Suffix + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} WireResult Handle{{Suffix}}(DeserializeBuffer* deserializeBuffer); WireResult Do{{Suffix}}( - {%- for member in command.members if (not spanify or not member.is_length) -%} + {%- for member in command.members if not member.is_length -%} {%- if not loop.first -%}, {% endif %} {%- if member.handle_type -%} {{as_wireType(member.handle_type)}} {{as_varName(member.name)}} - {%- elif spanify and member.length and member.length != "constant" -%} - {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, spanify), member) + ">" %} - {% set index_type = member.length.type.name.canonical_case() %} - ityp::span<{{index_type}}, {{element_type}}> {{as_varName(member.name)}} + {%- elif member.length and member.constant_length != 1 -%} + {% set length = "dawn::detail::DynamicExtent<size_t>" %} + {% if member.length == "constant" %} + {% set length = member.constant_length %} + {% endif %} + {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, True), member) + ">" %} + ityp::span<size_t, {{element_type}}, {{length}}> {{as_varName(member.name)}} {%- else -%} {{as_annotated_wireType(member)}} {%- endif -%}
diff --git a/generator/templates/dawn/wire/client/api_structs.cpp b/generator/templates/dawn/wire/client/api_structs.cpp index c2fa258..6673d13 100644 --- a/generator/templates/dawn/wire/client/api_structs.cpp +++ b/generator/templates/dawn/wire/client/api_structs.cpp
@@ -61,7 +61,6 @@ {% for type in by_category["structure"] if type.name.get() not in SpecialStructures %} {% set CppType = as_cppType(type.name) %} {% set CType = as_cType(type.name) %} - {% set spanify = true %} static_assert(sizeof({{CppType}}) == sizeof({{CType}}), "sizeof mismatch for {{CppType}}"); static_assert(alignof({{CppType}}) == alignof({{CType}}), "alignof mismatch for {{CppType}}"); @@ -77,15 +76,16 @@ "offsetof mismatch for {{CppType}}::sType"); {% endif %} {% for member in type.members %} - {% if spanify and member.is_length %} + {% if member.is_length %} //* Skip as the member is included in the span member. - {% elif spanify and member.length and member.length != "constant" %} - // TODO(https://crbug.com/524405497): Support fixed-length spans. + {% elif member.length and member.constant_length != 1 %} {% set memberName = member.name.camelCase() %} - {% set lengthName = member.length.name.camelCase() %} using {{CppType}}{{memberName}}Span = decltype(std::declval<{{CppType}}>().{{memberName}}); - static_assert(offsetof({{CppType}}, {{memberName}}) + {{CppType}}{{memberName}}Span::GetOffsetOfSize() == offsetof({{CType}}, {{lengthName}}), - "offsetof mismatch for {{CppType}}::{{memberName}}::mSize"); + {% if member.length != "constant" %} + {% set lengthName = member.length.name.camelCase() %} + static_assert(offsetof({{CppType}}, {{memberName}}) + {{CppType}}{{memberName}}Span::GetOffsetOfSize() == offsetof({{CType}}, {{lengthName}}), + "offsetof mismatch for {{CppType}}::{{memberName}}::mSize"); + {% endif %} static_assert(offsetof({{CppType}}, {{memberName}}) + {{CppType}}{{memberName}}Span::GetOffsetOfData() == offsetof({{CType}}, {{memberName}}), "offsetof mismatch for {{CppType}}::{{memberName}}::mData"); {% else %} @@ -100,7 +100,6 @@ {% for type in by_category["structure"] if type.has_free_members_function %} {% set CppType = as_cppType(type.name) %} - {% set spanify = true %} // {{as_cppType(type.name)}} {{CppType}}::~{{CppType}}() { @@ -108,12 +107,12 @@ } {{CppType}}::{{CppType}}({{CppType}}&& rhs) - : {% for member in type.members if (not spanify or not member.is_length)%} + : {% for member in type.members if not member.is_length %} {%- set memberName = member.name.camelCase() -%} {{memberName}}(rhs.{{memberName}}){% if not loop.last %},{{"\n "}}{% endif %} {% endfor -%} { - {% for member in type.members if (not spanify or not member.is_length)%} + {% for member in type.members if not member.is_length %} rhs.{{member.name.camelCase()}} = {}; {% endfor %} } @@ -123,10 +122,10 @@ return *this; } FreeMembers(); - {% for member in type.members if (not spanify or not member.is_length)%} + {% for member in type.members if not member.is_length %} this->{{member.name.camelCase()}} = std::move(rhs.{{member.name.camelCase()}}); {% endfor %} - {% for member in type.members if (not spanify or not member.is_length)%} + {% for member in type.members if not member.is_length %} rhs.{{member.name.camelCase()}} = {}; {% endfor %} return *this; @@ -135,8 +134,10 @@ void {{CppType}}::FreeMembers() { bool needsFreeing = false; {%- for member in type.members if member.annotation != 'value' %} - {% if spanify and member.length != "constant" %} + {% if member.length and member.length != "constant" %} if (!this->{{member.name.camelCase()}}.empty()) { needsFreeing = true; } + {% elif member.length == "constant" and member.constant_length != 1 %} + if (this->{{member.name.camelCase()}}.data() != nullptr) { needsFreeing = true; } {% else %} if (this->{{member.name.camelCase()}} != nullptr) { needsFreeing = true; } {% endif %}
diff --git a/generator/templates/dawn/wire/client/api_structs.h b/generator/templates/dawn/wire/client/api_structs.h index f4c9970..c8e8ae0 100644 --- a/generator/templates/dawn/wire/client/api_structs.h +++ b/generator/templates/dawn/wire/client/api_structs.h
@@ -127,7 +127,6 @@ {% for type in by_category["structure"] if type.name.get() not in SpecialStructures %} {% set CppType = as_cppType(type.name) %} - {% set spanify = true %} {% if type.chained %} {% set chainedStructType = "ChainedStructOut" if type.chained == "out" else "ChainedStruct" %} struct {{CppType}} : {{chainedStructType}} { @@ -171,17 +170,19 @@ {% endif %} {% endif %} - {% if spanify and member.is_length %} + {% if member.is_length %} //* Skip as it's included in the span just below. - {% elif spanify and member.length and member.length != "constant" %} - // TODO(https://crbug.com/524405497): Support fixed-length spans. + {% elif member.length and member.constant_length != 1 %} + {% set length = "dawn::detail::DynamicExtent<size_t>" %} + {% if member.length == "constant" %} + {% set length = member.constant_length %} + {% endif %} {% if member.type.name.canonical_case() == "void" %} {% set element_type = "const std::byte" %} {% else %} {% set element_type = "std::remove_pointer_t<" + decorate(as_wire_clientType(member.type), member) + ">" %} {% endif %} - {% set index_type = member.length.type.name.canonical_case() %} - ityp::span<{{index_type}}, {{element_type}}> {{as_varName(member.name)}}; + ityp::span<size_t, {{element_type}}, {{length}}> {{as_varName(member.name)}}; {% else %} {{as_annotated_wire_clientType(member)}} {{render_cpp_default_value(member, forced_default_value)}}; {% endif %}
diff --git a/generator/templates/dawn/wire/server/ServerDoers.cpp b/generator/templates/dawn/wire/server/ServerDoers.cpp index b40a45a..775d699 100644 --- a/generator/templates/dawn/wire/server/ServerDoers.cpp +++ b/generator/templates/dawn/wire/server/ServerDoers.cpp
@@ -37,11 +37,10 @@ {% set Suffix = command.name.CamelCase() %} {% set CmdName = Suffix + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} {% if Suffix not in client_side_commands %} {% if is_method %} WireResult Server::Do{{Suffix}}( - {%- for member in command.members if (not spanify or not member.is_length) -%} + {%- for member in command.members if not member.is_length -%} {%- if not loop.first -%}, {% endif %} {%- if member.is_return_value -%} {%- if member.handle_type -%} @@ -49,15 +48,17 @@ {%- else -%} {{as_cType(member.type.name)}}* {{as_varName(member.name)}} {%- endif -%} - {%- elif spanify and member.length and member.length != "constant" -%} - //* TODO(https://crbug.com/524405497): Support fixed-length spans. - {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, spanify), member) + ">" %} + {%- elif member.length and member.constant_length != 1 -%} + {% set length = "dawn::detail::DynamicExtent<size_t>" %} + {% if member.length == "constant" %} + {% set length = member.constant_length %} + {% endif %} + {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, True), member) + ">" %} {% if is_wire_data_only(member) %} //* If the member is data only, we do not copy the data, so it will be volatile. {% set element_type = "volatile " + element_type %} {% endif %} - {% set index_type = member.length.type.name.canonical_case() %} - ityp::span<{{index_type}}, {{element_type}}> {{as_varName(member.name)}} + ityp::span<size_t, {{element_type}}, {{length}}> {{as_varName(member.name)}} {%- else -%} {{as_annotated_cType(member)}} {%- endif -%} @@ -77,10 +78,10 @@ mProcs->{{as_varName(type.name, method.name)}}( {%- for member in command.members if not member.is_return_value -%} {%- if not loop.first -%}, {% endif %} - {%- if spanify and member.is_length -%} + {%- if member.is_length -%} {%- set span_members = command.members | selectattr("length", "equalto", member) | list -%} {{as_varName(span_members[0].name)}}.size() - {%- elif spanify and member.length and member.length != "constant" -%} + {%- elif member.length and member.constant_length != 1 -%} {% if is_wire_data_only(member) %} //* For wire data types, we cast away the volatile here. This //* is fine since the data is not sensitive to TOCTOU attacks.
diff --git a/generator/templates/dawn/wire/server/ServerHandlers.cpp b/generator/templates/dawn/wire/server/ServerHandlers.cpp index a4bb1d2..aca4bbd 100644 --- a/generator/templates/dawn/wire/server/ServerHandlers.cpp +++ b/generator/templates/dawn/wire/server/ServerHandlers.cpp
@@ -36,7 +36,6 @@ {% set Suffix = command.name.CamelCase() %} {% set CmdName = Suffix + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} //* The generic command handlers WireResult Server::Handle{{Suffix}}(DeserializeBuffer* deserializeBuffer) { {{Suffix}}Cmd cmd; @@ -69,7 +68,7 @@ //* Do command WIRE_TRY(Do{{Suffix}}( - {%- for member in command.members if (not spanify or not member.is_length) -%} + {%- for member in command.members if not member.is_length -%} {%- if not loop.first -%}, {% endif %} {%- if member.is_return_value -%} {%- if member.handle_type -%}
diff --git a/generator/templates/dawn/wire/server/ServerPrototypes.inc b/generator/templates/dawn/wire/server/ServerPrototypes.inc index 7ead424..e78cec4 100644 --- a/generator/templates/dawn/wire/server/ServerPrototypes.inc +++ b/generator/templates/dawn/wire/server/ServerPrototypes.inc
@@ -29,10 +29,9 @@ {% for command in cmd_records["command"] %} {% set Suffix = command.name.CamelCase() %} {% set CmdName = Suffix + "Cmd" %} - {% set spanify = CmdName not in cmd_spanification_blocklist %} WireResult Handle{{Suffix}}(DeserializeBuffer* deserializeBuffer); WireResult Do{{Suffix}}( - {%- for member in command.members if (not spanify or not member.is_length) -%} + {%- for member in command.members if not member.is_length -%} {%- if not loop.first -%}, {% endif %} {%- if member.is_return_value -%} {%- if member.handle_type -%} @@ -42,14 +41,17 @@ {%- endif -%} {%- elif member.id_type != None -%} Known<WGPU{{member.id_type.name.CamelCase()}}> {{member.name.camelCase()}} - {%- elif spanify and member.length and member.length != "constant" -%} - {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, spanify), member) + ">" %} + {%- elif member.length and member.constant_length != 1 -%} + {% set length = "dawn::detail::DynamicExtent<size_t>" %} + {% if member.length == "constant" %} + {% set length = member.constant_length %} + {% endif %} + {% set element_type = "std::remove_pointer_t<" + decorate(as_cType(member.type.name, True), member) + ">" %} {% if is_wire_data_only(member) %} //* If the member is data only, we do not copy the data, so it will be volatile. {% set element_type = "volatile " + element_type %} {% endif %} - {% set index_type = member.length.type.name.canonical_case() %} - ityp::span<{{index_type}}, {{element_type}}> {{as_varName(member.name)}} + ityp::span<size_t, {{element_type}}, {{length}}> {{as_varName(member.name)}} {%- else -%} {{as_annotated_cType(member)}} {%- endif -%}
diff --git a/src/dawn/dawn_wire.json b/src/dawn/dawn_wire.json index 78c107a..68aeb46 100644 --- a/src/dawn/dawn_wire.json +++ b/src/dawn/dawn_wire.json
@@ -227,12 +227,6 @@ ] }, "special items": { - "_cmd_spanification_blocklist_comment": "// TODO(https://crbug.com/526537254): Drive this list down.", - "cmd_spanification_blocklist": [ - ], - "_function_cpp_blocklist_comment": "// TODO(https://crbug.com/526537254): Drive this list down.", - "function_cpp_blocklist": [ - ], "client_side_structures": [ "DawnWGSLBlocklist", "FutureWaitInfo",