Name

    ARB_multi_bind

Name Strings

    GL_ARB_multi_bind

Contact

    Pat Brown, NVIDIA Corporation (pbrown 'at' nvidia.com)

Contributors

    Jeff Bolz, NVIDIA
    Frank Chen, Qualcomm
    Piers Daniell, NVIDIA
    Daniel Koch, NVIDIA
    Jon Leech

Notice

    Copyright (c) 2013 The Khronos Group Inc. Copyright terms at
        http://www.khronos.org/registry/speccopyright.html

Specification Update Policy

    Khronos-approved extension specifications are updated in response to
    issues and bugs prioritized by the Khronos OpenGL Working Group. For
    extensions which have been promoted to a core Specification, fixes will
    first appear in the latest version of that core Specification, and will
    eventually be backported to the extension document. This policy is
    described in more detail at
        https://www.khronos.org/registry/OpenGL/docs/update_policy.php

Status

    Complete. Approved by the ARB on June 3, 2013.
    Ratified by the Khronos Board of Promoters on July 19, 2013.

Version

    Last Modified Date:         May 30, 2013
    Revision:                   10

Number

    ARB Extension #147

Dependencies

    This extension is written against the OpenGL 4.3 (Compatibility Profile)
    Specification, dated August 6, 2012.

    OpenGL 3.0 is required.

    This extension interacts with OpenGL 3.3 and ARB_sampler_objects.

    This extension interacts with OpenGL 4.3 and ARB_vertex_attrib_binding.

Overview

    This extension provides a new set of commands allowing applications to
    bind or unbind a set of objects in a single call, instead of requiring a
    separate call for each bind or unbind operation.  Using a single command
    allows OpenGL implementations to amortize function call, name space
    lookup, and potential locking overhead over multiple bind or unbind
    operations.  The rendering loops of graphics applications frequently
    switch between different states, binding different sets of resources,
    including texture objects, sampler objects, textures for image loads and
    stores, uniform buffers, and vertex buffers; this extension provides
    "multi-bind" entry points for all of these object types.

    Each command in this extension includes a <first> and <count> parameter,
    specifying a continguous range of binding points to update, as well as an
    array of <count> object names specifying the objects to bind.  Unlike
    single bind commands, multi-bind commands can be used only to bind or
    unbind existing objects.  Passing a previously unused object name
    (generated or not) results in an error and does not create a new object.
    For binding points with associated data (e.g., ranges of a buffer),
    separate arrays are used to pass the associated data for each binding
    point.  Passing zero values in the array of object names removes the
    object bound to the current bounding point.  Additionally, if NULL is
    passed as the array of objects, objects bound to the entire range of
    binding points are unbound, as though the caller passed an array of
    zeroes.

New Procedures and Functions

    void BindBuffersBase(enum target, uint first, sizei count, 
                         const uint *buffers);

    void BindBuffersRange(enum target, uint first, sizei count, 
                          const uint *buffers, const intptr *offsets,
                          const sizeiptr *sizes);

    void BindTextures(uint first, sizei count, const uint *textures);

    void BindSamplers(uint first, sizei count, const uint *samplers);

    void BindImageTextures(uint first, sizei count, const uint *textures);

    void BindVertexBuffers(uint first, sizei count, const uint *buffers,
                           const intptr *offsets, const sizei *strides);

New Tokens

    None.

Modifications to the OpenGL 4.3 (Compatibility Profile) Specification

    Modify Section 2.3.1, Errors, p. 15

    (modify third paragraph, p. 16, adding "unless otherwise noted"
     qualification to the general rule that commands producing errors have no
     side effects)

    Table 2.3 summarizes ...  if an OUT_OF_MEMORY error has occurred.  In
    other cases, there are no side effects unless otherwise noted; the command
    which generates the error is ignored so that it has no effect on GL state
    or framebuffer contents. ...


    Modify Section 6.1.1, Binding Buffer Objects To Indexed Targets, p. 55

    (insert immediately after the "Errors" block at the end of the section,
    p. 56)

    The commands

      void BindBuffersBase(enum target, uint first, sizei count, 
                           const uint *buffers);

      void BindBuffersRange(enum target, uint first, sizei count, 
                            const uint *buffers, const intptr *offsets,
                            const sizeiptr *sizes);

    bind <count> existing buffer objects to bindings numbered <first> through
    <first>+<count>-1 in the array of buffer binding points corresponding to
    <target>.  If <buffers> is not NULL, it specifies an array of <count>
    values, each of which must be zero or the name of an existing buffer
    object.  For BindBuffersRange, <offsets> and <sizes> specify arrays of
    <count> values indicating the range of each buffer to bind.  If <buffers>
    is NULL, all bindings from <first> through <first>+<count>-1 are reset
    to their unbound (zero) state. In this case, the offsets and sizes
    associated with the binding points are set to default values, ignoring
    <offsets> and <sizes>.

    BindBuffersBase is equivalent to:

      for (i = 0; i < count; i++) {
        if (buffers == NULL) {
          glBindBufferBase(target, first + i, 0);
        } else {
          glBindBufferBase(target, first + i, buffers[i]);
        }
      }

    except that the single general buffer binding corresponding to <target>
    is unmodified, and that buffers will not be created if they do not
    exist.

    BindBuffersRange is equivalent to:

      for (i = 0; i < count; i++) {
        if (buffers == NULL) {
          glBindBufferRange(target, first + i, 0, 0, 0);
        } else {
          glBindBufferRange(target, first + i, buffers[i], offsets[i], 
                            sizes[i]);
        }
      }

    except that the single general buffer binding corresponding to <target>
    is unmodified, and that buffers will not be created if they do not
    exist.

    The values specified in <buffers>, <offsets>, and <sizes> will be checked
    separately for each binding point.  When values for a specific binding
    point are invalid, the state for that binding point will be unchanged and
    an error will be generated.  However, state for other binding points will
    still be changed if their corresponding values are valid.

    Errors

      An INVALID_ENUM error is generated if <target> is not one of the targets
      listed above.

      An INVALID_OPERATION error is generated if <first> + <count> is greater
      than the number of target-specific indexed binding points, as described
      in section 6.7.1.

      An INVALID_OPERATION error is generated if any value in <buffers> is not
      zero or the name of an existing buffer object (per binding).

      An INVALID_VALUE error is generated by BindBuffersRange if any value in
      <offsets> is less than zero (per binding).

      An INVALID_VALUE error is generated by BindBuffersRange if any value in
      <sizes> is less than or equal to zero (per binding).

      An INVALID_VALUE error is generated by BindBuffersRange if any pair of
      values in <offsets> and <sizes> does not respectively satisfy the
      constraints described for those parameters for the specified target, as
      described in section 6.7.1 (per binding).


    Modify Section 8.1, Texture Objects (p. 155)

    (insert after errors section, p. 156)

    The command

      void BindTextures(uint first, sizei count, const uint *textures);

    binds <count> existing texture objects to texture image units numbered
    <first> through <first>+<count>-1.  If <textures> is not NULL, it
    specifies an array of <count> values, each of which must be zero or the
    name of an existing texture object.  When an entry in <textures> is the
    name of an existing texture object, that object is bound to corresponding
    texture unit for the target specified when the texture object was created.
    When an entry in <textures> is zero, each of the targets enumerated at the
    beginning of this section is reset to its default texture for the
    corresponding texture image unit.  If <textures> is NULL, each target of
    each affected texture image unit from <first> through <first>+<count>-1 is
    reset to its default texture.

    BindTextures is equivalent to

      for (i = 0; i < count; i++) {
        uint texture;
        if (textures == NULL) { 
          texture = 0;
        } else {
          texture = textures[i];
        }
        ActiveTexture(TEXTURE0 + first + i);
        if (texture != 0) {
          enum target = /* target of texture object textures[i] */;
          BindTexture(target, textures[i]);
        } else {
          for (target in all supported targets) {
            BindTexture(target, 0);
          }
        }
      }

    except that the active texture selector retains its original value upon
    completion of the command, and that textures will not be created if they
    do not exist.


    The values specified in <textures> will be checked separately for each
    texture image unit.  When a value for a specific texture image unit is
    invalid, the state for that texture image unit will be unchanged and an
    error will be generated.  However, state for other texture image units
    will still be changed if their corresponding values are valid.

    Errors

      An INVALID_OPERATION error is generated if <first> + <count> is greater
      than the number of texture image units supported by the implementation.

      An INVALID_OPERATION error is generated if any value in <textures> is
      not zero or the name of an existing texture object (per binding).


    Modify Section 8.2, Sampler Objects (p. 158)

    (insert after errors section, p. 159)

    The command

      void BindSamplers(uint first, sizei count, const uint *samplers);

    binds <count> existing sampler objects to texture image units numbered
    <first> through <first>+<count>-1.  If <samplers> is not NULL, it
    specifies an array of <count> values, each of which must be zero or the
    name of an existing sampler object.  If <samplers> is NULL, each affected
    texture image unit from <first> through <first>+<count>-1 will be reset to
    have no bound sampler object.

    BindSamplers is equivalent to

      for (i = 0; i < count; i++) {
        if (samplers == NULL) {
          glBindSampler(first + i, 0);
        } else {
          glBindSampler(first + i, samplers[i]);
        }
      }

    The values specified in <samplers> will be checked separately for each
    texture image unit.  When a value for a specific texture image unit is
    invalid, the state for that texture image unit will be unchanged and an
    error will be generated.  However, state for other texture image units
    will still be changed if their corresponding values are valid.

    Errors

      An INVALID_OPERATION error is generated if <first> + <count> is greater
      than the number of texture image units supported by the implementation.

      An INVALID_OPERATION error is generated if any value in <samplers> is
      not zero or the name of an existing sampler object (per binding).


    Modify Section 8.25, Texture Image Loads and Stores, p. 281

    (insert before the next-to-last paragraph, p. 282, "When a shader
     accesses...")

    The command

      void BindImageTextures(uint first, sizei count, const uint *textures);

    binds <count> existing texture objects to image units numbered <first>
    through <first>+<count>-1.  If <textures> is not NULL, it specifies an
    array of <count> values, each of which must be zero or the name of an
    existing texture object.  If <textures> is NULL, each affected image unit
    from <first> through <first>+<count>-1 will be reset to have no bound
    texture object.

    When binding a non-zero texture object to an image unit, the image unit
    <level>, <layered>, <layer>, and <access> parameters are set to zero,
    TRUE, zero, and READ_WRITE, respectively.  The image unit <format>
    parameter is taken from the internal format of the texture image at level
    zero of the texture object identified by <textures>.  For cube map
    textures, the internal format of the TEXTURE_CUBE_MAP_POSITIVE_X image of
    level zero is used.  For multisample, multisample array, buffer, and
    rectangle textures, the internal format of the single texture level is
    used.

    When unbinding a texture object from an image unit, the image unit
    parameters <level>, <layered>, <layer>, and <format> will be reset to
    their default values of zero, FALSE, 0, and R8, respectively.

    BindImageTextures is equivalent to

      for (i = 0; i < count; i++) {
        if (textures == NULL || textures[i] = 0) {
          glBindImageTexture(first + i, 0, 0, FALSE, 0, READ_ONLY, R8);
        } else {
          glBindImageTexture(first + i, textures[i], 0, TRUE, 0, READ_WRITE,
                             lookupInternalFormat(textures[i]));
        }
      }

    where lookupInternalFormat returns the internal format of the specified
    texture object.

    The values specified in <textures> will be checked separately for each
    image unit.  When a value for a specific image unit is invalid, the state
    for that image unit will be unchanged and an error will be generated.
    However, state for other image units will still be changed if their
    corresponding values are valid.

    Errors

      An INVALID_OPERATION error is generated if <first> + <count> is greater
      than the number of image units supported by the implementation.

      An INVALID_OPERATION error is generated if any value in <textures> is
      not zero or the name of an existing texture object (per binding).

      An INVALID_OPERATION error is generated if the internal format of the
      level zero texture image of any texture in <textures> is not found in
      table 8.33 (per binding).

      An INVALID_OPERATION error is generated if the width, height, or depth
      of the level zero texture image of any texture in <textures> is zero
      (per binding).


    Modify Section 10.3.1, Specifying Arrays For Generic Attributes, p. 340

    (insert after first errors section, p. 343)

    The command

      void BindVertexBuffers(uint first, sizei count, const uint *buffers,
                             const intptr *offsets, const sizei *strides);

    binds <count> existing buffer objects to vertex buffer binding points
    numbered <first> through <first>+<count>-1.  If <buffers> is not NULL, it
    specifies an array of <count> values, each of which must be zero or the
    name of an existing buffer object.  <offsets> and <strides> specify arrays
    of <count> values indicating the offset of the first element and stride
    between elements in each buffer, respectively.  If <buffers> is NULL, each
    affected vertex buffer binding point from <first> through
    <first>+<count>-1 will be reset to have no bound buffer object.  In this
    case, the offsets and strides associated with the binding points are set
    to default values, ignoring <offsets> and <strides>.

    BindVertexBuffers is equivalent to

      for (i = 0; i < count; i++) {
        if (buffers == NULL) {
          glBindVertexBuffer(first + i, 0, 0, 16);
        } else {
          glBindVertexBuffer(first + i, buffers[i], offsets[i], strides[i]);
        }
      }

    except that buffers will not be created if they do not exist.

    The values specified in <buffers>, <offsets>, and <strides> will be
    checked separately for each vertex buffer binding point.  When a value for
    a specific binding point is invalid, the state for that binding point will
    be unchanged and an error will be generated.  However, state for other
    binding points will still be changed if their corresponding values are
    valid.

    Errors

      An INVALID_OPERATION error is generated if <first> + <count> is greater
      than the value of MAX_VERTEX_ATTRIB_BINDINGS.

      An INVALID_OPERATION error is generated if any value in <buffers> is not
      zero or the name of an existing buffer object (per binding).

      An INVALID_VALUE error is generated if any value in <offsets> or
      <strides> is negative (per binding).


    Modify Section 21.4.1, Commands Not Usable in Display Lists, p. 618

    (add a new section below "Debug output", p. 619)

    Multi-object binds:  BindBuffersBase, BindBuffersRange, BindTextures,
    BindSamplers, BindImageTextures, BindVertexBuffers


Additions to the AGL/EGL/GLX/WGL Specifications

    None

GLX Protocol

    TBD

Dependencies on OpenGL 3.3 and ARB_sampler_objects

    If neither OpenGL 3.3 nor ARB_sampler_objects is supported, references to
    BindSamplers should be removed.

Dependencies on OpenGL 4.3 and ARB_vertex_attrib_binding

    If neither OpenGL 4.3 nor ARB_vertex_attrib_binding is supported,
    references to BindVertexBuffers should be removed.

Errors

    An INVALID_ENUM error is generated by BindBuffersBase or BindBuffersRange
    if <target> is not one of the indexed targets for buffer bindings.

    An INVALID_OPERATION error is generated by BindBuffersBase or
    BindBuffersRange if <first> + <count> is greater than the number of
    target-specific indexed binding points, as described in section 6.7.1.

    An INVALID_OPERATION error is generated by BindBuffersBase or
    BindBuffersRange if any value in <buffers> is not zero or the name of an
    existing buffer object (per binding).

    An INVALID_VALUE error is generated by BindBuffersRange if any value in
    <offsets> is less than zero (per binding).

    An INVALID_VALUE error is generated by BindBuffersRange if any value in
    <sizes> is less than or equal to zero (per binding).

    An INVALID_VALUE error is generated by BindBuffersRange if any pair of
    values in <offsets> and <sizes> do not respectively satisfy the
    constraints described for those parameters for the specified target, as
    described in section 6.7.1 (per binding).

    An INVALID_OPERATION error is generated by BindTextures if <first> +
    <count> is greater than the number of texture image units supported by the
    implementation.

    An INVALID_OPERATION error is generated by BindTextures if any value in
    <textures> is not zero or the name of an existing texture object (per
    binding).

    An INVALID_OPERATION error is generated by BindSamplers if <first> +
    <count> is greater than the number of texture image units supported by the
    implementation.

    An INVALID_OPERATION error is generated by BindSamplers if any value in
    <samplers> is not zero or the name of an existing texture object (per
    binding).

    An INVALID_OPERATION error is generated by BindImageTextures if <first> +
    <count> is greater than the number of image units supported by the
    implementation.

    An INVALID_OPERATION error is generated by BindImageTextures if any value
    in <textures> is not zero or the name of an existing texture object (per
    binding).

    An INVALID_OPERATION error is generated by BindImageTextures if the
    internal format of the level zero texture image of any texture in
    <textures> is not found in table 8.33 (per binding).

    An INVALID_OPERATION error is generated by BindImageTextures if the width,
    height, or depth of the level zero texture image of any texture in
    <textures> is zero (per binding).

    An INVALID_OPERATION error is generated by BindVertexBuffers if <first> +
    <count> is greater than the value of MAX_VERTEX_ATTRIB_BINDINGS.

    An INVALID_OPERATION error is generated by BindVertexBuffers if any value
    in <buffers> is not zero or the name of an existing texture object (per
    binding).

    An INVALID_VALUE error is generated by BindVertexBuffers if any value in
    <offsets> or <strides> is negative (per binding).

New State

    None.

New Implementation Dependent State

    None.

Issues

    (1) Regular binding commands such as BindBuffer or BindTexture can be used
        either to bind an existing object or to create and bind a new object.
        Should the multi-bind commands behave similarly?

      RESOLVED:  No.  Multi-Bind commands will only support binding existing
      objects.  They will generate an error if any of the provided objects
      doesn't already exist.

      This extension is intended to provide efficient APIs allowing
      applications to bind multiple objects for rendering in a single command.
      Implementations of these commands are intended to bind the objects to
      consecutive binding points in a loop amortizing function call, name
      space lookup, locking, and other overhead over <N> objects.  Not
      supporting bind-to-create reduces the number of cases that this loop
      needs to handle.

      Even if bind-to-create were supported, it probably wouldn't be very
      useful.  When bind-to-create is used in current single-bind APIs, the
      binding serves two purposes -- to create the object and to bind it for
      use by subsequent "update" APIs defining the state of the new object.
      In a multi-Bind API, it wouldn't be possible to bind more than one of
      the <N> objects for update.

      Additionally, if BindTexture is used to create a texture object, the
      texture type is established based on the <target> parameter (e.g.,
      TEXTURE_2D).  The multi-Bind API for textures doesn't include <target>
      parameters, so we wouldn't know what type of texture to create.

    (2) Should we provide a command binding multiple texture objects of
        different targets (e.g., TEXTURE_2D and TEXTURE_3D) in a single call?
        For example, should you be able to bind three 2D textures to the
        TEXTURE_2D target of image units 1, 2, and 3, as well as binding two
        3D textures to the TEXTURE_3D target of texture image units 0 and 4?

      RESOLVED:  Yes.  The BindTextures() command does not take <target>
      enums.  Instead, the target used for each texture image unit comes from
      the target used when the texture object was created.

    (3) Should we support unbinding objects in a multi-bind command?  If so,
        how does this work for texture objects, where each texture image unit
        has multiple binding points (targets)?

      RESOLVED:  Yes, applications can unbind objects by passing zero in the
      array of object names.  For textures, passing zero will unbind textures
      from all texture targets.

    (4) Should we provide a simple way to unbind objects from a collection of
        contiguous binding points?

      RESOLVED:  Yes, passing a NULL pointer instead of an array of object
      names does an unbind for all binding points.  Basically, it's treated
      like an array of zeroes.

    (5) Should we support multiple bindings of buffer objects using both the
        "BindBufferBase" and the "BindBufferRange" styles?  If so, what name
        should we use for these APIs?

      RESOLVED:  Yes.  BindBuffersBase() is equivalent to a loop repeatedly
      calling BindBufferBase(); BindBuffersRange() is equivalent to a loop
      repeatedly calling BindBufferRange().

      The name choice for the "plural" forms of BindBufferBase and
      BindBufferRange was tricky.  "BindBufferRanges" would have been a fine
      choice for BindBufferRange, but using "BindBufferBases" would have been
      strange since "BindBufferBase" means "bind a buffer from the base of its
      storage (offset zero)".  We considered "BindBuffers" as the plural for
      "BindBufferBase", but decided to use "BindBuffers{Base,Range}".

    (6) If we support multiple bindings using the BindBufferRange style, how
        should the application specify the ranges?

      RESOLVED:  Applications will pass separate arrays of offsets and sizes.

      Alternate options included:

        * a single array where entry 2<N> specifies the offset for binding <N>
          and entry 2<N>+1 specifies the size for binding <N>;

        * defining a new structure type including an offset and a size, and
          accepting an array of <N> structures

    (7) Should we create a "multi-bind" command for specifying vertex buffer
        bindings (those specified via BindVertexBuffer)?

      RESOLVED:  Yes.

    (8) If we add a "multi-bind" command for specifying vertex buffer
        bindings, should we also create a similar command for specifying
        multiple vertex formats (VertexAttrib*Format) in a single call?

      RESOLVED:  No.  The design of ARB_vertex_attrib_binding separated
      vertex buffer bindings from vertex formats, expecting that many
      applications will change bindings frequently but change formats
      relatively infrequently.  While we could create a command specifying
      multiple formats at once, but it would require us to turn several format
      parameters (<size>, <type>, <normalized>, <relativeoffset>) into arrays.

      Additionally, mutable vertex array objects can already be used to make a
      wholesale change of formats and bindings.  An application using a small
      number of formats with a large number of bindings could create a
      separate VAO for each format, and then change bindings with the
      "multi-bind" command.

    (9) Should we provide a command to specify multiple image unit bindings in
        a single command?

      RESOLVED:  Yes.  We decided to support this for completeness, though the
      required number of image units is relatively small (8).

    (10) Should binding an array of buffer objects via BindBuffersBase or
         BindBuffersRange update the generic (non-indexed) binding points for
         <target>?

      RESOLVED:  No.

      In unextended OpenGL 4.3, targets like UNIFORM_BUFFER include both an
      array of indexed bindings used for shader execution as well as a generic
      "non-indexed" binding point that can be used for commands such as
      BufferSubData.  Calling BindBufferBase or BindBufferRange updates two
      binding points -- binding <index> in the array of indexed bindings as
      well as the generic binding point.  Updating both binding points allows
      applications to bind a buffer for manipulation and update in a single
      command.

      For BindBuffersBase and BindBuffersRange, the caller specifies <count>
      separate buffers.  We have specified these commands not to update the
      generic binding point.  Even if we were to update the generic binding
      point, we'd have to pick one arbitrarily.

    (11) Typically, OpenGL specifies that if an error is generated by a
         command, that command has no effect.  This is somewhat unfortunate
         for multi-bind commands, because it would require a first pass to
         scan the entire list of bound objects for errors and then a second
         pass to actually perform the bindings.  Should we have different
         error semantics?

      RESOLVED:  Yes.  In this specification, when the parameters for one of
      the <count> binding points are invalid, that binding point is not
      updated and an error will be generated.  However, other binding points
      in the same command will be updated if their parameters are valid and no
      other error occurs.

    (12) What error should be generated if the <first> and <count> parameters
         specified in multi-bind commands specify a range beyond
         implementation-dependent limits?

      RESOLVED:  INVALID_OPERATION is typically generated when the
      combination of two values is illegal.  INVALID_VALUE would also be
      defensible.

    (13) How are the <offsets> and <sizes> parameters of BindBuffersRange used
         if <buffers> is NULL?

      RESOLVED:  We specify that these parameters are ignored when buffers
      is NULL, so that applications can unbind a range of buffers with:

        BindBuffersRange(target, 0, 8, NULL, NULL, NULL);

    (14) Should we provide a "multi-bind" API to attach multiple textures to
         the color attachments of a framebuffer object?  Should we add an API
         populating all attachments at once?

      RESOLVED:  No.  We could consider an API like:

        void FramebufferColorTextures(enum target, uint first, sizei count,
                                      const uint *textures, 
                                      const uint *levels);

      One might omit the <levels> parameter, since level 0 is used most
      frequently, and non-zero levels could still be handled by creating
      spearate views via ARB_texture_view.  If we wanted to be able to specify
      the full set of attachments at once, we could have:

        void FramebufferTextures(enum target, sizei count,
                                 const uint *colorAttachments,
                                 const uint depthAttachment,
                                 const uint stencilAttachment);

      This API effectively omits the <first> argument and always starts at
      zero.  The "all attachments" API could be handled in OpenGL today by
      using separate framebuffer objects for each attachment combination.
      However, for applications that work with various combinations of
      attachments but don't already have a notion of "attachment sets" to map
      to framebuffer objects, caching different attachment combinations is
      somewhat unwieldy.

    (15) Should we provide a multi-bind API that binds pairs of textures and
    samplers to a set of consecutive texture image units?

      RESOLVED:  No.  We could provide a command such as:

        void BindTexturesSamplers(uint first, sizei count,
                                  const uint *textures, 
                                  const uint *samplers);

      that would be roughly equivalent to:

        BindTextures(first, count, textures);
        BindSamplers(first, count, samplers);

      If we did this, we'd have to decide how it would interact with the error
      semantics in issue (11).  If we have an error generated because of an
      invalid texture for a given unit, would the sampler state for that unit
      still be updated if the sampler provided were valid?  Since we chose not
      to support this feature, we don't need to address this question.

    (16) When binding a non-zero texture to a texture image unit, should
         BindTextures implicitly unbind the textures bound to all other
         targets of the unit?

      RESOLVED:  No.

      This approach was considered to behave similarly to the proposed
      behavior for binding zero in a multi-bind API, where it unbinds any
      bound texture for all targets.  Applications using BindTextures
      exclusively would never have more than one texture bound to the targets
      of a texture image unit.  A driver implementation might optimize for
      this behavior by having a single "primary" binding point for each
      texture unit (used by this API) and then "backup" binding points for the
      other targets (used by BindTexture).  This API would update the
      "primary" binding point but would only need to touch the "backup"
      binding points if something were bound there via BindTexture.  However,
      BindTexture would still be available and is commonly used today, so
      there would probably be little benefit.

    (17) For the BindTextures API, should the <first> parameter be an unsigned
         integer (0) or an enum (GL_TEXTURE0)?

      RESOLVED:  Use an integer unit number.

    (18) The BindImageTexture API not only binds a texture to an image unit,
         but also sets several additional pieces of state associated with an
         image unit (level, layered or not, selected layer, and image unit
         format).  How should this state be set?  Should we provide separate
         arrays for each extra parameter?

      RESOLVED:  Use "default" values for each image unit.  When unbinding
      textures, reset the state to API defaults (level zero, non-layered,
      layer zero, and R8 format).  When binding textures, bind all layers of
      level zero and take the format from the internal format of the texture
      level being bound.  Setting <layered> to TRUE in this case is not the
      default state, but it seems like the best default choice for cube map or
      array textures.  For textures without layers, the <layered> parameter
      has no effect, so this doesn't cause any problems with other targets
      like TEXTURE_2D.

      If an application wants to bind levels other than zero, select
      individual layers of a level for array textures, or use a format
      different from that of the texture, it will be necessary to do
      individual bindings via BindImageTexture.

    (19) If a texture bound to an image unit via BindImageTextures doesn't
         have a defined texture image (i.e., width = height = 0 for 2D
         textures), what internal format is associated with the binding?

      UNRESOLVED:  We will generate INVALID_OPERATION if there is no defined
      texture image.

      Note that even if a texture level has no texels defined, there is still
      an <internalformat> associated with the level, which can be queried with
      GetTexLevelParameter.  That value could be used, but it would still have
      to be checked to see if it's valid for image loads and stores.
      BindImageTexture doesn't accept all possible <format> enums.
      Additionally, the default internal format is profile-dependent:  core
      uses "RGBA", compatibility uses "1" (from OpenGL 1.0, meaning
      LUMINANCE).  Neither is accepted by BindImageTexture, though RGBA might
      be mapped internally by a driver to an internal format like RGBA8 that
      is accepted.

      Given the potential confusion over the internal format for zero-sized
      images and default internal formats, it's best to just not accept
      textures without defined images.

    (20) The BindBuffersRange and BindVertexBuffers accept arrays of "intptr"
         and "sizeiptr" values, which will have different sizes on 32- and
         64-bit architectures.  Is there any problem here?

      RESOLVED:  The API is fine.  Application developers will need to be
      careful to use the correct data type for the arrays it passes to these
      commands.  If the array passed to <offsets> is an array of "int" instead
      of "intptr", that code will typically work fine when compiled on 32-bit
      architectures if "int" types are stored as 32-bit values.  But if the
      same code is compiled for a 64-bit architecture, the array will be too
      small.  We expect that compilers will generate warnings and/or errors
      if the caller passes a pointer to the wrong type.

    (21) In the compatibility profile, can multi-bind commands be included in
         display lists?

      RESOLVED:  No.

    (22) What error should be generated when one of the names passed to a
         multi-bind command is not the name of an existing object?

      UNRESOLVED:  INVALID_OPERATION.  For the core profile, as well as for
      object types created since OpenGL 3.1, we have spec errors like the
      following for BindTexture:

        An INVALID_OPERATION error is generated if <texture> is not zero or a
        name returned from a previous call to GenTextures, or if such a name
        has since been deleted.

      In issue (1), we decided that the multi-bind commands could not be used
      to create objects, whether or not the object names had previously been
      returned by commands like GenTextures.  The errors we require for the
      multi-bind commands are different from the BindTexture language quoted
      immmediately above only in the sense that the multi-bind will
      additionally throw an error if a texture name has been generated by
      GenTextures but the underlying texture object hasn't yet been created.
      However, the errors are similar enough that they should both throw the
      same error code (INVALID_OPERATION).


Revision History

    Revision 11, August 16, 2013 (Jon Leech)
      - Typo fix for BindBuffers* "offsets and strides" -> "offsets and
        sizes" (Bug 10685).
    Revision 10, July 21, 2013 (Jon Leech)
      - Specify that multibind commands are equivalent to repeated calls to
        the corresponding single bind commands except that objects are not
        created if they do not exist, matching issue 1. The other single
        bind commands do not create objects so this clarification is not
        needed for them (Bug 10486).

    Revision 9, May 30, 2013 (Jon Leech)
      - Fix typo for <offsets> "less than to zero" -> "less than zero". Use
        "<first> *through* <first> + <count> - 1" consistently.

    Revision 8, May 28, 2013
      - Change the error thrown when an object name passed to a multi-bind
        command doesn't yet exist from INVALID_VALUE to INVALID_OPERATION 
        (bug 10264).
      - Disallow the use of multi-bind commands in display lists (bug 10322).
      - Change the <count> parameter in multi-bind commands to use the type
        "sizei" to be consistent with other GL commands accepting a <count>
         parameter (bug 10323).
      - Clarify that passing NULL in arguments like <buffers> only affect
        bindings <first> through <first>+<count>-1 (bug 10289).
      - In the errors section for multi-bind commands, clarify which errors
        apply to only a single binding and which apply to the entire call (bug
        10289). 
      - Clarify in the spec language that BindImageTextures sets <access> to
        READ_WRITE for all bindings, which was already in the pseudocode (bug
        10289).
      - Use the term "general buffer binding" in spec language stating that
        BindBuffersBase and BindBuffersRange only affect numbered binding
        points (bug 10289).
      - Add issues (21) and (22).

    Revision 7, May 18, 2013
      - Fix typo in the description of BindSamplers.

    Revision 6, May 17, 2013
      - Modify the pseudocode for BindTextures to add in TEXTURE0 to the
        value passed to ActiveTexture, since it takes an enum and not an
        integer.

    Revision 5, May 10, 2013
      - Define lookupInternalFormat in pseudocode example.

    Revision 4, May 2, 2013
      - Renamed entry points for buffer bindings from BindBuffers() and
        BindBufferRanges() to BindBuffersBase() and BindBuffersRange(),
        respectively.
      - Add an INVALID_OPERATION error if a non-zero texture passed to
        BindImageTextures() does not have a defined image array.
      - Add an "unless otherwise noted" qualification to the general spec rule
        that commands producing errors do not modify the GL state.  Multi-bind
        commands have special error behavior discussed in issue (11).
      - Mark issues resolved based on previous spec reviews.
      - Added issue (20).

    Revision 3, April 19, 2013
      - Add a BindImageTextures API to bind a collection of textures to image
        units (for shader image loads/stores).
      - Fix the spec to consistently use the parameter name <first> to
        identify the first binding point to update.
      - Add new issues.

    Revision 2, January 20, 2013
      - Fix various specification errors.
      - Add an issue about whether we should provide a multi-bind API for
        framebuffer object attachments.

    Revision 1, January 18, 2013
      - Initial revision.
