Problem: Passing a ByteBuffer wrapping a byte[] containing image data into GLES20.glTexImage2D(...) is working for me if and only if the ByteBuffer has no offset - otherwise (if there's an offset set) it crashes unhelpfully with something like:
Fatal signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 0x61616162636575 in tid 32016 (GLThread 4912), pid 31806
Background: I have a single byte[] of YUV (I420) data for a 720p image - and I need to read this out as 3 separate ByteBuffers to pass to an OpenGL shader which has 3 different sampler2D channels (1 channel per buffer).
Ideally, since all the information is there in memory, I would create three ByteBuffers wrapping different parts of the byte[] like this:
ByteBuffer yBuffer = ByteBuffer.wrap(rawYUVData, 0, yBufferSize);
ByteBuffer uBuffer = ByteBuffer.wrap(rawYUVData, yBufferSize, uBufferSize);
ByteBuffer vBuffer = ByteBuffer.wrap(rawYUVData, yBufferSize+uBufferSize, uBufferSize);
And then in my renderer code, I call OpenGL glTexImage2D three times also:
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, yTexDataHandle);
GLES20.glTexImage2D(GLES20.GL_TEXTURE_2D, 0, GLES20.GL_LUMINANCE, imgWidth, imgHeight, 0, GLES20.GL_LUMINANCE, GLES20.GL_UNSIGNED_BYTE, yBuffer);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, uTexDataHandle);
GLES20.glTexImage2D(GLES20.GL_TEXTURE_2D, 0, GLES20.GL_LUMINANCE, uWidth, uHeight, 0, GLES20.GL_LUMINANCE, GLES20.GL_UNSIGNED_BYTE, uBuffer);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, vTexDataHandle);
GLES20.glTexImage2D(GLES20.GL_TEXTURE_2D, 0, GLES20.GL_LUMINANCE, uWidth, uHeight, 0, GLES20.GL_LUMINANCE, GLES20.GL_UNSIGNED_BYTE, vBuffer);
This is crashing. I can fix the crash just fine by copying the contents of the above uBuffer and vBuffer into new byte[]s, then rewrapping the ByteBuffers over the new arrays.
But I'm copying data needlessly, and 30x per second.
Can I not wrap ByteBuffers over the contiguous byte[], with offsets, and use these in OpenGL for some reason? Do I really have to copy all the time?
- I've checked it's not an issue in my shader file, by removing the calls to
texture2D()that involve the offending samplers. - Even just adding an offset of 1 to my construction of
yBuffer, and it crashes where with 0 it works fine. (rawYUVData.length is always > yBufferSize + 1)