Structs

Oliver Hunt oliver at apple.com
Thu Jun 3 14:42:01 PDT 2010


On Jun 3, 2010, at 2:19 PM, Brendan Eich wrote:

> On Jun 2, 2010, at 4:43 PM, Oliver Hunt wrote:
> 
>> I feel this proposal is incredibly complicated for basically the single use case of WebGL.  The majority of use cases for typed arrays are for homogenous element types, and I believe most of what WebGL wants could be achieved simply by use of homogeneously typed arrays that were stepped in a way to avoid aliasing (this would not be complicated from either implementation or specification PoV).  The usability would likely be better than the current webgl model, it wouldn't require aliasing, and it would require such a complicated addition to the language.
> 
> It would help for the WebGL use case to be simplified to unify typed arrays and array buffers, eliminating aliasing and requiring monotyped arrays.
> 
> But IIRC WebGL folks other than yourself (who should please speak up ;-) can't take the hit of, e.g. (r << 24) | (g << 16) | (b << 8) | a and then a 32-bit store via assignment to the "rgba" element of what is ideally a typed array of {x, y, z: uint32; r, g, b, a: uint8} structs (to abuse syntax further), but which per your suggestion above would have to be a uint32 array with x, y, z, and rgba elements stored in sequence.

My proposal would have you do something along the lines of:
buffer = new ArrayBuffer({x, y, z: uint32; r, g, b, a: uint8} ) // using your abused syntax

producing an object where you would do:
buffer.x[i] = ...;
buffer.y[i] = ...;
...
buffer.r[i] = ...;
buffer.g[i] = ...;

etc

> This could all be "optimization", an implementation issue. Except WebGL needs speed, and this need is evident in the semantics of proposals such as typed arrays.
> 
> Ignoring all such optimization guarantees, the shift and OR code is ugly and verbose. So there's a usability argument to be made for arrays of structs, if not typed arrays as proposed.

I'm not sure where this shift/or stuff comes from?

> 
> As your amusing ES5 metaprogramming code shows, we could support arrays of structs using objects, and leave optimization out of the spec. In doing this we'd be preserving the "b = a[i]; b.x = 42; assert(a[i].x === 42)" behavior.
> 
> We would break "a[j] = a[i]; a[j].x = 42; assert(a[i].x === 42)" for j != i and j < a.length. But perhaps that is not a useful equivalence. Or we could require an explicit copy operation to assign from a[i] to a[j], or throw an error (but the last seems gratuitous since one can introduce a temporary b as workaround).
> 
> Implicit struct copy seems worse than reified object as fat-pointer. Implicit copying could be quite expensive, even if optimized away for "a[i].x" but not "b = a[i]".
> 
> Bottom line: it still seems to me that the WebGL use-case is C-like (GL was a C API back in the day), and wants arrays (C vectors) of structs that are allocated in-line and packed full of machine types, and possibly even sub-structs or sub-typed-arrays. Vlad averred as much recently.
> 
> The current typed array views into array buffers, besides reminding Tucker of Common Lisp "displaced arrays", smell of Fortran common blocks holding overlayed vectors. Surely we can do better!

My intention was that you end up with a "struct of arrays" rather than an "array of structs" -- internally the implementation would be using flat storage in the form requested.  The exposed accessor for a given field array would be something akin to

return toJSValue(*(MachineType*)(data + index * structSize + fieldOffset))

--Oliver



More information about the es-discuss mailing list