BindEntry
Interface in Reflection
One resource slot in a reflected bind group: the shape of a single WGSL @group(G) @binding(B) var<space> name: T declaration, or of the sampler uniform or std140 block the GLSL ES 3.00 backend emits for it.
import type { BindEntry } from 'typeshade'
The signature, the description and the examples come from the compiler's own source at commit 26de7be8.
Syntax
interface BindEntry { readonly group: number; readonly binding: number; readonly name: string; readonly space: AddressSpace; readonly access?: 'read' | 'read_write'; readonly resourceKind: ResourceKind; readonly owner: 'module' | 'host'; readonly glslSpelling?: 'std140-block' | 'loose'; readonly structName?: string; readonly textureDim?: '2d' | '2d-ms' | '2d-array' | 'cube' | '3d' | '1d' | 'cube-array'; readonly textureElem?: TextureElem; readonly sampleType?: 'float' | 'unfilterable-float' | 'depth' | 'sint' | 'uint'; readonly storageFormat?: StorageTextureFormat; readonly storageAccess?: 'write-only' | 'read-only' | 'read-write'; readonly textureDepth?: true; readonly samplerComparison?: true; readonly stages: readonly ('vertex' | 'fragment' | 'compute')[];}Description
name is the declaration’s own identifier,
the one shader code reads through (field_view.foo). A GLSL host binding a struct binding
needs structName instead: GLSL’s block syntax is
layout(std140) uniform <StructName> { … } <name>;, so getUniformBlockIndex takes the
struct’s type name ('FieldView' for a binding named field_view). Passing name there
does not fail to link; the block silently lands at GL’s default binding point 0 and aliases
whatever else is bound there.
group and binding are metadata only on the GLSL backend. The emitted GLSL carries no
binding qualifier, so a GLSL host resolves every entry by name at link time and assigns the
binding point or texture unit itself from these numbers. GLSL has one flat namespace and
no group, so a host whose modules declare more than one group folds group into the point
it assigns (group * 8 + binding, say) so that two groups’ binding 0 do not collide.
Instance properties
groupread onlynumberbindingread onlynumbernameread onlystringspaceread onlyAddressSpaceaccessoptionalread only'read' | 'read_write'resourceKindread onlyResourceKindownerread only'module' | 'host'Who owns the resource.
'module'when the module declares it and the host builds its bind group from this reflection;'host'when the surrounding host owns it and the host’s own layout is the authority. Always set.bindGroupslists host-owned bindings too: a host still has to know about a binding it owns, it just must not allocate for it.glslSpellingoptionalread only'std140-block' | 'loose'How GLSL ES 3.00 spells a host-owned struct binding. Present only when
owneris'host'and the binding’s type is a struct: a module-owned block is always a std140 block, and WGSL has one spelling regardless.'std140-block'means bind a uniform buffer to the block index;'loose'means the members were flattened into the default uniform block and are set individually withglUniform*under their field names (the layout inuniformsstill lists them, in declaration order).structNameoptionalread onlystringThe struct’s type name, for a binding whose type is a struct; absent on every other kind. It is the name a GLSL host passes to
getUniformBlockIndex.textureDimoptionalread only'2d' | '2d-ms' | '2d-array' | 'cube' | '3d' | '1d' | 'cube-array'The texture dimension the shader declared, so a host can create or validate the matching view:
'2d-array'needs an array view and a layer-aware bind,'2d-ms'a multisampled one,'cube'a cube view,'3d'a 3d one,'1d'a 1d one and'cube-array'a cube-array view — the valueGPUTextureViewDescriptor.dimensiontakes. Always set on atextureentry, absent on every other kind.textureElemoptionalread onlyTextureElemThe texel element the shader declared. Always set on a
textureentry, absent on every other kind.A host needs both
textureDimandtextureElemto build a valid binding, since the dimension alone does not say whether the view is float or integer. WebGPU’sGPUTextureBindingLayout.sampleTypemust be'uint'or'sint'for au32ori32texture and one of the two float types forf32; WebGL2 must back an integer texture with an integer internal format (R32UI,R32I). The value is the DSL’s own element, untranslated, because reflection takes a module and never a backend.An integer texture is unfilterable, so a host must not pair one with a filtering sampler. A module that type-checks never asks it to:
textureSamplerejects an integer texture at compile time.BindEntry.sampleTypeis what a layout takes for it, from this element and the calls that read the texture.sampleTypeoptionalread only'float' | 'unfilterable-float' | 'depth' | 'sint' | 'uint'What a host’s
GPUTextureBindingLayout.sampleTypetakes for this texture, in WebGPU’s own words, from the element the shader declared and the calls that read it. Always set on atextureentry, absent on every other kind, so a host never has to read absence as a default.'depth'for a depth texture;'uint'or'sint'for au32or ani32texture;'float'for anf32texture that a call pairs with asampler: atextureSample(any of its forms) or atextureGatherin an entry or in a function an entry calls, through a helper’s parameters or aconstof the texture as well. Asamplerbinding is laid outfiltering, which WebGPU refuses beside an unfilterable texture, and a'float'layout takes a filterable format only;'unfilterable-float'for every otherf32texture: one the entries load, measure or count and never sample, one no entry reaches, and a multisampled one, which no sampler reads. It takes every format a'float'layout takes, and the 32-bit float formats (r32float,rgba32float) that layout refuses.
A module with a
rawstatement in what its entries reach is opaque, so each of itsf32textures but a multisampled one is'float'. A module with no entry is read whole, since a host writes the entries over it. The sample type follows the texture, not one entry: a texture that one entry samples and another loads is'float'for both.A host that samples an unfilterable format through a non-filtering sampler, which a module cannot say, writes its own layout for that binding.
storageFormatoptionalread onlyStorageTextureFormatThe texel format the shader declared for a storage texture, exactly as WebGPU’s
GPUStorageTextureBindingLayout.formatspells it. Always set on astorage-textureentry, absent on every other kind (roadmap 0.4 item 10).A storage texture’s format is part of its type in WGSL, not a property of the view, and a host’s bind group layout has to repeat it exactly: a layout whose format differs from the shader’s is a validation error at pipeline creation.
storageAccessoptionalread only'write-only' | 'read-only' | 'read-write'How the shader may touch a storage texture, in WebGPU’s spelling rather than WGSL’s —
'write-only','read-only','read-write'— which is whatGPUStorageTextureBindingLayout.accesstakes. Always set on astorage-textureentry, absent on every other kind.A host passing WGSL’s own
write/read/read_writethrough gets a validation error, so the translation happens here rather than in every host.textureDepthoptionalread onlytrueSet on a depth texture (roadmap 0.4 item 11): the host’s
GPUTextureBindingLayouttakessampleType: 'depth'for it, whichBindEntry.sampleTypereports, and pairs it with a comparison sampler. Alwaystrueon such an entry, absent on every other kind, so a host never has to read absence as “not depth” on an entry that is not a texture at all. A depth texture has notextureElem.samplerComparisonoptionalread onlytrueSet on a comparison sampler (roadmap 0.4 item 11): the host’s
GPUSamplerBindingLayouttakestype: 'comparison'for it. Alwaystrueon such an entry, absent otherwise.stagesread onlyreadonly ('vertex' | 'fragment' | 'compute')[]The stages that reference this binding, in the order vertex, fragment, compute. It comes from the same reachability walk the per-stage GLSL emit uses to decide which shader declares which uniform, so a host’s stage mask can never describe a narrower program than the emit produces. It is
GPUBindGroupLayoutEntry.visibilitybefore it becomes a bitmask, and the same fact a WebGL2 host uses to assign uniform-block binding points and texture units per stage. It is a list so that compute is expressible alongside vertex and fragment.Always set, and it can be empty.
bindGroupslists every declared binding, so a binding no entry point reaches (declared and never read, or in a module with no entry point at all) reports[]. A host must not invent a visibility for it.For a host-owned binding (
owner: 'host') this is the module’s view and therefore a lower bound: the host’s real layout may expose the resource to stages this module’s entries never reach. Merge it into the host layout; do not narrow the host layout to it.
See also
Source
src/core/reflect.ts, line 341, at commit 26de7be8